def __call__(self, *args): expr = "eval('('+{func_text}+')')({args})".format( func_text=self.source, args=escape_js(*args) ) wrapper_script = get_process_errors_js(expr) res = self.tab.evaljs(wrapper_script) if not isinstance(res, dict): raise ScriptError({ 'type': ScriptError.UNKNOWN_ERROR, 'js_error_message': res, 'message': "unknown error during JS function call: " "{!r}; {!r}".format(res, wrapper_script) }) if res.get("error", False): err_message = res.get('errorMessage') err_type = res.get('errorType', '<custom JS error>') err_repr = res.get('errorRepr', '<unknown JS error>') if err_message is None: err_message = err_repr raise ScriptError({ 'type': ScriptError.JS_ERROR, 'js_error_type': err_type, 'js_error_message': err_message, 'js_error': err_repr, 'message': "error during JS function call: " "{!r}".format(err_repr) }) return res.get("result")
def evaljs(self, js_source, handle_errors=True, result_protection=True): """ Run JS code in page context and return the result. If JavaScript exception or an syntax error happens and `handle_errors` is True then Python JsError exception is raised. When `result_protection` is True (default) protection against badly written or malicious scripts is activated. Disable it when the script result is known to be good, i.e. it only contains objects/arrays/primitives without circular references. """ frame = self.web_page.mainFrame() eval_expr = u"eval({})".format(escape_js(js_source)) if result_protection: eval_expr = get_sanitized_result_js(eval_expr) if not handle_errors: return qt2py(frame.evaluateJavaScript(eval_expr)) res = frame.evaluateJavaScript(get_process_errors_js(eval_expr)) if not isinstance(res, dict): raise JsError({ 'type': ScriptError.UNKNOWN_ERROR, 'js_error_message': res, 'message': "unknown JS error: {!r}".format(res) }) if res.get("error", False): err_message = res.get('errorMessage') err_type = res.get('errorType', '<custom JS error>') err_repr = res.get('errorRepr', '<unknown JS error>') if err_message is None: err_message = err_repr raise JsError({ 'type': ScriptError.JS_ERROR, 'js_error_type': err_type, 'js_error_message': err_message, 'js_error': err_repr, 'message': "JS error: {!r}".format(err_repr) }) return res.get("result", None)
def escape_and_evaljs(frame, js_func): eval_expr = u"eval({})".format(escape_js(js_func)) return frame.evaluateJavaScript(get_process_errors_js(eval_expr))
def evaljs(self, js_source, handle_errors=True, result_protection=True, dom_elements=True): """ Run JS code in page context and return the result. If JavaScript exception or an syntax error happens and `handle_errors` is True then Python JsError exception is raised. When `result_protection` is True (default) protection against badly written or malicious scripts is activated. Disable it when the script result is known to be good, i.e. it only contains objects/arrays/primitives without circular references. When `dom_elements` is True (default) top-level DOM elements will be saved in JS field of window object under `self._elements_storage.name` key. The result of evaluation will be object with `type` property and `id` property. In JS the original DOM element can accessed through ``window[self._elements_storage.name][id]``. """ frame = self.web_page.mainFrame() eval_expr = u"eval({})".format(escape_js(js_source)) if dom_elements: self._init_js_objects_storage() eval_expr = store_dom_elements(eval_expr, self._elements_storage.name) if result_protection: eval_expr = get_sanitized_result_js(eval_expr) if handle_errors: res = frame.evaluateJavaScript(get_process_errors_js(eval_expr)) if not isinstance(res, dict): raise JsError({ 'type': ScriptError.UNKNOWN_ERROR, 'js_error_message': res, 'message': "unknown JS error: {!r}".format(res) }) if res.get("error", False): err_message = res.get('errorMessage') err_type = res.get('errorType', '<custom JS error>') err_repr = res.get('errorRepr', '<unknown JS error>') if err_message is None: err_message = err_repr raise JsError({ 'type': ScriptError.JS_ERROR, 'js_error_type': err_type, 'js_error_message': err_message, 'js_error': err_repr, 'message': "JS error: {!r}".format(err_repr) }) result = res.get("result", None) else: result = qt2py(frame.evaluateJavaScript(eval_expr)) return self._process_js_result(result, allow_dom=dom_elements)