0

I have a text file like this:

// start file

var nameVar1 = '';
// var nameVar1 = '';

var otherVar1= "test1";

var nameVar2 ="test2",
    otherVar2 =  'test3';
    
var nameVar3    =    true;

var     otherVar3 = false   ;

var objName = {
    test: 'test'
};

var expression = nameVar1 + nameVar2;

// comment

for(var test in templateConfig) {
  if( templateConfig ){ defaultLang = langParam; }
}

// end file

I am trying to find all the variables that have fields and replace them with interpolation and get an example below:

// start file

{{nameVar1}}
// var nameVar1 = '';

{{otherVar1}}

{{nameVar2}}
{{otherVar2}}
    
{{nameVar3}}

{{otherVar3}}

{{objName}}

var expression = nameVar1 + nameVar2;

// comment

for(var test in templateConfig) {
  if( templateConfig ){ defaultLang = langParam; }
}

// end file

I got a regular expression but it doesn't work very well because it also finds variables in loops or expressions

const regex = /(?<!\/\/\s*?)(?:var|let|const)(?:\s+)(.*?)(?:\s+)?=\s?(?:.*?);/gms;
const subst = `{{$1}}`;
const result = str.replace(regex, subst);

https://regex101.com/r/RVhsBl/2

Firelight
  • 1
  • 2
  • 1
    Why would you want to do any of this? Using regex on a with programming code? You should be using a parser *at the very least*. And replacing text in the file? I suspect you have [an XY problem](https://meta.stackexchange.com/questions/346503/what-is-the-opposite-of-the-xy-problem). – VLAZ Oct 02 '20 at 17:25
  • 2
    Templating javascript seems like an idea bound to have tons of bugs. – Taplar Oct 02 '20 at 17:26
  • @Taplar having worked with templated code files (not JS, though), I can say that it is *also* very unwieldy and is likely to create entirely new problems for you because all your generated code would do the same stuff, so stuff like adding a property to a templated classes adds it to *all other* generated code, whether you want it or not. – VLAZ Oct 02 '20 at 17:50
  • There are various configuration files that ordinary people without programming knowledge work with, files of mixed content html and javascript. The idea is to make an editor where fields can be edited independently of the code ... – Firelight Oct 02 '20 at 18:02
  • Sounds like you need to just allow people to edit the configuration and then you need to make *you code* use that configuration to operate. Not generate code *based on* the configuration. – VLAZ Oct 02 '20 at 18:04
  • These configurations already exist, they are made by different programmers and for different purposes. The editor must find all fields and objects and replace them with new ones without breaking the existing code. – Firelight Oct 02 '20 at 18:11

2 Answers2

0

First you would have to breakdown the var comma delimited declaration here:

// find
// var x = [{whatever: true}, true, false], y = 'something', z = {x: {john: true}, y: true}

// replace this with
// var x = [{whatever: true}, true, false];
// var y = 'something';
// var z = {x: {john: true}, y: true}

Then you could use this approach: You could extract data between the var and the semicolon like this. That way you don't have to know about all the possible variable values - true, false, undefined, null, 3533, etc....

// Then:
// safety - put a semicolon before each var, just in case they don't exist at end of line
str = str.replace(/(^|\s*)var /g, '$1;var ');

// extract data between var and ;
// var x   = anything except semicolon;
const regex = /(^|\n)\s*var +([\$\_a-z]\w*) *\=[^\;]*\;/gi;


const result = str.replace(regex, `{{$2}}`);

// remove duplicate semicolon as cleanup. Probably not needed since the above will have replaced them all.
str = str.replace(/\;var /g, 'var');
Steve Tomlin
  • 3,391
  • 3
  • 31
  • 63
0

I was able to compose a regular expression that satisfies my requests

const regex = /(?<!\/\s*?)\bvar\b\s+(.*?)\s*?=\s*?['"{ft].*?['"}e]\s*?;/ gsmi;
const subst = `{{$1}}`;
const result = str.replace(regex, subst);
  • (?<!\/\s*?) -exclude matches if there is a comment before them // var template = test
  • \bvar\b\s+ -Search var followed by one or more spaces
  • (.*?)\s*?=\s*? -in brackets the name of the variable before the equals sign and after may be spaces
  • ['"{ft] -look for an opening quotation mark ' or " or a parenthesis { or the first letters of the words true or false
  • .*? -any character, these are the values ​​of the variable
  • ['"}e] -look for the closing quotation mark ' or " or parenthesis } or the last letters of the words true or false
  • \s*?; -are looking for ; before which there may be spaces

then we can make additional checks for errors, check the received entities, whether they are a string, a object or a boolean value ...

the regex below also handles non-semicolon variables, and recursive nested objects, new regex (?<!\/\s*?)\bvar\b\s+(.*?)\s*?=\s*?(?:(?:\{(?:\{.*?\}|(?!;)[^\{])*\})|(?:\bfalse\b|\btrue\b)|(?:['"][^"|']*['"]))\s*?;?\s*?\n

link that helped me https://stackoverflow.com/a/2563520/14201692 thanks you Sean Huber!

Firelight
  • 1
  • 2