mirror of
https://github.com/hapifhir/hapi-fhir.git
synced 2025-02-19 19:35:42 +00:00
Avoid concurrency issue introduced by #1489
This commit is contained in:
parent
21841aedff
commit
dfe07e7a2b
@ -27,7 +27,6 @@ import ca.uhn.fhir.model.primitive.IdDt;
|
||||
import ca.uhn.fhir.rest.api.Constants;
|
||||
import ca.uhn.fhir.rest.server.exceptions.InternalErrorException;
|
||||
import ca.uhn.fhir.util.UrlUtil;
|
||||
|
||||
import com.google.common.base.Charsets;
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.apache.commons.lang3.Validate;
|
||||
@ -68,47 +67,6 @@ public abstract class BaseParser implements IParser {
|
||||
private boolean mySuppressNarratives;
|
||||
private Set<String> myDontStripVersionsFromReferencesAtPaths;
|
||||
|
||||
private Map<Key, List<CompositeChildElement>> compositeChildrenCache = new HashMap<>();
|
||||
|
||||
private static class Key {
|
||||
private final BaseRuntimeElementCompositeDefinition<?> resDef;
|
||||
private final boolean theContainedResource;
|
||||
private final CompositeChildElement theParent;
|
||||
private final EncodeContext theEncodeContext;
|
||||
|
||||
public Key(BaseRuntimeElementCompositeDefinition<?> resDef, final boolean theContainedResource, final CompositeChildElement theParent, EncodeContext theEncodeContext) {
|
||||
this.resDef = resDef;
|
||||
this.theContainedResource = theContainedResource;
|
||||
this.theParent = theParent;
|
||||
this.theEncodeContext = theEncodeContext;
|
||||
}
|
||||
@Override
|
||||
public int hashCode() {
|
||||
final int prime = 31;
|
||||
int result = 1;
|
||||
result = prime * result + ((resDef == null) ? 0 : resDef.hashCode());
|
||||
result = prime * result + (theContainedResource ? 1231 : 1237);
|
||||
result = prime * result + ((theParent == null) ? 0 : theParent.hashCode());
|
||||
result = prime * result + ((theEncodeContext == null) ? 0 : theEncodeContext.hashCode());
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(final Object obj) {
|
||||
if (this == obj) {
|
||||
return true;
|
||||
}
|
||||
if (obj instanceof Key) {
|
||||
final Key that = (Key) obj;
|
||||
return Objects.equals(this.resDef, that.resDef) &&
|
||||
this.theContainedResource == that.theContainedResource &&
|
||||
Objects.equals(this.theParent, that.theParent) &&
|
||||
Objects.equals(this.theEncodeContext, that.theEncodeContext);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
@ -171,7 +129,7 @@ public abstract class BaseParser implements IParser {
|
||||
|
||||
protected Iterable<CompositeChildElement> compositeChildIterator(IBase theCompositeElement, final boolean theContainedResource, final CompositeChildElement theParent, EncodeContext theEncodeContext) {
|
||||
BaseRuntimeElementCompositeDefinition<?> elementDef = (BaseRuntimeElementCompositeDefinition<?>) myContext.getElementDefinition(theCompositeElement.getClass());
|
||||
return compositeChildrenCache.computeIfAbsent(new Key(elementDef, theContainedResource, theParent, theEncodeContext), (k) -> {
|
||||
return theEncodeContext.getCompositeChildrenCache().computeIfAbsent(new Key(elementDef, theContainedResource, theParent, theEncodeContext), (k) -> {
|
||||
|
||||
final List<BaseRuntimeChildDefinition> children = elementDef.getChildrenAndExtension();
|
||||
final List<CompositeChildElement> result = new ArrayList<>(children.size());
|
||||
@ -1369,13 +1327,17 @@ public abstract class BaseParser implements IParser {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* EncodeContext is a shared state object that is passed around the
|
||||
* encode process
|
||||
*/
|
||||
protected class EncodeContext extends EncodeContextPath {
|
||||
private final ArrayList<EncodeContextPathElement> myResourcePath = new ArrayList<>(10);
|
||||
private final Map<Key, List<CompositeChildElement>> myCompositeChildrenCache = new HashMap<>();
|
||||
|
||||
public Map<Key, List<CompositeChildElement>> getCompositeChildrenCache() {
|
||||
return myCompositeChildrenCache;
|
||||
}
|
||||
|
||||
protected ArrayList<EncodeContextPathElement> getResourcePath() {
|
||||
return myResourcePath;
|
||||
@ -1508,6 +1470,46 @@ public abstract class BaseParser implements IParser {
|
||||
}
|
||||
}
|
||||
|
||||
private static class Key {
|
||||
private final BaseRuntimeElementCompositeDefinition<?> resDef;
|
||||
private final boolean theContainedResource;
|
||||
private final CompositeChildElement theParent;
|
||||
private final EncodeContext theEncodeContext;
|
||||
|
||||
public Key(BaseRuntimeElementCompositeDefinition<?> resDef, final boolean theContainedResource, final CompositeChildElement theParent, EncodeContext theEncodeContext) {
|
||||
this.resDef = resDef;
|
||||
this.theContainedResource = theContainedResource;
|
||||
this.theParent = theParent;
|
||||
this.theEncodeContext = theEncodeContext;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
final int prime = 31;
|
||||
int result = 1;
|
||||
result = prime * result + ((resDef == null) ? 0 : resDef.hashCode());
|
||||
result = prime * result + (theContainedResource ? 1231 : 1237);
|
||||
result = prime * result + ((theParent == null) ? 0 : theParent.hashCode());
|
||||
result = prime * result + ((theEncodeContext == null) ? 0 : theEncodeContext.hashCode());
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(final Object obj) {
|
||||
if (this == obj) {
|
||||
return true;
|
||||
}
|
||||
if (obj instanceof Key) {
|
||||
final Key that = (Key) obj;
|
||||
return Objects.equals(this.resDef, that.resDef) &&
|
||||
this.theContainedResource == that.theContainedResource &&
|
||||
Objects.equals(this.theParent, that.theParent) &&
|
||||
Objects.equals(this.theEncodeContext, that.theEncodeContext);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
static class ContainedResources {
|
||||
private long myNextContainedId = 1;
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user