-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
restructure directories so that `mod.ts` now exports all of the important stuff and works with `typedoc` documentation generator port over signal test from `kitchensink_ts` as `./test/legacy_signal.test.ts` move the test in `mod.ts` to `./test/simple_signal.test.ts` add more `ts-ignore` so that `deno task test` does not fail change dependance on `kitchensink_ts` directly from github repo HEAD to `kitchensink_ts v0.7.0` in `deno.land/x/` remove JOJO reference in `signal.ts`... NANI! repo is ready to go public and be released onto `deno.land/x/`
- Loading branch information
Showing
12 changed files
with
308 additions
and
105 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,32 +1,23 @@ | ||
export { | ||
bindMethodToSelfByName, | ||
bind_array_clear, | ||
bind_array_push, | ||
bind_array_pop, | ||
bind_array_push, | ||
bind_map_clear, | ||
bind_map_get, | ||
bind_map_set, | ||
bind_set_add, | ||
bind_set_clear, | ||
bind_set_delete, | ||
bind_set_has | ||
} from "https://raw.githubusercontent.com/omar-azmi/kitchensink_ts/main/src/binder.ts" | ||
export { THROTTLE_REJECT, throttle } from "https://raw.githubusercontent.com/omar-azmi/kitchensink_ts/main/src/browser.ts" | ||
export { object_assign, array_isArray } from "https://raw.githubusercontent.com/omar-azmi/kitchensink_ts/main/src/builtin_aliases_deps.ts" | ||
export { prototypeOfClass } from "https://raw.githubusercontent.com/omar-azmi/kitchensink_ts/main/src/struct.ts" | ||
export * as typedefs from "https://raw.githubusercontent.com/omar-azmi/kitchensink_ts/main/src/typedefs.ts" | ||
export type { CallableFunctionsOf, ConstructorOf, MethodsOf } from "https://raw.githubusercontent.com/omar-azmi/kitchensink_ts/main/src/typedefs.ts" | ||
} from "https://deno.land/x/kitchensink_ts@v0.7.0/binder.ts" | ||
export { THROTTLE_REJECT, throttle } from "https://deno.land/x/kitchensink_ts@v0.7.0/browser.ts" | ||
export { array_isArray, noop, object_assign, object_keys, object_values } from "https://deno.land/x/kitchensink_ts@v0.7.0/builtin_aliases_deps.ts" | ||
export { prototypeOfClass } from "https://deno.land/x/kitchensink_ts@v0.7.0/struct.ts" | ||
export * as typedefs from "https://deno.land/x/kitchensink_ts@v0.7.0/typedefs.ts" | ||
export type { CallableFunctionsOf, ConstructorOf, MethodsOf, StaticImplements } from "https://deno.land/x/kitchensink_ts@v0.7.0/typedefs.ts" | ||
|
||
|
||
export const enum DEBUG { | ||
LOG = 0, | ||
} | ||
|
||
export const { | ||
keys: object_keys, | ||
values: object_values, | ||
} = Object | ||
|
||
export type StaticImplements<CONSTRUCTOR extends new (...args: any[]) => any, CLASS extends CONSTRUCTOR> = InstanceType<CONSTRUCTOR> | ||
|
||
export type SubPropertyMapper<T, PROP extends keyof T[keyof T]> = { [K in keyof T]: T[K][PROP] } |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,44 +1,12 @@ | ||
/** */ | ||
|
||
import { Context } from "./context.ts" | ||
import { EffectSignal_Factory, LazySignal_Factory, MemoSignal_Factory, StateSignal_Factory } from "./signal.ts" | ||
|
||
const | ||
ctx = new Context(), | ||
createState = ctx.addClass(StateSignal_Factory), | ||
createMemo = ctx.addClass(MemoSignal_Factory), | ||
createLazy = ctx.addClass(LazySignal_Factory), | ||
createEffect = ctx.addClass(EffectSignal_Factory), | ||
setFn = ctx.dynamic.setFn | ||
|
||
const | ||
[, A, setA] = createState(1, { name: "A" }), | ||
[, B, setB] = createState(2, { name: "B" }), | ||
[, C, setC] = createState(3, { name: "C" }), | ||
[, H] = createMemo((id) => (A(id) + G(id)), { name: "H" }), | ||
[, G] = createMemo((id) => (- D(id) + E(id) + 100), { name: "G" }), | ||
[, D] = createMemo((id) => (A(id) * 0 + 10), { name: "D" }), | ||
[, E] = createMemo((id) => (B(id) + F(id) + D(id) + C(id)), { name: "E" }), | ||
[, F] = createMemo((id) => (C(id) + 20), { name: "F" }), | ||
[, I] = createMemo((id) => (F(id) - 100), { name: "I" }), | ||
[idK, K, fireK] = createEffect((id) => { console.log("this is effect K, broadcasting", A(id), B(id), E(id)); J(id) }, { name: "K", dynamic: true }), | ||
[, J, fireJ] = createEffect((id) => { console.log("this is effect J, broadcasting", H(id), D(id), E(id)) }, { name: "J" }) | ||
|
||
I() | ||
H() | ||
K() | ||
fireK() | ||
setFn(idK, () => { console.log("effect K is now free of all worldy dependencies, yet it is still fired when one of its previous dependiencies are updated. so saj...") }) | ||
fireK() | ||
|
||
/* | ||
let start = performance.now() | ||
for (let A_value = 0; A_value < 100_000; A_value++) { | ||
setA(A_value) | ||
} | ||
let end = performance.now() | ||
console.log("time:\t", end - start, " ms") // takes 70ms to 130ms for updating signal `A` 100_000 times (with `DEBUG` off) (dfs nodes to update/visit are cached after first run) | ||
setA(10) | ||
setB(10) | ||
/** a equal-calorie clone of the popular reactivity library [SolidJS](https://github.com/solidjs/solid). <br> | ||
* @module | ||
*/ | ||
|
||
export { Context } from "./context.ts" | ||
export type { Context_Batch, Context_Dynamic } from "./context.ts" | ||
export { default_equality, falsey_equality, throttlingEquals } from "./funcdefs.ts" | ||
export type * from "./mapped_signal.ts" | ||
export { RecordMemoSignal_Factory, RecordSignal_Factory, RecordStateSignal_Factory } from "./mapped_signal.ts" | ||
export type * from "./signal.ts" | ||
export { EffectSignal_Factory, LazySignal_Factory, MemoSignal_Factory, SimpleSignal_Factory, StateSignal_Factory } from "./signal.ts" | ||
export type * from "./typedefs.ts" |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,146 @@ | ||
import { assert } from "https://deno.land/std/testing/asserts.ts" | ||
import { Context } from "../src/context.ts" | ||
import { EffectSignal_Factory, LazySignal_Factory, MemoSignal_Factory, StateSignal_Factory, } from "../src/signal.ts" | ||
|
||
const | ||
ctx = new Context(), | ||
createState = ctx.addClass(StateSignal_Factory), | ||
createMemo = ctx.addClass(MemoSignal_Factory), | ||
createLazy = ctx.addClass(LazySignal_Factory), | ||
createEffect = ctx.addClass(EffectSignal_Factory) | ||
|
||
Deno.test("create a signal and test getter and setter functions", () => { | ||
const [, getValue, setValue] = createState<number>(0) | ||
assert(getValue() === 0) | ||
setValue(42) | ||
assert(getValue() === 42) | ||
}) | ||
|
||
Deno.test("create a memo and test its memorization and reactivity with signals", () => { | ||
let counter = 0 | ||
const [, memo1] = createMemo((id) => (counter++)) | ||
assert(memo1() === 0) | ||
assert(memo1() === 0) // memoized value remains the same | ||
|
||
const [, getCounter, setCounter] = createState<number>(0) | ||
let times_memo_was_run: number = 0 | ||
const [, memo2] = createMemo((id) => { | ||
times_memo_was_run++ | ||
let double = getCounter(id) * 2 | ||
return double | ||
}) | ||
assert((memo2() === 0) && (times_memo_was_run === 1 as number)) | ||
setCounter(5) | ||
assert((memo2() === 10) && (times_memo_was_run === 2 as number)) | ||
setCounter(5.0) // same value as before, therefore, signal should NOT notify its `memo2` observer to rerun | ||
assert((memo2() === 10) && (times_memo_was_run === 2 as number)) | ||
}) | ||
|
||
Deno.test("create and execute an effect", () => { | ||
// test option `{ defer?: false }`, to fire the effect right after initialization | ||
let times_effect_was_run: number = 0 | ||
const [, getEffect1, fireEffect1] = createEffect((id) => { | ||
times_effect_was_run++ | ||
}, { defer: false }) | ||
assert(times_effect_was_run === 1) | ||
|
||
const [, getCounter, setCounter] = createState<number>(0) | ||
let times_effect_was_run2: number = 0 | ||
|
||
// test option `{ defer?: true }` and dependance on another effect signal | ||
const [, getEffect2, fireEffect2] = createEffect((id) => { | ||
getEffect1(id) // here, we declare that we are depending on `effect1`, therefore `effect2` must rerun each time `effect1` is run | ||
times_effect_was_run2++ | ||
console.log(times_effect_was_run2) | ||
let double = getCounter(id) * 2 | ||
return undefined | ||
}) | ||
assert(times_effect_was_run2 === 0 && times_effect_was_run === 1) | ||
setCounter(2) | ||
assert(times_effect_was_run2 === 0) // because `effect2` has never been run before (due to `{ defer: undefined }`), it must at least run once so as to capture all of its dependencies | ||
fireEffect2() // dependencies of `effect2` have been captured now, and `effect2` will now react to any of its two dependencies | ||
setCounter(5) | ||
assert(times_effect_was_run2 === 1 as number) | ||
setCounter(5.0) //same value as before, therefore, signal should NOT notify its `effect2` observer to rerun | ||
assert(times_effect_was_run2 === 1 as number) | ||
//TODO trigger cleanup and implement async testing | ||
}) | ||
|
||
Deno.test("batch set", () => { | ||
let counter = 0 | ||
const [, getCounter1, setCounter1] = createState<number>(0) | ||
const [, getCounter2, setCounter2] = createState<number>(0) | ||
const [, getCounter3, setCounter3] = createState<number>(0) | ||
|
||
createEffect((id) => { | ||
getCounter1(id) | ||
getCounter2(id) | ||
getCounter3(id) | ||
counter++ | ||
}, { defer: false }) | ||
assert(counter === 1) | ||
// begin batching. this prevents any update cycle from firing, until `endBatching` is called, | ||
// upon which all fired events are ran all at once (of course, still respecting their topological ordering) | ||
ctx.batch.startBatching() | ||
setCounter1(1) | ||
setCounter2(2) | ||
setCounter3(3) | ||
ctx.batch.endBatching() | ||
assert((getCounter1() === 1) && (getCounter2() === 2) && (getCounter3() === 3)) | ||
assert(counter === 2 as number) | ||
}) | ||
|
||
Deno.test("untrack reactive dependencies", () => { | ||
let counter = 0 | ||
const [, getCounter1, setCounter1] = createState<number>(0) | ||
const [, getCounter2, setCounter2] = createState<number>(0) | ||
const [, getCounter3, setCounter3] = createState<number>(0) | ||
createEffect((id) => { | ||
// not passing an `id` to dependency signals (or passing `id = 0`) will result in the signal not becoming a dependency | ||
getCounter1() | ||
getCounter2() | ||
getCounter3() | ||
counter++ | ||
}, { defer: false }) | ||
assert(counter === 1) | ||
setCounter1(1) | ||
setCounter2(2) | ||
setCounter3(3) | ||
assert((getCounter1() === 1) && (getCounter2() === 2) && (getCounter3() === 3)) | ||
assert(counter === 1) // had `id` been passed to all 3 signals, this would have been: `counter === 1` | ||
}) | ||
|
||
/* | ||
Deno.test("evaluate function with explicit dependencies", () => { | ||
let counter = 0 | ||
const [, getA, setA] = createState<number>(0) | ||
const [, getB, setB] = createState<number>(0) | ||
const [, getC, setC] = createState<number>(0) | ||
const dependencyFn = createMemo(dependsOn([getA, getB, getC], () => { | ||
counter++ | ||
return getA() + getB() | ||
})) | ||
setA(1) | ||
setB(2) | ||
setC(3) | ||
assert(counter === 4) | ||
assert(dependencyFn() === 3) | ||
}) | ||
Deno.test("create effect with explicit dependencies", () => { | ||
let counter = 0 | ||
const [getA, setA] = createState<number>(0) | ||
const [getB, setB] = createState<number>(0) | ||
const [getC, setC] = createState<number>(0) | ||
createEffect(dependsOn([getA, getB, getC], () => { | ||
counter++ | ||
})) | ||
assert(counter === 1 as number) | ||
setA(1) | ||
assert(counter === 2 as number) | ||
setB(2) | ||
assert(counter === 3 as number) | ||
setC(3) | ||
assert(counter === 4 as number) | ||
}) | ||
*/ |
Oops, something went wrong.