def _get_tree(code): """Return an AST tree of the JS passed in `code`.""" if not code: return # Acceptable unicode characters still need to be stripped. Just remove the # slash: a character is necessary to prevent bad identifier errors. code = JS_ESCAPE.sub("u", unicodehelper.decode(code)) shell_obj = subprocess.Popen( ["node", "./acorn.js"], shell=False, stdin=subprocess.PIPE, stderr=subprocess.PIPE, stdout=subprocess.PIPE) data, stderr = shell_obj.communicate(code.encode('utf-8')) if stderr: raise RuntimeError('Error calling acorn: %s' % stderr) if not data: raise JSReflectException("Reflection failed") parsed = json.loads(unicodehelper.decode(data), strict=False) if parsed.get("error"): raise JSReflectException( parsed["error_message"]).line_num(parsed["line_number"]) return parsed
def _get_tree(code, shell=SPIDERMONKEY_INSTALLATION): """Return an AST tree of the JS passed in `code`.""" if not code: return None cmd = [shell, "-e", BOOTSTRAP_SCRIPT] shell_obj = subprocess.Popen( cmd, shell=False, stdin=subprocess.PIPE, stderr=subprocess.PIPE, stdout=subprocess.PIPE) code = json.dumps(JS_ESCAPE.sub("u", unicodehelper.decode(code))) data, stderr = shell_obj.communicate(code) if stderr: raise RuntimeError('Error calling %r: %s' % (cmd, stderr)) if not data: raise JSReflectException("Reflection failed") data = unicodehelper.decode(data) parsed = json.loads(data, strict=False) if parsed.get("error"): if parsed["error_message"].startswith("ReferenceError: Reflect"): raise RuntimeError("Spidermonkey version too old; " "1.8pre+ required; error='%s'; " "spidermonkey='%s'" % (parsed["error_message"], shell)) else: raise JSReflectException(parsed["error_message"]).line_num( parsed["line_number"]) return parsed
def get_tree_from_spidermonkey(shell, code): data = run_with_serialize(shell, code) data = unicodehelper.decode(data) try: return json.loads(data, strict=False) except ValueError: # Okay, maybe it was an encoding issue. data = run_with_tempfile(shell, code) data = unicodehelper.decode(data) return json.loads(data, strict=False)
def run_with_tempfile(shell, code): data = unicodehelper.decode(code).encode('utf-8', 'replace') with NamedTemporaryFile() as f: f.write(data) f.flush() data, stderr = run_js(shell, BOOTSTRAP_FILE_SCRIPT % f.name) return data
def _get_tree(code, shell=SPIDERMONKEY_INSTALLATION): """Return an AST tree of the JS passed in `code`.""" if not code: return None code = prepare_code(code) temp = tempfile.NamedTemporaryFile(mode="w+b", delete=False) temp.write(code.encode("utf_8")) temp.flush() data = """ try{options("allow_xml");}catch(e){} try{ print(JSON.stringify(Reflect.parse(read(%s)))); } catch(e) { print(JSON.stringify({ "error":true, "error_message":e.toString(), "line_number":e.lineNumber })); }""" % json.dumps(temp.name) try: cmd = [shell, "-e", data, "-U"] shell_obj = subprocess.Popen( cmd, shell=False, stderr=subprocess.PIPE, stdout=subprocess.PIPE) data, stderr = shell_obj.communicate() if stderr: raise RuntimeError('Error calling %r: %s' % (cmd, stderr)) # Closing the temp file will delete it. finally: try: temp.close() os.unlink(temp.name) except IOError: pass if not data: raise JSReflectException("Reflection failed") data = unicodehelper.decode(data) parsed = json.loads(data, strict=False) if "error" in parsed and parsed["error"]: if parsed["error_message"].startswith("ReferenceError: Reflect"): raise RuntimeError("Spidermonkey version too old; " "1.8pre+ required; error='%s'; " "spidermonkey='%s'" % (parsed["error_message"], shell)) else: raise JSReflectException(parsed["error_message"]).line_num( parsed["line_number"]) return parsed
def run_with_tempfile(shell, code): data = unicodehelper.decode(code).encode("utf-8", "replace") with NamedTemporaryFile() as f: f.write(data) f.flush() data, stderr = run_js(shell, BOOTSTRAP_FILE_SCRIPT % f.name) return data
def prepare_code(code): """Prepare code for tree generation.""" code = unicodehelper.decode(code) # Acceptable unicode characters still need to be stripped. Just remove the # slash: a character is necessary to prevent bad identifier errors. return JS_ESCAPE.sub("u", code)
def _do_test(path): "Performs a test on a JS file" text = open(path).read() utext = unicodehelper.decode(text) print utext.encode("ascii", "backslashreplace") nose.tools.eq_(utext, COMPARISON)
def _save_to_buffer(self, data): """Save data to the XML buffer for the current tag.""" # We're not interested in data that isn't in a tag. if not self.xml_buffer: return self.xml_buffer[-1] += unicodehelper.decode(data)
def _get_tree(code, shell=SPIDERMONKEY_INSTALLATION): """Return an AST tree of the JS passed in `code`.""" if not code: return None code = prepare_code(code) with tempfile.NamedTemporaryFile(mode="w+b", delete=False) as temp: temp_name = temp.name temp.write(code.encode("utf_8")) data = """ try{options("allow_xml");}catch(e){} try{ print(JSON.stringify(Reflect.parse(read(%s)))); } catch(e) { print(JSON.stringify({ "error":true, "error_message":e.toString(), "line_number":e.lineNumber })); }""" % json.dumps(temp_name) try: cmd = [shell, "-e", data, "-U"] shell_obj = subprocess.Popen( cmd, shell=False, stderr=subprocess.PIPE, stdout=subprocess.PIPE) data, stderr = shell_obj.communicate() if stderr: raise RuntimeError('Error calling %r: %s' % (cmd, stderr)) finally: try: os.unlink(temp_name) except IOError: pass if not data: raise JSReflectException("Reflection failed") data = unicodehelper.decode(data) parsed = json.loads(data, strict=False) if parsed.get("error"): if parsed["error_message"].startswith("ReferenceError: Reflect"): raise RuntimeError("Spidermonkey version too old; " "1.8pre+ required; error='%s'; " "spidermonkey='%s'" % (parsed["error_message"], shell)) else: raise JSReflectException(parsed["error_message"]).line_num( parsed["line_number"]) return parsed
def _feed_parser(self, line): """Feed incoming data into the underlying HTMLParser.""" line = unicodehelper.decode(line) try: self.feed(line + u"\n") except UnicodeDecodeError, exc_instance: # There's no recovering from a unicode error here. We've got the # unicodehelper; if that doesn't help us, nothing will. return
def _get_tree(code, shell=SPIDERMONKEY_INSTALLATION): """Return an AST tree of the JS passed in `code`.""" if not code: return None cmd = [shell, "-e", BOOTSTRAP_SCRIPT] shell_obj = subprocess.Popen(cmd, shell=False, stdin=subprocess.PIPE, stderr=subprocess.PIPE, stdout=subprocess.PIPE) code = json.dumps(JS_ESCAPE.sub("u", unicodehelper.decode(code))) data, stderr = shell_obj.communicate(code) if stderr: raise RuntimeError('Error calling %r: %s' % (cmd, stderr)) if not data: raise JSReflectException("Reflection failed") data = unicodehelper.decode(data) parsed = json.loads(data, strict=False) if parsed.get("error"): if parsed["error_message"].startswith("ReferenceError: Reflect"): raise RuntimeError("Spidermonkey version too old; " "1.8pre+ required; error='%s'; " "spidermonkey='%s'" % (parsed["error_message"], shell)) else: raise JSReflectException(parsed["error_message"]).line_num( parsed["line_number"]) return parsed
def _get_tree(code, shell=SPIDERMONKEY_INSTALLATION): """Return an AST tree of the JS passed in `code`.""" if not code: return None code = prepare_code(code) with tempfile.NamedTemporaryFile(mode="w+b", delete=False) as temp: temp_name = temp.name temp.write(code.encode("utf_8")) data = """ try{options("allow_xml");}catch(e){} try{ print(JSON.stringify(Reflect.parse(read(%s)))); } catch(e) { print(JSON.stringify({ "error":true, "error_message":e.toString(), "line_number":e.lineNumber })); }""" % json.dumps(temp_name) try: cmd = [shell, "-e", data, "-U"] shell_obj = subprocess.Popen( cmd, shell=False, stderr=subprocess.PIPE, stdout=subprocess.PIPE) data, stderr = shell_obj.communicate() # Spidermonkey dropped the -U flag on 29 Oct 2012 if stderr and ("Invalid short option: -U" in stderr or "usage: js [options] [scriptfile]" in stderr): cmd.remove("-U") shell_obj = subprocess.Popen( cmd, shell=False, stderr=subprocess.PIPE, stdout=subprocess.PIPE) data, stderr = shell_obj.communicate() if stderr: raise RuntimeError('Error calling %r: %s' % (cmd, stderr)) finally: try: os.unlink(temp_name) except IOError: pass if not data: raise JSReflectException("Reflection failed") data = unicodehelper.decode(data) parsed = json.loads(data, strict=False) if parsed.get("error"): if parsed["error_message"].startswith("ReferenceError: Reflect"): raise RuntimeError("Spidermonkey version too old; " "1.8pre+ required; error='%s'; " "spidermonkey='%s'" % (parsed["error_message"], shell)) else: raise JSReflectException(parsed["error_message"]).line_num( parsed["line_number"]) return parsed
def serialize_code(code): return json.dumps(JS_ESCAPE.sub("u", unicodehelper.decode(code)))