Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix!: remove handling of types not present in type signatures #70

Merged
merged 12 commits into from
Jan 26, 2025

Conversation

aleclarson
Copy link
Member

@aleclarson aleclarson commented Jul 3, 2024

Tip

The owner of this PR can publish a preview release by commenting /publish in this PR. Afterwards, anyone can try it out by running pnpm add radashi@pr<PR_NUMBER>.

Summary

This PR removes any implicit handling of null/undefined input values.

Some notes:

  • replace and replaceOrAppend still skip an undefined item argument
  • Many if (!array.length) checks were also removed, preferring brevity over performance for those code paths. I'd be fine with reinstating these checks on a case-by-case basis if benchmarks prove a substantial benefit and the frequency of empty arrays being passed is deemed common.

See the linked discussion for the philosophy behind this change.

Related issue, if any:

https://github.com/orgs/radashi-org/discussions/48

For any code change,

  • Related documentation has been updated, if needed
  • Related tests have been added or updated, if needed
  • Related benchmarks have been added or updated, if needed

Does this PR introduce a breaking change?

Yes

As of now, a codemod will not be provided. Implicit nullish handling was never actually documented, so I assume most Radash users will not be affected.

Bundle impact

Status File Size 1 Difference
M src/array/alphabetical.ts 171 -15 (-8%)
M src/array/boil.ts 68 -12 (-15%)
M src/array/counting.ts 105 -5 (-5%)
M src/array/diff.ts 112 -97 (-46%)
M src/array/first.ts 61 -1 (-2%)
M src/array/fork.ts 93 -5 (-5%)
M src/array/intersects.ts 135 -19 (-12%)
M src/array/last.ts 69 -1 (-1%)
M src/array/merge.ts 138 -72 (-34%)
M src/array/replace.ts 146 -15 (-9%)
M src/array/replaceOrAppend.ts 166 -27 (-14%)
M src/array/select.ts 131 -15 (-10%)
M src/array/selectFirst.ts 130 -13 (-9%)
M src/array/sort.ts 116 -15 (-11%)
M src/array/toggle.ts 223 -31 (-12%)
M src/array/unzip.ts 155 -26 (-14%)
M src/array/zipToObject.ts 188 -26 (-12%)
M src/async/map.ts 109 -15 (-12%)
M src/async/reduce.ts 239 -10 (-4%)
M src/number/inRange.ts 83 -102 (-55%)
M src/number/max.ts 113 -12 (-10%)
M src/number/min.ts 113 -12 (-10%)
M src/object/assign.ts 347 -26 (-7%)
M src/object/clone.ts 198 -130 (-40%)
M src/object/construct.ts 537 -156 (-23%)
M src/object/crush.ts 285 -5 (-2%)
M src/object/invert.ts 89 -5 (-5%)
M src/object/keys.ts 382 -15 (-4%)
M src/object/listify.ts 106 -39 (-27%)
M src/object/mapEntries.ts 122 -5 (-4%)
M src/object/omit.ts 97 -9 (-8%)
M src/object/pick.ts 251 -15 (-6%)
M src/object/set.ts 465 -151 (-25%)
M src/object/shake.ts 115 -5 (-4%)
M src/string/camel.ts 280 -77 (-22%)
M src/string/capitalize.ts 123 -29 (-19%)
M src/string/dash.ts 257 -77 (-23%)
M src/string/pascal.ts 186 -15 (-7%)
M src/string/snake.ts 346 -95 (-22%)
M src/string/title.ts 239 -34 (-12%)
M src/string/trim.ts 135 -15 (-10%)

Footnotes

  1. Function size includes the import dependencies of the function.

@aleclarson aleclarson added the BREAKING CHANGE Not backwards compatible label Jul 3, 2024
@aleclarson aleclarson marked this pull request as draft July 3, 2024 18:08
@aleclarson aleclarson force-pushed the main branch 2 times, most recently from 2154f96 to 6a4b4f6 Compare July 12, 2024 00:23
@aleclarson aleclarson changed the base branch from main to next July 16, 2024 15:08
@aleclarson aleclarson force-pushed the breaking/remove-undefined-checks branch from a6d708e to 85bd936 Compare January 26, 2025 03:29
@aleclarson aleclarson marked this pull request as ready for review January 26, 2025 03:54
@radashi-bot
Copy link

