Skip to content

Commit c3eb356

Browse files
authored
Merge pull request #1187 from HubSpot/keep-meta-context-variables
Keep meta context variables when importing
2 parents b5e4e74 + ec179b8 commit c3eb356

19 files changed

Lines changed: 107 additions & 75 deletions

src/main/java/com/hubspot/jinjava/el/ext/eager/EvalResultHolder.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -136,7 +136,7 @@ static String reconstructNode(
136136
.getELResolver()
137137
.getValue(context, null, ExtendedParser.INTERPRETER)
138138
).getContext()
139-
.getMetaContextVariables()
139+
.getComputedMetaContextVariables()
140140
.contains(name)
141141
) {
142142
return name;

src/main/java/com/hubspot/jinjava/interpret/Context.java

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@
2020
import com.google.common.collect.HashMultimap;
2121
import com.google.common.collect.ImmutableSet;
2222
import com.google.common.collect.SetMultimap;
23+
import com.google.common.collect.Sets;
2324
import com.hubspot.jinjava.lib.Importable;
2425
import com.hubspot.jinjava.lib.expression.DefaultExpressionStrategy;
2526
import com.hubspot.jinjava.lib.expression.ExpressionStrategy;
@@ -34,6 +35,7 @@
3435
import com.hubspot.jinjava.lib.tag.Tag;
3536
import com.hubspot.jinjava.lib.tag.TagLibrary;
3637
import com.hubspot.jinjava.lib.tag.eager.DeferredToken;
38+
import com.hubspot.jinjava.mode.EagerExecutionMode;
3739
import com.hubspot.jinjava.tree.Node;
3840
import com.hubspot.jinjava.util.DeferredValueUtils;
3941
import com.hubspot.jinjava.util.ScopeMap;
@@ -117,6 +119,7 @@ public enum Library {
117119
private boolean unwrapRawOverride = false;
118120
private DynamicVariableResolver dynamicVariableResolver = null;
119121
private final Set<String> metaContextVariables; // These variable names aren't tracked in eager execution
122+
private final Set<String> overriddenNonMetaContextVariables;
120123
private Node currentNode;
121124

122125
public Context() {
@@ -209,6 +212,8 @@ public Context(
209212
new FunctionLibrary(parent == null, disabled.get(Library.FUNCTION));
210213
this.metaContextVariables =
211214
parent == null ? new HashSet<>() : parent.metaContextVariables;
215+
this.overriddenNonMetaContextVariables =
216+
parent == null ? new HashSet<>() : parent.overriddenNonMetaContextVariables;
212217
if (parent != null) {
213218
this.expressionStrategy = parent.expressionStrategy;
214219
this.partialMacroEvaluation = parent.partialMacroEvaluation;
@@ -348,10 +353,37 @@ public void addResolvedFunction(String function) {
348353
}
349354
}
350355

356+
@Deprecated
357+
@Beta
351358
public Set<String> getMetaContextVariables() {
352359
return metaContextVariables;
353360
}
354361

362+
@Beta
363+
public Set<String> getComputedMetaContextVariables() {
364+
return Sets.difference(metaContextVariables, overriddenNonMetaContextVariables);
365+
}
366+
367+
@Beta
368+
public void addMetaContextVariables(Collection<String> variables) {
369+
metaContextVariables.addAll(variables);
370+
}
371+
372+
@Beta
373+
public void addNonMetaContextVariables(Collection<String> variables) {
374+
overriddenNonMetaContextVariables.addAll(
375+
variables
376+
.stream()
377+
.filter(var -> !EagerExecutionMode.STATIC_META_CONTEXT_VARIABLES.contains(var))
378+
.collect(Collectors.toList())
379+
);
380+
}
381+
382+
@Beta
383+
public void removeNonMetaContextVariables(Collection<String> variables) {
384+
overriddenNonMetaContextVariables.removeAll(variables);
385+
}
386+
355387
public void handleDeferredNode(Node node) {
356388
if (
357389
JinjavaInterpreter

src/main/java/com/hubspot/jinjava/interpret/JinjavaInterpreter.java

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -111,7 +111,6 @@ public JinjavaInterpreter(
111111
this.context = context;
112112
this.config = renderConfig;
113113
this.application = application;
114-
115114
this.config.getExecutionMode().prepareContext(this.context);
116115

117116
switch (config.getRandomNumberGeneratorStrategy()) {

src/main/java/com/hubspot/jinjava/lib/tag/ForTag.java

Lines changed: 2 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,6 @@
3737
import com.hubspot.jinjava.tree.Node;
3838
import com.hubspot.jinjava.tree.TagNode;
3939
import com.hubspot.jinjava.tree.parse.TagToken;
40-
import com.hubspot.jinjava.util.EagerReconstructionUtils;
4140
import com.hubspot.jinjava.util.ForLoop;
4241
import com.hubspot.jinjava.util.HelperStringTokenizer;
4342
import com.hubspot.jinjava.util.LengthLimitingStringBuilder;
@@ -48,7 +47,6 @@
4847
import java.util.List;
4948
import java.util.Map.Entry;
5049
import java.util.Optional;
51-
import java.util.Set;
5250
import java.util.regex.Matcher;
5351
import java.util.regex.Pattern;
5452
import org.apache.commons.lang3.tuple.Pair;
@@ -165,11 +163,7 @@ public String renderForCollection(
165163
) {
166164
ForLoop loop = ObjectIterator.getLoop(collection);
167165

168-
Set<String> removedMetaContextVariables =
169-
EagerReconstructionUtils.removeMetaContextVariables(
170-
loopVars.stream(),
171-
interpreter.getContext()
172-
);
166+
interpreter.getContext().addNonMetaContextVariables(loopVars);
173167
try (InterpreterScopeClosable c = interpreter.enterScope()) {
174168
if (interpreter.isValidationMode() && !loop.hasNext()) {
175169
loop = ObjectIterator.getLoop(new DummyObject());
@@ -298,10 +292,7 @@ public String renderForCollection(
298292
}
299293
return checkLoopVariable(interpreter, buff);
300294
} finally {
301-
interpreter
302-
.getContext()
303-
.getMetaContextVariables()
304-
.addAll(removedMetaContextVariables);
295+
interpreter.getContext().removeNonMetaContextVariables(loopVars);
305296
}
306297
}
307298

src/main/java/com/hubspot/jinjava/lib/tag/eager/DeferredToken.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -378,7 +378,7 @@ private static Collection<String> markDeferredWordsAndFindSources(
378378
}
379379
return !(val instanceof DeferredValue);
380380
})
381-
.filter(prop -> !context.getMetaContextVariables().contains(prop))
381+
.filter(prop -> !context.getComputedMetaContextVariables().contains(prop))
382382
.filter(prop -> {
383383
DeferredValue deferredValue = convertToDeferredValue(context, prop);
384384
context.put(prop, deferredValue);

src/main/java/com/hubspot/jinjava/lib/tag/eager/EagerForTag.java

Lines changed: 2 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -185,11 +185,7 @@ private EagerExecutionResult runLoopOnce(
185185
List<String> loopVars = getTag()
186186
.getLoopVarsAndExpression((TagToken) tagNode.getMaster())
187187
.getLeft();
188-
Set<String> removedMetaContextVariables =
189-
EagerReconstructionUtils.removeMetaContextVariables(
190-
loopVars.stream(),
191-
interpreter.getContext()
192-
);
188+
interpreter.getContext().addNonMetaContextVariables(loopVars);
193189
loopVars.forEach(var ->
194190
interpreter.getContext().put(var, DeferredValue.instance())
195191
);
@@ -198,10 +194,7 @@ private EagerExecutionResult runLoopOnce(
198194
renderChildren(tagNode, eagerInterpreter)
199195
);
200196
} finally {
201-
interpreter
202-
.getContext()
203-
.getMetaContextVariables()
204-
.addAll(removedMetaContextVariables);
197+
interpreter.getContext().removeNonMetaContextVariables(loopVars);
205198
if (clearDeferredWords) {
206199
interpreter
207200
.getContext()

src/main/java/com/hubspot/jinjava/lib/tag/eager/EagerSetTagStrategy.java

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -40,11 +40,11 @@ public String run(TagNode tagNode, JinjavaInterpreter interpreter) {
4040
variables = new String[] { var };
4141
expression = tagNode.getHelpers();
4242
}
43-
44-
EagerReconstructionUtils.removeMetaContextVariables(
45-
Arrays.stream(variables).map(String::trim),
46-
interpreter.getContext()
47-
);
43+
interpreter
44+
.getContext()
45+
.addNonMetaContextVariables(
46+
Arrays.stream(variables).map(String::trim).collect(Collectors.toList())
47+
);
4848

4949
EagerExecutionResult eagerExecutionResult = getEagerExecutionResult(
5050
tagNode,
@@ -167,7 +167,7 @@ public static String getSuffixToPreserveState(
167167
if (
168168
maybeTemporaryImportAlias.isPresent() &&
169169
!AliasedEagerImportingStrategy.isTemporaryImportAlias(variables) &&
170-
!interpreter.getContext().getMetaContextVariables().contains(variables)
170+
!interpreter.getContext().getComputedMetaContextVariables().contains(variables)
171171
) {
172172
if (!interpreter.getContext().containsKey(maybeTemporaryImportAlias.get())) {
173173
if (

src/main/java/com/hubspot/jinjava/lib/tag/eager/importing/FlatEagerImportingStrategy.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -72,7 +72,7 @@ public String getFinalOutput(
7272
Set<String> metaContextVariables = importingData
7373
.getOriginalInterpreter()
7474
.getContext()
75-
.getMetaContextVariables();
75+
.getComputedMetaContextVariables();
7676
// defer imported variables
7777
EagerReconstructionUtils.buildSetTag(
7878
child

src/main/java/com/hubspot/jinjava/mode/EagerExecutionMode.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -53,6 +53,6 @@ public void prepareContext(Context context) {
5353
.filter(Optional::isPresent)
5454
.forEach(maybeEagerTag -> context.registerTag(maybeEagerTag.get()));
5555
context.setExpressionStrategy(new EagerExpressionStrategy());
56-
context.getMetaContextVariables().addAll(STATIC_META_CONTEXT_VARIABLES);
56+
context.addMetaContextVariables(STATIC_META_CONTEXT_VARIABLES);
5757
}
5858
}

src/main/java/com/hubspot/jinjava/util/DeferredValueUtils.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -119,7 +119,7 @@ private static void markDeferredProperties(Context context, Set<String> props) {
119119
props
120120
.stream()
121121
.filter(prop -> !(context.get(prop) instanceof DeferredValue))
122-
.filter(prop -> !context.getMetaContextVariables().contains(prop))
122+
.filter(prop -> !context.getComputedMetaContextVariables().contains(prop))
123123
.forEach(prop -> {
124124
Object value = context.get(prop);
125125
if (value != null) {

0 commit comments

Comments
 (0)