Skip to content

Commit 88f7749

Browse files
authored
continue snapshot reads implementation (#824)
* CDRIVER-4042 Add snapshot to all commands when enabled * CDRIVER-4043 Raise error for snapshot sessions on < 5.0 * Add listIndexes to unified test runner
1 parent 4ce4cce commit 88f7749

10 files changed

+807
-188
lines changed

src/libmongoc/src/mongoc/mongoc-client-private.h

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -94,6 +94,8 @@ BSON_BEGIN_DECLS
9494
#define WIRE_VERSION_4_9 12
9595
/* version corresponding to server 5.0 release */
9696
#define WIRE_VERSION_5_0 13
97+
/* first version to support snapshot reads */
98+
#define WIRE_VERSION_SNAPSHOT_READS 13
9799

98100
struct _mongoc_collection_t;
99101

@@ -147,9 +149,9 @@ BSON_STATIC_ASSERT2 (mongoc_cmd_rw,
147149
MONGOC_CMD_RW == (MONGOC_CMD_READ | MONGOC_CMD_WRITE));
148150

149151

150-
/* TODO (CDRIVER-4052): Move MONGOC_RR_DEFAULT_BUFFER_SIZE and _mongoc_client_get_rr to
151-
* mongoc-topology-private.h or in a separate file. There is no reason these
152-
* should be in mongoc-client. */
152+
/* TODO (CDRIVER-4052): Move MONGOC_RR_DEFAULT_BUFFER_SIZE and
153+
* _mongoc_client_get_rr to mongoc-topology-private.h or in a separate file.
154+
* There is no reason these should be in mongoc-client. */
153155
#define MONGOC_RR_DEFAULT_BUFFER_SIZE 1024
154156
bool
155157
_mongoc_client_get_rr (const char *service,

src/libmongoc/src/mongoc/mongoc-client-session-private.h

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -148,7 +148,6 @@ void
148148
_mongoc_client_session_append_read_concern (const mongoc_client_session_t *cs,
149149
const bson_t *user_read_concern,
150150
bool is_read_command,
151-
const char *cmd_name,
152151
bson_t *cmd);
153152

154153
void

src/libmongoc/src/mongoc/mongoc-client-session.c

Lines changed: 1 addition & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1569,7 +1569,6 @@ void
15691569
_mongoc_client_session_append_read_concern (const mongoc_client_session_t *cs,
15701570
const bson_t *rc,
15711571
bool is_read_command,
1572-
const char *cmd_name,
15731572
bson_t *cmd)
15741573
{
15751574
const mongoc_read_concern_t *txn_rc;
@@ -1579,7 +1578,6 @@ _mongoc_client_session_append_read_concern (const mongoc_client_session_t *cs,
15791578
bool has_timestamp;
15801579
bool is_snapshot;
15811580
bool has_level;
1582-
bool is_find_aggregate_distinct;
15831581
bson_t child;
15841582

15851583
ENTRY;
@@ -1593,16 +1591,11 @@ _mongoc_client_session_append_read_concern (const mongoc_client_session_t *cs,
15931591
return;
15941592
}
15951593

1596-
is_find_aggregate_distinct =
1597-
(!strcmp (cmd_name, "find") || !strcmp (cmd_name, "aggregate") ||
1598-
!strcmp (cmd_name, "distinct"));
1599-
16001594
has_timestamp =
16011595
(txn_state == MONGOC_INTERNAL_TRANSACTION_STARTING || is_read_command) &&
16021596
mongoc_session_opts_get_causal_consistency (&cs->opts) &&
16031597
cs->operation_timestamp;
1604-
is_snapshot = is_find_aggregate_distinct &&
1605-
mongoc_session_opts_get_snapshot (&cs->opts);
1598+
is_snapshot = mongoc_session_opts_get_snapshot (&cs->opts);
16061599
user_rc_has_level = rc && bson_has_field (rc, "level");
16071600
txn_has_level = txn_state == MONGOC_INTERNAL_TRANSACTION_STARTING &&
16081601
!mongoc_read_concern_is_default (txn_rc);

src/libmongoc/src/mongoc/mongoc-cmd.c

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -981,12 +981,24 @@ mongoc_cmd_parts_assemble (mongoc_cmd_parts_t *parts,
981981

982982
if (!is_get_more) {
983983
if (cs) {
984+
/* Snapshot Sessions Spec: "Snapshot reads require MongoDB 5.0+."
985+
* Throw an error if snapshot is enabled and wire version is less
986+
* than 13 before potentially appending "snapshot" read concern. */
987+
if (mongoc_session_opts_get_snapshot (&cs->opts) &&
988+
server_stream->sd->max_wire_version <
989+
WIRE_VERSION_SNAPSHOT_READS) {
990+
bson_set_error (error,
991+
MONGOC_ERROR_CLIENT,
992+
MONGOC_ERROR_CLIENT_SESSION_FAILURE,
993+
"Snapshot reads require MongoDB 5.0 or later");
994+
GOTO (done);
995+
}
996+
984997
_mongoc_cmd_parts_ensure_copied (parts);
985998
_mongoc_client_session_append_read_concern (
986999
cs,
9871000
&parts->read_concern_document,
9881001
parts->is_read_command,
989-
cmd_name,
9901002
&parts->assembled_body);
9911003
} else if (!bson_empty (&parts->read_concern_document)) {
9921004
_mongoc_cmd_parts_ensure_copied (parts);

src/libmongoc/tests/json/sessions/legacy/dirty-session-errors.json

Lines changed: 1 addition & 166 deletions
Original file line numberDiff line numberDiff line change
@@ -21,171 +21,6 @@
2121
}
2222
],
2323
"tests": [
24-
{
25-
"description": "Clean explicit session is not discarded",
26-
"operations": [
27-
{
28-
"name": "assertSessionNotDirty",
29-
"object": "testRunner",
30-
"arguments": {
31-
"session": "session0"
32-
}
33-
},
34-
{
35-
"name": "insertOne",
36-
"object": "collection",
37-
"arguments": {
38-
"session": "session0",
39-
"document": {
40-
"_id": 2
41-
}
42-
},
43-
"result": {
44-
"insertedId": 2
45-
}
46-
},
47-
{
48-
"name": "assertSessionNotDirty",
49-
"object": "testRunner",
50-
"arguments": {
51-
"session": "session0"
52-
}
53-
},
54-
{
55-
"name": "endSession",
56-
"object": "session0"
57-
},
58-
{
59-
"name": "find",
60-
"object": "collection",
61-
"arguments": {
62-
"filter": {
63-
"_id": -1
64-
}
65-
},
66-
"result": []
67-
},
68-
{
69-
"name": "assertSameLsidOnLastTwoCommands",
70-
"object": "testRunner"
71-
}
72-
],
73-
"expectations": [
74-
{
75-
"command_started_event": {
76-
"command": {
77-
"insert": "test",
78-
"documents": [
79-
{
80-
"_id": 2
81-
}
82-
],
83-
"ordered": true,
84-
"lsid": "session0"
85-
},
86-
"command_name": "insert",
87-
"database_name": "session-tests"
88-
}
89-
},
90-
{
91-
"command_started_event": {
92-
"command": {
93-
"find": "test",
94-
"filter": {
95-
"_id": -1
96-
},
97-
"lsid": "session0"
98-
},
99-
"command_name": "find",
100-
"database_name": "session-tests"
101-
}
102-
}
103-
],
104-
"outcome": {
105-
"collection": {
106-
"data": [
107-
{
108-
"_id": 1
109-
},
110-
{
111-
"_id": 2
112-
}
113-
]
114-
}
115-
}
116-
},
117-
{
118-
"description": "Clean implicit session is not discarded",
119-
"operations": [
120-
{
121-
"name": "insertOne",
122-
"object": "collection",
123-
"arguments": {
124-
"document": {
125-
"_id": 2
126-
}
127-
},
128-
"result": {
129-
"insertedId": 2
130-
}
131-
},
132-
{
133-
"name": "find",
134-
"object": "collection",
135-
"arguments": {
136-
"filter": {
137-
"_id": -1
138-
}
139-
},
140-
"result": []
141-
},
142-
{
143-
"name": "assertSameLsidOnLastTwoCommands",
144-
"object": "testRunner"
145-
}
146-
],
147-
"expectations": [
148-
{
149-
"command_started_event": {
150-
"command": {
151-
"insert": "test",
152-
"documents": [
153-
{
154-
"_id": 2
155-
}
156-
],
157-
"ordered": true
158-
},
159-
"command_name": "insert",
160-
"database_name": "session-tests"
161-
}
162-
},
163-
{
164-
"command_started_event": {
165-
"command": {
166-
"find": "test",
167-
"filter": {
168-
"_id": -1
169-
}
170-
},
171-
"command_name": "find",
172-
"database_name": "session-tests"
173-
}
174-
}
175-
],
176-
"outcome": {
177-
"collection": {
178-
"data": [
179-
{
180-
"_id": 1
181-
},
182-
{
183-
"_id": 2
184-
}
185-
]
186-
}
187-
}
188-
},
18924
{
19025
"description": "Dirty explicit session is discarded",
19126
"clientOptions": {
@@ -833,4 +668,4 @@
833668
}
834669
}
835670
]
836-
}
671+
}
Lines changed: 113 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,113 @@
1+
{
2+
"description": "snapshot-sessions-not-supported-client-error",
3+
"schemaVersion": "1.0",
4+
"runOnRequirements": [
5+
{
6+
"minServerVersion": "3.6",
7+
"maxServerVersion": "4.4.99"
8+
}
9+
],
10+
"createEntities": [
11+
{
12+
"client": {
13+
"id": "client0",
14+
"observeEvents": [
15+
"commandStartedEvent",
16+
"commandFailedEvent"
17+
]
18+
}
19+
},
20+
{
21+
"database": {
22+
"id": "database0",
23+
"client": "client0",
24+
"databaseName": "database0"
25+
}
26+
},
27+
{
28+
"collection": {
29+
"id": "collection0",
30+
"database": "database0",
31+
"collectionName": "collection0"
32+
}
33+
},
34+
{
35+
"session": {
36+
"id": "session0",
37+
"client": "client0",
38+
"sessionOptions": {
39+
"snapshot": true
40+
}
41+
}
42+
}
43+
],
44+
"initialData": [
45+
{
46+
"collectionName": "collection0",
47+
"databaseName": "database0",
48+
"documents": [
49+
{
50+
"_id": 1,
51+
"x": 11
52+
}
53+
]
54+
}
55+
],
56+
"tests": [
57+
{
58+
"description": "Client error on find with snapshot",
59+
"operations": [
60+
{
61+
"name": "find",
62+
"object": "collection0",
63+
"arguments": {
64+
"session": "session0",
65+
"filter": {}
66+
},
67+
"expectError": {
68+
"isClientError": true,
69+
"errorContains": "Snapshot reads require MongoDB 5.0 or later"
70+
}
71+
}
72+
],
73+
"expectEvents": []
74+
},
75+
{
76+
"description": "Client error on aggregate with snapshot",
77+
"operations": [
78+
{
79+
"name": "aggregate",
80+
"object": "collection0",
81+
"arguments": {
82+
"session": "session0",
83+
"pipeline": []
84+
},
85+
"expectError": {
86+
"isClientError": true,
87+
"errorContains": "Snapshot reads require MongoDB 5.0 or later"
88+
}
89+
}
90+
],
91+
"expectEvents": []
92+
},
93+
{
94+
"description": "Client error on distinct with snapshot",
95+
"operations": [
96+
{
97+
"name": "distinct",
98+
"object": "collection0",
99+
"arguments": {
100+
"fieldName": "x",
101+
"filter": {},
102+
"session": "session0"
103+
},
104+
"expectError": {
105+
"isClientError": true,
106+
"errorContains": "Snapshot reads require MongoDB 5.0 or later"
107+
}
108+
}
109+
],
110+
"expectEvents": []
111+
}
112+
]
113+
}

0 commit comments

Comments
 (0)