Mustache.js: рд░рд┐рдЯрд░реНрдирд┐рдВрдЧ рдЯреЗрдореНрдкреНрд▓реЗрдЯ рд╡реИрд░рд┐рдПрдмрд▓ рдирд╛рдо

рдХреЛ рдирд┐рд░реНрдорд┐рдд 31 рджрд┐рд╕ре░ 2015  ┬╖  12рдЯрд┐рдкреНрдкрдгрд┐рдпрд╛рдБ  ┬╖  рд╕реНрд░реЛрдд: janl/mustache.js

рдирдорд╕реНрддреЗ! рдпрд╣ рдПрдХ рдЕрдЬреАрдм рдЕрдиреБрд░реЛрдз рд╣реИ рд▓реЗрдХрд┐рди рдХреНрдпрд╛ рд╕реНрдЯреНрд░рд┐рдВрдЧ рдХреА рд╕рд░рдгреА рдпрд╛ рдСрдмреНрдЬреЗрдХреНрдЯ рдХреЗ рд░реВрдк рдореЗрдВ рдЗрдирдкреБрдЯ рдЪрд░ рдХреА рд╕реВрдЪреА рд╡рд╛рдкрд╕ рдХрд░рдиреЗ рдХреЗ рд▓рд┐рдП рд╡реИрд╕реЗ рднреА рд╣реИ? рдореЗрд░реЗ рдХреЛрдб рдореЗрдВ рдХреЛрдб рдЬрдирд░реЗрд╢рди рдлрд╝рдВрдХреНрд╢рди рдХреЗ рд▓рд┐рдП, рдореБрдЭреЗ рдЗрдирдкреБрдЯ рдХреА рдПрдХ рд╢реНрд░реГрдВрдЦрд▓рд╛ рдХреЛ рдореИрдк рдХрд░рдиреЗ рдХреА рдЖрд╡рд╢реНрдпрдХрддрд╛ рд╣реИ
рдПрдХ рдореВрдВрдЫ-рдЯреЗрдореНрдкрд░реНрдб рд╕реНрдЯреНрд░рд┐рдВрдЧред рдЗрдирдкреБрдЯ рд╡реЗрд░рд┐рдПрдмрд▓реНрд╕ рдХреЛ рдЯреЗрдореНрдкреНрд▓реЗрдЯрд┐рдВрдЧ рд╡реЗрд░рд┐рдПрдмрд▓реНрд╕ рдХреЗ рд╕рдорд╛рди рд╣реА рдирд╛рдо рджрд┐рдпрд╛ рдЧрдпрд╛ рд╣реИ рдФрд░ рдЙрдиреНрд╣реЗрдВ рдкреВрд░реА рддрд░рд╣ рд╕реЗ рдЫрд╛рдпрд╛/рдорд╛рдирдЪрд┐рддреНрд░рд┐рдд рдХрд░реЗрдЧрд╛ рдФрд░ рдХреНрдпреЛрдВрдХрд┐ рдЗрд╕реЗ рд╕реНрд╡рдЪрд╛рд▓рд┐рдд рд░реВрдк рд╕реЗ рдХрд░рдиреЗ рдХреА рдЖрд╡рд╢реНрдпрдХрддрд╛ рд╣реИ, рдЗрд╕рд▓рд┐рдП рдЕрдЬреАрдм рдЕрдиреБрд░реЛрдзред рдореЗрд░рд╛ рдХреНрдпрд╛ рдорддрд▓рдм рд╣реИ рдЗрд╕рдХрд╛ рдПрдХ рдЙрджрд╛рд╣рд░рдг рдпрд╣рд╛рдВ рджрд┐рдпрд╛ рдЧрдпрд╛ рд╣реИ:

рдПрдХ рдлрд╝рдВрдХреНрд╢рди рдХреЛ рдорд╛рдирддреЗ рд╣реБрдП Mustache.getTemplateVariablesListAsObject

var pycode = <see below>
Blockly.JavaScript['math_foo'] = function(block) {
  var value_name = Blockly.JavaScript.valueToCode(block, 'NAME', Blockly.JavaScript.ORDER_ATOMIC);
// result would be something like: {value_name: value_name}
var inputList =  Mustache.getTemplateVariablesListAsObject(pycode)

  var code = Mustache.render(pycode,  inputList)
  return code;
};
def hello(foo):
  print foo
hello({{value_name}})

