Replace string value with javascript object

前端 未结 4 517
清酒与你
清酒与你 2021-01-05 16:43

I am currently making a small module for NodeJs. For which I need a small help.

I will tell it like this. I have a variable with string. It contains a string html va

相关标签:
4条回答
  • 2021-01-05 17:19

    This solution uses template strings to do everything you want.

    This solution has the advantage that, in contrast to the naive roll-your-own regexp-based template replacement strategy as proposed in another answer, it supports arbitrary calculations, as in

    replacer("My name is ${name.toUpperCase()}", {name: "Bob"});
    

    In this version of replacer, we use new Function to create a function which takes the object properties as parameters, and returns the template passed in evaluated as a template string. Then we invoke that function with the values of the object properties.

    function replacer(template, obj) {
      var keys = Object.keys(obj);
      var func = Function(...keys, "return `" + template + "`;");
    
      return func(...keys.map(k => obj[k]));
    }
    

    We define the template using ${} for substitutions (instead of $()), but escaping as \${ to prevent evaluation. (We could also just specify it as a regular string literal, but would then lose multi-line capability).

    var html = `<!DOCTYPE html>
    <html lang="en">
    <head>
      <meta charset="UTF-8">
      <title>Document \${title}</title>  <!-- escape $ -->
    </head>
    <body>
    
      <h1>Test file, \${text}</h1>       <!-- escape $ -->
    
    </body>
    </html>`;
    

    Now things work exactly as you want:

    replacer(html, { "title" : "my title", "text" : "text is this" });
    

    Simple example:

    > replacer("My name is ${name}", {name: "Bob"})
    < "My name is Bob"
    

    Here's an example of calculated fields:

    > replacer("My name is ${name.toUpperCase()}", {name: "Bob"})
    < "My name is BOB"
    

    or even

    > replacer("My name is ${last ? lastName : firstName}", 
        {lastName: "Jones", firstName: "Bob", last: true})
    < "My name is Jones"
    
    0 讨论(0)
  • 2021-01-05 17:19

    Since you are using ES6 template string you can use a feature called 'tagged template strings'. Using tagged template strings you are allowed to modify the output of a template string. You create tagged template string by putting a 'tag' in front of the template string, the 'tag' is a reference to a method that will receive the string parts in a list as the first argument and the interpolation values as remaining arguments. The MDN page on template strings already provides an example template string 'tag' that we can use:

    function template(strings, ...keys) {
      return (function(...values) {
        var dict = values[values.length - 1] || {};
        var result = [strings[0]];
        keys.forEach(function(key, i) {
          var value = Number.isInteger(key) ? values[key] : dict[key];
          result.push(value, strings[i + 1]);
        });
        return result.join('');
     });
    }
    

    You use the 'tag' by calling:

    var tagged = template`<!DOCTYPE html>
    <html lang="en">
    <head>
       <meta charset="UTF-8">
      <title>Document ${'title'}</title>
    </head>
    <body>
    
      <h1>Test file, ${'text'}</h1>
    
    </body>
    </html>`;
    

    Notice that interpolation of variables uses the syntax ${'key'} instead of $(key). You can now call the produced function to get the desired result:

    tagged({ "title" : "my title", "text" : "text is this" });
    

    Run the code example on es6console

    0 讨论(0)
  • 2021-01-05 17:24
    var binddingData=function(id,data){
        var me=this,
            arr=[];
        arr=getControlBindding(id);
        arr.forEach(function(node){
            var content=getBinddingContent(node.getAttribute('DataTemp'),data);
            binddingToHtml(node,content);
        })
    
    }
    var getControlBindding=function(id){
        var me=this;
        return document.querySelectorAll('[DataTemp]');
    }
    
    
    var getBinddingContent=function(temp,data){
        var me=this,
            res='',
            hasNull=false;
        if(temp==null||typeof temp=='undefined'){
                return res;
            }
        res= temp.replace(/\$\{([^\}]+)?\}/g, function($1, $2) { 
            if(data[$2]==null||typeof data[$2]=='undefined'){
                hasNull=true;
            }
            return data[$2]; 
        });
        return hasNull?'':res;
    
    }
    
    var binddingToHtml=function(node,content){
        var me=this;
        if(node.getAttribute('IsDateTime')){
            node.innerText='';//if u want change it to datetime string
            return;
        }
        if(node.getAttribute('AddBr') && content==''){
            node.innerText='';
            var brTag=document.createElement('br');
            node.appendChild(brTag);
            return;
        }
       node.innerText=content;
    }
    

    You use the 'tag' by calling:

    <div DataTemp="${d1}"></div> 
        <div DataTemp="${d2}"></div>
        <div DataTemp="${d3}"></div> 
        <div DataTemp="${d3}+ +${d1}"></div> 
        <div DataTemp="${d3}/${d1}"></div>     
        <div DataTemp="${d4}\${d1}"></div>     
        <div DataTemp="(${d5}\${d1})"></div> 
        <div DataTemp="(${d3}\${d1})"></div>
    

    with data var data={d1:'t1',d2:'t2',d3:'t3'}

    0 讨论(0)
  • 2021-01-05 17:32

    You can use a simple template function using regex,

    var replacer = function(tpl, data) {
      var re = /\$\(([^\)]+)?\)/g, match;
      while(match = re.exec(tpl)) {
        tpl = tpl.replace(match[0], data[match[1]])
        re.lastIndex = 0;
      }
      return tpl;
    }
    

    use like

    var result = replacer(html, { "title" : "my title", "text" : "text is this" });
    

    jsfiddle

    detail here

    EDIT

    Actually as torazaburo mentioned in the comment, it can be refactored as

    var replacer = function(tpl, data) {
        return tpl.replace(/\$\(([^\)]+)?\)/g, function($1, $2) { return data[$2]; });
    }
    

    jsfiddle

    hope this helps

    0 讨论(0)
提交回复
热议问题