Skip to content

Commit 6292971

Browse files
committed
Fix merge-key handling in case the dictionary contains a sub-dictionary
1 parent 6bbc603 commit 6292971

File tree

3 files changed

+12
-6
lines changed

3 files changed

+12
-6
lines changed

src/nodebuilder.cpp

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -70,6 +70,7 @@ void NodeBuilder::OnMapStart(const Mark& mark, const std::string& tag,
7070
node.set_tag(tag);
7171
node.set_style(style);
7272
m_mapDepth++;
73+
m_mergeDicts.emplace_back();
7374
}
7475

7576
void MergeMapCollection(detail::node& map_to, detail::node& map_from,
@@ -86,11 +87,12 @@ void MergeMapCollection(detail::node& map_to, detail::node& map_from,
8687
void NodeBuilder::OnMapEnd() {
8788
assert(m_mapDepth > 0);
8889
detail::node& collection = *m_stack.back();
89-
for (detail::node* n : m_mergeDicts) {
90+
auto& toMerge = *m_mergeDicts.rbegin();
91+
for (detail::node* n : toMerge) {
9092
MergeMapCollection(collection, *n, m_pMemory);
9193
}
92-
m_mergeDicts.clear();
9394
m_mapDepth--;
95+
m_mergeDicts.pop_back();
9496
Pop();
9597
}
9698

@@ -135,13 +137,13 @@ void NodeBuilder::Pop() {
135137
((nk.tag() == "tag:yaml.org,2002:merge" && nk.scalar() == "<<") ||
136138
(nk.tag() == "?" && nk.scalar() == "<<"))) {
137139
if (node.type() == NodeType::Map) {
138-
m_mergeDicts.emplace_back(&node);
140+
m_mergeDicts.rbegin()->emplace_back(&node);
139141
m_keys.pop_back();
140142
} else if (node.type() == NodeType::Sequence) {
141143
for (auto i = node.begin(); i != node.end(); i++) {
142144
auto v = *i;
143145
if ((*v).type() == NodeType::Map) {
144-
m_mergeDicts.emplace_back(&(*v));
146+
m_mergeDicts.rbegin()->emplace_back(&(*v));
145147
} else {
146148
throw ParserException(
147149
node.mark(),

src/nodebuilder.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,7 @@ class NodeBuilder : public EventHandler {
6767

6868
using PushedKey = std::pair<detail::node*, bool>;
6969
std::vector<PushedKey> m_keys;
70-
Nodes m_mergeDicts;
70+
std::vector<Nodes> m_mergeDicts;
7171
std::size_t m_mapDepth;
7272
};
7373
} // namespace YAML

test/integration/load_node_test.cpp

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -188,7 +188,7 @@ TEST(LoadNodeTest, MergeKeyB) {
188188
Node node = Load(
189189
"{x: &foo {a : 1,b : 1,c : 1}, y: &bar {d: 2, e : 2, f : 2, a : 2}, z: "
190190
"&stuff { << : *foo, b : 3}, w: { << : [*stuff, *bar], c: 4 }, v: { '<<' "
191-
": *foo } , u : {!!merge << : *bar} }");
191+
": *foo } , u : {!!merge << : *bar}, t: {!!merge << : *bar, h: 3} }");
192192
EXPECT_EQ(NodeType::Map, node["z"].Type());
193193
EXPECT_EQ(NodeType::Map, node["w"].Type());
194194
EXPECT_FALSE(node["z"]["<<"]);
@@ -208,6 +208,10 @@ TEST(LoadNodeTest, MergeKeyB) {
208208

209209
EXPECT_FALSE(node["u"]["<<"]);
210210
EXPECT_EQ(2, node["u"]["d"].as<int>());
211+
212+
EXPECT_FALSE(node["t"]["<<"]);
213+
EXPECT_EQ(2, node["t"]["d"].as<int>());
214+
EXPECT_EQ(3, node["t"]["h"].as<int>());
211215
}
212216

213217
TEST(LoadNodeTest, ForceInsertIntoMap) {

0 commit comments

Comments
 (0)