Path: csiph.com!x330-a1.tempe.blueboxinc.net!usenet.pasdenom.info!gegeweb.org!de-l.enfer-du-nord.net!feeder1.enfer-du-nord.net!feeder.news-service.com!newsfeed101.telia.com!starscream.dk.telia.net!news.tele.dk!feed118.news.tele.dk!not-for-mail Newsgroups: comp.lang.javascript Subject: Re: Parsing String of Named Function & Converting To Source References: From: Lasse Reichstein Nielsen Date: Tue, 18 Oct 2011 18:34:17 +0200 Message-ID: <8voi2r92.fsf@gmail.com> User-Agent: Gnus/5.1006 (Gnus v5.10.6) XEmacs/21.4 (Rational FORTRAN, windows-nt) Cancel-Lock: sha1:ScbCwkGKJU1QQEhWsolTCBFL2SE= MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Lines: 93 Organization: TDC Totalloesninger NNTP-Posting-Host: 87.57.52.80 X-Trace: 1318955656 dtext01.news.tele.dk 277 87.57.52.80:50477 X-Complaints-To: abuse@post.tele.dk Xref: x330-a1.tempe.blueboxinc.net comp.lang.javascript:7541 Seni Seven writes: > Suppose I have HTML markup with a SCRIPT element as shown below: > > > > All of this markup and contained script code is retrieved as a string using > Ajax. So, it's a string with the above content (newlines and all). > I have an HTML parser with support for parsing the string containing the > script code. Ok. > In parsing the contained code (using JavaScript, of course), how would you > convert the contained script code from string into source? What's the difference? I assume your HTML parser extracts the content of the script element as a string. What do you want to do with that string? > What I have found so far (using Firebug in Firefox for development) is this: > > 1) Isolating the string "function multiply(a, b) { return a * b; }" and then > passing that string as an argument to eval() does not cause the definition > of the function named "multiply," it seems. It probably does, but in the scope where the eval is executed, not at the global scope. For that, you can use, e.g., window.eval(sourceString); (or any other non-direct call to eval). > 2) I can parse the function definition in a way to create the string: > > "var multiply = new Function (\"a\", \"b\", \"{ return a * b; }\");" How wasteful :) The function syntax is perfectly fine, no need to make it more convoluted. > and then use eval() on it (without error). And then when I eval() the > global level code in a debugger (Firebug in FireFox), as so > > eval("var i = multiply(2, 5); document.write(\"The value " + > "of i is \" + i);"); // parsed code as string on one line > > > the value of identifier 'i' is immediately set to 10 in the debugger, but > the debugger exits with error 'multiply is not defined', which indicates > multiple levels of execution contexts, I suppose. In fact, if I just do an > eval() on the "multiply" assignment of the Function constructor, the > identifier 'multiply' is still not defined. > > QUESTION: What's the solution to the goal I want to achieve? Try: var script = document.createElement("script"); script.textContent = sourceString; document.body.appendChild(script); This executes the code as top-level, non-eval code (which there is no way to do in pure Javascript). No guarantees wrt. old browsers, but it seems to work in the current versions. Alternatively, just use a non-direct call to eval. var topLevelEval = eval; topLevelEval(sourceString); > The string representing the markup obtained by Ajax retrieval is then passed > to a parsing function which is supposed to do it all: parses the HTML > markup using DOM methods to insert the DocumentFragment into the main > document tree. It also parses CSS (stylesheets and style attributes), as > well as any Javascript contained inside SCRIPT elements. Everything becomes > part of the interactive document by using DOM method calls, HTML --> element Why not pass it as something easier to parse and separate into CSS/HTML/JS, e.g., JSON? /L -- Lasse Reichstein Holst Nielsen 'Javascript frameworks is a disruptive technology'