рдореИрдВ рдЗрд╕ рдкрд░ рдПрдХ рдШрдВрдЯреЗ рд╕реЗ рдЕрдзрд┐рдХ рд╕рдордп рд╕реЗ рд╕реЛрдЪ рд░рд╣рд╛ рд╣реВрдВ рдФрд░ рдореБрдЭреЗ рдЕрднреА рднреА рдРрд╕рд╛ рдХрд░рдиреЗ рдХрд╛ рдмреЗрд╣рддрд░ рддрд░реАрдХрд╛ рдирд╣реАрдВ рдорд┐рд▓ рд░рд╣рд╛ рд╣реИред рд╡рд╛рд╕реНрддрд╡ рдореЗрдВ рдЖрднрд╛рд░реА рд╣реЛрдВрдЧреЗ рдпрджрд┐ рдЖрдк рдХреБрдЫ рд╡реИрдХрд▓реНрдкрд┐рдХ рддрд░реАрдХреЛрдВ рдЖрджрд┐ рдХреА рдкреЗрд╢рдХрд╢ рдХрд░ рд╕рдХрддреЗ рд╣реИрдВред

рд╕рдмрд╕реЗ рдЙрдкрдпреЛрдЧреА рдЯрд┐рдкреНрдкрдгреА

рдХреЗрд╡рд▓ рд╢реАрд░реНрд╖ рд╕реНрддрд░ рдкреНрд░рд╛рдкреНрдд рдХрд░рдиреЗ рдХрд╛ рд╕рд░рд▓ рдЙрдкрд╛рдп:

