Open skirtles-code opened 4 days ago
File | Size | Gzip | Brotli |
---|---|---|---|
runtime-dom.global.prod.js | 100 kB (+189 B) | 38 kB (+64 B) | 34.3 kB (+55 B) |
vue.global.prod.js | 158 kB (+189 B) | 57.9 kB (+79 B) | 51.5 kB (+80 B) |
Name | Size | Gzip | Brotli |
---|---|---|---|
createApp (CAPI only) | 47.2 kB (+1 B) | 18.4 kB (+6 B) | 16.8 kB (-1 B) |
createApp | 55.2 kB (+1 B) | 21.4 kB (+4 B) | 19.5 kB (+44 B) |
createSSRApp | 59.3 kB (+1 B) | 23.1 kB (+4 B) | 21 kB (+2 B) |
defineCustomElement | 60.1 kB (+1 B) | 22.9 kB (+7 B) | 20.9 kB (+2 B) |
overall | 69.1 kB (+1 B) | 26.5 kB (+4 B) | 24.1 kB (-12 B) |
``` pnpm add https://pkg.pr.new/@vue/compiler-core@12420 ```
``` pnpm add https://pkg.pr.new/@vue/compiler-dom@12420 ```
``` pnpm add https://pkg.pr.new/@vue/compiler-ssr@12420 ```
``` pnpm add https://pkg.pr.new/@vue/compiler-sfc@12420 ```
``` pnpm add https://pkg.pr.new/@vue/reactivity@12420 ```
``` pnpm add https://pkg.pr.new/@vue/runtime-core@12420 ```
``` pnpm add https://pkg.pr.new/@vue/runtime-dom@12420 ```
``` pnpm add https://pkg.pr.new/@vue/server-renderer@12420 ```
``` pnpm add https://pkg.pr.new/@vue/shared@12420 ```
``` pnpm add https://pkg.pr.new/vue@12420 ```
``` pnpm add https://pkg.pr.new/@vue/compat@12420 ```
commit: 9ceb497
/ecosystem-ci run
📝 Ran ecosystem CI: Open
suite | result | latest scheduled |
---|---|---|
language-tools | :white_check_mark: success | :white_check_mark: success |
nuxt | :white_check_mark: success | :white_check_mark: success |
pinia | :white_check_mark: success | :white_check_mark: success |
primevue | :white_check_mark: success | :white_check_mark: success |
quasar | :white_check_mark: success | :white_check_mark: success |
radix-vue | :white_check_mark: success | :white_check_mark: success |
router | :white_check_mark: success | :white_check_mark: success |
test-utils | :white_check_mark: success | :white_check_mark: success |
vant | :white_check_mark: success | :white_check_mark: success |
vite-plugin-vue | :white_check_mark: success | :white_check_mark: success |
vitepress | :white_check_mark: success | :white_check_mark: success |
vue-i18n | :white_check_mark: success | :white_check_mark: success |
vue-macros | :white_check_mark: success | :white_check_mark: success |
vuetify | :white_check_mark: success | :white_check_mark: success |
vueuse | :white_check_mark: success | :white_check_mark: success |
vue-simple-compiler | :white_check_mark: success | :white_check_mark: success |
This PR has some performance impact on ref. The baseline is the main branch.
✓ packages/reactivity/__benchmarks__/ref.bench.ts (4) 11856ms
✓ ref (4) 11854ms
name hz min max mean p75 p99 p995 p999 rme samples
· create ref 11,642,281.81 0.0000 0.2558 0.0001 0.0001 0.0001 0.0001 0.0002 ±0.21% 5821141 [0.55x] ⇓
create ref 21,231,067.58 0.0000 0.1998 0.0000 0.0000 0.0001 0.0001 0.0001 ±0.21% 10615534 (baseline)
· write ref 10,862,161.63 0.0000 2.2381 0.0001 0.0001 0.0001 0.0001 0.0002 ±0.95% 5431081 [0.53x] ⇓
write ref 20,480,924.69 0.0000 0.5687 0.0000 0.0000 0.0001 0.0001 0.0002 ±0.55% 10240463 (baseline)
· read ref 15,235,715.02 0.0000 0.7686 0.0001 0.0001 0.0001 0.0002 0.0002 ±0.59% 7617858 [0.61x] ⇓
read ref 24,909,611.96 0.0000 0.7011 0.0000 0.0000 0.0000 0.0001 0.0001 ±0.76% 12454807 (baseline)
· write/read ref 10,840,440.94 0.0000 0.3820 0.0001 0.0001 0.0001 0.0001 0.0002 ±0.39% 5420221 [0.53x] ⇓
write/read ref 20,325,089.63 0.0000 0.6985 0.0000 0.0000 0.0001 0.0001 0.0002 ±0.71% 10162545 (baseline)
with the following steps:
1. switch to main branch
2. nr prebench-compare
3. nr bench ref
4. switch to this PR
5. nr prebench-compare
6. nr bench-compare ref
envinfo:
System:
OS: macOS 14.5
CPU: (8) arm64 Apple M1
Memory: 127.44 MB / 16.00 GB
Shell: 5.9 - /bin/zsh
Binaries:
Node: 22.7.0 - /usr/local/bin/node
@edison1105 Would you be able to try that performance benchmark again?
I tried running it locally, but it seems to get stuck running bench-compare
. It starts off OK, then it just gets stuck at 100% CPU and never completes.
I don't think my changes should impact those benchmarks. The benchmark you mentioned seems to be testing ref()
, which should be unchanged by this PR.
I would expect some performance impact on toRef()
when passing toRef(obj, 'property')
, but that doesn't seem to be what's tested in the benchmarks.
@skirtles-code
I tested it again. This time, I repeated step 6 above three times, and the results showed that performance was not affected. Below are the results from the third execution.
The above test results were obtained from the first time run nr bench-compare ref
. It is strange that there is a significant performance difference.
✓ packages/reactivity/__benchmarks__/ref.bench.ts (4) 16730ms
✓ ref (4) 16728ms
name hz min max mean p75 p99 p995 p999 rme samples
· create ref 21,076,099.66 0.0000 0.2064 0.0000 0.0000 0.0001 0.0001 0.0002 ±0.23% 10538050 [1.00x] ⇓
create ref 21,152,011.37 0.0000 0.5231 0.0000 0.0000 0.0001 0.0001 0.0002 ±0.38% 10576006 (baseline)
· write ref 20,557,804.48 0.0000 0.4285 0.0000 0.0000 0.0001 0.0001 0.0001 ±0.51% 10278903 [1.02x] ⇑
write ref 20,076,703.63 0.0000 0.5026 0.0000 0.0000 0.0001 0.0001 0.0002 ±0.52% 10038353 (baseline)
· read ref 24,080,925.98 0.0000 0.7341 0.0000 0.0000 0.0000 0.0001 0.0002 ±1.10% 12040464 [0.99x] ⇓
read ref 24,253,846.74 0.0000 1.1237 0.0000 0.0000 0.0000 0.0001 0.0001 ±1.02% 12126924 (baseline)
· write/read ref 19,876,380.25 0.0000 0.5281 0.0001 0.0000 0.0001 0.0001 0.0002 ±0.64% 9938191 [1.03x] ⇑
write/read ref 19,240,027.69 0.0000 2.3183 0.0001 0.0000 0.0001 0.0001 0.0002 ±1.21% 9620095 (baseline)
This PR aims to address several related edge cases.
Case 1
The original motivation came from https://github.com/vuejs/pinia/issues/2812.
Long story short, consider the following code:
The call to
toRef
currently triggers the logging, even if the returned ref is never used:While attempting to fix this, I kept running into other edge cases, mostly involving
toRef
andshallowReactive
/shallowReadonly
. I've tried to fix all of those edge cases too.Case 2
Consider the following:
This should result in
t.value
being1
, but currently it ends up as0
.Case 3
Consider this example:
t.value
should be7
, respecting the default value. But currently it isundefined
.Case 4
This is somewhat separate, but it impacted the tests I wrote for array handling with
toRef
.Consider the following:
Arrays don't unwrap refs used as elements, but they do unwrap arrays added using custom properties such as
foo
. Essentially, custom properties on reactive arrays behave just like properties of normal reactive objects. Apart from in the case outlined above, where the ref is replaced rather than updated byarr.foo = 2
. I've changed this inbaseHandlers.ts
, so that updating a custom property on an array behaves the same as for an object:Notes on the changes
The key change is to move the logic for handling nested refs from
propertyToRef
to insideObjectRefImpl
.Detecting whether a source will automatically unwrap refs is a bit tricky. It isn't sufficient just to check for
isShallow
, as you could haveshallowReadonly
wrapped aroundreactive
. Instead I've recursively checked each wrapper proxy to check whether any level would unwrap.As noted earlier, arrays also pose a specific challenge, as they don't unwrap elements even inside
reactive
orreadonly
.There is one existing test case that no longer passes. Specifically, this one:
This is expecting the exact same ref to be returned by
toRef
. But returning the same ref is the underlying cause of most of the edge cases outlined above. From what I can tell, the original motivation for that test case was just to ensure that nested refs are unwrapped, not that they need to be===
. Returning an equivalent ref should be sufficient.I do wonder whether there's an easier way to implement all of this, but currently I'm not seeing it.