radashi-bot commented Jan 26, 2025

Benchmark Results

Name Current Baseline Change
alphabetical ▶︎ with ascending order 2,244,618.95 ops/sec ±0.53% 2,262,642.45 ops/sec ±0.57% 🔗 🐢 -0.8%
alphabetical ▶︎ with descending order 2,167,145.26 ops/sec ±1.71% 2,299,565.74 ops/sec ±0.63% 🔗 🐢 -5.76%
boil ▶︎ with non-empty array 4,617,895.97 ops/sec ±0.52% 5,601,425.98 ops/sec ±0.41% 🔗 🐢 -17.56%
boil ▶︎ with empty array 4,965,288.42 ops/sec ±0.16% 6,259,328.67 ops/sec ±0.14% 🔗 🐢 -20.67%
counting ▶︎ with valid input 2,964,775.69 ops/sec ±0.6% 3,223,445.38 ops/sec ±0.6% 🔗 🐢 -8.02%
diff ▶︎ with entirely different arrays 2,857,264 ops/sec ±0.11% 3,136,555.76 ops/sec ±0.63% 🔗 🐢 -8.9%
diff ▶︎ with identity function 2,548,275.08 ops/sec ±0.3% 2,507,880.48 ops/sec ±0.31% 🔗 🚀 +1.61%
first ▶︎ with non-empty array 4,947,281.87 ops/sec ±0.09% 5,978,646.31 ops/sec ±0.1% 🔗 🐢 -17.25%
first ▶︎ with empty array and a default value 4,957,815.56 ops/sec ±0.09% 6,132,559.47 ops/sec ±0.09% 🔗 🐢 -19.16%
fork ▶︎ with empty array 5,009,355.76 ops/sec ±0.08% 5,748,687.48 ops/sec ±0.09% 🔗 🐢 -12.86%
fork ▶︎ with non-empty array 3,881,187.17 ops/sec ±0.13% 4,333,099.28 ops/sec ±0.11% 🔗 🐢 -10.43%
intersects ▶︎ with mixed arrays 4,528,408.8 ops/sec ±0.09% 5,462,312.5 ops/sec ±0.09% 🔗 🐢 -17.1%
intersects ▶︎ with no common items 4,479,298.67 ops/sec ±0.17% 5,511,979.79 ops/sec ±0.12% 🔗 🐢 -18.74%
intersects ▶︎ with custom identity function 2,013,525.34 ops/sec ±0.38% 2,169,024.49 ops/sec ±0.4% 🔗 🐢 -7.17%
intersects ▶︎ with object arrays 4,004,623.1 ops/sec ±1.39% 5,291,786.87 ops/sec ±0.61% 🔗 🐢 -24.32%
last ▶︎ with valid input 5,057,516.6 ops/sec ±0.09% 5,729,410.92 ops/sec ±0.13% 🔗 🐢 -11.73%
last ▶︎ with empty list 5,009,970.65 ops/sec ±0.09% 5,932,029.47 ops/sec ±0.09% 🔗 🐢 -15.54%
merge ▶︎ with two empty array inputs 2,304,845.49 ops/sec ±0.29% 2,481,622.56 ops/sec ±0.27% 🔗 🐢 -7.12%
merge ▶︎ with complex inputs 1,784,682.6 ops/sec ±0.28% 1,909,861.3 ops/sec ±0.17% 🔗 🐢 -6.55%
merge ▶︎ with long arrays 413.1 ops/sec ±1.66% 422.79 ops/sec ±1.71% 🔗 🐢 -2.29%
replace ▶︎ with undefined new item 4,674,360.39 ops/sec ±0.09% 5,614,778.87 ops/sec ±0.16% 🔗 🐢 -16.75%
replace ▶︎ with item by index 4,516,449.58 ops/sec ±0.09% 5,388,528.63 ops/sec ±0.11% 🔗 🐢 -16.18%
replace ▶︎ with item in a list of objects 4,411,037.87 ops/sec ±0.45% 4,968,455.24 ops/sec ±0.44% 🔗 🐢 -11.22%
replaceOrAppend ▶︎ with item at start 4,305,596.96 ops/sec ±0.09% 4,956,122.32 ops/sec ±0.12% 🔗 🐢 -13.13%
replaceOrAppend ▶︎ with item in middle 4,255,899.26 ops/sec ±0.09% 4,759,797.66 ops/sec ±0.09% 🔗 🐢 -10.59%
replaceOrAppend ▶︎ with item at end 4,248,789.93 ops/sec ±0.09% 4,700,415.53 ops/sec ±0.09% 🔗 🐢 -9.61%
replaceOrAppend ▶︎ append item 4,034,261.04 ops/sec ±0.23% 4,583,819.72 ops/sec ±0.13% 🔗 🐢 -11.99%
select ▶︎ with non-empty input list 3,924,485.39 ops/sec ±0.18% 4,264,959.09 ops/sec ±0.63% 🔗 🐢 -7.98%
select ▶︎ with empty input list 4,904,757.48 ops/sec ±0.13% 5,508,716.39 ops/sec ±0.17% 🔗 🐢 -10.96%
select ▶︎ with index 3,177,210.67 ops/sec ±0.34% 3,408,681.95 ops/sec ±0.56% 🔗 🐢 -6.79%
select ▶︎ without a condition callback 3,646,413.89 ops/sec ±0.55% 3,915,219.8 ops/sec ±0.55% 🔗 🐢 -6.87%
selectFirst ▶︎ with non-empty input list 4,203,755.09 ops/sec ±0.48% 4,877,417.74 ops/sec ±0.57% 🔗 🐢 -13.81%
selectFirst ▶︎ with empty input list 4,671,811.83 ops/sec ±0.12% 5,192,315.29 ops/sec ±0.09% 🔗 🐢 -10.02%
selectFirst ▶︎ with index 3,654,814.16 ops/sec ±0.2% 4,194,108.99 ops/sec ±0.13% 🔗 🐢 -12.86%
selectFirst ▶︎ without a condition callback 3,796,631.04 ops/sec ±0.41% 4,176,431.18 ops/sec ±0.42% 🔗 🐢 -9.09%
sort ▶︎ with ascending order 2,462,202.5 ops/sec ±0.51% 2,658,114.36 ops/sec ±0.73% 🔗 🐢 -7.37%
sort ▶︎ with descending order 2,478,447.46 ops/sec ±0.55% 2,645,338.71 ops/sec ±0.54% 🔗 🐢 -6.31%
toggle ▶︎ with item that does not exist 3,834,677.02 ops/sec ±0.65% 4,269,642.48 ops/sec ±0.68% 🔗 🐢 -10.19%
toggle ▶︎ with item that does exist 3,786,620.75 ops/sec ±0.52% 4,293,040.26 ops/sec ±0.52% 🔗 🐢 -11.8%
toggle ▶︎ with item that does exist and custom matcher 3,401,520.61 ops/sec ±0.17% 3,814,576.66 ops/sec ±0.09% 🔗 🐢 -10.83%
toggle ▶︎ with item that does not exist and custom matcher 3,402,986.67 ops/sec ±0.14% 3,804,297.81 ops/sec ±0.47% 🔗 🐢 -10.55%
toggle ▶︎ with strategy prepend 4,047,698.55 ops/sec ±0.38% 4,588,862.63 ops/sec ±0.42% 🔗 🐢 -11.79%
unzip ▶︎ with non-empty arrays 378,067.2 ops/sec ±0.2% 383,937.38 ops/sec ±0.56% 🔗 🐢 -1.53%
zipToObject ▶︎ with non-empty arrays 3,004,722.08 ops/sec ±0.2% 3,176,320.15 ops/sec ±0.58% 🔗 🐢 -5.4%
zipToObject ▶︎ with custom map function 2,962,469.52 ops/sec ±0.37% 3,170,650.99 ops/sec ±0.33% 🔗 🐢 -6.57%
zipToObject ▶︎ with only one value 2,785,043.61 ops/sec ±0.5% 3,044,018.13 ops/sec ±0.47% 🔗 🐢 -8.51%
inRange ▶︎ with non-empty range 1,814,824.92 ops/sec ±0.13% 1,863,404.6 ops/sec ±0.09% 🔗 🐢 -2.61%
inRange ▶︎ with two params 1,771,405.12 ops/sec ±0.09% 1,854,557.93 ops/sec ±0.08% 🔗 🐢 -4.48%
max ▶︎ with list of numbers 4,710,873.29 ops/sec ±0.09% 5,224,009.55 ops/sec ±0.13% 🔗 🐢 -9.82%
max ▶︎ with list of objects 3,410,652.94 ops/sec ±0.6% 3,771,046.17 ops/sec ±0.4% 🔗 🐢 -9.56%
min ▶︎ with list of numbers 4,820,949.98 ops/sec ±0.09% 5,359,351.36 ops/sec ±0.42% 🔗 🐢 -10.05%
min ▶︎ with list of objects 3,486,192.29 ops/sec ±0.61% 3,818,461.26 ops/sec ±0.47% 🔗 🐢 -8.7%
assign ▶︎ with valid input 242,554.4 ops/sec ±0.3% 247,670.24 ops/sec ±0.1% 🔗 🐢 -2.07%
clone ▶︎ with object 1,503,764.22 ops/sec ±0.32% 1,446,097.49 ops/sec ±0.23% 🔗 🚀 +3.99%
clone ▶︎ with class instance 210,612.64 ops/sec ±5.92% 207,288.75 ops/sec ±5.28% 🔗 🚀 +1.6%
construct ▶︎ with valid input 98,459.73 ops/sec ±0.29% 99,277.32 ops/sec ±0.31% 🔗 🐢 -0.82%
crush ▶︎ with valid input 152,825.91 ops/sec ±0.24% 153,806.74 ops/sec ±0.17% 🔗 🐢 -0.64%
invert ▶︎ with empty object 2,429,985.6 ops/sec ±0.33% 2,670,174.24 ops/sec ±0.46% 🔗 🐢 -9%
invert ▶︎ with non-empty object 2,015,322.99 ops/sec ±0.09% 2,201,187.67 ops/sec ±0.09% 🔗 🐢 -8.44%
keys ▶︎ with empty object 1,233,189.53 ops/sec ±0.24% 1,274,409.83 ops/sec ±0.51% 🔗 🐢 -3.23%
keys ▶︎ with non-empty object 214,337.32 ops/sec ±0.32% 214,121.75 ops/sec ±0.27% 🔗 🚀 +0.1%
listify ▶︎ with empty object 2,509,295.55 ops/sec ±0.16% 2,812,372.58 ops/sec ±0.29% 🔗 🐢 -10.78%
listify ▶︎ with non-empty object 1,562,291.63 ops/sec ±0.5% 1,678,352.29 ops/sec ±0.38% 🔗 🐢 -6.92%
mapEntries ▶︎ with valid input 1,203,950.6 ops/sec ±0.32% 1,216,657.36 ops/sec ±0.54% 🔗 🐢 -1.04%
omit ▶︎ with empty keys 4,906,778.98 ops/sec ±0.14% 5,659,221.99 ops/sec ±0.09% 🔗 🐢 -13.3%
omit ▶︎ with specific keys 1,896,000.17 ops/sec ±0.44% 2,005,328.7 ops/sec ±0.38% 🔗 🐢 -5.45%
pick ▶︎ with empty keys 3,655,397.45 ops/sec ±0.55% 3,970,519.65 ops/sec ±0.46% 🔗 🐢 -7.94%
pick ▶︎ with key not in object 2,016,723.52 ops/sec ±0.41% 2,138,971.96 ops/sec ±0.4% 🔗 🐢 -5.72%
pick ▶︎ with one key not in object 1,368,018.21 ops/sec ±0.09% 1,416,503.98 ops/sec ±0.16% 🔗 🐢 -3.42%
set ▶︎ with simple path 1,349,297.81 ops/sec ±0.23% 1,383,602.75 ops/sec ±0.25% 🔗 🐢 -2.48%
set ▶︎ with deep path 745,047.09 ops/sec ±0.34% 766,682.9 ops/sec ±0.33% 🔗 🐢 -2.82%
set ▶︎ with array index path 519,380.63 ops/sec ±0.26% 517,667.64 ops/sec ±0.3% 🔗 🚀 +0.33%
set ▶︎ with numeric key 715,297.54 ops/sec ±0.1% 736,185.52 ops/sec ±0.09% 🔗 🐢 -2.84%
shake ▶︎ with valid input 1,726,894.67 ops/sec ±0.34% 1,730,603.38 ops/sec ±0.59% 🔗 🐢 -0.21%
shake ▶︎ with filter function input 1,744,030.77 ops/sec ±0.55% 1,855,686.81 ops/sec ±0.34% 🔗 🐢 -6.02%
camel ▶︎ with valid input 1,303,518.5 ops/sec ±0.35% 1,333,871.89 ops/sec ±0.34% 🔗 🐢 -2.28%
capitalize ▶︎ with valid input 3,594,142.65 ops/sec ±0.09% 3,949,633.83 ops/sec ±0.15% 🔗 🐢 -9%
dash ▶︎ with valid input 1,461,295.58 ops/sec ±0.09% 1,461,157.54 ops/sec ±0.6% 🔗 🚀 +0.01%
pascal ▶︎ with valid input 1,281,262.58 ops/sec ±0.19% 1,316,329.12 ops/sec ±0.13% 🔗 🐢 -2.66%
pascal ▶︎ with camelCase input 2,419,522.22 ops/sec ±0.31% 2,526,031.87 ops/sec ±0.25% 🔗 🐢 -4.22%
pascal ▶︎ with non alphanumerics 733,487.11 ops/sec ±0.14% 751,821.6 ops/sec ±0.14% 🔗 🐢 -2.44%
snake ▶︎ with valid input 1,220,937.59 ops/sec ±0.26% 1,253,671.87 ops/sec ±0.56% 🔗 🐢 -2.61%
snake ▶︎ with numbers and special characters (no split on number) 1,145,978.29 ops/sec ±0.26% 1,203,171.42 ops/sec ±0.25% 🔗 🐢 -4.75%
title ▶︎ with valid input 1,120,949.09 ops/sec ±0.63% 1,144,289.5 ops/sec ±0.65% 🔗 🐢 -2.04%
trim ▶︎ with valid input 801,629.13 ops/sec ±0.11% 820,398 ops/sec ±0.1% 🔗 🐢 -2.29%
trim ▶︎ with a specified character 958,821.27 ops/sec ±0.09% 988,620.18 ops/sec ±0.39% 🔗 🐢 -3.01%
trim ▶︎ with two special characters 744,824.25 ops/sec ±0.41% 767,052.66 ops/sec ±0.09% 🔗 🐢 -2.9%

Performance regressions of 30% or more should be investigated, unless they were anticipated. Smaller regressions may be due to normal variability, as we don't use dedicated CI infrastructure.

@aleclarson aleclarson force-pushed the breaking/remove-undefined-checks branch from 38dd7b8 to 0e05f8e Compare January 26, 2025 05:29
@aleclarson aleclarson changed the title refactor!: remove implicit nullish handling fix!: remove handling of types not present in type signatures Jan 26, 2025
@aleclarson aleclarson merged commit be86c34 into next Jan 26, 2025
8 checks passed
@aleclarson
Copy link
Member Author

This PR has been released in radashi@next.

pnpm add radashi@next -E

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
BREAKING CHANGE Not backwards compatible
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants