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

feat: Spawn layout evaluation #2348

Merged
merged 39 commits into from
Feb 18, 2025
Merged

feat: Spawn layout evaluation #2348

merged 39 commits into from
Feb 18, 2025

Conversation

AdamGS
Copy link
Contributor

@AdamGS AdamGS commented Feb 13, 2025

very hacky demo

@AdamGS AdamGS added the benchmark Run benchmarks on this branch label Feb 13, 2025
@github-actions github-actions bot removed the benchmark Run benchmarks on this branch label Feb 13, 2025
Copy link
Contributor

github-actions bot commented Feb 13, 2025

Benchmarks: TPC-H

Table of Results
name PR a57d067 base 489262d ratio (PR/base) unit
tpch_q01/arrow 572915978 6.31692e+08 0.906954 ns
tpch_q01/parquet 777981174 8.41168e+08 0.924882 ns
tpch_q01/vortex-file-compressed 498870537 5.76502e+08 0.86534 ns
tpch_q02/arrow 147541098 1.77586e+08 0.830816 ns
tpch_q02/parquet 188707251 2.07002e+08 0.911618 ns
tpch_q02/vortex-file-compressed 157651088 1.77407e+08 0.888641 ns
tpch_q03/arrow 186041904 2.08549e+08 0.892076 ns
tpch_q03/parquet 388515067 4.35395e+08 0.892328 ns
tpch_q03/vortex-file-compressed 233211880 2.53796e+08 0.918896 ns
tpch_q04/arrow 185141093 2.13387e+08 0.867631 ns
tpch_q04/parquet 221373377 2.49796e+08 0.886216 ns
tpch_q04/vortex-file-compressed 166654355 1.78547e+08 0.933391 ns
tpch_q05/arrow 350306315 3.97522e+08 0.881225 ns
tpch_q05/parquet 531480517 5.91394e+08 0.898691 ns
tpch_q05/vortex-file-compressed 373068865 4.133e+08 0.90266 ns
tpch_q06/arrow 26895551 3.0302e+07 0.887585 ns
tpch_q06/parquet 152444309 1.61258e+08 0.945347 ns
tpch_q06/vortex-file-compressed 62982643 7.01127e+07 0.898305 ns
tpch_q07/arrow 660844443 7.42854e+08 0.889602 ns
tpch_q07/parquet 812402234 8.9167e+08 0.911102 ns
tpch_q07/vortex-file-compressed 660670312 7.5421e+08 0.875977 ns
tpch_q08/arrow 276553399 3.0458e+08 0.907982 ns
tpch_q08/parquet 562960458 6.24926e+08 0.900843 ns
tpch_q08/vortex-file-compressed 380263354 3.97346e+08 0.957007 ns
tpch_q09/arrow 499096340 5.78968e+08 0.862045 ns
tpch_q09/parquet 800531965 9.21944e+08 0.868309 ns
tpch_q09/vortex-file-compressed 656203073 7.19125e+08 0.912502 ns
tpch_q10/arrow 281706273 3.14302e+08 0.896293 ns
tpch_q10/parquet 521760652 5.65736e+08 0.922268 ns
tpch_q10/vortex-file-compressed 287404402 3.07934e+08 0.93333 ns
tpch_q11/arrow 146366725 1.70246e+08 0.859738 ns
tpch_q11/parquet 157896109 1.90512e+08 0.828797 ns
tpch_q11/vortex-file-compressed 137643218 1.50133e+08 0.916807 ns
tpch_q12/arrow 186992506 1.92392e+08 0.971936 ns
tpch_q12/parquet 334410150 3.6197e+08 0.92386 ns
tpch_q12/vortex-file-compressed 218982680 2.3541e+08 0.930217 ns
tpch_q13/arrow 186331662 2.15712e+08 0.863798 ns
tpch_q13/parquet 322701243 3.73146e+08 0.864813 ns
tpch_q13/vortex-file-compressed 180810159 2.02782e+08 0.891647 ns
tpch_q14/arrow 41560909 4.81695e+07 0.862805 ns
tpch_q14/parquet 240518865 2.47711e+08 0.970964 ns
tpch_q14/vortex-file-compressed 66932733 7.43645e+07 0.900063 ns
tpch_q15/arrow 75550827 8.20035e+07 0.921312 ns
tpch_q15/parquet 338534572 3.51581e+08 0.962893 ns
tpch_q15/vortex-file-compressed 121337731 1.30688e+08 0.928455 ns
tpch_q16/arrow 105690759 1.19093e+08 0.887461 ns
tpch_q16/parquet 124941802 1.39725e+08 0.8942 ns
tpch_q16/vortex-file-compressed 114645635 1.24521e+08 0.920694 ns
tpch_q17/arrow 671861360 7.63651e+08 0.879801 ns
tpch_q17/parquet 699363622 8.30347e+08 0.842255 ns
tpch_q17/vortex-file-compressed 608914110 6.79223e+08 0.896486 ns
tpch_q18/arrow 1348004198 1.63094e+09 0.826522 ns
tpch_q18/parquet 1548188193 1.78328e+09 0.86817 ns
tpch_q18/vortex-file-compressed 1351949467 1.54395e+09 0.875644 ns
tpch_q19/arrow 153649046 1.6215e+08 0.947571 ns
tpch_q19/parquet 419107491 4.28992e+08 0.97696 ns
tpch_q19/vortex-file-compressed 127404426 1.68892e+08 0.754356 ns
tpch_q20/arrow 179583640 2.13663e+08 0.8405 ns
tpch_q20/parquet 322500195 3.57937e+08 0.900996 ns
tpch_q20/vortex-file-compressed 211398214 2.3531e+08 0.898383 ns
tpch_q21/arrow 1084526377 1.15164e+09 0.941723 ns
tpch_q21/parquet 1170309562 1.3411e+09 0.87265 ns
tpch_q21/vortex-file-compressed 972349028 1.13125e+09 0.859533 ns
tpch_q22/arrow 80720100 8.90485e+07 0.906474 ns
tpch_q22/parquet 112470639 1.23365e+08 0.911691 ns
tpch_q22/vortex-file-compressed 84312891 9.14421e+07 0.922036 ns

