Skip to content

Commit

Permalink
[REF] web: reduce number of useless try/catch
Browse files Browse the repository at this point in the history
Before this commit, whenever we evaluate a partial context (for example,
when opening a form view), we would do a large number of try/catch, with
many of them resulting in an error.

This is because the context string represents an object with many field
values, which are not in the evaluation context. The purpose of the
evalPartialContext is to get the static values from the context. But
these errors are annoying if we are debugging and have a break on caught
exception setting on, which is usually what i do.

So, this commit improves the situation by avoiding the try/catch in some
cases where we know that the operation will fail anyway. This is a
heuristics, but it basically completely solves the issue in most cases.

closes odoo#142486

Signed-off-by: Mathieu Duckerts-Antoine (dam) <[email protected]>
  • Loading branch information
ged-odoo committed Nov 17, 2023
1 parent 28d02ed commit 83fb217
Showing 1 changed file with 30 additions and 0 deletions.
30 changes: 30 additions & 0 deletions addons/web/static/src/core/context.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
/** @odoo-module **/

import { evaluateExpr, parseExpr } from "./py_js/py";
import { BUILTINS } from "./py_js/py_builtin";
import { evaluate } from "./py_js/py_interpreter";

/**
Expand Down Expand Up @@ -29,6 +30,30 @@ export function makeContext(contexts, initialEvaluationContext) {
return context;
}

/**
* Extract a partial list of variable names found in the AST.
* Note that it is not complete. It is used as an heuristic to avoid
* evaluating expressions that we know for sure will fail.
*
* @param {AST} ast
* @returns string[]
*/
function getPartialNames(ast) {
if (ast.type === 5) {
return [ast.value];
}
if (ast.type === 6) {
return getPartialNames(ast.right);
}
if (ast.type === 14 || ast.type === 7) {
return getPartialNames(ast.left).concat(getPartialNames(ast.right));
}
if (ast.type === 15) {
return getPartialNames(ast.obj);
}
return [];
}

/**
* Allow to evaluate a context with an incomplete evaluation context. The evaluated context only
* contains keys whose values are static or can be evaluated with the given evaluation context.
Expand All @@ -42,6 +67,11 @@ export function evalPartialContext(_context, evaluationContext = {}) {
const context = {};
for (const key in ast.value) {
const value = ast.value[key];
if (
getPartialNames(value).some((name) => !(name in evaluationContext || name in BUILTINS))
) {
continue;
}
try {
context[key] = evaluate(value, evaluationContext);
} catch {
Expand Down

0 comments on commit 83fb217

Please sign in to comment.