UNPKG

@strapi/data-transfer

Version:

Data transfer capabilities for Strapi

1 lines • 25 kB
{"version":3,"file":"pull.mjs","sources":["../../../../src/strapi/remote/handlers/pull.ts"],"sourcesContent":["import { Readable } from 'stream';\nimport { randomUUID, createHash } from 'crypto';\nimport type { Core } from '@strapi/types';\n\nimport { Handler } from './abstract';\nimport { handlerControllerFactory, isDataTransferMessage } from './utils';\nimport {\n createTransferAssetStreamChunk,\n transferAssetStreamChunkByteLength,\n} from '../../../utils/transfer-asset-chunk';\nimport {\n createLocalStrapiSourceProvider,\n estimateAssetTotals,\n ILocalStrapiSourceProvider,\n} from '../../providers';\nimport { ProviderTransferError } from '../../../errors/providers';\nimport type { IAsset, StageTotalsEstimate, TransferStage, Protocol } from '../../../../types';\nimport { Client } from '../../../../types/remote/protocol';\n\nconst TRANSFER_KIND = 'pull';\nconst VALID_TRANSFER_ACTIONS = ['bootstrap', 'close', 'getMetadata', 'getSchemas'] as const;\n\ntype PullTransferAction = (typeof VALID_TRANSFER_ACTIONS)[number];\n\nexport interface PullHandler extends Handler {\n provider?: ILocalStrapiSourceProvider;\n\n streams?: { [stage in TransferStage]?: Readable };\n checksumsEnabled?: boolean;\n\n assertValidTransferAction(action: string): asserts action is PullTransferAction;\n\n onTransferMessage(msg: Protocol.Client.TransferMessage): Promise<unknown> | unknown;\n onTransferAction(msg: Protocol.Client.Action): Promise<unknown> | unknown;\n onTransferStep(msg: Protocol.Client.TransferPullMessage): Promise<unknown> | unknown;\n\n createReadableStreamForStep(step: TransferStage): Promise<void>;\n\n flush(stage: TransferStage, id: string): Promise<void> | void;\n}\n\nexport const createPullController = handlerControllerFactory<Partial<PullHandler>>((proto) => ({\n isTransferStarted(this: PullHandler) {\n return proto.isTransferStarted.call(this) && this.provider !== undefined;\n },\n\n verifyAuth(this: PullHandler) {\n return proto.verifyAuth.call(this, TRANSFER_KIND);\n },\n\n cleanup(this: PullHandler) {\n proto.cleanup.call(this);\n\n this.streams = {};\n this.checksumsEnabled = false;\n\n delete this.provider;\n },\n\n onInfo(message) {\n this.diagnostics?.report({\n details: {\n message,\n origin: 'pull-handler',\n createdAt: new Date(),\n },\n kind: 'info',\n });\n },\n onWarning(message) {\n this.diagnostics?.report({\n details: {\n message,\n createdAt: new Date(),\n origin: 'pull-handler',\n },\n kind: 'warning',\n });\n },\n\n onError(error) {\n this.diagnostics?.report({\n details: {\n message: error.message,\n error,\n createdAt: new Date(),\n name: error.name,\n severity: 'fatal',\n },\n kind: 'error',\n });\n },\n\n assertValidTransferAction(this: PullHandler, action) {\n // Abstract the constant to string[] to allow looser check on the given action\n const validActions = VALID_TRANSFER_ACTIONS as unknown as string[];\n\n if (validActions.includes(action)) {\n return;\n }\n\n throw new ProviderTransferError(`Invalid action provided: \"${action}\"`, {\n action,\n validActions: Object.keys(VALID_TRANSFER_ACTIONS),\n });\n },\n\n async onMessage(this: PullHandler, raw) {\n const msg = JSON.parse(raw.toString());\n\n if (!isDataTransferMessage(msg)) {\n return;\n }\n\n if (!msg.uuid) {\n await this.respond(undefined, new Error('Missing uuid in message'));\n }\n\n if (proto.hasUUID(msg.uuid)) {\n const previousResponse = proto.response;\n if (previousResponse?.uuid === msg.uuid) {\n await this.respond(previousResponse?.uuid, previousResponse.e, previousResponse.data);\n }\n return;\n }\n\n const { uuid, type } = msg;\n proto.addUUID(uuid);\n // Regular command message (init, end, status)\n if (type === 'command') {\n const { command } = msg;\n this.onInfo(`received command:${command} uuid:${uuid}`);\n await this.executeAndRespond(uuid, () => {\n this.assertValidTransferCommand(command);\n\n // The status command don't have params\n if (command === 'status') {\n return this.status();\n }\n\n return this[command](msg.params);\n });\n }\n\n // Transfer message (the transfer must be init first)\n else if (type === 'transfer') {\n this.onInfo(`received transfer action:${msg.action} step:${msg.kind} uuid:${uuid}`);\n await this.executeAndRespond(uuid, async () => {\n await this.verifyAuth();\n\n this.assertValidTransfer();\n\n return this.onTransferMessage(msg);\n });\n }\n\n // Invalid messages\n else {\n await this.respond(uuid, new Error('Bad Request'));\n }\n },\n\n async onTransferMessage(this: PullHandler, msg) {\n const { kind } = msg;\n\n if (kind === 'action') {\n return this.onTransferAction(msg);\n }\n\n if (kind === 'step') {\n return this.onTransferStep(msg as Protocol.Client.TransferPullMessage);\n }\n },\n\n async onTransferAction(this: PullHandler, msg) {\n const { action } = msg;\n\n this.assertValidTransferAction(action);\n\n if (action === 'bootstrap') {\n return this.provider?.[action](this.diagnostics);\n }\n return this.provider?.[action]();\n },\n\n async flush(this: PullHandler, stage: Client.TransferPullStep, id) {\n type Stage = typeof stage;\n const batchSize = 1024 * 1024;\n let batch = [] as Client.GetTransferPullStreamData<Stage>;\n const stream = this.streams?.[stage];\n\n const batchLength = () => Buffer.byteLength(JSON.stringify(batch));\n\n const maybeConfirm = async (data: any) => {\n try {\n await this.confirm(data);\n } catch (error) {\n // Handle the error, log it, or take other appropriate actions\n\n strapi?.log.error(\n `[Data transfer] Message confirmation failed: ${(error as Error)?.message}`\n );\n this.onError(error as Error);\n }\n };\n\n const sendBatch = async () => {\n await this.confirm({\n type: 'transfer',\n data: batch,\n ended: false,\n error: null,\n id,\n });\n batch = [];\n };\n\n try {\n if (!stream) {\n throw new ProviderTransferError(`No available stream found for ${stage}`);\n }\n\n for await (const chunk of stream) {\n if (stage !== 'assets') {\n batch.push(chunk);\n if (batchLength() >= batchSize) {\n await sendBatch();\n }\n } else {\n await this.confirm({\n type: 'transfer',\n data: [chunk],\n ended: false,\n error: null,\n id,\n });\n }\n }\n\n if (batch.length > 0 && stage !== 'assets') {\n await sendBatch();\n }\n await this.confirm({ type: 'transfer', data: null, ended: true, error: null, id });\n } catch (e) {\n // TODO: if this confirm fails, can we abort the whole transfer?\n await maybeConfirm({ type: 'transfer', data: null, ended: true, error: e, id });\n }\n },\n\n async onTransferStep(this: PullHandler, msg) {\n const { step, action } = msg;\n\n if (action === 'start') {\n if (this.streams?.[step] instanceof Readable) {\n throw new Error('Stream already created, something went wrong');\n }\n\n const flushUUID = randomUUID();\n\n let totals: StageTotalsEstimate | undefined;\n if (step === 'assets') {\n totals = await estimateAssetTotals(strapi as Core.Strapi);\n }\n await this.createReadableStreamForStep(step);\n Promise.resolve(this.flush(step, flushUUID)).catch((err: unknown) => {\n this.onError(err instanceof Error ? err : new Error(String(err)));\n });\n\n return {\n ok: true,\n id: flushUUID,\n ...(totals !== undefined ? { totals } : {}),\n };\n }\n\n if (action === 'end') {\n const stream = this.streams?.[step];\n\n if (stream?.readableEnded === false) {\n await new Promise((resolve) => {\n stream?.on('close', resolve).destroy();\n });\n }\n\n delete this.streams?.[step];\n\n return { ok: true };\n }\n },\n\n async createReadableStreamForStep(this: PullHandler, step: Exclude<TransferStage, 'schemas'>) {\n const mapper = {\n entities: () => this.provider?.createEntitiesReadStream(),\n links: () => this.provider?.createLinksReadStream(),\n configuration: () => this.provider?.createConfigurationReadStream(),\n assets: () => {\n const assets = this.provider?.createAssetsReadStream();\n let batch: Protocol.Client.TransferAssetFlow[] = [];\n const checksumsEnabled = this.checksumsEnabled === true;\n\n const batchLength = () => {\n return batch.reduce((acc, chunk) => acc + transferAssetStreamChunkByteLength(chunk), 0);\n };\n\n const BATCH_MAX_SIZE = 1024 * 1024; // 1MB\n\n if (!assets) {\n throw new Error('Assets read stream could not be created');\n }\n /**\n * Generates batches of 1MB of data from the assets stream to avoid\n * sending too many small chunks\n *\n * @param stream Assets stream from the local source provider\n */\n async function* generator(stream: Readable) {\n let hasStarted = false;\n let assetID = '';\n let assetChecksum: ReturnType<typeof createHash> | undefined;\n\n for await (const chunk of stream) {\n const { stream: assetStream, ...assetData } = chunk as IAsset;\n if (!hasStarted) {\n assetID = randomUUID();\n assetChecksum = checksumsEnabled ? createHash('sha256') : undefined;\n // Start the transfer of a new asset\n batch.push({ action: 'start', assetID, data: assetData });\n hasStarted = true;\n }\n\n for await (const assetChunk of assetStream) {\n assetChecksum?.update(assetChunk);\n batch.push(createTransferAssetStreamChunk(assetID, assetChunk));\n\n // if the batch size is bigger than BATCH_MAX_SIZE stream the batch\n if (batchLength() >= BATCH_MAX_SIZE) {\n yield batch;\n batch = [];\n }\n }\n\n // All the asset data has been streamed and gets ready for the next one\n hasStarted = false;\n batch.push({\n action: 'end',\n assetID,\n ...(assetChecksum\n ? { checksum: { algorithm: 'sha256' as const, value: assetChecksum.digest('hex') } }\n : {}),\n });\n yield batch;\n batch = [];\n }\n }\n\n return Readable.from(generator(assets));\n },\n };\n\n if (!(step in mapper)) {\n throw new Error('Invalid transfer step, impossible to create a stream');\n }\n\n if (!this.streams) {\n throw new Error('Invalid transfer state');\n }\n\n this.streams[step] = await mapper[step]();\n },\n\n // Commands\n async init(this: PullHandler, params?: Protocol.Client.GetCommandParams<'init'>) {\n if (this.transferID || this.provider) {\n throw new Error('Transfer already in progress');\n }\n await this.verifyAuth();\n\n this.transferID = randomUUID();\n this.startedAt = Date.now();\n this.checksumsEnabled = params?.checksums === true;\n\n this.streams = {};\n\n this.provider = createLocalStrapiSourceProvider({\n autoDestroy: false,\n getStrapi: () => strapi as Core.Strapi,\n });\n\n return { transferID: this.transferID, checksums: true };\n },\n\n async end(\n this: PullHandler,\n params: Protocol.Client.GetCommandParams<'end'>\n ): Promise<Protocol.Server.Payload<Protocol.Server.EndMessage>> {\n await this.verifyAuth();\n\n if (this.transferID !== params?.transferID) {\n throw new ProviderTransferError('Bad transfer ID provided');\n }\n\n this.cleanup();\n\n return { ok: true };\n },\n\n async status(this: PullHandler) {\n const isStarted = this.isTransferStarted();\n\n if (!isStarted) {\n const startedAt = this.startedAt as number;\n return {\n active: true,\n kind: TRANSFER_KIND,\n startedAt,\n elapsed: Date.now() - startedAt,\n };\n }\n return { active: false, kind: null, elapsed: null, startedAt: null };\n },\n}));\n"],"names":["TRANSFER_KIND","VALID_TRANSFER_ACTIONS","createPullController","handlerControllerFactory","proto","isTransferStarted","call","provider","undefined","verifyAuth","cleanup","streams","checksumsEnabled","onInfo","message","diagnostics","report","details","origin","createdAt","Date","kind","onWarning","onError","error","name","severity","assertValidTransferAction","action","validActions","includes","ProviderTransferError","Object","keys","onMessage","raw","msg","JSON","parse","toString","isDataTransferMessage","uuid","respond","Error","hasUUID","previousResponse","response","e","data","type","addUUID","command","executeAndRespond","assertValidTransferCommand","status","params","assertValidTransfer","onTransferMessage","onTransferAction","onTransferStep","flush","stage","id","batchSize","batch","stream","batchLength","Buffer","byteLength","stringify","maybeConfirm","confirm","strapi","log","sendBatch","ended","chunk","push","length","step","Readable","flushUUID","randomUUID","totals","estimateAssetTotals","createReadableStreamForStep","Promise","resolve","catch","err","String","ok","readableEnded","on","destroy","mapper","entities","createEntitiesReadStream","links","createLinksReadStream","configuration","createConfigurationReadStream","assets","createAssetsReadStream","reduce","acc","transferAssetStreamChunkByteLength","BATCH_MAX_SIZE","generator","hasStarted","assetID","assetChecksum","assetStream","assetData","createHash","assetChunk","update","createTransferAssetStreamChunk","checksum","algorithm","value","digest","from","init","transferID","startedAt","now","checksums","createLocalStrapiSourceProvider","autoDestroy","getStrapi","end","isStarted","active","elapsed"],"mappings":"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"}