Copy link
Contributor

github-actions bot commented Feb 13, 2025

Benchmarks: random_access

Table of Results
name PR a57d067 base 489262d ratio (PR/base) unit
random-access/vortex-tokio-local-disk 2.54366e+06 2.31588e+06 1.09836 ns
random-access/vortex-local-fs 2.75291e+06 2.88728e+06 0.953462 ns
random-access/parquet-tokio-local-disk 2.16002e+08 2.13357e+08 1.0124 ns

Copy link

codspeed-hq bot commented Feb 13, 2025

CodSpeed Performance Report

Merging #2348 will improve performances by 43.48%

Comparing adamg/spawn-evaluate (29e1da2) with develop (bff9fc2)

Summary

⚡ 125 improvements
✅ 136 untouched benchmarks

Benchmarks breakdown

Benchmark BASE HEAD Change
dict_encode_varbin 99.9 ms 75.6 ms +32.13%
dict_encode_view 107 ms 84.9 ms +26.02%
filter_run_end n: 1000, run_count: 250, true_count: 1, ratio: 0.004 62.3 µs 54.4 µs +14.41%
filter_run_end n: 1000, run_count: 250, true_count: 10, ratio: 0.04 62.1 µs 54.4 µs +14.32%
filter_run_end n: 1000, run_count: 250, true_count: 15, ratio: 0.06 62.2 µs 54.4 µs +14.31%
filter_run_end n: 1000, run_count: 250, true_count: 20, ratio: 0.08 62 µs 54.2 µs +14.38%
filter_run_end n: 1000, run_count: 250, true_count: 25, ratio: 0.1 62.4 µs 54.6 µs +14.28%
filter_run_end n: 1000, run_count: 250, true_count: 30, ratio: 0.12 62.2 µs 54.4 µs +14.36%
filter_run_end n: 1000, run_count: 3, true_count: 1, ratio: 0.3333333333333333 51.9 µs 47.2 µs +10.14%
filter_run_end n: 100000, run_count: 1, true_count: 1311, ratio: 1311 383.4 µs 324.6 µs +18.1%
filter_run_end n: 100000, run_count: 1, true_count: 1638, ratio: 1638 383.5 µs 324.8 µs +18.1%
filter_run_end n: 100000, run_count: 1, true_count: 1966, ratio: 1966 383.4 µs 324.7 µs +18.1%
filter_run_end n: 100000, run_count: 1, true_count: 655, ratio: 655 384 µs 325.2 µs +18.07%
filter_run_end n: 100000, run_count: 1, true_count: 66, ratio: 66 383.4 µs 324.6 µs +18.1%
filter_run_end n: 100000, run_count: 1, true_count: 983, ratio: 983 383.8 µs 325 µs +18.08%
filter_run_end n: 100000, run_count: 25000, true_count: 100, ratio: 0.004 1.4 ms 1.1 ms +26.59%
filter_run_end n: 100000, run_count: 25000, true_count: 1000, ratio: 0.04 1.4 ms 1.1 ms +26.57%
filter_run_end n: 100000, run_count: 25000, true_count: 1500, ratio: 0.06 1.4 ms 1.1 ms +26.57%
filter_run_end n: 100000, run_count: 25000, true_count: 2000, ratio: 0.08 1.4 ms 1.1 ms +26.57%
filter_run_end n: 100000, run_count: 25000, true_count: 2500, ratio: 0.1 1.4 ms 1.1 ms +26.56%
... ... ... ... ...

ℹ️ Only the first 20 benchmarks are displayed. Go to the app to view all benchmarks.

