* UpdateAllMatchingDocuments updates documents that match the query * and need to be updated based on the update document. Returns the * number of updated rows and matched documents for the query. */
| 1795 | * number of updated rows and matched documents for the query. |
| 1796 | */ |
| 1797 | static UpdateAllMatchingDocsResult |
| 1798 | UpdateAllMatchingDocuments(MongoCollection *collection, |
| 1799 | UpdateOneParams *currentUpdate, |
| 1800 | bool hasShardKeyValueFilter, int64 shardKeyHash, |
| 1801 | ExprEvalState *schemaValidationExprEvalState, |
| 1802 | bool *hasOnlyObjectIdFilter) |
| 1803 | { |
| 1804 | const char *tableName = collection->tableName; |
| 1805 | bool isLocalShardQuery = false; |
| 1806 | bool setShardKeyValueFilter = false; |
| 1807 | if (collection->shardTableName[0] != '\0') |
| 1808 | { |
| 1809 | /* If we can push down to the local shard, then prefer that. */ |
| 1810 | tableName = collection->shardTableName; |
| 1811 | isLocalShardQuery = true; |
| 1812 | NumBsonDocumentsUpdated = 0; |
| 1813 | } |
| 1814 | else if (!DefaultInlineWriteOperations) |
| 1815 | { |
| 1816 | setShardKeyValueFilter = true; |
| 1817 | } |
| 1818 | |
| 1819 | StringInfoData updateQuery; |
| 1820 | |
| 1821 | UpdateAllMatchingDocsResult result; |
| 1822 | memset(&result, 0, sizeof(UpdateAllMatchingDocsResult)); |
| 1823 | |
| 1824 | SPI_connect(); |
| 1825 | |
| 1826 | /* Here we need to create a document wrapper to preserve the type */ |
| 1827 | pgbson *updateDoc = BsonValueToDocumentPgbson(currentUpdate->update); |
| 1828 | pgbson *arrayFilters = currentUpdate->arrayFilters == NULL ? NULL : |
| 1829 | BsonValueToDocumentPgbson(currentUpdate->arrayFilters); |
| 1830 | |
| 1831 | /* Do these under the SPI Context so that they get deleted automatically at the end */ |
| 1832 | bool queryHasNonIdFilters = false; |
| 1833 | |
| 1834 | /* TODO: if the _id is collation-sensitive, we will avoid filtering by _id */ |
| 1835 | /* in the WHERE clause directly. */ |
| 1836 | bool isIdFilterCollationAwareIgnore = false; |
| 1837 | pgbson *objectIdFilter = GetObjectIdFilterFromQueryDocumentValue(currentUpdate->query, |
| 1838 | &queryHasNonIdFilters, |
| 1839 | & |
| 1840 | isIdFilterCollationAwareIgnore); |
| 1841 | |
| 1842 | *hasOnlyObjectIdFilter = objectIdFilter != NULL && !queryHasNonIdFilters; |
| 1843 | |
| 1844 | const bson_value_t *variableSpec = currentUpdate->variableSpec; |
| 1845 | pgbson *variableSpecBson = NULL; |
| 1846 | if (queryHasNonIdFilters) |
| 1847 | { |
| 1848 | variableSpecBson = variableSpec != NULL && |
| 1849 | variableSpec->value_type == BSON_TYPE_DOCUMENT ? |
| 1850 | PgbsonInitFromDocumentBsonValue(variableSpec) : NULL; |
| 1851 | } |
| 1852 | |
| 1853 | bool applyVariablSpec = variableSpecBson != NULL; |
| 1854 |
no test coverage detected