Skip to content

Commit a468a81

Browse files
committed
CXX-687: add option class for index creation
1 parent b3ba233 commit a468a81

File tree

10 files changed

+748
-9
lines changed

10 files changed

+748
-9
lines changed

examples/mongocxx/index.cpp

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,9 @@
11
#include <bsoncxx/builder/stream/document.hpp>
22

3+
#include <bsoncxx/stdx/make_unique.hpp>
34
#include <mongocxx/client.hpp>
45
#include <mongocxx/instance.hpp>
6+
#include <mongocxx/stdx.hpp>
57
#include <mongocxx/uri.hpp>
68

79
using bsoncxx::builder::stream::document;
@@ -15,6 +17,11 @@ int main(int, char**) {
1517
mongocxx::client conn{mongocxx::uri{}};
1618

1719
auto db = conn["test"];
20+
try {
21+
db["restaurants"].drop();
22+
} catch (const std::exception&) {
23+
// Collection did not exist.
24+
}
1825

1926
// Create a single field index.
2027
{
@@ -27,10 +34,38 @@ int main(int, char**) {
2734

2835
// Create a compound index.
2936
{
37+
db["restaurants"].drop();
3038
// @begin: cpp-create-compound-index
3139
document index_spec;
3240
index_spec << "cuisine" << 1 << "address.zipcode" << -1;
3341
db["restaurants"].create_index(index_spec, {});
3442
// @end: cpp-create-compound-index
3543
}
44+
45+
// Create a unique index.
46+
{
47+
db["restaurants"].drop();
48+
// @begin: cpp-create-unique-index
49+
document index_spec;
50+
mongocxx::options::index index_options{};
51+
index_spec << "website" << 1;
52+
index_options.unique(true);
53+
db["restaurants"].create_index(index_spec, index_options);
54+
// @end: cpp-create-unique-index
55+
}
56+
57+
// Create an index with storage engine options
58+
{
59+
db["restaurants"].drop();
60+
// @begin: cpp-create-wt-options-index
61+
document index_spec;
62+
mongocxx::options::index index_options{};
63+
std::unique_ptr<mongocxx::options::index::wiredtiger_storage_options> wt_options =
64+
mongocxx::stdx::make_unique<mongocxx::options::index::wiredtiger_storage_options>();
65+
index_spec << "cuisine" << 1;
66+
wt_options->config_string("block_allocation=first");
67+
index_options.storage_options(std::move(wt_options));
68+
db["restaurants"].create_index(index_spec, index_options);
69+
// @begin: cpp-create-wt-options-index
70+
}
3671
}

src/mongocxx/CMakeLists.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,7 @@ set(mongocxx_sources
4747
options/find_one_and_delete.cpp
4848
options/find_one_and_replace.cpp
4949
options/find_one_and_update.cpp
50+
options/index.cpp
5051
options/insert.cpp
5152
options/ssl.cpp
5253
options/update.cpp

src/mongocxx/collection.cpp

Lines changed: 92 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -466,12 +466,102 @@ std::int64_t collection::count(bsoncxx::document::view filter, const options::co
466466
}
467467

468468
bsoncxx::document::value collection::create_index(bsoncxx::document::view keys,
469-
bsoncxx::document::view options) {
469+
const options::index& options) {
470470
scoped_bson_t bson_keys{keys};
471471
bson_error_t error;
472+
::mongoc_index_opt_geo_t geo_opt{};
473+
::mongoc_index_opt_t opt{};
474+
::mongoc_index_opt_wt_t wt_opt{};
475+
libmongoc::index_opt_init(&opt);
476+
477+
if (options.background()) {
478+
opt.background = *options.background();
479+
}
480+
481+
if (options.unique()) {
482+
opt.unique = *options.unique();
483+
}
484+
485+
if (options.name()) {
486+
opt.name = options.name()->c_str();
487+
}
488+
489+
if (options.sparse()) {
490+
opt.sparse = *options.sparse();
491+
}
492+
493+
if (options.storage_options()) {
494+
const options::index::wiredtiger_storage_options* wt_options;
495+
libmongoc::index_opt_wt_init(&wt_opt);
496+
497+
if (options.storage_options()->type() ==
498+
::mongoc_index_storage_opt_type_t::MONGOC_INDEX_STORAGE_OPT_WIREDTIGER) {
499+
wt_options = static_cast<const options::index::wiredtiger_storage_options*>(
500+
options.storage_options().get());
501+
502+
if (wt_options->config_string()) {
503+
wt_opt.config_str = wt_options->config_string()->c_str();
504+
}
505+
opt.storage_options = reinterpret_cast<mongoc_index_opt_storage_t*>(&wt_opt);
506+
}
507+
}
508+
509+
if (options.expire_after_seconds()) {
510+
opt.expire_after_seconds = *options.expire_after_seconds();
511+
}
512+
513+
if (options.version()) {
514+
opt.v = *options.version();
515+
}
516+
517+
if (options.weights()) {
518+
scoped_bson_t weights{options.weights()};
519+
opt.weights = weights.bson();
520+
}
521+
522+
if (options.default_language()) {
523+
opt.default_language = options.default_language()->c_str();
524+
}
525+
526+
if (options.language_override()) {
527+
opt.language_override = options.language_override()->c_str();
528+
}
529+
530+
if (options.partial_filter_expression()) {
531+
scoped_bson_t partial_filter_expression{options.partial_filter_expression()};
532+
opt.partial_filter_expression = partial_filter_expression.bson();
533+
}
534+
535+
if (options.twod_sphere_version() || options.twod_bits_precision() ||
536+
options.twod_location_min() || options.twod_location_max() ||
537+
options.haystack_bucket_size()) {
538+
libmongoc::index_opt_geo_init(&geo_opt);
539+
540+
if (options.twod_sphere_version()) {
541+
geo_opt.twod_sphere_version = *options.twod_sphere_version();
542+
}
543+
544+
if (options.twod_bits_precision()) {
545+
geo_opt.twod_bits_precision = *options.twod_bits_precision();
546+
}
547+
548+
if (options.twod_location_min()) {
549+
geo_opt.twod_location_min = *options.twod_location_min();
550+
}
551+
552+
if (options.twod_location_max()) {
553+
geo_opt.twod_location_max = *options.twod_location_max();
554+
}
555+
556+
if (options.haystack_bucket_size()) {
557+
geo_opt.haystack_bucket_size = *options.haystack_bucket_size();
558+
}
559+
560+
opt.geo_options = &geo_opt;
561+
}
472562

473563
auto result =
474-
libmongoc::collection_create_index(_impl->collection_t, bson_keys.bson(), nullptr, &error);
564+
libmongoc::collection_create_index(_impl->collection_t, bson_keys.bson(), &opt, &error);
475565

476566
if (!result) {
477567
throw exception::operation(std::make_tuple(error.message, error.code));

src/mongocxx/collection.hpp

Lines changed: 4 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,7 @@
3737
#include <mongocxx/options/find_one_and_delete.hpp>
3838
#include <mongocxx/options/find_one_and_replace.hpp>
3939
#include <mongocxx/options/find_one_and_update.hpp>
40+
#include <mongocxx/options/index.hpp>
4041
#include <mongocxx/options/insert.hpp>
4142
#include <mongocxx/options/update.hpp>
4243
#include <mongocxx/read_preference.hpp>
@@ -203,16 +204,14 @@ class MONGOCXX_API collection {
203204
/// @param keys
204205
/// The keys for the index: @c {a: 1, b: -1}
205206
/// @param options
206-
/// Optional arguments to index creation command, see ensureindex-options link
207+
/// Optional arguments, see mongocxx::options::index.
207208
///
208209
/// @throws exception::operation if index creation fails.
209210
///
210211
/// @see http://docs.mongodb.org/manual/reference/method/db.collection.createIndex/
211-
/// @see
212-
/// http://docs.mongodb.org/manual/reference/method/db.collection.ensureIndex/#ensureindex-options
213212
///
214-
bsoncxx::document::value create_index(
215-
bsoncxx::document::view keys, bsoncxx::document::view options = bsoncxx::document::view{});
213+
bsoncxx::document::value create_index(bsoncxx::document::view keys,
214+
const options::index& options = options::index());
216215

217216
///
218217
/// Deletes all matching documents from the collection.

src/mongocxx/options/index.cpp

Lines changed: 179 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,179 @@
1+
// Copyright 2015 MongoDB Inc.
2+
//
3+
// Licensed under the Apache License, Version 2.0 (the "License");
4+
// you may not use this file except in compliance with the License.
5+
// You may obtain a copy of the License at
6+
//
7+
// http://www.apache.org/licenses/LICENSE-2.0
8+
//
9+
// Unless required by applicable law or agreed to in writing, software
10+
// distributed under the License is distributed on an "AS IS" BASIS,
11+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
// See the License for the specific language governing permissions and
13+
// limitations under the License.
14+
15+
#include <mongocxx/options/index.hpp>
16+
17+
#include <bsoncxx/stdx/make_unique.hpp>
18+
#include <mongocxx/private/libmongoc.hpp>
19+
20+
namespace mongocxx {
21+
MONGOCXX_INLINE_NAMESPACE_BEGIN
22+
namespace options {
23+
24+
index::index() = default;
25+
26+
void index::background(bool background) {
27+
_background = background;
28+
}
29+
30+
void index::unique(bool unique) {
31+
_unique = unique;
32+
}
33+
34+
void index::name(std::string name) {
35+
_name = std::move(name);
36+
}
37+
38+
void index::sparse(bool sparse) {
39+
_sparse = sparse;
40+
}
41+
42+
void index::storage_options(std::unique_ptr<index::base_storage_options> storage_options) {
43+
_storage_options = std::move(storage_options);
44+
}
45+
46+
void index::storage_options(std::unique_ptr<index::wiredtiger_storage_options> storage_options) {
47+
_storage_options = std::move(std::unique_ptr<index::base_storage_options>(
48+
static_cast<index::base_storage_options*>(storage_options.release())));
49+
}
50+
51+
void index::expire_after_seconds(std::int32_t expire_after_seconds) {
52+
_expire_after_seconds = expire_after_seconds;
53+
}
54+
55+
void index::version(std::int32_t version) {
56+
_version = version;
57+
}
58+
59+
void index::weights(bsoncxx::document::view weights) {
60+
_weights = weights;
61+
}
62+
63+
void index::default_language(std::string default_language) {
64+
_default_language = std::move(default_language);
65+
}
66+
67+
void index::language_override(std::string language_override) {
68+
_language_override = std::move(language_override);
69+
}
70+
71+
void index::partial_filter_expression(bsoncxx::document::view partial_filter_expression) {
72+
_partial_filter_expression = partial_filter_expression;
73+
}
74+
75+
void index::twod_sphere_version(std::uint8_t twod_sphere_version) {
76+
_twod_sphere_version = twod_sphere_version;
77+
}
78+
79+
void index::twod_bits_precision(std::uint8_t twod_bits_precision) {
80+
_twod_bits_precision = twod_bits_precision;
81+
}
82+
83+
void index::twod_location_min(double twod_location_min) {
84+
_twod_location_min = twod_location_min;
85+
}
86+
87+
void index::twod_location_max(double twod_location_max) {
88+
_twod_location_max = twod_location_max;
89+
}
90+
91+
void index::haystack_bucket_size(double haystack_bucket_size) {
92+
_haystack_bucket_size = haystack_bucket_size;
93+
}
94+
95+
const stdx::optional<bool>& index::background() const {
96+
return _background;
97+
}
98+
99+
const stdx::optional<bool>& index::unique() const {
100+
return _unique;
101+
}
102+
103+
const stdx::optional<std::string>& index::name() const {
104+
return _name;
105+
}
106+
107+
const stdx::optional<bool>& index::sparse() const {
108+
return _sparse;
109+
}
110+
111+
const std::unique_ptr<index::base_storage_options>& index::storage_options() const {
112+
return _storage_options;
113+
}
114+
115+
const stdx::optional<std::int32_t>& index::expire_after_seconds() const {
116+
return _expire_after_seconds;
117+
}
118+
119+
const stdx::optional<std::int32_t>& index::version() const {
120+
return _version;
121+
}
122+
123+
const stdx::optional<bsoncxx::document::view>& index::weights() const {
124+
return _weights;
125+
}
126+
127+
const stdx::optional<std::string>& index::default_language() const {
128+
return _default_language;
129+
}
130+
131+
const stdx::optional<std::string>& index::language_override() const {
132+
return _language_override;
133+
}
134+
135+
const stdx::optional<bsoncxx::document::view>& index::partial_filter_expression() const {
136+
return _partial_filter_expression;
137+
}
138+
139+
const stdx::optional<std::uint8_t>& index::twod_sphere_version() const {
140+
return _twod_sphere_version;
141+
}
142+
143+
const stdx::optional<std::uint8_t>& index::twod_bits_precision() const {
144+
return _twod_bits_precision;
145+
}
146+
147+
const stdx::optional<double>& index::twod_location_min() const {
148+
return _twod_location_min;
149+
}
150+
151+
const stdx::optional<double>& index::twod_location_max() const {
152+
return _twod_location_max;
153+
}
154+
155+
const stdx::optional<double>& index::haystack_bucket_size() const {
156+
return _haystack_bucket_size;
157+
}
158+
159+
index::base_storage_options::~base_storage_options() = default;
160+
161+
index::wiredtiger_storage_options::~wiredtiger_storage_options() = default;
162+
163+
void index::wiredtiger_storage_options::config_string(std::string config_string) {
164+
_config_string = std::move(config_string);
165+
}
166+
167+
const stdx::optional<std::string>& index::wiredtiger_storage_options::config_string() const {
168+
return _config_string;
169+
}
170+
171+
const int index::wiredtiger_storage_options::type() const {
172+
return mongoc_index_storage_opt_type_t::MONGOC_INDEX_STORAGE_OPT_WIREDTIGER;
173+
}
174+
175+
} // namespace options
176+
MONGOCXX_INLINE_NAMESPACE_END
177+
} // namespace mongocxx
178+
179+
#include <mongocxx/config/postlude.hpp>

0 commit comments

Comments
 (0)