All files / json-patch-ot/transforms xAdd.ts

91.3% Statements 21/23
85.71% Branches 12/14
100% Functions 1/1
100% Lines 18/18

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33  1x   1x 1x   1x 39x 39x   39x 39x 39x   39x   36x 21x 21x 21x 15x       15x   15x       21x    
import type {OpAdd, Op} from '../../json-patch/op';
import {isRoot, isValidIndex, isChild, formatJsonPointer} from '@jsonjoy.com/json-pointer';
import type {Operation} from '../../json-patch/types';
import {bumpArrayPath} from './util';
import {operationToOp} from '../../json-patch/codec/json';
 
export const xAdd = (add: OpAdd, op: Op): null | Op => {
  Iif (isRoot(add.path)) return null;
  Iif (isRoot(op.path)) return op;
 
  const lastIndex = add.path.length - 1;
  const lastStep = add.path[lastIndex];
  const isLastStepNumberLike = isValidIndex(lastStep);
 
  if (isChild(add.path, op.path) && !isLastStepNumberLike) return null;
 
  if (isLastStepNumberLike) {
    const newPath = bumpArrayPath(add.path, op.path);
    const newFrom = op.from ? bumpArrayPath(add.path, op.from) : undefined;
    if (newPath || newFrom) {
      const operation: Operation = {
        ...op.toJson(),
        path: newPath ? formatJsonPointer(newPath) : op.path,
      };
      if (newFrom) (operation as any).from = formatJsonPointer(newFrom);
      // TODO: The second argument should not be {}
      return operationToOp(operation, {});
    }
  }
 
  return op;
};