protected Node representMapping(Tag tag, Map<?, ?> mapping, Boolean flowStyle) { List<NodeTuple> value = new ArrayList<NodeTuple>(mapping.size()); MappingNode node = new MappingNode(tag, value, flowStyle); representedObjects.put(objectToRepresent, node); boolean bestStyle = true; for (Map.Entry<?, ?> entry : mapping.entrySet()) { Node nodeKey = representData(entry.getKey()); Node nodeValue = representData(entry.getValue()); if (!(nodeKey instanceof ScalarNode && ((ScalarNode) nodeKey).getStyle() == null)) { bestStyle = false; } if (!(nodeValue instanceof ScalarNode && ((ScalarNode) nodeValue).getStyle() == null)) { bestStyle = false; } value.add(new NodeTuple(nodeKey, nodeValue)); } if (flowStyle == null) { if (defaultFlowStyle != FlowStyle.AUTO) { node.setFlowStyle(defaultFlowStyle.getStyleBoolean()); } else { node.setFlowStyle(bestStyle); } } return node; }
@Override public void construct2ndStep(Node node, Object object) { // Compact Object Notation may contain only one entry MappingNode mnode = (MappingNode) node; NodeTuple nodeTuple = mnode.getValue().iterator().next(); Node valueNode = nodeTuple.getValueNode(); if (valueNode instanceof MappingNode) { valueNode.setType(object.getClass()); constructJavaBean2ndStep((MappingNode) valueNode, object); } else { // value is a list applySequence(object, constructSequence((SequenceNode) valueNode)); } }
protected void constructSet2ndStep(MappingNode node, Set<Object> set) { List<NodeTuple> nodeValue = (List<NodeTuple>) node.getValue(); for (NodeTuple tuple : nodeValue) { Node keyNode = tuple.getKeyNode(); Object key = constructObject(keyNode); if (key != null) { try { key.hashCode();// check circular dependencies } catch (Exception e) { throw new ConstructorException("while constructing a Set", node.getStartMark(), "found unacceptable key " + key, tuple.getKeyNode().getStartMark(), e); } } if (keyNode.isTwoStepsConstruction()) { /* * if keyObject is created it 2 steps we should postpone putting * it into the set because it may have different hash after * initialization compared to clean just created one. And set of * course does not observe value hashCode changes. */ sets2fill.add(0, new RecursiveTuple<Set<Object>, Object>(set, key)); } else { set.add(key); } } }
protected void constructSet2ndStep(MappingNode node, Set<Object> set) { List<NodeTuple> nodeValue = node.getValue(); for (NodeTuple tuple : nodeValue) { Node keyNode = tuple.getKeyNode(); Object key = constructObject(keyNode); if (key != null) { try { key.hashCode();// check circular dependencies } catch (Exception e) { throw new ConstructorException("while constructing a Set", node.getStartMark(), "found unacceptable key " + key, tuple.getKeyNode().getStartMark(), e); } } if (keyNode.isTwoStepsConstruction()) { /* * if keyObject is created it 2 steps we should postpone putting * it into the set because it may have different hash after * initialization compared to clean just created one. And set of * course does not observe value hashCode changes. */ sets2fill.add(0, new RecursiveTuple<Set<Object>, Object>(set, key)); } else { set.add(key); } } }
private void dumpConfiguration(Path configFilePath) { try (FileWriter fileWriter = new FileWriter(configFilePath.toFile())) { DumperOptions options = new DumperOptions(); options.setDefaultFlowStyle(DumperOptions.FlowStyle.BLOCK); Representer representer = new Representer() { @Override protected NodeTuple representJavaBeanProperty(Object javaBean, Property property, Object propertyValue,Tag customTag) { // if value of property is null, ignore it. if (propertyValue == null) { return null; } else { return super.representJavaBeanProperty(javaBean, property, propertyValue, customTag); } } }; representer.addClassTag(Configuration.class, Tag.MAP); Yaml yaml = new Yaml(representer, options); yaml.dump(configuration, fileWriter); } catch (IOException e) { throw new RuntimeException("Failed to dump configuration in file " + configFilePath, e); } }
@Test public void notNullMapProperty() { bean.setMapProperty(ImmutableMap.<String, Long> builder().put("first", 1L).put("second", 2L).build()); Property property = new MethodProperty(getPropertyDescriptor("mapProperty")); NodeTuple nodeTuple = representer.representJavaBeanProperty(bean, property, bean.getMapProperty(), null); assertThat(nodeTuple, is(notNullValue())); assertThat(nodeTuple.getKeyNode(), is(instanceOf(ScalarNode.class))); assertThat(((ScalarNode) nodeTuple.getKeyNode()).getValue(), is("map-property")); assertThat(nodeTuple.getValueNode(), is(instanceOf(MappingNode.class))); assertThat(((MappingNode) nodeTuple.getValueNode()).getValue().size(), is(2)); assertThat(((MappingNode) nodeTuple.getValueNode()).getValue().get(0), is(instanceOf(NodeTuple.class))); assertThat(((ScalarNode) ((MappingNode) nodeTuple.getValueNode()).getValue().get(0).getKeyNode()).getValue(), is("first")); assertThat(((ScalarNode) ((MappingNode) nodeTuple.getValueNode()).getValue().get(0).getValueNode()).getValue(), is("1")); assertThat(((ScalarNode) ((MappingNode) nodeTuple.getValueNode()).getValue().get(1).getKeyNode()).getValue(), is("second")); assertThat(((ScalarNode) ((MappingNode) nodeTuple.getValueNode()).getValue().get(1).getValueNode()).getValue(), is("2")); }
@Override public Set<String> getKeys() { if (this.node instanceof MappingNode) { List<NodeTuple> tuples = ((MappingNode) this.node).getValue(); Set<String> result = new LinkedHashSet<>(tuples.size()); for (NodeTuple tuple : tuples) { Node keyNode = tuple.getKeyNode(); if (keyNode instanceof ScalarNode) { result.add(((ScalarNode) keyNode).getValue()); } } return result; } return Collections.emptySet(); }
@Nullable private Node getNode(MappingNode node, String key, boolean remove) { for (Iterator<NodeTuple> iterator = node.getValue().iterator(); iterator.hasNext(); ) { NodeTuple tuple = iterator.next(); Node keyNode = tuple.getKeyNode(); if (! (keyNode instanceof ScalarNode)) { return null; } if (key.equals(((ScalarNode) keyNode).getValue())) { if (remove) { iterator.remove(); } return tuple.getValueNode(); } } return null; }
@SuppressWarnings("unchecked") @Override public <K, T, M extends Map<K, T>> void getMap(String key, Function<String, K> keyMapper, Class<T> type, M map) { Node node = this.getNode(this.node, key); if (! (node instanceof MappingNode)) { throw new DeserializationException(type, this, "Can't find valid value for key: " + key); } MappingNode mappingNode = (MappingNode) node; Tag typeTag = new Tag(type); for (NodeTuple tuple : mappingNode.getValue()) { Node keyNode = tuple.getKeyNode(); keyNode.setTag(Tag.STR); K keyObj = keyMapper.apply(this.constructor.constructObject(keyNode).toString()); Node valueNode = tuple.getValueNode(); if (type != Object.class) { valueNode.setTag(typeTag); } map.put(keyObj, (T) this.constructor.constructObject(valueNode)); } }
protected Node composeMappingNode(String anchor) { MappingStartEvent startEvent = (MappingStartEvent) parser.getEvent(); String tag = startEvent.getTag(); Tag nodeTag; boolean resolved = false; if (tag == null || tag.equals("!")) { nodeTag = resolver.resolve(NodeId.mapping, null, startEvent.getImplicit()); resolved = true; } else { nodeTag = new Tag(tag); } final List<NodeTuple> children = new ArrayList<NodeTuple>(); MappingNode node = new MappingNode(nodeTag, resolved, children, startEvent.getStartMark(), null, startEvent.getFlowStyle()); if (anchor != null) { anchors.put(anchor, node); } while (!parser.checkEvent(Event.ID.MappingEnd)) { composeMappingChildren(children, node); } Event endEvent = parser.getEvent(); node.setEndMark(endEvent.getEndMark()); return node; }
@Override protected void constructMapping2ndStep(MappingNode node, Map<Object, Object> mapping) { List<NodeTuple> nodeValue = (List<NodeTuple>) node.getValue(); for (NodeTuple tuple : nodeValue) { Node keyNode = tuple.getKeyNode(); Node valueNode = tuple.getValueNode(); Object key = constructObject(keyNode); if (key != null) { key.hashCode();// check circular dependencies } Object value = constructObject(valueNode); Object old = mapping.put(key, value); if (old != null) { throw new YAMLException("The key is not unique " + key); } } }
@SuppressWarnings("unchecked") public Car construct(Node node) { Car car = new Car(); MappingNode mapping = (MappingNode) node; List<NodeTuple> list = mapping.getValue(); for (NodeTuple tuple : list) { String field = toScalarString(tuple.getKeyNode()); if ("plate".equals(field)) { car.setPlate(toScalarString(tuple.getValueNode())); } if ("wheels".equals(field)) { SequenceNode snode = (SequenceNode) tuple.getValueNode(); List<Wheel> wheels = (List<Wheel>) constructSequence(snode); car.setWheels(wheels); } } return car; }
@Override public Node getSingleNode() { Node node = super.getSingleNode(); if (!MappingNode.class.isAssignableFrom(node.getClass())) { throw new RuntimeException( "Document is not structured as expected. Root element should be a map!"); } MappingNode root = (MappingNode) node; for (NodeTuple tuple : root.getValue()) { Node keyNode = tuple.getKeyNode(); if (ScalarNode.class.isAssignableFrom(keyNode.getClass())) { if (((ScalarNode) keyNode).getValue().equals(nodeName)) { return tuple.getValueNode(); } } } throw new RuntimeException("Did not find key \"" + nodeName + "\" in document-level map"); }
private void loadYamlLookupSets(MappingNode entry, String filename) { // LOG.info("Loading lookupSet.({}:{})", filename, entry.getStartMark().getLine()); String name = null; Set<String> lookupSet = new HashSet<>(); for (NodeTuple tuple : entry.getValue()) { switch (getKeyAsString(tuple, filename)) { case "name": name = getValueAsString(tuple, filename); break; case "values": SequenceNode node = getValueAsSequenceNode(tuple, filename); List<String> values = getStringValues(node, filename); for (String value: values) { lookupSet.add(value.toLowerCase(Locale.ENGLISH)); } break; default: break; } } lookupSets.put(name, lookupSet); }
private static Node getNode(final MappingNode node, final String key, final boolean remove) { for (final Iterator<NodeTuple> it = node.getValue().iterator(); it.hasNext(); ) { final NodeTuple nodeTuple = it.next(); final Node keyNode = nodeTuple.getKeyNode(); if (keyNode instanceof ScalarNode) { if (key.equals(((ScalarNode) keyNode).getValue())) { if (remove) { it.remove(); } return nodeTuple.getValueNode(); } } } return null; }
@Override public Object construct(Node node) { if(!(node instanceof MappingNode)) { fail("The value of the !select-engine tag must be a map" + "\nGot: " + node); } String matchingKey = null; Object result = null; for(NodeTuple tuple : ((MappingNode)node).getValue()) { Node keyNode = tuple.getKeyNode(); if(!(keyNode instanceof ScalarNode)) { fail("The key in a !select-engine map must be a scalar" + "\nGot: " + constructObject(keyNode)); } String key = ((ScalarNode)keyNode).getValue(); if(IT_ENGINE.equals(key) || (matchingKey == null && ALL_ENGINE.equals(key))) { matchingKey = key; result = constructObject(tuple.getValueNode()); } } if(matchingKey != null) { LOG.debug("Select engine: '{}' => '{}'", matchingKey, result); return result; } else { LOG.debug("Select engine: no match"); return null; } }
private void validateKeys(MappingNode node) { Map<String, Long> keyCounts = node.getValue().stream() .map(NodeTuple::getKeyNode) .filter(n -> n instanceof ScalarNode) .map(ScalarNode.class::cast) .filter(n -> !"!include".equals(n.getTag().getValue())) // exclude !include tag .collect(Collectors.groupingBy(ScalarNode::getValue, Collectors.counting())); List<String> duplicatedKeys = keyCounts.entrySet().stream() .filter(it -> it.getValue() > 1) .map(Map.Entry<String, Long>::getKey) .collect(Collectors.toList()); if (!duplicatedKeys.isEmpty()) { throw new DuplicateKeyYAMLException(duplicatedKeys); } }
protected List<Position> calculatePositions(MappingNode mapping) { List<Position> positions = new ArrayList<>(); int start; int end = -1; for (NodeTuple tuple : mapping.getValue()) { start = tuple.getKeyNode().getStartMark().getLine(); end = tuple.getValueNode().getEndMark().getLine(); if ((end - start) > 0) { try { int startOffset = document.getLineOffset(start); int endOffset = document.getLineOffset(end); positions.add(new Position(startOffset, (endOffset - startOffset))); } catch (BadLocationException e) { } } if (tuple.getValueNode() instanceof MappingNode) { positions.addAll(calculatePositions((MappingNode) tuple.getValueNode())); } } return positions; }
protected Node representMapping(Tag tag, Map<? extends Object, Object> mapping, Boolean flowStyle) { List<NodeTuple> value = new ArrayList<NodeTuple>(mapping.size()); MappingNode node = new MappingNode(tag, value, flowStyle); representedObjects.put(objectToRepresent, node); boolean bestStyle = true; for (Map.Entry<? extends Object, Object> entry : mapping.entrySet()) { Node nodeKey = representData(entry.getKey()); Node nodeValue = representData(entry.getValue()); if (!((nodeKey instanceof ScalarNode && ((ScalarNode) nodeKey).getStyle() == null))) { bestStyle = false; } if (!((nodeValue instanceof ScalarNode && ((ScalarNode) nodeValue).getStyle() == null))) { bestStyle = false; } value.add(new NodeTuple(nodeKey, nodeValue)); } if (flowStyle == null) { if (defaultFlowStyle != FlowStyle.AUTO) { node.setFlowStyle(defaultFlowStyle.getStyleBoolean()); } else { node.setFlowStyle(bestStyle); } } return node; }
@Override protected NodeTuple representJavaBeanProperty(Object javaBean, Property property, Object propertyValue, Tag customTag) { if (javaBean instanceof AbstractElement) { if ("path".equals(property.getName()) || "buildPath".equals(property.getName())) //$NON-NLS-1$ //$NON-NLS-2$ { String path = (String) propertyValue; IPath relative = Path.fromOSString(path).makeRelativeTo( Path.fromOSString(bundleDirectory.getAbsolutePath())); propertyValue = relative.toOSString(); } } return super.representJavaBeanProperty(javaBean, property, propertyValue, customTag); }