Skip to content

Commit da08d99

Browse files
committed
ENH: implement variables substitution in configuration
1 parent 6c720bb commit da08d99

File tree

1 file changed

+63
-0
lines changed

1 file changed

+63
-0
lines changed

mesonpy/_substitutions.py

Lines changed: 63 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,63 @@
1+
# SPDX-FileCopyrightText: 2023 The meson-python developers
2+
#
3+
# SPDX-License-Identifier: MIT
4+
5+
from __future__ import annotations
6+
7+
import ast
8+
import functools
9+
import operator
10+
import typing
11+
12+
13+
from typing import Any, Dict
14+
15+
16+
class Interpreter:
17+
18+
_operators = {
19+
ast.Add: operator.add,
20+
ast.Sub: operator.sub,
21+
ast.Mult: operator.mul,
22+
ast.Div: operator.truediv,
23+
}
24+
25+
def __init__(self, variables: Dict[str, Any]):
26+
self._variables = variables
27+
28+
def eval(self, string: str) -> Any:
29+
expr = ast.parse(string, mode='eval')
30+
return self._eval(expr)
31+
32+
__getitem__ = eval
33+
34+
@functools.singledispatchmethod
35+
def _eval(self, node: ast.Node) -> Any:
36+
print(node, type(node))
37+
raise ValueError
38+
39+
@_eval.register
40+
def _expression(self, node: ast.Expression) -> Any:
41+
return self._eval(node.body)
42+
43+
@_eval.register
44+
def _binop(self, node: ast.BinOp) -> Any:
45+
func = self._operators.get(type(node.op))
46+
if func is None:
47+
raise ValueError(node.op)
48+
return func(self._eval(node.left), self._eval(node.right))
49+
50+
@_eval.register
51+
def _constant(self, node: ast.Constant) -> Any:
52+
return node.value
53+
54+
@_eval.register
55+
def _variable(self, node: ast.Name) -> Any:
56+
value = self._variables.get(node.id)
57+
if value is None:
58+
raise ValueError
59+
return value
60+
61+
62+
def interpolate(string, **variables):
63+
return string % Interpreter(variables)

0 commit comments

Comments
 (0)