Skip to content

Commit 53d3ec4

Browse files
committed
CDRIVER-2558 add label to server selection error
1 parent 16fa9f1 commit 53d3ec4

15 files changed

+395
-135
lines changed

src/libmongoc/src/mongoc/mongoc-bulk-operation.c

Lines changed: 21 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -695,17 +695,13 @@ mongoc_bulk_operation_execute (mongoc_bulk_operation_t *bulk, /* IN */
695695

696696
BSON_ASSERT (bulk);
697697

698-
if (reply) {
699-
bson_init (reply);
700-
}
701-
702698
if (!bulk->client) {
703699
bson_set_error (error,
704700
MONGOC_ERROR_COMMAND,
705701
MONGOC_ERROR_COMMAND_INVALID_ARG,
706702
"mongoc_bulk_operation_execute() requires a client "
707703
"and one has not been set.");
708-
RETURN (false);
704+
GOTO (err);
709705
}
710706
cluster = &bulk->client->cluster;
711707

@@ -722,14 +718,14 @@ mongoc_bulk_operation_execute (mongoc_bulk_operation_t *bulk, /* IN */
722718
MONGOC_ERROR_COMMAND_INVALID_ARG,
723719
"mongoc_bulk_operation_execute() requires a database "
724720
"and one has not been set.");
725-
RETURN (false);
721+
GOTO (err);
726722
} else if (!bulk->collection) {
727723
bson_set_error (error,
728724
MONGOC_ERROR_COMMAND,
729725
MONGOC_ERROR_COMMAND_INVALID_ARG,
730726
"mongoc_bulk_operation_execute() requires a collection "
731727
"and one has not been set.");
732-
RETURN (false);
728+
GOTO (err);
733729
}
734730

735731
/* error stored by functions like mongoc_bulk_operation_insert that
@@ -739,29 +735,38 @@ mongoc_bulk_operation_execute (mongoc_bulk_operation_t *bulk, /* IN */
739735
memcpy (error, &bulk->result.error, sizeof (bson_error_t));
740736
}
741737

742-
RETURN (false);
738+
GOTO (err);
743739
}
744740

745741
if (!bulk->commands.len) {
746742
bson_set_error (error,
747743
MONGOC_ERROR_COMMAND,
748744
MONGOC_ERROR_COMMAND_INVALID_ARG,
749745
"Cannot do an empty bulk write");
750-
RETURN (false);
746+
GOTO (err);
751747
}
752748

753749
for (i = 0; i < bulk->commands.len; i++) {
754750
if (bulk->server_id) {
755-
server_stream = mongoc_cluster_stream_for_server (
756-
cluster, bulk->server_id, true /* reconnect_ok */, error);
751+
server_stream =
752+
mongoc_cluster_stream_for_server (cluster,
753+
bulk->server_id,
754+
true /* reconnect_ok */,
755+
bulk->session,
756+
reply,
757+
error);
757758
} else {
758-
server_stream = mongoc_cluster_stream_for_writes (cluster, error);
759+
server_stream = mongoc_cluster_stream_for_writes (
760+
cluster, bulk->session, reply, error);
759761
}
760762

761763
if (!server_stream) {
764+
/* stream_for_server and stream_for_writes initialize reply on error */
762765
RETURN (false);
763766
}
764767

768+
_mongoc_bson_init_if_set (reply);
769+
765770
command =
766771
&_mongoc_array_index (&bulk->commands, mongoc_write_command_t, i);
767772

@@ -796,6 +801,10 @@ mongoc_bulk_operation_execute (mongoc_bulk_operation_t *bulk, /* IN */
796801
error);
797802

798803
RETURN (ret ? bulk->server_id : 0);
804+
805+
err:
806+
_mongoc_bson_init_if_set (reply);
807+
RETURN (false);
799808
}
800809

801810
void

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

Lines changed: 48 additions & 44 deletions
Original file line numberDiff line numberDiff line change
@@ -1566,8 +1566,8 @@ _mongoc_client_retryable_write_command_with_stream (
15661566
mongoc_server_stream_cleanup (retry_server_stream);
15671567
}
15681568