impl TaskExecutor for InlineTaskExecutor {
async fn execute(&self, array: &Array, tasks: &[ScanTask]) -> VortexResult<Array> {
fn execute(&self, array: &Array, tasks: &[ScanTask]) -> VortexResult<Array> {
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this is a flyby but seems like it can be blocking now? potentially not even needed but I'm not sure what are your plans for it

@AdamGS AdamGS requested a review from gatesn February 13, 2025 16:57
@AdamGS AdamGS added the benchmark Run benchmarks on this branch label Feb 13, 2025
@github-actions github-actions bot removed the benchmark Run benchmarks on this branch label Feb 13, 2025
Copy link
Contributor

Benchmarks: compress

Table of Results
name PR 206ae5b base 060d713 ratio (PR/base) unit
compress time/wide table cols=10 chunks=1 rows=1000 3.50534e+06 3.46381e+06 1.01199 ns
compress time/wide table cols=10 chunks=1 rows=1000 throughput 0.0342739 0.0346849 0.988152 bytes/ns
parquet_rs-zstd compress time/wide table cols=10 chunks=1 rows=1000 732361 716585 1.02202 ns
parquet_rs-zstd compress time/wide table cols=10 chunks=1 rows=1000 throughput 0.164048 0.167659 0.978459 bytes/ns
decompress time/wide table cols=10 chunks=1 rows=1000 130611 128700 1.01484 ns
decompress time/wide table cols=10 chunks=1 rows=1000 throughput 0.919848 0.933501 0.985374 bytes/ns
parquet_rs-zstd decompress time/wide table cols=10 chunks=1 rows=1000 244739 243053 1.00694 ns
parquet_rs-zstd decompress time/wide table cols=10 chunks=1 rows=1000 throughput 0.490898 0.494303 0.993112 bytes/ns
compress time/wide table cols=100 chunks=1 rows=1000 3.61739e+07 3.53375e+07 1.02367 ns
compress time/wide table cols=100 chunks=1 rows=1000 throughput 0.0332068 0.0339928 0.976878 bytes/ns
parquet_rs-zstd compress time/wide table cols=100 chunks=1 rows=1000 9.37457e+06 7.71092e+06 1.21575 ns
parquet_rs-zstd compress time/wide table cols=100 chunks=1 rows=1000 throughput 0.128136 0.155782 0.822536 bytes/ns
decompress time/wide table cols=100 chunks=1 rows=1000 1.48702e+06 1.40875e+06 1.05556 ns
decompress time/wide table cols=100 chunks=1 rows=1000 throughput 0.807804 0.852689 0.947361 bytes/ns
parquet_rs-zstd decompress time/wide table cols=100 chunks=1 rows=1000 2.68562e+06 2.52433e+06 1.0639 ns
parquet_rs-zstd decompress time/wide table cols=100 chunks=1 rows=1000 throughput 0.447279 0.475859 0.939941 bytes/ns
compress time/wide table cols=1000 chunks=1 rows=1000 3.68118e+08 3.62496e+08 1.01551 ns
compress time/wide table cols=1000 chunks=1 rows=1000 throughput 0.0326309 0.0331369 0.984729 bytes/ns
parquet_rs-zstd compress time/wide table cols=1000 chunks=1 rows=1000 9.90048e+07 9.56923e+07 1.03462 ns
parquet_rs-zstd compress time/wide table cols=1000 chunks=1 rows=1000 throughput 0.121328 0.125528 0.966542 bytes/ns
decompress time/wide table cols=1000 chunks=1 rows=1000 1.97667e+07 1.74194e+07 1.13475 ns
decompress time/wide table cols=1000 chunks=1 rows=1000 throughput 0.607691 0.689579 0.88125 bytes/ns
parquet_rs-zstd decompress time/wide table cols=1000 chunks=1 rows=1000 3.07447e+07 2.90788e+07 1.05729 ns
parquet_rs-zstd decompress time/wide table cols=1000 chunks=1 rows=1000 throughput 0.390703 0.413085 0.945815 bytes/ns
compress time/wide table cols=10 chunks=50 rows=1000 7.45532e+07 7.10192e+07 1.04976 ns
compress time/wide table cols=10 chunks=50 rows=1000 throughput 0.00169628 0.00178069 0.952597 bytes/ns
parquet_rs-zstd compress time/wide table cols=10 chunks=50 rows=1000 1.11932e+06 1.00778e+06 1.11067 ns
parquet_rs-zstd compress time/wide table cols=10 chunks=50 rows=1000 throughput 0.112982 0.125486 0.900357 bytes/ns
decompress time/wide table cols=10 chunks=50 rows=1000 783026 797146 0.982286 ns
decompress time/wide table cols=10 chunks=50 rows=1000 throughput 0.161506 0.158645 1.01803 bytes/ns
parquet_rs-zstd decompress time/wide table cols=10 chunks=50 rows=1000 255937 254078 1.00732 ns
parquet_rs-zstd decompress time/wide table cols=10 chunks=50 rows=1000 throughput 0.494117 0.497732 0.992737 bytes/ns
compress time/wide table cols=100 chunks=50 rows=1000 7.40707e+08 7.17676e+08 1.03209 ns
compress time/wide table cols=100 chunks=50 rows=1000 throughput 0.0017017 0.00175631 0.968907 bytes/ns
parquet_rs-zstd compress time/wide table cols=100 chunks=50 rows=1000 1.50414e+07 1.36809e+07 1.09944 ns
parquet_rs-zstd compress time/wide table cols=100 chunks=50 rows=1000 throughput 0.0837997 0.0921329 0.909552 bytes/ns
decompress time/wide table cols=100 chunks=50 rows=1000 8.13827e+06 7.93028e+06 1.02623 ns
decompress time/wide table cols=100 chunks=50 rows=1000 throughput 0.154881 0.158943 0.974444 bytes/ns
parquet_rs-zstd decompress time/wide table cols=100 chunks=50 rows=1000 2.7582e+06 2.56255e+06 1.07635 ns
parquet_rs-zstd decompress time/wide table cols=100 chunks=50 rows=1000 throughput 0.456987 0.491878 0.929066 bytes/ns
compress time/wide table cols=1000 chunks=50 rows=1000 7.69705e+09 7.29656e+09 1.05489 ns
compress time/wide table cols=1000 chunks=50 rows=1000 throughput 0.00163705 0.0017269 0.947969 bytes/ns
parquet_rs-zstd compress time/wide table cols=1000 chunks=50 rows=1000 2.1521e+08 1.93565e+08 1.11182 ns
parquet_rs-zstd compress time/wide table cols=1000 chunks=50 rows=1000 throughput 0.0585496 0.0650969 0.899422 bytes/ns
decompress time/wide table cols=1000 chunks=50 rows=1000 8.6724e+07 8.6579e+07 1.00167 ns
decompress time/wide table cols=1000 chunks=50 rows=1000 throughput 0.145294 0.145537 0.998329 bytes/ns
parquet_rs-zstd decompress time/wide table cols=1000 chunks=50 rows=1000 3.09878e+07 2.89791e+07 1.06932 ns
parquet_rs-zstd decompress time/wide table cols=1000 chunks=50 rows=1000 throughput 0.406626 0.434813 0.935176 bytes/ns
compress time/taxi 1.66312e+09 1.56922e+09 1.05983 ns
compress time/taxi throughput 0.283089 0.300027 0.943544 bytes/ns
parquet_rs-zstd compress time/taxi 1.91043e+09 1.86978e+09 1.02174 ns
parquet_rs-zstd compress time/taxi throughput 0.246442 0.251799 0.978722 bytes/ns
decompress time/taxi 1.87682e+08 1.85842e+08 1.0099 ns
decompress time/taxi throughput 2.50856 2.53339 0.990199 bytes/ns
parquet_rs-zstd decompress time/taxi 3.13483e+08 2.97494e+08 1.05375 ns
parquet_rs-zstd decompress time/taxi throughput 1.50187 1.58259 0.948995 bytes/ns
compress time/AirlineSentiment 164045 155640 1.054 ns
compress time/AirlineSentiment throughput 0.0124356 0.0131072 0.948767 bytes/ns
parquet_rs-zstd compress time/AirlineSentiment 50097.3 48374.5 1.03561 ns
parquet_rs-zstd compress time/AirlineSentiment throughput 0.0407207 0.0421709 0.965612 bytes/ns
decompress time/AirlineSentiment 35205.6 37467 0.939642 ns
decompress time/AirlineSentiment throughput 0.0579454 0.0544479 1.06423 bytes/ns
parquet_rs-zstd decompress time/AirlineSentiment 29470.4 28926.2 1.01882 ns
parquet_rs-zstd decompress time/AirlineSentiment throughput 0.0692219 0.0705243 0.981532 bytes/ns
compress time/Arade 3.23755e+09 3.14011e+09 1.03103 ns
compress time/Arade throughput 0.243094 0.250637 0.969904 bytes/ns
parquet_rs-zstd compress time/Arade 3.52578e+09 3.39366e+09 1.03893 ns
parquet_rs-zstd compress time/Arade throughput 0.223221 0.231912 0.962526 bytes/ns
decompress time/Arade 5.43038e+08 5.15003e+08 1.05444 ns
decompress time/Arade throughput 1.44931 1.5282 0.948373 bytes/ns
parquet_rs-zstd decompress time/Arade 6.62275e+08 6.39185e+08 1.03612 ns
parquet_rs-zstd decompress time/Arade throughput 1.18837 1.2313 0.965135 bytes/ns
compress time/Bimbo 1.06376e+10 9.73667e+09 1.09253 ns
compress time/Bimbo throughput 0.669449 0.731395 0.915305 bytes/ns
parquet_rs-zstd compress time/Bimbo 2.26378e+10 2.18563e+10 1.03576 ns
parquet_rs-zstd compress time/Bimbo throughput 0.314578 0.325826 0.965478 bytes/ns
decompress time/Bimbo 3.97645e+09 3.71497e+09 1.07038 ns
decompress time/Bimbo throughput 1.79088 1.91693 0.934244 bytes/ns
parquet_rs-zstd decompress time/Bimbo 2.55892e+09 2.51581e+09 1.01713 ns
parquet_rs-zstd decompress time/Bimbo throughput 2.78295 2.83064 0.983155 bytes/ns
compress time/CMSprovider 2.38467e+10 2.25347e+10 1.05822 ns
compress time/CMSprovider throughput 0.215927 0.228499 0.944982 bytes/ns
parquet_rs-zstd compress time/CMSprovider 1.90962e+10 1.87191e+10 1.02015 ns
parquet_rs-zstd compress time/CMSprovider throughput 0.269642 0.275074 0.980253 bytes/ns
decompress time/CMSprovider 6.25166e+09 5.91511e+09 1.0569 ns
decompress time/CMSprovider throughput 0.823646 0.870508 0.946167 bytes/ns
parquet_rs-zstd decompress time/CMSprovider 3.61312e+09 3.5089e+09 1.0297 ns
parquet_rs-zstd decompress time/CMSprovider throughput 1.42513 1.46746 0.971155 bytes/ns
compress time/Euro2016 2.23563e+09 2.13943e+09 1.04497 ns
compress time/Euro2016 throughput 0.175903 0.183813 0.956969 bytes/ns
parquet_rs-zstd compress time/Euro2016 1.78989e+09 1.75083e+09 1.02231 ns
parquet_rs-zstd compress time/Euro2016 throughput 0.219709 0.22461 0.978178 bytes/ns
decompress time/Euro2016 3.97956e+08 3.8169e+08 1.04262 ns
decompress time/Euro2016 throughput 0.988188 1.0303 0.959127 bytes/ns
parquet_rs-zstd decompress time/Euro2016 5.03792e+08 4.80164e+08 1.04921 ns
parquet_rs-zstd decompress time/Euro2016 throughput 0.78059 0.819001 0.9531 bytes/ns
compress time/Food 9.58375e+08 9.00805e+08 1.06391 ns
compress time/Food throughput 0.347171 0.369359 0.93993 bytes/ns
parquet_rs-zstd compress time/Food 1.16992e+09 1.15083e+09 1.01659 ns
parquet_rs-zstd compress time/Food throughput 0.284395 0.289112 0.983684 bytes/ns
decompress time/Food 1.63882e+08 1.54867e+08 1.05821 ns
decompress time/Food throughput 2.03024 2.14842 0.944994 bytes/ns
parquet_rs-zstd decompress time/Food 2.26646e+08 2.15765e+08 1.05043 ns
parquet_rs-zstd decompress time/Food throughput 1.46802 1.54205 0.951991 bytes/ns
compress time/HashTags 3.9756e+09 3.8613e+09 1.0296 ns
compress time/HashTags throughput 0.202359 0.208349 0.971249 bytes/ns
parquet_rs-zstd compress time/HashTags 2.84645e+09 2.81701e+09 1.01045 ns
parquet_rs-zstd compress time/HashTags throughput 0.282633 0.285586 0.98966 bytes/ns
decompress time/HashTags 1.01632e+09 1.00001e+09 1.01631 ns
decompress time/HashTags throughput 0.791581 0.804491 0.983954 bytes/ns
parquet_rs-zstd decompress time/HashTags 8.17781e+08 7.6506e+08 1.06891 ns
parquet_rs-zstd decompress time/HashTags throughput 0.983759 1.05155 0.935531 bytes/ns
compress time/TPC-H l_comment chunked 1.11246e+09 1.08093e+09 1.02917 ns
compress time/TPC-H l_comment chunked throughput 0.224007 0.230541 0.971658 bytes/ns
parquet_rs-zstd compress time/TPC-H l_comment chunked 9.91369e+08 9.71347e+08 1.02061 ns
parquet_rs-zstd compress time/TPC-H l_comment chunked throughput 0.251368 0.256549 0.979804 bytes/ns
decompress time/TPC-H l_comment chunked 1.10607e+08 1.05378e+08 1.04962 ns
decompress time/TPC-H l_comment chunked throughput 2.253 2.3648 0.952721 bytes/ns
parquet_rs-zstd decompress time/TPC-H l_comment chunked 2.51642e+08 2.48552e+08 1.01243 ns
parquet_rs-zstd decompress time/TPC-H l_comment chunked throughput 0.990292 1.0026 0.987721 bytes/ns
compress time/TPC-H l_comment canonical 1.09636e+09 1.06176e+09 1.03259 ns
compress time/TPC-H l_comment canonical throughput 0.227295 0.234702 0.968439 bytes/ns
parquet_rs-zstd compress time/TPC-H l_comment canonical 1.00225e+09 9.78222e+08 1.02456 ns
parquet_rs-zstd compress time/TPC-H l_comment canonical throughput 0.24864 0.254746 0.976031 bytes/ns
decompress time/TPC-H l_comment canonical 1.12611e+08 1.08475e+08 1.03813 ns
decompress time/TPC-H l_comment canonical throughput 2.2129 2.29728 0.96327 bytes/ns
parquet_rs-zstd decompress time/TPC-H l_comment canonical 2.52105e+08 2.49628e+08 1.00992 ns
parquet_rs-zstd decompress time/TPC-H l_comment canonical throughput 0.988468 0.998275 0.990176 bytes/ns

@AdamGS
Copy link
Contributor Author

AdamGS commented Feb 13, 2025

made another round of changes, I think this interface is more general (and works better for the non-specific runtime case), but spawn might not be the best name here, as for the inline variant awaiting is necessary to make progress. It fits our current usecase which is good enough for now IMO

@AdamGS
Copy link
Contributor Author

AdamGS commented Feb 14, 2025

I have an idea for the non-specific-runtime variant, coding it now

result: oneshot::Sender<R>,
}

impl<F, R> Task for ExecutorTask<F, R>
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

definitely not taken from @a10y 😇

AdamGS added a commit that referenced this pull request Feb 14, 2025
just a temporary measure until the [language API](rust-lang/rust#70142) is stabilized. 
I have a couple of these cases in #2348 so I figured its worth pulling into a separate PR.
@AdamGS AdamGS added benchmark Run benchmarks on this branch benchmark-sql and removed benchmark Run benchmarks on this branch labels Feb 18, 2025
Copy link
Contributor

github-actions bot commented Feb 18, 2025

Benchmarks: TPC-H on NVME

Table of Results
name PR 7d3c5aa base 202cffc ratio (PR/base) unit
tpch_q01/arrow 86601616 84086384 1.02991 ns
tpch_q02/arrow 44590951 44657745 0.998504 ns
tpch_q03/arrow 37859297 37528817 1.00881 ns
tpch_q04/arrow 32251466 34018862 0.948047 ns
tpch_q05/arrow 58937351 62511635 0.942822 ns
tpch_q06/arrow 8387067 9929981 0.844621 ns
tpch_q07/arrow 103215807 109088414 0.946167 ns
tpch_q08/arrow 59115105 60283528 0.980618 ns
tpch_q09/arrow 90687637 93369619 0.971276 ns
tpch_q10/arrow 60442938 59728459 1.01196 ns
tpch_q11/arrow 28728931 27009002 1.06368 ns
tpch_q12/arrow 35671562 33535326 1.0637 ns
tpch_q13/arrow 27630269 27032919 1.0221 ns
tpch_q14/arrow 13447899 13335658 1.00842 ns
tpch_q15/arrow 29179961 26614627 1.09639 ns
tpch_q16/arrow 23893765 23464119 1.01831 ns
tpch_q17/arrow 85541138 88430567 0.967325 ns
tpch_q18/arrow 159157930 178222592 0.893029 ns
tpch_q19/arrow 26238372 27723974 0.946415 ns
tpch_q20/arrow 37786928 39931967 0.946283 ns
tpch_q21/arrow 159826779 172058036 0.928912 ns
tpch_q22/arrow 18089456 18270956 0.990066 ns
tpch_q01/parquet 163672926 155797687 1.05055 ns
tpch_q02/parquet 104016119 98970497 1.05098 ns
tpch_q03/parquet 115640287 110922987 1.04253 ns
tpch_q04/parquet 63113674 62174508 1.01511 ns
tpch_q05/parquet 122148513 118531984 1.03051 ns
tpch_q06/parquet 29971694 45772447 0.654798 ns
tpch_q07/parquet 154215885 159513791 0.966787 ns
tpch_q08/parquet 153821486 157265686 0.978099 ns
tpch_q09/parquet 218755794 207177953 1.05588 ns
tpch_q10/parquet 162257196 160760757 1.00931 ns
tpch_q11/parquet 48565142 51220258 0.948163 ns
tpch_q12/parquet 103405794 99274531 1.04161 ns
tpch_q13/parquet 170103608 195174611 0.871546 ns
tpch_q14/parquet 51607265 50438964 1.02316 ns
tpch_q15/parquet 85555312 83378674 1.02611 ns
tpch_q16/parquet 49332680 49423755 0.998157 ns
tpch_q17/parquet 170281123 160384771 1.0617 ns
tpch_q18/parquet 243233368 250676612 0.970307 ns
tpch_q19/parquet 101450772 86446730 1.17356 ns
tpch_q20/parquet 100442370 104765067 0.958739 ns
tpch_q21/parquet 216000145 211880136 1.01944 ns
tpch_q22/parquet 48551343 52842152 0.9188 ns
tpch_q01/vortex-file-compressed 69388241 151213329 0.458876 ns
tpch_q02/vortex-file-compressed 45565338 50392425 0.90421 ns
tpch_q03/vortex-file-compressed 38502458 126999492 0.30317 ns
tpch_q04/vortex-file-compressed 26280131 85464157 0.307499 ns
tpch_q05/vortex-file-compressed 56437864 91753147 0.615105 ns
tpch_q06/vortex-file-compressed 16380571 49330141 0.33206 ns
tpch_q07/vortex-file-compressed 95393328 172789280 0.552079 ns
tpch_q08/vortex-file-compressed 67904955 120198027 0.564942 ns
tpch_q09/vortex-file-compressed 99249519 145053731 0.684226 ns
tpch_q10/vortex-file-compressed 62469694 127733609 0.489062 ns
tpch_q11/vortex-file-compressed 26542276 25653441 1.03465 ns
tpch_q12/vortex-file-compressed 45149982 125539172 0.359649 ns
tpch_q13/vortex-file-compressed 31649332 111069014 0.284952 ns
tpch_q14/vortex-file-compressed 20386113 44281586 0.460374 ns
tpch_q15/vortex-file-compressed 34805187 83227729 0.418192 ns
tpch_q16/vortex-file-compressed 26240238 33306851 0.787833 ns
tpch_q17/vortex-file-compressed 84855235 103924600 0.816508 ns
tpch_q18/vortex-file-compressed 150935999 183449650 0.822765 ns
tpch_q19/vortex-file-compressed 33357757 103811150 0.321331 ns
tpch_q20/vortex-file-compressed 41629755 75377774 0.552282 ns
tpch_q21/vortex-file-compressed 147444585 267103408 0.552013 ns
tpch_q22/vortex-file-compressed 30556876 33610863 0.909137 ns

}
}

struct Inner {
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This structure is needed to achieve the behavior we want, where arbitrary futures can be spawned on this runtime. I've tried to structure it differently but I honestly think this is pretty nice, and we can definitely try and improve that later.

Copy link
Contributor

Benchmarks: TPC-H on S3

Table of Results
name PR 3999105 base 89df1a1 ratio (PR/base) unit
tpch_q01/parquet 291434496 310504328 0.938584 ns
tpch_q02/parquet 750716552 777376261 0.965706 ns
tpch_q03/parquet 462260716 482101091 0.958846 ns
tpch_q04/parquet 255343241 268363747 0.951482 ns
tpch_q05/parquet 615344783 648012621 0.949588 ns
tpch_q06/parquet 197851269 202255637 0.978224 ns
tpch_q07/parquet 699927655 707679389 0.989046 ns
tpch_q08/parquet 858520382 850473705 1.00946 ns
tpch_q09/parquet 715603839 736865919 0.971145 ns
tpch_q10/parquet 580724511 603937457 0.961564 ns
tpch_q11/parquet 292906199 302431984 0.968503 ns
tpch_q12/parquet 288124025 301936759 0.954253 ns
tpch_q13/parquet 424723338 421868842 1.00677 ns
tpch_q14/parquet 277335251 296947147 0.933955 ns
tpch_q15/parquet 522417857 496765888 1.05164 ns
tpch_q16/parquet 311926627 287274780 1.08581 ns
tpch_q17/parquet 445628211 432080496 1.03135 ns
tpch_q18/parquet 625919223 616845063 1.01471 ns
tpch_q19/parquet 320682951 330777893 0.969481 ns
tpch_q20/parquet 594930169 583548047 1.01951 ns
tpch_q21/parquet 692295387 736676547 0.939755 ns
tpch_q22/parquet 313461606 313221105 1.00077 ns
tpch_q01/vortex-file-compressed 472241846 546759503 0.86371 ns
tpch_q02/vortex-file-compressed 406844295 413728875 0.98336 ns
tpch_q03/vortex-file-compressed 643165836 693520962 0.927392 ns
tpch_q04/vortex-file-compressed 508167512 629317380 0.80749 ns
tpch_q05/vortex-file-compressed 507289883 528499123 0.959869 ns
tpch_q06/vortex-file-compressed 572216600 524694044 1.09057 ns
tpch_q07/vortex-file-compressed 755754113 876055570 0.862678 ns
tpch_q08/vortex-file-compressed 664121606 746329136 0.889851 ns
tpch_q09/vortex-file-compressed 632227918 715329314 0.883828 ns
tpch_q10/vortex-file-compressed 554676157 554514707 1.00029 ns
tpch_q11/vortex-file-compressed 148413789 163172334 0.909552 ns
tpch_q12/vortex-file-compressed 854988511 915413578 0.933992 ns
tpch_q13/vortex-file-compressed 185620564 349160437 0.53162 ns
tpch_q14/vortex-file-compressed 460907131 487363240 0.945716 ns
tpch_q15/vortex-file-compressed 999746340 1078746376 0.926767 ns
tpch_q16/vortex-file-compressed 186362227 189874631 0.981501 ns
tpch_q17/vortex-file-compressed 418362767 484965683 0.862665 ns
tpch_q18/vortex-file-compressed 510327166 586694541 0.869835 ns
tpch_q19/vortex-file-compressed 447349957 451743780 0.990274 ns
tpch_q20/vortex-file-compressed 665781035 701455842 0.949142 ns
tpch_q21/vortex-file-compressed 1246642824 1455729099 0.85637 ns
tpch_q22/vortex-file-compressed 188195468 172664956 1.08995 ns

Copy link
Contributor

github-actions bot commented Feb 18, 2025

Benchmarks: Clickbench on NVME

Table of Results
name PR c22bad0 base 1761a2d ratio (PR/base) unit
clickbench_q00/parquet 2376343 2556353 0.929583 ns
clickbench_q01/parquet 66152050 67358429 0.98209 ns
clickbench_q02/parquet 126916981 128944025 0.98428 ns
clickbench_q03/parquet 91140062 96615777 0.943325 ns
clickbench_q04/parquet 694470723 769497145 0.902499 ns
clickbench_q05/parquet 769495231 801821152 0.959684 ns
clickbench_q06/parquet 2526583 2518137 1.00335 ns
clickbench_q07/parquet 67300972 67594531 0.995657 ns
clickbench_q08/parquet 773515273 825762978 0.936728 ns
clickbench_q09/parquet 1174655548 1174548975 1.00009 ns
clickbench_q10/parquet 277910893 283282174 0.981039 ns
clickbench_q11/parquet 327121445 342808178 0.95424 ns
clickbench_q12/parquet 786881783 827927549 0.950423 ns
clickbench_q13/parquet 1090176439 1109029902 0.983 ns
clickbench_q14/parquet 746443434 789587362 0.945359 ns
clickbench_q15/parquet 756182149 851239577 0.888331 ns
clickbench_q16/parquet 1637892443 1674416985 0.978187 ns
clickbench_q17/parquet 1486494140 1564520980 0.950127 ns
clickbench_q18/parquet 3163427334 3362940158 0.940673 ns
clickbench_q19/parquet 68242346 72463590 0.941747 ns
clickbench_q20/parquet 1128562724 1267872205 0.890123 ns
clickbench_q21/parquet 1302120974 1427590098 0.912111 ns
clickbench_q22/parquet 1924780774 2041594112 0.942783 ns
clickbench_q23/parquet 8260978507 8963055199 0.92167 ns
clickbench_q24/parquet 468610545 472959190 0.990805 ns
clickbench_q25/parquet 400973056 435850168 0.919979 ns
clickbench_q26/parquet 501786127 561742263 0.893268 ns
clickbench_q27/parquet 1611523590 1746327047 0.922807 ns
clickbench_q28/parquet 11407468493 11602459931 0.983194 ns
clickbench_q29/parquet 433742056 447397617 0.969478 ns
clickbench_q30/parquet 675349873 714609938 0.945061 ns
clickbench_q31/parquet 729388243 832850000 0.875774 ns
clickbench_q32/parquet 2818226323 3176646611 0.88717 ns
clickbench_q33/parquet 2900607998 3116322952 0.930779 ns
clickbench_q34/parquet 2799671815 3021564927 0.926564 ns
clickbench_q35/parquet 864930267 953503882 0.907107 ns
clickbench_q36/parquet 175632626 192138653 0.914093 ns
clickbench_q37/parquet 86117079 90419943 0.952412 ns
clickbench_q38/parquet 109557395 119641178 0.915716 ns
clickbench_q39/parquet 318664904 347178054 0.917872 ns
clickbench_q40/parquet 52718181 60419060 0.872542 ns
clickbench_q41/parquet 52569423 54483646 0.964866 ns
clickbench_q42/parquet 72435840 78085917 0.927643 ns
clickbench_q00/vortex-file-compressed 2208734 3194159 0.691492 ns
clickbench_q01/vortex-file-compressed 22269677 23151775 0.961899 ns
clickbench_q02/vortex-file-compressed 57851378 60646464 0.953912 ns
clickbench_q03/vortex-file-compressed 64331218 69821768 0.921363 ns
clickbench_q04/vortex-file-compressed 639982352 735031826 0.870687 ns
clickbench_q05/vortex-file-compressed 630135443 732217688 0.860585 ns
clickbench_q06/vortex-file-compressed 2344993 2648642 0.885357 ns
clickbench_q07/vortex-file-compressed 30098828 34672095 0.868099 ns
clickbench_q08/vortex-file-compressed 703481555 842595234 0.834899 ns
clickbench_q09/vortex-file-compressed 865564622 1007352803 0.859247 ns
clickbench_q10/vortex-file-compressed 155989349 219180199 0.711695 ns
clickbench_q11/vortex-file-compressed 183086374 238436680 0.767862 ns
clickbench_q12/vortex-file-compressed 518705872 646816250 0.801937 ns
clickbench_q13/vortex-file-compressed 795670118 909292989 0.875043 ns
clickbench_q14/vortex-file-compressed 505847124 527798130 0.95841 ns
clickbench_q15/vortex-file-compressed 722027811 798203010 0.904567 ns
clickbench_q16/vortex-file-compressed 1397887827 1560669479 0.895698 ns
clickbench_q17/vortex-file-compressed 1390459853 1498452445 0.927931 ns
clickbench_q18/vortex-file-compressed 2924104758 3090238046 0.946239 ns
clickbench_q19/vortex-file-compressed 45844362 55655007 0.823724 ns
clickbench_q20/vortex-file-compressed 607604059 718634893 0.845498 ns
clickbench_q21/vortex-file-compressed 699159818 821797661 0.850769 ns
clickbench_q22/vortex-file-compressed 1220114247 1345132284 0.907059 ns
clickbench_q23/vortex-file-compressed 1936213336 2194177703 0.882432 ns
clickbench_q24/vortex-file-compressed 254618488 278871629 0.913031 ns
clickbench_q25/vortex-file-compressed 245144027 273267815 0.897083 ns
clickbench_q26/vortex-file-compressed 302886678 352923078 0.858223 ns
clickbench_q27/vortex-file-compressed 1124123083 1213539709 0.926318 ns
clickbench_q28/vortex-file-compressed 10441050767 10516591555 0.992817 ns
clickbench_q29/vortex-file-compressed 731083333 747239590 0.978379 ns
clickbench_q30/vortex-file-compressed 434520846 468527782 0.927417 ns
clickbench_q31/vortex-file-compressed 457709180 488155918 0.937629 ns
clickbench_q32/vortex-file-compressed 2752162039 3025571542 0.909634 ns
clickbench_q33/vortex-file-compressed 2273114366 2464793344 0.922233 ns
clickbench_q34/vortex-file-compressed 2332276196 2505779171 0.930759 ns
clickbench_q35/vortex-file-compressed 972790247 1045268897 0.93066 ns
clickbench_q36/vortex-file-compressed 102270373 171113128 0.597677 ns
clickbench_q37/vortex-file-compressed 54549358 89782565 0.607572 ns
clickbench_q38/vortex-file-compressed 38857396 135476432 0.28682 ns
clickbench_q39/vortex-file-compressed 180947787 287271776 0.629884 ns
clickbench_q40/vortex-file-compressed 33447731 46504081 0.719243 ns
clickbench_q41/vortex-file-compressed 32342635 62502397 0.517462 ns
clickbench_q42/vortex-file-compressed 51453614 68472563 0.751449 ns

Copy link
Contributor

github-actions bot commented Feb 18, 2025

Benchmarks: TPC-H on NVME

Table of Results
name PR c22bad0 base 1761a2d ratio (PR/base) unit
tpch_q01/arrow 90351497 90169322 1.00202 ns
tpch_q02/arrow 43847639 47866793 0.916035 ns
tpch_q03/arrow 36913875 39306329 0.939133 ns
tpch_q04/arrow 33371771 34939311 0.955135 ns
tpch_q05/arrow 62472870 63729738 0.980278 ns
tpch_q06/arrow 9142609 9528504 0.959501 ns
tpch_q07/arrow 106427043 111013042 0.95869 ns
tpch_q08/arrow 62651632 63216167 0.99107 ns
tpch_q09/arrow 89177142 91422423 0.975441 ns
tpch_q10/arrow 59592398 59865020 0.995446 ns
tpch_q11/arrow 27688971 27163200 1.01936 ns
tpch_q12/arrow 34426139 32420219 1.06187 ns
tpch_q13/arrow 26483287 25751723 1.02841 ns
tpch_q14/arrow 13523082 12865863 1.05108 ns
tpch_q15/arrow 27395901 26173939 1.04669 ns
tpch_q16/arrow 22865326 23714461 0.964193 ns
tpch_q17/arrow 88667137 88330429 1.00381 ns
tpch_q18/arrow 173111309 170508236 1.01527 ns
tpch_q19/arrow 27969341 28844231 0.969668 ns
tpch_q20/arrow 38959136 39605436 0.983682 ns
tpch_q21/arrow 168624616 176476685 0.955506 ns
tpch_q22/arrow 17593706 18387489 0.95683 ns
tpch_q01/parquet 165088122 165473757 0.99767 ns
tpch_q02/parquet 99201012 104919579 0.945496 ns
tpch_q03/parquet 112643957 113580669 0.991753 ns
tpch_q04/parquet 62071315 63523602 0.977138 ns
tpch_q05/parquet 116877816 121681489 0.960523 ns
tpch_q06/parquet 29797360 29898491 0.996618 ns
tpch_q07/parquet 153588071 152203608 1.0091 ns
tpch_q08/parquet 148125453 155446870 0.952901 ns
tpch_q09/parquet 202847147 219248857 0.925191 ns
tpch_q10/parquet 159482555 168518239 0.946382 ns
tpch_q11/parquet 49368496 52956346 0.932249 ns
tpch_q12/parquet 97550353 88578568 1.10129 ns
tpch_q13/parquet 174147533 184375318 0.944527 ns
tpch_q14/parquet 51740551 50669946 1.02113 ns
tpch_q15/parquet 82937190 96213120 0.862015 ns
tpch_q16/parquet 47698182 50653966 0.941648 ns
tpch_q17/parquet 161262036 173863683 0.92752 ns
tpch_q18/parquet 249977710 277982566 0.899257 ns
tpch_q19/parquet 84068723 102629961 0.819144 ns
tpch_q20/parquet 102739798 107002426 0.960163 ns
tpch_q21/parquet 208287006 217139408 0.959232 ns
tpch_q22/parquet 53844639 51660687 1.04227 ns
tpch_q01/vortex-file-compressed 68337413 163825376 0.417136 ns
tpch_q02/vortex-file-compressed 47776618 54026539 0.884318 ns
tpch_q03/vortex-file-compressed 40012713 128790742 0.31068 ns
tpch_q04/vortex-file-compressed 27645828 91257553 0.302943 ns
tpch_q05/vortex-file-compressed 56656739 95783935 0.591506 ns
tpch_q06/vortex-file-compressed 16772966 49825632 0.336633 ns
tpch_q07/vortex-file-compressed 94883618 172082573 0.551384 ns
tpch_q08/vortex-file-compressed 64750635 125675409 0.515221 ns
tpch_q09/vortex-file-compressed 93812360 156924479 0.597819 ns
tpch_q10/vortex-file-compressed 60689919 135054457 0.449374 ns
tpch_q11/vortex-file-compressed 24615691 27236283 0.903783 ns
tpch_q12/vortex-file-compressed 43206094 128354305 0.336616 ns
tpch_q13/vortex-file-compressed 31153105 108833798 0.286245 ns
tpch_q14/vortex-file-compressed 20410298 44090668 0.462917 ns
tpch_q15/vortex-file-compressed 34929631 84064813 0.415508 ns
tpch_q16/vortex-file-compressed 26975979 33256526 0.811148 ns
tpch_q17/vortex-file-compressed 82468023 110070493 0.749229 ns
tpch_q18/vortex-file-compressed 156072677 207929900 0.750602 ns
tpch_q19/vortex-file-compressed 34387080 110122344 0.312263 ns
tpch_q20/vortex-file-compressed 41872910 84921543 0.493078 ns
tpch_q21/vortex-file-compressed 137478807 271173798 0.506977 ns
tpch_q22/vortex-file-compressed 30393172 33191783 0.915684 ns

@AdamGS AdamGS marked this pull request as ready for review February 18, 2025 13:06
@AdamGS AdamGS changed the title [wip] Spawn layout evaluation feat: Spawn layout evaluation Feb 18, 2025
@AdamGS
Copy link
Contributor Author

AdamGS commented Feb 18, 2025

All benchmarks look good, not much difference on S3 (maybe slightly better) and much better on disk (especially for TPC-H).

@@ -68,7 +70,9 @@ impl<D: ScanDriver> ScanBuilder<D> {
row_indices: None,
split_by: SplitBy::Layout,
canonicalize: false,
concurrency: 32,
concurrency: std::thread::available_parallelism()
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't know that this should default to nthreads, this is "concurrency" and not "parallelism", the number of row splits to make progress on concurrently. Basically... we want as many as possible provided the data fits in some reasonable memory, since the more concurrency, the more visibility into upcoming I/O, and therefore the more coalescing.

Copy link
Contributor Author

@AdamGS AdamGS Feb 18, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yeah, it was an idea but we probably do want to oversubscribe the tokio runtime if we can and buffer by a different metric

use vortex_error::VortexResult;

pub trait Executor {
/// Spawns a future to run on a different runtime. The shouldn't be polled to make progress.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fix up doc

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LMK what you think of the new one


pub trait Executor {
/// Spawns a future to run on a different runtime. The shouldn't be polled to make progress.
fn spawn<F>(&self, f: F) -> VortexResult<BoxFuture<'static, VortexResult<F::Output>>>
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Does this need to return a result? Can it just be BoxFuture<'static, VortexResult<..>>? Since the impl can always return ready(Err(...)) if it needs to.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don' think we want to return ready(Err(...)) here, but if we're ok with panicking in cases where we can't submit work/tasks start getting cancelled, we can get the nicer function signature.


/// Generic wrapper around different async runtimes. Used to spawn async tasks to run in the background, concurrently with other tasks.
#[derive(Clone)]
pub enum TaskExecutor {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I wonder what the performance hit is to just have a dyn Executor? Seems like a lot of code here for basically |f| tokio::spawn(f)

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

IDK if we can have dyn Executor here without a major change due to the generics

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You would have to take / return BoxFuture. You already return one

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think its that much code (probably less than what happens in Arc), but in order to make it dyn-compatible we'll also have to move the generic bound from the function to the trait itself (example), which makes this thing less useful in other cases IMO.

@AdamGS AdamGS enabled auto-merge (squash) February 18, 2025 16:54
@AdamGS AdamGS merged commit 661f6cd into develop Feb 18, 2025
25 checks passed
@AdamGS AdamGS deleted the adamg/spawn-evaluate branch February 18, 2025 16:56
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants