Skip to content

Commit 8a69389

Browse files
committed
Replace pending_count() function by has_pending() in middle
We are never looking at the actual count, so a boolean is enough. Also add tests for tracking node changes to ways.
1 parent d263925 commit 8a69389

File tree

8 files changed

+209
-9
lines changed

8 files changed

+209
-9
lines changed

src/middle-pgsql.cpp

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -804,7 +804,8 @@ middle_pgsql_t::get_query_instance()
804804
return std::shared_ptr<middle_query_t>(mid.release());
805805
}
806806

807-
size_t middle_pgsql_t::pending_count() const
807+
bool middle_pgsql_t::has_pending() const
808808
{
809-
return m_ways_pending_tracker->size() + m_rels_pending_tracker->size();
809+
return (m_ways_pending_tracker->size() > 0) ||
810+
(m_rels_pending_tracker->size() > 0);
810811
}

src/middle-pgsql.hpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -83,7 +83,7 @@ struct middle_pgsql_t : public slim_middle_t
8383
void iterate_ways(middle_t::pending_processor &pf) override;
8484
void iterate_relations(pending_processor &pf) override;
8585

86-
size_t pending_count() const override;
86+
bool has_pending() const override;
8787

8888
class table_desc
8989
{

src/middle-ram.cpp

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -76,8 +76,6 @@ void middle_ram_t::iterate_relations(pending_processor &pf)
7676
pf.process_relations();
7777
}
7878

79-
size_t middle_ram_t::pending_count() const { return 0; }
80-
8179
void middle_ram_t::iterate_ways(middle_t::pending_processor &pf)
8280
{
8381
//let the outputs enqueue everything they have the non slim middle

src/middle-ram.hpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -118,7 +118,7 @@ struct middle_ram_t : public middle_t, public middle_query_t
118118
void iterate_ways(middle_t::pending_processor &pf) override;
119119
void iterate_relations(pending_processor &pf) override;
120120

121-
size_t pending_count() const override;
121+
bool has_pending() const override { return false; }
122122

123123
std::shared_ptr<middle_query_t> get_query_instance() override;
124124

src/middle.hpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -133,7 +133,7 @@ struct middle_t
133133
virtual void iterate_ways(pending_processor &pf) = 0;
134134
virtual void iterate_relations(pending_processor &pf) = 0;
135135

136-
virtual size_t pending_count() const = 0;
136+
virtual bool has_pending() const = 0;
137137

138138
virtual std::shared_ptr<middle_query_t> get_query_instance() = 0;
139139
};

