feat(collection): 采集箱开发
This commit is contained in:
+19
-8
@@ -33,23 +33,34 @@ const objectStorage = new S3Client({
|
||||
},
|
||||
});
|
||||
const mediaUploadCleanup = new MediaUploadCleanup(database, objectStorage);
|
||||
type StoreVerificationJob = OutboxJob & { payload: { store_id: string; operation_id: string; secret_id?: string } };
|
||||
|
||||
const worker = new Worker<OutboxJob>(
|
||||
'atlas-dispatch',
|
||||
async (job) => {
|
||||
if (job.name === 'store_credential_verification.requested') {
|
||||
await verifyStoreCredentials(database, job.data);
|
||||
await verifyStoreCredentials(database, job.data as OutboxJob & { payload: { store_id: string; operation_id: string; secret_id?: string } });
|
||||
} else if (job.name === 'collection.cleanup.requested') {
|
||||
await cleanupCollection(database, job.data as OutboxJob & { payload: { operation_id: string; collection_item_ids: string[] } });
|
||||
}
|
||||
},
|
||||
{ connection, concurrency: 5 },
|
||||
);
|
||||
|
||||
async function cleanupCollection(database: Database, job: OutboxJob & { payload: { operation_id: string; collection_item_ids: string[] } }) {
|
||||
await database.workspaceTransaction(job.workspaceId, async (tx) => {
|
||||
await tx.query(`UPDATE atlas.operations SET status = 'running', started_at = coalesce(started_at, now()), attempt_count = attempt_count + 1 WHERE id = $1 AND status = 'queued'`, [job.payload.operation_id]);
|
||||
await tx.query(`UPDATE atlas.collection_asset_transfers SET status = 'cancelled', updated_at = now(), completed_at = now() WHERE collection_item_id = ANY($1::uuid[]) AND status IN ('queued', 'running')`, [job.payload.collection_item_ids]);
|
||||
await tx.query(`UPDATE atlas.operations SET status = 'succeeded', completed_at = now(), result = jsonb_build_object('cancelled_transfer_count', 0) WHERE id = $1 AND status IN ('queued', 'running')`, [job.payload.operation_id]);
|
||||
});
|
||||
}
|
||||
|
||||
worker.on('failed', (job, error) => {
|
||||
if (!job || job.attemptsMade < (job.opts.attempts ?? 1)) return;
|
||||
void markUnavailable(database, job.data, error);
|
||||
if (!job || job.attemptsMade < (job.opts.attempts ?? 1) || job.name !== 'store_credential_verification.requested') return;
|
||||
void markUnavailable(database, job.data as StoreVerificationJob, error);
|
||||
});
|
||||
|
||||
async function verifyStoreCredentials(database: Database, job: OutboxJob) {
|
||||
async function verifyStoreCredentials(database: Database, job: StoreVerificationJob) {
|
||||
const source = await database.workspaceTransaction(
|
||||
job.workspaceId,
|
||||
async (tx) => {
|
||||
@@ -98,7 +109,7 @@ async function verifyStoreCredentials(database: Database, job: OutboxJob) {
|
||||
}
|
||||
}
|
||||
|
||||
async function cancelStaleOperation(database: Database, job: OutboxJob) {
|
||||
async function cancelStaleOperation(database: Database, job: StoreVerificationJob) {
|
||||
await database.workspaceTransaction(job.workspaceId, (tx) =>
|
||||
tx.query(
|
||||
`UPDATE atlas.operations SET status = 'cancelled', completed_at = now(),
|
||||
@@ -111,7 +122,7 @@ async function cancelStaleOperation(database: Database, job: OutboxJob) {
|
||||
|
||||
async function completeVerification(
|
||||
database: Database,
|
||||
job: OutboxJob,
|
||||
job: StoreVerificationJob,
|
||||
valid: boolean,
|
||||
rejectedStatus?: 401 | 403,
|
||||
) {
|
||||
@@ -175,7 +186,7 @@ async function completeVerification(
|
||||
|
||||
async function markRequestRejected(
|
||||
database: Database,
|
||||
job: OutboxJob,
|
||||
job: StoreVerificationJob,
|
||||
status: number,
|
||||
) {
|
||||
await database.workspaceTransaction(job.workspaceId, async (tx) => {
|
||||
@@ -205,7 +216,7 @@ async function markRequestRejected(
|
||||
|
||||
async function markUnavailable(
|
||||
database: Database,
|
||||
job: OutboxJob,
|
||||
job: StoreVerificationJob,
|
||||
_error: Error,
|
||||
) {
|
||||
await database.workspaceTransaction(job.workspaceId, async (tx) => {
|
||||
|
||||
Reference in New Issue
Block a user