Skip to content

Latest commit

 

History

History
170 lines (114 loc) · 6.33 KB

File metadata and controls

170 lines (114 loc) · 6.33 KB

CLAUDE.md

This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.

Project Overview

Mapstronaut is a TypeScript-based JavaScript object mapper library designed for both Node.js and browsers. The project uses jsonpath-plus as its core dependency for object path traversal and mapping operations.

Development Commands

  • Build: npm run build - Compiles TypeScript to JavaScript in the dist/ directory
  • Test: npm run test - Runs Mocha tests from test/*/.ts
  • Format: npm run format - Formats source code using Prettier, YOU MUST use this command after you finish all your developments to keep a clean code environment
  • Coverage: npm run coverage - Get coverage for the project - should always be above 95%
  • Benchmark: npm run benchmark - Run benchmark

Architecture

Project Structure

  • src/ - TypeScript source code
  • src/test/ - Test files using Mocha testing framework
  • src/types/ - TypeScript type definitions
  • dist/ - Compiled JavaScript output (generated by build process)
  • docs/ - Documentation directory

Key Configuration

  • TypeScript: Strict configuration with ES2020 target and NodeNext modules
  • Testing: Mocha framework with TypeScript support
  • Formatting: Prettier with default configuration
  • Module System: ES modules with NodeNext resolution

Dependencies

  • Runtime: jsonpath-plus for JSON path operations
  • Development: TypeScript, Mocha, Prettier, and corresponding type definitions

Implementation Notes

The library is configured as an ES module with strict TypeScript settings including noUncheckedIndexedAccess and exactOptionalPropertyTypes.

Your workflow

When adding a new feature or updating an existing one, use the following workflow:

  • Think hard about the feature and how to implement it, and write specifications
  • Implement the feature, using all the documentation and specifications available to you, running tests to make sure you do not break anything
  • Add comprehensive tests. We should have a 95+% test coverage
  • Add documentation. Each main feature should have its own .md file in ./docs
  • Run code formatting to clean up

Ubiquitous langage

  • mapstronaut : this whole library
  • source object : the full source object we will map
  • target : the target object
  • source : the jsonpath entry in the rule, accessing a source object property
  • mapper : the main Mapper class that maps from one object to another
  • outpath: an internal library that write object values with dot notation
  • automapper : or automapping, is writing recursively from one object to another when properties match. The same properties MUST be present in both source and target objects.

Features

  • automapping: it should be possible to map matching properties in the source object and target directly (see Automapper, Mapper should use Automapper internally)
  • sources should be defined using JsonPath strings ($. can be removed for convenience)
  • target properties should be specified using OutPath internal library
  • each rule can have a filter, which is a function (possibly async) that return a boolean indicating if the mapping for this rule should be done. This function has the data for this rule (which is the data matching the jsonpath for this source object) as the first parameter, the full source in second, and the target in its current state as third
  • it should be possible to map to object and classes
  • it should be possible to map from any type (string, Array, object, number, etc)
  • it should be possible to add an optional "target" argument, that Mapstronaut will update instead of creating an empty object
  • an optional transform function (possibly async) can be given for each rule, for "manual" mapping. This function has the data for this rule (which is the data matching the jsonpath for this source object) as the first parameter, the full source in second, and the target in its current state as third.
  • an optional defaultValue can be given for each rule, to use when the data is null or undefined
  • an optional constant can be given for each rule. When constant is defined, the source is not required, otherwise it is.
  • an optional failOn function (possibly async) can be given for each rule, if it returns true a descriptive error will be thrown and the mapping stopped

API

Automapper

Automapper is a class that automatically maps fields that exists in both source and target. It takes the following options :

type AutomapperConfiguration = {
  checkType: boolean; // default false, check if source/target property type matches
};

It should work with object and classes.

Mapper

Mapper is the main mapping class. It takes a structure, a source, an optional target (creates an empty object when not provided) and options.

Examples:

const mapper = new Mapper<SourceClass, TargetClass>(structure, options);
// Mapper is the main non-async mapper class

const mappedObject = mapper.map(source);
const mappedObjectMerge = mapper.map(source, target);

const options = mapper.getOptions(); // also setOptions
const structure = mapper.getStructure(); // also setStructure

// for each possible option, add getsetters
mapper.automap = false; // etc
const mapper = new AsyncMapper<SourceClass, TargetClass>(structure, options);
// AsyncMapper is the async mapper class
// to use with async filters, failOn, or transform

const mappedObject = await mapper.map(source);

Options : see MapperOptions in src/types/mapper.ts

For practical reasons, there should also be a quick access function that directly returns the mapped object.

mapObject(structure, source, target?, options?);

OutPath

OutPath is using dot-prop library for target mapping

See: src/outpath.ts

Examples :

const obj: MyTarget = {};
const outpath = new OutPath<MyTarget>();

outpath.write(obj, "first.a", "demo");
console.log(obj.first.a): // demo

outpath.write(obj, "first.b.test", false);
console.log(obj.first.b.test); // false
console.log(obj.first.a): // demo

outpath.write(obj, "arr[0].name", "ex");
console.log(obj.arr); [{ name: "ex" }]

Structure

Define the mapping rules.

See : src/types/mapper.ts

Documentation

Examples are stored in ./docs/examples.md.

All examples and documentation should revolve around space themes.

Benchmark

A script that runs a benchmark can be found in ./benchmark.ts.