@mastra/mssql 1.10.6-alpha.0 → 1.10.6
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/docs/SKILL.md +1 -1
- package/dist/docs/assets/SOURCE_MAP.json +1 -1
- package/dist/index.cjs +42 -7
- package/dist/index.cjs.map +1 -1
- package/dist/index.js +42 -7
- package/dist/index.js.map +1 -1
- package/dist/storage/db/run-fencing.d.ts +6 -0
- package/dist/storage/db/run-fencing.d.ts.map +1 -1
- package/dist/storage/domains/workflows/index.d.ts +9 -3
- package/dist/storage/domains/workflows/index.d.ts.map +1 -1
- package/package.json +5 -5
package/dist/index.js
CHANGED
|
@@ -2162,9 +2162,17 @@ function withRunFence(pool, claimsTable, fence, operation, write) {
|
|
|
2162
2162
|
* duplicate key if they don't. On retry the row exists and the claim
|
|
2163
2163
|
* serializes behind its row lock.
|
|
2164
2164
|
*/
|
|
2165
|
-
|
|
2165
|
+
function claimTransaction(pool, fn) {
|
|
2166
|
+
return retryWriteRace(() => inTransaction(pool, fn));
|
|
2167
|
+
}
|
|
2168
|
+
/**
|
|
2169
|
+
* Runs `write` again when it lost a race to insert the same row: a deadlock
|
|
2170
|
+
* victim or a duplicate key. `write` must be a whole statement or
|
|
2171
|
+
* transaction, since a deadlock victim's transaction has already ended.
|
|
2172
|
+
*/
|
|
2173
|
+
async function retryWriteRace(write) {
|
|
2166
2174
|
for (let attempt = 1;; attempt++) try {
|
|
2167
|
-
return await
|
|
2175
|
+
return await write();
|
|
2168
2176
|
} catch (error) {
|
|
2169
2177
|
const number = error.number;
|
|
2170
2178
|
if (attempt >= MAX_CLAIM_ATTEMPTS || !(number === ERR_DEADLOCK_VICTIM || number === ERR_PRIMARY_KEY || number === ERR_UNIQUE_INDEX)) throw error;
|
|
@@ -4636,6 +4644,9 @@ var WorkflowsMSSQL = class WorkflowsMSSQL extends WorkflowsStorage {
|
|
|
4636
4644
|
this.skipDefaultIndexes = skipDefaultIndexes;
|
|
4637
4645
|
this.indexes = indexes?.filter((idx) => WorkflowsMSSQL.MANAGED_TABLES.includes(idx.table));
|
|
4638
4646
|
}
|
|
4647
|
+
supportsGuardedSnapshotWrites() {
|
|
4648
|
+
return true;
|
|
4649
|
+
}
|
|
4639
4650
|
supportsConcurrentUpdates() {
|
|
4640
4651
|
return true;
|
|
4641
4652
|
}
|
|
@@ -4945,14 +4956,16 @@ var WorkflowsMSSQL = class WorkflowsMSSQL extends WorkflowsStorage {
|
|
|
4945
4956
|
}, error);
|
|
4946
4957
|
}
|
|
4947
4958
|
}
|
|
4948
|
-
async persistWorkflowSnapshot({ workflowName, runId, resourceId, snapshot, fence }) {
|
|
4959
|
+
async persistWorkflowSnapshot({ workflowName, runId, resourceId, snapshot, fence, expectedStatus }) {
|
|
4949
4960
|
const table = getTableName({
|
|
4950
4961
|
indexName: TABLE_WORKFLOW_SNAPSHOT,
|
|
4951
4962
|
schemaName: getSchemaName(this.schema)
|
|
4952
4963
|
});
|
|
4953
4964
|
const now = (/* @__PURE__ */ new Date()).toISOString();
|
|
4965
|
+
const expectedStatuses = expectedStatus === void 0 ? void 0 : Array.isArray(expectedStatus) ? expectedStatus : [expectedStatus];
|
|
4966
|
+
const guard = expectedStatuses === void 0 ? "" : expectedStatuses.length === 0 ? " AND 1 = 0" : ` AND JSON_VALUE(target.[snapshot], '$.status') IN (${expectedStatuses.map((_, i) => `@expectedStatus${i}`).join(", ")})`;
|
|
4954
4967
|
try {
|
|
4955
|
-
await withRunFence(this.pool, this.#runOwnersTable, resolveRunFence(this, fence, runId), "persistWorkflowSnapshot", async (q) => {
|
|
4968
|
+
return await retryWriteRace(() => withRunFence(this.pool, this.#runOwnersTable, resolveRunFence(this, fence, runId), "persistWorkflowSnapshot", async (q) => {
|
|
4956
4969
|
const request = q.request();
|
|
4957
4970
|
request.input("workflow_name", workflowName);
|
|
4958
4971
|
request.input("run_id", runId);
|
|
@@ -4960,17 +4973,18 @@ var WorkflowsMSSQL = class WorkflowsMSSQL extends WorkflowsStorage {
|
|
|
4960
4973
|
request.input("snapshot", JSON.stringify(snapshot));
|
|
4961
4974
|
request.input("createdAt", sql.DateTime2, new Date(now));
|
|
4962
4975
|
request.input("updatedAt", sql.DateTime2, new Date(now));
|
|
4976
|
+
expectedStatuses?.forEach((status, i) => request.input(`expectedStatus${i}`, status));
|
|
4963
4977
|
const mergeSql = `MERGE INTO ${table} AS target
|
|
4964
4978
|
USING (SELECT @workflow_name AS workflow_name, @run_id AS run_id) AS src
|
|
4965
4979
|
ON target.workflow_name = src.workflow_name AND target.run_id = src.run_id
|
|
4966
|
-
WHEN MATCHED THEN UPDATE SET
|
|
4980
|
+
WHEN MATCHED${guard} THEN UPDATE SET
|
|
4967
4981
|
resourceId = @resourceId,
|
|
4968
4982
|
snapshot = @snapshot,
|
|
4969
4983
|
[updatedAt] = @updatedAt
|
|
4970
4984
|
WHEN NOT MATCHED THEN INSERT (workflow_name, run_id, resourceId, snapshot, [createdAt], [updatedAt])
|
|
4971
4985
|
VALUES (@workflow_name, @run_id, @resourceId, @snapshot, @createdAt, @updatedAt);`;
|
|
4972
|
-
await request.query(mergeSql);
|
|
4973
|
-
});
|
|
4986
|
+
return ((await request.query(mergeSql)).rowsAffected[0] ?? 0) > 0;
|
|
4987
|
+
}));
|
|
4974
4988
|
} catch (error) {
|
|
4975
4989
|
if (isRunFenceConflictError(error)) throw error;
|
|
4976
4990
|
throw new MastraError({
|
|
@@ -4984,6 +4998,27 @@ var WorkflowsMSSQL = class WorkflowsMSSQL extends WorkflowsStorage {
|
|
|
4984
4998
|
}, error);
|
|
4985
4999
|
}
|
|
4986
5000
|
}
|
|
5001
|
+
async loadWorkflowRunStatus({ workflowName, runId }) {
|
|
5002
|
+
try {
|
|
5003
|
+
const request = this.pool.request();
|
|
5004
|
+
request.input("workflow_name", workflowName);
|
|
5005
|
+
request.input("run_id", runId);
|
|
5006
|
+
return (await request.query(`SELECT TOP 1 JSON_VALUE([snapshot], '$.status') AS status FROM ${getTableName({
|
|
5007
|
+
indexName: TABLE_WORKFLOW_SNAPSHOT,
|
|
5008
|
+
schemaName: getSchemaName(this.schema)
|
|
5009
|
+
})} WHERE workflow_name = @workflow_name AND run_id = @run_id`)).recordset?.[0]?.status ?? null;
|
|
5010
|
+
} catch (error) {
|
|
5011
|
+
throw new MastraError({
|
|
5012
|
+
id: createStorageErrorId("MSSQL", "LOAD_WORKFLOW_RUN_STATUS", "FAILED"),
|
|
5013
|
+
domain: ErrorDomain.STORAGE,
|
|
5014
|
+
category: ErrorCategory.THIRD_PARTY,
|
|
5015
|
+
details: {
|
|
5016
|
+
workflowName,
|
|
5017
|
+
runId
|
|
5018
|
+
}
|
|
5019
|
+
}, error);
|
|
5020
|
+
}
|
|
5021
|
+
}
|
|
4987
5022
|
async loadWorkflowSnapshot({ workflowName, runId }) {
|
|
4988
5023
|
try {
|
|
4989
5024
|
const result = await this.db.load({
|