Displaying Your Goodie Instant Answer

Making a Cheat Sheet? Skip to the Cheat Sheet Reference.

The final step in every Instant Answer is displaying it to the user. All Instant Answers display in the "AnswerBar", which is the area above the organic search results. The way each Instant Answer is displayed and behaves is determined by a set of display options and events. This document shows you how to set these options for a Goodie.

goodie answerbar

Easy Structured Responses

If your answer requires html templates and special interactions, consider setting display properties.

Many Goodies are simple operations that return a string response. For example, the Flip Text Goodie:

flip text goodie

Displaying such Goodies is easy. Instead of setting display properties, simply return three properties:

  • Input (what the user typed in, perhaps highlighting how it was parsed)
  • Operation (the term for what happened)
  • Result (the final answer)

For example, for the Flip Text Goodie:

flip text goodie diagram

Passing Structured Responses

Here is the return statement of the Flip Text Goodie:

my $result = upside_down($input);

return $result, # text-only Goodie result, for the API
    structured_answer => {
        input     => [html_enc($input)],
        operation => 'Flip text',
        result    => html_enc($result),
    };

The following properties are returned in the structured_answer hash:

input [required, but can be empty] array

  • Make sure to html_enc() any user input to prevent XSS
  • To avoid displaying an input, pass an empty array: [] (see the GUID Goodie)

operation [required] string

  • Stated as a command, e.g. "Calculate", "Flip text", "URL decode", etc.

result [required] string

  • Make sure to html_enc() input to display characters properly
  • Do not pass custom HTML in this string; instead specify a template.

Further Examples

Here are some more Goodies that make use of simple, structured responses:

Setting Display Properties in a Goodie

If your Goodie is very simple, consider passing a structured response instead.

When developing a Goodie, display options can be set either in your backend (Perl) or frontend (JavaScript) code. Most display properties can be set in either. Some Display properties, by their nature, can only be set in the frontend.

Here is a quick summary of the break down of display options:

Display Property Can Set in Perl (Backend) Can Set in JavaScript (Frontend)
id
name
data
meta
templates
view
model
normalize
relevancy
sort_fields
Events

Setting Display Options on the Backend

If your Goodie is very simple, consider passing a structured response instead.

Most options can be defined in the Goodie's backend, the Perl file. These options are set by returning as a hash called structured_answer when the Perl file finishes running. This hash is returned alongside the $plaintext string version of your Goodie result, used for the API):

return $plaintext,
    structured_answer => {
        ...
    };

For an example of how this works, take a look at the final return statement of the BPM to ms Goodie Perl file.

Specifying options in Perl is the most straightforward method, but there are several optional properties that cannot be specified on the server-side. These must be specified in the Goodie's frontend, in a JavaScript file.

The following is a code summary of how display options are set in your Goodie Perl file:

return $plaintext,
    structured_answer => {
        id => String,
        name => String,
        data => Array or Hash (in the case of a single item),
        meta => {
            searchTerm => String,
            itemType => String,

            primaryText => String,
            secondaryText => String,

            sourceName => String,
            sourceLogo => String,
            sourceUrl => String (url),
            sourceIcon => Boolean,
            sourceIconUrl => String (url),

            snippetChars => Integer
        },
        templates => {          
            group => String,
            options => Hash,

            # Note that while the following may reference JavaScript variables, 
            # they are still specified as strings in Perl

            item => String,
            item_custom => String,
            item_mobile => String,

            detail => String,
            detail_custom => String,
            detail_mobile => String,
            item_detail => String,

            variants => Hash,

            elClass => Hash,
        }

        view => String,
        model => String,
    };

For more information on each property and its usage, visit the display options reference.

Setting Goodie Display Options on the Frontend

While most display properties can be set in a Goodie's Perl file, others by their nature must be specified in the frontend part of the code. These are:

To specify any of these, simply create a javascript file in share/goodie/INSTANT_ANSWER_ID/INSTANT_ANSWER_ID.js. For example, using the "BP to ms" Instant Answer as an example (where the id is set to 'bpmto_ms'):

Create a file at share/goodie/bpmto_ms/bpmto_ms.js, which creates a namespace and a build function.

DDH.bpmto_ms = DDH.bpmto_ms || {}; // create the namespace in case it doesn't exist

DDH.bpmto_ms.build = function(ops) {

    return {
        // Specify any frontend display properties here
    };

};

The build function takes ops as an argument; this represents the structured_answer hash from the Perl as a JavaScript object.

Your build function returns an object with any frontend display properties you want to set. For example, you could set an event:

return {
    onShow: function() {
        console.log("onShow for bpmto_ms");
    },
}

Or you could set a normalize function - and so on:

return {
    ...
    normalize: function(item){
        return {
            title: item.heading
        };
    }
}

Additionally, it is worth noting that all of the display options specified in Perl could instead be specified in your JavaScript - if you so desired.

For example:

return {
    ...
    templates: {
        group: 'base',
        detail: false,
        options: {
            // Note that because this is JavaScript, sub-templates are specified
            // as function references rather than strings. 
            content: DDH.bpmto_ms.content
        }
    }
}

Fun with Goodie JavaScript

Goodie's frontend components allow you to do much more than set display properties and events. You may also execute any JavaScript you'd like to do interesting and delightful things.

Continuing from the example above from the BP to ms Instant Answer, we created a JavaScript file at share/goodie/bpmto_ms/bpmto_ms.js. Inside this file, we declare a build function.

Everything returned by your build function is used to extend your structured_answer Perl hash (from your Goodie's .pm file). However, you can use the function to run other JavaScript, making use of JQuery.

DDH.bpmto_ms.build = function(ops) {

    // Execute delightful JavaScript here
    // with access to JQuery 

    return {
        // Specify any frontend display properties here
        onShow: function(){
            // Consider using an event, such as onShow, to run your code at the right time
        }
    };

};

Consider using events as the starting points for your code. You can also create a css file to reference, for example share/goodie/bpmto_ms/bpmto_ms.css.

You might use Goodie JavaScript to create an in-browser game related to certain search results. Or an easter egg, for fun. The community is excited to review pull requests for fun and delightful additions to DuckDuckGo's Instant Answers.