// TODO: handle null values sS replaceDollarVars_js(S s, O... _) { //ret replaceDollarVars_withCustomToString(s, o -> jsonEncode_extended(o), _); MapSO vars = paramsToMap_withNulls(_); if (empty(vars)) ret s; var vars2 = mapKeys dropDollarPrefix(vars); ret replaceDollarVars_dyn(s, var -> { if (!vars2.containsKey(var)) null; O value = vars2.get(var); ret jsonEncode_extended(value); }); }