From dbadfe50e6391f0a65648d9025ae6f1e9026db02 Mon Sep 17 00:00:00 2001 From: Felix Kaspar Date: Sat, 18 May 2024 22:49:06 +0200 Subject: [PATCH] updateMetadata --- .../src/components/fields/GenericField.tsx | 25 ++- .../src/functions/splitPdfByIndex.ts | 4 +- .../src/functions/updateMetadata.ts | 150 ++++++++++++------ 3 files changed, 126 insertions(+), 53 deletions(-) diff --git a/client-tauri/src/components/fields/GenericField.tsx b/client-tauri/src/components/fields/GenericField.tsx index 638346950..76231e261 100644 --- a/client-tauri/src/components/fields/GenericField.tsx +++ b/client-tauri/src/components/fields/GenericField.tsx @@ -58,8 +58,13 @@ export function GenericField({ fieldName, joiDefinition }: GenericFieldProps) { ); } else { - // TODO: Implement unrestrained text input - return (
string, unrestrained text input is not implemented
) + return ( + + + +
+
+ ) } break; case "comma_array": @@ -114,6 +119,22 @@ export function GenericField({ fieldName, joiDefinition }: GenericFieldProps) {
); + case "boolean": + return ( + + + +
+
+ ); + case "date": + return ( + + + +
+
+ ); default: console.log(joiDefinition); return (
GenericField.tsx:
"{fieldName}": requested type "{joiDefinition.type}" not found. Check console for further info.
) diff --git a/shared-operations/src/functions/splitPdfByIndex.ts b/shared-operations/src/functions/splitPdfByIndex.ts index 3874d0bd8..848e65752 100644 --- a/shared-operations/src/functions/splitPdfByIndex.ts +++ b/shared-operations/src/functions/splitPdfByIndex.ts @@ -1,4 +1,4 @@ -import { PdfFile, RepresentationType } from "../wrappers/PdfFile"; +import { PdfFile } from "../wrappers/PdfFile"; import { Operator, Progress, oneToN } from "."; import Joi from "@stirling-tools/joi"; @@ -21,7 +21,7 @@ export class SplitPdfByIndex extends Operator { protected static valueSchema = Joi.object({ pageIndexes: CommaArrayJoiExt.comma_array().items(Joi.number().integer()).required() .label(i18next.t("values.pageIndexes.friendlyName", { ns: "splitPdfByIndex" })).description(i18next.t("values.pageIndexes.description", { ns: "splitPdfByIndex" })) - .example("1").example("1, 2, 3, 4").example("4, 2, 4, 3").required() + .example("1").example("1, 2, 3, 4").example("4, 2, 4, 3") }); protected static outputSchema = JoiPDFFileSchema.label(i18next.t("outputs.pdffile.name")).description(i18next.t("outputs.pdffile.description")); diff --git a/shared-operations/src/functions/updateMetadata.ts b/shared-operations/src/functions/updateMetadata.ts index 39aa52923..fb98f6d3d 100644 --- a/shared-operations/src/functions/updateMetadata.ts +++ b/shared-operations/src/functions/updateMetadata.ts @@ -1,54 +1,106 @@ - import { PdfFile } from "../wrappers/PdfFile"; +import { Operator, Progress, oneToOne } from "."; -export interface UpdateMetadataParams { - file: PdfFile, - deleteAll?: boolean, // Delete all metadata if set to true - author?: string, // The author of the document - creationDate?: Date, // The creation date of the document (format: yyyy/MM/dd HH:mm:ss) - creator?: string, // The creator of the document - keywords?: string, // The keywords for the document - modificationDate?: Date, // The modification date of the document (format: yyyy/MM/dd HH:mm:ss) - producer?: string, // The producer of the document - subject?: string, // The subject of the document - title?: string, // The title of the document - //trapped?: string, // The trapped status of the document - //allRequestParams?: {[key: string]: [key: string]}, // Map list of key and value of custom parameters. Note these must start with customKey and customValue if they are non-standard -} +import Joi from "@stirling-tools/joi"; -export async function updateMetadata(params: UpdateMetadataParams): Promise { - const pdfDoc = await params.file.pdfLibDocument; +import { JoiPDFFileSchema } from "../wrappers/PdfFileJoi"; - if (params.deleteAll) { - pdfDoc.setAuthor(""); - pdfDoc.setCreationDate(new Date(0)); - pdfDoc.setCreator(""); - pdfDoc.setKeywords([]); - pdfDoc.setModificationDate(new Date(0)); - pdfDoc.setProducer(""); - pdfDoc.setSubject(""); - pdfDoc.setTitle(""); +import i18next from "i18next"; + +export class UpdateMetadata extends Operator { + static type = "updateMetadata"; + + /** + * Validation & Localisation + */ + + protected static inputSchema = JoiPDFFileSchema.label(i18next.t("inputs.pdffile.name")).description(i18next.t("inputs.pdffile.description")); + protected static valueSchema = Joi.object({ + deleteAll: Joi.boolean().invalid(false) + .label(i18next.t("values.deleteAll.friendlyName", { ns: "updateMetadata" })).description(i18next.t("values.deleteAll.description", { ns: "updateMetadata" })) + .example("true").example("false"), + author: Joi.string().optional().allow('') + .label(i18next.t("values.author.friendlyName", { ns: "updateMetadata" })).description(i18next.t("values.author.description", { ns: "updateMetadata" })) + .example("John Doe").example("Anthony Stirling"), // The author of the document + creationDate: Joi.date().allow("").allow(null) + .label(i18next.t("values.creationDate.friendlyName", { ns: "updateMetadata" })).description(i18next.t("values.creationDate.description", { ns: "updateMetadata" })) + .example("YYYY-MM-DD").example("2023-01-27"), // The creation date of the document (format: yyyy/MM/dd HH:mm:ss) + creator: Joi.string().optional().allow('') + .label(i18next.t("values.creator.friendlyName", { ns: "updateMetadata" })).description(i18next.t("values.creator.description", { ns: "updateMetadata" })) + .example("John Doe").example("Anthony Stirling"), // The creator of the document + keywords: Joi.string().optional().allow('') + .label(i18next.t("values.keywords.friendlyName", { ns: "updateMetadata" })).description(i18next.t("values.keywords.description", { ns: "updateMetadata" })) + .example("General").example("finances, leisure").example("finances leisure"), // The keywords for the document + modificationDate: Joi.date().allow("").allow(null) + .label(i18next.t("values.modificationDate.friendlyName", { ns: "updateMetadata" })).description(i18next.t("values.modificationDate.description", { ns: "updateMetadata" })) + .example("YYYY-MM-DD").example("2023-01-27"), // The modification date of the document (format: yyyy/MM/dd HH:mm:ss) + producer: Joi.string().optional().allow('') + .label(i18next.t("values.producer.friendlyName", { ns: "updateMetadata" })).description(i18next.t("values.producer.description", { ns: "updateMetadata" })) + .example("John Doe").example("Anthony Stirling"), // The producer of the document + subject: Joi.string().optional().allow('') + .label(i18next.t("values.subject.friendlyName", { ns: "updateMetadata" })).description(i18next.t("values.subject.description", { ns: "updateMetadata" })) + .example("Subject").example("This is an example Subject."), // The subject of the document + title: Joi.string().optional().allow('') + .label(i18next.t("values.title.friendlyName", { ns: "updateMetadata" })).description(i18next.t("values.title.description", { ns: "updateMetadata" })) + .example("Title").example("This is an example title."), // The title of the document + + // TODO: trapped?: string, // The trapped status of the document + + // TODO: allRequestParams?: {[key: string]: [key: string]}, // Map list of key and value of custom parameters. Note these must start with customKey and customValue if they are non-standard + }); + protected static outputSchema = JoiPDFFileSchema.label(i18next.t("outputs.pdffile.name")).description(i18next.t("outputs.pdffile.description")); + + static schema = Joi.object({ + input: UpdateMetadata.inputSchema, + values: UpdateMetadata.valueSchema.required(), + output: UpdateMetadata.outputSchema + }).label(i18next.t("friendlyName", { ns: "updateMetadata" })).description(i18next.t("description", { ns: "updateMetadata" })); + + + /** + * Logic + */ + + /** PDF extraction, specify pages from one pdf and output them to a new pdf */ + async run(input: PdfFile[], progressCallback: (state: Progress) => void): Promise { + return oneToOne(input, async (input, index, max) => { + + const pdfDoc = await input.pdfLibDocument; + + if (this.actionValues.deleteAll) { + pdfDoc.setAuthor(""); + pdfDoc.setCreationDate(new Date(0)); + pdfDoc.setCreator(""); + pdfDoc.setKeywords([]); + pdfDoc.setModificationDate(new Date(0)); + pdfDoc.setProducer(""); + pdfDoc.setSubject(""); + pdfDoc.setTitle(""); + } + + if(this.actionValues.author) + pdfDoc.setAuthor(this.actionValues.author); + if(this.actionValues.creationDate) + pdfDoc.setCreationDate(this.actionValues.creationDate); + if(this.actionValues.creator) + pdfDoc.setCreator(this.actionValues.creator); + if(this.actionValues.keywords) + pdfDoc.setKeywords(this.actionValues.keywords.split(",")); + if(this.actionValues.modificationDate) + pdfDoc.setModificationDate(this.actionValues.modificationDate); + if(this.actionValues.producer) + pdfDoc.setProducer(this.actionValues.producer); + if(this.actionValues.subject) + pdfDoc.setSubject(this.actionValues.subject); + if(this.actionValues.title) + pdfDoc.setTitle(this.actionValues.title); + + // TODO: add trapped and custom metadata. May need another library + + progressCallback({ curFileProgress: 1, operationProgress: index/max }); + + input.filename += "_updatedMetadata"; + return input; + }); } - - if(params.author) - pdfDoc.setAuthor(params.author); - if(params.creationDate) - pdfDoc.setCreationDate(params.creationDate); - if(params.creator) - pdfDoc.setCreator(params.creator); - if(params.keywords) - pdfDoc.setKeywords(params.keywords.split(",")); - if(params.modificationDate) - pdfDoc.setModificationDate(params.modificationDate); - if(params.producer) - pdfDoc.setProducer(params.producer); - if(params.subject) - pdfDoc.setSubject(params.subject); - if(params.title) - pdfDoc.setTitle(params.title); - - // TODO add trapped and custom metadata. May need another library - - params.file.filename += "_updatedMetadata"; - return params.file; -} +} \ No newline at end of file