@domql/element 2.3.154 → 2.4.1

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.
Files changed (48) hide show
  1. package/LICENSE +21 -0
  2. package/cache/index.js +3 -0
  3. package/create.js +21 -35
  4. package/dist/cjs/applyParam.js +41 -0
  5. package/dist/cjs/create.js +262 -0
  6. package/dist/cjs/define.js +34 -0
  7. package/dist/cjs/extend.js +87 -0
  8. package/dist/cjs/index.js +44 -0
  9. package/dist/cjs/iterate.js +108 -0
  10. package/dist/cjs/node.js +85 -0
  11. package/dist/cjs/package.json +4 -0
  12. package/dist/cjs/set.js +58 -0
  13. package/dist/cjs/tree.js +31 -0
  14. package/dist/cjs/update.js +223 -0
  15. package/index.js +2 -12
  16. package/iterate.js +1 -1
  17. package/methods/index.js +165 -0
  18. package/methods/set.js +41 -0
  19. package/{methods.js → methods/v2.js} +1 -7
  20. package/mixins/attr.js +23 -0
  21. package/mixins/classList.js +48 -0
  22. package/{remove.js → mixins/content.js} +19 -2
  23. package/mixins/data.js +21 -0
  24. package/mixins/html.js +20 -0
  25. package/mixins/index.js +23 -0
  26. package/mixins/registry.js +66 -0
  27. package/mixins/state.js +20 -0
  28. package/mixins/style.js +14 -0
  29. package/mixins/text.js +41 -0
  30. package/node.js +2 -2
  31. package/package.json +14 -6
  32. package/props/create.js +60 -0
  33. package/props/ignore.js +3 -0
  34. package/props/index.js +6 -0
  35. package/props/inherit.js +34 -0
  36. package/props/update.js +17 -0
  37. package/set.js +4 -6
  38. package/test/create.test.js +61 -0
  39. package/test/set.test.js +13 -0
  40. package/test/update.test.js +13 -0
  41. package/tree.js +11 -0
  42. package/update.js +5 -7
  43. package/utils/component.js +112 -0
  44. package/utils/extendUtils.js +118 -0
  45. package/utils/index.js +5 -0
  46. package/utils/object.js +141 -0
  47. package/parse.js +0 -17
  48. /package/{options.js → cache/options.js} +0 -0
@@ -0,0 +1,34 @@
1
+ 'use strict'
2
+
3
+ import { exec, is, isString } from '@domql/utils'
4
+
5
+ const objectizeStringProperty = propValue => {
6
+ if (is(propValue)('string', 'number')) {
7
+ return { inheritedString: propValue }
8
+ }
9
+ return propValue
10
+ }
11
+
12
+ export const inheritParentProps = (element, parent) => {
13
+ let propsStack = []
14
+ const parentProps = exec(parent, parent.state).props
15
+
16
+ const matchParent = parent.props && parentProps[element.key]
17
+ const matchParentIsString = isString(matchParent)
18
+ const matchParentChildProps = parentProps && parentProps.childProps
19
+
20
+ if (matchParent) {
21
+ if (matchParentIsString) {
22
+ const inheritedStringExists = propsStack.filter(v => v.inheritedString)[0]
23
+ if (inheritedStringExists) inheritedStringExists.inheritedString = matchParent
24
+ else {
25
+ propsStack = [].concat(objectizeStringProperty(matchParent), propsStack)
26
+ }
27
+ } else {
28
+ propsStack.push(objectizeStringProperty(matchParent))
29
+ }
30
+ }
31
+ if (matchParentChildProps) propsStack.push(matchParentChildProps)
32
+
33
+ return propsStack
34
+ }
@@ -0,0 +1,17 @@
1
+ 'use strict'
2
+
3
+ import { syncProps } from './create'
4
+ import { inheritParentProps } from './inherit'
5
+
6
+ export const updateProps = (newProps, element, parent) => {
7
+ const { __ref } = element
8
+ let propsStack = __ref.__props
9
+
10
+ const parentProps = inheritParentProps(element, parent)
11
+ if (parentProps) propsStack = __ref.__props = [].concat(parentProps, propsStack)
12
+ if (newProps) propsStack = __ref.__props = [].concat(newProps, propsStack)
13
+
14
+ if (propsStack) syncProps(propsStack, element)
15
+
16
+ return element
17
+ }
package/set.js CHANGED
@@ -1,20 +1,18 @@
1
1
  'use strict'