Mustache.parse(template).filter(function(v) { return v[0] === 'name' || v[0] === '#' || v[0] === '&' } рдореИрдк (рдлрд╝рдВрдХреНрд╢рди (рд╡реА) {рд░рд┐рдЯрд░реНрди рд╡реА [1];});

рд╕рднреА 12 рдЯрд┐рдкреНрдкрдгрд┐рдпрд╛рдБ

рдЕрдЧрд░ рдореИрдВ рдЖрдкрдХреЛ рд╕рд╣реА рдврдВрдЧ рд╕реЗ рд╕рдордЭ рд░рд╣рд╛ рд╣реВрдВ рддреЛ рдЖрдкрдХреЛ рдРрд╕рд╛ рдХреБрдЫ рдЪрд╛рд╣рд┐рдП

var myTemplate = "{{foo}} is {{bar}}";
var variableNames = Mustache.VariableNames(myTemplate) // ['foo', 'bar']

рдпрд╣ рдорд╛рди рд░рд╣рд╛ рд╣реИ рдХрд┐ VariableNames рдЧрдпрд╛ рдФрд░ рдЯреЗрдореНрдкрд▓реЗрдЯ рд╕реЗ рд╕рднреА рдЪрд░ рдирд╛рдо рд╡рд╛рдкрд╕ рдХрд░ рджрд┐рдПред рдпрджрд┐ рдЖрдк рдпрд╣реА рдЪрд╛рд╣рддреЗ рд╣реИрдВ рддреЛ рдЖрдк рд╢рд╛рдпрдж рдореВрдВрдЫ рд▓реЗрдЦрдХ рдкрд░ рдЙрдЬрд╛рдЧрд░ parse рдлрд╝рдВрдХреНрд╢рди рдХрд╛ рдЙрдкрдпреЛрдЧ рдХрд░рдХреЗ рдХрд╛рд░реНрдпрд╛рдиреНрд╡рдпрди рдХреЛ рд╣реИрдХ рдХрд░ рд╕рдХрддреЗ рд╣реИрдВред

рд╢реБрд░реВ рдХрд░рдиреЗ рдХреЗ рд▓рд┐рдП рдпрд╣рд╛рдВ рдХреБрдЫ рдХреЛрдб рджрд┐рдпрд╛ рдЧрдпрд╛ рд╣реИ:

var results = Mustache.parse('{{foo}} is {{bar}}')
                       .filter(function(v) { return v[0] === 'name' })
                       .map(function(v) { return v[1]; });

console.log(results) // ["foo", "bar"]

рдзреНрдпрд╛рди рджреЗрдВ рдХрд┐ рдЗрд╕рдХреЗ рдПрдХ рдЕрдиреБрднрд╡рд╣реАрди рд╕рдВрд╕реНрдХрд░рдг рдХреЛ рд▓рд╛рдЧреВ рдХрд░рдирд╛ рд╕рдВрднрд╡ рд╣реИ, рд▓реЗрдХрд┐рди рд╕рднреА рдЯреИрдЧ рдирд╛рдореЛрдВ рдХреЛ рд╕реНрдкрд╖реНрдЯ рд░реВрдк рд╕реЗ рдирд┐рдХрд╛рд▓рдиреЗ рдХрд╛ рдХреЛрдИ рддрд░реАрдХрд╛ рдирд╣реАрдВ рд╣реИ, рдХреНрдпреЛрдВрдХрд┐ рдЗрд╕ рддрд░рд╣ рдХреА рдЪреАрдЬреЗрдВ:

{{# foo }}
  * {{ bar }}
{{/ foo }}

... рдХрд╛ рдорддрд▓рдм рдпрд╛ рддреЛ {foo: {bar: 'baz'}} _or_ {foo: true, bar: 'baz'}} рд╣реЛ рд╕рдХрддрд╛ рд╣реИред

@bobthecow рдЗрд╕ рдкрд░рд┐рд╕реНрдерд┐рддрд┐ рдореЗрдВ рдкреВрд░реА рддрд░рд╣ рд╕реЗ рд╕рд╣реА рд╣реИред рдореИрдВрдиреЗ рдЬреЛ рдЙрджрд╛рд╣рд░рдг рджрд┐рдпрд╛ рд╣реИ рд╡рд╣ рдХреЗрд╡рд▓ рд╕рднреА рдкрд╣рдЪрд╛рдирдХрд░реНрддрд╛ рдиреЛрдбреНрд╕ рдХреЛ рдЦреАрдВрдЪреЗрдЧрд╛, рдпрд╣ рдкреЗрдбрд╝ рдХреЛ рдкреНрд░рднрд╛рд╡реА рдврдВрдЧ рд╕реЗ рд╕рдорддрд▓ рдХрд░рдиреЗ рд╡рд╛рд▓реА рд╕рднреА рд╕рдВрд░рдЪрдирд╛ рдХреЛ рднреА рд╣рдЯрд╛ рджреЗрдЧрд╛ред

@Romanx @bobthecow рдЖрдкрдХреА рдорджрдж рдХреЗ рд▓рд┐рдП рдзрдиреНрдпрд╡рд╛рдж!

рдХреЛрдИ рджрд┐рдХреНрдХрдд рдирд╣реАрдВ рд╣реИред рдЖрдкрдХреЛ рдХрд╛рдордпрд╛рдмреА рдорд┐рд▓реЗ :)

рдореЗрд░реЗ рдкрд╛рд╕ рдПрдХ рд╕рдорд╛рди рдЕрдиреБрд░реЛрдз рдерд╛, рд▓реЗрдХрд┐рди рд╕рднреА рдкрд░рд┐рд╡рд░реНрддрдиреАрдп рдирд╛рдореЛрдВ рдХреЛ рдЦреЛрдЬрдиреЗ рдХреЗ рд▓рд┐рдП рдкреЗрдбрд╝ рдХреЛ рдкрд╛рд░ рдХрд░рдиреЗ рдХреА рдЖрд╡рд╢реНрдпрдХрддрд╛ рдереАред рд╕реЛрдЪрд╛ рдХрд┐ рдЕрдЧрд░ рдХрд┐рд╕реА рдХреЛ рд╕рдВрджрд░реНрдн рдХреА рдЖрд╡рд╢реНрдпрдХрддрд╛ рд╣реИ рддреЛ рдореИрдВ рдЙрд╕ рд╕рдорд╛рдзрд╛рди рдХреЛ рд╕рд╛рдЭрд╛ рдХрд░реВрдВрдЧрд╛ рдЬрд┐рд╕рдХрд╛ рдореИрдВрдиреЗ рдЙрдкрдпреЛрдЧ рдХрд┐рдпрд╛ рдерд╛ред

var parseTree = Mustache.parse('{{#foo}}{{bar}}{{/foo}} {{baz}}');
var variableList = parseTree.reduce(function flattenVariablesFromParseTree(acc, v){
                    if(v[0] === 'name'){
                      return acc.concat([v]);
                    } else if (v[0] === '#') {
                      return acc.concat(v[4].reduce(flattenVariablesFromParseTree, []));
                    } else {
                      return acc;
                    }
                  }, [])
                  .map(function(v){ return v[1]; });
//variableList: ["bar", "baz"]

@nicluo рдХреНрдпрд╛ рдпрд╣ рднреА рдЕрд╕реНрдкрд╖реНрдЯрддрд╛ рдХреА рд╕рдорд╕реНрдпрд╛ рд╕реЗ рдЧреНрд░рд╕реНрдд рд╣реИ?

рд╣рд╛рдВред рдпрд╣ рднрд╛рд╖рд╛ рдХреА рдХрд▓реНрдкрдирд╛ рдореЗрдВ рдирд┐рд╣рд┐рдд рд╣реИред

рдЕрд╕реНрдкрд╖реНрдЯрддрд╛ рд╕рдорд╕реНрдпрд╛ рджрд┐рд▓рдЪрд╕реНрдк рд╣реИ, рджрд╕реНрддрд╛рд╡реЗрдЬрд╝реЛрдВ рдХрд╛ рдЙрд▓реНрд▓реЗрдЦ рд╣реИ рдХрд┐ рдпрд╣ рдЗрд╕ рд╕рдВрджрд░реНрдн рдореЗрдВ рдореВрд▓реНрдп рдЦреЛрдЬрдиреЗ рдХрд╛ рдкреНрд░рдпрд╛рд╕ рдХрд░реЗрдЧрд╛ рдФрд░ рдлрд┐рд░ рдХреЛрдИ рдорд╛рди рдирд╣реАрдВ рдорд┐рд▓рдиреЗ рдкрд░ рдорд╛рддрд╛-рдкрд┐рддрд╛ рдХреЗ рд╕рдВрджрд░реНрдн рдХреЛ рдЦреЛрдЬреЗрдЧрд╛ред рдереЛрдбрд╝реА рдЬрд╛рдВрдЪ рдиреЗ рдореБрдЭреЗ рдЗрд╕рдореЗрдВ рдорд┐рд▓рд╛:

{{bar}} 
{{#foo}}
  {{bar}} 
  {{#foo}}
    {{bar}} 
    {{#baz}}
      {{no}} 
      {{yes}}
    {{/baz}}
  {{/foo}}
{{/foo}}

var renderString = '{{bar}} {{#foo}}{{bar}} {{#foo}}{{bar}} {{#baz}}{{no}} {{yes}}{{/baz}}{{/foo}}{{/foo}}';
var renderContext = new Mustache.Context({
  bar: 'bar',
  baz: {
    no: 'no'
  },
  foo: {
    bar: 'y',
    foo: {
      bar: 'z',
      yes: 'yes'
    }
  }});

var parseTree = Mustache.parse(renderString);
var variableRefList = [];
var variableNameList = parseTree.reduce(function flattenVariablesFromParseTree(acc, v){
                    // Skip non-name or non-# tags
                    if(v[0] !== 'name' && v[0] !== '#'){
                      return acc;
                    }

                    var paths = [v[1]].concat(this.parents.slice(0).map(function(e){
                      return [e, v[1]].join('.');
                    }));

                    // Pops available context until a value is found
                    var path;
                    while(path = paths.pop()){
                      if(renderContext.lookup(path)){
                        //push to advanced list
                        variableRefList.push(path);
                        contextFound = true;
                        break;
                      }
                    }

                    if(v[0] === 'name'){
                      return acc.concat([v]);
                    } else if (v[0] === '#')  {
                      if(typeof renderContext.lookup(path) === 'object'){
                        this.parents = this.parents.concat([path]);
                      }

                      return acc.concat(v[4].reduce(
                        flattenVariablesFromParseTree.bind({
                          parents: this.parents
                        }), []));
                    }
                  }.bind({parents: []}), [])
                  .map(function(v){ return v[1]; });

//variableNameList: ["bar", "bar", "bar", "no", "yes"]
//variableRefList: ["bar", "foo", "foo.bar", "foo.foo", "foo.foo.bar", "baz", "baz.no", "foo.foo.yes"]
//Mustache.render(renderString, renderContext): bar y z no yes

рдЙрджрд╛рд╣рд░рдг рдмрд╣реБрдд рд╣реА рдХрд╛рд▓реНрдкрдирд┐рдХ рд╣реИ, рдФрд░ рд╕рдВрдХреНрд╖рд┐рдкреНрдд рд░рд╣рдиреЗ рдХреЗ рд▓рд┐рдП рдХрдИ рддрд░рдХреАрдмреЛрдВ рдХрд╛ рдЙрдкрдпреЛрдЧ рдХрд┐рдпрд╛ рдЬрд╛рддрд╛ рд╣реИ, рд▓реЗрдХрд┐рди рдпрд╣ рджрд┐рдЦрд╛рдирд╛ рдЪрд╛рд╣рд┐рдП рдХрд┐ рдкрд╣рд┐рдпрд╛ рдХреЛ рдлрд┐рд░ рд╕реЗ рд╢реБрд░реВ рдХрд░рдирд╛ рдореБрдЭреЗ рдХрд┐рддрдирд╛ рдореБрд╢реНрдХрд┐рд▓ рд▓рдЧрддрд╛ рд╣реИред рдЪрд┐рдпрд░реНрд╕

@Immortalin рдХреНрдпрд╛ рдЖрдк рд╕рдорд╕реНрдпрд╛ рдХреА рдмреЗрд╣рддрд░ рдкрд░рд┐рднрд╛рд╖рд╛ рд╡рд┐рд╕реНрддреГрдд/рдкреНрд░рджрд╛рди рдХрд░ рд╕рдХрддреЗ рд╣реИрдВ? рд╡рд╕реНрддреБрдУрдВ рдореЗрдВ рдиреЗрд╕реНрдЯреЗрдб рдЧреБрдгреЛрдВ рдХреЗ рд╕рд╛рде рдХреНрдпрд╛ рд╣реЛрддрд╛ рд╣реИ? рдХреНрдпрд╛ рдЖрдк рдЕрдзрд┐рдХ рд╕рдВрдкреВрд░реНрдг рдЗрдирдкреБрдЯ рдФрд░ рдЖрдЙрдЯрдкреБрдЯ рдкреНрд░рджрд╛рди рдХрд░ рд╕рдХрддреЗ рд╣реИрдВ?

@dasilvacontin рдЬрд┐рд╕ рдкрд░рд┐рдпреЛрдЬрдирд╛ рдХреЗ рд▓рд┐рдП рдЗрд╕ рд╕реБрд╡рд┐рдзрд╛ рдХреА рдЖрд╡рд╢реНрдпрдХрддрд╛ рд╣реИ рд╡рд╣ рд╡рд░реНрддрдорд╛рди рдореЗрдВ рдЕрдВрддрд░рд╛рд▓ рдкрд░ рд╣реИ рдЗрд╕рд▓рд┐рдП рдореИрдВ рдЗрд╕реЗ рдХреБрдЫ рд╕рдордп рдХреЗ рд▓рд┐рдП рдмрдВрдж рдХрд░рдиреЗ рдЬрд╛ рд░рд╣рд╛ рд╣реВрдВ

рдХреЗрд╡рд▓ рд╢реАрд░реНрд╖ рд╕реНрддрд░ рдкреНрд░рд╛рдкреНрдд рдХрд░рдиреЗ рдХрд╛ рд╕рд░рд▓ рдЙрдкрд╛рдп:

Mustache.parse(template).filter(function(v) { return v[0] === 'name' || v[0] === '#' || v[0] === '&' } рдореИрдк (рдлрд╝рдВрдХреНрд╢рди (рд╡реА) {рд░рд┐рдЯрд░реНрди рд╡реА [1];});

рдХреНрдпрд╛ рдпрд╣ рдкреГрд╖реНрда рдЙрдкрдпреЛрдЧреА рдерд╛?
0 / 5 - 0 рд░реЗрдЯрд┐рдВрдЧреНрд╕

рд╕рдВрдмрдВрдзрд┐рдд рдореБрджреНрджреЛрдВ

zekth picture zekth  ┬╖  18рдЯрд┐рдкреНрдкрдгрд┐рдпрд╛рдБ

kuldeepdhaka picture kuldeepdhaka  ┬╖  9рдЯрд┐рдкреНрдкрдгрд┐рдпрд╛рдБ

connor11528 picture connor11528  ┬╖  3рдЯрд┐рдкреНрдкрдгрд┐рдпрд╛рдБ

barbalex picture barbalex  ┬╖  5рдЯрд┐рдкреНрдкрдгрд┐рдпрд╛рдБ

chlab picture chlab  ┬╖  11рдЯрд┐рдкреНрдкрдгрд┐рдпрд╛рдБ