2016-02-10 00:12:00 +01:00
|
|
|
// Copyright (c) 2011-present, Facebook, Inc. All rights reserved.
|
2017-07-16 01:03:42 +02:00
|
|
|
// This source code is licensed under both the GPLv2 (found in the
|
|
|
|
// COPYING file in the root directory) and Apache 2.0 License
|
|
|
|
// (found in the LICENSE.Apache file in the root directory).
|
SpatialDB
Summary:
This diff is adding spatial index support to RocksDB.
When creating the DB user specifies a list of spatial indexes. Spatial indexes can cover different areas and have different resolution (i.e. number of tiles). This is useful for supporting different zoom levels.
Each element inserted into SpatialDB has:
* a bounding box, which determines how will the element be indexed
* string blob, which will usually be WKB representation of the polygon (http://en.wikipedia.org/wiki/Well-known_text)
* feature set, which is a map of key-value pairs, where value can be int, double, bool, null or a string. FeatureSet will be a set of tags associated with geo elements (for example, 'road': 'highway' and similar)
* a list of indexes to insert the element in. For example, small river element will be inserted in index for high zoom level, while country border will be inserted in all indexes (including the index for low zoom level).
Each query is executed on single spatial index. Query guarantees that it will return all elements intersecting the specified bounding box, but it might also return some extra non-intersecting elements.
Test Plan: Added bunch of unit tests in spatial_db_test
Reviewers: dhruba, yinwang
Reviewed By: yinwang
Subscribers: leveldb
Differential Revision: https://reviews.facebook.net/D20361
2014-07-23 20:22:58 +02:00
|
|
|
|
2015-07-14 03:35:03 +02:00
|
|
|
#ifndef ROCKSDB_LITE
|
|
|
|
|
SpatialDB
Summary:
This diff is adding spatial index support to RocksDB.
When creating the DB user specifies a list of spatial indexes. Spatial indexes can cover different areas and have different resolution (i.e. number of tiles). This is useful for supporting different zoom levels.
Each element inserted into SpatialDB has:
* a bounding box, which determines how will the element be indexed
* string blob, which will usually be WKB representation of the polygon (http://en.wikipedia.org/wiki/Well-known_text)
* feature set, which is a map of key-value pairs, where value can be int, double, bool, null or a string. FeatureSet will be a set of tags associated with geo elements (for example, 'road': 'highway' and similar)
* a list of indexes to insert the element in. For example, small river element will be inserted in index for high zoom level, while country border will be inserted in all indexes (including the index for low zoom level).
Each query is executed on single spatial index. Query guarantees that it will return all elements intersecting the specified bounding box, but it might also return some extra non-intersecting elements.
Test Plan: Added bunch of unit tests in spatial_db_test
Reviewers: dhruba, yinwang
Reviewed By: yinwang
Subscribers: leveldb
Differential Revision: https://reviews.facebook.net/D20361
2014-07-23 20:22:58 +02:00
|
|
|
#include <vector>
|
|
|
|
#include <string>
|
|
|
|
#include <set>
|
|
|
|
|
|
|
|
#include "rocksdb/utilities/spatial_db.h"
|
2015-06-18 23:55:05 +02:00
|
|
|
#include "util/compression.h"
|
SpatialDB
Summary:
This diff is adding spatial index support to RocksDB.
When creating the DB user specifies a list of spatial indexes. Spatial indexes can cover different areas and have different resolution (i.e. number of tiles). This is useful for supporting different zoom levels.
Each element inserted into SpatialDB has:
* a bounding box, which determines how will the element be indexed
* string blob, which will usually be WKB representation of the polygon (http://en.wikipedia.org/wiki/Well-known_text)
* feature set, which is a map of key-value pairs, where value can be int, double, bool, null or a string. FeatureSet will be a set of tags associated with geo elements (for example, 'road': 'highway' and similar)
* a list of indexes to insert the element in. For example, small river element will be inserted in index for high zoom level, while country border will be inserted in all indexes (including the index for low zoom level).
Each query is executed on single spatial index. Query guarantees that it will return all elements intersecting the specified bounding box, but it might also return some extra non-intersecting elements.
Test Plan: Added bunch of unit tests in spatial_db_test
Reviewers: dhruba, yinwang
Reviewed By: yinwang
Subscribers: leveldb
Differential Revision: https://reviews.facebook.net/D20361
2014-07-23 20:22:58 +02:00
|
|
|
#include "util/testharness.h"
|
|
|
|
#include "util/testutil.h"
|
|
|
|
#include "util/random.h"
|
|
|
|
|
|
|
|
namespace rocksdb {
|
|
|
|
namespace spatial {
|
|
|
|
|
2015-03-17 22:08:00 +01:00
|
|
|
class SpatialDBTest : public testing::Test {
|
SpatialDB
Summary:
This diff is adding spatial index support to RocksDB.
When creating the DB user specifies a list of spatial indexes. Spatial indexes can cover different areas and have different resolution (i.e. number of tiles). This is useful for supporting different zoom levels.
Each element inserted into SpatialDB has:
* a bounding box, which determines how will the element be indexed
* string blob, which will usually be WKB representation of the polygon (http://en.wikipedia.org/wiki/Well-known_text)
* feature set, which is a map of key-value pairs, where value can be int, double, bool, null or a string. FeatureSet will be a set of tags associated with geo elements (for example, 'road': 'highway' and similar)
* a list of indexes to insert the element in. For example, small river element will be inserted in index for high zoom level, while country border will be inserted in all indexes (including the index for low zoom level).
Each query is executed on single spatial index. Query guarantees that it will return all elements intersecting the specified bounding box, but it might also return some extra non-intersecting elements.
Test Plan: Added bunch of unit tests in spatial_db_test
Reviewers: dhruba, yinwang
Reviewed By: yinwang
Subscribers: leveldb
Differential Revision: https://reviews.facebook.net/D20361
2014-07-23 20:22:58 +02:00
|
|
|
public:
|
|
|
|
SpatialDBTest() {
|
2018-07-14 02:18:39 +02:00
|
|
|
dbname_ = test::PerThreadDBPath("spatial_db_test");
|
SpatialDB
Summary:
This diff is adding spatial index support to RocksDB.
When creating the DB user specifies a list of spatial indexes. Spatial indexes can cover different areas and have different resolution (i.e. number of tiles). This is useful for supporting different zoom levels.
Each element inserted into SpatialDB has:
* a bounding box, which determines how will the element be indexed
* string blob, which will usually be WKB representation of the polygon (http://en.wikipedia.org/wiki/Well-known_text)
* feature set, which is a map of key-value pairs, where value can be int, double, bool, null or a string. FeatureSet will be a set of tags associated with geo elements (for example, 'road': 'highway' and similar)
* a list of indexes to insert the element in. For example, small river element will be inserted in index for high zoom level, while country border will be inserted in all indexes (including the index for low zoom level).
Each query is executed on single spatial index. Query guarantees that it will return all elements intersecting the specified bounding box, but it might also return some extra non-intersecting elements.
Test Plan: Added bunch of unit tests in spatial_db_test
Reviewers: dhruba, yinwang
Reviewed By: yinwang
Subscribers: leveldb
Differential Revision: https://reviews.facebook.net/D20361
2014-07-23 20:22:58 +02:00
|
|
|
DestroyDB(dbname_, Options());
|
|
|
|
}
|
|
|
|
|
|
|
|
void AssertCursorResults(BoundingBox<double> bbox, const std::string& index,
|
|
|
|
const std::vector<std::string>& blobs) {
|
|
|
|
Cursor* c = db_->Query(ReadOptions(), bbox, index);
|
|
|
|
ASSERT_OK(c->status());
|
|
|
|
std::multiset<std::string> b;
|
|
|
|
for (auto x : blobs) {
|
|
|
|
b.insert(x);
|
|
|
|
}
|
|
|
|
|
|
|
|
while (c->Valid()) {
|
|
|
|
auto itr = b.find(c->blob().ToString());
|
|
|
|
ASSERT_TRUE(itr != b.end());
|
|
|
|
b.erase(itr);
|
|
|
|
c->Next();
|
|
|
|
}
|
|
|
|
ASSERT_EQ(b.size(), 0U);
|
|
|
|
ASSERT_OK(c->status());
|
|
|
|
delete c;
|
|
|
|
}
|
|
|
|
|
|
|
|
std::string dbname_;
|
|
|
|
SpatialDB* db_;
|
|
|
|
};
|
|
|
|
|
2015-03-17 22:08:00 +01:00
|
|
|
TEST_F(SpatialDBTest, FeatureSetSerializeTest) {
|
2015-06-18 23:55:05 +02:00
|
|
|
if (!LZ4_Supported()) {
|
|
|
|
return;
|
|
|
|
}
|
SpatialDB
Summary:
This diff is adding spatial index support to RocksDB.
When creating the DB user specifies a list of spatial indexes. Spatial indexes can cover different areas and have different resolution (i.e. number of tiles). This is useful for supporting different zoom levels.
Each element inserted into SpatialDB has:
* a bounding box, which determines how will the element be indexed
* string blob, which will usually be WKB representation of the polygon (http://en.wikipedia.org/wiki/Well-known_text)
* feature set, which is a map of key-value pairs, where value can be int, double, bool, null or a string. FeatureSet will be a set of tags associated with geo elements (for example, 'road': 'highway' and similar)
* a list of indexes to insert the element in. For example, small river element will be inserted in index for high zoom level, while country border will be inserted in all indexes (including the index for low zoom level).
Each query is executed on single spatial index. Query guarantees that it will return all elements intersecting the specified bounding box, but it might also return some extra non-intersecting elements.
Test Plan: Added bunch of unit tests in spatial_db_test
Reviewers: dhruba, yinwang
Reviewed By: yinwang
Subscribers: leveldb
Differential Revision: https://reviews.facebook.net/D20361
2014-07-23 20:22:58 +02:00
|
|
|
FeatureSet fs;
|
|
|
|
|
|
|
|
fs.Set("a", std::string("b"));
|
|
|
|
fs.Set("x", static_cast<uint64_t>(3));
|
|
|
|
fs.Set("y", false);
|
|
|
|
fs.Set("n", Variant()); // null
|
|
|
|
fs.Set("m", 3.25);
|
|
|
|
|
|
|
|
ASSERT_TRUE(fs.Find("w") == fs.end());
|
|
|
|
ASSERT_TRUE(fs.Find("x") != fs.end());
|
|
|
|
ASSERT_TRUE((*fs.Find("x")).second == Variant(static_cast<uint64_t>(3)));
|
|
|
|
ASSERT_TRUE((*fs.Find("y")).second != Variant(true));
|
|
|
|
std::set<std::string> keys({"a", "x", "y", "n", "m"});
|
|
|
|
for (const auto& x : fs) {
|
|
|
|
ASSERT_TRUE(keys.find(x.first) != keys.end());
|
|
|
|
keys.erase(x.first);
|
|
|
|
}
|
|
|
|
ASSERT_EQ(keys.size(), 0U);
|
|
|
|
|
|
|
|
std::string serialized;
|
|
|
|
fs.Serialize(&serialized);
|
|
|
|
|
|
|
|
FeatureSet deserialized;
|
|
|
|
ASSERT_TRUE(deserialized.Deserialize(serialized));
|
|
|
|
|
|
|
|
ASSERT_TRUE(deserialized.Contains("a"));
|
|
|
|
ASSERT_EQ(deserialized.Get("a").type(), Variant::kString);
|
|
|
|
ASSERT_EQ(deserialized.Get("a").get_string(), "b");
|
|
|
|
ASSERT_TRUE(deserialized.Contains("x"));
|
|
|
|
ASSERT_EQ(deserialized.Get("x").type(), Variant::kInt);
|
|
|
|
ASSERT_EQ(deserialized.Get("x").get_int(), static_cast<uint64_t>(3));
|
|
|
|
ASSERT_TRUE(deserialized.Contains("y"));
|
|
|
|
ASSERT_EQ(deserialized.Get("y").type(), Variant::kBool);
|
|
|
|
ASSERT_EQ(deserialized.Get("y").get_bool(), false);
|
|
|
|
ASSERT_TRUE(deserialized.Contains("n"));
|
|
|
|
ASSERT_EQ(deserialized.Get("n").type(), Variant::kNull);
|
|
|
|
ASSERT_TRUE(deserialized.Contains("m"));
|
|
|
|
ASSERT_EQ(deserialized.Get("m").type(), Variant::kDouble);
|
|
|
|
ASSERT_EQ(deserialized.Get("m").get_double(), 3.25);
|
|
|
|
|
|
|
|
// corrupted serialization
|
Adapt three unit tests with newer compiler/libraries (#4562)
Summary:
This fixes three tests that fail with relatively recent tools and libraries:
The tests are:
* `spatial_db_test`
* `table_test`
* `db_universal_compaction_test`
I'm using:
* `gcc` 7.3.0
* `glibc` 2.27
* `snappy` 1.1.7
* `gflags` 2.2.1
* `zlib` 1.2.11
* `bzip2` 1.0.6.0.1
* `lz4` 1.8.2
* `jemalloc` 5.0.1
The versions used in the Travis environment (which is two Ubuntu LTS versions behind the current one and doesn't use `lz4` or `jemalloc`) don't seem to have a problem. However, to be safe, I verified that these tests pass with and without my changes in a trusty Docker container without `lz4` and `jemalloc`.
However, I do get an unrelated set of other failures when using a trusty Docker container that uses `lz4` and `jemalloc`:
```
db/db_universal_compaction_test.cc:506: Failure
Value of: num + 1
Actual: 3
Expected: NumSortedRuns(1)
Which is: 4
[ FAILED ] UniversalCompactionNumLevels/DBTestUniversalCompaction.DynamicUniversalCompactionReadAmplification/0, where GetParam() = (1, false) (1189 ms)
[ RUN ] UniversalCompactionNumLevels/DBTestUniversalCompaction.DynamicUniversalCompactionReadAmplification/1
db/db_universal_compaction_test.cc:506: Failure
Value of: num + 1
Actual: 3
Expected: NumSortedRuns(1)
Which is: 4
[ FAILED ] UniversalCompactionNumLevels/DBTestUniversalCompaction.DynamicUniversalCompactionReadAmplification/1, where GetParam() = (1, true) (1246 ms)
[ RUN ] UniversalCompactionNumLevels/DBTestUniversalCompaction.DynamicUniversalCompactionReadAmplification/2
db/db_universal_compaction_test.cc:506: Failure
Value of: num + 1
Actual: 3
Expected: NumSortedRuns(1)
Which is: 4
[ FAILED ] UniversalCompactionNumLevels/DBTestUniversalCompaction.DynamicUniversalCompactionReadAmplification/2, where GetParam() = (3, false) (1237 ms)
[ RUN ] UniversalCompactionNumLevels/DBTestUniversalCompaction.DynamicUniversalCompactionReadAmplification/3
db/db_universal_compaction_test.cc:506: Failure
Value of: num + 1
Actual: 3
Expected: NumSortedRuns(1)
Which is: 4
[ FAILED ] UniversalCompactionNumLevels/DBTestUniversalCompaction.DynamicUniversalCompactionReadAmplification/3, where GetParam() = (3, true) (1195 ms)
[ RUN ] UniversalCompactionNumLevels/DBTestUniversalCompaction.DynamicUniversalCompactionReadAmplification/4
db/db_universal_compaction_test.cc:506: Failure
Value of: num + 1
Actual: 3
Expected: NumSortedRuns(1)
Which is: 4
[ FAILED ] UniversalCompactionNumLevels/DBTestUniversalCompaction.DynamicUniversalCompactionReadAmplification/4, where GetParam() = (5, false) (1161 ms)
[ RUN ] UniversalCompactionNumLevels/DBTestUniversalCompaction.DynamicUniversalCompactionReadAmplification/5
db/db_universal_compaction_test.cc:506: Failure
Value of: num + 1
Actual: 3
Expected: NumSortedRuns(1)
Which is: 4
[ FAILED ] UniversalCompactionNumLevels/DBTestUniversalCompaction.DynamicUniversalCompactionReadAmplification/5, where GetParam() = (5, true) (1229 ms)
```
I haven't attempted to fix these since I'm not using trusty and Travis doesn't use `lz4` and `jemalloc`. However, the final commit in this PR does at least fix the compilation errors that occur when using trusty's version of `lz4`.
Pull Request resolved: https://github.com/facebook/rocksdb/pull/4562
Differential Revision: D10510917
Pulled By: maysamyabandeh
fbshipit-source-id: 59534042015ec339270e5fc2f6ac4d859370d189
2018-10-24 17:14:39 +02:00
|
|
|
serialized = serialized.substr(0, serialized.size() - 1);
|
SpatialDB
Summary:
This diff is adding spatial index support to RocksDB.
When creating the DB user specifies a list of spatial indexes. Spatial indexes can cover different areas and have different resolution (i.e. number of tiles). This is useful for supporting different zoom levels.
Each element inserted into SpatialDB has:
* a bounding box, which determines how will the element be indexed
* string blob, which will usually be WKB representation of the polygon (http://en.wikipedia.org/wiki/Well-known_text)
* feature set, which is a map of key-value pairs, where value can be int, double, bool, null or a string. FeatureSet will be a set of tags associated with geo elements (for example, 'road': 'highway' and similar)
* a list of indexes to insert the element in. For example, small river element will be inserted in index for high zoom level, while country border will be inserted in all indexes (including the index for low zoom level).
Each query is executed on single spatial index. Query guarantees that it will return all elements intersecting the specified bounding box, but it might also return some extra non-intersecting elements.
Test Plan: Added bunch of unit tests in spatial_db_test
Reviewers: dhruba, yinwang
Reviewed By: yinwang
Subscribers: leveldb
Differential Revision: https://reviews.facebook.net/D20361
2014-07-23 20:22:58 +02:00
|
|
|
deserialized.Clear();
|
|
|
|
ASSERT_TRUE(!deserialized.Deserialize(serialized));
|
|
|
|
}
|
|
|
|
|
2015-03-17 22:08:00 +01:00
|
|
|
TEST_F(SpatialDBTest, TestNextID) {
|
2015-06-18 23:55:05 +02:00
|
|
|
if (!LZ4_Supported()) {
|
|
|
|
return;
|
|
|
|
}
|
2014-07-24 22:39:33 +02:00
|
|
|
ASSERT_OK(SpatialDB::Create(
|
SpatialDB
Summary:
This diff is adding spatial index support to RocksDB.
When creating the DB user specifies a list of spatial indexes. Spatial indexes can cover different areas and have different resolution (i.e. number of tiles). This is useful for supporting different zoom levels.
Each element inserted into SpatialDB has:
* a bounding box, which determines how will the element be indexed
* string blob, which will usually be WKB representation of the polygon (http://en.wikipedia.org/wiki/Well-known_text)
* feature set, which is a map of key-value pairs, where value can be int, double, bool, null or a string. FeatureSet will be a set of tags associated with geo elements (for example, 'road': 'highway' and similar)
* a list of indexes to insert the element in. For example, small river element will be inserted in index for high zoom level, while country border will be inserted in all indexes (including the index for low zoom level).
Each query is executed on single spatial index. Query guarantees that it will return all elements intersecting the specified bounding box, but it might also return some extra non-intersecting elements.
Test Plan: Added bunch of unit tests in spatial_db_test
Reviewers: dhruba, yinwang
Reviewed By: yinwang
Subscribers: leveldb
Differential Revision: https://reviews.facebook.net/D20361
2014-07-23 20:22:58 +02:00
|
|
|
SpatialDBOptions(), dbname_,
|
2014-07-24 22:39:33 +02:00
|
|
|
{SpatialIndexOptions("simple", BoundingBox<double>(0, 0, 100, 100), 2)}));
|
SpatialDB
Summary:
This diff is adding spatial index support to RocksDB.
When creating the DB user specifies a list of spatial indexes. Spatial indexes can cover different areas and have different resolution (i.e. number of tiles). This is useful for supporting different zoom levels.
Each element inserted into SpatialDB has:
* a bounding box, which determines how will the element be indexed
* string blob, which will usually be WKB representation of the polygon (http://en.wikipedia.org/wiki/Well-known_text)
* feature set, which is a map of key-value pairs, where value can be int, double, bool, null or a string. FeatureSet will be a set of tags associated with geo elements (for example, 'road': 'highway' and similar)
* a list of indexes to insert the element in. For example, small river element will be inserted in index for high zoom level, while country border will be inserted in all indexes (including the index for low zoom level).
Each query is executed on single spatial index. Query guarantees that it will return all elements intersecting the specified bounding box, but it might also return some extra non-intersecting elements.
Test Plan: Added bunch of unit tests in spatial_db_test
Reviewers: dhruba, yinwang
Reviewed By: yinwang
Subscribers: leveldb
Differential Revision: https://reviews.facebook.net/D20361
2014-07-23 20:22:58 +02:00
|
|
|
|
2014-07-24 22:39:33 +02:00
|
|
|
ASSERT_OK(SpatialDB::Open(SpatialDBOptions(), dbname_, &db_));
|
SpatialDB
Summary:
This diff is adding spatial index support to RocksDB.
When creating the DB user specifies a list of spatial indexes. Spatial indexes can cover different areas and have different resolution (i.e. number of tiles). This is useful for supporting different zoom levels.
Each element inserted into SpatialDB has:
* a bounding box, which determines how will the element be indexed
* string blob, which will usually be WKB representation of the polygon (http://en.wikipedia.org/wiki/Well-known_text)
* feature set, which is a map of key-value pairs, where value can be int, double, bool, null or a string. FeatureSet will be a set of tags associated with geo elements (for example, 'road': 'highway' and similar)
* a list of indexes to insert the element in. For example, small river element will be inserted in index for high zoom level, while country border will be inserted in all indexes (including the index for low zoom level).
Each query is executed on single spatial index. Query guarantees that it will return all elements intersecting the specified bounding box, but it might also return some extra non-intersecting elements.
Test Plan: Added bunch of unit tests in spatial_db_test
Reviewers: dhruba, yinwang
Reviewed By: yinwang
Subscribers: leveldb
Differential Revision: https://reviews.facebook.net/D20361
2014-07-23 20:22:58 +02:00
|
|
|
ASSERT_OK(db_->Insert(WriteOptions(), BoundingBox<double>(5, 5, 10, 10),
|
|
|
|
"one", FeatureSet(), {"simple"}));
|
|
|
|
ASSERT_OK(db_->Insert(WriteOptions(), BoundingBox<double>(10, 10, 15, 15),
|
|
|
|
"two", FeatureSet(), {"simple"}));
|
|
|
|
delete db_;
|
2017-05-19 19:43:11 +02:00
|
|
|
db_ = nullptr;
|
SpatialDB
Summary:
This diff is adding spatial index support to RocksDB.
When creating the DB user specifies a list of spatial indexes. Spatial indexes can cover different areas and have different resolution (i.e. number of tiles). This is useful for supporting different zoom levels.
Each element inserted into SpatialDB has:
* a bounding box, which determines how will the element be indexed
* string blob, which will usually be WKB representation of the polygon (http://en.wikipedia.org/wiki/Well-known_text)
* feature set, which is a map of key-value pairs, where value can be int, double, bool, null or a string. FeatureSet will be a set of tags associated with geo elements (for example, 'road': 'highway' and similar)
* a list of indexes to insert the element in. For example, small river element will be inserted in index for high zoom level, while country border will be inserted in all indexes (including the index for low zoom level).
Each query is executed on single spatial index. Query guarantees that it will return all elements intersecting the specified bounding box, but it might also return some extra non-intersecting elements.
Test Plan: Added bunch of unit tests in spatial_db_test
Reviewers: dhruba, yinwang
Reviewed By: yinwang
Subscribers: leveldb
Differential Revision: https://reviews.facebook.net/D20361
2014-07-23 20:22:58 +02:00
|
|
|
|
2014-07-24 22:39:33 +02:00
|
|
|
ASSERT_OK(SpatialDB::Open(SpatialDBOptions(), dbname_, &db_));
|
2017-05-19 19:43:11 +02:00
|
|
|
assert(db_ != nullptr);
|
SpatialDB
Summary:
This diff is adding spatial index support to RocksDB.
When creating the DB user specifies a list of spatial indexes. Spatial indexes can cover different areas and have different resolution (i.e. number of tiles). This is useful for supporting different zoom levels.
Each element inserted into SpatialDB has:
* a bounding box, which determines how will the element be indexed
* string blob, which will usually be WKB representation of the polygon (http://en.wikipedia.org/wiki/Well-known_text)
* feature set, which is a map of key-value pairs, where value can be int, double, bool, null or a string. FeatureSet will be a set of tags associated with geo elements (for example, 'road': 'highway' and similar)
* a list of indexes to insert the element in. For example, small river element will be inserted in index for high zoom level, while country border will be inserted in all indexes (including the index for low zoom level).
Each query is executed on single spatial index. Query guarantees that it will return all elements intersecting the specified bounding box, but it might also return some extra non-intersecting elements.
Test Plan: Added bunch of unit tests in spatial_db_test
Reviewers: dhruba, yinwang
Reviewed By: yinwang
Subscribers: leveldb
Differential Revision: https://reviews.facebook.net/D20361
2014-07-23 20:22:58 +02:00
|
|
|
ASSERT_OK(db_->Insert(WriteOptions(), BoundingBox<double>(55, 55, 65, 65),
|
|
|
|
"three", FeatureSet(), {"simple"}));
|
|
|
|
delete db_;
|
|
|
|
|
2014-07-24 22:39:33 +02:00
|
|
|
ASSERT_OK(SpatialDB::Open(SpatialDBOptions(), dbname_, &db_));
|
SpatialDB
Summary:
This diff is adding spatial index support to RocksDB.
When creating the DB user specifies a list of spatial indexes. Spatial indexes can cover different areas and have different resolution (i.e. number of tiles). This is useful for supporting different zoom levels.
Each element inserted into SpatialDB has:
* a bounding box, which determines how will the element be indexed
* string blob, which will usually be WKB representation of the polygon (http://en.wikipedia.org/wiki/Well-known_text)
* feature set, which is a map of key-value pairs, where value can be int, double, bool, null or a string. FeatureSet will be a set of tags associated with geo elements (for example, 'road': 'highway' and similar)
* a list of indexes to insert the element in. For example, small river element will be inserted in index for high zoom level, while country border will be inserted in all indexes (including the index for low zoom level).
Each query is executed on single spatial index. Query guarantees that it will return all elements intersecting the specified bounding box, but it might also return some extra non-intersecting elements.
Test Plan: Added bunch of unit tests in spatial_db_test
Reviewers: dhruba, yinwang
Reviewed By: yinwang
Subscribers: leveldb
Differential Revision: https://reviews.facebook.net/D20361
2014-07-23 20:22:58 +02:00
|
|
|
AssertCursorResults(BoundingBox<double>(0, 0, 100, 100), "simple",
|
|
|
|
{"one", "two", "three"});
|
|
|
|
delete db_;
|
|
|
|
}
|
|
|
|
|
2015-03-17 22:08:00 +01:00
|
|
|
TEST_F(SpatialDBTest, FeatureSetTest) {
|
2015-06-18 23:55:05 +02:00
|
|
|
if (!LZ4_Supported()) {
|
|
|
|
return;
|
|
|
|
}
|
2014-07-24 22:39:33 +02:00
|
|
|
ASSERT_OK(SpatialDB::Create(
|
SpatialDB
Summary:
This diff is adding spatial index support to RocksDB.
When creating the DB user specifies a list of spatial indexes. Spatial indexes can cover different areas and have different resolution (i.e. number of tiles). This is useful for supporting different zoom levels.
Each element inserted into SpatialDB has:
* a bounding box, which determines how will the element be indexed
* string blob, which will usually be WKB representation of the polygon (http://en.wikipedia.org/wiki/Well-known_text)
* feature set, which is a map of key-value pairs, where value can be int, double, bool, null or a string. FeatureSet will be a set of tags associated with geo elements (for example, 'road': 'highway' and similar)
* a list of indexes to insert the element in. For example, small river element will be inserted in index for high zoom level, while country border will be inserted in all indexes (including the index for low zoom level).
Each query is executed on single spatial index. Query guarantees that it will return all elements intersecting the specified bounding box, but it might also return some extra non-intersecting elements.
Test Plan: Added bunch of unit tests in spatial_db_test
Reviewers: dhruba, yinwang
Reviewed By: yinwang
Subscribers: leveldb
Differential Revision: https://reviews.facebook.net/D20361
2014-07-23 20:22:58 +02:00
|
|
|
SpatialDBOptions(), dbname_,
|
2014-07-24 22:39:33 +02:00
|
|
|
{SpatialIndexOptions("simple", BoundingBox<double>(0, 0, 100, 100), 2)}));
|
|
|
|
ASSERT_OK(SpatialDB::Open(SpatialDBOptions(), dbname_, &db_));
|
SpatialDB
Summary:
This diff is adding spatial index support to RocksDB.
When creating the DB user specifies a list of spatial indexes. Spatial indexes can cover different areas and have different resolution (i.e. number of tiles). This is useful for supporting different zoom levels.
Each element inserted into SpatialDB has:
* a bounding box, which determines how will the element be indexed
* string blob, which will usually be WKB representation of the polygon (http://en.wikipedia.org/wiki/Well-known_text)
* feature set, which is a map of key-value pairs, where value can be int, double, bool, null or a string. FeatureSet will be a set of tags associated with geo elements (for example, 'road': 'highway' and similar)
* a list of indexes to insert the element in. For example, small river element will be inserted in index for high zoom level, while country border will be inserted in all indexes (including the index for low zoom level).
Each query is executed on single spatial index. Query guarantees that it will return all elements intersecting the specified bounding box, but it might also return some extra non-intersecting elements.
Test Plan: Added bunch of unit tests in spatial_db_test
Reviewers: dhruba, yinwang
Reviewed By: yinwang
Subscribers: leveldb
Differential Revision: https://reviews.facebook.net/D20361
2014-07-23 20:22:58 +02:00
|
|
|
|
|
|
|
FeatureSet fs;
|
|
|
|
fs.Set("a", std::string("b"));
|
|
|
|
fs.Set("c", std::string("d"));
|
|
|
|
|
|
|
|
ASSERT_OK(db_->Insert(WriteOptions(), BoundingBox<double>(5, 5, 10, 10),
|
|
|
|
"one", fs, {"simple"}));
|
|
|
|
|
|
|
|
Cursor* c =
|
|
|
|
db_->Query(ReadOptions(), BoundingBox<double>(5, 5, 10, 10), "simple");
|
|
|
|
|
|
|
|
ASSERT_TRUE(c->Valid());
|
|
|
|
ASSERT_EQ(c->blob().compare("one"), 0);
|
|
|
|
FeatureSet returned = c->feature_set();
|
|
|
|
ASSERT_TRUE(returned.Contains("a"));
|
|
|
|
ASSERT_TRUE(!returned.Contains("b"));
|
|
|
|
ASSERT_TRUE(returned.Contains("c"));
|
|
|
|
ASSERT_EQ(returned.Get("a").type(), Variant::kString);
|
|
|
|
ASSERT_EQ(returned.Get("a").get_string(), "b");
|
|
|
|
ASSERT_EQ(returned.Get("c").type(), Variant::kString);
|
|
|
|
ASSERT_EQ(returned.Get("c").get_string(), "d");
|
|
|
|
|
|
|
|
c->Next();
|
|
|
|
ASSERT_TRUE(!c->Valid());
|
|
|
|
|
|
|
|
delete c;
|
|
|
|
delete db_;
|
|
|
|
}
|
|
|
|
|
2015-03-17 22:08:00 +01:00
|
|
|
TEST_F(SpatialDBTest, SimpleTest) {
|
2015-06-18 23:55:05 +02:00
|
|
|
if (!LZ4_Supported()) {
|
|
|
|
return;
|
|
|
|
}
|
2014-08-26 02:50:18 +02:00
|
|
|
// iter 0 -- not read only
|
|
|
|
// iter 1 -- read only
|
|
|
|
for (int iter = 0; iter < 2; ++iter) {
|
|
|
|
DestroyDB(dbname_, Options());
|
|
|
|
ASSERT_OK(SpatialDB::Create(
|
|
|
|
SpatialDBOptions(), dbname_,
|
|
|
|
{SpatialIndexOptions("index", BoundingBox<double>(0, 0, 128, 128),
|
|
|
|
3)}));
|
|
|
|
ASSERT_OK(SpatialDB::Open(SpatialDBOptions(), dbname_, &db_));
|
2017-05-19 19:43:11 +02:00
|
|
|
assert(db_ != nullptr);
|
2014-08-26 02:50:18 +02:00
|
|
|
|
|
|
|
ASSERT_OK(db_->Insert(WriteOptions(), BoundingBox<double>(33, 17, 63, 79),
|
|
|
|
"one", FeatureSet(), {"index"}));
|
|
|
|
ASSERT_OK(db_->Insert(WriteOptions(), BoundingBox<double>(65, 65, 111, 111),
|
|
|
|
"two", FeatureSet(), {"index"}));
|
|
|
|
ASSERT_OK(db_->Insert(WriteOptions(), BoundingBox<double>(1, 49, 127, 63),
|
|
|
|
"three", FeatureSet(), {"index"}));
|
|
|
|
ASSERT_OK(db_->Insert(WriteOptions(), BoundingBox<double>(20, 100, 21, 101),
|
|
|
|
"four", FeatureSet(), {"index"}));
|
|
|
|
ASSERT_OK(db_->Insert(WriteOptions(), BoundingBox<double>(81, 33, 127, 63),
|
|
|
|
"five", FeatureSet(), {"index"}));
|
|
|
|
ASSERT_OK(db_->Insert(WriteOptions(), BoundingBox<double>(1, 65, 47, 95),
|
|
|
|
"six", FeatureSet(), {"index"}));
|
|
|
|
|
|
|
|
if (iter == 1) {
|
|
|
|
delete db_;
|
2017-05-19 19:43:11 +02:00
|
|
|
db_ = nullptr;
|
2014-08-26 02:50:18 +02:00
|
|
|
ASSERT_OK(SpatialDB::Open(SpatialDBOptions(), dbname_, &db_, true));
|
|
|
|
}
|
SpatialDB
Summary:
This diff is adding spatial index support to RocksDB.
When creating the DB user specifies a list of spatial indexes. Spatial indexes can cover different areas and have different resolution (i.e. number of tiles). This is useful for supporting different zoom levels.
Each element inserted into SpatialDB has:
* a bounding box, which determines how will the element be indexed
* string blob, which will usually be WKB representation of the polygon (http://en.wikipedia.org/wiki/Well-known_text)
* feature set, which is a map of key-value pairs, where value can be int, double, bool, null or a string. FeatureSet will be a set of tags associated with geo elements (for example, 'road': 'highway' and similar)
* a list of indexes to insert the element in. For example, small river element will be inserted in index for high zoom level, while country border will be inserted in all indexes (including the index for low zoom level).
Each query is executed on single spatial index. Query guarantees that it will return all elements intersecting the specified bounding box, but it might also return some extra non-intersecting elements.
Test Plan: Added bunch of unit tests in spatial_db_test
Reviewers: dhruba, yinwang
Reviewed By: yinwang
Subscribers: leveldb
Differential Revision: https://reviews.facebook.net/D20361
2014-07-23 20:22:58 +02:00
|
|
|
|
2014-08-26 02:50:18 +02:00
|
|
|
AssertCursorResults(BoundingBox<double>(33, 17, 47, 31), "index", {"one"});
|
|
|
|
AssertCursorResults(BoundingBox<double>(17, 33, 79, 63), "index",
|
|
|
|
{"one", "three"});
|
|
|
|
AssertCursorResults(BoundingBox<double>(17, 81, 63, 111), "index",
|
|
|
|
{"four", "six"});
|
|
|
|
AssertCursorResults(BoundingBox<double>(85, 86, 85, 86), "index", {"two"});
|
|
|
|
AssertCursorResults(BoundingBox<double>(33, 1, 127, 111), "index",
|
|
|
|
{"one", "two", "three", "five", "six"});
|
|
|
|
// even though the bounding box doesn't intersect, we got "four" back
|
|
|
|
// because
|
|
|
|
// it's in the same tile
|
|
|
|
AssertCursorResults(BoundingBox<double>(18, 98, 19, 99), "index", {"four"});
|
|
|
|
AssertCursorResults(BoundingBox<double>(130, 130, 131, 131), "index", {});
|
|
|
|
AssertCursorResults(BoundingBox<double>(81, 17, 127, 31), "index", {});
|
|
|
|
AssertCursorResults(BoundingBox<double>(90, 50, 91, 51), "index",
|
|
|
|
{"three", "five"});
|
|
|
|
|
|
|
|
delete db_;
|
2017-05-19 19:43:11 +02:00
|
|
|
db_ = nullptr;
|
2014-08-26 02:50:18 +02:00
|
|
|
}
|
SpatialDB
Summary:
This diff is adding spatial index support to RocksDB.
When creating the DB user specifies a list of spatial indexes. Spatial indexes can cover different areas and have different resolution (i.e. number of tiles). This is useful for supporting different zoom levels.
Each element inserted into SpatialDB has:
* a bounding box, which determines how will the element be indexed
* string blob, which will usually be WKB representation of the polygon (http://en.wikipedia.org/wiki/Well-known_text)
* feature set, which is a map of key-value pairs, where value can be int, double, bool, null or a string. FeatureSet will be a set of tags associated with geo elements (for example, 'road': 'highway' and similar)
* a list of indexes to insert the element in. For example, small river element will be inserted in index for high zoom level, while country border will be inserted in all indexes (including the index for low zoom level).
Each query is executed on single spatial index. Query guarantees that it will return all elements intersecting the specified bounding box, but it might also return some extra non-intersecting elements.
Test Plan: Added bunch of unit tests in spatial_db_test
Reviewers: dhruba, yinwang
Reviewed By: yinwang
Subscribers: leveldb
Differential Revision: https://reviews.facebook.net/D20361
2014-07-23 20:22:58 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
namespace {
|
|
|
|
std::string RandomStr(Random* rnd) {
|
|
|
|
std::string r;
|
|
|
|
for (int k = 0; k < 10; ++k) {
|
2017-10-19 19:48:47 +02:00
|
|
|
r.push_back(static_cast<char>(rnd->Uniform(26)) + 'a');
|
SpatialDB
Summary:
This diff is adding spatial index support to RocksDB.
When creating the DB user specifies a list of spatial indexes. Spatial indexes can cover different areas and have different resolution (i.e. number of tiles). This is useful for supporting different zoom levels.
Each element inserted into SpatialDB has:
* a bounding box, which determines how will the element be indexed
* string blob, which will usually be WKB representation of the polygon (http://en.wikipedia.org/wiki/Well-known_text)
* feature set, which is a map of key-value pairs, where value can be int, double, bool, null or a string. FeatureSet will be a set of tags associated with geo elements (for example, 'road': 'highway' and similar)
* a list of indexes to insert the element in. For example, small river element will be inserted in index for high zoom level, while country border will be inserted in all indexes (including the index for low zoom level).
Each query is executed on single spatial index. Query guarantees that it will return all elements intersecting the specified bounding box, but it might also return some extra non-intersecting elements.
Test Plan: Added bunch of unit tests in spatial_db_test
Reviewers: dhruba, yinwang
Reviewed By: yinwang
Subscribers: leveldb
Differential Revision: https://reviews.facebook.net/D20361
2014-07-23 20:22:58 +02:00
|
|
|
}
|
|
|
|
return r;
|
|
|
|
}
|
|
|
|
|
|
|
|
BoundingBox<int> RandomBoundingBox(int limit, Random* rnd, int max_size) {
|
|
|
|
BoundingBox<int> r;
|
|
|
|
r.min_x = rnd->Uniform(limit - 1);
|
|
|
|
r.min_y = rnd->Uniform(limit - 1);
|
|
|
|
r.max_x = r.min_x + rnd->Uniform(std::min(limit - 1 - r.min_x, max_size)) + 1;
|
|
|
|
r.max_y = r.min_y + rnd->Uniform(std::min(limit - 1 - r.min_y, max_size)) + 1;
|
|
|
|
return r;
|
|
|
|
}
|
|
|
|
|
|
|
|
BoundingBox<double> ScaleBB(BoundingBox<int> b, double step) {
|
|
|
|
return BoundingBox<double>(b.min_x * step + 1, b.min_y * step + 1,
|
|
|
|
(b.max_x + 1) * step - 1,
|
|
|
|
(b.max_y + 1) * step - 1);
|
|
|
|
}
|
|
|
|
|
|
|
|
} // namespace
|
|
|
|
|
2015-03-17 22:08:00 +01:00
|
|
|
TEST_F(SpatialDBTest, RandomizedTest) {
|
2015-06-18 23:55:05 +02:00
|
|
|
if (!LZ4_Supported()) {
|
|
|
|
return;
|
|
|
|
}
|
SpatialDB
Summary:
This diff is adding spatial index support to RocksDB.
When creating the DB user specifies a list of spatial indexes. Spatial indexes can cover different areas and have different resolution (i.e. number of tiles). This is useful for supporting different zoom levels.
Each element inserted into SpatialDB has:
* a bounding box, which determines how will the element be indexed
* string blob, which will usually be WKB representation of the polygon (http://en.wikipedia.org/wiki/Well-known_text)
* feature set, which is a map of key-value pairs, where value can be int, double, bool, null or a string. FeatureSet will be a set of tags associated with geo elements (for example, 'road': 'highway' and similar)
* a list of indexes to insert the element in. For example, small river element will be inserted in index for high zoom level, while country border will be inserted in all indexes (including the index for low zoom level).
Each query is executed on single spatial index. Query guarantees that it will return all elements intersecting the specified bounding box, but it might also return some extra non-intersecting elements.
Test Plan: Added bunch of unit tests in spatial_db_test
Reviewers: dhruba, yinwang
Reviewed By: yinwang
Subscribers: leveldb
Differential Revision: https://reviews.facebook.net/D20361
2014-07-23 20:22:58 +02:00
|
|
|
Random rnd(301);
|
|
|
|
std::vector<std::pair<std::string, BoundingBox<int>>> elements;
|
|
|
|
|
|
|
|
BoundingBox<double> spatial_index_bounds(0, 0, (1LL << 32), (1LL << 32));
|
2014-07-24 22:39:33 +02:00
|
|
|
ASSERT_OK(SpatialDB::Create(
|
SpatialDB
Summary:
This diff is adding spatial index support to RocksDB.
When creating the DB user specifies a list of spatial indexes. Spatial indexes can cover different areas and have different resolution (i.e. number of tiles). This is useful for supporting different zoom levels.
Each element inserted into SpatialDB has:
* a bounding box, which determines how will the element be indexed
* string blob, which will usually be WKB representation of the polygon (http://en.wikipedia.org/wiki/Well-known_text)
* feature set, which is a map of key-value pairs, where value can be int, double, bool, null or a string. FeatureSet will be a set of tags associated with geo elements (for example, 'road': 'highway' and similar)
* a list of indexes to insert the element in. For example, small river element will be inserted in index for high zoom level, while country border will be inserted in all indexes (including the index for low zoom level).
Each query is executed on single spatial index. Query guarantees that it will return all elements intersecting the specified bounding box, but it might also return some extra non-intersecting elements.
Test Plan: Added bunch of unit tests in spatial_db_test
Reviewers: dhruba, yinwang
Reviewed By: yinwang
Subscribers: leveldb
Differential Revision: https://reviews.facebook.net/D20361
2014-07-23 20:22:58 +02:00
|
|
|
SpatialDBOptions(), dbname_,
|
2014-07-24 22:39:33 +02:00
|
|
|
{SpatialIndexOptions("index", spatial_index_bounds, 7)}));
|
|
|
|
ASSERT_OK(SpatialDB::Open(SpatialDBOptions(), dbname_, &db_));
|
SpatialDB
Summary:
This diff is adding spatial index support to RocksDB.
When creating the DB user specifies a list of spatial indexes. Spatial indexes can cover different areas and have different resolution (i.e. number of tiles). This is useful for supporting different zoom levels.
Each element inserted into SpatialDB has:
* a bounding box, which determines how will the element be indexed
* string blob, which will usually be WKB representation of the polygon (http://en.wikipedia.org/wiki/Well-known_text)
* feature set, which is a map of key-value pairs, where value can be int, double, bool, null or a string. FeatureSet will be a set of tags associated with geo elements (for example, 'road': 'highway' and similar)
* a list of indexes to insert the element in. For example, small river element will be inserted in index for high zoom level, while country border will be inserted in all indexes (including the index for low zoom level).
Each query is executed on single spatial index. Query guarantees that it will return all elements intersecting the specified bounding box, but it might also return some extra non-intersecting elements.
Test Plan: Added bunch of unit tests in spatial_db_test
Reviewers: dhruba, yinwang
Reviewed By: yinwang
Subscribers: leveldb
Differential Revision: https://reviews.facebook.net/D20361
2014-07-23 20:22:58 +02:00
|
|
|
double step = (1LL << 32) / (1 << 7);
|
|
|
|
|
|
|
|
for (int i = 0; i < 1000; ++i) {
|
|
|
|
std::string blob = RandomStr(&rnd);
|
|
|
|
BoundingBox<int> bbox = RandomBoundingBox(128, &rnd, 10);
|
|
|
|
ASSERT_OK(db_->Insert(WriteOptions(), ScaleBB(bbox, step), blob,
|
|
|
|
FeatureSet(), {"index"}));
|
|
|
|
elements.push_back(make_pair(blob, bbox));
|
|
|
|
}
|
|
|
|
|
2014-11-13 22:34:29 +01:00
|
|
|
// parallel
|
|
|
|
db_->Compact(2);
|
|
|
|
// serial
|
|
|
|
db_->Compact(1);
|
SpatialDB
Summary:
This diff is adding spatial index support to RocksDB.
When creating the DB user specifies a list of spatial indexes. Spatial indexes can cover different areas and have different resolution (i.e. number of tiles). This is useful for supporting different zoom levels.
Each element inserted into SpatialDB has:
* a bounding box, which determines how will the element be indexed
* string blob, which will usually be WKB representation of the polygon (http://en.wikipedia.org/wiki/Well-known_text)
* feature set, which is a map of key-value pairs, where value can be int, double, bool, null or a string. FeatureSet will be a set of tags associated with geo elements (for example, 'road': 'highway' and similar)
* a list of indexes to insert the element in. For example, small river element will be inserted in index for high zoom level, while country border will be inserted in all indexes (including the index for low zoom level).
Each query is executed on single spatial index. Query guarantees that it will return all elements intersecting the specified bounding box, but it might also return some extra non-intersecting elements.
Test Plan: Added bunch of unit tests in spatial_db_test
Reviewers: dhruba, yinwang
Reviewed By: yinwang
Subscribers: leveldb
Differential Revision: https://reviews.facebook.net/D20361
2014-07-23 20:22:58 +02:00
|
|
|
|
|
|
|
for (int i = 0; i < 1000; ++i) {
|
|
|
|
BoundingBox<int> int_bbox = RandomBoundingBox(128, &rnd, 10);
|
|
|
|
BoundingBox<double> double_bbox = ScaleBB(int_bbox, step);
|
|
|
|
std::vector<std::string> blobs;
|
|
|
|
for (auto e : elements) {
|
|
|
|
if (e.second.Intersects(int_bbox)) {
|
|
|
|
blobs.push_back(e.first);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
AssertCursorResults(double_bbox, "index", blobs);
|
|
|
|
}
|
|
|
|
|
|
|
|
delete db_;
|
|
|
|
}
|
|
|
|
|
|
|
|
} // namespace spatial
|
|
|
|
} // namespace rocksdb
|
|
|
|
|
2015-03-17 22:08:00 +01:00
|
|
|
int main(int argc, char** argv) {
|
|
|
|
::testing::InitGoogleTest(&argc, argv);
|
|
|
|
return RUN_ALL_TESTS();
|
|
|
|
}
|
2015-07-14 03:35:03 +02:00
|
|
|
|
|
|
|
#else
|
|
|
|
#include <stdio.h>
|
|
|
|
|
2018-04-16 02:19:57 +02:00
|
|
|
int main(int /*argc*/, char** /*argv*/) {
|
2015-07-14 03:35:03 +02:00
|
|
|
fprintf(stderr, "SKIPPED as SpatialDB is not supported in ROCKSDB_LITE\n");
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
#endif // !ROCKSDB_LITE
|