valtio-define 1.2.0 → 1.2.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.
package/README.md CHANGED
@@ -7,7 +7,7 @@
7
7
  [![coverage][coverage-src]][coverage-href]
8
8
  [![License][license-src]][license-href].
9
9
 
10
- ⚡️ **valtio-define** is a lightweight factory for creating fully functional, robust [Valtio](https://valtio.dev) stores. It simplifies state management in React by providing a structured API for state, actions, and computed getters.
10
+ ⚡️ **valtio-define** is a lightweight factory for creating fully functional, robust [Valtio](https://github.com/pmndrs/valtio) stores. It simplifies state management in React by providing a structured API for state, actions, and computed getters.
11
11
 
12
12
  ## 📦 Installation
13
13
 
@@ -15,8 +15,18 @@
15
15
  pnpm add valtio-define
16
16
  ```
17
17
 
18
+ <details>
19
+ <summary>Are you an AI?</summary>
20
+
21
+ You can run <code>npx skills add hairyf/valtio-define --skill valtio-define -y</code> to install the skills!
22
+
23
+ Remember to ask your owner which <a href="https://github.com/vercel-labs/skills?tab=readme-ov-file#supported-agents">Agents</a> need to be supported (using the <code>--agent</code> parameter of skills) to avoid installing too many default <code>agents</code> directories.
24
+
25
+ </details>
26
+
18
27
  ## 🚀 Quick Start
19
28
 
29
+
20
30
  ### Basic Store
21
31
 
22
32
  `defineStore` allows you to encapsulate state and logic in one place. Use `useStore` to consume the reactive state in your components.
@@ -161,6 +171,28 @@ function Profile() {
161
171
  }
162
172
  ```
163
173
 
174
+ ### Controlled inputs may lose caret position
175
+
176
+ Ref: https://github.com/pmndrs/valtio/issues/270
177
+
178
+ This happens because Valtio batches state updates causing React to re-render after the input event. React resets the DOM value and loses the caret position.
179
+
180
+ Use `{ sync: true }` to update synchronously and preserve the caret:
181
+
182
+ ```tsx
183
+ function Input() {
184
+ const { text } = useStore(store, { sync: true })
185
+ // const [text, setText] = storeToState(store, 'text', { sync: true })
186
+
187
+ return (
188
+ <input
189
+ onChange={e => store.text = e.target.value}
190
+ value={text}
191
+ />
192
+ )
193
+ }
194
+ ```
195
+
164
196
  -----
165
197
 
166
198
  ## 🛰 Store API
package/dist/index.d.mts CHANGED
@@ -38,18 +38,21 @@ declare function use(plugin: Plugin): void;
38
38
  declare function defineStore<S extends object = {}, A extends Actions<S> = {}, G extends Getters<S> = {}>(define: StoreDefine<S, A, G>): Store<S, A, G>;
39
39
  //#endregion
40
40
  //#region src/hooks.d.ts
41
- interface UseStoreOptions {
41
+ declare function useStore<S extends object, A extends Actions<S>, G extends Getters<S>>(store: Store<S, A, G>, options?: {
42
42
  sync?: boolean;
43
- }
44
- declare function useStore<S extends object, A extends Actions<S>, G extends Getters<S>>(store: Store<S, A, G>, options?: UseStoreOptions): Snapshot<S & GettersReturnType<G> & A>;
43
+ }): Snapshot<S & GettersReturnType<G> & A>;
45
44
  //#endregion
46
45
  //#region src/utils.d.ts
47
- declare function storeToState<S extends object, K extends keyof S>(store: Store<S>, key: K): [S[K], Dispatch<SetStateAction<S[K]>>];
48
- declare function storeToStates<S extends object>(store: Store<S>): { [K in keyof S]: [S[K], Dispatch<SetStateAction<S[K]>>] };
46
+ declare function storeToState<S extends object, K extends keyof S>(store: Store<S>, key: K, options?: {
47
+ sync?: boolean;
48
+ }): [S[K], Dispatch<SetStateAction<S[K]>>];
49
+ declare function storeToStates<S extends object>(store: Store<S>, options?: {
50
+ sync?: boolean;
51
+ }): { [K in keyof S]: [S[K], Dispatch<SetStateAction<S[K]>>] };
49
52
  //#endregion
50
53
  //#region src/index.d.ts
51
54
  declare const _default: {
52
55
  use: typeof use;
53
56
  };
54
57
  //#endregion
55
- export { Actions, ActionsOmitThisParameter, ActionsTree, Getters, GettersReturnType, Patch, Plugin, PluginContext, Signal, Store, StoreDefine, StoreDefineOptions, StoreOptions, Subscribe, SubscribeKey, UseStoreOptions, _default as default, defineStore, plugins, storeToState, storeToStates, use, useStore };
58
+ export { Actions, ActionsOmitThisParameter, ActionsTree, Getters, GettersReturnType, Patch, Plugin, PluginContext, Signal, Store, StoreDefine, StoreDefineOptions, StoreOptions, Subscribe, SubscribeKey, _default as default, defineStore, plugins, storeToState, storeToStates, use, useStore };
package/dist/index.mjs CHANGED
@@ -1 +1 @@
1
- import{proxy as e,ref as t,subscribe as n,useSnapshot as r}from"valtio";import{createElement as i}from"react";import{subscribeKey as a}from"valtio/utils";const o=e([]);function s(e){o.push(e)}function c(s){let c=typeof s.state==`function`?s.state():s.state,u=s.getters||{},d=s.actions||{},f=e(c),p={},m={},h=new WeakSet;for(let e in d)p[e]=t(d[e].bind(f)),f[e]=p[e];for(let e in u)l(f,e,()=>u[e].call(f)),l(m,e,()=>f[e]);function g(e){return n(f,t=>e(f,t))}function _(e,t){return a(f,e,e=>t(e),!0)}function v(e){typeof e==`function`?e(f):Object.assign(f,e)}function y(e){return i(()=>e(r(f)))}function b(e){o.push(e),C(e)}let x={$subscribe:g,$subscribeKey:_,$patch:v,$state:f,$actions:p,$getters:m,$signal:y,use:b},S=new Proxy(x,{get(e,t){return t in p?p[t]:t in e?e[t]:f[t]},has(e,t){return t in e||t in p||t in f},set(e,t,n){return t in f?f[t]=n:e[t]=n,!0}});function C(e){h.has(e)||(h.add(e),e({store:S,options:s}))}for(let e of o)C(e);return n(o,()=>{for(let e of o)C(e)}),S}function l(e,t,n){Object.defineProperty(e,t,{get:n,enumerable:!0})}function u(e,t){return r(e.$state,t)}function d(e,t){let n=u(e);function r(n){typeof n==`function`?e.$patch(e=>{e[t]=n(e[t])}):e.$patch(e=>{e[t]=n})}return[n[t],r]}function f(e){return Object.fromEntries(Object.keys(e.$state).map(t=>[t,d(e,t)]))}var p={use:s};export{p as default,c as defineStore,o as plugins,d as storeToState,f as storeToStates,s as use,u as useStore};
1
+ import{proxy as e,ref as t,subscribe as n,useSnapshot as r}from"valtio";import{createElement as i}from"react";import{subscribeKey as a}from"valtio/utils";const o=e([]);function s(e){o.push(e)}function c(s){let c=typeof s.state==`function`?s.state():s.state,u=s.getters||{},d=s.actions||{},f=e(c),p={},m={},h=new WeakSet;for(let e in d)p[e]=t(d[e].bind(f)),f[e]=p[e];for(let e in u)l(f,e,()=>u[e].call(f)),l(m,e,()=>f[e]);function g(e){return n(f,t=>e(f,t))}function _(e,t){return a(f,e,e=>t(e),!0)}function v(e){typeof e==`function`?e(f):Object.assign(f,e)}function y(e){return i(()=>e(r(f)))}function b(e){o.push(e),C(e)}let x={$subscribe:g,$subscribeKey:_,$patch:v,$state:f,$actions:p,$getters:m,$signal:y,use:b},S=new Proxy(x,{get(e,t){return t in p?p[t]:t in e?e[t]:f[t]},has(e,t){return t in e||t in p||t in f},set(e,t,n){return t in f?f[t]=n:e[t]=n,!0}});function C(e){h.has(e)||(h.add(e),e({store:S,options:s}))}for(let e of o)C(e);return n(o,()=>{for(let e of o)C(e)}),S}function l(e,t,n){Object.defineProperty(e,t,{get:n,enumerable:!0})}function u(e,t){return r(e.$state,t)}function d(e,t,n){let r=u(e,n);function i(n){typeof n==`function`?e.$patch(e=>{e[t]=n(e[t])}):e.$patch(e=>{e[t]=n})}return[r[t],i]}function f(e,t){return Object.fromEntries(Object.keys(e.$state).map(n=>[n,d(e,n,t)]))}var p={use:s};export{p as default,c as defineStore,o as plugins,d as storeToState,f as storeToStates,s as use,u as useStore};
@@ -1,2 +1,2 @@
1
- import { PersistentMountOptions, StorePersistentOptions, persist } from "./persist/index.mjs";
2
- export { PersistentMountOptions, StorePersistentOptions, persist };
1
+ import { PersistentMountOptions, persist } from "./persist/index.mjs";
2
+ export { PersistentMountOptions, persist };
@@ -8,9 +8,6 @@ interface PersistentMountOptions {
8
8
  */
9
9
  hydrate?: boolean;
10
10
  }
11
- interface StorePersistentOptions {
12
- mount: () => void;
13
- }
14
11
  declare function persist({
15
12
  hydrate
16
13
  }?: PersistentMountOptions): Plugin;
@@ -21,4 +18,4 @@ declare module 'valtio-define' {
21
18
  interface StoreOptions extends PersistentStore {}
22
19
  }
23
20
  //#endregion
24
- export { PersistentMountOptions, StorePersistentOptions, persist };
21
+ export { PersistentMountOptions, persist };
@@ -1 +1 @@
1
- import{subscribe as e}from"valtio";import{get as t,set as n}from"@hairy/utils";import{destr as r}from"destr";import{generateStructureId as i}from"structure-id";function a({hydrate:a=!0}={}){return o=>{let{persist:s,getters:c}=o.options,{$state:l}=o.store;if(!s)return;let u=s===!0?{}:s,d=u.key||i(l),f=u.storage??(typeof localStorage<`u`?localStorage:void 0);if(!f?.getItem||!f?.setItem)return;let p=!1;function m(e){let t=r(e);t&&typeof t==`object`&&(Object.keys(c||{}).forEach(e=>Reflect.deleteProperty(t,e)),Object.assign(l,t)),p=!0}function h(){let e=f.getItem(d);e instanceof Promise?e.then(m):m(e)}function g(){e(l,()=>{if(!p)return;let e=(u.paths||Object.keys(l)).reduce((e,r)=>n(e,r,t(l,r)),{});f.setItem(d,JSON.stringify(e))})}o.store.$persist={mount:h},a&&h(),g()}}export{a as persist};
1
+ import{subscribe as e}from"valtio";import{get as t,set as n}from"@hairy/utils";import{destr as r}from"destr";import{generateStructureId as i}from"structure-id";function a({hydrate:a=!0}={}){return o=>{let{persist:s,getters:c}=o.options,{$state:l}=o.store;if(o.store.$persist?.unmount?.(),!s)return;let u=s===!0?{}:s,d=u.key||i(l),f=u.storage??(typeof localStorage<`u`?localStorage:void 0);if(!f?.getItem||!f?.setItem)return;let p=o.store.$persist?.meta??{mounted:!1,hydrated:!1};function m(e){let t=r(e);t&&typeof t==`object`&&(Object.keys(c||{}).forEach(e=>Reflect.deleteProperty(t,e)),Object.assign(l,t)),p.hydrated=!0}function h(){p.mounted=!0;let e=f.getItem(d);e instanceof Promise?e.then(m):m(e)}function g(){p.unsubscribe?.(),p.unsubscribe=void 0}function _(){g(),p.unsubscribe=e(l,()=>{if(!p.hydrated)return;let e=(u.paths||Object.keys(l)).reduce((e,r)=>n(e,r,t(l,r)),{});f.setItem(d,JSON.stringify(e))})}o.store.$persist={mount:h,unmount:g,meta:p},a&&!p.mounted&&h(),_()}}export{a as persist};
@@ -12,10 +12,17 @@ interface PersistentOptions<S extends object> {
12
12
  storage?: Storage;
13
13
  paths?: DeepKeys<S>[];
14
14
  }
15
+ interface PersistentMeta {
16
+ mounted: boolean;
17
+ hydrated: boolean;
18
+ unsubscribe?: () => void;
19
+ }
15
20
  interface PersistentStore {
16
21
  $persist: {
17
22
  mount: () => void;
23
+ unmount: () => void;
24
+ meta: PersistentMeta;
18
25
  };
19
26
  }
20
27
  //#endregion
21
- export { DeepKeys, PersistentOptions, PersistentStore, Storage };
28
+ export { DeepKeys, PersistentMeta, PersistentOptions, PersistentStore, Storage };
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "valtio-define",
3
3
  "type": "module",
4
- "version": "1.2.0",
4
+ "version": "1.2.1",
5
5
  "description": "⚡quickly create a fully functional and robust Valtio factory",
6
6
  "author": "Hairyf <wwu710632@gmail.com>",
7
7
  "license": "MIT",
package/README.OLD.md DELETED
@@ -1,391 +0,0 @@
1
- # valtio-define
2
-
3
- [![npm version][npm-version-src]][npm-version-href]
4
- [![npm downloads][npm-downloads-src]][npm-downloads-href]
5
- [![bundle][bundle-src]][bundle-href]
6
- [![JSDocs][jsdocs-src]][jsdocs-href]
7
- [![coverage][coverage-src]][coverage-href]
8
- [![License][license-src]][license-href]
9
-
10
- ⚡ Quickly create a fully functional and robust [Valtio](https://valtio.dev) factory
11
-
12
- ## Installation
13
-
14
- ```bash
15
- pnpm add valtio-define
16
- ```
17
-
18
- ## Usage
19
-
20
- ### Basic Store
21
-
22
- Create a reactive store with state and actions. The store provides a simple and intuitive API for managing state in React applications, built on top of Valtio.
23
-
24
- ```tsx
25
- import { defineStore, useStore } from 'valtio-define'
26
-
27
- const store = defineStore({
28
- state: () => ({ count: 0 }),
29
- actions: {
30
- increment() {
31
- this.count++
32
- },
33
- },
34
- })
35
-
36
- function Counter() {
37
- const { count } = useStore(store)
38
- return (
39
- <div>
40
- <button onClick={store.increment}>Increment</button>
41
- <div>{count}</div>
42
- </div>
43
- )
44
- }
45
- ```
46
-
47
- ### With Getters
48
-
49
- Getters are computed properties that automatically update when their dependencies change. They provide a clean way to derive state without manually tracking dependencies.
50
-
51
- ```tsx
52
- const store = defineStore({
53
- state: () => ({ count: 0 }),
54
- getters: {
55
- doubled() {
56
- return this.count * 2
57
- },
58
- },
59
- actions: {
60
- increment() {
61
- this.count++
62
- },
63
- },
64
- })
65
-
66
- function Counter() {
67
- const state = useStore(store)
68
- return (
69
- <div>
70
- <div>
71
- Count:
72
- {state.count}
73
- </div>
74
- <div>
75
- Doubled:
76
- {state.doubled}
77
- </div>
78
- <button onClick={store.increment}>Increment</button>
79
- </div>
80
- )
81
- }
82
- ```
83
-
84
- ### Persistence
85
-
86
- The persistence plugin allows you to persist store state to storage (e.g., localStorage).
87
-
88
- First, register the persist plugin:
89
-
90
- ```tsx
91
- import valtio from 'valtio-define'
92
- import { persist } from 'valtio-define/plugins'
93
-
94
- // Register the persist plugin globally
95
- valtio.use(persist())
96
- ```
97
-
98
- Then use it in your store:
99
-
100
- ```tsx
101
- import { defineStore } from 'valtio-define'
102
-
103
- const store = defineStore({
104
- state: () => ({ count: 0 }),
105
- actions: {
106
- increment() {
107
- this.count++
108
- },
109
- },
110
- persist: {
111
- key: 'my-store',
112
- storage: localStorage,
113
- paths: ['count'], // Only persist 'count', or omit to persist all state
114
- },
115
- })
116
- ```
117
-
118
- If `persist` is `true`, it will use `structure-id` to generate a unique key for the store automatically.
119
-
120
- ```tsx
121
- const store = defineStore({
122
- state: () => ({ count: 0 }),
123
- persist: true, // Auto-generates key using structure-id
124
- })
125
- ```
126
-
127
- You can pass `hydrate` when registering the plugin (default `true`). When `true`, state is hydrated from storage as soon as the store is created. Set `hydrate: false` when you need to avoid running persistence during server-side rendering, and manually mount persist in your App entry instead:
128
-
129
- ```tsx
130
- // Register with hydrate: false
131
- store.use(persist({ hydrate: false }))
132
-
133
- // In your App (client entry), after store is used:
134
- useEffect(() => store.$persist.mount(), [])
135
- ```
136
-
137
- ### Subscribe to Changes
138
-
139
- ```tsx
140
- const store = defineStore({
141
- state: () => ({ count: 0 }),
142
- actions: {
143
- increment() {
144
- this.count++
145
- },
146
- },
147
- })
148
-
149
- // Subscribe to state changes
150
- const unsubscribe = store.$subscribe((state) => {
151
- console.log('State changed:', state)
152
- })
153
-
154
- // Subscribe to specific key changes
155
- const unsubscribeKey = store.$subscribeKey('count', (value) => {
156
- console.log('Count changed:', value)
157
- })
158
- ```
159
-
160
- ### Patch State
161
-
162
- ```tsx
163
- // Patch with object
164
- store.$patch({ count: 10 })
165
-
166
- // Patch with function
167
- store.$patch((state) => {
168
- state.count += 5
169
- })
170
- ```
171
-
172
- ### Signal (JSX Component)
173
-
174
- ```tsx
175
- function App() {
176
- return (
177
- <div>
178
- Count:
179
- {' '}
180
- {store.$signal(state => state.count)}
181
- </div>
182
- )
183
- }
184
- ```
185
-
186
- ### Store to State Hooks
187
-
188
- Convert store state to React hooks similar to `useState`. This provides a more React-idiomatic way to access and update store state.
189
-
190
- #### `storeToState(store, key)`
191
-
192
- Returns a tuple `[state, setter]` for a single store key, similar to React's `useState`.
193
-
194
- ```tsx
195
- import { defineStore, storeToState } from 'valtio-define'
196
-
197
- const store = defineStore({
198
- state: { count: 0, name: 'test' },
199
- })
200
-
201
- function Counter() {
202
- const [count, setCount] = storeToState(store, 'count')
203
- const [name, setName] = storeToState(store, 'name')
204
-
205
- return (
206
- <div>
207
- <button onClick={() => setCount(count + 1)}>Increment</button>
208
- <button onClick={() => setCount(prev => prev + 1)}>Increment (functional)</button>
209
- <div>
210
- Count:
211
- {count}
212
- </div>
213
- <div>
214
- Name:
215
- {name}
216
- </div>
217
- </div>
218
- )
219
- }
220
- ```
221
-
222
- **Parameters:**
223
- - `store`: Store instance created by `defineStore`
224
- - `key`: Key of the state property to access
225
-
226
- **Returns:** `[state, setter]` tuple where:
227
- - `state`: Current value of the state property
228
- - `setter`: Function to update the state (accepts value or updater function)
229
-
230
- #### `storeToStates(store)`
231
-
232
- Returns an object with all store keys mapped to `[state, setter]` tuples.
233
-
234
- ```tsx
235
- function Component() {
236
- const {
237
- count: [count, setCount],
238
- name: [name, setName],
239
- user: [user, setUser],
240
- } = storeToStates(store)
241
-
242
- return (
243
- <div>
244
- <button onClick={() => setCount(count + 1)}>Increment</button>
245
- <div>
246
- Count:
247
- {count}
248
- </div>
249
- <div>
250
- Name:
251
- {name}
252
- </div>
253
- <div>
254
- User:
255
- {user.name}
256
- </div>
257
- </div>
258
- )
259
- }
260
- ```
261
-
262
- **Parameters:**
263
- - `store`: Store instance created by `defineStore`
264
-
265
- **Returns:** Object where each key maps to a `[state, setter]` tuple
266
-
267
- ## API
268
-
269
- ### `defineStore(store)`
270
-
271
- Creates a store with state, actions, and getters.
272
-
273
- **Parameters:**
274
- - `store.state`: Initial state object or factory function
275
- - `store.actions`: Object containing action methods
276
- - `store.getters`: Object containing getter methods
277
- - `store.persist`: Persistence plugin configuration (boolean or object) - see [Persistence Plugin](#persistence)
278
-
279
- **Returns:** Store instance with reactive state and actions
280
-
281
- ### `useStore(store)`
282
-
283
- React hook that returns a snapshot of the store state.
284
-
285
- **Parameters:**
286
- - `store`: Store instance created by `defineStore`
287
-
288
- **Returns:** Snapshot of the store state
289
-
290
- ### `storeToState(store, key)`
291
-
292
- React hook that returns a `[state, setter]` tuple for a single store key, similar to React's `useState`.
293
-
294
- **Parameters:**
295
- - `store`: Store instance created by `defineStore`
296
- - `key`: Key of the state property to access
297
-
298
- **Returns:** `[state, setter]` tuple where:
299
- - `state`: Current value of the state property
300
- - `setter`: Function to update the state (accepts value or updater function like `setState(value)` or `setState(prev => newValue)`)
301
-
302
- ### `storeToStates(store)`
303
-
304
- React hook that returns an object with all store keys mapped to `[state, setter]` tuples.
305
-
306
- **Parameters:**
307
- - `store`: Store instance created by `defineStore`
308
-
309
- **Returns:** Object where each key maps to a `[state, setter]` tuple, preserving the correct type for each property
310
-
311
- ### Plugins
312
-
313
- Plugins allow you to extend store functionality. You can use plugins globally or per-store.
314
-
315
- #### Global Plugin Registration
316
-
317
- ```tsx
318
- import valtio from 'valtio-define'
319
- import { persist } from 'valtio-define/plugins'
320
-
321
- // Register plugin globally - applies to all stores
322
- valtio.use(persist())
323
- ```
324
-
325
- #### Per-Store Plugin Registration
326
-
327
- ```tsx
328
- import { defineStore } from 'valtio-define'
329
- import { persist } from 'valtio-define/plugins'
330
-
331
- const store = defineStore({
332
- state: () => ({ count: 0 }),
333
- })
334
-
335
- // Register plugin for this specific store
336
- store.use(persist())
337
- ```
338
-
339
- #### Creating Custom Plugins
340
-
341
- ```tsx
342
- import type { Plugin } from 'valtio-define'
343
-
344
- function myPlugin() {
345
- ({ store, options }: PluginContext) => {
346
- // Access store methods
347
- store.$subscribe((state) => {
348
- console.log('State changed:', state)
349
- })
350
-
351
- // Access store options
352
- if (options.someOption) {
353
- // Do something
354
- }
355
- }
356
- }
357
-
358
- declare module 'valtio-define' {
359
- export interface StoreDefine<S extends object, A extends ActionsTree, G extends Getters<any>> {
360
- myPlugin?: {
361
- someOption?: boolean
362
- }
363
- }
364
- }
365
-
366
- // Use the plugin
367
- use(myPlugin())
368
- ```
369
-
370
- **Plugin Context:**
371
- - `context.store`: The store instance with all methods (`$state`, `$patch`, `$subscribe`, etc.)
372
- - `context.options`: The original store definition options
373
-
374
- ## License
375
-
376
- [MIT](./LICENSE) License © [Hairyf](https://github.com/hairyf)
377
-
378
- <!-- Badges -->
379
-
380
- [npm-version-src]: https://img.shields.io/npm/v/valtio-define?style=flat&colorA=080f12&colorB=1fa669
381
- [npm-version-href]: https://npmjs.com/package/valtio-define
382
- [npm-downloads-src]: https://img.shields.io/npm/dm/valtio-define?style=flat&colorA=080f12&colorB=1fa669
383
- [npm-downloads-href]: https://npmjs.com/package/valtio-define
384
- [bundle-src]: https://img.shields.io/bundlephobia/minzip/valtio-define?style=flat&colorA=080f12&colorB=1fa669&label=minzip
385
- [bundle-href]: https://bundlephobia.com/result?p=valtio-define
386
- [license-src]: https://img.shields.io/github/license/hairyf/valtio-define.svg?style=flat&colorA=080f12&colorB=1fa669
387
- [license-href]: https://github.com/hairyf/valtio-define/blob/main/LICENSE
388
- [jsdocs-src]: https://img.shields.io/badge/jsdocs-reference-080f12?style=flat&colorA=080f12&colorB=1fa669
389
- [jsdocs-href]: https://www.jsdocs.io/package/valtio-define
390
- [coverage-src]: https://codecov.io/gh/hairyf/valtio-define/graph/badge.svg?token=PG5YIEEEHJ
391
- [coverage-href]: https://codecov.io/gh/hairyf/valtio-define