src/osmdata.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -403,7 +403,7 @@ struct pending_threaded_processor : public middle_t::pending_processor
403403
*/
404404
bool osmdata_t::has_pending() const noexcept
405405
{
406-
if (m_mid->pending_count() > 0) {
406+
if (m_mid->has_pending()) {
407407
return true;
408408
}
409409

tests/test-middle.cpp

Lines changed: 201 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,8 @@
1010
#include "common-options.hpp"
1111
#include "common-pg.hpp"
1212

13+
#include <algorithm>
14+
1315
static pg::tempdb_t db;
1416

1517
namespace {
@@ -497,6 +499,32 @@ static void check_way(std::shared_ptr<middle_pgsql_t> const &mid,
497499
REQUIRE(orig_crc().checksum() == test_crc().checksum());
498500
}
499501

502+
/**
503+
* Check that the nodes (ids and locations) of the way with the way_id in the
504+
* mid are identical to the nodes in the nodes vector.
505+
*/
506+
static void check_way_nodes(std::shared_ptr<middle_pgsql_t> const &mid,
507+
osmid_t way_id,
508+
std::vector<osmium::Node const *> nodes)
509+
{
510+
auto const mid_q = mid->get_query_instance();
511+
512+
osmium::memory::Buffer outbuf{4096, osmium::memory::Buffer::auto_grow::yes};
513+
REQUIRE(mid_q->way_get(way_id, outbuf));
514+
auto &way = outbuf.get<osmium::Way>(0);
515+
516+
REQUIRE(mid_q->nodes_get_list(&way.nodes()) == way.nodes().size());
517+
REQUIRE(way.nodes().size() == nodes.size());
518+
519+
auto it = way.nodes().cbegin();
520+
for (auto const *nptr : nodes) {
521+
REQUIRE(nptr->id() == it->ref());
522+
REQUIRE(nptr->location() == it->location());
523+
++it;
524+
}
525+
REQUIRE(it == way.nodes().cend());
526+
}
527+
500528
/// Return true if the way with the specified id is not in the mid.
501529
static bool no_way(std::shared_ptr<middle_pgsql_t> const &mid, osmid_t id)
502530
{
@@ -978,3 +1006,176 @@ TEMPLATE_TEST_CASE("middle: add relation with attributes", "",
9781006
mid->commit();
9791007
}
9801008
}
1009+
1010+
class test_pending_processor : public middle_t::pending_processor
1011+
{
1012+
public:
1013+
test_pending_processor() = default;
1014+
1015+
void enqueue_ways(osmid_t id) override { m_way_ids.push_back(id); }
1016+
1017+
void process_ways() override{};
1018+
void enqueue_relations(osmid_t) override{};
1019+
void process_relations() override{};
1020+
1021+
void check_way_ids_equal_to(std::initializer_list<osmid_t> list) noexcept
1022+
{
1023+
REQUIRE(!m_way_ids.empty());
1024+
1025+
// The last tracked id is always the invalid id, which we ignore
1026+
REQUIRE_FALSE(id_tracker::is_valid(m_way_ids.back()));
1027+
m_way_ids.pop_back();
1028+
1029+
REQUIRE(m_way_ids.size() == list.size());
1030+
REQUIRE(std::equal(m_way_ids.cbegin(), m_way_ids.cend(), list.begin()));
1031+
}
1032+
1033+
private:
1034+
std::vector<osmid_t> m_way_ids;
1035+
};
1036+
1037+
TEMPLATE_TEST_CASE("middle: change nodes in way", "", options_slim_default,
1038+
options_slim_dense_cache, options_flat_node_cache)
1039+
{
1040+
options_t options = TestType::options(db);
1041+
1042+
testing::cleanup::file_t flatnode_cleaner{
1043+
options.flat_node_file.get_value_or("")};
1044+
1045+
// create some nodes and ways we'll use for the tests
1046+
test_buffer_t buffer;
1047+
auto const &node10 = buffer.add_node_and_get(10, 1.0, 0.0);
1048+
auto const &node11 = buffer.add_node_and_get(11, 1.1, 0.0);
1049+
auto const &node12 = buffer.add_node_and_get(12, 1.2, 0.0);
1050+
auto const &node10a = buffer.add_node_and_get(10, 2.0, 0.0);
1051+
1052+
auto const &way20 = buffer.add_way_and_get(20, {10, 11});
1053+
auto const &way21 = buffer.add_way_and_get(21, {11, 12});
1054+
auto const &way22 = buffer.add_way_and_get(22, {12, 10});
1055+
auto const &way20a = buffer.add_way_and_get(20, {11, 12});
1056+
1057+
// Set up middle in "create" mode to get a cleanly initialized database and
1058+
// add some nodes and ways. Does this in its own scope so that the mid is
1059+
// closed properly.
1060+
{
1061+
auto mid = std::make_shared<middle_pgsql_t>(&options);
1062+
mid->start();
1063+
1064+
mid->node_set(node10);
1065+
mid->node_set(node11);
1066+
mid->node_set(node12);
1067+
mid->flush();
1068+
mid->way_set(way20);
1069+
mid->way_set(way21);
1070+
mid->flush();
1071+
1072+
check_node(mid, node10);
1073+
check_node(mid, node11);
1074+
check_node(mid, node12);
1075+
check_way(mid, way20);
1076+
check_way_nodes(mid, way20.id(), {&node10, &node11});
1077+
check_way(mid, way21);
1078+
check_way_nodes(mid, way21.id(), {&node11, &node12});
1079+
1080+
// Nothing pending yet
1081+
REQUIRE_FALSE(mid->has_pending());
1082+
test_pending_processor proc;
1083+
mid->iterate_ways(proc);
1084+
proc.check_way_ids_equal_to({});
1085+
1086+
mid->commit();
1087+
}
1088+
1089+
// From now on use append mode to not destroy the data we just added.
1090+
options.append = true;
1091+
1092+
SECTION("single way affected")
1093+
{
1094+
auto mid = std::make_shared<middle_pgsql_t>(&options);
1095+
mid->start();
1096+
1097+
mid->node_delete(10);
1098+
mid->node_set(node10a);
1099+
mid->node_changed(10);
1100+
mid->flush();
1101+
1102+
REQUIRE(mid->has_pending());
1103+
test_pending_processor proc;
1104+
mid->iterate_ways(proc);
1105+
proc.check_way_ids_equal_to({20});
1106+
1107+
check_way(mid, way20);
1108+
check_way_nodes(mid, way20.id(), {&node10a, &node11});
1109+
1110+
mid->commit();
1111+
}
1112+
1113+
SECTION("two ways affected")
1114+
{
1115+
{
1116+
auto mid = std::make_shared<middle_pgsql_t>(&options);
1117+
mid->start();
1118+
1119+
mid->way_set(way22);
1120+
mid->flush();
1121+
check_way(mid, way22);
1122+
1123+
mid->commit();
1124+
}
1125+
{
1126+
auto mid = std::make_shared<middle_pgsql_t>(&options);
1127+
mid->start();
1128+
1129+
mid->node_delete(10);
1130+
mid->node_set(node10a);
1131+
mid->node_changed(10);
1132+
mid->flush();
1133+
1134+
REQUIRE(mid->has_pending());
1135+
test_pending_processor proc;
1136+
mid->iterate_ways(proc);
1137+
proc.check_way_ids_equal_to({20, 22});
1138+
1139+
check_way(mid, way20);
1140+
check_way_nodes(mid, way20.id(), {&node10a, &node11});
1141+
check_way(mid, way22);
1142+
check_way_nodes(mid, way22.id(), {&node12, &node10a});
1143+
1144+
mid->commit();
1145+
}
1146+
}
1147+
1148+
SECTION("change way so the changing node isn't in it any more")
1149+
{
1150+
{
1151+
auto mid = std::make_shared<middle_pgsql_t>(&options);
1152+
mid->start();
1153+
1154+
mid->way_delete(20);
1155+
mid->way_set(way20a);
1156+
mid->flush();
1157+
1158+
check_way(mid, way20a);
1159+
check_way_nodes(mid, way20.id(), {&node11, &node12});
1160+
1161+
mid->commit();
1162+
}
1163+
1164+
{
1165+
auto mid = std::make_shared<middle_pgsql_t>(&options);
1166+
mid->start();
1167+
1168+
mid->node_delete(10);
1169+
mid->node_set(node10a);
1170+
mid->node_changed(10);
1171+
mid->flush();
1172+
1173+
REQUIRE_FALSE(mid->has_pending());
1174+
test_pending_processor proc;
1175+
mid->iterate_ways(proc);
1176+
proc.check_way_ids_equal_to({});
1177+
1178+
mid->commit();
1179+
}
1180+
}
1181+
}

tests/test-parse-osmium.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,7 @@ struct counting_slim_middle_t : public slim_middle_t
2828

2929
void iterate_ways(pending_processor &) override {}
3030
void iterate_relations(pending_processor &) override {}
31-
size_t pending_count() const override { return 0; }
31+
bool has_pending() const override { return false; }
3232

3333
std::shared_ptr<middle_query_t> get_query_instance() override
3434
{

0 commit comments

Comments
 (0)