@natlibfi/marc-record-merge 6.0.0-beta.10 → 6.0.0-beta.11

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -11,7 +11,10 @@ Object.defineProperty(exports, "Reducers", {
11
11
  });
12
12
  exports.default = void 0;
13
13
  var _reducers = _interopRequireDefault(require("./reducers"));
14
+ var _debug = _interopRequireDefault(require("debug"));
14
15
  function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
16
+ const debug = (0, _debug.default)('@natlibfi/melinda-marc-record-merge:index');
17
+ const debugData = debug.extend('data');
15
18
  // export default ({base, source, reducers}) => reducers.reduce((base, reducer) => reducer(base, source), base);
16
19
  // NV: Modified the reducer loop so, that not only base, but also is carried back.
17
20
  // However, we try to be backward-compatible: normally after the reducers, only base is returned.
@@ -23,30 +26,42 @@ var _default = ({
23
26
  const combo = {
24
27
  base,
25
28
  source
26
- }; // eslint-disable-line functional/no-let
27
-
28
- reducers.reduce((combo, reducer) => {
29
- combo = singleRound(reducer, combo.base, combo.source); // eslint-disable-line no-param-reassign
30
-
31
- return combo;
29
+ };
30
+ const resultCombo = reducers.reduce((combo, reducer) => {
31
+ const returnCombo = singleRound(reducer, combo.base, combo.source);
32
+ //debugData(`returnCombo after current reducer: ${JSON.stringify(returnCombo)}`);
33
+ return returnCombo;
32
34
  }, combo);
35
+ debugData(`ResultCombo after reducers: ${JSON.stringify(resultCombo)}`);
33
36
 
34
37
  // Hack to make my melinda-marc-record-merge-reducers single tests that expect both
35
38
  // base and source to return them both:
36
- if (reducers.length === 1 && combo.base && combo.source) {
37
- return combo;
39
+ if (reducers.length === 1 && resultCombo.base && resultCombo.source) {
40
+ debug('Single reducer, returning resultCombo');
41
+ debugData(JSON.stringify(resultCombo));
42
+ return resultCombo;
38
43
  }
39
44
  // All other tests return just base... Backward (compability) it is!
40
- return combo.base;
45
+ debug('Multiple reducers, returning just base');
46
+ debugData(JSON.stringify(resultCombo.base));
47
+ return resultCombo.base;
41
48
  function singleRound(reducer, base, source) {
42
- const combo = reducer(base, source);
43
- if (combo.base !== undefined && combo.source !== undefined) {
44
- //console.info('NEW STYLE REDUCER RESULT v2'); // eslint-disable-line no-console
49
+ //debug(`SINGLE ROUND INPUT (base, source)`);
50
+ //debugData(base);
51
+ //debugData(base);
52
+ const reducerResult = reducer(base, source);
53
+ //debug(`reducerResult:`);
54
+ //debugData(reducerResult);
55
+ if (reducerResult.base !== undefined && reducerResult.source !== undefined) {
56
+ debug('NEW STYLE REDUCER RESULT v2');
57
+ const combo = reducerResult;
58
+ //debugData(combo);
45
59
  return combo;
46
60
  }
47
- //console.info('OLD SCHOOL REDUCER RESULT v2'); // eslint-disable-line no-console
61
+ debug('OLD SCHOOL REDUCER RESULT v2');
62
+ //debugData({base: reducerResult, source});
48
63
  return {
49
- base: combo.base,
64
+ base: reducerResult,
50
65
  source
51
66
  };
52
67
  }
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","names":["base","source","reducers","combo","reduce","reducer","singleRound","length","undefined"],"sources":["../src/index.js"],"sourcesContent":["import Reducers from './reducers';\n\nexport {Reducers};\n// export default ({base, source, reducers}) => reducers.reduce((base, reducer) => reducer(base, source), base);\n\n// NV: Modified the reducer loop so, that not only base, but also is carried back.\n// However, we try to be backward-compatible: normally after the reducers, only base is returned.\nexport default ({base, source, reducers}) => {\n const combo = {base, source}; // eslint-disable-line functional/no-let\n\n reducers.reduce((combo, reducer) => {\n combo = singleRound(reducer, combo.base, combo.source); // eslint-disable-line no-param-reassign\n\n return combo;\n }, combo);\n\n // Hack to make my melinda-marc-record-merge-reducers single tests that expect both\n // base and source to return them both:\n if (reducers.length === 1 && combo.base && combo.source) {\n return combo;\n }\n // All other tests return just base... Backward (compability) it is!\n return combo.base;\n\n function singleRound(reducer, base, source) {\n const combo = reducer(base, source);\n if (combo.base !== undefined && combo.source !== undefined) {\n //console.info('NEW STYLE REDUCER RESULT v2'); // eslint-disable-line no-console\n return combo;\n }\n //console.info('OLD SCHOOL REDUCER RESULT v2'); // eslint-disable-line no-console\n return {base: combo.base, source};\n }\n};\n"],"mappings":";;;;;;;;;;;;AAAA;AAAkC;AAGlC;AAEA;AACA;AAAA,eACe,CAAC;EAACA,IAAI;EAAEC,MAAM;EAAEC;AAAQ,CAAC,KAAK;EAC3C,MAAMC,KAAK,GAAG;IAACH,IAAI;IAAEC;EAAM,CAAC,CAAC,CAAC;;EAE9BC,QAAQ,CAACE,MAAM,CAAC,CAACD,KAAK,EAAEE,OAAO,KAAK;IAClCF,KAAK,GAAGG,WAAW,CAACD,OAAO,EAAEF,KAAK,CAACH,IAAI,EAAEG,KAAK,CAACF,MAAM,CAAC,CAAC,CAAC;;IAExD,OAAOE,KAAK;EACd,CAAC,EAAEA,KAAK,CAAC;;EAET;EACA;EACA,IAAID,QAAQ,CAACK,MAAM,KAAK,CAAC,IAAIJ,KAAK,CAACH,IAAI,IAAIG,KAAK,CAACF,MAAM,EAAE;IACvD,OAAOE,KAAK;EACd;EACA;EACA,OAAOA,KAAK,CAACH,IAAI;EAEjB,SAASM,WAAW,CAACD,OAAO,EAAEL,IAAI,EAAEC,MAAM,EAAE;IAC1C,MAAME,KAAK,GAAGE,OAAO,CAACL,IAAI,EAAEC,MAAM,CAAC;IACnC,IAAIE,KAAK,CAACH,IAAI,KAAKQ,SAAS,IAAIL,KAAK,CAACF,MAAM,KAAKO,SAAS,EAAE;MAC1D;MACA,OAAOL,KAAK;IACd;IACA;IACA,OAAO;MAACH,IAAI,EAAEG,KAAK,CAACH,IAAI;MAAEC;IAAM,CAAC;EACnC;AACF,CAAC;AAAA"}
1
+ {"version":3,"file":"index.js","names":["debug","createDebugLogger","debugData","extend","base","source","reducers","combo","resultCombo","reduce","reducer","returnCombo","singleRound","JSON","stringify","length","reducerResult","undefined"],"sources":["../src/index.js"],"sourcesContent":["import Reducers from './reducers';\nimport createDebugLogger from 'debug';\n\nconst debug = createDebugLogger('@natlibfi/melinda-marc-record-merge:index');\nconst debugData = debug.extend('data');\n\nexport {Reducers};\n// export default ({base, source, reducers}) => reducers.reduce((base, reducer) => reducer(base, source), base);\n\n// NV: Modified the reducer loop so, that not only base, but also is carried back.\n// However, we try to be backward-compatible: normally after the reducers, only base is returned.\n\nexport default ({base, source, reducers}) => {\n\n const combo = {base, source};\n const resultCombo = reducers.reduce((combo, reducer) => {\n const returnCombo = singleRound(reducer, combo.base, combo.source);\n //debugData(`returnCombo after current reducer: ${JSON.stringify(returnCombo)}`);\n return returnCombo;\n }, combo);\n\n debugData(`ResultCombo after reducers: ${JSON.stringify(resultCombo)}`);\n\n // Hack to make my melinda-marc-record-merge-reducers single tests that expect both\n // base and source to return them both:\n if (reducers.length === 1 && resultCombo.base && resultCombo.source) {\n debug('Single reducer, returning resultCombo');\n debugData(JSON.stringify(resultCombo));\n\n return resultCombo;\n }\n // All other tests return just base... Backward (compability) it is!\n debug('Multiple reducers, returning just base');\n debugData(JSON.stringify(resultCombo.base));\n return resultCombo.base;\n\n function singleRound(reducer, base, source) {\n //debug(`SINGLE ROUND INPUT (base, source)`);\n //debugData(base);\n //debugData(base);\n const reducerResult = reducer(base, source);\n //debug(`reducerResult:`);\n //debugData(reducerResult);\n if (reducerResult.base !== undefined && reducerResult.source !== undefined) {\n debug('NEW STYLE REDUCER RESULT v2');\n const combo = reducerResult;\n //debugData(combo);\n return combo;\n }\n debug('OLD SCHOOL REDUCER RESULT v2');\n //debugData({base: reducerResult, source});\n return {base: reducerResult, source};\n }\n};\n"],"mappings":";;;;;;;;;;;;AAAA;AACA;AAAsC;AAEtC,MAAMA,KAAK,GAAG,IAAAC,cAAiB,EAAC,2CAA2C,CAAC;AAC5E,MAAMC,SAAS,GAAGF,KAAK,CAACG,MAAM,CAAC,MAAM,CAAC;AAGtC;AAEA;AACA;AAAA,eAEe,CAAC;EAACC,IAAI;EAAEC,MAAM;EAAEC;AAAQ,CAAC,KAAK;EAE3C,MAAMC,KAAK,GAAG;IAACH,IAAI;IAAEC;EAAM,CAAC;EAC5B,MAAMG,WAAW,GAAGF,QAAQ,CAACG,MAAM,CAAC,CAACF,KAAK,EAAEG,OAAO,KAAK;IACtD,MAAMC,WAAW,GAAGC,WAAW,CAACF,OAAO,EAAEH,KAAK,CAACH,IAAI,EAAEG,KAAK,CAACF,MAAM,CAAC;IAClE;IACA,OAAOM,WAAW;EACpB,CAAC,EAAEJ,KAAK,CAAC;EAETL,SAAS,CAAE,+BAA8BW,IAAI,CAACC,SAAS,CAACN,WAAW,CAAE,EAAC,CAAC;;EAEvE;EACA;EACA,IAAIF,QAAQ,CAACS,MAAM,KAAK,CAAC,IAAIP,WAAW,CAACJ,IAAI,IAAII,WAAW,CAACH,MAAM,EAAE;IACnEL,KAAK,CAAC,uCAAuC,CAAC;IAC9CE,SAAS,CAACW,IAAI,CAACC,SAAS,CAACN,WAAW,CAAC,CAAC;IAEtC,OAAOA,WAAW;EACpB;EACA;EACAR,KAAK,CAAC,wCAAwC,CAAC;EAC/CE,SAAS,CAACW,IAAI,CAACC,SAAS,CAACN,WAAW,CAACJ,IAAI,CAAC,CAAC;EAC3C,OAAOI,WAAW,CAACJ,IAAI;EAEvB,SAASQ,WAAW,CAACF,OAAO,EAAEN,IAAI,EAAEC,MAAM,EAAE;IAC1C;IACA;IACA;IACA,MAAMW,aAAa,GAAGN,OAAO,CAACN,IAAI,EAAEC,MAAM,CAAC;IAC3C;IACA;IACA,IAAIW,aAAa,CAACZ,IAAI,KAAKa,SAAS,IAAID,aAAa,CAACX,MAAM,KAAKY,SAAS,EAAE;MAC1EjB,KAAK,CAAC,6BAA6B,CAAC;MACpC,MAAMO,KAAK,GAAGS,aAAa;MAC3B;MACA,OAAOT,KAAK;IACd;IACAP,KAAK,CAAC,8BAA8B,CAAC;IACrC;IACA,OAAO;MAACI,IAAI,EAAEY,aAAa;MAAEX;IAAM,CAAC;EACtC;AACF,CAAC;AAAA"}
@@ -0,0 +1,59 @@
1
+ "use strict";
2
+
3
+ var _index = _interopRequireWildcard(require("./index"));
4
+ var _util = require("util");
5
+ var _debug = _interopRequireDefault(require("debug"));
6
+ var _chai = require("chai");
7
+ var _marcRecord = require("@natlibfi/marc-record");
8
+ var _fixura = require("@natlibfi/fixura");
9
+ var _fixugen = _interopRequireDefault(require("@natlibfi/fixugen"));
10
+ function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
11
+ function _getRequireWildcardCache(nodeInterop) { if (typeof WeakMap !== "function") return null; var cacheBabelInterop = new WeakMap(); var cacheNodeInterop = new WeakMap(); return (_getRequireWildcardCache = function (nodeInterop) { return nodeInterop ? cacheNodeInterop : cacheBabelInterop; })(nodeInterop); }
12
+ function _interopRequireWildcard(obj, nodeInterop) { if (!nodeInterop && obj && obj.__esModule) { return obj; } if (obj === null || typeof obj !== "object" && typeof obj !== "function") { return { default: obj }; } var cache = _getRequireWildcardCache(nodeInterop); if (cache && cache.has(obj)) { return cache.get(obj); } var newObj = {}; var hasPropertyDescriptor = Object.defineProperty && Object.getOwnPropertyDescriptor; for (var key in obj) { if (key !== "default" && Object.prototype.hasOwnProperty.call(obj, key)) { var desc = hasPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : null; if (desc && (desc.get || desc.set)) { Object.defineProperty(newObj, key, desc); } else { newObj[key] = obj[key]; } } } newObj.default = obj; if (cache) { cache.set(obj, newObj); } return newObj; }
13
+ (0, _fixugen.default)({
14
+ callback,
15
+ path: [__dirname, '..', 'test-fixtures', 'index'],
16
+ recurse: false,
17
+ useMetadataFile: true,
18
+ fixura: {
19
+ failWhenNotFound: false,
20
+ reader: _fixura.READERS.JSON
21
+ }
22
+ });
23
+ function callback({
24
+ getFixture,
25
+ reducerConfigs = []
26
+ }) {
27
+ const base = new _marcRecord.MarcRecord(getFixture('base.json'), {
28
+ subfieldValues: false
29
+ });
30
+ const source = new _marcRecord.MarcRecord(getFixture('source.json'), {
31
+ subfieldValues: false
32
+ });
33
+ const expectedRecord = getFixture('merged.json');
34
+ const debug = (0, _debug.default)('@natlibfi/melinda-marc-record-merge-reducers:index:test');
35
+ const debugData = debug.extend('data');
36
+ const testReducerConfigs = reducerConfigs;
37
+ const reducers = [...testReducerConfigs.map(conf => _index.Reducers.copy(conf))];
38
+ debugData(`Reducers: ${(0, _util.inspect)(reducers, {
39
+ colors: true,
40
+ maxArrayLength: 10,
41
+ depth: 8
42
+ })})}`);
43
+ const result = (0, _index.default)({
44
+ base,
45
+ source,
46
+ reducers
47
+ });
48
+ debug(`Merge result is: ${result.constructor.name}`);
49
+ debugData(`${JSON.stringify(result)}`);
50
+
51
+ // Use either result.base or a plain result as resultRecord
52
+ // It can also be a MarcRecord or a plain object
53
+ const resultRecord = result.base || result;
54
+ const resultRecordToRecord = new _marcRecord.MarcRecord(resultRecord, {
55
+ subfieldValues: false
56
+ });
57
+ (0, _chai.expect)(resultRecordToRecord.toObject()).to.eql(expectedRecord);
58
+ }
59
+ //# sourceMappingURL=index.spec.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.spec.js","names":["generateTests","callback","path","__dirname","recurse","useMetadataFile","fixura","failWhenNotFound","reader","READERS","JSON","getFixture","reducerConfigs","base","MarcRecord","subfieldValues","source","expectedRecord","debug","createDebugLogger","debugData","extend","testReducerConfigs","reducers","map","conf","Reducers","copy","inspect","colors","maxArrayLength","depth","result","merger","constructor","name","stringify","resultRecord","resultRecordToRecord","expect","toObject","to","eql"],"sources":["../src/index.spec.js"],"sourcesContent":["import merger, {Reducers} from './index';\nimport {inspect} from 'util';\nimport createDebugLogger from 'debug';\nimport {expect} from 'chai';\nimport {MarcRecord} from '@natlibfi/marc-record';\nimport {READERS} from '@natlibfi/fixura';\nimport generateTests from '@natlibfi/fixugen';\n\ngenerateTests({\n callback,\n path: [__dirname, '..', 'test-fixtures', 'index'],\n recurse: false,\n useMetadataFile: true,\n fixura: {\n failWhenNotFound: false,\n reader: READERS.JSON\n }\n});\n\nfunction callback({getFixture, reducerConfigs = []}) {\n const base = new MarcRecord(getFixture('base.json'), {subfieldValues: false});\n const source = new MarcRecord(getFixture('source.json'), {subfieldValues: false});\n const expectedRecord = getFixture('merged.json');\n\n const debug = createDebugLogger('@natlibfi/melinda-marc-record-merge-reducers:index:test');\n const debugData = debug.extend('data');\n\n const testReducerConfigs = reducerConfigs;\n const reducers = [...testReducerConfigs.map(conf => Reducers.copy(conf))];\n\n debugData(`Reducers: ${inspect(reducers, {colors: true, maxArrayLength: 10, depth: 8})})}`);\n\n const result = merger({base, source, reducers});\n\n debug(`Merge result is: ${result.constructor.name}`);\n debugData(`${JSON.stringify(result)}`);\n\n // Use either result.base or a plain result as resultRecord\n // It can also be a MarcRecord or a plain object\n const resultRecord = result.base || result;\n const resultRecordToRecord = new MarcRecord(resultRecord, {subfieldValues: false});\n expect(resultRecordToRecord.toObject()).to.eql(expectedRecord);\n\n\n}\n"],"mappings":";;AAAA;AACA;AACA;AACA;AACA;AACA;AACA;AAA8C;AAAA;AAAA;AAE9C,IAAAA,gBAAa,EAAC;EACZC,QAAQ;EACRC,IAAI,EAAE,CAACC,SAAS,EAAE,IAAI,EAAE,eAAe,EAAE,OAAO,CAAC;EACjDC,OAAO,EAAE,KAAK;EACdC,eAAe,EAAE,IAAI;EACrBC,MAAM,EAAE;IACNC,gBAAgB,EAAE,KAAK;IACvBC,MAAM,EAAEC,eAAO,CAACC;EAClB;AACF,CAAC,CAAC;AAEF,SAAST,QAAQ,CAAC;EAACU,UAAU;EAAEC,cAAc,GAAG;AAAE,CAAC,EAAE;EACnD,MAAMC,IAAI,GAAG,IAAIC,sBAAU,CAACH,UAAU,CAAC,WAAW,CAAC,EAAE;IAACI,cAAc,EAAE;EAAK,CAAC,CAAC;EAC7E,MAAMC,MAAM,GAAG,IAAIF,sBAAU,CAACH,UAAU,CAAC,aAAa,CAAC,EAAE;IAACI,cAAc,EAAE;EAAK,CAAC,CAAC;EACjF,MAAME,cAAc,GAAGN,UAAU,CAAC,aAAa,CAAC;EAEhD,MAAMO,KAAK,GAAG,IAAAC,cAAiB,EAAC,yDAAyD,CAAC;EAC1F,MAAMC,SAAS,GAAGF,KAAK,CAACG,MAAM,CAAC,MAAM,CAAC;EAEtC,MAAMC,kBAAkB,GAAGV,cAAc;EACzC,MAAMW,QAAQ,GAAG,CAAC,GAAGD,kBAAkB,CAACE,GAAG,CAACC,IAAI,IAAIC,eAAQ,CAACC,IAAI,CAACF,IAAI,CAAC,CAAC,CAAC;EAEzEL,SAAS,CAAE,aAAY,IAAAQ,aAAO,EAACL,QAAQ,EAAE;IAACM,MAAM,EAAE,IAAI;IAAEC,cAAc,EAAE,EAAE;IAAEC,KAAK,EAAE;EAAC,CAAC,CAAE,IAAG,CAAC;EAE3F,MAAMC,MAAM,GAAG,IAAAC,cAAM,EAAC;IAACpB,IAAI;IAAEG,MAAM;IAAEO;EAAQ,CAAC,CAAC;EAE/CL,KAAK,CAAE,oBAAmBc,MAAM,CAACE,WAAW,CAACC,IAAK,EAAC,CAAC;EACpDf,SAAS,CAAE,GAAEV,IAAI,CAAC0B,SAAS,CAACJ,MAAM,CAAE,EAAC,CAAC;;EAEtC;EACA;EACA,MAAMK,YAAY,GAAGL,MAAM,CAACnB,IAAI,IAAImB,MAAM;EAC1C,MAAMM,oBAAoB,GAAG,IAAIxB,sBAAU,CAACuB,YAAY,EAAE;IAACtB,cAAc,EAAE;EAAK,CAAC,CAAC;EAClF,IAAAwB,YAAM,EAACD,oBAAoB,CAACE,QAAQ,EAAE,CAAC,CAACC,EAAE,CAACC,GAAG,CAACzB,cAAc,CAAC;AAGhE"}
@@ -30,11 +30,34 @@ var _default = ({
30
30
  swapSubfieldCode = [],
31
31
  doNotCopyIfFieldPresent = false
32
32
  }) => (base, source) => {
33
- const baseRecord = new _marcRecord.MarcRecord(base, baseValidators);
34
- const sourceRecord = new _marcRecord.MarcRecord(source, sourceValidators);
35
- const debug = (0, _debug.default)('@natlibfi/marc-record-merge');
33
+ const debug = (0, _debug.default)('@natlibfi/marc-record-merge:copy');
34
+ const debugData = debug.extend('data');
36
35
  const debugOptions = (0, _debug.default)('@natlibfi/marc-record-merge:compare-options');
37
36
  const debugCompare = (0, _debug.default)('@natlibfi/marc-record-merge:compare');
37
+ debugData(`base: ${JSON.stringify(base)}`);
38
+ debugData(`source: ${JSON.stringify(source)}`);
39
+ const {
40
+ baseRecord,
41
+ sourceRecord
42
+ } = getRecordsFromParameters(base, source, baseValidators, sourceValidators);
43
+ function getRecordsFromParameters(base, source, baseValidators, sourceValidators) {
44
+ // records if we got an object ({base, source}) as a parameter
45
+ if (source === undefined && base.base !== undefined && base.source !== undefined) {
46
+ const baseRecord = new _marcRecord.MarcRecord(base.base, baseValidators);
47
+ const sourceRecord = new _marcRecord.MarcRecord(base.source, sourceValidators);
48
+ return {
49
+ baseRecord,
50
+ sourceRecord
51
+ };
52
+ }
53
+ // records if we got an non-object (base, source) as a parameter
54
+ const baseRecord = new _marcRecord.MarcRecord(base, baseValidators);
55
+ const sourceRecord = new _marcRecord.MarcRecord(source, sourceValidators);
56
+ return {
57
+ baseRecord,
58
+ sourceRecord
59
+ };
60
+ }
38
61
  const ignoreInd1 = compareWithoutIndicators || compareWithoutIndicator1;
39
62
  const ignoreInd2 = compareWithoutIndicators || compareWithoutIndicator2;
40
63
  debugOptions(`Tag Pattern: ${tagPattern}`);
@@ -68,6 +91,8 @@ var _default = ({
68
91
 
69
92
  // Add fields to base;
70
93
  uniqueFields.forEach(field => baseRecord.insertField(field));
94
+ debugData(`baseRecord before return: ${JSON.stringify(baseRecord)}`);
95
+ //return baseRecord;
71
96
  return baseRecord.toObject();
72
97
  function compareFields(sourceFields, baseCompareFields, uniqFields = []) {
73
98
  const [sourceField, ...rest] = sourceFields;
@@ -1 +1 @@
1
- {"version":3,"file":"copy.js","names":["tagPattern","compareTagsOnly","compareWithoutTag","compareWithoutIndicators","compareWithoutIndicator1","compareWithoutIndicator2","subfieldsMustBeIdentical","excludeSubfields","dropSubfields","copyUnless","baseValidators","subfieldValues","sourceValidators","swapTag","swapSubfieldCode","doNotCopyIfFieldPresent","base","source","baseRecord","MarcRecord","sourceRecord","debug","createDebugLogger","debugOptions","debugCompare","ignoreInd1","ignoreInd2","JSON","stringify","baseFields","get","sourceFields","doNotCopy","length","toObject","baseCompareFields","map","baseField","createCompareField","compareResultFields","compareFields","droppedUnwantedSubfield","checkDropSubfields","droppedUnwantedFields","checkCopyUnlessFields","swappedSubfields","checkSwapSubfieldCodes","swappedTags","checkSwapTag","uniqueFields","Set","field","parse","forEach","insertField","uniqFields","sourceField","rest","undefined","sourceCompareField","unique","checkCompareFields","baseCompareField","value","ind1","ind2","allFound","checkSubfields","subfields","sourceSubfields","baseSubfields","foundSubs","filter","sSub","some","bSub","code","tag","filteredField","foundRule","rule","RegExp","from","test","replacementTag","to","params","name","createCompareSubfields","param","Object","fromEntries","nonExcludedSubfields","sub","normalizedSubfields","normalizeSubfieldValue","toLowerCase","replace","fields","swapTagsFunc","swapSubfieldCodesFunc","dropSubfieldsFunc","condition"],"sources":["../../src/reducers/copy.js"],"sourcesContent":["/* eslint-disable max-statements */\n/* eslint-disable no-unused-vars */\n\nimport {MarcRecord} from '@natlibfi/marc-record';\nimport createDebugLogger from 'debug';\n\nexport default ({\n tagPattern,\n compareTagsOnly = false,\n compareWithoutTag = false,\n compareWithoutIndicators = false,\n compareWithoutIndicator1 = false,\n compareWithoutIndicator2 = false,\n subfieldsMustBeIdentical = true,\n excludeSubfields = [],\n dropSubfields = [],\n copyUnless = [],\n baseValidators = {subfieldValues: false},\n sourceValidators = {subfieldValues: false},\n swapTag = [],\n swapSubfieldCode = [],\n doNotCopyIfFieldPresent = false\n}) => (base, source) => {\n const baseRecord = new MarcRecord(base, baseValidators);\n const sourceRecord = new MarcRecord(source, sourceValidators);\n\n const debug = createDebugLogger('@natlibfi/marc-record-merge');\n const debugOptions = createDebugLogger('@natlibfi/marc-record-merge:compare-options');\n const debugCompare = createDebugLogger('@natlibfi/marc-record-merge:compare');\n\n const ignoreInd1 = compareWithoutIndicators || compareWithoutIndicator1;\n const ignoreInd2 = compareWithoutIndicators || compareWithoutIndicator2;\n\n debugOptions(`Tag Pattern: ${tagPattern}`);\n debugOptions(`Compare tags only: ${compareTagsOnly}`);\n debugOptions(`Omit indicator 1 from comparison: ${ignoreInd1}`);\n debugOptions(`Omit indicator 2 from comparison: ${ignoreInd2}`);\n debugOptions(`Copy if identical: ${subfieldsMustBeIdentical}`);\n debugOptions(`Exclude subfields: [${excludeSubfields}]`);\n debugOptions(`Drop subfields [${dropSubfields}]`);\n debugOptions(`Copy unless contains subfields: ${JSON.stringify(copyUnless)}`);\n\n const baseFields = baseRecord.get(tagPattern);\n const sourceFields = sourceRecord.get(tagPattern);\n const doNotCopy = doNotCopyIfFieldPresent ? baseRecord.get(doNotCopyIfFieldPresent).length > 0 : false;\n\n if (doNotCopy) {\n return baseRecord.toObject();\n }\n debug(`FFS: ${compareWithoutIndicator1}, ${compareWithoutIndicators}, ${ignoreInd1}`);\n debug(`Base fields: `, baseFields);\n debug(`Source fields: `, sourceFields);\n\n // Logic steps\n const baseCompareFields = baseFields.map(baseField => createCompareField(baseField));\n const compareResultFields = compareFields(sourceFields, baseCompareFields);\n const droppedUnwantedSubfield = checkDropSubfields(compareResultFields);\n const droppedUnwantedFields = checkCopyUnlessFields(droppedUnwantedSubfield);\n const swappedSubfields = checkSwapSubfieldCodes(droppedUnwantedFields);\n const swappedTags = checkSwapTag(swappedSubfields);\n const uniqueFields = [...new Set(swappedTags.map(field => JSON.stringify(field)))].map(field => JSON.parse(field));\n debug('Fields to be copied');\n debug(JSON.stringify(uniqueFields));\n\n // Add fields to base;\n uniqueFields.forEach(field => baseRecord.insertField(field));\n return baseRecord.toObject();\n\n function compareFields(sourceFields, baseCompareFields, uniqFields = []) {\n const [sourceField, ...rest] = sourceFields;\n if (sourceField === undefined) {\n return uniqFields;\n }\n\n if (baseCompareFields.length === 0) {\n return compareFields(rest, baseCompareFields, [...uniqFields, sourceField]);\n }\n\n // Source and base are also compared for identicalness\n // Non-identical fields are copied from source to base as duplicates\n const sourceCompareField = createCompareField(sourceField);\n const unique = checkCompareFields(baseCompareFields, sourceCompareField);\n\n debugCompare(`${JSON.stringify(sourceField)} ${unique ? 'is UNIQUE' : 'not UNIQUE'}`);\n\n if (unique) {\n return compareFields(rest, baseCompareFields, [...uniqFields, sourceField]);\n }\n\n return compareFields(rest, baseCompareFields, uniqFields);\n\n function checkCompareFields(baseCompareFields, sourceCompareField) {\n let unique = true; // eslint-disable-line functional/no-let\n\n baseCompareFields.forEach(baseCompareField => {\n debugCompare(`Comparing ${JSON.stringify(sourceCompareField)} to ${JSON.stringify(baseCompareField)}}`);\n\n if (sourceCompareField.value !== baseCompareField.value) {\n debugCompare(`Value is different ${sourceCompareField.value} !== ${baseCompareField.value}`);\n return;\n }\n\n if (sourceCompareField.ind1 !== baseCompareField.ind1) {\n debugCompare(`Ind1 is different ${sourceCompareField.ind1} !== ${baseCompareField.ind1}`);\n return;\n }\n\n if (sourceCompareField.ind2 !== baseCompareField.ind2) {\n debugCompare(`Ind2 is different ${sourceCompareField.ind2} !== ${baseCompareField.ind2}`);\n return;\n }\n\n if ('subfields' in sourceCompareField) {\n const allFound = checkSubfields(sourceCompareField.subfields, baseCompareField.subfields);\n debugCompare(`Subfields are different ${!allFound}`);\n if (!allFound) {\n return;\n }\n\n unique = false;\n return;\n }\n\n unique = false;\n return;\n });\n\n return unique;\n }\n\n function checkSubfields(sourceSubfields, baseSubfields) {\n const foundSubs = sourceSubfields.filter(sSub => baseSubfields.some(bSub => sSub.code === bSub.code && sSub.value === bSub.value));\n\n if (subfieldsMustBeIdentical) {\n return foundSubs.length === sourceSubfields.length && foundSubs.length === baseSubfields.length;\n }\n\n return foundSubs.length === sourceSubfields.length;\n }\n }\n\n // compare objects have only fields that matter in comparison\n function createCompareField(field) {\n if (compareTagsOnly) {\n return {tag: field.tag};\n }\n\n if ('value' in field) {\n return {tag: field.tag, value: field.value};\n }\n\n const [filteredField] = checkDropSubfields([field]);\n const [foundRule] = swapTag.filter(rule => new RegExp(rule.from, 'u').test(field.tag));\n const replacementTag = foundRule ? foundRule.to : undefined;\n\n const params = [\n {name: 'tag', value: compareWithoutTag ? replacementTag : field.tag},\n {name: 'ind1', value: ignoreInd1 ? undefined : field.ind1},\n {name: 'ind2', value: ignoreInd2 ? undefined : field.ind2},\n {name: 'subfields', value: createCompareSubfields(filteredField.subfields)}\n ].map(param => [param.name, param.value]);\n\n return Object.fromEntries(params);\n\n function createCompareSubfields(subfields) {\n const nonExcludedSubfields = subfields.filter(sub => !excludeSubfields.some(code => code === sub.code));\n const normalizedSubfields = nonExcludedSubfields.map(sub => ({code: sub.code, value: normalizeSubfieldValue(sub.value)}));\n\n return normalizedSubfields;\n\n function normalizeSubfieldValue(value) {\n return value.toLowerCase().replace(/\\s+/ug, '');\n }\n }\n }\n\n function checkSwapTag(fields) {\n if (swapTag.length > 0) {\n return fields.map(field => ({...field, tag: swapTagsFunc(field.tag)}));\n }\n\n return fields;\n\n function swapTagsFunc(tag) {\n const [foundRule] = swapTag.filter(rule => new RegExp(rule.from, 'u').test(tag));\n\n if (foundRule === undefined) {\n return tag;\n }\n\n return foundRule.to;\n }\n }\n\n function checkSwapSubfieldCodes(fields) {\n if (swapSubfieldCode.length > 0) {\n return fields.map(field => ({...field, subfields: swapSubfieldCodesFunc(field.subfields)}));\n }\n\n return fields;\n\n function swapSubfieldCodesFunc(subfields) {\n return subfields.map(sub => {\n const [foundRule] = swapSubfieldCode.filter(rule => rule.from === sub.code);\n\n if (foundRule === undefined) {\n return sub;\n }\n\n return {code: foundRule.to, value: sub.value};\n });\n }\n }\n\n function checkDropSubfields(fields) {\n if (dropSubfields.length > 0) {\n return fields.map(field => ({...field, subfields: dropSubfieldsFunc(field.subfields)}))\n .filter(field => field.subfields.length > 0);\n }\n\n return fields;\n\n function dropSubfieldsFunc(subfields) {\n return subfields.filter(sub => { // eslint-disable-line\n return !dropSubfields.some(({code, value = false, condition = false}) => {\n if (code !== sub.code) {\n return false;\n }\n\n if (!condition && value) {\n return value === sub.value;\n }\n\n if (condition === 'unless' && value) {\n return !new RegExp(value, 'u').test(sub.value);\n }\n\n return true;\n });\n });\n }\n }\n\n function checkCopyUnlessFields(fields) {\n if (copyUnless.length > 0) {\n return fields.filter(({subfields}) => copyUnless.some(filter => !subfields.some(sub => sub.code === filter.code && new RegExp(filter.value, 'u').test(sub.value))));\n }\n\n return fields;\n }\n};\n"],"mappings":"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"}
1
+ {"version":3,"file":"copy.js","names":["tagPattern","compareTagsOnly","compareWithoutTag","compareWithoutIndicators","compareWithoutIndicator1","compareWithoutIndicator2","subfieldsMustBeIdentical","excludeSubfields","dropSubfields","copyUnless","baseValidators","subfieldValues","sourceValidators","swapTag","swapSubfieldCode","doNotCopyIfFieldPresent","base","source","debug","createDebugLogger","debugData","extend","debugOptions","debugCompare","JSON","stringify","baseRecord","sourceRecord","getRecordsFromParameters","undefined","MarcRecord","ignoreInd1","ignoreInd2","baseFields","get","sourceFields","doNotCopy","length","toObject","baseCompareFields","map","baseField","createCompareField","compareResultFields","compareFields","droppedUnwantedSubfield","checkDropSubfields","droppedUnwantedFields","checkCopyUnlessFields","swappedSubfields","checkSwapSubfieldCodes","swappedTags","checkSwapTag","uniqueFields","Set","field","parse","forEach","insertField","uniqFields","sourceField","rest","sourceCompareField","unique","checkCompareFields","baseCompareField","value","ind1","ind2","allFound","checkSubfields","subfields","sourceSubfields","baseSubfields","foundSubs","filter","sSub","some","bSub","code","tag","filteredField","foundRule","rule","RegExp","from","test","replacementTag","to","params","name","createCompareSubfields","param","Object","fromEntries","nonExcludedSubfields","sub","normalizedSubfields","normalizeSubfieldValue","toLowerCase","replace","fields","swapTagsFunc","swapSubfieldCodesFunc","dropSubfieldsFunc","condition"],"sources":["../../src/reducers/copy.js"],"sourcesContent":["/* eslint-disable max-statements */\n/* eslint-disable no-unused-vars */\n\nimport {MarcRecord} from '@natlibfi/marc-record';\nimport createDebugLogger from 'debug';\n\nexport default ({\n tagPattern,\n compareTagsOnly = false,\n compareWithoutTag = false,\n compareWithoutIndicators = false,\n compareWithoutIndicator1 = false,\n compareWithoutIndicator2 = false,\n subfieldsMustBeIdentical = true,\n excludeSubfields = [],\n dropSubfields = [],\n copyUnless = [],\n baseValidators = {subfieldValues: false},\n sourceValidators = {subfieldValues: false},\n swapTag = [],\n swapSubfieldCode = [],\n doNotCopyIfFieldPresent = false\n}) => (base, source) => {\n\n const debug = createDebugLogger('@natlibfi/marc-record-merge:copy');\n const debugData = debug.extend('data');\n const debugOptions = createDebugLogger('@natlibfi/marc-record-merge:compare-options');\n const debugCompare = createDebugLogger('@natlibfi/marc-record-merge:compare');\n\n debugData(`base: ${JSON.stringify(base)}`);\n debugData(`source: ${JSON.stringify(source)}`);\n\n const {baseRecord, sourceRecord} = getRecordsFromParameters(base, source, baseValidators, sourceValidators);\n\n function getRecordsFromParameters(base, source, baseValidators, sourceValidators) {\n // records if we got an object ({base, source}) as a parameter\n if (source === undefined && base.base !== undefined && base.source !== undefined) {\n const baseRecord = new MarcRecord(base.base, baseValidators);\n const sourceRecord = new MarcRecord(base.source, sourceValidators);\n return {baseRecord, sourceRecord};\n }\n // records if we got an non-object (base, source) as a parameter\n const baseRecord = new MarcRecord(base, baseValidators);\n const sourceRecord = new MarcRecord(source, sourceValidators);\n return {baseRecord, sourceRecord};\n }\n\n const ignoreInd1 = compareWithoutIndicators || compareWithoutIndicator1;\n const ignoreInd2 = compareWithoutIndicators || compareWithoutIndicator2;\n\n debugOptions(`Tag Pattern: ${tagPattern}`);\n debugOptions(`Compare tags only: ${compareTagsOnly}`);\n debugOptions(`Omit indicator 1 from comparison: ${ignoreInd1}`);\n debugOptions(`Omit indicator 2 from comparison: ${ignoreInd2}`);\n debugOptions(`Copy if identical: ${subfieldsMustBeIdentical}`);\n debugOptions(`Exclude subfields: [${excludeSubfields}]`);\n debugOptions(`Drop subfields [${dropSubfields}]`);\n debugOptions(`Copy unless contains subfields: ${JSON.stringify(copyUnless)}`);\n\n const baseFields = baseRecord.get(tagPattern);\n const sourceFields = sourceRecord.get(tagPattern);\n const doNotCopy = doNotCopyIfFieldPresent ? baseRecord.get(doNotCopyIfFieldPresent).length > 0 : false;\n\n if (doNotCopy) {\n return baseRecord.toObject();\n }\n debug(`FFS: ${compareWithoutIndicator1}, ${compareWithoutIndicators}, ${ignoreInd1}`);\n debug(`Base fields: `, baseFields);\n debug(`Source fields: `, sourceFields);\n\n // Logic steps\n const baseCompareFields = baseFields.map(baseField => createCompareField(baseField));\n const compareResultFields = compareFields(sourceFields, baseCompareFields);\n const droppedUnwantedSubfield = checkDropSubfields(compareResultFields);\n const droppedUnwantedFields = checkCopyUnlessFields(droppedUnwantedSubfield);\n const swappedSubfields = checkSwapSubfieldCodes(droppedUnwantedFields);\n const swappedTags = checkSwapTag(swappedSubfields);\n const uniqueFields = [...new Set(swappedTags.map(field => JSON.stringify(field)))].map(field => JSON.parse(field));\n debug('Fields to be copied');\n debug(JSON.stringify(uniqueFields));\n\n // Add fields to base;\n uniqueFields.forEach(field => baseRecord.insertField(field));\n debugData(`baseRecord before return: ${JSON.stringify(baseRecord)}`);\n //return baseRecord;\n return baseRecord.toObject();\n\n function compareFields(sourceFields, baseCompareFields, uniqFields = []) {\n const [sourceField, ...rest] = sourceFields;\n if (sourceField === undefined) {\n return uniqFields;\n }\n\n if (baseCompareFields.length === 0) {\n return compareFields(rest, baseCompareFields, [...uniqFields, sourceField]);\n }\n\n // Source and base are also compared for identicalness\n // Non-identical fields are copied from source to base as duplicates\n const sourceCompareField = createCompareField(sourceField);\n const unique = checkCompareFields(baseCompareFields, sourceCompareField);\n\n debugCompare(`${JSON.stringify(sourceField)} ${unique ? 'is UNIQUE' : 'not UNIQUE'}`);\n\n if (unique) {\n return compareFields(rest, baseCompareFields, [...uniqFields, sourceField]);\n }\n\n return compareFields(rest, baseCompareFields, uniqFields);\n\n function checkCompareFields(baseCompareFields, sourceCompareField) {\n let unique = true; // eslint-disable-line functional/no-let\n\n baseCompareFields.forEach(baseCompareField => {\n debugCompare(`Comparing ${JSON.stringify(sourceCompareField)} to ${JSON.stringify(baseCompareField)}}`);\n\n if (sourceCompareField.value !== baseCompareField.value) {\n debugCompare(`Value is different ${sourceCompareField.value} !== ${baseCompareField.value}`);\n return;\n }\n\n if (sourceCompareField.ind1 !== baseCompareField.ind1) {\n debugCompare(`Ind1 is different ${sourceCompareField.ind1} !== ${baseCompareField.ind1}`);\n return;\n }\n\n if (sourceCompareField.ind2 !== baseCompareField.ind2) {\n debugCompare(`Ind2 is different ${sourceCompareField.ind2} !== ${baseCompareField.ind2}`);\n return;\n }\n\n if ('subfields' in sourceCompareField) {\n const allFound = checkSubfields(sourceCompareField.subfields, baseCompareField.subfields);\n debugCompare(`Subfields are different ${!allFound}`);\n if (!allFound) {\n return;\n }\n\n unique = false;\n return;\n }\n\n unique = false;\n return;\n });\n\n return unique;\n }\n\n function checkSubfields(sourceSubfields, baseSubfields) {\n const foundSubs = sourceSubfields.filter(sSub => baseSubfields.some(bSub => sSub.code === bSub.code && sSub.value === bSub.value));\n\n if (subfieldsMustBeIdentical) {\n return foundSubs.length === sourceSubfields.length && foundSubs.length === baseSubfields.length;\n }\n\n return foundSubs.length === sourceSubfields.length;\n }\n }\n\n // compare objects have only fields that matter in comparison\n function createCompareField(field) {\n if (compareTagsOnly) {\n return {tag: field.tag};\n }\n\n if ('value' in field) {\n return {tag: field.tag, value: field.value};\n }\n\n const [filteredField] = checkDropSubfields([field]);\n const [foundRule] = swapTag.filter(rule => new RegExp(rule.from, 'u').test(field.tag));\n const replacementTag = foundRule ? foundRule.to : undefined;\n\n const params = [\n {name: 'tag', value: compareWithoutTag ? replacementTag : field.tag},\n {name: 'ind1', value: ignoreInd1 ? undefined : field.ind1},\n {name: 'ind2', value: ignoreInd2 ? undefined : field.ind2},\n {name: 'subfields', value: createCompareSubfields(filteredField.subfields)}\n ].map(param => [param.name, param.value]);\n\n return Object.fromEntries(params);\n\n function createCompareSubfields(subfields) {\n const nonExcludedSubfields = subfields.filter(sub => !excludeSubfields.some(code => code === sub.code));\n const normalizedSubfields = nonExcludedSubfields.map(sub => ({code: sub.code, value: normalizeSubfieldValue(sub.value)}));\n\n return normalizedSubfields;\n\n function normalizeSubfieldValue(value) {\n return value.toLowerCase().replace(/\\s+/ug, '');\n }\n }\n }\n\n function checkSwapTag(fields) {\n if (swapTag.length > 0) {\n return fields.map(field => ({...field, tag: swapTagsFunc(field.tag)}));\n }\n\n return fields;\n\n function swapTagsFunc(tag) {\n const [foundRule] = swapTag.filter(rule => new RegExp(rule.from, 'u').test(tag));\n\n if (foundRule === undefined) {\n return tag;\n }\n\n return foundRule.to;\n }\n }\n\n function checkSwapSubfieldCodes(fields) {\n if (swapSubfieldCode.length > 0) {\n return fields.map(field => ({...field, subfields: swapSubfieldCodesFunc(field.subfields)}));\n }\n\n return fields;\n\n function swapSubfieldCodesFunc(subfields) {\n return subfields.map(sub => {\n const [foundRule] = swapSubfieldCode.filter(rule => rule.from === sub.code);\n\n if (foundRule === undefined) {\n return sub;\n }\n\n return {code: foundRule.to, value: sub.value};\n });\n }\n }\n\n function checkDropSubfields(fields) {\n if (dropSubfields.length > 0) {\n return fields.map(field => ({...field, subfields: dropSubfieldsFunc(field.subfields)}))\n .filter(field => field.subfields.length > 0);\n }\n\n return fields;\n\n function dropSubfieldsFunc(subfields) {\n return subfields.filter(sub => { // eslint-disable-line\n return !dropSubfields.some(({code, value = false, condition = false}) => {\n if (code !== sub.code) {\n return false;\n }\n\n if (!condition && value) {\n return value === sub.value;\n }\n\n if (condition === 'unless' && value) {\n return !new RegExp(value, 'u').test(sub.value);\n }\n\n return true;\n });\n });\n }\n }\n\n function checkCopyUnlessFields(fields) {\n if (copyUnless.length > 0) {\n return fields.filter(({subfields}) => copyUnless.some(filter => !subfields.some(sub => sub.code === filter.code && new RegExp(filter.value, 'u').test(sub.value))));\n }\n\n return fields;\n }\n};\n"],"mappings":"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"}
@@ -0,0 +1,67 @@
1
+ "use strict";
2
+
3
+ var _chai = require("chai");
4
+ var _fixura = require("@natlibfi/fixura");
5
+ var _copy = _interopRequireDefault(require("./copy"));
6
+ var _fixugen = _interopRequireDefault(require("@natlibfi/fixugen"));
7
+ function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
8
+ //import createDebugLogger from 'debug'; // <---
9
+ //const debug = createDebugLogger('@natlibfi/marc-record-merge/copy.spec.js'); // <---
10
+
11
+ (0, _fixugen.default)({
12
+ callback,
13
+ path: [__dirname, '..', '..', 'test-fixtures', 'reducers', 'copy'],
14
+ useMetadataFile: true,
15
+ recurse: true,
16
+ fixura: {
17
+ reader: _fixura.READERS.JSON,
18
+ failWhenNotFound: false
19
+ }
20
+ });
21
+ function callback({
22
+ getFixture,
23
+ tagPatternRegExp,
24
+ compareTagsOnly = false,
25
+ compareWithoutTag = false,
26
+ compareWithoutIndicators = false,
27
+ compareWithoutIndicator1 = false,
28
+ compareWithoutIndicator2 = false,
29
+ subfieldsMustBeIdentical = false,
30
+ copyUnless = undefined,
31
+ excludeSubfields = undefined,
32
+ dropSubfields = undefined,
33
+ swapSubfieldCode = [],
34
+ swapTag = [],
35
+ doNotCopyIfFieldPresent = false
36
+ }) {
37
+ const base = getFixture('base.json');
38
+ const source = getFixture('source.json');
39
+ const tagPattern = new RegExp(tagPatternRegExp, 'u');
40
+ const expectedRecord = getFixture('merged.json');
41
+ const merged = (0, _copy.default)({
42
+ tagPattern,
43
+ compareTagsOnly,
44
+ compareWithoutTag,
45
+ compareWithoutIndicators,
46
+ compareWithoutIndicator1,
47
+ compareWithoutIndicator2,
48
+ copyUnless,
49
+ subfieldsMustBeIdentical,
50
+ excludeSubfields,
51
+ dropSubfields,
52
+ swapSubfieldCode,
53
+ swapTag,
54
+ doNotCopyIfFieldPresent
55
+ })({
56
+ base,
57
+ source
58
+ });
59
+ //debug(`*** mergedRecord: `, mergedRecord); //<--
60
+ //debug(`*** mergedRecord,Strfy: `, JSON.stringify(mergedRecord)); //<--
61
+ //debug(`*** expectedRecord: `, expectedRecord); //<--
62
+ //debug(`*** expectedRecord,Strfy: `, JSON.stringify(expectedRecord)); //<--
63
+ (0, _chai.expect)(merged.constructor.name).not.to.eql('MarcRecord');
64
+ (0, _chai.expect)(merged.constructor.name).to.eql('Object');
65
+ (0, _chai.expect)(merged).to.eql(expectedRecord);
66
+ }
67
+ //# sourceMappingURL=copy2.spec.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"copy2.spec.js","names":["generateTests","callback","path","__dirname","useMetadataFile","recurse","fixura","reader","READERS","JSON","failWhenNotFound","getFixture","tagPatternRegExp","compareTagsOnly","compareWithoutTag","compareWithoutIndicators","compareWithoutIndicator1","compareWithoutIndicator2","subfieldsMustBeIdentical","copyUnless","undefined","excludeSubfields","dropSubfields","swapSubfieldCode","swapTag","doNotCopyIfFieldPresent","base","source","tagPattern","RegExp","expectedRecord","merged","createReducer","expect","constructor","name","not","to","eql"],"sources":["../../src/reducers/copy2.spec.js"],"sourcesContent":["import {expect} from 'chai';\nimport {READERS} from '@natlibfi/fixura';\nimport createReducer from './copy';\nimport generateTests from '@natlibfi/fixugen';\n\n//import createDebugLogger from 'debug'; // <---\n//const debug = createDebugLogger('@natlibfi/marc-record-merge/copy.spec.js'); // <---\n\ngenerateTests({\n callback,\n path: [__dirname, '..', '..', 'test-fixtures', 'reducers', 'copy'],\n useMetadataFile: true,\n recurse: true,\n fixura: {\n reader: READERS.JSON,\n failWhenNotFound: false\n }\n});\n\n\nfunction callback({\n getFixture,\n tagPatternRegExp,\n compareTagsOnly = false,\n compareWithoutTag = false,\n compareWithoutIndicators = false,\n compareWithoutIndicator1 = false,\n compareWithoutIndicator2 = false,\n subfieldsMustBeIdentical = false,\n copyUnless = undefined,\n excludeSubfields = undefined,\n dropSubfields = undefined,\n swapSubfieldCode = [],\n swapTag = [],\n doNotCopyIfFieldPresent = false\n}) {\n const base = getFixture('base.json');\n const source = getFixture('source.json');\n const tagPattern = new RegExp(tagPatternRegExp, 'u');\n const expectedRecord = getFixture('merged.json');\n\n const merged = createReducer({\n tagPattern, compareTagsOnly, compareWithoutTag, compareWithoutIndicators, compareWithoutIndicator1, compareWithoutIndicator2,\n copyUnless, subfieldsMustBeIdentical, excludeSubfields,\n dropSubfields, swapSubfieldCode, swapTag,\n doNotCopyIfFieldPresent\n })({base, source});\n //debug(`*** mergedRecord: `, mergedRecord); //<--\n //debug(`*** mergedRecord,Strfy: `, JSON.stringify(mergedRecord)); //<--\n //debug(`*** expectedRecord: `, expectedRecord); //<--\n //debug(`*** expectedRecord,Strfy: `, JSON.stringify(expectedRecord)); //<--\n expect(merged.constructor.name).not.to.eql('MarcRecord');\n expect(merged.constructor.name).to.eql('Object');\n expect(merged).to.eql(expectedRecord);\n}\n"],"mappings":";;AAAA;AACA;AACA;AACA;AAA8C;AAE9C;AACA;;AAEA,IAAAA,gBAAa,EAAC;EACZC,QAAQ;EACRC,IAAI,EAAE,CAACC,SAAS,EAAE,IAAI,EAAE,IAAI,EAAE,eAAe,EAAE,UAAU,EAAE,MAAM,CAAC;EAClEC,eAAe,EAAE,IAAI;EACrBC,OAAO,EAAE,IAAI;EACbC,MAAM,EAAE;IACNC,MAAM,EAAEC,eAAO,CAACC,IAAI;IACpBC,gBAAgB,EAAE;EACpB;AACF,CAAC,CAAC;AAGF,SAAST,QAAQ,CAAC;EAChBU,UAAU;EACVC,gBAAgB;EAChBC,eAAe,GAAG,KAAK;EACvBC,iBAAiB,GAAG,KAAK;EACzBC,wBAAwB,GAAG,KAAK;EAChCC,wBAAwB,GAAG,KAAK;EAChCC,wBAAwB,GAAG,KAAK;EAChCC,wBAAwB,GAAG,KAAK;EAChCC,UAAU,GAAGC,SAAS;EACtBC,gBAAgB,GAAGD,SAAS;EAC5BE,aAAa,GAAGF,SAAS;EACzBG,gBAAgB,GAAG,EAAE;EACrBC,OAAO,GAAG,EAAE;EACZC,uBAAuB,GAAG;AAC5B,CAAC,EAAE;EACD,MAAMC,IAAI,GAAGf,UAAU,CAAC,WAAW,CAAC;EACpC,MAAMgB,MAAM,GAAGhB,UAAU,CAAC,aAAa,CAAC;EACxC,MAAMiB,UAAU,GAAG,IAAIC,MAAM,CAACjB,gBAAgB,EAAE,GAAG,CAAC;EACpD,MAAMkB,cAAc,GAAGnB,UAAU,CAAC,aAAa,CAAC;EAEhD,MAAMoB,MAAM,GAAG,IAAAC,aAAa,EAAC;IAC3BJ,UAAU;IAAEf,eAAe;IAAEC,iBAAiB;IAAEC,wBAAwB;IAAEC,wBAAwB;IAAEC,wBAAwB;IAC5HE,UAAU;IAAED,wBAAwB;IAAEG,gBAAgB;IACtDC,aAAa;IAAEC,gBAAgB;IAAEC,OAAO;IACxCC;EACF,CAAC,CAAC,CAAC;IAACC,IAAI;IAAEC;EAAM,CAAC,CAAC;EAClB;EACA;EACA;EACA;EACA,IAAAM,YAAM,EAACF,MAAM,CAACG,WAAW,CAACC,IAAI,CAAC,CAACC,GAAG,CAACC,EAAE,CAACC,GAAG,CAAC,YAAY,CAAC;EACxD,IAAAL,YAAM,EAACF,MAAM,CAACG,WAAW,CAACC,IAAI,CAAC,CAACE,EAAE,CAACC,GAAG,CAAC,QAAQ,CAAC;EAChD,IAAAL,YAAM,EAACF,MAAM,CAAC,CAACM,EAAE,CAACC,GAAG,CAACR,cAAc,CAAC;AACvC"}
@@ -19,15 +19,38 @@ function subsetEquality(subfieldA, subfieldB) {
19
19
  // EqualityFunction can be either strictEquality or subsetEquality
20
20
  var _default = ({
21
21
  tagPattern,
22
- equalityFunction = strictEquality
23
- }) => (base, source) => {
24
- const debug = (0, _debug.default)('@natlibfi/marc-record-merge:select');
25
- const baseRecord = new _marcRecord.MarcRecord(base, {
22
+ equalityFunction = strictEquality,
23
+ baseValidators = {
26
24
  subfieldValues: false
27
- });
28
- const sourceRecord = new _marcRecord.MarcRecord(source, {
25
+ },
26
+ sourceValidators = {
29
27
  subfieldValues: false
30
- });
28
+ }
29
+ // eslint-disable-next-line max-statements
30
+ }) => (base, source) => {
31
+ const debug = (0, _debug.default)('@natlibfi/marc-record-merge:select');
32
+ const {
33
+ baseRecord,
34
+ sourceRecord
35
+ } = getRecordsFromParameters(base, source, baseValidators, sourceValidators);
36
+ function getRecordsFromParameters(base, source, baseValidators, sourceValidators) {
37
+ // records if we got an object ({base, source}) as a parameter
38
+ if (source === undefined && base.base !== undefined && base.source !== undefined) {
39
+ const baseRecord = new _marcRecord.MarcRecord(base.base, baseValidators);
40
+ const sourceRecord = new _marcRecord.MarcRecord(base.source, sourceValidators);
41
+ return {
42
+ baseRecord,
43
+ sourceRecord
44
+ };
45
+ }
46
+ // records if we got an non-object (base, source) as a parameter
47
+ const baseRecord = new _marcRecord.MarcRecord(base, baseValidators);
48
+ const sourceRecord = new _marcRecord.MarcRecord(source, sourceValidators);
49
+ return {
50
+ baseRecord,
51
+ sourceRecord
52
+ };
53
+ }
31
54
  const baseFields = baseRecord.get(tagPattern);
32
55
  const sourceFields = sourceRecord.get(tagPattern);
33
56
  const fieldTag = sourceFields.map(field => field.tag);
@@ -37,14 +60,14 @@ var _default = ({
37
60
  if (baseFields.length > 1 || sourceFields.length > 1) {
38
61
  debug(`Multiple fields in base or source`);
39
62
  debug(`No changes to base`);
40
- return base;
63
+ return baseRecord.toObject();
41
64
  }
42
65
  const [baseField] = baseFields;
43
66
  const [sourceField] = sourceFields;
44
67
  if (baseField.tag === sourceField.tag === false) {
45
68
  debug(`Base tag ${baseField.tag} is not equal to source tag ${sourceField.tag}`);
46
69
  debug(`No changes to base`);
47
- return base;
70
+ return baseRecord.toObject();
48
71
  }
49
72
  const baseSubs = baseField.subfields;
50
73
  const sourceSubs = sourceField.subfields;
@@ -73,7 +96,7 @@ var _default = ({
73
96
  if (baseSubs.length === sourceSubs.length && equalSubfieldsBase.length < baseSubs.length) {
74
97
  debug(`Base and source subfields are not equal`);
75
98
  debug(`No changes to base`);
76
- return base;
99
+ return baseRecord.toObject();
77
100
  }
78
101
  if (baseSubs.length === sourceSubs.length && equalSubfieldsBase.length === equalSubfieldsSource.length) {
79
102
  debug(`Checking subfield equality`);
@@ -84,14 +107,14 @@ var _default = ({
84
107
  value
85
108
  }) => value.length).reduce((acc, value) => acc + value);
86
109
  if (totalSubfieldLengthSource > totalSubfieldLengthBase) {
87
- return replaceBasefieldWithSourcefield(base);
110
+ return replaceBasefieldWithSourcefield(baseRecord.toObject());
88
111
  }
89
112
  }
90
113
  if (sourceSubs.length > baseSubs.length && equalSubfieldsBase.length === baseSubs.length) {
91
- return replaceBasefieldWithSourcefield(base);
114
+ return replaceBasefieldWithSourcefield(baseRecord.toObject());
92
115
  }
93
116
  debug(`No changes to base`);
94
- return base;
117
+ return baseRecord.toObject();
95
118
  function replaceBasefieldWithSourcefield(base) {
96
119
  const index = base.fields.findIndex(field => field === baseField);
97
120
  base.fields.splice(index, 1, sourceField); // eslint-disable-line functional/immutable-data
@@ -1 +1 @@
1
- {"version":3,"file":"select.js","names":["strictEquality","subfieldA","subfieldB","code","value","subsetEquality","indexOf","tagPattern","equalityFunction","base","source","debug","createDebugLogger","baseRecord","MarcRecord","subfieldValues","sourceRecord","baseFields","get","sourceFields","fieldTag","map","field","tag","checkFieldType","length","baseField","sourceField","baseSubs","subfields","sourceSubs","baseSubsNormalized","normalizeSubfieldValue","sourceSubsNormalized","equalSubfieldsBase","filter","baseSubfield","some","sourceSubfield","JSON","stringify","undefined","equalSubfieldsSource","totalSubfieldLengthBase","reduce","acc","totalSubfieldLengthSource","replaceBasefieldWithSourcefield","index","fields","findIndex","splice","checkedFields","Error","punctuation","normalizeSync","toLowerCase","replace","trim"],"sources":["../../src/reducers/select.js"],"sourcesContent":["import {normalizeSync} from 'normalize-diacritics';\nimport createDebugLogger from 'debug';\nimport {MarcRecord} from '@natlibfi/marc-record';\n\nexport function strictEquality(subfieldA, subfieldB) {\n return subfieldA.code === subfieldB.code &&\n subfieldA.value === subfieldB.value;\n}\n\nexport function subsetEquality(subfieldA, subfieldB) {\n return subfieldA.code === subfieldB.code &&\n (subfieldA.value.indexOf(subfieldB.value) !== -1 || subfieldB.value.indexOf(subfieldA.value) !== -1);\n}\n// EqualityFunction can be either strictEquality or subsetEquality\nexport default ({tagPattern, equalityFunction = strictEquality}) => (base, source) => {\n const debug = createDebugLogger('@natlibfi/marc-record-merge:select');\n const baseRecord = new MarcRecord(base, {subfieldValues: false});\n const sourceRecord = new MarcRecord(source, {subfieldValues: false});\n const baseFields = baseRecord.get(tagPattern);\n const sourceFields = sourceRecord.get(tagPattern);\n const fieldTag = sourceFields.map(field => field.tag);\n debug(`Comparing field ${fieldTag}`);\n\n checkFieldType(baseFields);\n checkFieldType(sourceFields);\n\n if (baseFields.length > 1 || sourceFields.length > 1) {\n debug(`Multiple fields in base or source`);\n debug(`No changes to base`);\n return base;\n }\n const [baseField] = baseFields;\n const [sourceField] = sourceFields;\n\n if (baseField.tag === sourceField.tag === false) {\n debug(`Base tag ${baseField.tag} is not equal to source tag ${sourceField.tag}`);\n debug(`No changes to base`);\n return base;\n }\n const baseSubs = baseField.subfields;\n const sourceSubs = sourceField.subfields;\n\n const baseSubsNormalized = baseSubs\n .map(({code, value}) => ({code, value: normalizeSubfieldValue(value)}));\n\n const sourceSubsNormalized = sourceSubs\n .map(({code, value}) => ({code, value: normalizeSubfieldValue(value)}));\n\n // Returns the base subfields for which a matching source subfield is found\n const equalSubfieldsBase = baseSubsNormalized\n .filter(baseSubfield => sourceSubsNormalized\n .some(sourceSubfield => equalityFunction(baseSubfield, sourceSubfield)));\n debug(`equalSubfieldsBase: ${JSON.stringify(equalSubfieldsBase, undefined, 2)}`);\n\n // Returns the source subfields for which a matching base subfield is found\n const equalSubfieldsSource = sourceSubsNormalized\n .filter(sourceSubfield => baseSubsNormalized\n .some(baseSubfield => equalityFunction(sourceSubfield, baseSubfield)));\n debug(`equalSubfieldsSource: ${JSON.stringify(equalSubfieldsSource, undefined, 2)}`);\n\n if (baseSubs.length === sourceSubs.length && equalSubfieldsBase.length < baseSubs.length) {\n debug(`Base and source subfields are not equal`);\n debug(`No changes to base`);\n return base;\n }\n\n if (baseSubs.length === sourceSubs.length && equalSubfieldsBase.length === equalSubfieldsSource.length) {\n debug(`Checking subfield equality`);\n const totalSubfieldLengthBase = baseSubsNormalized\n .map(({value}) => value.length)\n .reduce((acc, value) => acc + value);\n const totalSubfieldLengthSource = sourceSubsNormalized\n .map(({value}) => value.length)\n .reduce((acc, value) => acc + value);\n\n if (totalSubfieldLengthSource > totalSubfieldLengthBase) {\n return replaceBasefieldWithSourcefield(base);\n }\n }\n\n if (sourceSubs.length > baseSubs.length && equalSubfieldsBase.length === baseSubs.length) {\n return replaceBasefieldWithSourcefield(base);\n }\n\n debug(`No changes to base`);\n return base;\n\n function replaceBasefieldWithSourcefield(base) {\n const index = base.fields.findIndex(field => field === baseField);\n base.fields.splice(index, 1, sourceField); // eslint-disable-line functional/immutable-data\n debug(`Source field is longer, replacing base with source`);\n return base;\n }\n\n function checkFieldType(fields) {\n const checkedFields = fields.map(field => {\n if ('value' in field) { // eslint-disable-line functional/no-conditional-statement\n throw new Error('Invalid control field, expected data field');\n }\n return field;\n });\n return checkedFields;\n }\n\n function normalizeSubfieldValue(value) {\n // Regexp options: g: global search, u: unicode\n const punctuation = /[.,\\-/#!?$%^&*;:{}=_`~()[\\]]/gu;\n return normalizeSync(value).toLowerCase().replace(punctuation, '', 'u').replace(/\\s+/gu, ' ').trim();\n }\n};\n"],"mappings":"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"}
1
+ {"version":3,"file":"select.js","names":["strictEquality","subfieldA","subfieldB","code","value","subsetEquality","indexOf","tagPattern","equalityFunction","baseValidators","subfieldValues","sourceValidators","base","source","debug","createDebugLogger","baseRecord","sourceRecord","getRecordsFromParameters","undefined","MarcRecord","baseFields","get","sourceFields","fieldTag","map","field","tag","checkFieldType","length","toObject","baseField","sourceField","baseSubs","subfields","sourceSubs","baseSubsNormalized","normalizeSubfieldValue","sourceSubsNormalized","equalSubfieldsBase","filter","baseSubfield","some","sourceSubfield","JSON","stringify","equalSubfieldsSource","totalSubfieldLengthBase","reduce","acc","totalSubfieldLengthSource","replaceBasefieldWithSourcefield","index","fields","findIndex","splice","checkedFields","Error","punctuation","normalizeSync","toLowerCase","replace","trim"],"sources":["../../src/reducers/select.js"],"sourcesContent":["import {normalizeSync} from 'normalize-diacritics';\nimport createDebugLogger from 'debug';\nimport {MarcRecord} from '@natlibfi/marc-record';\n\nexport function strictEquality(subfieldA, subfieldB) {\n return subfieldA.code === subfieldB.code &&\n subfieldA.value === subfieldB.value;\n}\n\nexport function subsetEquality(subfieldA, subfieldB) {\n return subfieldA.code === subfieldB.code &&\n (subfieldA.value.indexOf(subfieldB.value) !== -1 || subfieldB.value.indexOf(subfieldA.value) !== -1);\n}\n// EqualityFunction can be either strictEquality or subsetEquality\n\nexport default ({\n tagPattern,\n equalityFunction = strictEquality,\n baseValidators = {subfieldValues: false},\n sourceValidators = {subfieldValues: false}\n// eslint-disable-next-line max-statements\n}) => (base, source) => {\n const debug = createDebugLogger('@natlibfi/marc-record-merge:select');\n\n const {baseRecord, sourceRecord} = getRecordsFromParameters(base, source, baseValidators, sourceValidators);\n\n function getRecordsFromParameters(base, source, baseValidators, sourceValidators) {\n // records if we got an object ({base, source}) as a parameter\n if (source === undefined && base.base !== undefined && base.source !== undefined) {\n const baseRecord = new MarcRecord(base.base, baseValidators);\n const sourceRecord = new MarcRecord(base.source, sourceValidators);\n return {baseRecord, sourceRecord};\n }\n // records if we got an non-object (base, source) as a parameter\n const baseRecord = new MarcRecord(base, baseValidators);\n const sourceRecord = new MarcRecord(source, sourceValidators);\n return {baseRecord, sourceRecord};\n }\n\n const baseFields = baseRecord.get(tagPattern);\n const sourceFields = sourceRecord.get(tagPattern);\n const fieldTag = sourceFields.map(field => field.tag);\n debug(`Comparing field ${fieldTag}`);\n\n checkFieldType(baseFields);\n checkFieldType(sourceFields);\n\n if (baseFields.length > 1 || sourceFields.length > 1) {\n debug(`Multiple fields in base or source`);\n debug(`No changes to base`);\n return baseRecord.toObject();\n }\n const [baseField] = baseFields;\n const [sourceField] = sourceFields;\n\n if (baseField.tag === sourceField.tag === false) {\n debug(`Base tag ${baseField.tag} is not equal to source tag ${sourceField.tag}`);\n debug(`No changes to base`);\n return baseRecord.toObject();\n }\n const baseSubs = baseField.subfields;\n const sourceSubs = sourceField.subfields;\n\n const baseSubsNormalized = baseSubs\n .map(({code, value}) => ({code, value: normalizeSubfieldValue(value)}));\n\n const sourceSubsNormalized = sourceSubs\n .map(({code, value}) => ({code, value: normalizeSubfieldValue(value)}));\n\n // Returns the base subfields for which a matching source subfield is found\n const equalSubfieldsBase = baseSubsNormalized\n .filter(baseSubfield => sourceSubsNormalized\n .some(sourceSubfield => equalityFunction(baseSubfield, sourceSubfield)));\n debug(`equalSubfieldsBase: ${JSON.stringify(equalSubfieldsBase, undefined, 2)}`);\n\n // Returns the source subfields for which a matching base subfield is found\n const equalSubfieldsSource = sourceSubsNormalized\n .filter(sourceSubfield => baseSubsNormalized\n .some(baseSubfield => equalityFunction(sourceSubfield, baseSubfield)));\n debug(`equalSubfieldsSource: ${JSON.stringify(equalSubfieldsSource, undefined, 2)}`);\n\n if (baseSubs.length === sourceSubs.length && equalSubfieldsBase.length < baseSubs.length) {\n debug(`Base and source subfields are not equal`);\n debug(`No changes to base`);\n return baseRecord.toObject();\n }\n\n if (baseSubs.length === sourceSubs.length && equalSubfieldsBase.length === equalSubfieldsSource.length) {\n debug(`Checking subfield equality`);\n const totalSubfieldLengthBase = baseSubsNormalized\n .map(({value}) => value.length)\n .reduce((acc, value) => acc + value);\n const totalSubfieldLengthSource = sourceSubsNormalized\n .map(({value}) => value.length)\n .reduce((acc, value) => acc + value);\n\n if (totalSubfieldLengthSource > totalSubfieldLengthBase) {\n return replaceBasefieldWithSourcefield(baseRecord.toObject());\n }\n }\n\n if (sourceSubs.length > baseSubs.length && equalSubfieldsBase.length === baseSubs.length) {\n return replaceBasefieldWithSourcefield(baseRecord.toObject());\n }\n\n debug(`No changes to base`);\n return baseRecord.toObject();\n\n function replaceBasefieldWithSourcefield(base) {\n const index = base.fields.findIndex(field => field === baseField);\n base.fields.splice(index, 1, sourceField); // eslint-disable-line functional/immutable-data\n debug(`Source field is longer, replacing base with source`);\n return base;\n }\n\n function checkFieldType(fields) {\n const checkedFields = fields.map(field => {\n if ('value' in field) { // eslint-disable-line functional/no-conditional-statement\n throw new Error('Invalid control field, expected data field');\n }\n return field;\n });\n return checkedFields;\n }\n\n function normalizeSubfieldValue(value) {\n // Regexp options: g: global search, u: unicode\n const punctuation = /[.,\\-/#!?$%^&*;:{}=_`~()[\\]]/gu;\n return normalizeSync(value).toLowerCase().replace(punctuation, '', 'u').replace(/\\s+/gu, ' ').trim();\n }\n};\n"],"mappings":"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"}
@@ -0,0 +1,58 @@
1
+ "use strict";
2
+
3
+ var _chai = require("chai");
4
+ var _marcRecord = require("@natlibfi/marc-record");
5
+ var _select = _interopRequireWildcard(require("./select"));
6
+ var _fixura = require("@natlibfi/fixura");
7
+ var _fixugen = _interopRequireDefault(require("@natlibfi/fixugen"));
8
+ function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
9
+ function _getRequireWildcardCache(nodeInterop) { if (typeof WeakMap !== "function") return null; var cacheBabelInterop = new WeakMap(); var cacheNodeInterop = new WeakMap(); return (_getRequireWildcardCache = function (nodeInterop) { return nodeInterop ? cacheNodeInterop : cacheBabelInterop; })(nodeInterop); }
10
+ function _interopRequireWildcard(obj, nodeInterop) { if (!nodeInterop && obj && obj.__esModule) { return obj; } if (obj === null || typeof obj !== "object" && typeof obj !== "function") { return { default: obj }; } var cache = _getRequireWildcardCache(nodeInterop); if (cache && cache.has(obj)) { return cache.get(obj); } var newObj = {}; var hasPropertyDescriptor = Object.defineProperty && Object.getOwnPropertyDescriptor; for (var key in obj) { if (key !== "default" && Object.prototype.hasOwnProperty.call(obj, key)) { var desc = hasPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : null; if (desc && (desc.get || desc.set)) { Object.defineProperty(newObj, key, desc); } else { newObj[key] = obj[key]; } } } newObj.default = obj; if (cache) { cache.set(obj, newObj); } return newObj; }
11
+ _marcRecord.MarcRecord.setValidationOptions({
12
+ subfieldValues: false
13
+ });
14
+ (0, _fixugen.default)({
15
+ callback,
16
+ path: [__dirname, '..', '..', 'test-fixtures', 'reducers', 'select'],
17
+ useMetadataFile: true,
18
+ recurse: false,
19
+ fixura: {
20
+ reader: _fixura.READERS.JSON,
21
+ failWhenNotFound: false
22
+ }
23
+ });
24
+ function callback({
25
+ getFixture,
26
+ disabled = false,
27
+ tagPatternRegExp = false,
28
+ expectedError = false,
29
+ useSubsetEquality = false
30
+ }) {
31
+ if (disabled) {
32
+ console.log('TEST DISABLED!'); // eslint-disable-line no-console
33
+ return;
34
+ }
35
+ // const base = new MarcRecord(getFixture('base.json'), {subfieldValues: false});
36
+ // const source = new MarcRecord(getFixture('source.json'), {subfieldValues: false});
37
+
38
+ const base = getFixture('base.json');
39
+ const source = getFixture('source.json');
40
+ const tagPattern = new RegExp(tagPatternRegExp, 'u');
41
+ const expectedRecord = getFixture('merged.json');
42
+ const equalityFunction = useSubsetEquality ? _select.subsetEquality : undefined;
43
+
44
+ // Bypass expected error in testing
45
+ if (expectedError) {
46
+ (0, _chai.expect)(() => _select.default.to.throw(Error, 'control field'));
47
+ return;
48
+ }
49
+ const mergedRecord = (0, _select.default)({
50
+ tagPattern,
51
+ equalityFunction
52
+ })({
53
+ base,
54
+ source
55
+ });
56
+ (0, _chai.expect)(mergedRecord).to.eql(expectedRecord);
57
+ }
58
+ //# sourceMappingURL=select2.spec.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"select2.spec.js","names":["MarcRecord","setValidationOptions","subfieldValues","generateTests","callback","path","__dirname","useMetadataFile","recurse","fixura","reader","READERS","JSON","failWhenNotFound","getFixture","disabled","tagPatternRegExp","expectedError","useSubsetEquality","console","log","base","source","tagPattern","RegExp","expectedRecord","equalityFunction","subsetEquality","undefined","expect","createReducer","to","throw","Error","mergedRecord","eql"],"sources":["../../src/reducers/select2.spec.js"],"sourcesContent":["import {expect} from 'chai';\nimport {MarcRecord} from '@natlibfi/marc-record';\nimport createReducer, {subsetEquality} from './select';\nimport {READERS} from '@natlibfi/fixura';\nimport generateTests from '@natlibfi/fixugen';\n\nMarcRecord.setValidationOptions({subfieldValues: false});\n\ngenerateTests({\n callback,\n path: [__dirname, '..', '..', 'test-fixtures', 'reducers', 'select'],\n useMetadataFile: true,\n recurse: false,\n fixura: {\n reader: READERS.JSON,\n failWhenNotFound: false\n }\n});\n\nfunction callback({\n getFixture,\n disabled = false,\n tagPatternRegExp = false,\n expectedError = false,\n useSubsetEquality = false\n}) {\n if (disabled) {\n console.log('TEST DISABLED!'); // eslint-disable-line no-console\n return;\n }\n // const base = new MarcRecord(getFixture('base.json'), {subfieldValues: false});\n // const source = new MarcRecord(getFixture('source.json'), {subfieldValues: false});\n\n const base = getFixture('base.json');\n const source = getFixture('source.json');\n\n const tagPattern = new RegExp(tagPatternRegExp, 'u');\n const expectedRecord = getFixture('merged.json');\n const equalityFunction = useSubsetEquality ? subsetEquality : undefined;\n\n // Bypass expected error in testing\n if (expectedError) {\n expect(() => createReducer.to.throw(Error, 'control field'));\n return;\n }\n\n const mergedRecord = createReducer({tagPattern, equalityFunction})({base, source});\n expect(mergedRecord).to.eql(expectedRecord);\n}\n"],"mappings":";;AAAA;AACA;AACA;AACA;AACA;AAA8C;AAAA;AAAA;AAE9CA,sBAAU,CAACC,oBAAoB,CAAC;EAACC,cAAc,EAAE;AAAK,CAAC,CAAC;AAExD,IAAAC,gBAAa,EAAC;EACZC,QAAQ;EACRC,IAAI,EAAE,CAACC,SAAS,EAAE,IAAI,EAAE,IAAI,EAAE,eAAe,EAAE,UAAU,EAAE,QAAQ,CAAC;EACpEC,eAAe,EAAE,IAAI;EACrBC,OAAO,EAAE,KAAK;EACdC,MAAM,EAAE;IACNC,MAAM,EAAEC,eAAO,CAACC,IAAI;IACpBC,gBAAgB,EAAE;EACpB;AACF,CAAC,CAAC;AAEF,SAAST,QAAQ,CAAC;EAChBU,UAAU;EACVC,QAAQ,GAAG,KAAK;EAChBC,gBAAgB,GAAG,KAAK;EACxBC,aAAa,GAAG,KAAK;EACrBC,iBAAiB,GAAG;AACtB,CAAC,EAAE;EACD,IAAIH,QAAQ,EAAE;IACZI,OAAO,CAACC,GAAG,CAAC,gBAAgB,CAAC,CAAC,CAAC;IAC/B;EACF;EACA;EACA;;EAEA,MAAMC,IAAI,GAAGP,UAAU,CAAC,WAAW,CAAC;EACpC,MAAMQ,MAAM,GAAGR,UAAU,CAAC,aAAa,CAAC;EAExC,MAAMS,UAAU,GAAG,IAAIC,MAAM,CAACR,gBAAgB,EAAE,GAAG,CAAC;EACpD,MAAMS,cAAc,GAAGX,UAAU,CAAC,aAAa,CAAC;EAChD,MAAMY,gBAAgB,GAAGR,iBAAiB,GAAGS,sBAAc,GAAGC,SAAS;;EAEvE;EACA,IAAIX,aAAa,EAAE;IACjB,IAAAY,YAAM,EAAC,MAAMC,eAAa,CAACC,EAAE,CAACC,KAAK,CAACC,KAAK,EAAE,eAAe,CAAC,CAAC;IAC5D;EACF;EAEA,MAAMC,YAAY,GAAG,IAAAJ,eAAa,EAAC;IAACP,UAAU;IAAEG;EAAgB,CAAC,CAAC,CAAC;IAACL,IAAI;IAAEC;EAAM,CAAC,CAAC;EAClF,IAAAO,YAAM,EAACK,YAAY,CAAC,CAACH,EAAE,CAACI,GAAG,CAACV,cAAc,CAAC;AAC7C"}
package/package.json CHANGED
@@ -14,7 +14,7 @@
14
14
  "url": "git@github.com:natlibfi/marc-record-merge-js.git"
15
15
  },
16
16
  "license": "MIT",
17
- "version": "6.0.0-beta.10",
17
+ "version": "6.0.0-beta.11",
18
18
  "main": "./dist/index.js",
19
19
  "engines": {
20
20
  "node": ">=14"
@@ -25,8 +25,8 @@
25
25
  "prepublishOnly": "npm run build:transpile",
26
26
  "lint": "eslint ./src",
27
27
  "lint:dev": "eslint ./src --fix",
28
- "test:base": "cross-env NODE_ENV=test mocha --require @babel/register --reporter-option maxDiffSize=15000 src/reducers/*.spec.js",
29
- "test": "npm run lint && npm run test:base",
28
+ "test:base": "cross-env NODE_ENV=test mocha --require @babel/register --reporter-option maxDiffSize=15000",
29
+ "test": "npm run lint && npm run test:base -- --recursive src",
30
30
  "test:dev": "npm run lint:dev && npm run coverage",
31
31
  "coverage": "npm run coverage:unit && npm run coverage:report",
32
32
  "coverage:unit": "nyc --silent npm run test:base",
@@ -38,25 +38,25 @@
38
38
  },
39
39
  "dependencies": {
40
40
  "@natlibfi/fixugen": "1.1.0",
41
- "@natlibfi/fixura": "^2.2.1",
42
- "@natlibfi/marc-record": "^7.1.0-alpha.2",
41
+ "@natlibfi/fixura": "^2.2.5",
42
+ "@natlibfi/marc-record": "^7.2.2",
43
43
  "debug": "^4.3.4",
44
44
  "normalize-diacritics": "2.14.0"
45
45
  },
46
46
  "devDependencies": {
47
- "@babel/cli": "^7.17.10",
48
- "@babel/core": "^7.18.5",
49
- "@babel/eslint-parser": "^7.18.2",
50
- "@babel/preset-env": "^7.18.2",
51
- "@babel/register": "^7.17.7",
52
- "@natlibfi/eslint-config-melinda-backend": "^2.0.0",
47
+ "@babel/cli": "^7.19.3",
48
+ "@babel/core": "^7.19.6",
49
+ "@babel/eslint-parser": "^7.19.1",
50
+ "@babel/preset-env": "^7.19.4",
51
+ "@babel/register": "^7.18.9",
52
+ "@natlibfi/eslint-config-melinda-backend": "^2.0.1",
53
53
  "babel-plugin-istanbul": "^6.1.1",
54
54
  "babel-plugin-rewire": "^1.2.0",
55
55
  "chai": "^4.3.6",
56
56
  "cross-env": "^7.0.3",
57
- "eslint": "^8.17.0",
58
- "mocha": "^10.0.0",
59
- "nodemon": "^2.0.16",
57
+ "eslint": "^8.25.0",
58
+ "mocha": "^10.1.0",
59
+ "nodemon": "^2.0.20",
60
60
  "nyc": "^15.1.0"
61
61
  },
62
62
  "eslintConfig": {
package/src/index.js CHANGED
@@ -1,34 +1,54 @@
1
1
  import Reducers from './reducers';
2
+ import createDebugLogger from 'debug';
3
+
4
+ const debug = createDebugLogger('@natlibfi/melinda-marc-record-merge:index');
5
+ const debugData = debug.extend('data');
2
6
 
3
7
  export {Reducers};
4
8
  // export default ({base, source, reducers}) => reducers.reduce((base, reducer) => reducer(base, source), base);
5
9
 
6
10
  // NV: Modified the reducer loop so, that not only base, but also is carried back.
7
11
  // However, we try to be backward-compatible: normally after the reducers, only base is returned.
8
- export default ({base, source, reducers}) => {
9
- const combo = {base, source}; // eslint-disable-line functional/no-let
10
12
 
11
- reducers.reduce((combo, reducer) => {
12
- combo = singleRound(reducer, combo.base, combo.source); // eslint-disable-line no-param-reassign
13
+ export default ({base, source, reducers}) => {
13
14
 
14
- return combo;
15
+ const combo = {base, source};
16
+ const resultCombo = reducers.reduce((combo, reducer) => {
17
+ const returnCombo = singleRound(reducer, combo.base, combo.source);
18
+ //debugData(`returnCombo after current reducer: ${JSON.stringify(returnCombo)}`);
19
+ return returnCombo;
15
20
  }, combo);
16
21
 
22
+ debugData(`ResultCombo after reducers: ${JSON.stringify(resultCombo)}`);
23
+
17
24
  // Hack to make my melinda-marc-record-merge-reducers single tests that expect both
18
25
  // base and source to return them both:
19
- if (reducers.length === 1 && combo.base && combo.source) {
20
- return combo;
26
+ if (reducers.length === 1 && resultCombo.base && resultCombo.source) {
27
+ debug('Single reducer, returning resultCombo');
28
+ debugData(JSON.stringify(resultCombo));
29
+
30
+ return resultCombo;
21
31
  }
22
32
  // All other tests return just base... Backward (compability) it is!
23
- return combo.base;
33
+ debug('Multiple reducers, returning just base');
34
+ debugData(JSON.stringify(resultCombo.base));
35
+ return resultCombo.base;
24
36
 
25
37
  function singleRound(reducer, base, source) {
26
- const combo = reducer(base, source);
27
- if (combo.base !== undefined && combo.source !== undefined) {
28
- //console.info('NEW STYLE REDUCER RESULT v2'); // eslint-disable-line no-console
38
+ //debug(`SINGLE ROUND INPUT (base, source)`);
39
+ //debugData(base);
40
+ //debugData(base);
41
+ const reducerResult = reducer(base, source);
42
+ //debug(`reducerResult:`);
43
+ //debugData(reducerResult);
44
+ if (reducerResult.base !== undefined && reducerResult.source !== undefined) {
45
+ debug('NEW STYLE REDUCER RESULT v2');
46
+ const combo = reducerResult;
47
+ //debugData(combo);
29
48
  return combo;
30
49
  }
31
- //console.info('OLD SCHOOL REDUCER RESULT v2'); // eslint-disable-line no-console
32
- return {base: combo.base, source};
50
+ debug('OLD SCHOOL REDUCER RESULT v2');
51
+ //debugData({base: reducerResult, source});
52
+ return {base: reducerResult, source};
33
53
  }
34
54
  };
@@ -0,0 +1,45 @@
1
+ import merger, {Reducers} from './index';
2
+ import {inspect} from 'util';
3
+ import createDebugLogger from 'debug';
4
+ import {expect} from 'chai';
5
+ import {MarcRecord} from '@natlibfi/marc-record';
6
+ import {READERS} from '@natlibfi/fixura';
7
+ import generateTests from '@natlibfi/fixugen';
8
+
9
+ generateTests({
10
+ callback,
11
+ path: [__dirname, '..', 'test-fixtures', 'index'],
12
+ recurse: false,
13
+ useMetadataFile: true,
14
+ fixura: {
15
+ failWhenNotFound: false,
16
+ reader: READERS.JSON
17
+ }
18
+ });
19
+
20
+ function callback({getFixture, reducerConfigs = []}) {
21
+ const base = new MarcRecord(getFixture('base.json'), {subfieldValues: false});
22
+ const source = new MarcRecord(getFixture('source.json'), {subfieldValues: false});
23
+ const expectedRecord = getFixture('merged.json');
24
+
25
+ const debug = createDebugLogger('@natlibfi/melinda-marc-record-merge-reducers:index:test');
26
+ const debugData = debug.extend('data');
27
+
28
+ const testReducerConfigs = reducerConfigs;
29
+ const reducers = [...testReducerConfigs.map(conf => Reducers.copy(conf))];
30
+
31
+ debugData(`Reducers: ${inspect(reducers, {colors: true, maxArrayLength: 10, depth: 8})})}`);
32
+
33
+ const result = merger({base, source, reducers});
34
+
35
+ debug(`Merge result is: ${result.constructor.name}`);
36
+ debugData(`${JSON.stringify(result)}`);
37
+
38
+ // Use either result.base or a plain result as resultRecord
39
+ // It can also be a MarcRecord or a plain object
40
+ const resultRecord = result.base || result;
41
+ const resultRecordToRecord = new MarcRecord(resultRecord, {subfieldValues: false});
42
+ expect(resultRecordToRecord.toObject()).to.eql(expectedRecord);
43
+
44
+
45
+ }
@@ -21,13 +21,30 @@ export default ({
21
21
  swapSubfieldCode = [],
22
22
  doNotCopyIfFieldPresent = false
23
23
  }) => (base, source) => {
24
- const baseRecord = new MarcRecord(base, baseValidators);
25
- const sourceRecord = new MarcRecord(source, sourceValidators);
26
24
 
27
- const debug = createDebugLogger('@natlibfi/marc-record-merge');
25
+ const debug = createDebugLogger('@natlibfi/marc-record-merge:copy');
26
+ const debugData = debug.extend('data');
28
27
  const debugOptions = createDebugLogger('@natlibfi/marc-record-merge:compare-options');
29
28
  const debugCompare = createDebugLogger('@natlibfi/marc-record-merge:compare');
30
29
 
30
+ debugData(`base: ${JSON.stringify(base)}`);
31
+ debugData(`source: ${JSON.stringify(source)}`);
32
+
33
+ const {baseRecord, sourceRecord} = getRecordsFromParameters(base, source, baseValidators, sourceValidators);
34
+
35
+ function getRecordsFromParameters(base, source, baseValidators, sourceValidators) {
36
+ // records if we got an object ({base, source}) as a parameter
37
+ if (source === undefined && base.base !== undefined && base.source !== undefined) {
38
+ const baseRecord = new MarcRecord(base.base, baseValidators);
39
+ const sourceRecord = new MarcRecord(base.source, sourceValidators);
40
+ return {baseRecord, sourceRecord};
41
+ }
42
+ // records if we got an non-object (base, source) as a parameter
43
+ const baseRecord = new MarcRecord(base, baseValidators);
44
+ const sourceRecord = new MarcRecord(source, sourceValidators);
45
+ return {baseRecord, sourceRecord};
46
+ }
47
+
31
48
  const ignoreInd1 = compareWithoutIndicators || compareWithoutIndicator1;
32
49
  const ignoreInd2 = compareWithoutIndicators || compareWithoutIndicator2;
33
50
 
@@ -64,6 +81,8 @@ export default ({
64
81
 
65
82
  // Add fields to base;
66
83
  uniqueFields.forEach(field => baseRecord.insertField(field));
84
+ debugData(`baseRecord before return: ${JSON.stringify(baseRecord)}`);
85
+ //return baseRecord;
67
86
  return baseRecord.toObject();
68
87
 
69
88
  function compareFields(sourceFields, baseCompareFields, uniqFields = []) {
@@ -0,0 +1,55 @@
1
+ import {expect} from 'chai';
2
+ import {READERS} from '@natlibfi/fixura';
3
+ import createReducer from './copy';
4
+ import generateTests from '@natlibfi/fixugen';
5
+
6
+ //import createDebugLogger from 'debug'; // <---
7
+ //const debug = createDebugLogger('@natlibfi/marc-record-merge/copy.spec.js'); // <---
8
+
9
+ generateTests({
10
+ callback,
11
+ path: [__dirname, '..', '..', 'test-fixtures', 'reducers', 'copy'],
12
+ useMetadataFile: true,
13
+ recurse: true,
14
+ fixura: {
15
+ reader: READERS.JSON,
16
+ failWhenNotFound: false
17
+ }
18
+ });
19
+
20
+
21
+ function callback({
22
+ getFixture,
23
+ tagPatternRegExp,
24
+ compareTagsOnly = false,
25
+ compareWithoutTag = false,
26
+ compareWithoutIndicators = false,
27
+ compareWithoutIndicator1 = false,
28
+ compareWithoutIndicator2 = false,
29
+ subfieldsMustBeIdentical = false,
30
+ copyUnless = undefined,
31
+ excludeSubfields = undefined,
32
+ dropSubfields = undefined,
33
+ swapSubfieldCode = [],
34
+ swapTag = [],
35
+ doNotCopyIfFieldPresent = false
36
+ }) {
37
+ const base = getFixture('base.json');
38
+ const source = getFixture('source.json');
39
+ const tagPattern = new RegExp(tagPatternRegExp, 'u');
40
+ const expectedRecord = getFixture('merged.json');
41
+
42
+ const merged = createReducer({
43
+ tagPattern, compareTagsOnly, compareWithoutTag, compareWithoutIndicators, compareWithoutIndicator1, compareWithoutIndicator2,
44
+ copyUnless, subfieldsMustBeIdentical, excludeSubfields,
45
+ dropSubfields, swapSubfieldCode, swapTag,
46
+ doNotCopyIfFieldPresent
47
+ })({base, source});
48
+ //debug(`*** mergedRecord: `, mergedRecord); //<--
49
+ //debug(`*** mergedRecord,Strfy: `, JSON.stringify(mergedRecord)); //<--
50
+ //debug(`*** expectedRecord: `, expectedRecord); //<--
51
+ //debug(`*** expectedRecord,Strfy: `, JSON.stringify(expectedRecord)); //<--
52
+ expect(merged.constructor.name).not.to.eql('MarcRecord');
53
+ expect(merged.constructor.name).to.eql('Object');
54
+ expect(merged).to.eql(expectedRecord);
55
+ }
@@ -12,10 +12,31 @@ export function subsetEquality(subfieldA, subfieldB) {
12
12
  (subfieldA.value.indexOf(subfieldB.value) !== -1 || subfieldB.value.indexOf(subfieldA.value) !== -1);
13
13
  }
14
14
  // EqualityFunction can be either strictEquality or subsetEquality
15
- export default ({tagPattern, equalityFunction = strictEquality}) => (base, source) => {
15
+
16
+ export default ({
17
+ tagPattern,
18
+ equalityFunction = strictEquality,
19
+ baseValidators = {subfieldValues: false},
20
+ sourceValidators = {subfieldValues: false}
21
+ // eslint-disable-next-line max-statements
22
+ }) => (base, source) => {
16
23
  const debug = createDebugLogger('@natlibfi/marc-record-merge:select');
17
- const baseRecord = new MarcRecord(base, {subfieldValues: false});
18
- const sourceRecord = new MarcRecord(source, {subfieldValues: false});
24
+
25
+ const {baseRecord, sourceRecord} = getRecordsFromParameters(base, source, baseValidators, sourceValidators);
26
+
27
+ function getRecordsFromParameters(base, source, baseValidators, sourceValidators) {
28
+ // records if we got an object ({base, source}) as a parameter
29
+ if (source === undefined && base.base !== undefined && base.source !== undefined) {
30
+ const baseRecord = new MarcRecord(base.base, baseValidators);
31
+ const sourceRecord = new MarcRecord(base.source, sourceValidators);
32
+ return {baseRecord, sourceRecord};
33
+ }
34
+ // records if we got an non-object (base, source) as a parameter
35
+ const baseRecord = new MarcRecord(base, baseValidators);
36
+ const sourceRecord = new MarcRecord(source, sourceValidators);
37
+ return {baseRecord, sourceRecord};
38
+ }
39
+
19
40
  const baseFields = baseRecord.get(tagPattern);
20
41
  const sourceFields = sourceRecord.get(tagPattern);
21
42
  const fieldTag = sourceFields.map(field => field.tag);
@@ -27,7 +48,7 @@ export default ({tagPattern, equalityFunction = strictEquality}) => (base, sourc
27
48
  if (baseFields.length > 1 || sourceFields.length > 1) {
28
49
  debug(`Multiple fields in base or source`);
29
50
  debug(`No changes to base`);
30
- return base;
51
+ return baseRecord.toObject();
31
52
  }
32
53
  const [baseField] = baseFields;
33
54
  const [sourceField] = sourceFields;
@@ -35,7 +56,7 @@ export default ({tagPattern, equalityFunction = strictEquality}) => (base, sourc
35
56
  if (baseField.tag === sourceField.tag === false) {
36
57
  debug(`Base tag ${baseField.tag} is not equal to source tag ${sourceField.tag}`);
37
58
  debug(`No changes to base`);
38
- return base;
59
+ return baseRecord.toObject();
39
60
  }
40
61
  const baseSubs = baseField.subfields;
41
62
  const sourceSubs = sourceField.subfields;
@@ -61,7 +82,7 @@ export default ({tagPattern, equalityFunction = strictEquality}) => (base, sourc
61
82
  if (baseSubs.length === sourceSubs.length && equalSubfieldsBase.length < baseSubs.length) {
62
83
  debug(`Base and source subfields are not equal`);
63
84
  debug(`No changes to base`);
64
- return base;
85
+ return baseRecord.toObject();
65
86
  }
66
87
 
67
88
  if (baseSubs.length === sourceSubs.length && equalSubfieldsBase.length === equalSubfieldsSource.length) {
@@ -74,16 +95,16 @@ export default ({tagPattern, equalityFunction = strictEquality}) => (base, sourc
74
95
  .reduce((acc, value) => acc + value);
75
96
 
76
97
  if (totalSubfieldLengthSource > totalSubfieldLengthBase) {
77
- return replaceBasefieldWithSourcefield(base);
98
+ return replaceBasefieldWithSourcefield(baseRecord.toObject());
78
99
  }
79
100
  }
80
101
 
81
102
  if (sourceSubs.length > baseSubs.length && equalSubfieldsBase.length === baseSubs.length) {
82
- return replaceBasefieldWithSourcefield(base);
103
+ return replaceBasefieldWithSourcefield(baseRecord.toObject());
83
104
  }
84
105
 
85
106
  debug(`No changes to base`);
86
- return base;
107
+ return baseRecord.toObject();
87
108
 
88
109
  function replaceBasefieldWithSourcefield(base) {
89
110
  const index = base.fields.findIndex(field => field === baseField);
@@ -0,0 +1,49 @@
1
+ import {expect} from 'chai';
2
+ import {MarcRecord} from '@natlibfi/marc-record';
3
+ import createReducer, {subsetEquality} from './select';
4
+ import {READERS} from '@natlibfi/fixura';
5
+ import generateTests from '@natlibfi/fixugen';
6
+
7
+ MarcRecord.setValidationOptions({subfieldValues: false});
8
+
9
+ generateTests({
10
+ callback,
11
+ path: [__dirname, '..', '..', 'test-fixtures', 'reducers', 'select'],
12
+ useMetadataFile: true,
13
+ recurse: false,
14
+ fixura: {
15
+ reader: READERS.JSON,
16
+ failWhenNotFound: false
17
+ }
18
+ });
19
+
20
+ function callback({
21
+ getFixture,
22
+ disabled = false,
23
+ tagPatternRegExp = false,
24
+ expectedError = false,
25
+ useSubsetEquality = false
26
+ }) {
27
+ if (disabled) {
28
+ console.log('TEST DISABLED!'); // eslint-disable-line no-console
29
+ return;
30
+ }
31
+ // const base = new MarcRecord(getFixture('base.json'), {subfieldValues: false});
32
+ // const source = new MarcRecord(getFixture('source.json'), {subfieldValues: false});
33
+
34
+ const base = getFixture('base.json');
35
+ const source = getFixture('source.json');
36
+
37
+ const tagPattern = new RegExp(tagPatternRegExp, 'u');
38
+ const expectedRecord = getFixture('merged.json');
39
+ const equalityFunction = useSubsetEquality ? subsetEquality : undefined;
40
+
41
+ // Bypass expected error in testing
42
+ if (expectedError) {
43
+ expect(() => createReducer.to.throw(Error, 'control field'));
44
+ return;
45
+ }
46
+
47
+ const mergedRecord = createReducer({tagPattern, equalityFunction})({base, source});
48
+ expect(mergedRecord).to.eql(expectedRecord);
49
+ }
@@ -0,0 +1,24 @@
1
+ {
2
+ "leader": "01331cam a22003494i 4500",
3
+ "fields": [
4
+ {
5
+ "tag": "001",
6
+ "value": "001_base"
7
+ },
8
+ {
9
+ "tag": "010",
10
+ "ind1": " ",
11
+ "ind2": " ",
12
+ "subfields": [
13
+ {
14
+ "code": "a",
15
+ "value": "010a_base"
16
+ },
17
+ {
18
+ "code": "b",
19
+ "value": "010b_base"
20
+ }
21
+ ]
22
+ }
23
+ ]
24
+ }
@@ -0,0 +1,24 @@
1
+ {
2
+ "leader": "01331cam a22003494i 4500",
3
+ "fields": [
4
+ {
5
+ "tag": "001",
6
+ "value": "001_base"
7
+ },
8
+ {
9
+ "tag": "010",
10
+ "ind1": " ",
11
+ "ind2": " ",
12
+ "subfields": [
13
+ {
14
+ "code": "a",
15
+ "value": "010a_base"
16
+ },
17
+ {
18
+ "code": "b",
19
+ "value": "010b_base"
20
+ }
21
+ ]
22
+ }
23
+ ]
24
+ }
@@ -0,0 +1,8 @@
1
+ {
2
+ "description":"Reducers should run after each another - two reducers",
3
+ "reducerConfigs": [
4
+ {"tagPattern": "/010/u", "compareTagsOnly": true},
5
+ {"tagPattern": "/33./u"}
6
+
7
+ ]
8
+ }
@@ -0,0 +1,40 @@
1
+ {
2
+ "leader": "01331cam a22003494i 4500",
3
+ "fields": [
4
+ {
5
+ "tag": "001",
6
+ "value": "001_sorsa"
7
+ },
8
+ {
9
+ "tag": "010",
10
+ "ind1": " ",
11
+ "ind2": " ",
12
+ "subfields": [
13
+ {
14
+ "code": "a",
15
+ "value": "010a_sorsa"
16
+ },
17
+ {
18
+ "code": "b",
19
+ "value": "010b_sorsa"
20
+ }
21
+ ]
22
+ },
23
+ {
24
+ "tag": "650",
25
+ "ind1": " ",
26
+ "ind2": "7",
27
+ "subfields": [
28
+ {
29
+ "code": "a",
30
+ "value": "poista mut"
31
+ },
32
+ {
33
+ "code": "2",
34
+ "value": "ysa"
35
+ }
36
+ ]
37
+ }
38
+
39
+ ]
40
+ }
@@ -0,0 +1,24 @@
1
+ {
2
+ "leader": "01331cam a22003494i 4500",
3
+ "fields": [
4
+ {
5
+ "tag": "001",
6
+ "value": "001_base"
7
+ },
8
+ {
9
+ "tag": "010",
10
+ "ind1": " ",
11
+ "ind2": " ",
12
+ "subfields": [
13
+ {
14
+ "code": "a",
15
+ "value": "010a_base"
16
+ },
17
+ {
18
+ "code": "b",
19
+ "value": "010b_base"
20
+ }
21
+ ]
22
+ }
23
+ ]
24
+ }
@@ -0,0 +1,24 @@
1
+ {
2
+ "leader": "01331cam a22003494i 4500",
3
+ "fields": [
4
+ {
5
+ "tag": "001",
6
+ "value": "001_base"
7
+ },
8
+ {
9
+ "tag": "010",
10
+ "ind1": " ",
11
+ "ind2": " ",
12
+ "subfields": [
13
+ {
14
+ "code": "a",
15
+ "value": "010a_base"
16
+ },
17
+ {
18
+ "code": "b",
19
+ "value": "010b_base"
20
+ }
21
+ ]
22
+ }
23
+ ]
24
+ }
@@ -0,0 +1,7 @@
1
+ {
2
+ "description":"Reducers should run after each another - single reducer",
3
+ "reducerConfigs": [
4
+ {"tagPattern": "/33./u"}
5
+ ],
6
+ "skip": false
7
+ }
@@ -0,0 +1,40 @@
1
+ {
2
+ "leader": "01331cam a22003494i 4500",
3
+ "fields": [
4
+ {
5
+ "tag": "001",
6
+ "value": "001_sorsa"
7
+ },
8
+ {
9
+ "tag": "010",
10
+ "ind1": " ",
11
+ "ind2": " ",
12
+ "subfields": [
13
+ {
14
+ "code": "a",
15
+ "value": "010a_sorsa"
16
+ },
17
+ {
18
+ "code": "b",
19
+ "value": "010b_sorsa"
20
+ }
21
+ ]
22
+ },
23
+ {
24
+ "tag": "650",
25
+ "ind1": " ",
26
+ "ind2": "7",
27
+ "subfields": [
28
+ {
29
+ "code": "a",
30
+ "value": "poista mut"
31
+ },
32
+ {
33
+ "code": "2",
34
+ "value": "ysa"
35
+ }
36
+ ]
37
+ }
38
+
39
+ ]
40
+ }