tao-test/app/tao/views/js/tpl.js

166 lines
5.4 KiB
JavaScript

/**
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; under version 2
* of the License (non-upgradable).
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*
* Copyright (c) 2013-2019 (original work) Open Assessment Technologies SA (under the project TAO-PRODUCT);
*
*
*/
/**
* ORGINAL VERSION:
* https://github.com/epeli/requirejs-hbs
* Copyright 2013 Esa-Matti Suuronen
* MIT License : https://github.com/epeli/requirejs-hbs/blob/master/LICENSE
*
* MODIFIED VERSION:
* @author Bertrand Chevrier <bertrand@taotesting.com> for OAT SA
* - Minor code refactoring
* - i18n helper has been added
* - dompurify helper has been added
*/
define([
'handlebars',
'i18n',
'lodash',
'lib/dompurify/purify'
], function(hb, __, _, DOMPurify){
'use strict';
var buildMap = {};
var extension = '.tpl';
//register a i18n helper
hb.registerHelper('__', function(key){
return __(key);
});
/**
* Register dompurify helper
*
* https://github.com/cure53/DOMPurify
* with config SAFE_FOR_TEMPLATES: true
* to make output safe for template systems
*/
hb.registerHelper('dompurify', function(context){
return DOMPurify.sanitize(context);
});
/**
* Register join helper
*
* Example :
* var values = {a:v1, b:v2, c:v3};
* Using {{{join attributes '=' ' ' '"'}}} will return : a="v1" b="v2" c="v3"
* Using {{{join values null ' or ' '*'}}} will return : *v1* or *v2* or *v3*
*/
hb.registerHelper('join', function(arr, keyValueGlue, fragmentGlue, wrapper){
var fragments = [];
keyValueGlue = typeof(keyValueGlue) === 'string' ? keyValueGlue : undefined;
fragmentGlue = typeof(fragmentGlue) === 'string' ? fragmentGlue : ' ';
wrapper = typeof(wrapper) === 'string' ? wrapper : '"';
_.forIn(arr, function(value, key){
var fragment = '';
if(value !== null || value !== undefined){
if(typeof(value) === 'boolean'){
value = value ? 'true' : 'false';
}else if(typeof(value) === 'object'){
value = _.values(value).join(' ');
}
}else{
value = '';
}
if(keyValueGlue !== undefined){
fragment += key + keyValueGlue;
}
fragment += wrapper + value + wrapper;
fragments.push(fragment);
});
return fragments.join(fragmentGlue);
});
//register a classic "for loop" helper
//it also adds a local variable "i" as the index in each iteration loop
hb.registerHelper('for', function(startIndex, stopIndex, increment, options){
var ret = '';
startIndex = parseInt(startIndex);
stopIndex = parseInt(stopIndex);
increment = parseInt(increment);
for(var i = startIndex; i < stopIndex; i += increment){
ret += options.fn(_.extend({}, this, {'i' : i}));
}
return ret;
});
hb.registerHelper('equal', function(var1, var2, options){
if(var1 == var2){
return options.fn(this);
}else{
return options.inverse(this);
}
});
// register a "get property" helper
// it gets the named property from the provided context
hb.registerHelper('property', function(name, context){
return (typeof (context[name]) !== "undefined") ? new hb.SafeString(context[name]) : '';
});
// register an 'includes' helper
// it checks if value is in array
hb.registerHelper('includes', function (haystack, needle, options) {
if (_.contains(haystack, needle)) {
return options.fn(this);
}
});
return {
load : function(name, req, onload, config){
extension = extension || config.extension;
if(config.isBuild){
//optimization, r.js node.js version
buildMap[name] = fs.readFileSync(req.toUrl(name + extension)).toString().trim();
onload();
} else {
req(["text!" + name + extension], function(raw){
// Just return the compiled template
onload(function(){
var compiled = hb.compile(raw);
return compiled.apply(hb, arguments).trim();
});
});
}
},
write : function(pluginName, moduleName, write){
var compiled;
if(moduleName in buildMap){
compiled = hb.precompile(buildMap[moduleName]);
// Write out precompiled version of the template function as AMD definition.
write(
"define('tpl!" + moduleName + "', ['handlebars'], function(hb){ \n" +
"return hb.template(" + compiled.toString() + ");\n" +
"});\n"
);
}
}
};
});