Implicitly escaped $ (or not) in quasis?

Brendan Eich brendan at
Thu Jun 28 04:03:47 PDT 2012

gaz Heyes wrote:
> On 27 June 2012 15:59, Allen Wirfs-Brock <allen at 
> <mailto:allen at>> wrote:
> >
> > I don't see why the above issue would be a problem with this quasi 
> proposal, as quasi do no implicit evals or implicit reevaluation of 
> substitution  values.
> >
> > Consider this code:
> >
> > var USER_INPUT = getUserInput();  // assume the value returned is 
> "${globalVariable}"
> >
> > var message = `USER_INPUT`;   //The value of message is the string 
> "USER_INPUT", no substitution occurred
> >
> > var messageWithSub =  `${USER_INPUT}`;  //The value of 
> messageWithSub is the string "${globalVariable}", literally.  No eval 
> is performed.
> I understand the syntax now and I was correct with my initial assumptions.

Ok, I knew you knew what I thought you knew ;-).

> Although eval isn't performed on the placeholder text, you can access 
> variables from outside the scope intended. For example:
> !function(){
> var cookie=document.cookie, x =1;
> func`${cookie}`;
> }();
> If an injection occurs within the Quasi-Literal then you can use 
> unintended variables because there is no strict definition of which 
> variables substitution should occur. I also wonder if the syntax is 
> extended to support access object properties if this is a further 
> security risk.
> !function(){
> var x =1; //intended to use this variable
> func`${arguments.callee.caller()}`;
> func`${arguments[0]}`;
> }();
> It seems to me this is similar to having variable access inside string 
> literals and presents a real security risk even when a developer 
> escapes a quasi literal correctly.

Let's define risk:

risk = probability * cost

Assume fixed high cost of injection attack (they're bad).

Probability, or observed likelihood, is non-zero in JS today. People 
write string-concatenation-based formatting APIs, they call them with 
unsanitized arguments that interpolate, they're pwned.

Does adding quasiliterals change this probability appreciably?

Maybe it does raise probability for the unprefixed case, but the 
concatenation-based APIs still exist. You could argue that `SELECT * 
FROM Users WHERE Passwd = '${pwn_me}'` is an attractive nuisance.

On the other hand, safesql`SELECT * FROM Users WHERE Passwd = 
'${cant_pwn_me}'` support and developer evangelization means we have an 
affordance beyond library code to reduce the probability of injection 

Hard to say more without empirical studies, but I see plus and minus and 
can't jump to the conclusion that risk goes up just from the design of 

It's true one could evangelize a sanitizing API like the Caja one on 
which quasis were based. But developers fail to use such APIs. Several 
reasons I see:

1. They have to procure and load a library (true for safesql in the 
quasis case too, unless we standardize some functions -- which we could).

2. They have to pay the price of calling the API.

3. The API has overhead in parsing the format string.

Quasis address 2 in part, and 3 to a large extent if not completely (by 
parsing literal portions out of the format string in the JS compiler).

Quasis have other virtues as noted: multiline strings and regexps, even 
without any interpolation via ${...}.

Martin Johns among others has researched injection vulnerabilities. His 
SAP research page:

His old University of Passau home page:

Technical report:

Slide deck I recall from Dagstuhl 09141, and relevant to this thread:

This deck is about "Language-base prevention of code injection 
vulnerabilities". It is not all relevant to quasis, but  some of the 
goals and especially the conclusions are:

* reliably [prevent] string-based code injection,
* can be used for existing languages/frameworks/servers,
* [allow] integration of the complete foreign syntax,
* [preserve] (most of) the string-type conventions,
* and is applicable for all foreign language types
* Query, mark-up, general purpose, hybrid, …

There's no free lunch in defending against injection attacks. As Martin 
notes, you can add cumbersome constructive APIs, but practically no one 
will use them. You can go hog-wild with language integration, e.g. LINQ, 
E4X; but these are very costly to standardize. You can support 
"pre-processing", but that is a build step.

Quasis are trying to be an in-language programmable "pre-processor", so 
no build step. Instead you need to prefix the `...` with safesql where 
that identifier resolves (just like any identifier expression) to a 
function that takes the pre-processed raw and cooked literal portions, 
and the expressions to interpolate in between each literal portion.

Will programmers use quasis such as safesql and safehtml, where today 
they do not procure and use the library equivalents? Maybe, because the 
syntax is better due to in-order literal and expression portions, and 
the JS implementation does the raw/cooked string parsing and escaping.

It's hard to do more, in-language (again, LINQ, E4X -- just say no). 
Doing nothing leaves us as vulnerable as today. Unprefixed quasis could 
add likelihood of vulnerability (your concern).

This is not a topic with a clean, low-cost-lunch solution. Developers 
have to care, and take extra steps of some kind. On this basis, I think 
quasis are a net win, even excluding the multiline string benefit.

I don't agree that interpolation is riskier than concatenation, not 
without some evidence (perhaps there's been a study?).

Research tips welcome, I didn't look for other research than Martin's, 
with which I was already familiar. Cc'ing Mike Samuel in case he is 
behind on es-discuss, and Mark Miller.

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <>

More information about the es-discuss mailing list