diff --git a/src/components/playground/Playground/Playground.js b/src/components/playground/Playground/Playground.js index 1a28f3a..0f86406 100644 --- a/src/components/playground/Playground/Playground.js +++ b/src/components/playground/Playground/Playground.js @@ -55,9 +55,8 @@ class Playground extends Component { .addCondition(specs, realIndex, Boolean(position)) .then(() => this.setState({ - chunks: this.core.getChunks(), isEditingAtIndex: null, - regexChunks: this.core.getRegexChunks(), + ...this.core.getChunksState(), }) ) .catch(err => Promise.reject(err)) @@ -79,10 +78,9 @@ class Playground extends Component { .deleteCondition(index) .then(() => this.setState({ - chunks: this.core.getChunks(), isEditingAtIndex: null, - regexChunks: this.core.getRegexChunks(), sentenceEl: null, + ...this.core.getChunksState(), }) ) .catch(err => Promise.reject(err)) diff --git a/src/lib/core/core.js b/src/lib/core/core.js index a8ba36f..7b3a7f8 100644 --- a/src/lib/core/core.js +++ b/src/lib/core/core.js @@ -1,7 +1,9 @@ import { anchors, characters } from "./data" import conditionAdders from "./condition-adders" import { - getAnchorsWithoutUsedEdges, + getAvailableAnchors, + getAvailableBackReferences, + getAvailableDefaultCharacters, insertNewChunk, updateExistingChunk, } from "./utils" @@ -42,20 +44,18 @@ async function addCondition(specs, insertAtIndex = 0, newItem = true) { const insertChunk = newItem ? insertNewChunk : updateExistingChunk this.chunks = insertChunk(this.chunks, insertAtIndex, chunk) - this.regexChunks = this.chunks.map(({ regex }) => regex) - this.capturedChunks = this.chunks.reduce((acc, { regex, specs }, index) => { - const key = `\\${acc.length + 1}` - return specs.capturedExpression === "YES" - ? acc.concat({ index, label: regex, key, regex: key }) - : acc - }, []) - return Promise.resolve() } catch (err) { return Promise.reject(err) } } +function deleteAllConditions() { + this.chunks = [] + this.regexChunks = [] + this.capturedChunks = [] +} + function deleteCondition(targetIndex) { if (!this.chunks[targetIndex]) { return Promise.reject( @@ -64,76 +64,36 @@ function deleteCondition(targetIndex) { } this.chunks = this.chunks.filter((chunk, index) => targetIndex !== index) - this.regexChunks = this.chunks.map(({ regex }) => regex) return Promise.resolve() } -function getAvailableAnchors(targetIndex, position) { - const chunksLength = this.chunks.length - - if (!chunksLength) return Array.from(anchors) - - const data = getAnchorsWithoutUsedEdges(this.chunks, anchors, [ - "STARTS_WITH", - "ENDS_WITH", - ]) - - if (position === "before") { - return targetIndex === 0 - ? data.filter(item => item.key !== "ENDS_WITH") - : data.filter(item => item.key === "CONTAINS") - } else if (position === "after") { - return targetIndex === chunksLength - 1 - ? data.filter(item => item.key !== "STARTS_WITH") - : data.filter(item => item.key === "CONTAINS") - } - - return data.filter(item => item.key === "CONTAINS") -} - function getAvailableData(targetIndex, position) { return { - availableAnchors: this.getAvailableAnchors(targetIndex, position), - availableBackReferences: this.getAvailableBackReferences( + availableAnchors: getAvailableAnchors.call(this, targetIndex, position), + availableBackReferences: getAvailableBackReferences.call( + this, targetIndex, position ), - availableDefaultCharacters: this.getAvailableDefaultCharacters( + availableDefaultCharacters: getAvailableDefaultCharacters.call( + this, targetIndex, position ), } } -function getAvailableBackReferences(targetIndex, position) { - if (targetIndex < 0) return [] - - return this.capturedChunks.filter( - chunk => - (!position && chunk.index < targetIndex) || - (position === "before" && chunk.index < targetIndex) || - (position === "after" && chunk.index <= targetIndex) - ) -} - -function getAvailableDefaultCharacters(targetIndex, position) { - return !this.getAvailableBackReferences(targetIndex, position).length - ? characters.DEFAULT.filter(item => item.key !== "BACK_REFERENCES") - : characters.DEFAULT -} - -function getChunks() { - return Array.from(this.chunks) +function getChunksState() { + return { + chunks: Array.from(this.chunks), + regexChunks: Array.from(this.regexChunks), + } } function getFlags() { return JSON.parse(JSON.stringify(this.flags)) } -function getRegexChunks() { - return Array.from(this.regexChunks) -} - function setFlag(entry, value) { this.flags = { ...this.flags, @@ -141,30 +101,44 @@ function setFlag(entry, value) { } } -function deleteAllConditions() { - this.chunks = [] - this.regexChunks = [] - this.capturedChunks = [] +function execFuncWhileSyncChunksArrays(fn, args) { + return fn + .apply(this, args) + .then(() => { + this.regexChunks = this.chunks.map(({ regex }) => regex) + this.capturedChunks = this.chunks.reduce( + (acc, { regex, specs }, index) => { + const key = `\\${acc.length + 1}` + return specs.capturedExpression === "YES" + ? acc.concat({ index, label: regex, key, regex: key }) + : acc + }, + [] + ) + + return Promise.resolve() + }) + .catch(err => Promise.reject(err)) } const core = { - addCondition, + addCondition: function() { + return execFuncWhileSyncChunksArrays.call(this, addCondition, arguments) + }, + deleteCondition: function() { + return execFuncWhileSyncChunksArrays.call(this, deleteCondition, arguments) + }, capturedChunks: [], chunks: [], - deleteCondition, + deleteAllConditions, flags: { global: false, }, - getAvailableAnchors, - getAvailableBackReferences, getAvailableData, - getAvailableDefaultCharacters, - getChunks, + getChunksState, getFlags, - getRegexChunks, regexChunks: [], setFlag, - deleteAllConditions, } export default core diff --git a/src/lib/core/core.spec.js b/src/lib/core/core.spec.js index e63fad2..35f99c7 100644 --- a/src/lib/core/core.spec.js +++ b/src/lib/core/core.spec.js @@ -22,9 +22,9 @@ describe("Core", () => { const core = Object.create(Core) expect(core).toBeTruthy() - expect(core.getChunks()).toEqual([]) + expect(core.getChunksState().chunks).toEqual([]) expect(core.getFlags().global).toEqual(false) - expect(core.getRegexChunks()).toEqual([]) + expect(core.getChunksState().regexChunks).toEqual([]) }) it("add condition", async () => { @@ -32,8 +32,8 @@ describe("Core", () => { await core.addCondition(condition1) - expect(core.getChunks().length).toEqual(1) - expect(core.getRegexChunks().length).toEqual(1) + expect(core.getChunksState().chunks.length).toEqual(1) + expect(core.getChunksState().regexChunks.length).toEqual(1) const wrongCondition = { ...condition2, @@ -41,8 +41,8 @@ describe("Core", () => { } core.addCondition(wrongCondition).catch(() => { - expect(core.getChunks().length).toEqual(1) - expect(core.getRegexChunks().length).toEqual(1) + expect(core.getChunksState().chunks.length).toEqual(1) + expect(core.getChunksState().regexChunks.length).toEqual(1) }) }) @@ -52,8 +52,8 @@ describe("Core", () => { await core.addCondition(condition1) await core.addCondition(condition1, 0, false) - expect(core.getChunks().length).toEqual(1) - expect(core.getRegexChunks().length).toEqual(1) + expect(core.getChunksState().chunks.length).toEqual(1) + expect(core.getChunksState().regexChunks.length).toEqual(1) }) it("delete condition", async () => { @@ -65,12 +65,12 @@ describe("Core", () => { await core.deleteCondition(1) await core.deleteCondition(0) - expect(core.getChunks().length).toEqual(0) - expect(core.getRegexChunks().length).toEqual(0) + expect(core.getChunksState().chunks.length).toEqual(0) + expect(core.getChunksState().regexChunks.length).toEqual(0) core.deleteCondition(42).catch(() => { - expect(core.getChunks().length).toEqual(0) - expect(core.getRegexChunks().length).toEqual(0) + expect(core.getChunksState().chunks.length).toEqual(0) + expect(core.getChunksState().regexChunks.length).toEqual(0) }) }) @@ -85,22 +85,28 @@ describe("Core", () => { await core.addCondition(condition1) await core.addCondition(condition2) - expect(joinKeys(core.getAvailableAnchors(0, "before"))).toEqual( - "CONTAINS-STARTS_WITH" + expect( + joinKeys(core.getAvailableData(0, "before").availableAnchors) + ).toEqual("CONTAINS-STARTS_WITH") + expect( + joinKeys(core.getAvailableData(1, "before").availableAnchors) + ).toEqual("CONTAINS") + + expect( + joinKeys(core.getAvailableData(0, "after").availableAnchors) + ).toEqual("CONTAINS") + expect( + joinKeys(core.getAvailableData(1, "after").availableAnchors) + ).toEqual("CONTAINS-ENDS_WITH") + + expect(joinKeys(core.getAvailableData(0).availableAnchors)).toEqual( + "CONTAINS" ) - expect(joinKeys(core.getAvailableAnchors(1, "before"))).toEqual("CONTAINS") - - expect(joinKeys(core.getAvailableAnchors(0, "after"))).toEqual("CONTAINS") - expect(joinKeys(core.getAvailableAnchors(1, "after"))).toEqual( - "CONTAINS-ENDS_WITH" - ) - - expect(joinKeys(core.getAvailableAnchors(0))).toEqual("CONTAINS") await core.deleteCondition(1) await core.deleteCondition(0) - expect(joinKeys(core.getAvailableAnchors(0))).toEqual( + expect(joinKeys(core.getAvailableData(0).availableAnchors)).toEqual( "CONTAINS-ENDS_WITH-STARTS_WITH" ) }) diff --git a/src/lib/core/utils.js b/src/lib/core/utils.js index 15a5248..6424cd4 100644 --- a/src/lib/core/utils.js +++ b/src/lib/core/utils.js @@ -1,4 +1,6 @@ -export const getAnchorsWithoutUsedEdges = (dataSource, anchors, edges) => { +import { anchors, characters } from "./data" + +const getAnchorsWithoutUsedEdges = (dataSource, anchors, edges) => { return edges.reduce( (acc, anchor) => dataSource.some(({ specs }) => specs.anchor === anchor) @@ -8,6 +10,46 @@ export const getAnchorsWithoutUsedEdges = (dataSource, anchors, edges) => { ) } +export function getAvailableAnchors(targetIndex, position) { + const chunksLength = this.chunks.length + + if (!chunksLength) return Array.from(anchors) + + const data = getAnchorsWithoutUsedEdges(this.chunks, anchors, [ + "STARTS_WITH", + "ENDS_WITH", + ]) + + if (position === "before") { + return targetIndex === 0 + ? data.filter(item => item.key !== "ENDS_WITH") + : data.filter(item => item.key === "CONTAINS") + } else if (position === "after") { + return targetIndex === chunksLength - 1 + ? data.filter(item => item.key !== "STARTS_WITH") + : data.filter(item => item.key === "CONTAINS") + } + + return data.filter(item => item.key === "CONTAINS") +} + +export function getAvailableBackReferences(targetIndex, position) { + if (targetIndex < 0) return [] + + return this.capturedChunks.filter( + chunk => + (!position && chunk.index < targetIndex) || + (position === "before" && chunk.index < targetIndex) || + (position === "after" && chunk.index <= targetIndex) + ) +} + +export function getAvailableDefaultCharacters(targetIndex, position) { + return !getAvailableBackReferences.call(this, targetIndex, position).length + ? characters.DEFAULT.filter(item => item.key !== "BACK_REFERENCES") + : characters.DEFAULT +} + export const getLabelFromKey = (dataSource, targetKey, withCap = false) => { const { label } = dataSource.find(({ key }) => targetKey === key) || {}