2
2
 
3
3
  import { isEqualDeep } from '@domql/utils'
4
- import { removeContentElement } from './remove'
5
4
 
6
5
  import create from './create'
6
+ import OPTIONS from './cache/options'
7
7
  import { registry } from './mixins'
8
- import OPTIONS from './options'
8
+ import { removeContent } from './mixins/content'
9
9
 
10
10
  const set = function (params, options = {}, el) {
11
11
  const element = el || this
12
12
  const __contentRef = element.content && element.content.__ref
13
13
 
14
- const isEqual = isEqualDeep(params, element.content)
15
- // console.error(params)
16
- if (isEqual && __contentRef && __contentRef.__cached) return element
17
- removeContentElement(element)
14
+ if (__contentRef && __contentRef.__cached && isEqualDeep(params, element.content)) return element
15
+ removeContent(element)
18
16
 
19
17
  if (params) {
20
18
  const { childExtend } = params
@@ -0,0 +1,61 @@
1
+ 'use strict'
2
+
3
+ import { create } from '../../src/element'
4
+
5
+ const dom = create({})
6
+
7
+ test('should create EMPTY element', () => {
8
+ expect(dom).toHaveProperty('key')
9
+ expect(dom).toHaveProperty('state')
10
+ expect(dom).toHaveProperty('parent')
11
+ expect(dom).toHaveProperty('node')
12
+ expect(dom).toHaveProperty('set')
13
+ expect(dom).toHaveProperty('update')
14
+ expect(dom).toHaveProperty('__ref')
15
+ })
16
+
17
+ test('should create valid DOM node', () => {
18
+ expect(dom.node).toBeInstanceOf(window.HTMLDivElement)
19
+ })
20
+
21
+ test('must be able to create valid PATH', () => {
22
+ expect(dom.__ref.__path).toStrictEqual([dom.key])
23
+ })
24
+
25
+ test('if it HAS a NODE, don\'t recreate', () => {
26
+ const node = document.createElement('div')
27
+ const dom2 = create({ node })
28
+ expect(dom2.node.parentElement).toBe(document.body)
29
+ })
30
+
31
+ test('create with number', () => {
32
+ const numb = create(0)
33
+ expect(numb.text).toBe(0)
34
+ expect(numb.tag).toBe('string')
35
+ expect(numb.node.nodeType).toBe(3) // #text
36
+ })
37
+
38
+ test('create with string', () => {
39
+ const str = create('hello')
40
+ expect(str.text).toBe('hello')
41
+ expect(str.tag).toBe('string')
42
+ expect(str.node.nodeType).toBe(3) // #text
43
+ })
44
+
45
+ test('creating conditions', () => {
46
+ const element = create({
47
+ data: { visible: true },
48
+ if: element => element.data.visible
49
+ })
50
+ expect(element.tag).toBe('div')
51
+ })
52
+
53
+ test('creating nesting', () => {
54
+ const element = create({
55
+ header: {
56
+ h1: {}
57
+ }
58
+ })
59
+ expect(element.header.tag).toBe('header')
60
+ expect(element.header.h1.tag).toBe('h1')
61
+ })
@@ -0,0 +1,13 @@
1
+ 'use strict'
2
+
3
+ import { create } from '../../src/element'
4
+
5
+ const element = create({})
6
+
7
+ test('should SET element', () => {
8
+ element.set({ text: 'test' })
9
+ expect(element.content.text).toBe('test')
10
+
11
+ element.set({ text: 'test2' })
12
+ expect(element.content.text).toBe('test2')
13
+ })
@@ -0,0 +1,13 @@
1
+ 'use strict'
2
+
3
+ import { create } from '../../src/element'
4
+
5
+ const element = create({})
6
+
7
+ test('should UPDATE element', () => {
8
+ expect(element.text).toBeUndefined()
9
+
10
+ element.update('test')
11
+
12
+ expect(element.text).toBe('test')
13
+ })
package/tree.js ADDED
@@ -0,0 +1,11 @@
1
+ 'use strict'
2
+
3
+ import { document } from '@domql/utils'
4
+ import { report } from '@domql/report'
5
+
6
+ export const ROOT = {
7
+ key: ':root',
8
+ node: document ? document.body : report('DocumentNotDefined', document)
9
+ }
10
+
11
+ export const TREE = ROOT
package/update.js CHANGED
@@ -1,11 +1,9 @@
1
1
  'use strict'
2
2
 
3
- import { window } from '@domql/globals'
4
- import { exec, isArray, isFunction, isNumber, isObject, isString, isUndefined, merge, overwriteDeep } from '@domql/utils'
3
+ import { window, exec, isArray, isFunction, isNumber, isObject, isString, isUndefined, merge, overwriteDeep, createSnapshotId } from '@domql/utils'
5
4
  import { applyEvent, triggerEventOn, triggerEventOnUpdate } from '@domql/event'
6
- import { isMethod } from '@domql/methods'
7
- import { createSnapshotId } from '@domql/key'
8
- import { updateProps } from '@domql/props'
5
+ import { isMethod } from './methods'
6
+ import { updateProps } from './props'
9
7
  import { createState } from '@domql/state'
10
8
 
11
9
  import { METHODS_EXL, isVariant } from './utils'
@@ -13,7 +11,7 @@ import create from './create'
13
11
  import { throughUpdatedDefine, throughUpdatedExec } from './iterate'
14
12
  import { registry } from './mixins'
15
13
  import { applyParam } from './applyParam'
16
- import OPTIONS from './options'
14
+ import OPTIONS from './cache/options'
17
15
 
18
16
  const snapshot = {
19
17
  snapshotId: createSnapshotId
@@ -111,7 +109,7 @@ const update = function (params = {}, options = UPDATE_DEFAULT_OPTIONS) {
111
109
  const childUpdateCall = () => update.call(prop, params[prop], {
112
110
  ...options,
113
111
  currentSnapshot: snapshotOnCallee,
114
- calleeElement: calleeElement
112
+ calleeElement
115
113
  })
116
114
 
117
115
  if ((element.props && element.props.lazyLoad) || options.lazyLoad) {
@@ -0,0 +1,112 @@
1
+ 'use strict'
2
+
3
+ import { exec, isArray, isFunction, isObject, isString, overwriteDeep } from '@domql/utils'
4
+ import { applyExtend } from '../extend'
5
+ const ENV = process.env.NODE_ENV
6
+
7
+ export const checkIfKeyIsComponent = (key) => {
8
+ const isFirstKeyString = isString(key)
9
+ if (!isFirstKeyString) return
10
+ const firstCharKey = key.slice(0, 1)
11
+ return /^[A-Z]*$/.test(firstCharKey)
12
+ }
13
+
14
+ export const addAdditionalExtend = (newExtend, element) => {
15
+ const { extend } = element
16
+ const preserveExtend = isArray(extend) ? extend : [extend]
17
+ return {
18
+ ...element,
19
+ extend: [newExtend].concat(preserveExtend)
20
+ }
21
+ }
22
+
23
+ export const extendizeByKey = (element, parent, key) => {
24
+ const { tag, extend, props, state, childExtend, childProps, on } = element
25
+ const hasComponentAttrs = tag || extend || childExtend || props || state || on
26
+ const componentKey = key.includes('_')
27
+ ? key.split('_')[0]
28
+ : key.includes('.') ? key.split('.')[0] : key
29
+ const extendKey = componentKey || key
30
+
31
+ if (!hasComponentAttrs || childProps) {
32
+ return {
33
+ extend: extendKey,
34
+ props: { ...element }
35
+ }
36
+ } else if (!extend || extend === true) {
37
+ return {
38
+ ...element,
39
+ extend: extendKey
40
+ }
41
+ } else if (extend) {
42
+ addAdditionalExtend(extendKey, element)
43
+ } else if (isFunction(element)) {
44
+ return {
45
+ extend: extendKey,
46
+ props: { ...exec(element, parent) }
47
+ }
48
+ }
49
+ }
50
+
51
+ export const applyKeyComponentAsExtend = (element, parent, key) => {
52
+ return extendizeByKey(element, parent, key) || element
53
+ }
54
+
55
+ export const applyComponentFromContext = (element, parent, options) => {
56
+ const { context } = element
57
+ const { components } = context
58
+ const { extend } = element
59
+ const execExtend = exec(extend, element)
60
+ if (isString(execExtend)) {
61
+ if (components[execExtend]) element.extend = components[execExtend]
62
+ else {
63
+ if ((ENV === 'test' || ENV === 'development') && options.verbose) {
64
+ console.warn(execExtend, 'is not in library', components, element)
65
+ console.warn('replacing with ', {})
66
+ }
67
+ element.extend = {}
68
+ }
69
+ }
70
+ }
71
+
72
+ export const isVariant = (param) => {
73
+ if (!isString(param)) return
74
+ const firstCharKey = param.slice(0, 1)
75
+ // return (firstCharKey === '.' || firstCharKey === '$')
76
+ return (firstCharKey === '.')
77
+ }
78
+
79
+ export const hasVariantProp = (element) => {
80
+ const { props } = element
81
+ if (isObject(props) && isString(props.variant)) return true
82
+ }
83
+
84
+ export const overwriteVariant = (element, variant, variantProps) => {
85
+ let variantElement = element[variant]
86
+ if (!variantElement) return
87
+ const props = isObject(variantProps) ? variantProps : {}
88
+ if (isString(variantElement)) {
89
+ variantElement = {
90
+ extend: [{ props }, variantElement]
91
+ }
92
+ } else if (variantElement.extend) {
93
+ variantElement = addAdditionalExtend({ props }, variantElement)
94
+ }
95
+ return overwriteDeep(element, applyExtend(variantElement)) // TODO: check why string is not working
96
+ }
97
+
98
+ export const applyVariant = (element) => {
99
+ const { props } = element
100
+ if (!hasVariantProp(element)) return element
101
+ const { variant } = props
102
+ overwriteVariant(element, `.${variant}`)
103
+
104
+ const elKeys = Object.keys(element).filter((key) => isVariant(key))
105
+ elKeys.forEach((variant) => {
106
+ const slicedVariantElementKey = variant.slice(1)
107
+ const variantElementProps = props[slicedVariantElementKey]
108
+ if (variantElementProps) overwriteVariant(element, variant, variantElementProps)
109
+ })
110
+
111
+ return element
112
+ }
@@ -0,0 +1,118 @@
1
+ 'use strict'
2
+
3
+ import { isArray, isFunction, isObject, isString } from '@domql/utils'
4
+
5
+ export const generateHash = () => Math.random().toString(36).substring(2)
6
+
7
+ // hashing
8
+ export const extendStackRegistry = {}
9
+ export const extendCachedRegistry = {}
10
+
11
+ export const getHashedExtend = extend => {
12
+ return extendStackRegistry[extend.__hash]
13
+ }
14
+
15
+ export const setHashedExtend = (extend, stack) => {
16
+ const hash = generateHash()
17
+ if (!isString(extend)) { extend.__hash = hash }
18
+ extendStackRegistry[hash] = stack
19
+ return stack
20
+ }
21
+
22
+ export const getExtendStackRegistry = (extend, stack) => {
23
+ if (extend.__hash) { return stack.concat(getHashedExtend(extend)) }
24
+ return setHashedExtend(extend, stack) // stack .concat(hashedExtend)
25
+ }
26
+
27
+ // stacking
28
+ export const extractArrayExtend = (extend, stack) => {
29
+ extend.forEach(each => flattenExtend(each, stack))
30
+ return stack
31
+ }
32
+
33
+ export const deepExtend = (extend, stack) => {
34
+ const extendOflattenExtend = extend.extend
35
+ if (extendOflattenExtend) {
36
+ flattenExtend(extendOflattenExtend, stack)
37
+ }
38
+ return stack
39
+ }
40
+
41
+ export const flattenExtend = (extend, stack) => {
42
+ if (!extend) return stack
43
+ if (isArray(extend)) return extractArrayExtend(extend, stack)
44
+ stack.push(extend)
45
+ if (extend.extend) deepExtend(extend, stack)
46
+ return stack
47
+ }
48
+
49
+ // merging
50
+ export const deepCloneExtend = obj => {
51
+ const o = {}
52
+ for (const prop in obj) {
53
+ if (['parent', 'node', '__element'].indexOf(prop) > -1) continue
54
+ const objProp = obj[prop]
55
+ if (isObject(objProp)) {
56
+ o[prop] = deepCloneExtend(objProp)
57
+ } else if (isArray(objProp)) {
58
+ o[prop] = objProp.map(x => x)
59
+ } else o[prop] = objProp
60
+ }
61
+ return o
62
+ }
63
+
64
+ export const deepMergeExtend = (element, extend) => {
65
+ for (const e in extend) {
66
+ if (['parent', 'node', '__element'].indexOf(e) > -1) continue
67
+ const elementProp = element[e]
68
+ const extendProp = extend[e]
69
+ if (elementProp === undefined) {
70
+ element[e] = extendProp
71
+ } else if (isObject(elementProp) && isObject(extendProp)) {
72
+ deepMergeExtend(elementProp, extendProp)
73
+ } else if (isArray(elementProp) && isArray(extendProp)) {
74
+ element[e] = elementProp.concat(extendProp)
75
+ } else if (isArray(elementProp) && isObject(extendProp)) {
76
+ const obj = deepMergeExtend({}, elementProp)
77
+ element[e] = deepMergeExtend(obj, extendProp)
78
+ } else if (elementProp === undefined && isFunction(extendProp)) {
79
+ element[e] = extendProp
80
+ }
81
+ }
82
+ return element
83
+ }
84
+
85
+ export const cloneAndMergeArrayExtend = stack => {
86
+ return stack.reduce((a, c) => {
87
+ return deepMergeExtend(a, deepCloneExtend(c))
88
+ }, {})
89
+ }
90
+
91
+ export const replaceStringsWithComponents = (stack, components) => {
92
+ return stack.map(v => {
93
+ if (isString(v)) return components[v]
94
+ else return v
95
+ })
96
+ }
97
+
98
+ // joint stacks
99
+ export const jointStacks = (extendStack, childExtendStack) => {
100
+ return []
101
+ .concat(extendStack.slice(0, 1))
102
+ .concat(childExtendStack.slice(0, 1))
103
+ .concat(extendStack.slice(1))
104
+ .concat(childExtendStack.slice(1))
105
+ }
106
+
107
+ // init
108
+ export const getExtendStack = extend => {
109
+ if (!extend) return []
110
+ if (extend.__hash) return getHashedExtend(extend) || []
111
+ const stack = flattenExtend(extend, [])
112
+ return getExtendStackRegistry(extend, stack)
113
+ }
114
+
115
+ export const getExtendMerged = extend => {
116
+ const stack = getExtendStack(extend)
117
+ return cloneAndMergeArrayExtend(stack)
118
+ }
package/utils/index.js ADDED
@@ -0,0 +1,5 @@
1
+ 'use strict'
2
+
3
+ export * from './object'
4
+ export * from './extendUtils'
5
+ export * from './component'
@@ -0,0 +1,141 @@
1
+ 'use strict'
2
+
3
+ import { isArray, isObject, isObjectLike, joinArrays } from '@domql/utils'
4
+ import { IGNORE_STATE_PARAMS } from '@domql/state'
5
+ import { IGNORE_PROPS_PARAMS } from '../props'
6
+ import { METHODS } from '../methods'
7
+
8
+ export const METHODS_EXL = joinArrays(
9
+ ['node', 'state', 'context', 'extend'],
10
+ METHODS,
11
+ IGNORE_STATE_PARAMS,
12
+ IGNORE_PROPS_PARAMS
13
+ )
14
+
15
+ export const deepMerge = (element, extend, exclude = METHODS_EXL) => {
16
+ for (const e in extend) {
17
+ if (exclude.includes(e)) continue
18
+ const elementProp = element[e]
19
+ const extendProp = extend[e]
20
+ if (elementProp === undefined) {
21
+ element[e] = extendProp
22
+ } else if (isObjectLike(elementProp) && isObject(extendProp)) {
23
+ deepMerge(elementProp, extendProp)
24
+ }
25
+ }
26
+ return element
27
+ }
28
+
29
+ export const clone = (obj, exclude = METHODS_EXL) => {
30
+ const o = {}
31
+ for (const e in obj) {
32
+ if (exclude.includes(e)) continue
33
+ o[e] = obj[e]
34
+ }
35
+ return o
36
+ }
37
+
38
+ /**
39
+ * Deep cloning of object
40
+ */
41
+ export const deepClone = (obj, exclude = METHODS_EXL) => {
42
+ const o = isArray(obj) ? [] : {}
43
+ for (const e in obj) {
44
+ if (exclude.includes(e)) continue
45
+ let objProp = obj[e]
46
+ if (e === 'extend' && isArray(objProp)) {
47
+ objProp = mergeArray(objProp, exclude)
48
+ }
49
+ if (isObjectLike(objProp)) {
50
+ o[e] = deepClone(objProp, exclude)
51
+ } else o[e] = objProp
52
+ }
53
+ return o
54
+ }
55
+
56
+ /**
57
+ * Overwrites object properties with another
58
+ */
59
+ export const overwrite = (element, params, options) => {
60
+ const changes = {}
61
+ const { __ref } = element
62
+ const { __exec, __cached } = __ref
63
+
64
+ for (const e in params) {
65
+ if (e === 'props' || e === 'state' || e === '__ref') continue
66
+
67
+ const elementProp = element[e]
68
+ const paramsProp = params[e]
69
+
70
+ if (paramsProp !== undefined) {
71
+ __cached[e] = changes[e] = elementProp
72
+ element[e] = paramsProp
73
+ }
74
+
75
+ if (options.cleanExec) delete __exec[e]
76
+ }
77
+
78
+ return changes
79
+ }
80
+
81
+ export const overwriteShallow = (obj, params, exclude = METHODS_EXL) => {
82
+ for (const e in params) {
83
+ if (exclude.includes(e)) continue
84
+ obj[e] = params[e]
85
+ }
86
+ return obj
87
+ }
88
+
89
+ /**
90
+ * Overwrites DEEPly object properties with another
91
+ */
92
+ export const overwriteDeep = (obj, params, exclude = METHODS_EXL) => {
93
+ for (const e in params) {
94
+ if (exclude.includes(e)) continue
95
+ const objProp = obj[e]
96
+ const paramsProp = params[e]
97
+ if (isObjectLike(objProp) && isObjectLike(paramsProp)) {
98
+ overwriteDeep(objProp, paramsProp)
99
+ } else if (paramsProp !== undefined) {
100
+ obj[e] = paramsProp
101
+ }
102
+ }
103
+ return obj
104
+ }
105
+
106
+ /**
107
+ * Overwrites object properties with another
108
+ */
109
+ export const mergeIfExisted = (a, b) => {
110
+ if (isObjectLike(a) && isObjectLike(b)) return deepMerge(a, b)
111
+ return a || b
112
+ }
113
+
114
+ /**
115
+ * Merges array extends
116
+ */
117
+ export const mergeArray = (arr, exclude = ['parent', 'node', '__element', 'state', 'context', '__ref']) => {
118
+ return arr.reduce((a, c) => deepMerge(a, deepClone(c, exclude)), {})
119
+ }
120
+
121
+ /**
122
+ * Merges array extends
123
+ */
124
+ export const mergeAndCloneIfArray = obj => {
125
+ return isArray(obj) ? mergeArray(obj) : deepClone(obj)
126
+ }
127
+
128
+ /**
129
+ * Overwrites object properties with another
130
+ */
131
+ export const flattenRecursive = (param, prop, stack = []) => {
132
+ const objectized = mergeAndCloneIfArray(param)
133
+ stack.push(objectized)
134
+
135
+ const extendOfExtend = objectized[prop]
136
+ if (extendOfExtend) flattenRecursive(extendOfExtend, prop, stack)
137
+
138
+ delete objectized[prop]
139
+
140
+ return stack
141
+ }
package/parse.js DELETED
@@ -1,17 +0,0 @@
1
- 'use strict'
2
-
3
- import { assignNode } from '@domql/render'
4
- import create from './create'
5
-
6
- const parse = (element) => {
7
- const virtualTree = {
8
- node: document.createElement('div')
9
- }
10
-
11
- if (element && element.node) assignNode(element, virtualTree)
12
- else create(element, virtualTree)
13
-
14
- return virtualTree.node.innerHTML
15
- }
16
-
17
- export default parse
File without changes