@flowlab/all
Version:
A cool library focusing on handling various flows
44 lines (36 loc) • 1.96 kB
text/typescript
// src/transformers/mappingTransformer.ts
import { ITransformer, PipelineContext } from '../core/interfaces';
import { get, set } from 'lodash'; // Use lodash for safe nested access, install: npm i lodash @types/lodash
// Define rule structure (can be more sophisticated)
export interface MappingRule {
sourcePath: string; // Dot notation path in input object (e.g., 'user.profile.firstName')
targetPath: string; // Dot notation path in output object
// Optional: transformation function, default value, type casting etc.
transform?: (value: any, input: any, context: PipelineContext) => any;
defaultValue?: any;
}
export class MappingTransformer<TInput, TOutput> implements ITransformer<TInput, TOutput> {
private rules: MappingRule[];
constructor(rules: MappingRule[]) {
this.rules = rules;
}
async transform(data: TInput, context: PipelineContext): Promise<TOutput> {
const output: Partial<TOutput> = {}; // Start with an empty object
for (const rule of this.rules) {
let value = get(data, rule.sourcePath, rule.defaultValue); // Get value using lodash
if (rule.transform) {
try {
value = await Promise.resolve(rule.transform(value, data, context)); // Allow async transforms
} catch (err: any) {
context.logger.error({ err, rule, input: data }, `Error during custom mapping transformation for ${rule.sourcePath}`);
// Decide how to handle: skip field, throw, set default?
value = rule.defaultValue; // Default on error?
}
}
if (value !== undefined) { // Only set if value is not undefined (allows defaults)
set(output as object, rule.targetPath, value); // Set value using lodash
}
}
return output as TOutput; // Assume the output matches TOutput structure
}
}