1569-
retry_server_stream =
1570-
mongoc_cluster_stream_for_writes (&client->cluster, &ignored_error);
1569+
retry_server_stream = mongoc_cluster_stream_for_writes (
1570+
&client->cluster, parts->assembled.session, NULL, &ignored_error);
15711571

15721572
if (retry_server_stream &&
15731573
retry_server_stream->sd->max_wire_version >=
@@ -1645,16 +1645,13 @@ mongoc_client_command_simple (mongoc_client_t *client,
16451645
* preference argument."
16461646
*/
16471647
server_stream =
1648-
mongoc_cluster_stream_for_reads (cluster, read_prefs, NULL, error);
1648+
mongoc_cluster_stream_for_reads (cluster, read_prefs, NULL, reply, error);
16491649

16501650
if (server_stream) {
16511651
ret = _mongoc_client_command_with_stream (
16521652
client, &parts, server_stream, reply, error);
16531653
} else {
1654-
if (reply) {
1655-
bson_init (reply);
1656-
}
1657-
1654+
/* reply initialized by mongoc_cluster_stream_for_reads */
16581655
ret = false;
16591656
}
16601657

@@ -1713,10 +1710,12 @@ _mongoc_client_command_with_opts (mongoc_client_t *client,
17131710
const mongoc_read_prefs_t *prefs = COALESCE (user_prefs, default_prefs);
17141711
mongoc_server_stream_t *server_stream = NULL;
17151712
mongoc_cluster_t *cluster;
1713+
mongoc_client_session_t *cs;
17161714
bson_t reply_local;
17171715
bson_t *reply_ptr;
17181716
int32_t wire_version;
17191717
int32_t wc_wire_version;
1718+
bool reply_initialized = false;
17201719
bool ret = false;
17211720

17221721
ENTRY;
@@ -1725,22 +1724,26 @@ _mongoc_client_command_with_opts (mongoc_client_t *client,
17251724
BSON_ASSERT (db_name);
17261725
BSON_ASSERT (command);
17271726

1727+
command_name = _mongoc_get_command_name (command);
1728+
cluster = &client->cluster;
1729+
reply_ptr = reply ? reply : &reply_local;
1730+
17281731
mongoc_cmd_parts_init (&parts, client, db_name, flags, command);
17291732
parts.is_read_command = (mode & MONGOC_CMD_READ);
17301733
parts.is_write_command = (mode & MONGOC_CMD_WRITE);
17311734

17321735
if (!_mongoc_read_write_opts_parse (client, opts, &read_write_opts, error)) {
1733-
GOTO (err);
1736+
GOTO (done);
17341737
}
17351738

1736-
command_name = _mongoc_get_command_name (command);
1739+
cs = read_write_opts.client_session;
17371740

17381741
if (!command_name) {
17391742
bson_set_error (error,
17401743
MONGOC_ERROR_COMMAND,
17411744
MONGOC_ERROR_COMMAND_INVALID_ARG,
17421745
"Empty command document");
1743-
GOTO (err);
1746+
GOTO (done);
17441747
}
17451748

17461749
if (_mongoc_client_session_in_txn (read_write_opts.client_session)) {
@@ -1750,15 +1753,15 @@ _mongoc_client_command_with_opts (mongoc_client_t *client,
17501753
MONGOC_ERROR_COMMAND,
17511754
MONGOC_ERROR_COMMAND_INVALID_ARG,
17521755
"Read preference in a transaction must be primary");
1753-
GOTO (err);
1756+
GOTO (done);
17541757
}
17551758

17561759
if (!bson_empty (&read_write_opts.readConcern)) {
17571760
bson_set_error (error,
17581761
MONGOC_ERROR_COMMAND,
17591762
MONGOC_ERROR_COMMAND_INVALID_ARG,
17601763
"Cannot set read concern after starting transaction");
1761-
GOTO (err);
1764+
GOTO (done);
17621765
}
17631766

17641767
if (read_write_opts.writeConcern &&
@@ -1768,16 +1771,14 @@ _mongoc_client_command_with_opts (mongoc_client_t *client,
17681771
MONGOC_ERROR_COMMAND,
17691772
MONGOC_ERROR_COMMAND_INVALID_ARG,
17701773
"Cannot set write concern after starting transaction");
1771-
GOTO (err);
1774+
GOTO (done);
17721775
}
17731776
}
17741777

1775-
reply_ptr = reply ? reply : &reply_local;
1776-
17771778
if (mode == MONGOC_CMD_READ || mode == MONGOC_CMD_RAW) {
17781779
/* NULL read pref is ok */
17791780
if (!_mongoc_read_prefs_validate (prefs, error)) {
1780-
GOTO (err);
1781+
GOTO (done);
17811782
}
17821783

17831784
parts.read_prefs = prefs;
@@ -1786,31 +1787,37 @@ _mongoc_client_command_with_opts (mongoc_client_t *client,
17861787
prefs = NULL;
17871788
}
17881789

1789-
cluster = &client->cluster;
1790-
17911790
if (read_write_opts.serverId) {
17921791
/* "serverId" passed in opts */
1793-
server_stream = mongoc_cluster_stream_for_server (
1794-
cluster, read_write_opts.serverId, true /* reconnect ok */, error);
1792+
server_stream =
1793+
mongoc_cluster_stream_for_server (cluster,
1794+
read_write_opts.serverId,
1795+
true /* reconnect ok */,
1796+
cs,
1797+
reply_ptr,
1798+
error);
17951799

17961800
if (server_stream && server_stream->sd->type != MONGOC_SERVER_MONGOS) {
17971801
parts.user_query_flags |= MONGOC_QUERY_SLAVE_OK;
17981802
}
17991803
} else if (parts.is_write_command) {
1800-
server_stream = mongoc_cluster_stream_for_writes (cluster, error);
1804+
server_stream =
1805+
mongoc_cluster_stream_for_writes (cluster, cs, reply_ptr, error);
18011806
} else {
1802-
server_stream = mongoc_cluster_stream_for_reads (
1803-
cluster, prefs, read_write_opts.client_session, error);
1807+
server_stream =
1808+
mongoc_cluster_stream_for_reads (cluster, prefs, cs, reply_ptr, error);
18041809
}
18051810

18061811
if (!server_stream) {
1807-
GOTO (err);
1812+
/* stream_for_reads/writes/server has initialized reply */
1813+
reply_initialized = true;
1814+
GOTO (done);
18081815
}
18091816

18101817
wire_version = server_stream->sd->max_wire_version;
18111818
if (!mongoc_cmd_parts_append_read_write (
18121819
&parts, &read_write_opts, wire_version, error)) {
1813-
GOTO (err);
1820+
GOTO (done);
18141821
}
18151822

18161823
if (mode & MONGOC_CMD_WRITE) {
@@ -1828,7 +1835,7 @@ _mongoc_client_command_with_opts (mongoc_client_t *client,
18281835
command_name,
18291836
wire_version,
18301837
wc_wire_version);
1831-
GOTO (err);
1838+
GOTO (done);
18321839
}
18331840

18341841
/* use default write concern unless it's in opts */
@@ -1837,7 +1844,7 @@ _mongoc_client_command_with_opts (mongoc_client_t *client,
18371844
wire_version >= wc_wire_version) {
18381845
if (!mongoc_cmd_parts_set_write_concern (
18391846
&parts, default_wc, wire_version, error)) {
1840-
GOTO (err);
1847+
GOTO (done);
18411848
}
18421849
}
18431850
}
@@ -1846,27 +1853,27 @@ _mongoc_client_command_with_opts (mongoc_client_t *client,
18461853
if ((mode & MONGOC_CMD_READ) && bson_empty (&read_write_opts.readConcern)) {
18471854
if (!mongoc_cmd_parts_set_read_concern (
18481855
&parts, default_rc, wire_version, error)) {
1849-
GOTO (err);
1856+
GOTO (done);
18501857
}
18511858
}
18521859

18531860
ret = _mongoc_client_command_with_stream (
18541861
client, &parts, server_stream, reply_ptr, error);
18551862

1863+
reply_initialized = true;
1864+
18561865
if (ret && (mode & MONGOC_CMD_WRITE)) {
18571866
ret = !_mongoc_parse_wc_err (reply_ptr, error);
18581867
}
1859-
if (reply_ptr == &reply_local) {
1860-
bson_destroy (reply_ptr);
1861-
}
1862-
GOTO (done);
1863-
1864-
err:
1865-
if (reply) {
1866-
bson_init (reply);
1867-
}
18681868

18691869
done:
1870+
if (reply_ptr == &reply_local) {
1871+
if (reply_initialized) {
1872+
bson_destroy (reply_ptr);
1873+
}
1874+
} else if (!reply_initialized) {
1875+
_mongoc_bson_init_if_set (reply);
1876+
}
18701877

18711878
if (server_stream) {
18721879
mongoc_server_stream_cleanup (server_stream);
@@ -2000,7 +2007,7 @@ mongoc_client_command_simple_with_server_id (
20002007
}
20012008

20022009
server_stream = mongoc_cluster_stream_for_server (
2003-
&client->cluster, server_id, true /* reconnect ok */, error);
2010+
&client->cluster, server_id, true /* reconnect ok */, NULL, reply, error);
20042011

20052012
if (server_stream) {
20062013
mongoc_cmd_parts_init (
@@ -2014,10 +2021,7 @@ mongoc_client_command_simple_with_server_id (
20142021
mongoc_server_stream_cleanup (server_stream);
20152022
RETURN (ret);
20162023
} else {
2017-
if (reply) {
2018-
bson_init (reply);
2019-
}
2020-
2024+
/* stream_for_server initialized reply */
20212025
RETURN (false);
20222026
}
20232027
}
@@ -2055,7 +2059,7 @@ _mongoc_client_kill_cursor (mongoc_client_t *client,
20552059

20562060
/* don't attempt reconnect if server unavailable, and ignore errors */
20572061
server_stream = mongoc_cluster_stream_for_server (
2058-
&client->cluster, server_id, false /* reconnect_ok */, NULL /* error */);
2062+
&client->cluster, server_id, false /* reconnect_ok */, NULL, NULL, NULL);
20592063

20602064
if (!server_stream) {
20612065
return;
@@ -2759,7 +2763,7 @@ _mongoc_client_end_sessions (mongoc_client_t *client)
27592763
}
27602764

27612765
stream = mongoc_cluster_stream_for_server (
2762-
cluster, server_id, false /* reconnect_ok */, &error);
2766+
cluster, server_id, false /* reconnect_ok */, NULL, NULL, &error);
27632767

27642768
if (!stream) {
27652769
MONGOC_WARNING ("Couldn't send \"endSessions\": %s", error.message);

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

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -119,16 +119,21 @@ mongoc_server_stream_t *
119119
mongoc_cluster_stream_for_reads (mongoc_cluster_t *cluster,
120120
const mongoc_read_prefs_t *read_prefs,
121121
const mongoc_client_session_t *cs,
122+
bson_t *reply,
122123
bson_error_t *error);
123124

124125
mongoc_server_stream_t *
125126
mongoc_cluster_stream_for_writes (mongoc_cluster_t *cluster,
127+
const mongoc_client_session_t *cs,
128+
bson_t *reply,
126129
bson_error_t *error);
127130

128131
mongoc_server_stream_t *
129132
mongoc_cluster_stream_for_server (mongoc_cluster_t *cluster,
130133
uint32_t server_id,
131134
bool reconnect_ok,
135+
const mongoc_client_session_t *cs,
136+
bson_t *reply,
132137
bson_error_t *error);
133138

134139
bool

0 commit comments

Comments
 (0)