Kaynağa Gözat

feature(migrate to magic property)

Ryan Chandler 4 yıl önce
ebeveyn
işleme
6de4b2c874

Dosya farkı çok büyük olduğundan ihmal edildi
+ 0 - 0
dist/spruce.js


Dosya farkı çok büyük olduğundan ihmal edildi
+ 0 - 0
dist/spruce.js.map


Dosya farkı çok büyük olduğundan ihmal edildi
+ 0 - 0
dist/spruce.module.js


Dosya farkı çok büyük olduğundan ihmal edildi
+ 0 - 0
dist/spruce.module.js.map


Dosya farkı çok büyük olduğundan ihmal edildi
+ 0 - 0
dist/spruce.umd.js


Dosya farkı çok büyük olduğundan ihmal edildi
+ 0 - 0
dist/spruce.umd.js.map


+ 1 - 1
package.json

@@ -21,7 +21,7 @@
         "@babel/preset-env": "^7.9.5",
         "@testing-library/dom": "^7.2.2",
         "@testing-library/jest-dom": "^5.5.0",
-        "alpinejs": "^2.3.1",
+        "alpinejs": "^2.5",
         "jest": "^25.4.0",
         "jsdom-simulant": "^1.1.2",
         "microbundle": "^0.11.0",

+ 3 - 3
src/bus.js

@@ -50,11 +50,11 @@ export default {
         this.watchers[dotNotation].push(callback)
     },
 
