Compare commits
61 Commits
CLOUDP-698
...
r4.2.0-rc1
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
fdb56a92bf | ||
|
|
4f5550adae | ||
|
|
e52a0c4c3d | ||
|
|
214255bc66 | ||
|
|
6b893a4922 | ||
|
|
24d6fb41ff | ||
|
|
52149b6489 | ||
|
|
3dfc6949c2 | ||
|
|
41bf8a1db1 | ||
|
|
ba4d91f29e | ||
|
|
242a60b08c | ||
|
|
b66bef2c26 | ||
|
|
1f7ff3efd4 | ||
|
|
d9c43f9884 | ||
|
|
110cdbef08 | ||
|
|
6e5f9f0519 | ||
|
|
dbb9a7c7ac | ||
|
|
6256840f8d | ||
|
|
a3525b8116 | ||
|
|
fda81c9d47 | ||
|
|
4fc54eade0 | ||
|
|
13f72f733b | ||
|
|
0eb92d645b | ||
|
|
1dbfa74ff2 | ||
|
|
1b1cb58108 | ||
|
|
e291cbea17 | ||
|
|
339cec66f0 | ||
|
|
ce8dec71a3 | ||
|
|
95a175ffa9 | ||
|
|
ecd0a5451e | ||
|
|
0eea301d3d | ||
|
|
29624abb15 | ||
|
|
caa94f234c | ||
|
|
75cf3adf68 | ||
|
|
0c9d0e1810 | ||
|
|
b05af50a62 | ||
|
|
0a9bf038eb | ||
|
|
9013cc245b | ||
|
|
70de3cf1c8 | ||
|
|
b9677eb4b9 | ||
|
|
3215041d3b | ||
|
|
c798277149 | ||
|
|
b063681f5c | ||
|
|
a01fc83106 | ||
|
|
4b9ce53bec | ||
|
|
cabac3a0eb | ||
|
|
26f5879ea1 | ||
|
|
01ff5cd303 | ||
|
|
1f7005185f | ||
|
|
dbad05c3e7 | ||
|
|
f17ad42fb5 | ||
|
|
960e89726f | ||
|
|
0d26400300 | ||
|
|
aeb8148c54 | ||
|
|
84f1ba4d33 | ||
|
|
e2e5dc658a | ||
|
|
6484628232 | ||
|
|
777d16318b | ||
|
|
c710c8429d | ||
|
|
6ac1954e5b | ||
|
|
4c25ec3f60 |
@@ -147,15 +147,24 @@ function mount_drive {
|
||||
/sbin/mdadm --detail --scan > /etc/mdadm.conf
|
||||
/sbin/blockdev --setra 32 $device_name
|
||||
else
|
||||
device_name=$devices
|
||||
device_name="/dev/$device_names"
|
||||
fi
|
||||
|
||||
# Mount the $root_dir drive(s)
|
||||
/sbin/mkfs.$fs_type $mount_options -f $device_name
|
||||
echo "$device_name /$root_dir auto noatime 0 0" | tee -a /etc/fstab
|
||||
# We add an entry for the device to /etc/fstab so it is automatically mounted following a
|
||||
# machine reboot. The device is not guaranteed to be assigned the same name across restarts so
|
||||
# we use its UUID in order to identify it.
|
||||
#
|
||||
# We also specify type=$fs_type in the /etc/fstab entry because specifying type=auto on
|
||||
# Amazon Linux AMI 2018.03 leads to the drive not being mounted automatically following a
|
||||
# machine reboot.
|
||||
device_uuid=$(blkid -o value -s UUID "$device_name")
|
||||
echo "Adding entry to /etc/fstab for device '$device_name' with UUID '$device_uuid'"
|
||||
echo "UUID=$device_uuid /$root_dir $fs_type noatime 0 0" | tee -a /etc/fstab
|
||||
mkdir /$root_dir || true
|
||||
chmod 777 /$root_dir
|
||||
mount -t $fs_type $device_name /$root_dir
|
||||
mount -t $fs_type "UUID=$device_uuid" /$root_dir
|
||||
for sub_dir in $sub_dirs
|
||||
do
|
||||
mkdir -p /$root_dir/$sub_dir
|
||||
|
||||
@@ -1,10 +1,10 @@
|
||||
# This test suite exercises core, generic transactions behavior using the multiple transactions
|
||||
# oplog entry format. The tests in this suite, pulled from 'jstests/core/txns', should be "topology
|
||||
# agnostic". They ideally generalize to single replica sets and sharded clusters. Since transactions
|
||||
# aren't supported on MongoDB standalones in 4.0, we run this set of tests in their own suite,
|
||||
# against a 1-node replica set, to provide the most basic layer of test coverage. This allows us to
|
||||
# verify basic transaction behavior against a local node, without the need to exercise data
|
||||
# replication machinery.
|
||||
# This test suite exercises core, generic transactions behavior with the maximum number of
|
||||
# operations in a single transaction oplog entry set to 1. The tests in this suite, pulled from
|
||||
# 'jstests/core/txns', should be "topology agnostic". They ideally generalize to single replica
|
||||
# sets and sharded clusters. Since transactions aren't supported on MongoDB standalones in 4.0, we
|
||||
# run this set of tests in their own suite, against a 1-node replica set, to provide the most basic
|
||||
# layer of test coverage. This allows us to verify basic transaction behavior against a local node,
|
||||
# without the need to exercise data replication machinery.
|
||||
|
||||
test_kind: js_test
|
||||
selector:
|
||||
@@ -36,6 +36,6 @@ executor:
|
||||
mongod_options:
|
||||
set_parameters:
|
||||
enableTestCommands: 1
|
||||
useMultipleOplogEntryFormatForTransactions: true
|
||||
maxNumberOfTransactionOperationsInSingleOplogEntry: 1
|
||||
# Use a 1-node replica set.
|
||||
num_nodes: 1
|
||||
@@ -15,4 +15,4 @@ executor:
|
||||
global_vars:
|
||||
TestData:
|
||||
setParameters:
|
||||
useMultipleOplogEntryFormatForTransactions: true
|
||||
maxNumberOfTransactionOperationsInSingleOplogEntry: 1
|
||||
@@ -1,5 +1,5 @@
|
||||
# This test suite is intended to exercise the primary and secondary behavior for transactions
|
||||
# using the multiple oplog entries format.
|
||||
# with the maximum number of transaction operations in a single oplog entry set to 1.
|
||||
|
||||
test_kind: js_test
|
||||
|
||||
@@ -41,5 +41,5 @@ executor:
|
||||
mongod_options:
|
||||
set_parameters:
|
||||
enableTestCommands: 1
|
||||
useMultipleOplogEntryFormatForTransactions: true
|
||||
maxNumberOfTransactionOperationsInSingleOplogEntry: 1
|
||||
num_nodes: 2
|
||||
22
buildscripts/resmokeconfig/suites/search_beta_auth.yml
Normal file
22
buildscripts/resmokeconfig/suites/search_beta_auth.yml
Normal file
@@ -0,0 +1,22 @@
|
||||
config_variables:
|
||||
- &keyFile jstests/libs/authTestsKey
|
||||
- &keyFileData Thiskeyisonlyforrunningthesuitewithauthenticationdontuseitinanytestsdirectly
|
||||
|
||||
test_kind: js_test
|
||||
|
||||
selector:
|
||||
roots:
|
||||
- src/mongo/db/modules/*/jstests/search_beta/*.js
|
||||
|
||||
executor:
|
||||
config:
|
||||
shell_options:
|
||||
global_vars:
|
||||
TestData:
|
||||
auth: true
|
||||
authMechanism: SCRAM-SHA-1
|
||||
keyFile: *keyFile
|
||||
keyFileData: *keyFileData
|
||||
roleGraphInvalidationIsFatal: true
|
||||
nodb: ''
|
||||
readMode: commands
|
||||
@@ -1,3 +1,7 @@
|
||||
config_variables:
|
||||
- &keyFile jstests/libs/authTestsKey
|
||||
- &keyFileData Thiskeyisonlyforrunningthesuitewithauthenticationdontuseitinanytestsdirectly
|
||||
|
||||
test_kind: js_test
|
||||
|
||||
selector:
|
||||
@@ -7,6 +11,13 @@ selector:
|
||||
executor:
|
||||
config:
|
||||
shell_options:
|
||||
global_vars:
|
||||
TestData:
|
||||
auth: true
|
||||
authMechanism: SCRAM-SHA-1
|
||||
keyFile: *keyFile
|
||||
keyFileData: *keyFileData
|
||||
roleGraphInvalidationIsFatal: true
|
||||
nodb: ''
|
||||
readMode: commands
|
||||
ssl: ''
|
||||
|
||||
717
etc/drivers_nightly.yml
Normal file
717
etc/drivers_nightly.yml
Normal file
@@ -0,0 +1,717 @@
|
||||
#####################################################
|
||||
# Drivers Nightly Tests #
|
||||
#####################################################
|
||||
|
||||
### Instructions for Adding a Driver ###
|
||||
# The Major sections are:
|
||||
|
||||
# VARIABLES
|
||||
# FUNCTIONS (MongoDB and Drivers)
|
||||
# TASKS (MongoDB and Drivers)
|
||||
# AXES (Drivers)
|
||||
# MODULES (MongoDB and Drivers)
|
||||
# BUILDVARIANTS (MongoDB and Drivers)
|
||||
|
||||
# The Major sections of this config file have a space that handles the Mongodb setup, compile and test.
|
||||
# And a section that handles the same for drivers after MongoDB and compiled, tested, and pushed.
|
||||
|
||||
# To Add a Driver:
|
||||
|
||||
# Add your repo to the MODULES section
|
||||
# Add your Driver-specific AXES and variables
|
||||
# Add your Driver-specific Matrix at the bottom of this file
|
||||
# Update the Driver-specific variables in the 'run driver tests' function if needed
|
||||
|
||||
stepback: true
|
||||
command_type: system
|
||||
|
||||
# Files that match an ignore-list pattern will not trigger a build, if they're the only modified
|
||||
# files in the patch.
|
||||
ignore:
|
||||
- ".*"
|
||||
- "!.clang-format"
|
||||
- "!.eslintrc.yml"
|
||||
- "*.md"
|
||||
- "*.rst"
|
||||
- "*.txt"
|
||||
- "/distsrc/**"
|
||||
- "/docs/**"
|
||||
- "/etc/*.yml"
|
||||
- "!/etc/drivers_nightly.yml"
|
||||
- "README"
|
||||
|
||||
#######################################
|
||||
# VARIABLES #
|
||||
#######################################
|
||||
variables:
|
||||
|
||||
# Used when the tests it runs depend only on mongod, mongos, the mongo shell and the tools.
|
||||
- &task_template
|
||||
name: template
|
||||
depends_on:
|
||||
- name: compile
|
||||
commands:
|
||||
- func: "do setup"
|
||||
- func: "run mongo tests"
|
||||
vars:
|
||||
resmoke_args: --help
|
||||
run_multiple_jobs: false
|
||||
max_jobs: 0 # If set in combination with run_multiple_jobs, will cap the number of jobs used.
|
||||
|
||||
# Used to list modules to retrieve from GitHub and apply patches if necessary.
|
||||
- &git_get_project
|
||||
command: git.get_project
|
||||
params:
|
||||
directory: src
|
||||
revisions: # for each module include revision as <module_name>: ${<module_name>_rev}
|
||||
enterprise: ${enterprise_rev}
|
||||
mongo-java-driver: ${mongo-java-driver_rev}
|
||||
mongo-python-driver: ${mongo-python-driver_rev}
|
||||
drivers-evergreen-tools: ${drivers-evergreen-tools_rev}
|
||||
|
||||
- &generate_compile_expansions
|
||||
command: shell.exec
|
||||
params:
|
||||
working_dir: src
|
||||
script: |
|
||||
set -o errexit
|
||||
set -o verbose
|
||||
|
||||
# We get the raw version string (r1.2.3-45-gabcdef) from git
|
||||
MONGO_VERSION=$(git describe)
|
||||
# If this is a patch build, we add the patch version id to the version string so we know
|
||||
# this build was a patch, and which evergreen task it came from
|
||||
if [ "${is_patch|}" = "true" ]; then
|
||||
MONGO_VERSION="$MONGO_VERSION-patch-${version_id}"
|
||||
fi
|
||||
|
||||
# This script converts the generated version string into a sanitized version string for
|
||||
# use by scons and uploading artifacts as well as information about for the scons cache.
|
||||
MONGO_VERSION=$MONGO_VERSION SCONS_CACHE_MODE=${scons_cache_mode|nolinked} USE_SCONS_CACHE=${use_scons_cache|false} ${python|/opt/mongodbtoolchain/v2/bin/python2} buildscripts/generate_compile_expansions.py --out compile_expansions.yml
|
||||
|
||||
- &apply_compile_expansions
|
||||
command: expansions.update
|
||||
params:
|
||||
file: src/compile_expansions.yml
|
||||
|
||||
#######################################
|
||||
# FUNCTIONS #
|
||||
#######################################
|
||||
|
||||
### MONGODB COMPILE & TEST FUNCTIONS ###
|
||||
|
||||
functions:
|
||||
|
||||
"fetch and extract binaries": &fetch_extract_binaries
|
||||
command: shell.exec
|
||||
params:
|
||||
working_dir: src
|
||||
script: |
|
||||
set -o errexit
|
||||
set -o verbose
|
||||
|
||||
curl -s https://s3.amazonaws.com/mciuploads/drivers-nightly/${platform}/${revision}/binaries/mongo-${revision}.${ext} --output mongodb-binaries.${ext}
|
||||
# When we call git_get_project and check out our source code, it creates a directory called 'mongo',
|
||||
# this isn't needed and interferes with our shell binary 'mongo' when we try to copy it.
|
||||
# To prevent this, we just remove the 'mongo' directory first, then we do our copy.
|
||||
mv mongo mongo-old || true
|
||||
${decompress} mongodb-binaries.${ext|tgz}
|
||||
chmod +x mongodb*/bin/*
|
||||
mv mongodb*/bin/* .
|
||||
|
||||
"get buildnumber": &get_buildnumber
|
||||
command: keyval.inc
|
||||
params:
|
||||
key: "v4.2"
|
||||
destination: "builder_num"
|
||||
|
||||
"setup credentials": &setup_credentials
|
||||
command: shell.exec
|
||||
params:
|
||||
working_dir: src
|
||||
silent: true
|
||||
script: |
|
||||
cat > mci.buildlogger <<END_OF_CREDS
|
||||
slavename='${slave}'
|
||||
passwd='${passwd}'
|
||||
builder='MCI_${build_variant}'
|
||||
build_num=${builder_num}
|
||||
build_phase='${task_name}_${execution}'
|
||||
END_OF_CREDS
|
||||
|
||||
"do setup":
|
||||
- *git_get_project
|
||||
- *fetch_extract_binaries
|
||||
- *get_buildnumber
|
||||
- *setup_credentials
|
||||
|
||||
|
||||
### FOR MONGODB TESTS ###
|
||||
"set up virtualenv":
|
||||
command: shell.exec
|
||||
type: test
|
||||
params:
|
||||
working_dir: src
|
||||
script: |
|
||||
# exit immediately if virtualenv is not found
|
||||
set -o errexit
|
||||
set -o verbose
|
||||
|
||||
virtualenv --system-site-packages ./venv
|
||||
|
||||
"run mongo tests":
|
||||
command: shell.exec
|
||||
type: test
|
||||
params:
|
||||
working_dir: src
|
||||
script: |
|
||||
set -o errexit
|
||||
set -o verbose
|
||||
|
||||
# check if virtualenv is set up
|
||||
if [ -d "venv" ]; then
|
||||
if [ "Windows_NT" = "$OS" ]; then
|
||||
. ./venv/Scripts/activate
|
||||
else
|
||||
. ./venv/bin/activate
|
||||
fi
|
||||
fi
|
||||
|
||||
extra_args=""
|
||||
processor_architecture=$(uname -m)
|
||||
num_jobs_available=${num_jobs_available|1}
|
||||
|
||||
if [ ${max_jobs|0} -gt 0 ] && [ ${max_jobs|0} -lt $num_jobs_available ]; then
|
||||
extra_args="$extra_args --jobs=${max_jobs}"
|
||||
else
|
||||
extra_args="$extra_args --jobs=$num_jobs_available"
|
||||
fi
|
||||
|
||||
${rlp_environment} \
|
||||
${python|/opt/mongodbtoolchain/v2/bin/python2} buildscripts/resmoke.py ${resmoke_args} $extra_args ${test_flags} --log=buildlogger --reportFile=report.json
|
||||
|
||||
"cleanup environment":
|
||||
command: shell.exec
|
||||
params:
|
||||
script: |
|
||||
set -o errexit
|
||||
set -o verbose
|
||||
|
||||
rm -rf src /data/db/* mongo-diskstats* mongo-coredumps.tgz ~/.aws
|
||||
pkill -9 orchest
|
||||
|
||||
### DRIVERS FUNCTIONS ###
|
||||
|
||||
"bootstrap mongo-orchestration":
|
||||
- command: shell.exec
|
||||
params:
|
||||
script: |
|
||||
${PREPARE_SHELL}
|
||||
echo "{ \"releases\": { \"default\": \"$MONGODB_BINARIES\" }}" > $MONGO_ORCHESTRATION_HOME/orchestration.config
|
||||
MONGODB_VERSION="nightly" MONGODB_DOWNLOAD_URL=${MONGODB_DOWNLOAD_URL} TOPOLOGY=${TOPOLOGY} AUTH=${AUTH} SSL=${SSL} sh ${DRIVERS_TOOLS}/.evergreen/run-orchestration.sh
|
||||
# run-orchestration generates expansion file with the MONGODB_URI for the cluster
|
||||
- command: expansions.update
|
||||
params:
|
||||
file: mo-expansion.yml
|
||||
|
||||
"run driver tests":
|
||||
- command: shell.exec
|
||||
type: test
|
||||
params:
|
||||
working_dir: "src"
|
||||
script: |
|
||||
cd ${DRIVER_WORKING_DIRECTORY}
|
||||
${PREPARE_SHELL}
|
||||
echo $DRIVERS_TOOLS
|
||||
echo $MONGO_ORCHESTRATION_HOME
|
||||
echo $MONGODB_BINARIES
|
||||
echo $UPLOAD_BUCKET
|
||||
echo $PROJECT_DIRECTORY
|
||||
|
||||
echo $TMPDIR
|
||||
echo $PATH
|
||||
echo $PROJECT
|
||||
|
||||
# If there are extra dependencies, we set them up here first
|
||||
file="${PROJECT_DIRECTORY}/.evergreen/install-dependencies.sh"
|
||||
# Don't use ${file} syntax here because evergreen treats it as an empty expansion.
|
||||
[ -f "$file" ] && sh $file || echo "$file not available, skipping"
|
||||
|
||||
### DRIVER-SPECIFIC VARIABLES HERE
|
||||
PYTHON_BINARY="${PYTHON_BINARY}" \
|
||||
JDK="${JDK}" \
|
||||
AUTH="${AUTH}" SSL="${SSL}" MONGODB_URI="${MONGODB_URI}" TOPOLOGY="${TOPOLOGY}" .evergreen/run-tests.sh
|
||||
|
||||
"fix absolute paths":
|
||||
- command: shell.exec
|
||||
params:
|
||||
script: |
|
||||
${PREPARE_SHELL}
|
||||
for filename in $(find ${DRIVERS_TOOLS} -name \*.json); do
|
||||
perl -p -i -e "s|ABSOLUTE_PATH_REPLACEMENT_TOKEN|${DRIVERS_TOOLS}|g" $filename
|
||||
done
|
||||
|
||||
"windows fix":
|
||||
- command: shell.exec
|
||||
params:
|
||||
script: |
|
||||
# Make sure we are on Windows, otherwise don't run
|
||||
if [ "Windows_NT" == "$OS" ]; then # Magic variable in cygwin
|
||||
${PREPARE_SHELL}
|
||||
for i in $(find ${DRIVERS_TOOLS}/.evergreen ${PROJECT_DIRECTORY}/.evergreen -name \*.sh); do
|
||||
cat $i | tr -d '\r' > $i.new
|
||||
mv $i.new $i
|
||||
done
|
||||
# Copy client certificate because symlinks do not work on Windows.
|
||||
cp ${DRIVERS_TOOLS}/.evergreen/x509gen/client.pem ${MONGO_ORCHESTRATION_HOME}/lib/client.pem
|
||||
fi
|
||||
|
||||
"make files executable":
|
||||
- command: shell.exec
|
||||
params:
|
||||
script: |
|
||||
${PREPARE_SHELL}
|
||||
for i in $(find ${DRIVERS_TOOLS}/.evergreen ${PROJECT_DIRECTORY}/.evergreen -name \*.sh); do
|
||||
chmod +x $i
|
||||
done
|
||||
|
||||
"init test-results":
|
||||
- command: shell.exec
|
||||
params:
|
||||
script: |
|
||||
${PREPARE_SHELL}
|
||||
echo '{"results": [{ "status": "FAIL", "test_file": "Build", "log_raw": "No test-results.json found was created" } ]}' > ${PROJECT_DIRECTORY}/test-results.json
|
||||
|
||||
"upload xml test results":
|
||||
- command: attach.xunit_results
|
||||
params:
|
||||
file: "${DRIVER_TEST_UPLOAD_DIRECTORY}"
|
||||
|
||||
|
||||
### UPLOAD MONGODB AND ORCHESTRATION LOGS ###
|
||||
"upload mo artifacts":
|
||||
- command: shell.exec
|
||||
params:
|
||||
script: |
|
||||
${PREPARE_SHELL}
|
||||
find $MONGO_ORCHESTRATION_HOME -name \*.log | xargs tar czf ${PROJECT_DIRECTORY}/mongodb-logs.tar.gz
|
||||
- command: s3.put
|
||||
params:
|
||||
aws_key: ${aws_key}
|
||||
aws_secret: ${aws_secret}
|
||||
local_file: ${PROJECT_DIRECTORY}/mongodb-logs.tar.gz
|
||||
remote_file: ${UPLOAD_BUCKET}/${build_variant}/${revision}/${version_id}/${build_id}/logs/${task_id}-${execution}-mongodb-logs.tar.gz
|
||||
bucket: mciuploads
|
||||
permissions: public-read
|
||||
content_type: ${content_type|application/x-gzip}
|
||||
display_name: "mongodb-logs.tar.gz"
|
||||
- command: s3.put
|
||||
params:
|
||||
aws_key: ${aws_key}
|
||||
aws_secret: ${aws_secret}
|
||||
local_file: ${DRIVERS_TOOLS}/.evergreen/orchestration/server.log
|
||||
remote_file: ${UPLOAD_BUCKET}/${build_variant}/${revision}/${version_id}/${build_id}/logs/${task_id}-${execution}-orchestration.log
|
||||
bucket: mciuploads
|
||||
permissions: public-read
|
||||
content_type: ${content_type|text/plain}
|
||||
display_name: "orchestration.log"
|
||||
|
||||
"setup drivers environment":
|
||||
- command: shell.exec
|
||||
params:
|
||||
working_dir: "src"
|
||||
script: |
|
||||
cd ${DRIVER_WORKING_DIRECTORY}
|
||||
# Get the current unique version of this checkout
|
||||
if [ "${is_patch}" = "true" ]; then
|
||||
CURRENT_VERSION=$(git describe)-patch-${version_id}
|
||||
else
|
||||
CURRENT_VERSION=latest
|
||||
fi
|
||||
|
||||
export DRIVERS_TOOLS="$(pwd)/../drivers-evergreen-tools"
|
||||
|
||||
# Python has cygwin path problems on Windows. Detect prospective mongo-orchestration home directory
|
||||
if [ "Windows_NT" == "$OS" ]; then # Magic variable in cygwin
|
||||
export DRIVERS_TOOLS=$(cygpath -m $DRIVERS_TOOLS)
|
||||
fi
|
||||
|
||||
echo "TESTING PLATFORM ${PLATFORM}"
|
||||
|
||||
export MONGO_ORCHESTRATION_HOME="$DRIVERS_TOOLS/.evergreen/orchestration"
|
||||
export MONGODB_BINARIES="$DRIVERS_TOOLS/mongodb/bin"
|
||||
export UPLOAD_BUCKET="${project}"
|
||||
export PROJECT_DIRECTORY="$(pwd)"
|
||||
export MONGODB_DOWNLOAD_URL="https://s3.amazonaws.com/mciuploads/drivers-nightly/${PLATFORM}/${revision}/binaries/mongo-${revision}.${FILE_EXT}"
|
||||
|
||||
cat <<EOT > expansion.yml
|
||||
CURRENT_VERSION: "$CURRENT_VERSION"
|
||||
DRIVERS_TOOLS: "$DRIVERS_TOOLS"
|
||||
MONGO_ORCHESTRATION_HOME: "$MONGO_ORCHESTRATION_HOME"
|
||||
MONGODB_BINARIES: "$MONGODB_BINARIES"
|
||||
UPLOAD_BUCKET: "$UPLOAD_BUCKET"
|
||||
PROJECT_DIRECTORY: "$PROJECT_DIRECTORY"
|
||||
MONGODB_DOWNLOAD_URL: "$MONGODB_DOWNLOAD_URL"
|
||||
PREPARE_SHELL: |
|
||||
set -o errexit
|
||||
set -o xtrace
|
||||
export DRIVERS_TOOLS="$DRIVERS_TOOLS"
|
||||
export MONGO_ORCHESTRATION_HOME="$MONGO_ORCHESTRATION_HOME"
|
||||
export MONGODB_BINARIES="$MONGODB_BINARIES"
|
||||
export UPLOAD_BUCKET="$UPLOAD_BUCKET"
|
||||
export PROJECT_DIRECTORY="$PROJECT_DIRECTORY"
|
||||
export MONGODB_DOWNLOAD_URL="$MONGODB_DOWNLOAD_URL"
|
||||
|
||||
export TMPDIR="$MONGO_ORCHESTRATION_HOME/db"
|
||||
export PATH="$MONGODB_BINARIES:$PATH"
|
||||
export PROJECT="${project}"
|
||||
EOT
|
||||
# See what we've done
|
||||
cat expansion.yml
|
||||
|
||||
# Load the expansion file to make an evergreen variable with the current unique version
|
||||
- command: expansions.update
|
||||
params:
|
||||
file: src/${DRIVER_WORKING_DIRECTORY}/expansion.yml
|
||||
|
||||
### PRE ###
|
||||
pre:
|
||||
- func: "cleanup environment"
|
||||
|
||||
### POST ###
|
||||
post:
|
||||
- command: attach.results
|
||||
params:
|
||||
file_location: src/report.json
|
||||
- func: "upload mo artifacts"
|
||||
- func: "upload xml test results"
|
||||
# Cleanup steps.
|
||||
- command: shell.exec
|
||||
params:
|
||||
working_dir: src
|
||||
script: |
|
||||
# removes files from the (local) scons cache when it's over a
|
||||
# threshold, to the $prune_ratio percentage. Ideally override
|
||||
# these default values in the distro config in evergreen.
|
||||
|
||||
if [ -d "${scons_cache_path}" ]; then
|
||||
${python|python} buildscripts/scons_cache_prune.py --cache-dir '${scons_cache_path}' --cache-size ${scons_cache_size|200} --prune-ratio ${scons_prune_ratio|0.8}
|
||||
fi
|
||||
- func: "cleanup environment"
|
||||
|
||||
#######################################
|
||||
# TASKS #
|
||||
#######################################
|
||||
|
||||
tasks:
|
||||
|
||||
### MONGO COMPILE & TEST TASKS ###
|
||||
|
||||
- name: compile
|
||||
depends_on: []
|
||||
commands:
|
||||
- command: manifest.load
|
||||
- *git_get_project
|
||||
- func: "get buildnumber"
|
||||
- func: "setup credentials"
|
||||
- *generate_compile_expansions
|
||||
# Then we load the generated version data into the agent so we can use it in task definitions
|
||||
- *apply_compile_expansions
|
||||
|
||||
- command: shell.exec
|
||||
type: test
|
||||
params:
|
||||
working_dir: src
|
||||
script: |
|
||||
set -o errexit
|
||||
set -o verbose
|
||||
|
||||
rm -rf ${install_directory|/data/mongo-install-directory}
|
||||
|
||||
${compile_env|} ${python|/opt/mongodbtoolchain/v2/bin/python2} ./buildscripts/scons.py ${compile_flags|} ${scons_cache_args|} core unittests MONGO_VERSION=${version}
|
||||
|
||||
# Pack up the binaries
|
||||
mkdir -p mongodb-binaries/bin
|
||||
if [ `which strip` ]; then
|
||||
echo "found strip"
|
||||
find . -maxdepth 1 -type f -iname "mongo*" -exec strip {} \;
|
||||
fi
|
||||
find . -maxdepth 1 -type f -iname "mongo*" -exec mv {} ./mongodb-binaries/bin/ \;
|
||||
${compress} mongodb-binaries.${ext|tgz} mongodb-binaries/
|
||||
|
||||
### Run the unittests after the compile
|
||||
- func: "run mongo tests"
|
||||
vars:
|
||||
resmoke_args: --suites=unittests
|
||||
run_multiple_jobs: true
|
||||
- command: s3.put
|
||||
params:
|
||||
aws_key: ${aws_key}
|
||||
aws_secret: ${aws_secret}
|
||||
local_file: src/mongodb-binaries.${ext|tgz}
|
||||
remote_file: drivers-nightly/${platform}/${revision}/binaries/mongo-${revision}.${ext|tgz}
|
||||
bucket: mciuploads
|
||||
permissions: public-read
|
||||
content_type: ${content_type|application/x-gzip}
|
||||
display_name: Binaries
|
||||
|
||||
- <<: *task_template
|
||||
name: jsCore_WT
|
||||
commands:
|
||||
- func: "do setup"
|
||||
- func: "run mongo tests"
|
||||
vars:
|
||||
resmoke_args: --suites=core --storageEngine=wiredTiger
|
||||
run_multiple_jobs: true
|
||||
|
||||
### DRIVER TEST TASKS ###
|
||||
- name: "test-nightly-standalone"
|
||||
depends_on:
|
||||
- variant: ".compile-variant"
|
||||
name: "jsCore_WT"
|
||||
tags: ["nightly", "standalone"]
|
||||
commands:
|
||||
- *git_get_project
|
||||
- func: "setup drivers environment"
|
||||
vars:
|
||||
VERSION: "nightly"
|
||||
TOPOLOGY: "server"
|
||||
- func: "windows fix"
|
||||
- func: "fix absolute paths"
|
||||
- func: "init test-results"
|
||||
- func: "make files executable"
|
||||
- func: "bootstrap mongo-orchestration"
|
||||
- func: "run driver tests"
|
||||
|
||||
- name: "test-nightly-replica_set"
|
||||
depends_on:
|
||||
- variant: ".compile-variant"
|
||||
name: "jsCore_WT"
|
||||
tags: ["nightly", "replica_set"]
|
||||
commands:
|
||||
- *git_get_project
|
||||
- func: "setup drivers environment"
|
||||
vars:
|
||||
VERSION: "nightly"
|
||||
TOPOLOGY: "replica_set"
|
||||
- func: "windows fix"
|
||||
- func: "fix absolute paths"
|
||||
- func: "init test-results"
|
||||
- func: "make files executable"
|
||||
- func: "bootstrap mongo-orchestration"
|
||||
- func: "run driver tests"
|
||||
|
||||
- name: "test-nightly-sharded_cluster"
|
||||
depends_on:
|
||||
- variant: ".compile-variant"
|
||||
name: "jsCore_WT"
|
||||
tags: ["nightly", "sharded_cluster"]
|
||||
commands:
|
||||
- *git_get_project
|
||||
- func: "setup drivers environment"
|
||||
vars:
|
||||
VERSION: "nightly"
|
||||
TOPOLOGY: "sharded_cluster"
|
||||
- func: "windows fix"
|
||||
- func: "fix absolute paths"
|
||||
- func: "init test-results"
|
||||
- func: "make files executable"
|
||||
- func: "bootstrap mongo-orchestration"
|
||||
- func: "run driver tests"
|
||||
|
||||
#######################################
|
||||
# AXES #
|
||||
#######################################
|
||||
axes:
|
||||
### GENERAL FOR ALL DRIVERS TESTS ###
|
||||
- id: os
|
||||
display_name: OS
|
||||
values:
|
||||
- id: "rhel62"
|
||||
display_name: "RHEL 6.2"
|
||||
run_on: rhel62-test
|
||||
variables:
|
||||
PLATFORM: "linux"
|
||||
FILE_EXT: "tgz"
|
||||
- id: "windows64"
|
||||
display_name: "Windows 64"
|
||||
run_on: windows-64-vs2015-test
|
||||
variables:
|
||||
PLATFORM: "windows64"
|
||||
FILE_EXT: "zip"
|
||||
- id: auth
|
||||
display_name: Authentication
|
||||
values:
|
||||
- id: "auth"
|
||||
display_name: Auth
|
||||
variables:
|
||||
AUTH: "auth"
|
||||
- id: "noauth"
|
||||
display_name: NoAuth
|
||||
variables:
|
||||
AUTH: "noauth"
|
||||
- id: ssl
|
||||
display_name: SSL
|
||||
values:
|
||||
- id: "ssl"
|
||||
display_name: SSL
|
||||
variables:
|
||||
SSL: "ssl"
|
||||
- id: "nossl"
|
||||
display_name: NoSSL
|
||||
variables:
|
||||
SSL: "nossl"
|
||||
|
||||
### DRIVER-SPECIFIC AXES ###
|
||||
### DRIVERS TEAM, ADD YOUR AXES VARIABLES HERE ###
|
||||
|
||||
### Java ###
|
||||
- id: jdk
|
||||
display_name: JDK
|
||||
values:
|
||||
- id: "jdk8"
|
||||
display_name: JDK8
|
||||
variables:
|
||||
JDK: "jdk8"
|
||||
DRIVER_WORKING_DIRECTORY: "mongo-java-driver"
|
||||
DRIVER_TEST_UPLOAD_DIRECTORY: "src/mongo-java-driver/*/build/test-results/TEST-*.xml"
|
||||
### Python ###
|
||||
- id: python-linux
|
||||
display_name: "Python"
|
||||
values:
|
||||
- id: "2.6"
|
||||
display_name: "Python 2.6"
|
||||
variables:
|
||||
PYTHON_BINARY: "/opt/python/2.6/bin/python"
|
||||
DRIVER_WORKING_DIRECTORY: "mongo-python-driver"
|
||||
DRIVER_TEST_UPLOAD_DIRECTORY: "src/mongo-python-driver/xunit-results/TEST-*.xml"
|
||||
- id: "2.7"
|
||||
display_name: "Python 2.7"
|
||||
variables:
|
||||
PYTHON_BINARY: "/opt/python/2.7/bin/python"
|
||||
DRIVER_WORKING_DIRECTORY: "mongo-python-driver"
|
||||
- id: python-windows
|
||||
display_name: "Windows Visual Studio 2010 Python"
|
||||
values:
|
||||
- id: "3.6"
|
||||
display_name: "Python 3.6"
|
||||
variables:
|
||||
PYTHON_BINARY: "/cygdrive/c/python/Python36/python.exe"
|
||||
DRIVER_WORKING_DIRECTORY: "mongo-python-driver"
|
||||
DRIVER_TEST_UPLOAD_DIRECTORY: "src/mongo-python-driver/xunit-results/TEST-*.xml"
|
||||
|
||||
#######################################
|
||||
# MODULES #
|
||||
#######################################
|
||||
|
||||
# If a module is added it must be added to the manifest
|
||||
# be sure to add the module to 'git.get_project' revisions parameter
|
||||
# DRIVERS add your own git repo / branch here and add up top in 'git.get_project'
|
||||
modules:
|
||||
- name: enterprise
|
||||
repo: git@github.com:10gen/mongo-enterprise-modules.git
|
||||
prefix: src/mongo/db/modules
|
||||
branch: v4.2
|
||||
|
||||
# Shared by all drivers projects
|
||||
- name: drivers-evergreen-tools
|
||||
repo: git@github.com:mongodb-labs/drivers-evergreen-tools.git
|
||||
branch: master
|
||||
|
||||
### DRIVER REPOS ###
|
||||
### DRIVERS ADD YOUR GIT REPO HERE ###
|
||||
- name: mongo-java-driver
|
||||
repo: git@github.com:mongodb/mongo-java-driver.git
|
||||
branch: master
|
||||
|
||||
- name: mongo-python-driver
|
||||
repo: git@github.com:mongodb/mongo-python-driver.git
|
||||
branch: master
|
||||
|
||||
#######################################
|
||||
# BUILDVARIANTS #
|
||||
#######################################
|
||||
|
||||
buildvariants:
|
||||
|
||||
### MONGO COMPILE VARIANTS ###
|
||||
|
||||
### Linux Compile Variant ###
|
||||
- name: rhel62
|
||||
display_name: RHEL 6.2 MongoDB Compile
|
||||
modules:
|
||||
- enterprise
|
||||
run_on:
|
||||
- rhel62-small
|
||||
expansions:
|
||||
rlp_environment: MONGOD_UNITTEST_RLP_LANGUAGE_TEST_BTROOT=/opt/basis
|
||||
platform: linux
|
||||
compile_flags: --ssl MONGO_DISTMOD=rhel62 -j$(grep -c ^processor /proc/cpuinfo) --release --variables-files=etc/scons/mongodbtoolchain_gcc.vars CPPPATH="/opt/basis/rlp/rlp/include /opt/basis/rlp/utilities/include"
|
||||
multiversion_platform_arch: "rhel62"
|
||||
multiversion_edition: "targeted"
|
||||
num_jobs_available: $(grep -c ^processor /proc/cpuinfo)
|
||||
use_scons_cache: true
|
||||
### build_mongoreplay: true
|
||||
ext: tgz
|
||||
tags: ["compile-variant"]
|
||||
tasks:
|
||||
- name: compile
|
||||
distros:
|
||||
- rhel62-large
|
||||
- name: jsCore_WT
|
||||
|
||||
### Windows compile variant ###
|
||||
- name: enterprise-windows-64
|
||||
display_name: "Enterprise Windows MongoDB Compile"
|
||||
modules:
|
||||
- enterprise
|
||||
run_on:
|
||||
- windows-64-vs2015-compile
|
||||
expansions:
|
||||
platform: "windows64"
|
||||
exe: ".exe"
|
||||
content_type: application/zip
|
||||
compile_flags: --ssl MONGO_DISTMOD=windows-64 --release CPPPATH="c:/openssl/include c:/sasl/include c:/snmp/include c:/curl/include" LIBPATH="c:/openssl/lib c:/sasl/lib c:/snmp/lib c:/curl/lib" -j$(( $(grep -c ^processor /proc/cpuinfo) / 4 )) --dynamic-windows --win-version-min=ws08r2 VARIANT_DIR=win32
|
||||
num_jobs_available: $(grep -c ^processor /proc/cpuinfo)
|
||||
ext: zip
|
||||
use_scons_cache: true
|
||||
python: python
|
||||
tags: ["compile-variant"]
|
||||
tasks:
|
||||
- name: compile
|
||||
distros:
|
||||
- windows-64-vs2015-large
|
||||
- name: jsCore_WT
|
||||
|
||||
### DRIVER Test Variants
|
||||
### DRIVERS add your matrix or test variant here
|
||||
|
||||
### Python Matrix Linux
|
||||
- matrix_name: "python-driver-linux"
|
||||
matrix_spec: {auth: "*", ssl: "*", os: "rhel62", python-linux: "2.6"}
|
||||
display_name: "Python Driver ${os} ${python-linux} ${auth} ${ssl}"
|
||||
modules: ["mongo-python-driver", "drivers-evergreen-tools"]
|
||||
tasks:
|
||||
- name: "test-nightly-replica_set"
|
||||
- name: "test-nightly-sharded_cluster"
|
||||
- name: "test-nightly-standalone"
|
||||
|
||||
### Python Matrix Windows
|
||||
- matrix_name: "python-driver-windows"
|
||||
matrix_spec: {auth: "*", ssl: "*", os: "windows64", python-windows: "3.6"}
|
||||
display_name: "Python Driver ${os} ${python-windows} ${auth} ${ssl}"
|
||||
modules: ["mongo-python-driver", "drivers-evergreen-tools"]
|
||||
tasks:
|
||||
- name: "test-nightly-replica_set"
|
||||
- name: "test-nightly-sharded_cluster"
|
||||
- name: "test-nightly-standalone"
|
||||
|
||||
### Java Matrix Linux
|
||||
- matrix_name: "java-driver-linux"
|
||||
matrix_spec: {auth: "*", ssl: "*", os: "rhel62", jdk: "jdk8"}
|
||||
display_name: "Java Driver ${os} ${jdk} ${auth} ${ssl}"
|
||||
modules: ["mongo-java-driver", "drivers-evergreen-tools"]
|
||||
tasks:
|
||||
- name: "test-nightly-replica_set"
|
||||
- name: "test-nightly-sharded_cluster"
|
||||
- name: "test-nightly-standalone"
|
||||
@@ -249,7 +249,7 @@ variables:
|
||||
- func: "clear OOM messages"
|
||||
- command: manifest.load
|
||||
- func: "git get project"
|
||||
- func: "get modified patch files"
|
||||
- func: "get all modified patch files"
|
||||
- func: "set task expansion macros"
|
||||
# The python virtual environment is installed in ${workdir}, which is created in
|
||||
# "set up virtualenv".
|
||||
@@ -261,7 +261,6 @@ variables:
|
||||
- func: "get buildnumber"
|
||||
- func: "set up credentials"
|
||||
- func: "fetch and build OpenSSL"
|
||||
- func: "use WiredTiger develop" # noop if ${use_wt_develop} is not "true"
|
||||
- func: "generate compile expansions"
|
||||
teardown_group:
|
||||
- func: "scons cache pruning"
|
||||
@@ -392,7 +391,6 @@ variables:
|
||||
- enterprise-windows-64-2k8-nopush-template
|
||||
- enterprise-windows-64-2k8-openssl
|
||||
- enterprise-windows-64-2k8-required
|
||||
- enterprise-windows-64-2k8-wtdevelop
|
||||
- ubuntu1804-debug-asan
|
||||
- ubuntu1804-debug-ubsan
|
||||
- ubuntu1804-debug-aubsan-lite
|
||||
@@ -449,7 +447,6 @@ functions:
|
||||
directory: ${git_project_directory|src}
|
||||
revisions: # for each module include revision as <module_name> : ${<module_name>_rev}
|
||||
enterprise: ${enterprise_rev}
|
||||
wtdevelop: ${wtdevelop_rev}
|
||||
|
||||
"fetch artifacts": &fetch_artifacts
|
||||
command: s3.get
|
||||
@@ -528,7 +525,7 @@ functions:
|
||||
"get buildnumber": &get_buildnumber
|
||||
command: keyval.inc
|
||||
params:
|
||||
key: "${build_variant}_master"
|
||||
key: "${build_variant}_v4.2"
|
||||
destination: "builder_num"
|
||||
|
||||
"run diskstats": &run_diskstats
|
||||
@@ -780,21 +777,6 @@ functions:
|
||||
bash buildscripts/fetch_and_build_openssl.sh "${python|python3}" "${openssl_make_flags|}" "${openssl_config_flags|}"
|
||||
fi
|
||||
|
||||
"use WiredTiger develop":
|
||||
command: shell.exec
|
||||
params:
|
||||
working_dir: src
|
||||
script: |
|
||||
set -o errexit
|
||||
set -o verbose
|
||||
if [ "${use_wt_develop|}" = "true" ]; then
|
||||
cd src/third_party
|
||||
for wtdir in dist examples ext lang src test tools ; do
|
||||
rm -rf wiredtiger/$wtdir
|
||||
mv wtdevelop/$wtdir wiredtiger/
|
||||
done
|
||||
fi
|
||||
|
||||
"setup gradle signing keys":
|
||||
command: shell.exec
|
||||
params:
|
||||
@@ -1008,7 +990,7 @@ functions:
|
||||
mkdir -p ../../../../../../mongo-tools/distsrc
|
||||
cp THIRD-PARTY-NOTICES ../../../../../../mongo-tools/distsrc/THIRD-PARTY-NOTICES.gotools
|
||||
|
||||
"get modified patch files":
|
||||
"get all modified patch files":
|
||||
command: shell.exec
|
||||
params:
|
||||
working_dir: src
|
||||
@@ -1029,6 +1011,23 @@ functions:
|
||||
fi
|
||||
fi
|
||||
|
||||
# This function should only be called from patch-build-only tasks.
|
||||
"get added and modified patch files":
|
||||
command: shell.exec
|
||||
params:
|
||||
working_dir: src
|
||||
shell: bash
|
||||
script: |
|
||||
set -o verbose
|
||||
set -o errexit
|
||||
|
||||
git diff HEAD --name-only --line-prefix="${workdir}/src/" --diff-filter=d >> modified_and_created_patch_files.txt
|
||||
if [ -d src/mongo/db/modules/enterprise ]; then
|
||||
pushd src/mongo/db/modules/enterprise
|
||||
git diff HEAD --name-only --line-prefix="${workdir}/src/src/mongo/db/modules/enterprise/" --diff-filter=d >> ~1/modified_and_created_patch_files.txt
|
||||
popd
|
||||
fi
|
||||
|
||||
"determine resmoke jobs": &determine_resmoke_jobs
|
||||
command: shell.exec
|
||||
params:
|
||||
@@ -1819,7 +1818,7 @@ functions:
|
||||
|
||||
# Run parse-jsfiles on 50 files at a time with 32 processes in parallel.
|
||||
# Grep returns 1 if it fails to find a match.
|
||||
(grep "\.js$" patch_files.txt || true) | sed -e "s|^|$PWD/|" | xargs -P 32 -L 50 npm run --prefix jstestfuzz parse-jsfiles --
|
||||
(grep "\.js$" modified_and_created_patch_files.txt || true) | xargs -P 32 -L 50 npm run --prefix jstestfuzz parse-jsfiles --
|
||||
|
||||
"lint fuzzer sanity all":
|
||||
- command: shell.exec
|
||||
@@ -3705,9 +3704,9 @@ tasks:
|
||||
# CMake doesn't seem to do the dSYM for us for the framework
|
||||
if [ -e $BUILD_PREFIX/Frameworks ]; then
|
||||
pushd $BUILD_PREFIX/Frameworks
|
||||
xcrun dsymutil -o bson.framework.dSYM bson.framework/bson
|
||||
xcrun dsymutil -num-threads=1 -o bson.framework.dSYM bson.framework/bson
|
||||
xcrun strip -Sx bson.framework/bson
|
||||
xcrun dsymutil -o mongoc.framework.dSYM mongoc.framework/mongoc
|
||||
xcrun dsymutil -num-threads=1 -o mongoc.framework.dSYM mongoc.framework/mongoc
|
||||
xcrun strip -Sx mongoc.framework/mongoc
|
||||
popd
|
||||
fi
|
||||
@@ -4496,9 +4495,6 @@ tasks:
|
||||
set -o errexit
|
||||
set -o verbose
|
||||
|
||||
echo "Releases disabled on master."
|
||||
exit 0
|
||||
|
||||
if [ "${is_release|false}" != "true" ]; then
|
||||
echo "Not a release build"
|
||||
exit 0
|
||||
@@ -4585,7 +4581,6 @@ tasks:
|
||||
- func: "set up virtualenv"
|
||||
- func: "get buildnumber"
|
||||
- func: "set up credentials"
|
||||
- func: "use WiredTiger develop" # noop if ${use_wt_develop} is not "true"
|
||||
- func: "generate compile expansions"
|
||||
# Then we load the generated version data into the agent so we can use it in task definitions
|
||||
- func: "apply compile expansions"
|
||||
@@ -5319,19 +5314,20 @@ tasks:
|
||||
resmoke_args: --suites=jstestfuzz_replication_continuous_stepdown --flowControlTicketOverride=1 --storageEngine=wiredTiger
|
||||
name: jstestfuzz_replication_continuous_stepdown_flow_control
|
||||
|
||||
# TODO(SERVER-41608) Re-enable once root cause of failures has been addressed.
|
||||
## jstestfuzz concurrent replication continuous stepdown with flow control engaged ##
|
||||
- <<: *jstestfuzz_template
|
||||
name: jstestfuzz_concurrent_replication_continuous_stepdown_flow_control_gen
|
||||
tags: ["jstestfuzz", "common", "repl", "flow_control"]
|
||||
commands:
|
||||
- func: "generate fuzzer tasks"
|
||||
vars:
|
||||
<<: *jstestfuzz_config_vars
|
||||
num_files: ${jstestfuzz_concurrent_num_files|10}
|
||||
num_tasks: 15
|
||||
jstestfuzz_vars: --jsTestsDir ../jstests
|
||||
resmoke_args: --suites=jstestfuzz_replication_continuous_stepdown --flowControlTicketOverride=10 --storageEngine=wiredTiger --numClientsPerFixture=10
|
||||
name: jstestfuzz_concurrent_replication_continuous_stepdown_flow_control
|
||||
#- <<: *jstestfuzz_template
|
||||
# name: jstestfuzz_concurrent_replication_continuous_stepdown_flow_control_gen
|
||||
# tags: ["jstestfuzz", "common", "repl", "flow_control"]
|
||||
# commands:
|
||||
# - func: "generate fuzzer tasks"
|
||||
# vars:
|
||||
# <<: *jstestfuzz_config_vars
|
||||
# num_files: ${jstestfuzz_concurrent_num_files|10}
|
||||
# num_tasks: 15
|
||||
# jstestfuzz_vars: --jsTestsDir ../jstests
|
||||
# resmoke_args: --suites=jstestfuzz_replication_continuous_stepdown --flowControlTicketOverride=10 --storageEngine=wiredTiger --numClientsPerFixture=10
|
||||
# name: jstestfuzz_concurrent_replication_continuous_stepdown_flow_control
|
||||
|
||||
## jstestfuzz replica set ##
|
||||
- <<: *jstestfuzz_template
|
||||
@@ -5428,7 +5424,7 @@ tasks:
|
||||
- command: manifest.load
|
||||
- func: "git get project"
|
||||
- func: "set task expansion macros"
|
||||
- func: "get modified patch files"
|
||||
- func: "get added and modified patch files"
|
||||
- func: "setup jstestfuzz"
|
||||
- func: "lint fuzzer sanity patch"
|
||||
|
||||
@@ -5986,13 +5982,13 @@ tasks:
|
||||
resmoke_args: --suites=core_txns --storageEngine=wiredTiger
|
||||
|
||||
- <<: *task_template
|
||||
name: jsCore_txns_multi_oplog_entries
|
||||
name: jsCore_txns_large_txns_format
|
||||
tags: ["jscore", "txns"]
|
||||
commands:
|
||||
- func: "do setup"
|
||||
- func: "run tests"
|
||||
vars:
|
||||
resmoke_args: --suites=core_txns_multi_oplog_entries --storageEngine=wiredTiger
|
||||
resmoke_args: --suites=core_txns_large_txns_format --storageEngine=wiredTiger
|
||||
|
||||
- <<: *task_template
|
||||
name: sharded_jscore_txns
|
||||
@@ -6079,7 +6075,7 @@ tasks:
|
||||
fallback_num_sub_suites: 1
|
||||
|
||||
- <<: *task_template
|
||||
name: replica_sets_multi_oplog_txns_jscore_passthrough
|
||||
name: replica_sets_large_txns_format_jscore_passthrough
|
||||
tags: ["replica_sets", "multi_oplog", "large", "non_maj_read", "san"]
|
||||
depends_on:
|
||||
- name: jsCore
|
||||
@@ -6087,7 +6083,7 @@ tasks:
|
||||
- func: "do setup"
|
||||
- func: "run tests"
|
||||
vars:
|
||||
resmoke_args: --suites=replica_sets_multi_oplog_txns_jscore_passthrough --storageEngine=wiredTiger
|
||||
resmoke_args: --suites=replica_sets_large_txns_format_jscore_passthrough --storageEngine=wiredTiger
|
||||
|
||||
- <<: *task_template
|
||||
name: replica_sets_multi_stmt_txn_jscore_passthrough
|
||||
@@ -6707,7 +6703,7 @@ tasks:
|
||||
resmoke_args: --storageEngine=wiredTiger
|
||||
fallback_num_sub_suites: 7
|
||||
|
||||
- name: replica_sets_multi_oplog_txns_gen
|
||||
- name: replica_sets_large_txns_format_gen
|
||||
tags: ["replica_sets", "multi_oplog", "san"]
|
||||
commands:
|
||||
- func: "generate resmoke tasks"
|
||||
@@ -7927,6 +7923,15 @@ tasks:
|
||||
resmoke_args: --suites=search_beta --storageEngine=wiredTiger
|
||||
resmoke_jobs_max: 1
|
||||
|
||||
- <<: *task_template
|
||||
name: search_beta_auth
|
||||
commands:
|
||||
- func: "do setup"
|
||||
- func: "run tests"
|
||||
vars:
|
||||
resmoke_args: --suites=search_beta_auth --storageEngine=wiredTiger
|
||||
resmoke_jobs_max: 1
|
||||
|
||||
- <<: *task_template
|
||||
name: search_beta_ssl
|
||||
commands:
|
||||
@@ -8014,12 +8019,7 @@ modules:
|
||||
- name: enterprise
|
||||
repo: git@github.com:10gen/mongo-enterprise-modules.git
|
||||
prefix: src/mongo/db/modules
|
||||
branch: master
|
||||
|
||||
- name: wtdevelop
|
||||
repo: git@github.com:wiredtiger/wiredtiger.git
|
||||
prefix: src/third_party
|
||||
branch: develop
|
||||
branch: v4.2
|
||||
|
||||
#######################################
|
||||
# Buildvariants #
|
||||
@@ -8103,7 +8103,7 @@ buildvariants:
|
||||
- name: disk_wiredtiger
|
||||
- name: .integration !.audit
|
||||
- name: .jscore .common
|
||||
- name: jsCore_txns_multi_oplog_entries
|
||||
- name: jsCore_txns_large_txns_format
|
||||
- name: jsonSchema
|
||||
- name: .logical_session_cache
|
||||
- name: .multi_shard
|
||||
@@ -8118,20 +8118,6 @@ buildvariants:
|
||||
- name: sharding_gen
|
||||
- name: .stitch
|
||||
|
||||
- <<: *linux-64-debug-template
|
||||
name: linux-64-debug-wtdevelop
|
||||
display_name: "~ Linux DEBUG WiredTiger develop"
|
||||
batchtime: 1440 # 1 day
|
||||
modules:
|
||||
- wtdevelop
|
||||
expansions:
|
||||
use_wt_develop: true
|
||||
resmoke_jobs_factor: 0.5 # Avoid starting too many mongod's
|
||||
compile_flags: --dbg=on --opt=on -j$(grep -c ^processor /proc/cpuinfo) --variables-files=etc/scons/mongodbtoolchain_v3_gcc.vars --enable-free-mon=off --enable-http-client=off
|
||||
use_scons_cache: true
|
||||
build_mongoreplay: true
|
||||
test_flags: --excludeWithAnyTags=requires_http_client
|
||||
|
||||
- name: linux-64-duroff
|
||||
display_name: Linux (No Journal)
|
||||
run_on:
|
||||
@@ -9068,7 +9054,7 @@ buildvariants:
|
||||
distros:
|
||||
- windows-64-vs2017-compile
|
||||
- name: .jscore .common !.auth !.sharding
|
||||
- name: jsCore_txns_multi_oplog_entries
|
||||
- name: jsCore_txns_large_txns_format
|
||||
- name: jsonSchema
|
||||
- name: .logical_session_cache .one_sec
|
||||
- name: multi_shard_multi_stmt_txn_jscore_passthrough_gen
|
||||
@@ -9131,7 +9117,7 @@ buildvariants:
|
||||
- name: .jscore .common !.compat !.sharding
|
||||
- name: jsCore_auth
|
||||
- name: jsCore_ese
|
||||
- name: jsCore_txns_multi_oplog_entries
|
||||
- name: jsCore_txns_large_txns_format
|
||||
- name: .jstestfuzz .common
|
||||
- name: noPassthrough_gen
|
||||
- name: noPassthroughWithMongod_gen
|
||||
@@ -9148,17 +9134,6 @@ buildvariants:
|
||||
distros:
|
||||
- rhel70-small
|
||||
|
||||
- <<: *enterprise-windows-64-2k8-nopush-template
|
||||
name: enterprise-windows-64-2k8-wtdevelop
|
||||
display_name: "~ Enterprise Windows 2008R2 WiredTiger develop"
|
||||
batchtime: 1440 # 1 day
|
||||
modules:
|
||||
- enterprise
|
||||
- wtdevelop
|
||||
expansions:
|
||||
<<: *enterprise-windows-64-2k8-nopush-expansions-template
|
||||
use_wt_develop: true
|
||||
|
||||
- <<: *enterprise-windows-64-2k8-nopush-template
|
||||
name: enterprise-windows-64-2k8-compile-all
|
||||
display_name: "* Enterprise Windows 2008R2 compile_all"
|
||||
@@ -9440,10 +9415,10 @@ buildvariants:
|
||||
- name: disk_wiredtiger
|
||||
- name: failpoints
|
||||
- name: .jscore .common !.auth !.sharding
|
||||
- name: jsCore_txns_multi_oplog_entries
|
||||
- name: jsCore_txns_large_txns_format
|
||||
- name: mongosTest
|
||||
- name: replica_sets
|
||||
- name: replica_sets_multi_oplog_txns_gen
|
||||
- name: replica_sets_large_txns_format_gen
|
||||
- name: .ssl
|
||||
- name: .stitch
|
||||
- name: tool
|
||||
@@ -10027,7 +10002,7 @@ buildvariants:
|
||||
- name: .jscore .common
|
||||
- name: jsCore_minimum_batch_size
|
||||
- name: jsCore_op_query
|
||||
- name: jsCore_txns_multi_oplog_entries
|
||||
- name: jsCore_txns_large_txns_format
|
||||
- name: jsonSchema
|
||||
- name: .jstestfuzz
|
||||
- name: .logical_session_cache
|
||||
@@ -10049,6 +10024,7 @@ buildvariants:
|
||||
- name: .rollbackfuzzer
|
||||
- name: sasl
|
||||
- name: search_beta
|
||||
- name: search_beta_auth
|
||||
- name: search_beta_ssl
|
||||
- name: session_jscore_passthrough
|
||||
- name: .sharding .jscore !.wo_snapshot !.multi_stmt
|
||||
@@ -10066,8 +10042,8 @@ buildvariants:
|
||||
- ubuntu1604-packer
|
||||
- name: .publish
|
||||
|
||||
- name: enterprise-rhel-62-64-bit-multi-txn-oplog-entries
|
||||
display_name: "Enterprise RHEL 6.2 (Multiple oplog entries transaction format)"
|
||||
- name: enterprise-rhel-62-64-bit-large-txns-format
|
||||
display_name: "Enterprise RHEL 6.2 (large transactions format)"
|
||||
modules:
|
||||
- enterprise
|
||||
run_on:
|
||||
@@ -10087,7 +10063,7 @@ buildvariants:
|
||||
build_mongoreplay: true
|
||||
large_distro_name: rhel62-large
|
||||
test_flags: >-
|
||||
--mongodSetParameters="{useMultipleOplogEntryFormatForTransactions: true, maxNumberOfTransactionOperationsInSingleOplogEntry: 2}"
|
||||
--mongodSetParameters="{maxNumberOfTransactionOperationsInSingleOplogEntry: 2}"
|
||||
--excludeWithAnyTags=exclude_from_large_txns
|
||||
--excludeWithAnyTags=exclude_from_large_txns_due_to_change_streams
|
||||
tasks:
|
||||
@@ -10240,6 +10216,7 @@ buildvariants:
|
||||
- name: .rollbackfuzzer
|
||||
- name: sasl
|
||||
- name: search_beta
|
||||
- name: search_beta_auth
|
||||
- name: search_beta_ssl
|
||||
- name: secondary_reads_passthrough_gen
|
||||
- name: session_jscore_passthrough
|
||||
@@ -10303,7 +10280,7 @@ buildvariants:
|
||||
- name: .jscore .common
|
||||
- name: jsCore_minimum_batch_size
|
||||
- name: jsCore_op_query
|
||||
- name: jsCore_txns_multi_oplog_entries
|
||||
- name: jsCore_txns_large_txns_format
|
||||
- name: jsonSchema
|
||||
- name: .jstestfuzz !.flow_control
|
||||
- name: .logical_session_cache
|
||||
@@ -10323,6 +10300,7 @@ buildvariants:
|
||||
- name: .rollbackfuzzer
|
||||
- name: sasl
|
||||
- name: search_beta
|
||||
- name: search_beta_auth
|
||||
- name: search_beta_ssl
|
||||
- name: secondary_reads_passthrough_gen
|
||||
- name: session_jscore_passthrough
|
||||
@@ -10394,7 +10372,7 @@ buildvariants:
|
||||
- name: initial_sync_fuzzer_gen
|
||||
- name: .integration !.audit
|
||||
- name: .jscore .common
|
||||
- name: jsCore_txns_multi_oplog_entries
|
||||
- name: jsCore_txns_large_txns_format
|
||||
- name: jsCore_minimum_batch_size
|
||||
- name: jsCore_op_query
|
||||
- name: .logical_session_cache .one_sec
|
||||
@@ -10407,6 +10385,7 @@ buildvariants:
|
||||
- name: retryable_writes_jscore_passthrough_gen
|
||||
- name: sasl
|
||||
- name: search_beta
|
||||
- name: search_beta_auth
|
||||
- name: search_beta_ssl
|
||||
- name: secondary_reads_passthrough_gen
|
||||
- name: session_jscore_passthrough
|
||||
@@ -10456,7 +10435,7 @@ buildvariants:
|
||||
- name: .encrypt !.sharding !.replica_sets !.aggregation !.jscore
|
||||
- name: external_auth
|
||||
- name: .jscore .common !.compat !.decimal !.sharding
|
||||
- name: jsCore_txns_multi_oplog_entries
|
||||
- name: jsCore_txns_large_txns_format
|
||||
- name: .jstestfuzz .common
|
||||
- name: .logical_session_cache .one_sec
|
||||
- name: replica_sets_auth_gen
|
||||
@@ -10464,6 +10443,7 @@ buildvariants:
|
||||
- name: .replica_sets .multi_oplog
|
||||
- name: sasl
|
||||
- name: search_beta
|
||||
- name: search_beta_auth
|
||||
- name: search_beta_ssl
|
||||
- name: sharding_auth_audit_gen
|
||||
- name: sharding_auth_gen
|
||||
@@ -10525,7 +10505,7 @@ buildvariants:
|
||||
- name: jsCore
|
||||
- name: .read_write_concern !.write !.aggregation
|
||||
- name: replica_sets_jscore_passthrough
|
||||
- name: replica_sets_multi_oplog_txns_jscore_passthrough
|
||||
- name: replica_sets_large_txns_format_jscore_passthrough
|
||||
- name: sharded_collections_jscore_passthrough
|
||||
- name: sharding_gen
|
||||
- name: sharding_auth_gen
|
||||
@@ -11462,7 +11442,7 @@ buildvariants:
|
||||
- rhel62-large
|
||||
- name: .jscore .common !.decimal
|
||||
- name: jsCore_op_query
|
||||
- name: jsCore_txns_multi_oplog_entries
|
||||
- name: jsCore_txns_large_txns_format
|
||||
- name: .jstestfuzz !.initsync
|
||||
- name: .logical_session_cache
|
||||
- name: .multi_shard .common
|
||||
@@ -11884,14 +11864,14 @@ buildvariants:
|
||||
- name: .jscore .common
|
||||
- name: jsCore_minimum_batch_size
|
||||
- name: jsCore_op_query
|
||||
- name: jsCore_txns_multi_oplog_entries
|
||||
- name: jsCore_txns_large_txns_format
|
||||
- name: jsonSchema
|
||||
- name: .logical_session_cache
|
||||
- name: .multi_shard .common
|
||||
- name: multiversion
|
||||
- name: .read_write_concern
|
||||
- name: replica_sets_multi_oplog_txns_gen
|
||||
- name: replica_sets_multi_oplog_txns_jscore_passthrough
|
||||
- name: replica_sets_large_txns_format_gen
|
||||
- name: replica_sets_large_txns_format_jscore_passthrough
|
||||
- name: .replica_sets !.multi_oplog
|
||||
- name: .retry
|
||||
- name: .read_only
|
||||
@@ -11973,14 +11953,14 @@ buildvariants:
|
||||
- name: .jscore .common
|
||||
- name: jsCore_minimum_batch_size
|
||||
- name: jsCore_op_query
|
||||
- name: jsCore_txns_multi_oplog_entries
|
||||
- name: jsCore_txns_large_txns_format
|
||||
- name: jsonSchema
|
||||
- name: .logical_session_cache .one_sec
|
||||
- name: .multi_shard .common
|
||||
- name: multiversion
|
||||
- name: .read_write_concern
|
||||
- name: replica_sets_multi_oplog_txns_gen
|
||||
- name: replica_sets_multi_oplog_txns_jscore_passthrough
|
||||
- name: replica_sets_large_txns_format_gen
|
||||
- name: replica_sets_large_txns_format_jscore_passthrough
|
||||
- name: .replica_sets !.multi_oplog
|
||||
- name: .retry
|
||||
- name: .rollbackfuzzer
|
||||
@@ -12020,7 +12000,7 @@ buildvariants:
|
||||
- name: causally_consistent_jscore_txns_passthrough
|
||||
- name: jsCore
|
||||
- name: jsCore_txns
|
||||
- name: jsCore_txns_multi_oplog_entries
|
||||
- name: jsCore_txns_large_txns_format
|
||||
- name: .logical_session_cache .one_sec
|
||||
- name: watchdog_wiredtiger
|
||||
|
||||
@@ -12065,7 +12045,7 @@ buildvariants:
|
||||
- name: .jscore .common
|
||||
- name: jsCore_minimum_batch_size
|
||||
- name: jsCore_op_query
|
||||
- name: jsCore_txns_multi_oplog_entries
|
||||
- name: jsCore_txns_large_txns_format
|
||||
- name: .logical_session_cache .one_sec
|
||||
- name: multiversion
|
||||
- name: .read_write_concern
|
||||
|
||||
@@ -47,7 +47,7 @@ modules:
|
||||
- name: enterprise
|
||||
repo: git@github.com:10gen/mongo-enterprise-modules.git
|
||||
prefix: src/mongo/db/modules
|
||||
branch: master
|
||||
branch: v4.2
|
||||
- name: genny
|
||||
repo: git@github.com:mongodb/genny.git
|
||||
branch: master
|
||||
|
||||
@@ -763,7 +763,7 @@ modules:
|
||||
- name: enterprise
|
||||
repo: git@github.com:10gen/mongo-enterprise-modules.git
|
||||
prefix: src/mongo/db/modules
|
||||
branch: master
|
||||
branch: v4.2
|
||||
|
||||
#######################################
|
||||
# Buildvariants #
|
||||
|
||||
@@ -8,9 +8,9 @@
|
||||
(function() {
|
||||
"use strict";
|
||||
|
||||
load("jstests/libs/fixture_helpers.js"); // For FixtureHelpers.isMongos().
|
||||
load("jstests/libs/analyze_plan.js"); // For getAggPlanStage().
|
||||
load("jstests/aggregation/extras/out_helpers.js"); // For withEachMergeMode().
|
||||
load("jstests/libs/fixture_helpers.js"); // For FixtureHelpers.isMongos().
|
||||
load("jstests/libs/analyze_plan.js"); // For getAggPlanStage().
|
||||
load("jstests/aggregation/extras/merge_helpers.js"); // For withEachMergeMode().
|
||||
|
||||
let sourceColl = db.explain_writing_aggs_source;
|
||||
let targetColl = db.explain_writing_aggs_target;
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/**
|
||||
* Collection of helper functions for testing the $out aggregation stage.
|
||||
* Collection of helper functions for testing the $merge aggregation stage.
|
||||
*/
|
||||
|
||||
load("jstests/libs/fixture_helpers.js"); // For isSharded.
|
||||
@@ -31,43 +31,49 @@ function withEachMergeMode(callback) {
|
||||
callback({whenMatchedMode: [], whenNotMatchedMode: "discard"});
|
||||
}
|
||||
|
||||
function assertFailsWithoutUniqueIndex({source, target, onFields, options, prevStages}) {
|
||||
function assertMergeFailsForAllModesWithCode(
|
||||
{source, target, onFields, options, prevStages = [], errorCodes}) {
|
||||
withEachMergeMode(({whenMatchedMode, whenNotMatchedMode}) => {
|
||||
prevStages = (prevStages || []);
|
||||
const pipeline = prevStages.concat([{
|
||||
$merge: {
|
||||
into: {db: target.getDB().getName(), coll: target.getName()},
|
||||
on: onFields,
|
||||
whenMatched: whenMatchedMode,
|
||||
whenNotMatched: whenNotMatchedMode
|
||||
}
|
||||
}]);
|
||||
const mergeStage = {
|
||||
into: {db: target.getDB().getName(), coll: target.getName()},
|
||||
whenMatched: whenMatchedMode,
|
||||
whenNotMatched: whenNotMatchedMode
|
||||
};
|
||||
if (onFields) {
|
||||
mergeStage.on = onFields;
|
||||
}
|
||||
const pipeline = prevStages.concat([{$merge: mergeStage}]);
|
||||
|
||||
// In sharded passthrough suites, the error code may be different depending on where we
|
||||
// extract the "on" fields.
|
||||
const cmd = {aggregate: source.getName(), pipeline: pipeline, cursor: {}};
|
||||
assert.commandFailedWithCode(source.getDB().runCommand(Object.merge(cmd, options)),
|
||||
[51183, 51190]);
|
||||
errorCodes);
|
||||
});
|
||||
}
|
||||
|
||||
function assertSucceedsWithExpectedUniqueIndex({source, target, onFields, options, prevStages}) {
|
||||
function assertMergeFailsWithoutUniqueIndex({source, target, onFields, options, prevStages}) {
|
||||
assertMergeFailsForAllModesWithCode(
|
||||
{source, target, onFields, options, prevStages, errorCodes: [51183, 51190]});
|
||||
}
|
||||
|
||||
function assertMergeSucceedsWithExpectedUniqueIndex(
|
||||
{source, target, onFields, options, prevStages = []}) {
|
||||
withEachMergeMode(({whenMatchedMode, whenNotMatchedMode}) => {
|
||||
// Skip the combination of merge modes which will fail depending on the contents of the
|
||||
// source and target collection, as this will cause the assertion below to trip.
|
||||
if (whenMatchedMode == "fail" || whenNotMatchedMode == "fail")
|
||||
return;
|
||||
|
||||
prevStages = (prevStages || []);
|
||||
let mergeStage = {
|
||||
const mergeStage = {
|
||||
into: {db: target.getDB().getName(), coll: target.getName()},
|
||||
whenMatched: whenMatchedMode,
|
||||
whenNotMatched: whenNotMatchedMode
|
||||
};
|
||||
|
||||
// Do not include the "on" fields in the command if the caller did not specify it.
|
||||
if (onFields !== undefined) {
|
||||
mergeStage = Object.extend(mergeStage, {on: onFields});
|
||||
if (onFields) {
|
||||
mergeStage.on = onFields;
|
||||
}
|
||||
const pipeline = prevStages.concat([{$merge: mergeStage}]);
|
||||
|
||||
@@ -10,6 +10,8 @@
|
||||
(function() {
|
||||
"use strict";
|
||||
|
||||
// For assertMergeFailsForAllModesWithCode.
|
||||
load("jstests/aggregation/extras/merge_helpers.js");
|
||||
load("jstests/aggregation/extras/utils.js"); // For assertErrorCode.
|
||||
|
||||
const kFailPointName = "waitAfterPinningCursorBeforeGetMoreBatch";
|
||||
@@ -117,13 +119,13 @@
|
||||
// before the $merge. Without the $group we won't use the exchange optimization and instead
|
||||
// will send the $merge to each shard.
|
||||
st.shardColl(mongosDB.target, {_id: 1}, {_id: 0}, {_id: 1}, kDBName, false);
|
||||
assertErrorCode(
|
||||
coll,
|
||||
[
|
||||
{$group: {_id: "$fakeShardKey"}},
|
||||
{$merge: {into: "target", whenMatched: "replace", whenNotMatched: "insert"}}
|
||||
],
|
||||
ErrorCodes.FailPointEnabled);
|
||||
|
||||
assertMergeFailsForAllModesWithCode({
|
||||
source: coll,
|
||||
target: mongosDB.target,
|
||||
prevStages: [{$group: {_id: "$fakeShardKey"}}],
|
||||
errorCodes: ErrorCodes.FailPointEnabled
|
||||
});
|
||||
|
||||
// Neither mongos or the shards should leave cursors open.
|
||||
assert.eq(mongosDB.serverStatus().metrics.cursor.open.total, 0);
|
||||
|
||||
@@ -14,7 +14,7 @@
|
||||
let testColl = testDB.test;
|
||||
|
||||
// getHostName() doesn't include port, db.getMongo().host is 127.0.0.1:<port>
|
||||
const hostName = (getHostName().toLowerCase() + ":" + db.getMongo().host.split(":")[1]);
|
||||
const hostName = (getHostName() + ":" + db.getMongo().host.split(":")[1]);
|
||||
|
||||
// Test that the shard field is absent and the host field is present when run on mongoD.
|
||||
assert.eq(testColl
|
||||
@@ -41,10 +41,6 @@
|
||||
assert.commandWorked(
|
||||
testDB.adminCommand({shardCollection: testColl.getFullName(), key: {_id: "hashed"}}));
|
||||
|
||||
const getPrimary = (rs) => {
|
||||
return rs.getPrimary().host.toLowerCase();
|
||||
};
|
||||
|
||||
// Group $collStats result by $shard and $host to confirm that both fields are present.
|
||||
assert.eq(testColl
|
||||
.aggregate([
|
||||
@@ -54,8 +50,8 @@
|
||||
])
|
||||
.toArray(),
|
||||
[
|
||||
{_id: {shard: st.shard0.shardName, host: getPrimary(st.rs0)}},
|
||||
{_id: {shard: st.shard1.shardName, host: getPrimary(st.rs1)}},
|
||||
{_id: {shard: st.shard0.shardName, host: st.rs0.getPrimary().host}},
|
||||
{_id: {shard: st.shard1.shardName, host: st.rs1.getPrimary().host}},
|
||||
]);
|
||||
|
||||
st.stop();
|
||||
|
||||
@@ -5,8 +5,8 @@
|
||||
(function() {
|
||||
"use strict";
|
||||
|
||||
load("jstests/aggregation/extras/out_helpers.js"); // For withEachMergeMode.
|
||||
load("jstests/aggregation/extras/utils.js"); // For assertErrorCode.
|
||||
load("jstests/aggregation/extras/merge_helpers.js"); // For withEachMergeMode.
|
||||
load("jstests/aggregation/extras/utils.js"); // For assertErrorCode.
|
||||
|
||||
const coll = db.batch_writes;
|
||||
const outColl = db.batch_writes_out;
|
||||
|
||||
@@ -11,8 +11,8 @@
|
||||
(function() {
|
||||
'use strict';
|
||||
|
||||
load('jstests/aggregation/extras/out_helpers.js'); // For 'withEachMergeMode'.
|
||||
load('jstests/libs/fixture_helpers.js'); // For 'FixtureHelpers'.
|
||||
load('jstests/aggregation/extras/merge_helpers.js'); // For 'withEachMergeMode'.
|
||||
load('jstests/libs/fixture_helpers.js'); // For 'FixtureHelpers'.
|
||||
|
||||
const testDB = db.getSiblingDB("merge_to_referenced_coll");
|
||||
const coll = testDB.test;
|
||||
|
||||
@@ -6,7 +6,8 @@
|
||||
(function() {
|
||||
"use strict";
|
||||
|
||||
load("jstests/aggregation/extras/utils.js"); // For assertErrorCode.
|
||||
// For assertMergeFailsForAllModesWithCode.
|
||||
load("jstests/aggregation/extras/merge_helpers.js");
|
||||
|
||||
const coll = db.name;
|
||||
coll.drop();
|
||||
@@ -15,14 +16,5 @@
|
||||
for (let i = 0; i < nDocs; i++) {
|
||||
assert.commandWorked(coll.insert({_id: i, a: i}));
|
||||
}
|
||||
|
||||
assertErrorCode(
|
||||
coll,
|
||||
[{$merge: {into: coll.getName(), whenMatched: "replace", whenNotMatched: "insert"}}],
|
||||
51188);
|
||||
|
||||
assertErrorCode(
|
||||
coll,
|
||||
[{$merge: {into: coll.getName(), whenMatched: "fail", whenNotMatched: "insert"}}],
|
||||
51188);
|
||||
assertMergeFailsForAllModesWithCode({source: coll, target: coll, errorCodes: 51188});
|
||||
}());
|
||||
|
||||
@@ -8,8 +8,8 @@
|
||||
(function() {
|
||||
"use strict";
|
||||
|
||||
load("jstests/aggregation/extras/out_helpers.js"); // For withEachMergeMode,
|
||||
// assertFailsWithoutUniqueIndex.
|
||||
load("jstests/aggregation/extras/merge_helpers.js"); // For withEachMergeMode,
|
||||
// assertMergeFailsWithoutUniqueIndex.
|
||||
|
||||
const testDB = db.getSiblingDB("merge_requires_unique_index");
|
||||
assert.commandWorked(testDB.dropDatabase());
|
||||
@@ -74,7 +74,8 @@
|
||||
(function basicUniqueIndexWorks() {
|
||||
const target = testDB.regular_unique;
|
||||
dropWithoutImplicitRecreate(target);
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: ["_id", "a"], target: target});
|
||||
assertMergeFailsWithoutUniqueIndex(
|
||||
{source: source, onFields: ["_id", "a"], target: target});
|
||||
|
||||
assert.commandWorked(testDB.runCommand({create: target.getName()}));
|
||||
assert.commandWorked(target.createIndex({a: 1, _id: 1}, {unique: true}));
|
||||
@@ -95,11 +96,11 @@
|
||||
}
|
||||
}]));
|
||||
|
||||
assertFailsWithoutUniqueIndex(
|
||||
assertMergeFailsWithoutUniqueIndex(
|
||||
{source: source, onFields: ["_id", "a", "b"], target: target});
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: ["a", "b"], target: target});
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: ["b"], target: target});
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: ["a"], target: target});
|
||||
assertMergeFailsWithoutUniqueIndex({source: source, onFields: ["a", "b"], target: target});
|
||||
assertMergeFailsWithoutUniqueIndex({source: source, onFields: ["b"], target: target});
|
||||
assertMergeFailsWithoutUniqueIndex({source: source, onFields: ["a"], target: target});
|
||||
|
||||
assert.commandWorked(target.dropIndex({a: 1, _id: 1}));
|
||||
assert.commandWorked(target.createIndex({a: 1}, {unique: true}));
|
||||
@@ -115,8 +116,9 @@
|
||||
// Create a non-unique index and make sure that doesn't work.
|
||||
assert.commandWorked(target.dropIndex({a: 1}));
|
||||
assert.commandWorked(target.createIndex({a: 1}));
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: "a", target: target});
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: ["_id", "a"], target: target});
|
||||
assertMergeFailsWithoutUniqueIndex({source: source, onFields: "a", target: target});
|
||||
assertMergeFailsWithoutUniqueIndex(
|
||||
{source: source, onFields: ["_id", "a"], target: target});
|
||||
}());
|
||||
|
||||
// Test that a unique index on the "on" fields cannot be used to satisfy the requirement if it
|
||||
@@ -124,12 +126,13 @@
|
||||
(function uniqueButPartialShouldNotWork() {
|
||||
const target = testDB.unique_but_partial_indexes;
|
||||
dropWithoutImplicitRecreate(target);
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: "a", target: target});
|
||||
assertMergeFailsWithoutUniqueIndex({source: source, onFields: "a", target: target});
|
||||
|
||||
assert.commandWorked(
|
||||
target.createIndex({a: 1}, {unique: true, partialFilterExpression: {a: {$gte: 2}}}));
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: "a", target: target});
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: ["_id", "a"], target: target});
|
||||
assertMergeFailsWithoutUniqueIndex({source: source, onFields: "a", target: target});
|
||||
assertMergeFailsWithoutUniqueIndex(
|
||||
{source: source, onFields: ["_id", "a"], target: target});
|
||||
}());
|
||||
|
||||
// Test that a unique index on the "on" fields cannot be used to satisfy the requirement if it
|
||||
@@ -137,20 +140,20 @@
|
||||
(function indexMustMatchCollationOfOperation() {
|
||||
const target = testDB.collation_indexes;
|
||||
dropWithoutImplicitRecreate(target);
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: "a", target: target});
|
||||
assertMergeFailsWithoutUniqueIndex({source: source, onFields: "a", target: target});
|
||||
|
||||
assert.commandWorked(
|
||||
target.createIndex({a: 1}, {unique: true, collation: {locale: "en_US"}}));
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: "a", target: target});
|
||||
assertFailsWithoutUniqueIndex(
|
||||
assertMergeFailsWithoutUniqueIndex({source: source, onFields: "a", target: target});
|
||||
assertMergeFailsWithoutUniqueIndex(
|
||||
{source: source, onFields: "a", target: target, options: {collation: {locale: "en"}}});
|
||||
assertFailsWithoutUniqueIndex({
|
||||
assertMergeFailsWithoutUniqueIndex({
|
||||
source: source,
|
||||
onFields: "a",
|
||||
target: target,
|
||||
options: {collation: {locale: "simple"}}
|
||||
});
|
||||
assertFailsWithoutUniqueIndex({
|
||||
assertMergeFailsWithoutUniqueIndex({
|
||||
source: source,
|
||||
onFields: "a",
|
||||
target: target,
|
||||
@@ -169,7 +172,7 @@
|
||||
// Test that a non-unique index with the same collation cannot be used.
|
||||
assert.commandWorked(target.dropIndex({a: 1}));
|
||||
assert.commandWorked(target.createIndex({a: 1}, {collation: {locale: "en_US"}}));
|
||||
assertFailsWithoutUniqueIndex({
|
||||
assertMergeFailsWithoutUniqueIndex({
|
||||
source: source,
|
||||
onFields: "a",
|
||||
target: target,
|
||||
@@ -184,7 +187,7 @@
|
||||
assert.commandWorked(
|
||||
testDB.runCommand({create: target.getName(), collation: {locale: "en_US"}}));
|
||||
assert.commandWorked(target.createIndex({a: 1}, {unique: true}));
|
||||
assertFailsWithoutUniqueIndex({
|
||||
assertMergeFailsWithoutUniqueIndex({
|
||||
source: source,
|
||||
onFields: "a",
|
||||
target: target,
|
||||
@@ -230,7 +233,7 @@
|
||||
}
|
||||
}],
|
||||
{collation: {locale: "simple"}}));
|
||||
assertFailsWithoutUniqueIndex({
|
||||
assertMergeFailsWithoutUniqueIndex({
|
||||
source: source,
|
||||
onFields: "a",
|
||||
target: target,
|
||||
@@ -245,32 +248,38 @@
|
||||
dropWithoutImplicitRecreate(target);
|
||||
|
||||
assert.commandWorked(target.createIndex({a: 1, text: "text"}, {unique: true}));
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: "a", target: target});
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: ["a", "text"], target: target});
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: "text", target: target});
|
||||
assertMergeFailsWithoutUniqueIndex({source: source, onFields: "a", target: target});
|
||||
assertMergeFailsWithoutUniqueIndex(
|
||||
{source: source, onFields: ["a", "text"], target: target});
|
||||
assertMergeFailsWithoutUniqueIndex({source: source, onFields: "text", target: target});
|
||||
|
||||
dropWithoutImplicitRecreate(target);
|
||||
assert.commandWorked(target.createIndex({a: 1, geo: "2dsphere"}, {unique: true}));
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: "a", target: target});
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: ["a", "geo"], target: target});
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: ["geo", "a"], target: target});
|
||||
assertMergeFailsWithoutUniqueIndex({source: source, onFields: "a", target: target});
|
||||
assertMergeFailsWithoutUniqueIndex(
|
||||
{source: source, onFields: ["a", "geo"], target: target});
|
||||
assertMergeFailsWithoutUniqueIndex(
|
||||
{source: source, onFields: ["geo", "a"], target: target});
|
||||
|
||||
dropWithoutImplicitRecreate(target);
|
||||
assert.commandWorked(target.createIndex({geo: "2d"}, {unique: true}));
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: ["a", "geo"], target: target});
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: "geo", target: target});
|
||||
assertMergeFailsWithoutUniqueIndex(
|
||||
{source: source, onFields: ["a", "geo"], target: target});
|
||||
assertMergeFailsWithoutUniqueIndex({source: source, onFields: "geo", target: target});
|
||||
|
||||
dropWithoutImplicitRecreate(target);
|
||||
assert.commandWorked(
|
||||
target.createIndex({geo: "geoHaystack", a: 1}, {unique: true, bucketSize: 5}));
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: ["a", "geo"], target: target});
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: ["geo", "a"], target: target});
|
||||
assertMergeFailsWithoutUniqueIndex(
|
||||
{source: source, onFields: ["a", "geo"], target: target});
|
||||
assertMergeFailsWithoutUniqueIndex(
|
||||
{source: source, onFields: ["geo", "a"], target: target});
|
||||
|
||||
dropWithoutImplicitRecreate(target);
|
||||
// MongoDB does not support unique hashed indexes.
|
||||
assert.commandFailedWithCode(target.createIndex({a: "hashed"}, {unique: true}), 16764);
|
||||
assert.commandWorked(target.createIndex({a: "hashed"}));
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: "a", target: target});
|
||||
assertMergeFailsWithoutUniqueIndex({source: source, onFields: "a", target: target});
|
||||
}());
|
||||
|
||||
// Test that a unique index with dotted field names can be used.
|
||||
@@ -279,7 +288,7 @@
|
||||
dropWithoutImplicitRecreate(target);
|
||||
|
||||
assert.commandWorked(target.createIndex({a: 1, "b.c.d": -1}, {unique: true}));
|
||||
assertFailsWithoutUniqueIndex({source: source, onFields: "a", target: target});
|
||||
assertMergeFailsWithoutUniqueIndex({source: source, onFields: "a", target: target});
|
||||
assert.doesNotThrow(() => source.aggregate([
|
||||
{$project: {_id: 1, a: 1, b: {c: {d: "x"}}}},
|
||||
{
|
||||
|
||||
@@ -49,7 +49,7 @@
|
||||
|
||||
assert.commandWorked(sessionColl.deleteOne({_id: kDeletedDocumentId}));
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// Do applyOps on the collection that we care about. This is an "external" applyOps, though
|
||||
// (not run as part of a transaction) so its entries should be skipped in the change
|
||||
|
||||
@@ -43,7 +43,7 @@
|
||||
|
||||
assert.commandWorked(sessionColl.updateOne({_id: 1}, {$inc: {a: 1}}));
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// Now insert another document, not part of a transaction.
|
||||
assert.commandWorked(coll.insert({_id: 3, a: 123}));
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
'use strict';
|
||||
|
||||
var {withTxnAndAutoRetry} = (function() {
|
||||
var {withTxnAndAutoRetry, isKilledSessionCode} = (function() {
|
||||
|
||||
/**
|
||||
* Calls 'func' with the print() function overridden to be a no-op.
|
||||
@@ -145,14 +145,15 @@ var {withTxnAndAutoRetry} = (function() {
|
||||
|
||||
} catch (e) {
|
||||
if (!hasCommitTxnError) {
|
||||
// Use the version of abortTransaction() that ignores errors. We ignore the
|
||||
// error from abortTransaction because the transaction may have implicitly
|
||||
// been aborted by the server already and will therefore return a
|
||||
// NoSuchTransaction error response.
|
||||
// We need to call abortTransaction() in order to update the mongo shell's
|
||||
// state such that it agrees no transaction is currently in progress on this
|
||||
// session.
|
||||
session.abortTransaction();
|
||||
// We need to call abortTransaction_forTesting() in order to update the mongo
|
||||
// shell's state such that it agrees no transaction is currently in progress on
|
||||
// this session.
|
||||
// The transaction may have implicitly been aborted by the server or killed by
|
||||
// the kill_session helper and will therefore return a
|
||||
// NoSuchTransaction/Interrupted error code.
|
||||
assert.commandWorkedOrFailedWithCode(
|
||||
session.abortTransaction_forTesting(),
|
||||
[ErrorCodes.NoSuchTransaction, ErrorCodes.Interrupted]);
|
||||
}
|
||||
|
||||
if (shouldRetryEntireTxnOnError(e, hasCommitTxnError, retryOnKilledSession)) {
|
||||
|
||||
@@ -114,7 +114,8 @@ var $config = (function() {
|
||||
do {
|
||||
try {
|
||||
shouldJoin = false;
|
||||
quietly(() => this.session.commitTransaction());
|
||||
quietly(() =>
|
||||
assert.commandWorked(this.session.commitTransaction_forTesting()));
|
||||
} catch (e) {
|
||||
if (e.code === ErrorCodes.TransactionTooOld ||
|
||||
e.code === ErrorCodes.TransactionCommitted ||
|
||||
|
||||
@@ -81,7 +81,7 @@
|
||||
}
|
||||
const uri = new MongoURI(db.getMongo().host);
|
||||
assert(uri.servers.some((server) => {
|
||||
return result[0].host.toLowerCase() == getHostName() + ":" + server.port;
|
||||
return result[0].host == getHostName() + ":" + server.port;
|
||||
}));
|
||||
const idleCursor = result[0].cursor;
|
||||
assert.eq(idleCursor.nDocsReturned, 2, result);
|
||||
|
||||
@@ -12,13 +12,14 @@ for (var i = 1; i <= 10; i++) {
|
||||
}
|
||||
|
||||
// returns old
|
||||
out = t.findAndModify({update: {$set: {inprogress: true}, $inc: {value: 1}}});
|
||||
out = t.findAndModify({sort: {priority: 1}, update: {$set: {inprogress: true}, $inc: {value: 1}}});
|
||||
assert.eq(out.value, 0);
|
||||
assert.eq(out.inprogress, false);
|
||||
t.update({_id: out._id}, {$set: {inprogress: false}});
|
||||
|
||||
// returns new
|
||||
out = t.findAndModify({update: {$set: {inprogress: true}, $inc: {value: 1}}, 'new': true});
|
||||
out = t.findAndModify(
|
||||
{sort: {priority: 1}, update: {$set: {inprogress: true}, $inc: {value: 1}}, 'new': true});
|
||||
assert.eq(out.value, 2);
|
||||
assert.eq(out.inprogress, true);
|
||||
t.update({_id: out._id}, {$set: {inprogress: false}});
|
||||
|
||||
@@ -94,7 +94,7 @@
|
||||
assert.eq(countRes.length, 1, tojson(countRes));
|
||||
assert.eq(countRes[0].count, 2, tojson(countRes));
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
jsTestLog("Transaction committed.");
|
||||
|
||||
// Perform aggregations with non-cursor initial sources and assert that they are not supported
|
||||
|
||||
@@ -27,7 +27,7 @@
|
||||
|
||||
assert.docEq({_id: "insert-1"}, sessionColl.findOne({_id: "insert-1"}));
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
session.endSession();
|
||||
}());
|
||||
|
||||
@@ -27,7 +27,7 @@
|
||||
// Implicit creation.
|
||||
assert.commandWorked(db.runCommand({insert: "c", documents: [{x: 2}]}));
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
rst.stopSet();
|
||||
})();
|
||||
|
||||
@@ -41,7 +41,7 @@
|
||||
assert.commandWorked(testColl.insert({_id: 2}, {writeConcern: {w: "majority"}}));
|
||||
assertSameMembers([{_id: 0}]);
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
assertSameMembers([{_id: 0}, {_id: 1}, {_id: 2}]);
|
||||
session.endSession();
|
||||
|
||||
@@ -26,7 +26,7 @@
|
||||
// This only requires database IX lock.
|
||||
assert.commandWorked(db.runCommand({drop: "b"}));
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
rst.stopSet();
|
||||
})();
|
||||
|
||||
@@ -48,7 +48,7 @@
|
||||
"Test that we can't call prepareTransaction if the most recent transaction was committed");
|
||||
session.startTransaction();
|
||||
assert.commandWorked(sessionColl.insert({_id: 1}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
assert.commandFailedWithCode(sessionDB.adminCommand({
|
||||
prepareTransaction: 1,
|
||||
|
||||
@@ -22,7 +22,7 @@
|
||||
|
||||
session.startTransaction();
|
||||
assert.commandWorked(sessionColl.insert(doc));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
const txnNumber = NumberLong(session.getTxnNumber_forTesting());
|
||||
|
||||
|
||||
@@ -36,7 +36,7 @@
|
||||
assert.sameMembers(docs, [{_id: 0, a: 0}, {_id: 1, a: 1}, {_id: 2, a: 2}]);
|
||||
|
||||
// Commit the transaction.
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
/***********************************************************************************************
|
||||
* Do a non-matching find-and-modify with update.
|
||||
@@ -52,7 +52,7 @@
|
||||
assert.sameMembers(docs, [{_id: 0, a: 0}, {_id: 1, a: 1}, {_id: 2, a: 2}]);
|
||||
|
||||
// Commit the transaction.
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
/***********************************************************************************************
|
||||
* Do a matching find-and-modify with remove.
|
||||
@@ -68,7 +68,7 @@
|
||||
assert.sameMembers(docs, [{_id: 1, a: 1}, {_id: 2, a: 2}]);
|
||||
|
||||
// Commit the transaction.
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
/***********************************************************************************************
|
||||
* Do a matching find-and-modify with update, requesting the old doc.
|
||||
@@ -83,7 +83,7 @@
|
||||
assert.sameMembers(docs, [{_id: 1, a: 101}, {_id: 2, a: 2}]);
|
||||
|
||||
// Commit the transaction.
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
/***********************************************************************************************
|
||||
* Do a matching find-and-modify with update, requesting the new doc.
|
||||
@@ -98,7 +98,7 @@
|
||||
assert.sameMembers(docs, [{_id: 1, a: 101}, {_id: 2, a: 102}]);
|
||||
|
||||
// Commit the transaction.
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
/***********************************************************************************************
|
||||
* Do a matching find-and-modify with upsert, requesting the new doc.
|
||||
@@ -114,7 +114,7 @@
|
||||
assert.sameMembers(docs, [{_id: 1, a: 101}, {_id: 2, a: 202}]);
|
||||
|
||||
// Commit the transaction.
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
/***********************************************************************************************
|
||||
* Do a non-matching find-and-modify with upsert, requesting the old doc.
|
||||
@@ -129,7 +129,7 @@
|
||||
assert.sameMembers(docs, [{a: 103}]);
|
||||
|
||||
// Commit the transaction.
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
/***********************************************************************************************
|
||||
* Do a non-matching find-and-modify with upsert, requesting the new doc.
|
||||
@@ -146,6 +146,6 @@
|
||||
assert.sameMembers(docs, [newdoc]);
|
||||
|
||||
// Commit the transaction.
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
session.endSession();
|
||||
}());
|
||||
|
||||
@@ -23,7 +23,7 @@
|
||||
assert(res.hasOwnProperty("cursor"), tojson(res));
|
||||
assert(res.cursor.hasOwnProperty("id"), tojson(res));
|
||||
assert.commandWorked(sessionDb.runCommand({killCursors: collName, cursors: [res.cursor.id]}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
jsTest.log("Test that the killCursors cannot be the first operation in a transaction.");
|
||||
res = assert.commandWorked(sessionDb.runCommand({find: collName, batchSize: 2}));
|
||||
@@ -69,7 +69,7 @@
|
||||
// killCursors does not block behind the pending MODE_X lock.
|
||||
assert.commandWorked(sessionDb.runCommand({killCursors: collName, cursors: [res.cursor.id]}));
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// Once the transaction has committed, the drop can proceed.
|
||||
awaitDrop();
|
||||
|
||||
@@ -20,7 +20,7 @@
|
||||
let res = assert.commandWorked(sessionDb.runCommand({find: collName, batchSize: 2}));
|
||||
assert(res.hasOwnProperty("cursor"), tojson(res));
|
||||
assert(res.cursor.hasOwnProperty("id"), tojson(res));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
assert.commandWorked(sessionDb.runCommand({killCursors: collName, cursors: [res.cursor.id]}));
|
||||
|
||||
jsTest.log("Test that cursors created in transactions may be kill outside of the session.");
|
||||
@@ -28,7 +28,7 @@
|
||||
res = assert.commandWorked(sessionDb.runCommand({find: collName, batchSize: 2}));
|
||||
assert(res.hasOwnProperty("cursor"), tojson(res));
|
||||
assert(res.cursor.hasOwnProperty("id"), tojson(res));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
assert.commandWorked(testDB.runCommand({killCursors: collName, cursors: [res.cursor.id]}));
|
||||
|
||||
session.endSession();
|
||||
|
||||
@@ -55,7 +55,7 @@
|
||||
assert.commandWorked(sessionColl.insert({_id: 4}));
|
||||
|
||||
jsTest.log("Commit transaction.");
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
assert.sameMembers([{_id: 0}, {_id: 1}, {_id: 2}, {_id: 3}, {_id: 4}],
|
||||
sessionColl.find().toArray());
|
||||
|
||||
|
||||
@@ -54,7 +54,7 @@ var WriteConflictHelpers = (function() {
|
||||
assert(!res.hasOwnProperty("writeErrors"));
|
||||
assert.commandFailedWithCode(res, ErrorCodes.WriteConflict);
|
||||
|
||||
session1.commitTransaction();
|
||||
assert.commandWorked(session1.commitTransaction_forTesting());
|
||||
assert.commandFailedWithCode(session2.commitTransaction_forTesting(),
|
||||
ErrorCodes.NoSuchTransaction);
|
||||
}
|
||||
@@ -83,7 +83,7 @@ var WriteConflictHelpers = (function() {
|
||||
|
||||
assert.commandWorked(session1Coll.runCommand({find: collName})); // Start T1 with a no-op.
|
||||
assert.commandWorked(session2Coll.runCommand(txn2Op));
|
||||
session2.commitTransaction();
|
||||
assert.commandWorked(session2.commitTransaction_forTesting());
|
||||
|
||||
const res = session1Coll.runCommand(txn1Op);
|
||||
// Not a writeError but a total command failure
|
||||
|
||||
@@ -38,6 +38,6 @@
|
||||
assert(collObj.hasOwnProperty("info") == !nameOnly, tojson(collObj));
|
||||
}
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
session.endSession();
|
||||
}());
|
||||
|
||||
@@ -31,7 +31,7 @@
|
||||
res = sessionColl.find({});
|
||||
assert.sameMembers(res.toArray(), [{_id: 0, a: 0}, {_id: 1, a: 0}, {_id: 2, a: 1}]);
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
jsTest.log("Do a single-result multi-delete.");
|
||||
session.startTransaction({writeConcern: {w: "majority"}});
|
||||
@@ -42,7 +42,7 @@
|
||||
res = sessionColl.find({});
|
||||
assert.sameMembers(res.toArray(), [{_id: 0, a: 0}, {_id: 1, a: 0}]);
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
jsTest.log("Do a multiple-result multi-delete.");
|
||||
session.startTransaction({writeConcern: {w: "majority"}});
|
||||
@@ -53,7 +53,7 @@
|
||||
res = sessionColl.find({});
|
||||
assert.sameMembers(res.toArray(), []);
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// Collection should be empty.
|
||||
assert.eq(0, testColl.find().itcount());
|
||||
|
||||
@@ -49,7 +49,7 @@
|
||||
assert.eq(null, testColl.findOne({_id: "insert-2"}));
|
||||
|
||||
// Commit the transaction.
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// Read with default read concern sees the committed transaction.
|
||||
assert.eq({_id: "insert-1"}, testColl.findOne({_id: "insert-1"}));
|
||||
@@ -83,7 +83,7 @@
|
||||
assert.eq({_id: "update-2", a: 0}, testColl.findOne({_id: "update-2"}));
|
||||
|
||||
// Commit the transaction.
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// Read with default read concern sees the committed transaction.
|
||||
assert.eq({_id: "update-1", a: 2}, testColl.findOne({_id: "update-1"}));
|
||||
@@ -113,7 +113,7 @@
|
||||
assert.sameMembers([{_id: "doc-1", a: 1}, {_id: "doc-2", a: 1}], docs);
|
||||
|
||||
// Commit the transaction.
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// Read with default read concern sees the committed transaction.
|
||||
assert.eq({_id: "doc-1", a: 1}, testColl.findOne({_id: "doc-1"}));
|
||||
@@ -148,7 +148,7 @@
|
||||
assert.sameMembers([], docs);
|
||||
|
||||
// Commit the transaction.
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// Read with default read concern sees the commmitted transaction.
|
||||
assert.eq(null, testColl.findOne({_id: "doc-1"}));
|
||||
|
||||
@@ -34,7 +34,7 @@
|
||||
session.startTransaction({readConcern: {level: "snapshot"}, writeConcern: {w: "majority"}});
|
||||
|
||||
// Successfully call commitTransaction.
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
jsTestLog("Run CRUD ops, read ops, and commit transaction.");
|
||||
session.startTransaction({readConcern: {level: "snapshot"}, writeConcern: {w: "majority"}});
|
||||
@@ -67,7 +67,7 @@
|
||||
assert.docEq({_id: "insert-1", a: 1}, cursor.next());
|
||||
assert(!cursor.hasNext());
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// Make sure the correct documents exist after committing the transaciton.
|
||||
assert.eq({_id: "insert-1", a: 1}, sessionColl.findOne({_id: "insert-1"}));
|
||||
@@ -93,7 +93,7 @@
|
||||
bulk.find({_id: "bulk-1"}).updateOne({$set: {status: "bulk"}});
|
||||
bulk.find({_id: "bulk-2"}).updateOne({$set: {status: "bulk"}});
|
||||
assert.commandWorked(bulk.execute());
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
assert.eq({_id: "bulk-1", status: "bulk"}, sessionColl.findOne({_id: "bulk-1"}));
|
||||
assert.eq({_id: "bulk-2", status: "bulk"}, sessionColl.findOne({_id: "bulk-2"}));
|
||||
@@ -105,7 +105,7 @@
|
||||
bulk.find({_id: "bulk-1"}).removeOne();
|
||||
bulk.find({_id: "bulk-2"}).removeOne();
|
||||
assert.commandWorked(bulk.execute());
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
assert.eq(null, sessionColl.findOne({_id: "bulk-1"}));
|
||||
assert.eq(null, sessionColl.findOne({_id: "bulk-2"}));
|
||||
|
||||
@@ -40,7 +40,8 @@
|
||||
throw e;
|
||||
}
|
||||
} finally {
|
||||
session.abortTransaction();
|
||||
assert.commandFailedWithCode(session.abortTransaction_forTesting(),
|
||||
ErrorCodes.NoSuchTransaction);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -31,7 +31,7 @@
|
||||
res = sessionColl.find({});
|
||||
assert.sameMembers(res.toArray(), [{_id: 0, a: 0}, {_id: 1, a: 0}, {_id: 2, a: 1}]);
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
jsTest.log("Do a single-result multi-update.");
|
||||
session.startTransaction({writeConcern: {w: "majority"}});
|
||||
@@ -42,7 +42,7 @@
|
||||
res = sessionColl.find({});
|
||||
assert.sameMembers(res.toArray(), [{_id: 0, a: 0}, {_id: 1, a: 0}, {_id: 2, a: 1, b: 1}]);
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
jsTest.log("Do a multiple-result multi-update.");
|
||||
session.startTransaction({writeConcern: {w: "majority"}});
|
||||
@@ -54,7 +54,7 @@
|
||||
assert.sameMembers(res.toArray(),
|
||||
[{_id: 0, a: 0, b: 2}, {_id: 1, a: 0, b: 2}, {_id: 2, a: 1, b: 1}]);
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
jsTest.log("Do a multiple-query multi-update.");
|
||||
session.startTransaction({writeConcern: {w: "majority"}});
|
||||
@@ -71,7 +71,7 @@
|
||||
res.toArray(),
|
||||
[{_id: 0, a: 0, b: 2, c: 1}, {_id: 1, a: 0, b: 2, c: 1}, {_id: 2, a: 1, b: 1, c: 2}]);
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
jsTest.log("Do a multi-update with upsert.");
|
||||
session.startTransaction({writeConcern: {w: "majority"}});
|
||||
@@ -87,5 +87,5 @@
|
||||
{_id: 3, d: 1}
|
||||
]);
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
}());
|
||||
|
||||
@@ -24,7 +24,7 @@
|
||||
|
||||
session.startTransaction({writeConcern: {w: "majority"}});
|
||||
sessionColl.insert({_id: "doc"});
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
assert.eq({_id: "doc"}, testColl.findOne({_id: "doc"}));
|
||||
|
||||
// Insert fails when the collection does not exist.
|
||||
@@ -47,7 +47,7 @@
|
||||
|
||||
session.startTransaction({writeConcern: {w: "majority"}});
|
||||
sessionColl.update({_id: "doc"}, {$set: {updated: true}}, {upsert: true});
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
assert.eq({_id: "doc", updated: true}, testColl.findOne({_id: "doc"}));
|
||||
|
||||
// Update with upsert=true fails when the collection does not exist.
|
||||
@@ -67,7 +67,7 @@
|
||||
session.startTransaction({writeConcern: {w: "majority"}});
|
||||
assert.commandWorked(
|
||||
sessionColl.update({_id: "doc"}, {$set: {updated: true}}, {upsert: false}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
assert.eq(null, testColl.findOne({_id: "doc"}));
|
||||
|
||||
jsTest.log("Cannot implicitly create a collection in a transaction using findAndModify.");
|
||||
@@ -80,7 +80,7 @@
|
||||
let res = sessionColl.findAndModify(
|
||||
{query: {_id: "doc"}, update: {$set: {updated: true}}, upsert: true});
|
||||
assert.eq(null, res);
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
assert.eq({_id: "doc", updated: true}, testColl.findOne({_id: "doc"}));
|
||||
|
||||
// findAndModify with upsert=true fails when the collection does not exist.
|
||||
@@ -101,7 +101,7 @@
|
||||
res = sessionColl.findAndModify(
|
||||
{query: {_id: "doc"}, update: {$set: {updated: true}}, upsert: false});
|
||||
assert.eq(null, res);
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
assert.eq(null, testColl.findOne({_id: "doc"}));
|
||||
|
||||
session.endSession();
|
||||
|
||||
@@ -21,7 +21,7 @@
|
||||
session.startTransaction();
|
||||
assert.writeOK(sessionColl.update({}, {$set: {a: [1, 2, 3]}}));
|
||||
assert.eq(1, sessionColl.find({}, {_id: 0, a: 1}).sort({a: 1}).itcount());
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
assert.eq(1,
|
||||
db.getSiblingDB(dbName)
|
||||
|
||||
@@ -29,7 +29,7 @@
|
||||
db.adminCommand({renameCollection: "test.a", to: "test.b", dropTarget: true}));
|
||||
assert.commandWorked(db.adminCommand({renameCollection: "test.b", to: "test.c"}));
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
rst.stopSet();
|
||||
})();
|
||||
|
||||
@@ -50,7 +50,7 @@
|
||||
assert.sameMembers(expectedDocs, sessionColl.find().toArray());
|
||||
|
||||
jsTestLog("Committing the second transaction.");
|
||||
session2.commitTransaction();
|
||||
assert.commandWorked(session2.commitTransaction_forTesting());
|
||||
|
||||
jsTestLog(
|
||||
"Committed changes from the second transaction should still not be visible to the first.");
|
||||
@@ -65,7 +65,7 @@
|
||||
assert.sameMembers(expectedDocs, sessionColl.find().toArray());
|
||||
|
||||
jsTestLog("Committing first transaction.");
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// Make sure the correct documents exist after committing the second transaction.
|
||||
assert.sameMembers([{_id: 0}, {_id: 1, a: 1}, {_id: 3}, {_id: 4}],
|
||||
|
||||
@@ -36,7 +36,7 @@
|
||||
simulatePrompt();
|
||||
assert.commandWorked(coll.insert(doc));
|
||||
simulatePrompt();
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
assert.docEq(doc, coll.findOne());
|
||||
|
||||
coll.drop({writeConcern: {w: "majority"}});
|
||||
|
||||
@@ -99,10 +99,10 @@
|
||||
checkReads(defaultSession, [{_id: 0}, {_id: 1}], [{_id: "a"}]);
|
||||
|
||||
jsTestLog("Committing transactions.");
|
||||
snapshotSession.commitTransaction();
|
||||
majoritySession.commitTransaction();
|
||||
localSession.commitTransaction();
|
||||
defaultSession.commitTransaction();
|
||||
assert.commandWorked(snapshotSession.commitTransaction_forTesting());
|
||||
assert.commandWorked(majoritySession.commitTransaction_forTesting());
|
||||
assert.commandWorked(localSession.commitTransaction_forTesting());
|
||||
assert.commandWorked(defaultSession.commitTransaction_forTesting());
|
||||
|
||||
jsTestLog("A new local read must see all committed writes.");
|
||||
checkReads(defaultSession, [{_id: 0}, {_id: 1}], [{_id: "a"}, {_id: "b"}]);
|
||||
|
||||
@@ -41,7 +41,7 @@
|
||||
// Insert a doc within a transaction.
|
||||
assert.commandWorked(sessionColl.insert({_id: "insert-2"}));
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// Read with default read concern sees the committed transaction.
|
||||
assert.eq({_id: "insert-1"}, coll.findOne({_id: "insert-1"}));
|
||||
|
||||
@@ -19,7 +19,7 @@
|
||||
jsTestLog("Test that we cannot abort or commit a nonexistant transaction.");
|
||||
// Cannot abort or commit a nonexistant transaction.
|
||||
try {
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
} catch (e) {
|
||||
assert.eq(e.message, "There is no active transaction to commit on this session.");
|
||||
}
|
||||
@@ -51,11 +51,11 @@
|
||||
|
||||
// At this point, the transaction is still 'active'. We will commit this transaction and test
|
||||
// that calling commitTransaction again should work while calling abortTransaction should not.
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
jsTestLog("Test that we can commit a transaction more than once.");
|
||||
// The transaction state is 'committed'. We can call commitTransaction again in this state.
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
jsTestLog("Test that we cannot abort a transaction that has already been committed");
|
||||
// We cannot call abortTransaction on a transaction that has already been committed.
|
||||
@@ -75,7 +75,7 @@
|
||||
jsTestLog("Test that we cannot commit a transaction that has already been aborted.");
|
||||
// We cannot call commitTransaction on a transaction that has already been aborted.
|
||||
try {
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
} catch (e) {
|
||||
assert.eq(e.message, "Cannot call commitTransaction after calling abortTransaction.");
|
||||
}
|
||||
@@ -94,11 +94,11 @@
|
||||
session.startTransaction();
|
||||
assert.commandWorked(sessionColl.insert({_id: "insert-3"}));
|
||||
// The transaction state should be changed to 'committed'.
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
// The transaction state should be changed to 'inactive'.
|
||||
assert.commandWorked(sessionColl.insert({_id: "normal-insert"}));
|
||||
try {
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
} catch (e) {
|
||||
assert.eq(e.message, "There is no active transaction to commit on this session.");
|
||||
}
|
||||
|
||||
@@ -158,7 +158,7 @@
|
||||
assert.eq(profileObj.nModified, 1, tojson(profileObj));
|
||||
|
||||
jsTestLog("Committing transaction.");
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
jsTestLog("Test delete with a write conflict.");
|
||||
assert.commandWorked(sessionColl.insert({_id: "delete-doc"}, {writeConcern: {w: "majority"}}));
|
||||
|
||||
@@ -64,7 +64,7 @@
|
||||
assert.sameMembers(
|
||||
[{_id: "doc"}],
|
||||
sessionColl.find({$where: "sleep(1000); return true;"}).comment("read failure").toArray());
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
assert.commandWorked(testDB.killOp(opId));
|
||||
lockShell();
|
||||
@@ -97,7 +97,7 @@
|
||||
"since the transaction already has an IX DB lock.");
|
||||
assert.commandWorked(sessionColl.update(
|
||||
{$where: "sleep(1000); return true;"}, {$inc: {good: 1}}, {collation: {locale: "fr"}}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
assert.commandWorked(testDB.killOp(opId));
|
||||
lockShell();
|
||||
|
||||
@@ -55,6 +55,6 @@
|
||||
|
||||
assert.eq(view.distinct("_id"), ["kyle"]);
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
jsTestLog("Transaction committed.");
|
||||
}());
|
||||
|
||||
@@ -84,7 +84,7 @@
|
||||
// single doc write should get serialized after the transaction, we expect it to fail with a
|
||||
// duplicate key error.
|
||||
jsTestLog("Commit the multi-document transaction.");
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
thread.join();
|
||||
assert.commandFailedWithCode(thread.returnData(), ErrorCodes.DuplicateKey);
|
||||
|
||||
|
||||
@@ -23,6 +23,7 @@
|
||||
assert.commandWorked(testColl.update({_id: 1}, [{$set: {update: true}}]));
|
||||
assert.commandWorked(testColl.update({}, [{$set: {updateMulti: true}}], {multi: true}));
|
||||
assert.commandWorked(testColl.updateOne({_id: 1}, [{$set: {updateOne: true}}]));
|
||||
assert.commandWorked(testColl.updateMany({}, [{$set: {updateMany: true}}]));
|
||||
assert.commandWorked(testColl.bulkWrite([
|
||||
{updateOne: {filter: {_id: 1}, update: [{$set: {bulkWriteUpdateOne: true}}]}},
|
||||
{updateMany: {filter: {}, update: [{$set: {bulkWriteUpdateMany: true}}]}}
|
||||
@@ -49,6 +50,7 @@
|
||||
update: true,
|
||||
updateMulti: true,
|
||||
updateOne: true,
|
||||
updateMany: true,
|
||||
bulkWriteUpdateOne: true,
|
||||
bulkWriteUpdateMany: true,
|
||||
unorderedBulkOpUpdateOne: true,
|
||||
@@ -61,6 +63,7 @@
|
||||
a: 2,
|
||||
b: 3,
|
||||
updateMulti: true,
|
||||
updateMany: true,
|
||||
bulkWriteUpdateMany: true,
|
||||
unorderedBulkOpUpdateMulti: true,
|
||||
orderedBulkOpUpdateMulti: true
|
||||
|
||||
@@ -6,8 +6,10 @@
|
||||
(function() {
|
||||
"use strict";
|
||||
|
||||
// For arrayEq, assertErrorCode, and orderedArrayEq.
|
||||
load("jstests/aggregation/extras/utils.js");
|
||||
// For assertMergeFailsForAllModesWithCode.
|
||||
load("jstests/aggregation/extras/merge_helpers.js");
|
||||
load("jstests/aggregation/extras/utils.js"); // For arrayEq, assertErrorCode, and
|
||||
// orderedArrayEq.
|
||||
|
||||
let viewsDB = db.getSiblingDB("views_aggregation");
|
||||
assert.commandWorked(viewsDB.dropDatabase());
|
||||
@@ -75,38 +77,24 @@
|
||||
|
||||
// Test that the $out stage errors when writing to a view namespace.
|
||||
assertErrorCode(coll, [{$out: "emptyPipelineView"}], ErrorCodes.CommandNotSupportedOnView);
|
||||
|
||||
// Test that the $merge stage errors when writing to a view namespace.
|
||||
assertErrorCode(
|
||||
coll,
|
||||
[{$merge: {into: "emptyPipelineView", whenMatched: "fail", whenNotMatched: "insert"}}],
|
||||
ErrorCodes.CommandNotSupportedOnView);
|
||||
assertErrorCode(
|
||||
coll,
|
||||
[{$merge: {into: "emptyPipelineView", whenMatched: "replace", whenNotMatched: "insert"}}],
|
||||
ErrorCodes.CommandNotSupportedOnView);
|
||||
assertMergeFailsForAllModesWithCode({
|
||||
source: viewsDB.coll,
|
||||
target: viewsDB.emptyPipelineView,
|
||||
errorCodes: [ErrorCodes.CommandNotSupportedOnView]
|
||||
});
|
||||
|
||||
// Test that the $merge stage errors when writing to a view namespace in a foreign database.
|
||||
let foreignDB = db.getSiblingDB("views_aggregation_foreign");
|
||||
foreignDB.view.drop();
|
||||
assert.commandWorked(foreignDB.createView("view", "coll", []));
|
||||
assertErrorCode(coll,
|
||||
[{
|
||||
$merge: {
|
||||
into: {db: foreignDB.getName(), coll: "view"},
|
||||
whenMatched: "fail",
|
||||
whenNotMatched: "insert"
|
||||
}
|
||||
}],
|
||||
ErrorCodes.CommandNotSupportedOnView);
|
||||
assertErrorCode(coll,
|
||||
[{
|
||||
$merge: {
|
||||
into: {db: foreignDB.getName(), coll: "view"},
|
||||
whenMatched: "replace",
|
||||
whenNotMatched: "insert"
|
||||
}
|
||||
}],
|
||||
ErrorCodes.CommandNotSupportedOnView);
|
||||
|
||||
assertMergeFailsForAllModesWithCode({
|
||||
source: viewsDB.coll,
|
||||
target: foreignDB.view,
|
||||
errorCodes: [ErrorCodes.CommandNotSupportedOnView]
|
||||
});
|
||||
|
||||
// Test that an aggregate on a view propagates the 'bypassDocumentValidation' option.
|
||||
const validatedCollName = "collectionWithValidator";
|
||||
|
||||
@@ -18,3 +18,9 @@ function waitForCurOpByFailPoint(db, nss, failPoint) {
|
||||
let filter = {$and: [{"ns": nss}, {"msg": failPoint}]};
|
||||
waitForCurOpByFilter(db, filter);
|
||||
}
|
||||
|
||||
// Wait until the current operation reaches the fail point "failPoint" with no namespace.
|
||||
function waitForCurOpByFailPointNoNS(db, failPoint) {
|
||||
const filter = {"msg": failPoint};
|
||||
waitForCurOpByFilter(db, filter);
|
||||
}
|
||||
|
||||
@@ -127,13 +127,15 @@
|
||||
// both modify and replacement updates
|
||||
session.startTransaction();
|
||||
assert.writeError(sessionDB.foo.update({x: 80}, {$set: {x: 100}}));
|
||||
session.abortTransaction();
|
||||
assert.commandFailedWithCode(session.abortTransaction_forTesting(),
|
||||
ErrorCodes.NoSuchTransaction);
|
||||
|
||||
session.startTransaction();
|
||||
assert.throws(function() {
|
||||
sessionDB.foo.findAndModify({query: {x: 80}, update: {x: 100}});
|
||||
});
|
||||
session.abortTransaction();
|
||||
assert.commandFailedWithCode(session.abortTransaction_forTesting(),
|
||||
ErrorCodes.NoSuchTransaction);
|
||||
|
||||
mongos.getDB(kDbName).foo.drop();
|
||||
|
||||
|
||||
@@ -40,10 +40,10 @@ TestData.skipCheckingUUIDsConsistentAcrossCluster = true;
|
||||
"Expected \"" + v1 + "\" to compare equal to \"" + v2 + "\"");
|
||||
}
|
||||
|
||||
// The current version is in the 3.7 series. This has to be changed very time we bump
|
||||
// The current version is in the 4.2 series. This has to be changed very time we bump
|
||||
// the major version pair, but it provides a useful test of assumptions.
|
||||
assertBinVersionsEqual("4.1", version());
|
||||
assertBinVersionComparesEqual("4.1", version());
|
||||
assertBinVersionsEqual("4.2", version());
|
||||
assertBinVersionComparesEqual("4.2", version());
|
||||
|
||||
// "latest" is the same version as the shell, "last-stable" is not.
|
||||
assertBinVersionsEqual("latest", version());
|
||||
|
||||
@@ -0,0 +1,48 @@
|
||||
/**
|
||||
* The 'forEachCollectionFromDb' CollectionCatalog helper should abandon its snapshot before it
|
||||
* performs the user provided callback on each collection.
|
||||
* Any newly added collections have the chance to be seen as 'forEachCollectionFromDb' iterates over
|
||||
* the remaining collections. This could lead to inconsistencies, such as seeing indexes in the
|
||||
* IndexCatalog of the new collection but not seeing them on-disk due to using an older snapshot
|
||||
* (BF-13133).
|
||||
*
|
||||
* @tags: [requires_replication]
|
||||
*/
|
||||
(function() {
|
||||
"use strict";
|
||||
|
||||
const dbName = "test";
|
||||
const collName = "coll";
|
||||
|
||||
const rst = new ReplSetTest({nodes: 2});
|
||||
rst.startSet();
|
||||
rst.initiate();
|
||||
|
||||
const db = rst.getPrimary().getDB(dbName);
|
||||
assert.commandWorked(db.createCollection(collName));
|
||||
|
||||
const failpoint = 'hangBeforeGettingNextCollection';
|
||||
|
||||
// Hang 'forEachCollectionFromDb' after iterating through the first collection.
|
||||
assert.commandWorked(db.adminCommand({configureFailPoint: failpoint, mode: "alwaysOn"}));
|
||||
|
||||
TestData.failpoint = failpoint;
|
||||
const awaitCreateCollections = startParallelShell(() => {
|
||||
// The 'forEachCollectionFromDb' helper doesn't iterate in collection name order, so we need
|
||||
// to insert multiple collections to have at least one next collection when the
|
||||
// CollectionCatalog iterator is incremented.
|
||||
for (let i = 0; i < 25; i++) {
|
||||
const collName = "a".repeat(i + 1);
|
||||
assert.commandWorked(db.createCollection(collName));
|
||||
}
|
||||
|
||||
// Let 'forEachCollectionFromDb' iterate to the next collection.
|
||||
assert.commandWorked(
|
||||
db.adminCommand({configureFailPoint: TestData.failpoint, mode: "off"}));
|
||||
}, rst.getPrimary().port);
|
||||
|
||||
assert.commandWorked(db.stats());
|
||||
awaitCreateCollections();
|
||||
|
||||
rst.stopSet();
|
||||
}());
|
||||
75
jstests/noPassthrough/absent_ns_field_in_index_specs.js
Normal file
75
jstests/noPassthrough/absent_ns_field_in_index_specs.js
Normal file
@@ -0,0 +1,75 @@
|
||||
/**
|
||||
* Uses the 'disableIndexSpecNamespaceGeneration' server test parameter to disable the generation
|
||||
* of the 'ns' field for index specs to test the absence of the field.
|
||||
*
|
||||
* When the 'ns' field is missing from the index specs and the 'disableIndexSpecNamespaceGeneration'
|
||||
* server test parameter is disabled, the server should automatically add the 'ns' field to the
|
||||
* index specs missing it prior to returning them.
|
||||
*
|
||||
* @tags: [requires_replication, requires_persistence]
|
||||
*/
|
||||
(function() {
|
||||
'use strict';
|
||||
|
||||
const dbName = 'test';
|
||||
const collName = 'absent_ns';
|
||||
|
||||
let replSet = new ReplSetTest({name: 'absentNsField', nodes: 2});
|
||||
replSet.startSet();
|
||||
replSet.initiate();
|
||||
|
||||
const primary = replSet.getPrimary();
|
||||
const primaryDB = primary.getDB(dbName);
|
||||
const primaryColl = primaryDB.getCollection(collName);
|
||||
|
||||
const secondary = replSet.getSecondary();
|
||||
const secondaryDB = secondary.getDB(dbName);
|
||||
|
||||
// The primary will not generate the 'ns' field for index specs, but the secondary will.
|
||||
assert.commandWorked(primary.getDB('admin').runCommand(
|
||||
{setParameter: 1, disableIndexSpecNamespaceGeneration: 1}));
|
||||
|
||||
assert.commandWorked(primaryColl.insert({x: 100}));
|
||||
assert.commandWorked(primaryColl.createIndex({x: 1}));
|
||||
|
||||
replSet.awaitReplication();
|
||||
|
||||
let specPrimary =
|
||||
assert.commandWorked(primaryDB.runCommand({listIndexes: collName})).cursor.firstBatch[1];
|
||||
let specSecondary =
|
||||
assert.commandWorked(secondaryDB.runCommand({listIndexes: collName})).cursor.firstBatch[1];
|
||||
|
||||
assert.eq(false, specPrimary.hasOwnProperty('ns'));
|
||||
assert.eq(true, specSecondary.hasOwnProperty('ns'));
|
||||
assert.eq(dbName + '.' + collName, specSecondary.ns);
|
||||
|
||||
replSet.stopSet(/*signal=*/null, /*forRestart=*/true);
|
||||
|
||||
// The primaries index spec has no 'ns' field and the secondaries index spec does have the 'ns'
|
||||
// field. Restart the nodes as standalone and ensure that the primaries index spec gets updated
|
||||
// with the 'ns' field. No changes should be necessary to the secondaries index spec, but
|
||||
// verify that it still has the 'ns' field.
|
||||
const options = {dbpath: primary.dbpath, noCleanData: true};
|
||||
let conn = MongoRunner.runMongod(options);
|
||||
assert.neq(null, conn, 'mongod was unable to start up with options: ' + tojson(options));
|
||||
|
||||
let db = conn.getDB(dbName);
|
||||
let spec = assert.commandWorked(db.runCommand({listIndexes: collName})).cursor.firstBatch[1];
|
||||
|
||||
assert.eq(true, spec.hasOwnProperty('ns'));
|
||||
assert.eq(dbName + '.' + collName, spec.ns);
|
||||
|
||||
MongoRunner.stopMongod(conn);
|
||||
|
||||
options.dbpath = secondary.dbpath;
|
||||
conn = MongoRunner.runMongod(options);
|
||||
assert.neq(null, conn, 'mongod was unable to start up with options: ' + tojson(options));
|
||||
|
||||
db = conn.getDB(dbName);
|
||||
spec = assert.commandWorked(db.runCommand({listIndexes: collName})).cursor.firstBatch[1];
|
||||
|
||||
assert.eq(true, spec.hasOwnProperty('ns'));
|
||||
assert.eq(dbName + '.' + collName, spec.ns);
|
||||
|
||||
MongoRunner.stopMongod(conn);
|
||||
}());
|
||||
@@ -151,7 +151,7 @@
|
||||
assertNoChanges(changeStreamCursor);
|
||||
|
||||
// Transition the second transaction to prepared. We skip capturing the prepare
|
||||
// timestamp it is not required for abortTransaction().
|
||||
// timestamp it is not required for abortTransaction_forTesting().
|
||||
PrepareHelpers.prepareTransaction(session2);
|
||||
assertNoChanges(changeStreamCursor);
|
||||
|
||||
@@ -164,7 +164,7 @@
|
||||
//
|
||||
// Abort second transaction.
|
||||
//
|
||||
session2.abortTransaction();
|
||||
assert.commandWorked(session2.abortTransaction_forTesting());
|
||||
assertWriteVisibleWithCapture(
|
||||
changeStreamCursor, "insert", {_id: "no-txn-doc-4"}, changeList);
|
||||
assertNoChanges(changeStreamCursor);
|
||||
|
||||
@@ -60,7 +60,7 @@
|
||||
sessionColl.insert([{shard: 0, _id: "txn1-doc-6"}, {shard: 1, _id: "txn1-doc-7"}]));
|
||||
|
||||
// Commit the transaction.
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// Read the stream of events, capture them in 'changeList', and confirm that all events occurred
|
||||
// at or later than the clusterTime of the first event. Unfortunately, we cannot guarantee that
|
||||
|
||||
@@ -1,6 +1,10 @@
|
||||
/**
|
||||
* Characterizes the actions (rebuilds or drops the index) taken upon unfinished indexes when
|
||||
* restarting mongod from (standalone -> standalone) and (replica set member -> standalone).
|
||||
* Additionally, the primary will use the 'disableIndexSpecNamespaceGeneration' server test
|
||||
* parameter to prevent index specs from having the 'ns' field to test the absence of the 'ns' field
|
||||
* on a replica set with unfinished indexes during restart.
|
||||
*
|
||||
* @tags: [requires_replication, requires_persistence, requires_majority_read_concern]
|
||||
*/
|
||||
(function() {
|
||||
@@ -42,20 +46,14 @@
|
||||
}
|
||||
|
||||
function startReplSet() {
|
||||
let replSet = new ReplSetTest({name: "indexBuilds", nodes: 3, nodeOptions: {syncdelay: 1}});
|
||||
let replSet = new ReplSetTest({name: "indexBuilds", nodes: 2, nodeOptions: {syncdelay: 1}});
|
||||
let nodes = replSet.nodeList();
|
||||
|
||||
// We need an arbiter to ensure that the primary doesn't step down when we restart the
|
||||
// secondary
|
||||
replSet.startSet({startClean: true});
|
||||
replSet.initiate({
|
||||
_id: "indexBuilds",
|
||||
members: [
|
||||
{_id: 0, host: nodes[0]},
|
||||
{_id: 1, host: nodes[1]},
|
||||
{_id: 2, host: nodes[2], arbiterOnly: true}
|
||||
]
|
||||
});
|
||||
replSet.initiate(
|
||||
{_id: "indexBuilds", members: [{_id: 0, host: nodes[0]}, {_id: 1, host: nodes[1]}]});
|
||||
|
||||
replSet.getPrimary().getDB(dbName).dropDatabase();
|
||||
return replSet;
|
||||
@@ -81,6 +79,11 @@
|
||||
assert.commandWorked(secondaryDB.adminCommand(
|
||||
{configureFailPoint: "leaveIndexBuildUnfinishedForShutdown", mode: "alwaysOn"}));
|
||||
|
||||
// Do not generate the 'ns' field for index specs on the primary to test the absence of the
|
||||
// field on restart.
|
||||
assert.commandWorked(
|
||||
primaryDB.adminCommand({setParameter: 1, disableIndexSpecNamespaceGeneration: 1}));
|
||||
|
||||
try {
|
||||
let res = assert.commandWorked(primaryDB.runCommand({
|
||||
createIndexes: collName,
|
||||
@@ -142,6 +145,7 @@
|
||||
|
||||
let foundIndexEntry = false;
|
||||
for (let index = 0; index < collIndexes.length; index++) {
|
||||
assert.eq(true, collIndexes[index].hasOwnProperty('ns'));
|
||||
if (collIndexes[index].name == indexName) {
|
||||
foundIndexEntry = true;
|
||||
break;
|
||||
@@ -208,9 +212,7 @@
|
||||
|
||||
startIndexBuildOnSecondaryAndLeaveUnfinished(primaryDB, /*writeConcern=*/2, secondaryDB);
|
||||
|
||||
let secondaryId = replSet.getNodeId(secondary);
|
||||
replSet.stop(secondaryId);
|
||||
replSet.remove(secondaryId);
|
||||
replSet.stopSet(/*signal=*/null, /*forRestart=*/true);
|
||||
|
||||
let mongod = restartStandalone(secondary);
|
||||
|
||||
@@ -220,7 +222,15 @@
|
||||
checkForIndexRebuild(mongod, fourthIndex, /*shouldExist=*/true);
|
||||
|
||||
shutdownStandalone(mongod);
|
||||
stopReplSet(replSet);
|
||||
|
||||
mongod = restartStandalone(primary);
|
||||
let specs = mongod.getDB(dbName).getCollection(collName).getIndexes();
|
||||
assert.eq(specs.length, 5);
|
||||
for (let index = 0; index < specs.length; index++) {
|
||||
assert.eq(true, specs[index].hasOwnProperty('ns'));
|
||||
}
|
||||
|
||||
shutdownStandalone(mongod);
|
||||
}
|
||||
|
||||
/* Begin tests */
|
||||
|
||||
@@ -27,7 +27,7 @@
|
||||
|
||||
assert.eq(db.view.find().toArray().length, 1);
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
rst.stopSet();
|
||||
})();
|
||||
|
||||
@@ -40,7 +40,7 @@
|
||||
sessionDb.runCommand({find: collName, sort: sort, singleBatch: true}));
|
||||
assert.eq(expected, response.cursor.firstBatch);
|
||||
});
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
}
|
||||
|
||||
// insert
|
||||
|
||||
@@ -21,7 +21,7 @@
|
||||
const prepareTimestamp = PrepareHelpers.prepareTransaction(session);
|
||||
PrepareHelpers.commitTransaction(session, prepareTimestamp);
|
||||
} else {
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -21,7 +21,7 @@
|
||||
assert.commandFailedWithCode(dropDB.runCommand({dropDatabase: 1, maxTimeMS: 100}),
|
||||
ErrorCodes.MaxTimeMSExpired);
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
session.endSession();
|
||||
})();
|
||||
|
||||
@@ -56,7 +56,7 @@
|
||||
// This should timeout.
|
||||
dropDatabaseShell();
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
session.endSession();
|
||||
})();
|
||||
|
||||
|
||||
@@ -79,7 +79,7 @@
|
||||
return true;
|
||||
});
|
||||
|
||||
session.abortTransaction();
|
||||
assert.commandWorked(session.abortTransaction_forTesting());
|
||||
|
||||
st.stop();
|
||||
})();
|
||||
|
||||
@@ -66,7 +66,7 @@
|
||||
// commands are counted towards the "commands" counter.
|
||||
session.startTransaction();
|
||||
assert.commandWorked(sessionColl.insert({_id: "insert-1"}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
lastHistogram = checkHistogramDiff(lastHistogram,
|
||||
getHistogramStats(),
|
||||
{"reads": 0, "writes": 1, "commands": 2, "transactions": 1});
|
||||
@@ -99,7 +99,7 @@
|
||||
assert.commandWorked(sessionColl.insert({_id: "insert-3"}));
|
||||
assert.commandWorked(sessionColl.insert({_id: "insert-4"}));
|
||||
assert.eq(sessionColl.find({_id: "insert-1"}).itcount(), 1);
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
lastHistogram = checkHistogramDiff(lastHistogram,
|
||||
getHistogramStats(),
|
||||
{"reads": 1, "writes": 2, "commands": 2, "transactions": 1});
|
||||
@@ -111,7 +111,7 @@
|
||||
session.startTransaction();
|
||||
assert.eq(sessionColl.find({_id: "insert-1"}).itcount(), 1);
|
||||
sleep(sleepTime);
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
lastHistogram = checkHistogramLatencyDiff(lastHistogram, getHistogramStats(), sleepTime);
|
||||
}
|
||||
|
||||
|
||||
@@ -19,7 +19,7 @@
|
||||
// Run a transaction so the 'config.transactions' collection is implicitly created.
|
||||
session.startTransaction();
|
||||
assert.writeOK(primaryDB.getCollection(collName).insert({x: 2}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// Run a predicate query that would fail if we did not ignore the 'notablescan' flag.
|
||||
assert.eq(configDB.transactions.find({any_nonexistent_field: {$exists: true}}).itcount(),
|
||||
|
||||
@@ -28,11 +28,11 @@
|
||||
const primary = replSetTest.getPrimary();
|
||||
const primaryDB = primary.getDB('test');
|
||||
|
||||
const docsToInsert = 10;
|
||||
let numDocs = 10;
|
||||
let setUp = function(coll) {
|
||||
coll.drop();
|
||||
let bulk = coll.initializeUnorderedBulkOp();
|
||||
for (let i = 0; i < docsToInsert; i++) {
|
||||
for (let i = 0; i < numDocs; i++) {
|
||||
bulk.insert({i: i});
|
||||
}
|
||||
assert.commandWorked(bulk.execute());
|
||||
@@ -54,6 +54,11 @@
|
||||
const awaitBuild = IndexBuildTest.startIndexBuild(primary, coll.getFullName(), {i: 1});
|
||||
const opId = IndexBuildTest.waitForIndexBuildToStart(testDB, collName, "i_1");
|
||||
|
||||
// This insert will block until the index build pauses and releases its exclusive lock.
|
||||
// This guarantees that the subsequent transaction can immediately acquire a lock and not
|
||||
// fail with a LockTimeout error.
|
||||
assert.commandWorked(coll.insert({i: numDocs++}));
|
||||
|
||||
// Start a session and introduce a document that is in a prepared state, but should be
|
||||
// ignored by the index build, at least until the transaction commits.
|
||||
const session = primaryDB.getMongo().startSession();
|
||||
@@ -95,8 +100,8 @@
|
||||
awaitBuild();
|
||||
IndexBuildTest.waitForIndexBuildToStop(testDB, collName, "i_1");
|
||||
|
||||
assert.eq(docsToInsert, coll.count());
|
||||
assert.eq(docsToInsert, coll.find().itcount());
|
||||
assert.eq(numDocs, coll.count());
|
||||
assert.eq(numDocs, coll.find().itcount());
|
||||
};
|
||||
|
||||
runTest(replSetTest.getPrimary());
|
||||
|
||||
@@ -3,8 +3,8 @@
|
||||
* @tags: [requires_sharding, requires_replication]
|
||||
*/
|
||||
(function() {
|
||||
load("jstests/aggregation/extras/out_helpers.js"); // For withEachMergeMode().
|
||||
load("jstests/libs/fixture_helpers.js"); // For isMongos().
|
||||
load("jstests/aggregation/extras/merge_helpers.js"); // For withEachMergeMode().
|
||||
load("jstests/libs/fixture_helpers.js"); // For isMongos().
|
||||
load("jstests/libs/profiler.js"); // For profilerHasSingleMatchingEntryOrThrow.
|
||||
|
||||
const kDBName = "test";
|
||||
|
||||
@@ -43,7 +43,7 @@ function _getClusterTime(rst) {
|
||||
// 'atClusterTime' can be used with readConcern level 'snapshot'.
|
||||
session.startTransaction({readConcern: {level: "snapshot", atClusterTime: clusterTime}});
|
||||
assert.commandWorked(sessionDb.runCommand({find: collName}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// 'atClusterTime' cannot be greater than the current cluster time.
|
||||
const futureClusterTime = new Timestamp(clusterTime.getTime() + 1000, 1);
|
||||
@@ -130,7 +130,7 @@ function _getClusterTime(rst) {
|
||||
session.startTransaction(
|
||||
{readConcern: {level: "snapshot", atClusterTime: _getClusterTime(rst)}});
|
||||
assert.commandWorked(sessionDb.runCommand({find: collName}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
session.endSession();
|
||||
rst.stopSet();
|
||||
|
||||
@@ -144,7 +144,7 @@ function _getClusterTime(rst) {
|
||||
session.startTransaction(
|
||||
{readConcern: {level: "snapshot", atClusterTime: _getClusterTime(rst)}});
|
||||
assert.commandWorked(sessionDb.runCommand({find: collName}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
session.endSession();
|
||||
rst.stopSet();
|
||||
}
|
||||
|
||||
@@ -81,7 +81,7 @@
|
||||
assert.commandFailedWithCode(toRSSession.abortTransaction_forTesting(),
|
||||
ErrorCodes.NoSuchTransaction);
|
||||
} else {
|
||||
toRSSession.commitTransaction();
|
||||
assert.commandWorked(toRSSession.commitTransaction_forTesting());
|
||||
}
|
||||
|
||||
const toRSOpTime = getLastOpTime(toRS.getPrimary()).ts;
|
||||
|
||||
@@ -54,7 +54,7 @@
|
||||
primarySession.startTransaction(
|
||||
{readConcern: {level: "snapshot", atClusterTime: clusterTimePrimaryBefore}});
|
||||
res = assert.commandWorked(primaryDB.runCommand({find: collName}));
|
||||
primarySession.commitTransaction();
|
||||
assert.commandWorked(primarySession.commitTransaction_forTesting());
|
||||
assert.eq(res.cursor.firstBatch.length, 1, printjson(res));
|
||||
assert.eq(res.cursor.firstBatch[0]._id, "before", printjson(res));
|
||||
|
||||
@@ -80,7 +80,7 @@
|
||||
// Restart replication on one of the secondaries.
|
||||
restartServerReplication(secondaryConn1);
|
||||
// This time the transaction should commit.
|
||||
primarySession.commitTransaction();
|
||||
assert.commandWorked(primarySession.commitTransaction_forTesting());
|
||||
|
||||
// Restart replication on the lagged secondary.
|
||||
restartServerReplication(secondaryConn0);
|
||||
|
||||
@@ -62,7 +62,7 @@
|
||||
session.startTransaction({writeConcern: {w: "majority"}, readConcern: {level: "snapshot"}});
|
||||
assert.commandWorked(sessionDb.coll.insert({}));
|
||||
assert.commandWorked(sessionDb.runCommand({find: collName}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// readConcern 'snapshot' is allowed with 'afterClusterTime'.
|
||||
session.startTransaction();
|
||||
@@ -73,7 +73,7 @@
|
||||
find: collName,
|
||||
readConcern: {level: "snapshot", afterClusterTime: pingRes.$clusterTime.clusterTime}
|
||||
}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// readConcern 'snapshot' is not allowed with 'afterOpTime'.
|
||||
session.startTransaction(
|
||||
@@ -90,7 +90,7 @@
|
||||
session.startTransaction(
|
||||
{readConcern: {level: "snapshot", afterClusterTime: pingRes.$clusterTime.clusterTime}});
|
||||
assert.commandWorked(sessionDb.runCommand({find: collName}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
session.endSession();
|
||||
rst.stopSet();
|
||||
|
||||
@@ -206,7 +206,7 @@
|
||||
const sessionDb = session.getDatabase("test");
|
||||
session.startTransaction({readConcern: {level: "snapshot"}});
|
||||
const res = assert.commandWorked(sessionDb.runCommand({find: "coll", filter: {x: 1}}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
assert.eq(res.cursor.firstBatch.length, TestData.numDocs, tojson(res));
|
||||
}, {"command.filter": {x: 1}});
|
||||
|
||||
@@ -226,7 +226,7 @@
|
||||
{configureFailPoint: "setInterruptOnlyPlansCheckForInterruptHang", mode: "alwaysOn"}));
|
||||
const res = assert.commandWorked(sessionDb.runCommand(
|
||||
{getMore: NumberLong(cursorId), collection: "coll", batchSize: TestData.numDocs}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
assert.eq(
|
||||
res.cursor.nextBatch.length, TestData.numDocs - initialFindBatchSize, tojson(res));
|
||||
}, {"cursor.originatingCommand.filter": {x: 1}});
|
||||
@@ -238,7 +238,7 @@
|
||||
session.startTransaction({readConcern: {level: "snapshot"}});
|
||||
const res = assert.commandWorked(
|
||||
sessionDb.runCommand({aggregate: "coll", pipeline: [{$match: {x: 1}}], cursor: {}}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
assert.eq(res.cursor.firstBatch.length, TestData.numDocs, tojson(res));
|
||||
}, {"command.pipeline": [{$match: {x: 1}}]});
|
||||
|
||||
@@ -259,7 +259,7 @@
|
||||
{configureFailPoint: "setInterruptOnlyPlansCheckForInterruptHang", mode: "alwaysOn"}));
|
||||
const res = assert.commandWorked(
|
||||
sessionDb.runCommand({getMore: NumberLong(cursorId), collection: "coll"}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
assert.eq(
|
||||
res.cursor.nextBatch.length, TestData.numDocs - initialFindBatchSize, tojson(res));
|
||||
}, {"cursor.originatingCommand.filter": {x: 1}});
|
||||
@@ -270,7 +270,7 @@
|
||||
const sessionDb = session.getDatabase("test");
|
||||
session.startTransaction({readConcern: {level: "snapshot"}});
|
||||
const res = assert.commandWorked(sessionDb.runCommand({distinct: "coll", key: "_id"}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
assert(res.hasOwnProperty("values"));
|
||||
assert.eq(res.values.length, 4, tojson(res));
|
||||
}, {"command.distinct": "coll"});
|
||||
@@ -285,7 +285,7 @@
|
||||
updates:
|
||||
[{q: {}, u: {$set: {updated: true}}}, {q: {new: 1}, u: {$set: {updated: true}}}]
|
||||
}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
// Only update one existing doc committed before the transaction.
|
||||
assert.eq(res.n, 1, tojson(res));
|
||||
assert.eq(res.nModified, 1, tojson(res));
|
||||
@@ -298,7 +298,7 @@
|
||||
session.startTransaction({readConcern: {level: "snapshot"}});
|
||||
const res = assert.commandWorked(sessionDb.runCommand(
|
||||
{delete: "coll", deletes: [{q: {}, limit: 1}, {q: {new: 1}, limit: 1}]}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
// Only remove one existing doc committed before the transaction.
|
||||
assert.eq(res.n, 1, tojson(res));
|
||||
}, {op: "remove"}, true);
|
||||
@@ -310,7 +310,7 @@
|
||||
session.startTransaction({readConcern: {level: "snapshot"}});
|
||||
const res = assert.commandWorked(sessionDb.runCommand(
|
||||
{findAndModify: "coll", query: {new: 1}, update: {$set: {findAndModify: 1}}}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
assert(res.hasOwnProperty("lastErrorObject"));
|
||||
assert.eq(res.lastErrorObject.n, 0, tojson(res));
|
||||
assert.eq(res.lastErrorObject.updatedExisting, false, tojson(res));
|
||||
@@ -322,7 +322,7 @@
|
||||
session.startTransaction({readConcern: {level: "snapshot"}});
|
||||
const res = assert.commandWorked(sessionDb.runCommand(
|
||||
{findAndModify: "coll", query: {new: 1}, update: {$set: {findAndModify: 1}}}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
assert(res.hasOwnProperty("lastErrorObject"));
|
||||
assert.eq(res.lastErrorObject.n, 0, tojson(res));
|
||||
assert.eq(res.lastErrorObject.updatedExisting, false, tojson(res));
|
||||
|
||||
@@ -1,40 +0,0 @@
|
||||
/**
|
||||
* Tests that replSetInitiate and replSetReconfig ignore hostname case.
|
||||
*
|
||||
* @tags: [requires_replication]
|
||||
*/
|
||||
|
||||
(function() {
|
||||
"use strict";
|
||||
|
||||
const rst = new ReplSetTest({nodes: 2});
|
||||
rst.startSet();
|
||||
|
||||
jsTestLog("replSetInitiate with uppercase hostname");
|
||||
|
||||
let conf = rst.getReplSetConfig();
|
||||
conf.members[0].host = conf.members[0].host.toUpperCase();
|
||||
|
||||
rst.initiate(conf);
|
||||
|
||||
const dbName = "test";
|
||||
const collName = "test";
|
||||
const primary = rst.getPrimary();
|
||||
const testColl = primary.getDB(dbName).getCollection(collName);
|
||||
const doc = {a: 1};
|
||||
|
||||
assert.commandWorked(testColl.insert(doc, {writeConcern: {w: 2}}));
|
||||
|
||||
jsTestLog("replSetReconfig with uppercase hostname");
|
||||
|
||||
let secondary2 = MongoRunner.runMongod({replSet: rst.name});
|
||||
conf = rst.getReplSetConfigFromNode();
|
||||
conf.version++;
|
||||
conf.members.push({_id: 5, host: secondary2.host.toUpperCase()});
|
||||
assert.commandWorked(primary.getDB("admin").runCommand({replSetReconfig: conf}));
|
||||
assert.commandWorked(testColl.insert(doc, {writeConcern: {w: 2}}));
|
||||
assert.commandWorked(testColl.insert(doc, {writeConcern: {w: 3}}));
|
||||
|
||||
MongoRunner.stopMongod(secondary2);
|
||||
rst.stopSet();
|
||||
})();
|
||||
@@ -80,7 +80,7 @@
|
||||
initialStatus.transactions, newStatus.transactions, "currentInactive", 1);
|
||||
|
||||
// Compare server status after the transaction commit with the server status before.
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
newStatus = assert.commandWorked(testDB.adminCommand({serverStatus: 1}));
|
||||
verifyServerStatusFields(newStatus);
|
||||
verifyServerStatusChange(initialStatus.transactions, newStatus.transactions, "totalStarted", 1);
|
||||
@@ -180,7 +180,7 @@
|
||||
|
||||
session.startTransaction({readConcern: {level: 'snapshot'}});
|
||||
assert.commandWorked(sessionColl.update({}, {"update-1": 2}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
};
|
||||
const transactionProcess = startParallelShell(transactionFn, primary.port);
|
||||
|
||||
|
||||
@@ -157,7 +157,7 @@
|
||||
|
||||
// Verify the total prepared and aborted transaction counters are updated after an abort and the
|
||||
// current prepared counter is decremented.
|
||||
session.abortTransaction();
|
||||
assert.commandWorked(session.abortTransaction_forTesting());
|
||||
newStatus = assert.commandWorked(testDB.adminCommand({serverStatus: 1}));
|
||||
verifyServerStatusFields(newStatus);
|
||||
verifyServerStatusChange(
|
||||
|
||||
@@ -74,7 +74,7 @@
|
||||
// getMore tests snapshot isolation across multiple getMore invocations.
|
||||
res = assert.commandWorked(
|
||||
sessionDb.runCommand({getMore: cursor.id, collection: collName, batchSize: 20}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// The cursor has been exhausted.
|
||||
cursor = parseCursor(res);
|
||||
@@ -89,7 +89,7 @@
|
||||
session.startTransaction({readConcern: readConcern});
|
||||
res = assert.commandWorked(
|
||||
sessionDb.runCommand({find: collName, sort: {_id: 1}, batchSize: 20}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// The cursor has been exhausted.
|
||||
cursor = parseCursor(res);
|
||||
|
||||
@@ -33,7 +33,7 @@
|
||||
// Execute a transaction that should succeed.
|
||||
session.startTransaction();
|
||||
assert.commandWorked(sessionDb[collName].insert({x: 1}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
session.endSession();
|
||||
replTest.stopSet();
|
||||
|
||||
@@ -65,10 +65,8 @@
|
||||
// First we start up the mongod normally, all the files except mongod.lock should have the mode
|
||||
// 0600
|
||||
let conn = MongoRunner.runMongod(mongodOptions);
|
||||
|
||||
checkMask(conn.fullOptions.dbpath, defaultUmask, false);
|
||||
|
||||
MongoRunner.stopMongod(conn);
|
||||
checkMask(conn.fullOptions.dbpath, defaultUmask, false);
|
||||
|
||||
// Restart the mongod with honorSystemUmask, all files should have the mode 0666
|
||||
mongodOptions.setParameter = {honorSystemUmask: true};
|
||||
|
||||
@@ -59,7 +59,7 @@
|
||||
assert.writeOK(sessionColl.update({_id: i}, {$inc: {i: 1}}));
|
||||
}
|
||||
}
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
session.endSession();
|
||||
|
||||
jsTestLog('Applying updates on secondary ' + secondary.host);
|
||||
|
||||
@@ -134,7 +134,7 @@
|
||||
newSession.startTransaction({writeConcern: {w: 3}});
|
||||
const secondDoc = {_id: "second-doc"};
|
||||
assert.commandWorked(newSession.getDatabase(dbName).getCollection(collName).insert(secondDoc));
|
||||
newSession.commitTransaction();
|
||||
assert.commandWorked(newSession.commitTransaction_forTesting());
|
||||
assert.docEq(testDB.getCollection(collName).find().toArray(), [secondDoc]);
|
||||
assert.docEq(newTestDB.getCollection(collName).find().toArray(), [secondDoc]);
|
||||
|
||||
|
||||
@@ -3,8 +3,8 @@
|
||||
(function() {
|
||||
"use strict";
|
||||
|
||||
load("jstests/aggregation/extras/out_helpers.js"); // For withEachKindOfWriteStage.
|
||||
load("jstests/libs/write_concern_util.js"); // For [stop|restart]ServerReplication.
|
||||
load("jstests/aggregation/extras/merge_helpers.js"); // For withEachKindOfWriteStage.
|
||||
load("jstests/libs/write_concern_util.js"); // For [stop|restart]ServerReplication.
|
||||
|
||||
// Start a replica set with two nodes: one with the default configuration and one with priority
|
||||
// zero to ensure we don't have any elections.
|
||||
|
||||
@@ -84,7 +84,7 @@
|
||||
return true;
|
||||
}, () => "Failed to find create collection in currentOp() output: " + tojson(db.currentOp()));
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
threadCaptruncCmd.join();
|
||||
threadDBHash.join();
|
||||
|
||||
|
||||
@@ -159,7 +159,7 @@
|
||||
assert(initialSyncTest.step(), "Expected initial sync to have completed, but it did not");
|
||||
|
||||
// Abort transaction so that the data consistency checks in stop() can run.
|
||||
session.abortTransaction();
|
||||
assert.commandWorked(session.abortTransaction_forTesting());
|
||||
|
||||
// Issue a w:2 write to make sure the secondary has replicated the abortTransaction oplog entry.
|
||||
assert.commandWorked(primary.getDB("otherDB").otherColl.insert({x: 1}, {writeConcern: {w: 2}}));
|
||||
@@ -174,4 +174,4 @@
|
||||
// Do data consistency checks at the end.
|
||||
initialSyncTest.stop();
|
||||
|
||||
})();
|
||||
})();
|
||||
|
||||
@@ -66,7 +66,7 @@
|
||||
secondSession.startTransaction({writeConcern: {w: "majority"}});
|
||||
assert.commandWorked(
|
||||
secondSession.getDatabase(dbName).getCollection(collName).insert({_id: "second-doc"}));
|
||||
secondSession.commitTransaction();
|
||||
assert.commandWorked(secondSession.commitTransaction_forTesting());
|
||||
|
||||
// Unfreeze the original primary so that it can stand for election again for the next test.
|
||||
assert.commandWorked(primary.adminCommand({replSetFreeze: 0}));
|
||||
|
||||
@@ -26,7 +26,7 @@
|
||||
session.startTransaction();
|
||||
assert.commandWorked(sessionColl.insert({_id: 1}));
|
||||
assert.commandWorked(sessionColl.insert({_id: 2}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
session.endSession();
|
||||
};
|
||||
|
||||
|
||||
@@ -22,7 +22,7 @@
|
||||
assert.commandWorked(sessionColl1.insert({a: 1}));
|
||||
session1.startTransaction();
|
||||
assert.commandWorked(sessionColl1.insert({b: 1}));
|
||||
session1.commitTransaction();
|
||||
assert.commandWorked(session1.commitTransaction_forTesting());
|
||||
|
||||
rollbackTest.awaitLastOpCommitted();
|
||||
assert.commandWorked(
|
||||
@@ -33,20 +33,20 @@
|
||||
const sessionColl2 = sessionDb2[collName];
|
||||
session2.startTransaction();
|
||||
assert.commandWorked(sessionColl2.insert({c: 1}));
|
||||
session2.commitTransaction();
|
||||
assert.commandWorked(session2.commitTransaction_forTesting());
|
||||
|
||||
rollbackTest.transitionToRollbackOperations();
|
||||
|
||||
session2.startTransaction();
|
||||
assert.commandWorked(sessionColl2.insert({d: 1}));
|
||||
session2.commitTransaction();
|
||||
assert.commandWorked(session2.commitTransaction_forTesting());
|
||||
|
||||
const session3 = primary.startSession();
|
||||
const sessionDb3 = session3.getDatabase(dbName);
|
||||
const sessionColl3 = sessionDb3[collName];
|
||||
session3.startTransaction();
|
||||
assert.commandWorked(sessionColl3.insert({e: 1}));
|
||||
session3.commitTransaction();
|
||||
assert.commandWorked(session3.commitTransaction_forTesting());
|
||||
|
||||
assert.eq(sessionColl1.find().itcount(), 5);
|
||||
|
||||
|
||||
@@ -50,7 +50,7 @@
|
||||
jsTestLog("Starting non-majority commit transaction");
|
||||
session.startTransaction({readConcern: {level: "snapshot"}, writeConcern: {w: 1}});
|
||||
assert.eq(sessionColl.findOne({_id: 0}), {_id: 0, x: 1});
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// This transaction should not complete because it uses snapshot read concern, majority
|
||||
// write concern and the commit point is not advancing.
|
||||
|
||||
@@ -42,7 +42,7 @@
|
||||
|
||||
assert.commandWorked(sessionColl.update({_id: 0}, {$set: {x: 1}}));
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// The document should be updated on the local snapshot.
|
||||
assert.eq(coll.findOne({_id: 0}), {_id: 0, x: 1});
|
||||
@@ -67,7 +67,7 @@
|
||||
// Within the transaction, we should not see the out-of-transaction update.
|
||||
assert.eq(sessionColl.findOne({_id: 1}), {_id: 1});
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// The document should be updated on the local snapshot.
|
||||
assert.eq(coll.findOne({_id: 0}), {_id: 0, x: 2});
|
||||
@@ -108,7 +108,7 @@
|
||||
// Update it one more time.
|
||||
assert.commandWorked(sessionColl.update({_id: 0}, {$inc: {x: 1}}));
|
||||
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// The document should be updated on the local snapshot.
|
||||
assert.eq(coll.findOne({_id: 0}), {_id: 0, x: 3});
|
||||
|
||||
131
jstests/replsets/step_down_on_secondary.js
Normal file
131
jstests/replsets/step_down_on_secondary.js
Normal file
@@ -0,0 +1,131 @@
|
||||
/*
|
||||
* Tests that we don't hit a 3 way deadlock when a step down thread waits for the RSTL in SECONDARY
|
||||
* state. This occurs when two stepdowns begin concurrently and both attempt to acquire the RSTL.
|
||||
*
|
||||
* This test creates a scenario where:
|
||||
* 1) Read thread acquires RSTL in MODE_IX and is blocked by a prepared txn (from secondary oplog
|
||||
* application) due to a prepare conflict.
|
||||
* 2) Step down enqueues the RSTL in MODE_X and is blocked behind the read thread.
|
||||
* 3) Oplog applier is blocked trying to apply a 'commitTransaction' oplog entry. The commit is
|
||||
* attempting to acquire the RSTL lock in MODE_IX but is blocked behind the step down thread.
|
||||
*
|
||||
* @tags: [uses_transactions, uses_prepare_transaction]
|
||||
*/
|
||||
(function() {
|
||||
|
||||
"use strict";
|
||||
load('jstests/libs/parallelTester.js');
|
||||
load("jstests/libs/curop_helpers.js"); // for waitForCurOpByFailPoint().
|
||||
load("jstests/core/txns/libs/prepare_helpers.js");
|
||||
load("jstests/libs/check_log.js");
|
||||
|
||||
const dbName = "test";
|
||||
const collName = "coll";
|
||||
|
||||
const rst = new ReplSetTest({nodes: [{}, {rsConfig: {priority: 0}}]});
|
||||
rst.startSet();
|
||||
rst.initiate();
|
||||
|
||||
const primary = rst.getPrimary();
|
||||
const primaryDB = primary.getDB(dbName);
|
||||
const primaryColl = primaryDB[collName];
|
||||
const collNss = primaryColl.getFullName();
|
||||
const secondary = rst.getSecondary();
|
||||
|
||||
TestData.dbName = dbName;
|
||||
TestData.collName = collName;
|
||||
TestData.collNss = collNss;
|
||||
|
||||
jsTestLog("Do a document write");
|
||||
assert.commandWorked(primaryColl.insert({_id: 0}, {"writeConcern": {"w": "majority"}}));
|
||||
rst.awaitReplication();
|
||||
|
||||
jsTestLog("Hang primary on step down");
|
||||
const joinStepDownThread = startParallelShell(() => {
|
||||
assert.commandWorked(db.adminCommand(
|
||||
{configureFailPoint: "stepdownHangBeforeRSTLEnqueue", mode: "alwaysOn"}));
|
||||
|
||||
const freezeSecs = 24 * 60 * 60; // 24 hours
|
||||
assert.commandFailedWithCode(
|
||||
db.adminCommand({"replSetStepDown": freezeSecs, "force": true}), ErrorCodes.NotMaster);
|
||||
}, primary.port);
|
||||
|
||||
waitForCurOpByFailPointNoNS(primaryDB, "stepdownHangBeforeRSTLEnqueue");
|
||||
|
||||
jsTestLog("Force reconfig to swap the electable node");
|
||||
const newConfig = rst.getReplSetConfigFromNode();
|
||||
const oldPrimaryId = rst.getNodeId(primary);
|
||||
const newPrimaryId = rst.getNodeId(secondary);
|
||||
newConfig.members[newPrimaryId].priority = 1;
|
||||
newConfig.members[oldPrimaryId].priority = 0;
|
||||
newConfig.version++;
|
||||
assert.commandWorked(secondary.adminCommand({"replSetReconfig": newConfig, force: true}));
|
||||
|
||||
jsTestLog("Step up the new electable node");
|
||||
rst.stepUp(secondary);
|
||||
|
||||
jsTestLog("Wait for step up to complete");
|
||||
// Wait until the primary successfully steps down via heartbeat reconfig.
|
||||
rst.waitForState(secondary, ReplSetTest.State.PRIMARY);
|
||||
rst.waitForState(primary, ReplSetTest.State.SECONDARY);
|
||||
const newPrimary = rst.getPrimary();
|
||||
|
||||
jsTestLog("Prepare a transaction on the new primary");
|
||||
const session = newPrimary.startSession();
|
||||
const sessionDb = session.getDatabase(dbName);
|
||||
const sessionColl = sessionDb[collName];
|
||||
session.startTransaction({writeConcern: {w: "majority"}});
|
||||
assert.commandWorked(sessionColl.update({_id: 0}, {$set: {"b": 1}}));
|
||||
const prepareTimestamp = PrepareHelpers.prepareTransaction(session);
|
||||
|
||||
jsTestLog("Get a cluster time for afterClusterTime reads");
|
||||
TestData.clusterTimeAfterPrepare =
|
||||
assert
|
||||
.commandWorked(newPrimary.getDB(dbName)[collName].runCommand(
|
||||
"insert", {documents: [{_id: "clusterTimeAfterPrepare"}]}))
|
||||
.operationTime;
|
||||
|
||||
jsTestLog("Do a read that hits a prepare conflict on the old primary");
|
||||
assert.commandWorked(
|
||||
primary.adminCommand({configureFailPoint: "WTPrintPrepareConflictLog", mode: "alwaysOn"}));
|
||||
|
||||
const joinReadThread = startParallelShell(() => {
|
||||
db.getMongo().setSlaveOk(true);
|
||||
oldPrimaryDB = db.getSiblingDB(TestData.dbName);
|
||||
|
||||
assert.commandFailedWithCode(oldPrimaryDB.runCommand({
|
||||
find: TestData.collName,
|
||||
filter: {_id: 0},
|
||||
readConcern: {level: "local", afterClusterTime: TestData.clusterTimeAfterPrepare},
|
||||
}),
|
||||
ErrorCodes.InterruptedDueToReplStateChange);
|
||||
}, primary.port);
|
||||
|
||||
jsTestLog("Wait to hit a prepare conflict");
|
||||
checkLog.contains(primary, "WTPrintPrepareConflictLog fail point enabled");
|
||||
|
||||
jsTestLog("Allow step down to complete");
|
||||
assert.commandWorked(
|
||||
primary.adminCommand({configureFailPoint: "stepdownHangBeforeRSTLEnqueue", mode: "off"}));
|
||||
|
||||
jsTestLog("Wait for step down to start killing operations");
|
||||
checkLog.contains(primary, "Starting to kill user operations");
|
||||
|
||||
jsTestLog("Commit the prepared transaction");
|
||||
assert.commandWorked(PrepareHelpers.commitTransaction(session, prepareTimestamp));
|
||||
|
||||
jsTestLog("Join parallel shells");
|
||||
joinStepDownThread();
|
||||
joinReadThread();
|
||||
|
||||
// Validate that the read operation got killed during step down.
|
||||
const replMetrics = assert.commandWorked(primary.adminCommand({serverStatus: 1})).metrics.repl;
|
||||
assert.eq(replMetrics.stepDown.userOperationsKilled, 1, replMetrics);
|
||||
|
||||
jsTestLog("Check nodes have correct data");
|
||||
assert.docEq(newPrimary.getDB(dbName)[collName].find({_id: 0}).toArray(), [{_id: 0, b: 1}]);
|
||||
rst.awaitReplication();
|
||||
assert.docEq(primary.getDB(dbName)[collName].find({_id: 0}).toArray(), [{_id: 0, b: 1}]);
|
||||
|
||||
rst.stopSet();
|
||||
})();
|
||||
@@ -29,7 +29,7 @@
|
||||
session.startTransaction();
|
||||
assert.writeOK(coll.insert({_id: 0}));
|
||||
assert.writeOK(coll.insert({_id: 1}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
const opTime = session.getOperationTime();
|
||||
const txnNum = session.getTxnNumber_forTesting();
|
||||
jsTestLog('Successfully committed transaction at operation time ' + tojson(opTime) +
|
||||
|
||||
@@ -99,7 +99,7 @@
|
||||
// Make sure we read the updated data correctly.
|
||||
assert.docEq(sessionColl.find().sort({_id: 1}).toArray(),
|
||||
[{_id: 0, syncSource: 0, inTxn: 1}, {_id: 2}]);
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// Make sure data is visible after commit.
|
||||
assert.docEq(sessionColl.find().sort({_id: 1}).toArray(),
|
||||
@@ -110,7 +110,7 @@
|
||||
session.startTransaction();
|
||||
assert.docEq(sessionColl.find().sort({_id: 1}).toArray(), [{_id: 0}]);
|
||||
assert.commandWorked(sessionColl.update({_id: 0}, {$set: {inTxn: 1}}));
|
||||
session.commitTransaction();
|
||||
assert.commandWorked(session.commitTransaction_forTesting());
|
||||
|
||||
// Make sure data is visible after commit.
|
||||
assert.docEq(sessionColl.find().sort({_id: 1}).toArray(), [{_id: 0, inTxn: 1}]);
|
||||
|
||||
@@ -108,22 +108,22 @@
|
||||
primarySession.startTransaction();
|
||||
assert.commandWorked(
|
||||
primarySessionDb.runCommand({find: collName, $readPreference: {mode: "primary"}}));
|
||||
primarySession.commitTransaction();
|
||||
assert.commandWorked(primarySession.commitTransaction_forTesting());
|
||||
|
||||
primarySession.startTransaction();
|
||||
assert.commandWorked(
|
||||
primarySessionDb.runCommand({find: collName, $readPreference: {mode: "primaryPreferred"}}));
|
||||
primarySession.commitTransaction();
|
||||
assert.commandWorked(primarySession.commitTransaction_forTesting());
|
||||
|
||||
primarySession.startTransaction();
|
||||
assert.commandWorked(primarySessionDb.runCommand(
|
||||
{find: collName, $readPreference: {mode: "secondaryPreferred"}}));
|
||||
primarySession.commitTransaction();
|
||||
assert.commandWorked(primarySession.commitTransaction_forTesting());
|
||||
|
||||
primarySession.startTransaction();
|
||||
assert.commandWorked(
|
||||
primarySessionDb.runCommand({find: collName, $readPreference: {mode: "nearest"}}));
|
||||
primarySession.commitTransaction();
|
||||
assert.commandWorked(primarySession.commitTransaction_forTesting());
|
||||
|
||||
primarySession.endSession();
|
||||
|
||||
|
||||
@@ -86,15 +86,6 @@
|
||||
addShardRes = st.s.adminCommand({addShard: getHostName() + ":" + portWithoutHostRunning});
|
||||
assertAddShardFailed(addShardRes);
|
||||
|
||||
// 1.c. with uppercase hostname.
|
||||
|
||||
jsTest.log("Adding a standalone with an uppercase hostname should succeed.");
|
||||
let standalone1c = MongoRunner.runMongod({shardsvr: ''});
|
||||
addShardRes = st.s.adminCommand({addshard: standalone1c.name.toUpperCase()});
|
||||
assertAddShardSucceeded(addShardRes);
|
||||
removeShardWithName(addShardRes.shardAdded);
|
||||
MongoRunner.stopMongod(standalone1c);
|
||||
|
||||
// 2. Test adding a *replica set* with an ordinary set name
|
||||
|
||||
// 2.a. with or without specifying the shardName.
|
||||
@@ -149,20 +140,6 @@
|
||||
|
||||
rst3.stopSet();
|
||||
|
||||
// 2.c. with uppercase hostnames.
|
||||
|
||||
jsTest.log("Adding a replica set uppercase hostname should succeed.");
|
||||
let rst2c = new ReplSetTest({name: "rst2c", nodes: 1});
|
||||
rst2c.startSet({shardsvr: ''});
|
||||
rst2c.initiate();
|
||||
let rst2cURI = `${rst2c.name}/${rst2c.getPrimary().name.toUpperCase()}`;
|
||||
jsTestLog(`URI with uppercase hostname: ${rst2cURI}`);
|
||||
addShardRes = st.s.adminCommand({addShard: rst2cURI});
|
||||
assertAddShardSucceeded(addShardRes);
|
||||
assert.eq(rst2c.name, addShardRes.shardAdded);
|
||||
removeShardWithName(addShardRes.shardAdded);
|
||||
rst2c.stopSet();
|
||||
|
||||
// 3. Test adding a replica set whose *set name* is "config" with or without specifying the
|
||||
// shardName.
|
||||
|
||||
|
||||
@@ -478,10 +478,6 @@ TestData.skipAwaitingReplicationOnShardsBeforeCheckingUUIDs = true;
|
||||
assert(clusterAdminDB.logout());
|
||||
assert(clusterAdminDB.auth("user_inprog", "pwd"));
|
||||
|
||||
const getPrimary = (rs) => {
|
||||
return rs.getPrimary().host.toLowerCase();
|
||||
};
|
||||
|
||||
assert.eq(clusterAdminDB
|
||||
.aggregate([
|
||||
{$currentOp: {allUsers: true, idleConnections: true}},
|
||||
@@ -490,9 +486,9 @@ TestData.skipAwaitingReplicationOnShardsBeforeCheckingUUIDs = true;
|
||||
])
|
||||
.toArray(),
|
||||
[
|
||||
{_id: {shard: "aggregation_currentop-rs0", host: getPrimary(st.rs0)}},
|
||||
{_id: {shard: "aggregation_currentop-rs1", host: getPrimary(st.rs1)}},
|
||||
{_id: {shard: "aggregation_currentop-rs2", host: getPrimary(st.rs2)}}
|
||||
{_id: {shard: "aggregation_currentop-rs0", host: st.rs0.getPrimary().host}},
|
||||
{_id: {shard: "aggregation_currentop-rs1", host: st.rs1.getPrimary().host}},
|
||||
{_id: {shard: "aggregation_currentop-rs2", host: st.rs2.getPrimary().host}}
|
||||
]);
|
||||
|
||||
// Test that a $currentOp pipeline with {localOps:true} returns operations from the mongoS
|
||||
@@ -873,7 +869,7 @@ TestData.skipAwaitingReplicationOnShardsBeforeCheckingUUIDs = true;
|
||||
])
|
||||
.toArray(),
|
||||
[
|
||||
{_id: {host: shardConn.host.toLowerCase()}},
|
||||
{_id: {host: shardConn.host}},
|
||||
]);
|
||||
|
||||
// Test that attempting to 'spoof' a sharded request on non-shardsvr mongoD fails.
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user