@prismicio/babel-transform-config
Advanced tools
Comparing version 0.0.6-alpha.ea631c8 to 0.0.6
export default { | ||
mode: "universal", | ||
mode: 'universal', | ||
head: { | ||
title: process.env.npm_package_name || "", | ||
meta: [{ | ||
charset: "utf-8" | ||
title: process.env.npm_package_name || '', | ||
meta: [ | ||
{ | ||
charset: 'utf-8' | ||
}, | ||
{ | ||
name: "viewport", | ||
content: "width=device-width, initial-scale=1" | ||
name: 'viewport', | ||
content: 'width=device-width, initial-scale=1' | ||
}, | ||
{ | ||
hid: "description", | ||
name: "description", | ||
content: process.env.npm_package_description || "" | ||
hid: 'description', | ||
name: 'description', | ||
content: process.env.npm_package_description || '' | ||
} | ||
], | ||
link: [{ | ||
rel: "icon", | ||
type: "image/x-icon", | ||
href: "/favicon.ico" | ||
}], | ||
link: [ | ||
{ | ||
rel: 'icon', | ||
type: 'image/x-icon', | ||
href: '/favicon.ico' | ||
} | ||
], | ||
script: [] | ||
}, | ||
loading: { | ||
color: "#fff" | ||
color: '#fff' | ||
}, | ||
@@ -34,3 +37,3 @@ modules: [], | ||
extend(config, ctx) {} | ||
}, | ||
} | ||
}; |
export default { | ||
mode: "universal", | ||
mode: 'universal', | ||
css: [], | ||
@@ -4,0 +4,0 @@ modules: ['@org/my-nuxt-module'], |
export default { | ||
mode: "universal", | ||
mode: 'universal', | ||
head: { | ||
@@ -11,3 +11,6 @@ script: [] | ||
}, | ||
deleteMeMaybe: true | ||
delete: { | ||
deleteMeMaybe: [true] | ||
}, | ||
deleteMeMaybe: [true] | ||
}; |
@@ -1,20 +0,21 @@ | ||
const fs = require('fs') | ||
const path = require('path') | ||
const transformConfig = require('../') | ||
const fs = require('fs'); | ||
const path = require('path'); | ||
const transformConfig = require('../'); | ||
const code = fs.readFileSync(path.join(process.cwd(), 'examples/configs/nuxt.simple.js'), 'utf8') | ||
const code = fs.readFileSync( | ||
path.join(__dirname, 'configs', 'nuxt.simple.js'), | ||
'utf8' | ||
); | ||
const args = { | ||
css: ['path/to/file'], | ||
modules: [ | ||
['my-module', { config: true }] | ||
], | ||
modules: [['my-module', { config: true }]], | ||
transpile: ['my-other-module'] | ||
} | ||
}; | ||
const { code: updated } = transformConfig(code, 'nuxt', args) | ||
const { code: updated } = transformConfig(code, 'nuxt', args); | ||
console.log('previous code:\n', code) | ||
console.log('previous code:\n', code); | ||
console.log('passed args: ', JSON.stringify(args), '\n') | ||
console.log('new code:\n', updated) | ||
console.log('passed args: ', JSON.stringify(args), '\n'); | ||
console.log('new code:\n', updated); |
@@ -1,27 +0,37 @@ | ||
const fs = require('fs') | ||
const path = require('path') | ||
const transformCode = require('../').transform | ||
const fs = require('fs'); | ||
const path = require('path'); | ||
const transformCode = require('../').transform; | ||
const code = fs.readFileSync(path.join(process.cwd(), 'examples/configs/nuxt.trans.js'), 'utf8') | ||
const code = fs.readFileSync( | ||
path.join(__dirname, 'configs', 'nuxt.trans.js'), | ||
'utf8' | ||
); | ||
const transforms = { | ||
'head:script': { // create or replace export default { head: { script: [] }} | ||
'head:script': { | ||
// create or replace export default { head: { script: [] }} | ||
action: 'create:replace', | ||
value: ['my/script.js'] | ||
}, | ||
'deleteMeMaybe': { // delete export default { deleteMe: ... } | ||
'delete:deleteMeMaybe': { | ||
// delete export default { deleteMe: ... } | ||
action: 'delete' | ||
}, | ||
'build:transpile': { // merges export default { babel: { transpile: arrayOrObject } } | ||
deleteMeMaybe: { | ||
// delete export default { deleteMe: ... } | ||
action: 'delete' | ||
}, | ||
'build:transpile': { | ||
// merges export default { babel: { transpile: arrayOrObject } } | ||
action: 'merge:create', | ||
value: ['path/to/file'] | ||
} | ||
} | ||
}; | ||
const { code: updated } = transformCode(code, transforms) | ||
const { code: updated } = transformCode(code, transforms); | ||
console.log('previous code:\n', code) | ||
console.log('previous code:\n', code); | ||
console.log('passed transform args: ', JSON.stringify(transforms), '\n') | ||
console.log('passed transform args: ', JSON.stringify(transforms), '\n'); | ||
console.log('new code:\n', updated) | ||
console.log('new code:\n', updated); |
144
index.js
@@ -1,5 +0,5 @@ | ||
const consola = require('consola') | ||
const babelTransform = require('@babel/standalone').transform | ||
const consola = require('consola'); | ||
const babelTransform = require('@babel/standalone').transform; | ||
const babelTransformConfigPlugin = require('./plugin') | ||
const babelTransformConfigPlugin = require('./plugin'); | ||
@@ -9,56 +9,76 @@ const nuxt = { | ||
// arr of strings | ||
return ['css', { | ||
action: 'create:merge', | ||
value | ||
}] | ||
return [ | ||
'css', | ||
{ | ||
action: 'create:merge', | ||
value | ||
} | ||
]; | ||
}, | ||
script(value) { | ||
// arr of objects or strings | ||
return ['head:script', { | ||
action: 'create:merge', | ||
value | ||
}] | ||
return [ | ||
'head:script', | ||
{ | ||
action: 'create:merge', | ||
value | ||
} | ||
]; | ||
}, | ||
module(value) { | ||
return ['modules', { | ||
action: 'create:merge', | ||
value: [value] | ||
}] | ||
return [ | ||
'modules', | ||
{ | ||
action: 'create:merge', | ||
value: [value] | ||
} | ||
]; | ||
}, | ||
modules(value) { | ||
return ['modules', { | ||
action: 'create:merge', | ||
value | ||
}] | ||
return [ | ||
'modules', | ||
{ | ||
action: 'create:merge', | ||
value | ||
} | ||
]; | ||
}, | ||
transpile(value) { | ||
return ['build:transpile', { | ||
action: 'create:merge', | ||
value | ||
}] | ||
return [ | ||
'build:transpile', | ||
{ | ||
action: 'create:merge', | ||
value | ||
} | ||
]; | ||
}, | ||
libraries(value) { | ||
return ['build:transpile', { | ||
action: 'create:merge', | ||
value | ||
}] | ||
return [ | ||
'build:transpile', | ||
{ | ||
action: 'create:merge', | ||
value | ||
} | ||
]; | ||
} | ||
} | ||
const table = { nuxt } | ||
}; | ||
const table = { nuxt }; | ||
function createTransformArgs(framework, args, strict) { | ||
const frameworkTable = table[framework] | ||
const keysNotFound = [] | ||
if (!frameworkTable) { | ||
throw new Error(`[transform-configs] ${framework} Framework not supported\nUse babel plugin directly instead`) | ||
if (!table.hasOwnProperty(framework)) { | ||
throw new Error( | ||
`[transform-configs] ${framework} Framework not supported\nUse babel plugin directly instead` | ||
); | ||
} | ||
const frameworkTable = table[framework]; | ||
const keysNotFound = []; | ||
const transforms = Object.entries(args).reduce((acc, [k, v]) => { | ||
if (frameworkTable[k]) { | ||
const [key, value] = frameworkTable[k](v) | ||
const [key, value] = frameworkTable[k](v); | ||
return { | ||
...acc, | ||
[key]: value | ||
} | ||
}; | ||
} | ||
keysNotFound.push(k) | ||
keysNotFound.push(k); | ||
if (!strict) { | ||
@@ -68,13 +88,13 @@ return { | ||
[k]: { | ||
action: "create:merge", | ||
action: 'create:merge', | ||
value: v | ||
} | ||
} | ||
}; | ||
} | ||
return acc | ||
}, {}) | ||
return acc; | ||
}, {}); | ||
return { | ||
transforms, | ||
keysNotFound | ||
} | ||
}; | ||
} | ||
@@ -84,31 +104,31 @@ | ||
return babelTransform(code, { | ||
plugins: [ | ||
[ | ||
babelTransformConfigPlugin, | ||
transforms | ||
] | ||
] | ||
}) // { code } or Throws error | ||
plugins: [[babelTransformConfigPlugin, transforms]] | ||
}); // { code } or Throws error | ||
} | ||
function handleKeysNotFound(keys) { | ||
keys.forEach((key) => { | ||
consola.warn(`[transform-args] Key "${key}" not recognized.\nDefaulting to default transform`) | ||
}) | ||
keys.forEach(key => { | ||
consola.warn( | ||
`[transform-args] Key "${key}" not recognized.\nDefaulting to default transform` | ||
); | ||
}); | ||
} | ||
function transformConfig(code, framework, args, strict = true) { | ||
try { | ||
const { | ||
transforms, | ||
keysNotFound, | ||
} = createTransformArgs(framework, args, strict) | ||
const { transforms, keysNotFound } = createTransformArgs( | ||
framework, | ||
args, | ||
strict | ||
); | ||
if (!transforms) { | ||
return consola.error(reason) | ||
if (JSON.stringify(transforms) === '{}') { | ||
return consola.error('No transforms performed'); | ||
} | ||
if (!strict && keysNotFound.length) { | ||
handleKeysNotFound(keysNotFound); | ||
} | ||
return transform(code, transforms) | ||
} catch(e) { | ||
return transform(code, transforms); | ||
} catch (e) { | ||
consola.error(e.message); | ||
@@ -118,5 +138,5 @@ } | ||
transformConfig.transform = transform | ||
transformConfig.plugin = babelTransformConfigPlugin | ||
transformConfig.transform = transform; | ||
transformConfig.plugin = babelTransformConfigPlugin; | ||
module.exports = transformConfig | ||
module.exports = transformConfig; |
{ | ||
"name": "@prismicio/babel-transform-config", | ||
"version": "0.0.6-alpha.ea631c8", | ||
"version": "0.0.6", | ||
"description": "Transform JS config files (Next, Nuxt, Gatsby)", | ||
"main": "index.js", | ||
"scripts": { | ||
"test": "echo \"Error: no test specified\" && exit 1" | ||
"lint": "eslint --ext .js,.ts .", | ||
"jest": "jest", | ||
"test": "yarn lint && yarn jest" | ||
}, | ||
@@ -23,12 +25,29 @@ "keywords": [ | ||
"dependencies": { | ||
"@babel/core": "^7.8.7", | ||
"@babel/plugin-syntax-jsx": "^7.8.3", | ||
"@babel/plugin-transform-arrow-functions": "^7.8.3", | ||
"@babel/plugin-transform-runtime": "^7.8.3", | ||
"@babel/preset-env": "^7.8.7", | ||
"@babel/standalone": "^7.8.8", | ||
"@babel/template": "^7.8.6", | ||
"@babel/traverse": "^7.8.6", | ||
"consola": "^2.11.3" | ||
} | ||
"@babel/core": "^7.11.6", | ||
"@babel/plugin-syntax-jsx": "^7.10.4", | ||
"@babel/plugin-transform-arrow-functions": "^7.10.4", | ||
"@babel/plugin-transform-runtime": "^7.11.5", | ||
"@babel/preset-env": "^7.11.5", | ||
"@babel/standalone": "^7.11.6", | ||
"@babel/template": "^7.10.4", | ||
"@babel/traverse": "^7.11.5", | ||
"consola": "^2.15.0" | ||
}, | ||
"devDependencies": { | ||
"jest": "^26.4.2", | ||
"babel-eslint": "^10.1.0", | ||
"eslint": "^7.10.0", | ||
"eslint-config-prettier": "^6.12.0", | ||
"eslint-loader": "^4.0.2", | ||
"eslint-plugin-prettier": "^3.1.4", | ||
"prettier": "^2.1.2" | ||
}, | ||
"repository": { | ||
"type": "git", | ||
"url": "git+https://github.com/prismicio/babel-transform-config.git" | ||
}, | ||
"bugs": { | ||
"url": "https://github.com/prismicio/babel-transform-config/issues" | ||
}, | ||
"homepage": "https://github.com/prismicio/babel-transform-config#readme" | ||
} |
@@ -21,7 +21,9 @@ const Operations = require('./operations'); | ||
const [headList, last] = ArrayHelpers.splitAtLast(nodes); | ||
const formattedNodes = headList.map(k => _formatNode(k, null)).concat([_formatNode(last, value)]); | ||
const formattedNodes = headList | ||
.map(k => _formatNode(k, null)) | ||
.concat([_formatNode(last, value)]); | ||
return { | ||
nodes: formattedNodes, | ||
ops | ||
} | ||
}; | ||
} | ||
@@ -31,8 +33,11 @@ | ||
validate(key, action, value) { | ||
if (!action || !action.length) { | ||
throw new Error(`Transformation with key "${key}" should possess a non-empty "action" key`) | ||
throw new Error( | ||
`Transformation with key "${key}" should possess a non-empty "action" key` | ||
); | ||
} | ||
if (action.indexOf(Operations.delete) === -1 && value === undefined) { | ||
throw new Error(`Transformation with key "${key}" should possess a non-empty "value" key`) | ||
throw new Error( | ||
`Transformation with key "${key}" should possess a non-empty "value" key` | ||
); | ||
} | ||
@@ -46,6 +51,5 @@ | ||
convertToTree(action) { | ||
function toNodes(entries, ops) /* Node[] */ { | ||
const [head, tail] = ArrayHelpers.splitAtHead(entries); | ||
if(!head) return []; | ||
if (!head) return []; | ||
@@ -57,6 +61,4 @@ return [new Node(head.key, head.value, toNodes(tail, ops), ops)]; | ||
return new Tree( | ||
new Root(headNodes) | ||
); | ||
return new Tree(new Root(headNodes)); | ||
} | ||
} | ||
}; |
@@ -10,4 +10,4 @@ const consola = require('consola'); | ||
return Object.entries(transforms).map(([key, transform]) => { | ||
return Actions.validate(key, transform.action, transform.value) | ||
}) | ||
return Actions.validate(key, transform.action, transform.value); | ||
}); | ||
} | ||
@@ -20,40 +20,50 @@ | ||
const currentData = namedParent && parentData && parentData.nextNodes.find(n => n.key === namedParent); | ||
const currentData = | ||
namedParent && | ||
parentData && | ||
parentData.nextNodes.find(n => n.key === namedParent); | ||
if(currentData) { | ||
if (currentData) { | ||
// detect and create missing nodes | ||
const childrenKeys = path.node.properties.map(node => node.key.name); | ||
const missingKeys = ArrayHelpers.diff(currentData.nextNodes.map(n => n.key), childrenKeys); | ||
if(missingKeys.length) { | ||
missingKeys.forEach(key => { | ||
const newObjectProperty = globalTypes.ObjectProperty( | ||
globalTypes.identifier(key), | ||
toAst(globalTypes, {}) | ||
); | ||
const missingKeys = ArrayHelpers.diff( | ||
currentData.nextNodes.map(n => n.key), | ||
childrenKeys | ||
); | ||
missingKeys.forEach(key => { | ||
const newObjectProperty = globalTypes.ObjectProperty( | ||
globalTypes.identifier(key), | ||
toAst(globalTypes, {}) | ||
); | ||
path.node.properties = [ | ||
...path.node.properties, | ||
newObjectProperty | ||
]; | ||
}); | ||
} | ||
path.node.properties = [...path.node.properties, newObjectProperty]; | ||
}); | ||
// update current node if needed | ||
if(currentData.ops.includes(Operations.delete && !currentData.value) && !currentData.nextNodes.length) { | ||
path.remove(); | ||
} else if(currentData.value && currentData.ops.includes(Operations.merge)) { | ||
if(path.node.value) { | ||
if ( | ||
currentData.ops.includes(Operations.delete) && | ||
!currentData.value && | ||
!currentData.nextNodes.length | ||
) { | ||
path.parentPath.remove(); | ||
} else if ( | ||
currentData.value && | ||
currentData.ops.includes(Operations.merge) | ||
) { | ||
if (path.node.value) { | ||
const { type } = path.node.value; | ||
switch(type) { | ||
switch (type) { | ||
case 'ArrayExpression': | ||
const elements = path.node.elements.concat(toAst(globalTypes, currentData.value).elements); | ||
const updated = Object.assign({}, path.node, { elements }); | ||
path.replaceWithMultiple([ | ||
updated | ||
]); | ||
const elements = path.node.elements.concat( | ||
toAst(globalTypes, currentData.value).elements | ||
); | ||
const updatedArray = Object.assign({}, path.node, { elements }); | ||
path.replaceWithMultiple([updatedArray]); | ||
break; | ||
default: | ||
const properties = path.node.properties.concat(toAst(globalTypes, currentData.value).properties); | ||
const updated = Object.assign({}, path.node, { properties }); | ||
path.replaceWith(updated); | ||
const properties = path.node.properties.concat( | ||
toAst(globalTypes, currentData.value).properties | ||
); | ||
const updatedObj = Object.assign({}, path.node, { properties }); | ||
path.replaceWith(updatedObj); | ||
} | ||
@@ -63,3 +73,7 @@ } else { | ||
} | ||
} else if(currentData.value && (currentData.ops.includes(Operations.replace) || currentData.ops.includes(Operations.create))) { | ||
} else if ( | ||
currentData.value && | ||
(currentData.ops.includes(Operations.replace) || | ||
currentData.ops.includes(Operations.create)) | ||
) { | ||
path.replaceWith(toAst(globalTypes, currentData.value)); | ||
@@ -70,3 +84,23 @@ } | ||
path.skip(); | ||
path.traverse(nodeVisitor, { nodeData: currentData, globalTypes }) | ||
path.traverse(nodeVisitor, { nodeData: currentData, globalTypes }); | ||
} else if ( | ||
!namedParent && | ||
path.parent.type === 'ExportDefaultDeclaration' | ||
) { | ||
// Create missing nodes when at root | ||
const childrenKeys = path.node.properties.map(node => node.key.name); | ||
const missingNodes = parentData.nextNodes.filter( | ||
node => childrenKeys.indexOf(node.key) === -1 | ||
); | ||
if (missingNodes) { | ||
missingNodes.forEach(nodeData => { | ||
const newObjectProperty = globalTypes.ObjectProperty( | ||
globalTypes.identifier(nodeData.key), | ||
toAst(globalTypes, {}) | ||
); | ||
path.node.properties = [...path.node.properties, newObjectProperty]; | ||
}); | ||
} | ||
} | ||
@@ -78,17 +112,29 @@ }, | ||
const currentData = namedParent && parentData && parentData.nextNodes.find(n => n.key === namedParent); | ||
const currentData = | ||
namedParent && | ||
parentData && | ||
parentData.nextNodes.find(n => n.key === namedParent); | ||
// update current node if needed | ||
if(currentData) { | ||
if(currentData.ops.includes(Operations.delete && !currentData.value) && !currentData.nextNodes.length) { | ||
path.remove(); | ||
} else if(currentData.value && currentData.ops.includes(Operations.merge)) { | ||
const elements = path.node.elements.concat(toAst(globalTypes, currentData.value).elements); | ||
const updated = Object.assign({}, path.node, { elements }); | ||
path.replaceWithMultiple([ | ||
updated | ||
]); | ||
} else if(currentData.value && (currentData.ops.includes(Operations.replace) || currentData.ops.includes(Operations.create))) { | ||
path.replaceWithMultiple([ | ||
toAst(globalTypes, currentData.value) | ||
]); | ||
if (currentData) { | ||
if ( | ||
currentData.ops.includes(Operations.delete) && | ||
!currentData.value && | ||
!currentData.nextNodes.length | ||
) { | ||
path.parentPath.remove(); | ||
return; | ||
} else if (currentData.value) { | ||
if (currentData.ops.includes(Operations.merge)) { | ||
const elements = path.node.elements.concat( | ||
toAst(globalTypes, currentData.value).elements | ||
); | ||
const updated = Object.assign({}, path.node, { elements }); | ||
path.replaceWithMultiple([updated]); | ||
} else if ( | ||
currentData.ops.includes(Operations.replace) || | ||
currentData.ops.includes(Operations.create) | ||
) { | ||
path.replaceWithMultiple([toAst(globalTypes, currentData.value)]); | ||
} | ||
} | ||
@@ -101,5 +147,5 @@ | ||
} | ||
} | ||
}; | ||
module.exports = function({ types: globalTypes }, transforms) { | ||
module.exports = function ({ types: globalTypes }, transforms) { | ||
const validActions = validateTransforms(transforms); | ||
@@ -109,3 +155,3 @@ const data = validActions | ||
.reduce((accTree, actionTree) => { | ||
return accTree.combine(actionTree) | ||
return accTree.combine(actionTree); | ||
}, Trees.empty()); | ||
@@ -121,2 +167,2 @@ | ||
}; | ||
} | ||
}; |
const SEPARATOR = ':'; | ||
const Operations = { | ||
const OPERATIONS = { | ||
create: 'create', | ||
@@ -10,5 +10,7 @@ merge: 'merge', | ||
module.exports = { | ||
...Operations, | ||
...OPERATIONS, | ||
toString: () => { | ||
return Object.entries(Operations).map(([, v]) => v).join(' | '); | ||
return Object.entries(OPERATIONS) | ||
.map(([, v]) => v) | ||
.join(' | '); | ||
}, | ||
@@ -18,15 +20,29 @@ toList: (strOperations, value) => { | ||
operations.forEach((op) => { | ||
if (!Operations[op]) { | ||
throw new Error(`Operation "${op}" does not exist.\nDefined operations: ${Operations.toString()}`) | ||
operations.forEach(op => { | ||
if (!OPERATIONS[op]) { | ||
throw new Error( | ||
`Operation "${op}" does not exist.\nDefined operations: ${OPERATIONS.toString()}` | ||
); | ||
} | ||
}) | ||
if (operations.includes(Operations.merge) && operations.includes(Operations.replace)) { | ||
throw new Error('Operations "merge" and "update" cannot coexist in transform\'s "action" property') | ||
}); | ||
if ( | ||
operations.includes(OPERATIONS.merge) && | ||
operations.includes(OPERATIONS.replace) | ||
) { | ||
throw new Error( | ||
'Operations "merge" and "update" cannot coexist in transform\'s "action" property' | ||
); | ||
} | ||
if (operations.includes(Operations.create) && operations.includes(Operations.delete)) { | ||
throw new Error('Operations "create" and "delete" cannot coexist in transform\'s "action" property') | ||
if ( | ||
operations.includes(OPERATIONS.create) && | ||
operations.includes(OPERATIONS.delete) | ||
) { | ||
throw new Error( | ||
'Operations "create" and "delete" cannot coexist in transform\'s "action" property' | ||
); | ||
} | ||
if (operations.includes(Operations.merge) && !Array.isArray(value)) { | ||
throw new Error('Operations "merge" expects value to be of type "Array" (tested with Array.isArray)') | ||
if (operations.includes(OPERATIONS.merge) && !Array.isArray(value)) { | ||
throw new Error( | ||
'Operations "merge" expects value to be of type "Array" (tested with Array.isArray)' | ||
); | ||
} | ||
@@ -33,0 +49,0 @@ |
@@ -1,9 +0,11 @@ | ||
const babylon = require('@babel/parser') | ||
const babylon = require('@babel/parser'); | ||
const babelPluginTransformRuntime = require("@babel/plugin-transform-runtime").default; | ||
const babelPluginTransformArrowFunction = require("@babel/plugin-transform-arrow-functions").default; | ||
const babelPluginTransformRuntime = require('@babel/plugin-transform-runtime') | ||
.default; | ||
const babelPluginTransformArrowFunction = require('@babel/plugin-transform-arrow-functions') | ||
.default; | ||
function toAst(t, elem) { | ||
if (elem === null) { | ||
return t.nullLiteral() | ||
return t.nullLiteral(); | ||
} | ||
@@ -14,4 +16,4 @@ if (Array.isArray(elem)) { | ||
if (typeof elem === 'object') { | ||
const expression = t.objectExpression(Object.entries(elem) | ||
.reduce((acc, [key, value]) => { | ||
const expression = t.objectExpression( | ||
Object.entries(elem).reduce((acc, [key, value]) => { | ||
if (typeof value !== 'undefined') { | ||
@@ -21,8 +23,9 @@ const property = t.objectProperty( | ||
toAst(t, value) | ||
) | ||
return [...acc, property] | ||
); | ||
return [...acc, property]; | ||
} | ||
return acc | ||
}, [])) | ||
return expression | ||
return acc; | ||
}, []) | ||
); | ||
return expression; | ||
} | ||
@@ -38,8 +41,8 @@ switch (typeof elem) { | ||
const { params, body } = ast.program.body[0]; | ||
return t.functionExpression(null, params, body) | ||
case "number": | ||
return t.numericLiteral(elem) | ||
case "string": | ||
return t.stringLiteral(elem) | ||
case "boolean": | ||
return t.functionExpression(null, params, body); | ||
case 'number': | ||
return t.numericLiteral(elem); | ||
case 'string': | ||
return t.stringLiteral(elem); | ||
case 'boolean': | ||
return t.booleanLiteral(elem); | ||
@@ -49,2 +52,2 @@ } | ||
module.exports = toAst | ||
module.exports = toAst; |
@@ -9,13 +9,18 @@ const ArrayHelpers = require('./utils').ArrayHelpers; | ||
combine(/* Tree */other) { | ||
const mergedNodes = ArrayHelpers.flatten(other.root.nextNodes.map(otherNode => { | ||
const matchedNode = this.root.nextNodes.find(({ key }) => key === otherNode.key); | ||
if(matchedNode) return matchedNode.combine(otherNode); | ||
else return otherNode; | ||
})); | ||
combine(/* Tree */ other) { | ||
const mergedNodes = ArrayHelpers.flatten( | ||
other.root.nextNodes.map(otherNode => { | ||
const matchedNode = this.root.nextNodes.find( | ||
({ key }) => key === otherNode.key | ||
); | ||
if (matchedNode) return matchedNode.combine(otherNode); | ||
else return otherNode; | ||
}) | ||
); | ||
const mergedKeys = mergedNodes.map(({ key }) => key); | ||
const mergedKeys = mergedNodes.filter(n => n).map(({ key }) => key); | ||
const allNodes = this.root.nextNodes | ||
.filter(n => !mergedKeys.includes(n.keys)) | ||
.concat(mergedNodes); | ||
.filter(n => !mergedKeys.includes(n.key)) | ||
.concat(mergedNodes) | ||
.filter(n => n); | ||
@@ -27,3 +32,3 @@ return new Tree(new Root(allNodes)); | ||
class _TreeNode { | ||
constructor(/*Node[] */nextNodes) { | ||
constructor(/*Node[] */ nextNodes) { | ||
this.nextNodes = nextNodes; | ||
@@ -34,3 +39,3 @@ } | ||
class Root extends _TreeNode { | ||
constructor(/*Node[] */nextNodes) { | ||
constructor(/*Node[] */ nextNodes) { | ||
super(nextNodes); | ||
@@ -41,3 +46,8 @@ } | ||
class Node extends _TreeNode { | ||
constructor(/* string */key, /* any */value, /*Node[] */nextNodes, /* Operation[] */ ops) { | ||
constructor( | ||
/* string */ key, | ||
/* any */ value, | ||
/*Node[] */ nextNodes, | ||
/* Operation[] */ ops | ||
) { | ||
super(nextNodes); | ||
@@ -49,22 +59,38 @@ this.key = key; | ||
combine(/* Node */other) /* Node[] */ { | ||
if(this.key === node.key) { | ||
combine(/* Node */ other) /* Node[] */ { | ||
if (this.key === other.key) { | ||
const merged = (() => { | ||
const combinedOps = ArrayHelpers.distinct(this.ops, other.ops, (op1, op2) => op1 === op2); | ||
const combinedOps = ArrayHelpers.distinct( | ||
this.ops, | ||
other.ops, | ||
(op1, op2) => op1 === op2 | ||
); | ||
const finalValue = (() => { | ||
if(combinedOps.includes(Operations.delete)) return null; | ||
else { | ||
if(this.value && other.value) { | ||
if(Array.isArray(this.value)) return this.value.concat(other.value); | ||
else return Object.assign({}, this.value, other.value); | ||
} else return this.value || other.value; | ||
if (combinedOps.includes(Operations.delete)) { | ||
return null; | ||
} else { | ||
if (this.value && other.value) { | ||
if (Array.isArray(this.value)) { | ||
return this.value.concat(other.value); | ||
} else { | ||
return Object.assign({}, this.value, other.value); | ||
} | ||
} else { | ||
return this.value || other.value; | ||
} | ||
} | ||
})(); | ||
new Node( | ||
return new Node( | ||
this.key, | ||
finalValue, | ||
ArrayHelpers.distinct(this.nextNodes, other.nextNodes, (node1, node2) => node1.key === node2.key), | ||
ArrayHelpers.distinct( | ||
this.nextNodes, | ||
other.nextNodes, | ||
(node1, node2) => node1.key === node2.key | ||
), | ||
combinedOps | ||
) | ||
); | ||
})(); | ||
return [merged]; | ||
@@ -81,3 +107,3 @@ } else { | ||
} | ||
} | ||
}; | ||
@@ -84,0 +110,0 @@ module.exports = { |
const ArrayHelpers = { | ||
splitAtLast(array) { | ||
if(!array) return null; | ||
if (!array) return null; | ||
switch(array.length) { | ||
case 0: return [[], null]; | ||
case 1: return [[], array[0]]; | ||
default: return [array.slice(0, -1), array[array.length - 1]] | ||
switch (array.length) { | ||
case 0: | ||
return [[], null]; | ||
case 1: | ||
return [[], array[0]]; | ||
default: | ||
return [array.slice(0, -1), array[array.length - 1]]; | ||
} | ||
@@ -13,8 +16,11 @@ }, | ||
splitAtHead(array) { | ||
if(!array) return null; | ||
if (!array) return null; | ||
switch(array.length) { | ||
case 0: return [null, []]; | ||
case 1: return [array[0], []]; | ||
default: return [array[0], array.slice(1)] | ||
switch (array.length) { | ||
case 0: | ||
return [null, []]; | ||
case 1: | ||
return [array[0], []]; | ||
default: | ||
return [array[0], array.slice(1)]; | ||
} | ||
@@ -24,6 +30,13 @@ }, | ||
combine(array1, array2, mergeFn) { | ||
const [main, other] = array1.length > array2.length ? [array2, array1] : [array1, array2]; | ||
// FIXME: Behaving really weirdly / not used | ||
const [main, other] = | ||
array1.length > array2.length ? [array2, array1] : [array1, array2]; | ||
return main | ||
.map((value, index) => mergeFn(value, other[index])) | ||
.concat(other.slice(main.length, other.length).map(value => mergeFn(undefined, value))) | ||
.map((value, index) => mergeFn(value, other[index])) | ||
.concat( | ||
other | ||
.slice(main.length, other.length) | ||
.map(value => mergeFn(undefined, value)) | ||
); | ||
}, | ||
@@ -36,16 +49,22 @@ | ||
distinct(arr1, arr2, predicate) { | ||
this.flatten( | ||
this.combine(arr1, arr2, (item1, item2) => predicate(item1, item2) ? [item1] : [item1, item2]) | ||
); | ||
return arr1.concat(arr2).reduce((acc, current) => { | ||
for (const item of acc) { | ||
if (predicate(item, current)) { | ||
return acc; | ||
} | ||
} | ||
acc.push(current); | ||
return acc; | ||
}, []); | ||
}, | ||
diff(array1, array2) { | ||
return array1.filter(function(elm) { | ||
return array1.filter(function (elm) { | ||
return array2.indexOf(elm) === -1; | ||
}) | ||
}); | ||
} | ||
} | ||
}; | ||
module.exports = { | ||
ArrayHelpers | ||
} | ||
}; |
Major refactor
Supply chain riskPackage has recently undergone a major refactor. It may be unstable or indicate significant internal changes. Use caution when updating to versions that include significant changes.
Found 1 instance in 1 package
New author
Supply chain riskA new npm collaborator published a version of the package for the first time. New collaborators are usually benign additions to a project, but do indicate a change to the security surface area of a package.
Found 1 instance in 1 package
No bug tracker
MaintenancePackage does not have a linked bug tracker in package.json.
Found 1 instance in 1 package
No repository
Supply chain riskPackage does not have a linked source code repository. Without this field, a package will have no reference to the location of the source code use to generate the package.
Found 1 instance in 1 package
No tests
QualityPackage does not have any tests. This is a strong signal of a poorly maintained or low quality package.
Found 1 instance in 1 package
No website
QualityPackage does not have a website.
Found 1 instance in 1 package
41612
22
1116
0
1
2
7
2
Updated@babel/core@^7.11.6
Updated@babel/preset-env@^7.11.5
Updated@babel/standalone@^7.11.6
Updated@babel/template@^7.10.4
Updated@babel/traverse@^7.11.5
Updatedconsola@^2.15.0