-    runWatchers(stores, target, key, oldValue) {
+    runWatchers(stores, target, key, value) {
         const self = this
 
         if (self.watchers[key]) {
-            return self.watchers[key].forEach(callback => callback(oldValue, target[key]))
+            return self.watchers[key].forEach(callback => callback(value))
         }
 
         Object.keys(self.watchers)
@@ -66,7 +66,7 @@ export default {
 
                 dotNotationParts.reduce((comparison, part) => {
                     if (comparison[key] === target[key] || Object.is(target, comparison)) {
-                        self.watchers[fullDotNotationKey].forEach(callback => callback(oldValue, target[key]))
+                        self.watchers[fullDotNotationKey].forEach(callback => callback(value))
                     }
 
                     return comparison[part]

+ 21 - 32
src/index.js

@@ -1,19 +1,15 @@
-import { domReady, buildInitExpression, isNullOrUndefined } from './utils'
+import { domReady } from './utils'
 import { createObservable } from './observable'
 import EventBus from './bus'
 
 const Spruce = {
-    options: {
-        globalStoreVariable: false,
-    },
-
     events: EventBus,
 
     stores: {},
 
     subscribers: [],
 
-    start: async function () {
+    async start() {
         await domReady()
 
         this.emit('init')
@@ -23,32 +19,29 @@ const Spruce = {
         document.addEventListener('turbolinks:render', this.attach)
 
         this.stores = createObservable(this.stores, {
-            set: (target, key, value, oldValue) => {
-                this.events.runWatchers(this.stores, target, key, oldValue)
+            set: (target, key, value) => {
+                this.events.runWatchers(this.stores, target, key, value)
 
                 this.updateSubscribers()
             }
         })
-
-        if (this.options.globalStoreVariable) {
-            document.querySelectorAll('[x-data]').forEach(el => {
-                if (! this.subscribers.includes(el)) {
-                    this.subscribers.push(el)
-                }
-            })
-            
-            window.$store = this.stores
-        }
     },
 
     attach() {
-        document.querySelectorAll('[x-subscribe]').forEach(el => {
-            el.setAttribute('x-init', buildInitExpression(el))
-            el.removeAttribute('x-subscribe')
+        if (! window.Alpine) {
+            throw new Error('[Spruce] You must be using Alpine >= 2.5.0 to use Spruce.')
+        }
+
+        const self = this
+
+        window.Alpine.addMagicProperty('store', el => {
+            self.subscribe(el)
+
+            return self.stores
         })
     },
 
-    store: function (name, state) {
+    store(name, state) {
         if (! this.stores[name]) {
             this.stores[name] = state
         }
@@ -56,28 +49,24 @@ const Spruce = {
         return this.stores[name]
     },
 
-    reset: function (name, state) {
+    reset(name, state) {
         this.stores[name] = state
     },
 
     subscribe(el) {
-        this.subscribers.push(el)
+        if (! this.subscribers.includes(el)) {
+            this.subscribers.push(el)
+        }
 
         return this.stores
     },
 
     updateSubscribers() {
-        this.subscribers.forEach(el => {
-            if (el.__x !== undefined) {
-                el.__x.updateElements(el)
-            }
+        this.subscribers.filter(el => !! el.__x).forEach(el => {
+            el.__x.updateElements(el)
         })
     },
 
-    config(options = {}) {
-        this.options = Object.assign(this.options, options)
-    },
-
     on(name, callback) {
         return this.events.on(name, callback)
     },

+ 4 - 13
src/observable.js

@@ -1,28 +1,19 @@
-import { isNullOrUndefined } from './utils'
+import { isNullOrUndefined, isObject } from './utils'
 
 export const createObservable = (target, callbacks) => {
     Object.keys(target).forEach(key => {
-        if (! isNullOrUndefined(target[key]) && Object.getPrototypeOf(target[key]) === Object.prototype) {
+        if (! isNullOrUndefined(target[key]) && isObject(target[key])) {
             target[key] = createObservable(target[key], callbacks)
         }
     })
 
     return new Proxy(target, {
-        get(target, key) {
-            if (callbacks.hasOwnProperty('get')) {
-                callbacks.get(key)
-            }
-            
-            return target[key]
-        },
         set(target, key, value) {
-            const old = target[key]
-
-            if (! isNullOrUndefined(value) && typeof value === 'object') {
+            if (! isNullOrUndefined(value) && isObject(value)) {
                 value = createObservable(value, callbacks)
             }
 
-            callbacks.set(target, key, target[key] = value, old)
+            callbacks.set(target, key, target[key] = value)
 
             return true
         }

+ 4 - 0
src/utils.js

@@ -20,4 +20,8 @@ export const buildInitExpression = el => {
 
 export const isNullOrUndefined = value => {
     return value === null || value === undefined
+}
+
+export const isObject = _ => {
+    return Object.getPrototypeOf(_) === Object.prototype
 }

+ 2 - 4
tests/bus.spec.js

@@ -8,6 +8,7 @@ beforeEach(() => {
 
 beforeAll(() => {
     window.Spruce = Spruce
+    window.Alpine = Alpine
 })
 
 /* Spruce.on() */
@@ -94,14 +95,12 @@ test('.emit() > will dispatch browser event to window with spruce: prefix', asyn
 
 test('.watch() > can listen for changes to property', async () => {
     let fixture = undefined
-    let oldFixture = undefined
     
     Spruce.store('example', {
         cool: 'stuff'
     })
 
-    Spruce.watch('example.cool', (previous, value) => {
-        oldFixture = previous
+    Spruce.watch('example.cool', (value) => {
         fixture = value
     })
 
@@ -112,7 +111,6 @@ test('.watch() > can listen for changes to property', async () => {
     Spruce.stores.example.cool = 'amazing'
 
     expect(fixture).toEqual('amazing')
-    expect(oldFixture).toEqual('stuff')
 })
 
 test('.off() > can unregister listener', () => {

+ 1 - 0
tests/get.spec.js

@@ -8,6 +8,7 @@ beforeEach(() => {
 
 beforeAll(() => {
     window.Spruce = Spruce
+    window.Alpine = Alpine
 })
 
 test('$store > data can be retrieved from store inside component', async () => {

+ 1 - 10
tests/global-store.spec.js

@@ -8,16 +8,7 @@ beforeEach(() => {
 
 beforeAll(() => {
     window.Spruce = Spruce
-})
-
-test('$store > is available as global object', async () => {
-    Spruce.config({ globalStoreVariable: true })
-
-    expect(Spruce.options.globalStoreVariable).toBeTruthy()
-
-    await Spruce.start()
-
-    expect(window.$store).toEqual(Spruce.stores)
+    window.Alpine = Alpine
 })
 
 test('$store > can be used inside of component without subscribing', async () => {

+ 1 - 0
tests/reset.spec.js

@@ -8,6 +8,7 @@ beforeEach(() => {
 
 beforeAll(() => {
     window.Spruce = Spruce
+    window.Alpine = Alpine
 })
 
 test('.reset() > will overwrite existing properties', () => {

+ 1 - 0
tests/set.spec.js

@@ -8,6 +8,7 @@ beforeEach(() => {
 
 beforeAll(() => {
     window.Spruce = Spruce
+    window.Alpine = Alpine
 })
 
 test('$store > data can be set inside component', async () => {

+ 0 - 26
tests/subscribe.spec.js

@@ -1,26 +0,0 @@
-import Spruce from '../dist/spruce'
-import { waitFor } from '@testing-library/dom'
-
-test('x-subscribe > correctly updates x-init directive', async () => {
-    document.body.innerHTML = `
-        <div x-subscribe></div>
-    `
-
-    Spruce.start()
-
-    await waitFor(() => {
-        expect(document.querySelector('div').getAttribute('x-init')).toEqual('$store = Spruce.subscribe($el)')
-    })
-})
-
-test('x-subscribe > correctly updates x-init when already defined', async () => {
-    document.body.innerHTML = `
-        <div x-subscribe x-init="testing = true"></div>
-    `
-
-    Spruce.start()
-
-    await waitFor(() => {
-        expect(document.querySelector('div').getAttribute('x-init')).toEqual('$store = Spruce.subscribe($el); testing = true')
-    })
-})

+ 4 - 4
yarn.lock

@@ -1207,10 +1207,10 @@ alphanum-sort@^1.0.0, alphanum-sort@^1.0.1, alphanum-sort@^1.0.2:
   resolved "https://registry.yarnpkg.com/alphanum-sort/-/alphanum-sort-1.0.2.tgz#97a1119649b211ad33691d9f9f486a8ec9fbe0a3"
   integrity sha1-l6ERlkmyEa0zaR2fn0hqjsn74KM=
 
-alpinejs@^2.3.1:
-  version "2.3.1"
-  resolved "https://registry.yarnpkg.com/alpinejs/-/alpinejs-2.3.1.tgz#350b79b226fff35f026b70a631dde63a56142ea1"
-  integrity sha512-jkASU7vSv4rwTWLsH5kS+NxRw3D2dMhLigfXk88xPifkYWaKyGFMHzQtyCHUh3lDwTvPYCsLCvmPLZHtKgXFng==
+alpinejs@^2.5:
+  version "2.6.0"
+  resolved "https://registry.yarnpkg.com/alpinejs/-/alpinejs-2.6.0.tgz#0ff340e51e632fa4ed25f1c4ee0ce2515bd77491"
+  integrity sha512-4cW3zU17JIYzq6uS3asozwKIMVe5A7wrIfn3o0SNsH1YZ4D3cR2Cs+YThvf4dU3/O7EBzExBY4Dhd8LjtCnEqA==
 
 ansi-escapes@^4.2.1:
   version "4.3.1"

Bu fark içinde çok fazla dosya değişikliği olduğu için bazı dosyalar gösterilmiyor