Help:Widgets

From Guild Wars 2 Wiki
Jump to navigationJump to search

The Widgets extension allows the creation of raw HTML pages that can be embedded (similarly to templates) in normal wiki pages. You do this by creating pages in the Widget namespace. They avoid the security problems of raw HTML in editable wiki pages because the privilege to edit in the Widget namespace is managed.

MediaWiki Extension:Widgets

Overview[edit]

General[edit]

  • As mentioned above, only widget editors and sysops can edit widgets to prevent malicious code from being added.
  • Widgets run at the same time as the asyncronous ResourceLoader modules, e.g. jQuery, and will have to wait for the document to be ready before trying to use ResourceLoader dependencies.
  • Parameters can be passed to widgets using SmartySyntax. For example, you could pass a parameter named "clear" to a widget by including the following within the widget code: <!--{$clear|default:both|escape:'html'}-->, which would be replaced with the value left for example if used like {{#Widget:widget name|clear=left}}.
  • Use a counter to ensure that scripts and styles defined by the widget will only be included once, even if the widget is used multiple times on a single page.
  • An invalid widget will return a red error string along the lines of "Error in Widget:Widget name." Some smarty parameters will have to be escaped in order to produce a valid widget. Likewise invalid code will produce the same message.
  • After editing a widget page, it will need to be purged to generate the latest scripts.

Technical point[edit]

  • The widget extension effectively converts a widget page into a php template file that lives in the compiled_templates folder.
  • If there are any errors within the widget template, they will manifest themselves as PHP errors. That error will be added to the log.
  • The PHP error may not be visible to regular users since the live wiki operates with PHP errors hidden by default, however if you were to copy the exact widget code onto a fresh installation of MediaWiki, you would see PHP errors plastered in amongst the widget results.
  • In April 2020 there was an issue identified (a bug in the underlying template engine "smarty"), which had lead to the PHP error log file becoming so large that all the wiki disk space was exhausted, preventing files from being uploaded. Additionally widgets could not be recompiled after purging, leaving broken widgets everywhere. In order to avoid a repeat of this event, it is important that all smarty syntax is carefully checked for the following:
    • Empty parameter handling
      • Does the template use <!--{if isset($varname1) && isset($varname2)}--><!--{else}--><!--{/if}--> at the start for any required parameters?
      • Do user-exposed parameters have default values defined using the default: modifier?
    • User input validation
      • Are bad parameter inputs escaped to avoid malicious usage of widgets using the escape: modifier? (javascript/html/htmlall)
    • Good practice example: <!--{$varname1|default:''|escape:'javascript'}-->

API specific notes[edit]

  • If the language token, i.e. &lang=en, is not specified, it uses the browser's language. All widgets should use a language token to prevent unexpected results.
  • Queries made by wiki widgets also have &wiki=1, which does nothing but theoretically could allow ArenaNet to figure out how much traffic the API receives from wiki pages.
  • Results are not cached, but widget code is cached.

Typical widget page layout[edit]

<noinclude>
== Description ==
This widget performs function X Y Z. The widget is used by [[Template:Widget name ABC]].

=== Parameters ===
; wikiparameter1
: wikiparameter1 description

== Example ==
{{#Widget:Widget name|wikiparameter1=value1}}

[[Category:Widgets]]

</noinclude><includeonly>
<!-- HTML to be inserted by widget -->
<div class="widgetcontainer"><!--{$wikiparameter1|default:'Is it me you are looking for?'|escape:'htmlall'}--></div>

<!--{counter assign="WidgetName_counter" name="WidgetName_counter"}--><!--{if $WidgetName_counter eq 1}-->
<style>/* Custom CSS rules for the widget */</style>
<script>/* Custom JavaScript code for the widget */</script>
<!--{/if}--></includeonly>

Code to wait for the document to be ready[edit]

// defer script execution until the mediawiki loader and jQuery are available

// DEFER LOADING SCRIPT UNTIL JQUERY IS READY. WAIT 40MS BETWEEN ATTEMPTS.
function defer(method) {
    if (window.jQuery && mw && mw.loader) { // can remove the mw portion if not using mediawiki functions
        method();
    } else {
        setTimeout(function() { defer(method) }, 40);
    }
}

// INITIALISATION
defer(function () {
    console.log('mw.loader and jQuery are available now', $);

    // to load external scripts (here to load User:Example/common.js)
    mw.loader.load('//wiki.guildwars2.com/index.php?action=raw&ctype=text/javascript&title=User:Example/common.js');

    // to depend on other mediawiki modules
    mw.loader.using('mediawiki.api.parse', function () {
        var api = new mw.Api();
        api.parse('[[Sandbox]]').done(function (result) {
            console.log('Parsed HTML', result);
        });
    });
});

Widgets on this wiki[edit]

See also: Category:Test widgets, Category:Obsolete widgets

Notes[edit]