How would you turn a JavaScript variable into a Template literal?

后端 未结 4 1338
走了就别回头了
走了就别回头了 2020-11-30 15:32

I would like to take text that I generated and stored in a string and use it like a template literal.

var generatedText = \"Pretend this text was generated          


        
相关标签:
4条回答
  • 2020-11-30 15:59

    You should emulate a template literal instead, because letting text from ~somewhere~ run arbitrary JavaScript like a real template literal’s ${} sections can usually isn’t a good idea:

    generatedText.replace(/\$\{variable}/g, variable);
    
    0 讨论(0)
  • 2020-11-30 16:01

    For the general situation, you can use a replacer function to replace every occurrence of ${someProp} with the someProp property on an object:

    const interpolate = (str, obj) => str.replace(
      /\${([^}]+)}/g,
      (_, prop) => obj[prop]
    );
    
    const generatedText = "But I still need to use it as a template it to get ${variable}.";
    const variable = "Successs!!!!";
    
    console.log(interpolate(generatedText, { variable }));

    The regular expression \${([^}]+)} means:

    • \$ - Literal $
    • { - Literal {
    • ([^}]+) First (and only) capture group:
      • [^}]+ - One or more characters which are not }
    • } - Literal }

    Since prop is the property name found in between the brackets, replace with obj[prop] to replace with the desired replacement.

    0 讨论(0)
  • 2020-11-30 16:01

    The interpolate function below is an extended version of the above solution adds support for simple nested object field references, with addition of arrays (e.g.: a[0][2].b.c)

    const interpolate = (str, obj) => {
      return str.replace(/\${([^}]+)}/g, (_, target) => {
        let keys = target.split(".");
        return keys.reduce((prev, curr) => {
          if (curr.search(/\[/g) > -1) {
            //if element/key in target array is array, get the value and return
            let m_curr = curr.replace(/\]/g, "");
            let arr = m_curr.split("[");
            return arr.reduce((pr, cu) => {
              return pr && pr[cu];
            }, prev);
          } else {
            //else it is a object, get the value and return
            return prev && prev[curr];
          }
        }, obj);
      });
    };
    
    let template = "hello ${a[0][0].b.c}";
    let data = {
      a: [
        [{
          b: {
            c: "world",
            f: "greetings"
          }
        }, 2], 3
      ],
      d: 12,
      e: 14
    }
    console.log(interpolate(template, { ...data
    }));

    0 讨论(0)
  • 2020-11-30 16:03

    The interpolate function below is an extended version of this answer that adds support for simple nested object field references (e.g.: a.b.c)

    function interpolate(s, obj) {
      return s.replace(/[$]{([^}]+)}/g, function(_, path) {
        const properties = path.split('.');
        return properties.reduce((prev, curr) => prev && prev[curr], obj);
      })
    }
    
    console.log(interpolate('hello ${a.b.c}', {a: {b: {c: 'world'}}}));
    // Displays 'hello world'

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