Search code examples
javascriptregexregexp-replace

RegExp to strip a variable in ES6-like format


I'm using an ES6-like variable formatting with the syntax of ${varName}, and while processing them I'm trying to enumerate all unique variables specified, using the following code:

function enumVars(txt) {
    var v, names = [];
    var reg = /\$\{\s*[a-zA-Z\$_][a-zA-Z0-9\$_]*\s*}/g;
    while (v = reg.exec(txt)) {
        var svn = v[0].replace(/???/, ''); // stripped variable name;
        if (names.indexOf(svn) === -1) {
            names.push(svn);
        }
    }
    return names;
}

I haven't been able to figure out the correct RegExp for stripping the variable name from the exec result.

When I use v[0], it gives me ${varName} string, and I need to strip it into just varName, removing leading ${, trailing }, and all white spaces that may reside inside { } around the variable.

The variable is expected to follow the javascript naming convention, which means:

  • a valid variable starts with a letter, underscore or '$' symbol, followed by any combination of letters, digits, underscores or '$';
  • leading and trailing spaces around the variable are to be ignored.

In all, we may have a variable returned from exec as ${ _$abc12_$ }, and I need a RegExp for calling replace that would return just _$abc12_$.

Thanks everyone for helping!


Solution

  • Your replace regexp could be

    /^\$\{\s*|\s*}$/g
    

    In English, this says "remove both ${... at the beginning, or ...} at the end.

    It could be slightly easier to just grab all the strings, and transform them all at once, then filter out duplicates:

    function enumVars(txt) {
        return txt
    
            // Find all matches of form ${var}
            . match(/\$\{\s*[a-z$_][a-z0-9$_]*\s*}/gi)
    
            // Strip off ${ and }, yielding just variable name
            . map(function(v) { return v.replace( /^\$\{\s*|\s*}$/g, ''); })
    
            // Filter out duplicates
            . filter(function(v, i, a) { return a.indexOf(v) === i; });
    }