Skip to content

Commit

Permalink
✨ Produce "//" in web paths (#4935)
Browse files Browse the repository at this point in the history
Even if it used to be already the case, users had to specify a larger
than default size to be able to see paths containing a "//" into them.
As "//" is crucial in paths and totally part of the spec, they need to
be generated with our default size too.

The current PR makes sure we have a better balance between number of
segments in a path and length of the segments. Our previous version
(with default size) used to sacrify the number of segments and to prefer
longer one. We now mix both.

Related to #4896

<!-- Context of the PR: short description and potentially linked issues
-->

<!-- ...a few words to describe the content of this PR... -->
<!-- ... -->

<!-- Type of PR: [ ] unchecked / [ ] checked -->

**_Category:_**

- [x] ✨ Introduce new features
- [ ] 📝 Add or update documentation
- [ ] ✅ Add or update tests
- [ ] 🐛 Fix a bug
- [ ] 🏷️ Add or update types
- [ ] ⚡️ Improve performance
- [ ] _Other(s):_ ...
  <!-- Don't forget to add the gitmoji icon in the name of the PR -->
  <!-- See: https://gitmoji.dev/                                  -->

<!-- Fixing bugs, adding features... may impact existing ones -->
<!-- in order to track potential issues that could be related to your PR
-->
<!-- please check the impacts and describe more precisely what to expect
-->

**_Potential impacts:_**

<!-- Generated values: Can your change impact any of the existing
generators in terms of generated values, if so which ones? when? -->
<!-- Shrink values: Can your change impact any of the existing
generators in terms of shrink values, if so which ones? when? -->
<!-- Performance: Can it require some typings changes on user side?
Please give more details -->
<!-- Typings: Is there a potential performance impact? In which cases?
-->

- [x] Generated values: anything related on web-path
- [x] Shrink values: anything related on web-path
- [x] Performance: anything related on web-path might be slightly
slower, but probably unnoticeable
- [ ] Typings
- [ ] _Other(s):_ ...
  • Loading branch information
dubzzz authored Apr 26, 2024
1 parent 0bbef2c commit 043d6ef
Show file tree
Hide file tree
Showing 6 changed files with 280 additions and 108 deletions.
8 changes: 8 additions & 0 deletions .yarn/versions/f914e4ac.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
releases:
fast-check: minor

declined:
- "@fast-check/ava"
- "@fast-check/jest"
- "@fast-check/vitest"
- "@fast-check/worker"
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ import type { Size } from '../helpers/MaxLengthFromMinLength';
import { webSegment } from '../../webSegment';
import { array } from '../../array';
import { segmentsToPathMapper, segmentsToPathUnmapper } from '../mappers/SegmentsToPath';
import { oneof } from '../../oneof';

/** @internal */
function sqrtSize(size: Size): [Size, Size] {
Expand All @@ -21,10 +22,21 @@ function sqrtSize(size: Size): [Size, Size] {
}

/** @internal */
export function buildUriPathArbitrary(resolvedSize: Size): Arbitrary<string> {
const [segmentSize, numSegmentSize] = sqrtSize(resolvedSize);
function buildUriPathArbitraryInternal(segmentSize: Size, numSegmentSize: Size): Arbitrary<string> {
return array(webSegment({ size: segmentSize }), { size: numSegmentSize }).map(
segmentsToPathMapper,
segmentsToPathUnmapper,
);
}

/** @internal */
export function buildUriPathArbitrary(resolvedSize: Size): Arbitrary<string> {
const [segmentSize, numSegmentSize] = sqrtSize(resolvedSize);
if (segmentSize === numSegmentSize) {
return buildUriPathArbitraryInternal(segmentSize, numSegmentSize);
}
return oneof(
buildUriPathArbitraryInternal(segmentSize, numSegmentSize),
buildUriPathArbitraryInternal(numSegmentSize, segmentSize),
);
}
112 changes: 15 additions & 97 deletions packages/fast-check/test/e2e/__snapshots__/NoRegression.spec.ts.snap
Original file line number Diff line number Diff line change
Expand Up @@ -4998,104 +4998,22 @@ Execution summary:
`;

exports[`NoRegression > webPath 1`] = `
[Error: Property failed after 39 tests
{ seed: 42, path: "38:3:1:8:7:3:3:4:3:3:4", endOnFailure: true }
Counterexample: ["/%F0%AA%80%80"]
Shrunk 10 time(s)
[Error: Property failed after 2 tests
{ seed: 42, path: "1:1:2", endOnFailure: true }
Counterexample: ["//"]
Shrunk 2 time(s)
Got error: Property failed by returning false

Execution summary:
√ [""]
√ [""]
√ [""]
√ [""]
√ [""]
√ [""]
√ [""]
√ [""]
√ ["/VnAy7J*"]
√ [""]
√ [""]
√ ["/%F0%AF%A8%A94%F1%B9%A0%93o,"]
√ [""]
√ ["/s"]
√ ["/_1J7+HWJ"]
√ [""]
√ ["/rs%E1%BC%82iRu:%F0%96%A6%96T"]
√ [""]
√ ["/sd1_z5eON"]
√ ["/d"]
√ [""]
√ [""]
√ ["/J4"]
√ [""]
√ ["/U*q%F3%9F%84%9BN"]
√ ["/70O%F1%80%97%B7d"]
√ [""]
√ [""]
√ [""]
√ ["/ZQt"]
√ ["/+g@"]
√ ["/c(z"]
√ [""]
√ [""]
√ [""]
√ ["/E"]
√ ["/LzY0Xwu%F2%82%AB%B5"]
√ [""]
× ["/cJ%F0%AA%AC%A7&'i"]
× ["///%F2%8C%AD%96"]
. √ [""]
. √ ["/"]
. √ ["/&'i"]
. × ["/J%F0%AA%AC%A7&'i"]
. . √ [""]
. . × ["/%F0%AA%AC%A7&'i"]
. . . √ [""]
. . . √ ["/&'i"]
. . . √ ["/%20&'i"]
. . . √ ["/%F0%95%A6%94&'i"]
. . . √ ["/%F0%A0%89%9E&'i"]
. . . √ ["/%F0%A5%9B%83&'i"]
. . . √ ["/%F0%A8%83%B5&'i"]
. . . √ ["/%F0%A9%98%8E&'i"]
. . . × ["/%F0%AA%82%9B&'i"]
. . . . √ [""]
. . . . √ ["/'i"]
. . . . √ ["/&'i"]
. . . . √ ["/%F0%A9%AD%95&'i"]
. . . . √ ["/%F0%A9%B7%B8&'i"]
. . . . √ ["/%F0%A9%BD%8A&'i"]
. . . . √ ["/%F0%A9%BF%B3&'i"]
. . . . × ["/%F0%AA%81%87&'i"]
. . . . . √ [""]
. . . . . √ ["/'i"]
. . . . . √ ["/&'i"]
. . . . . × ["/%F0%AA%80%9D&'i"]
. . . . . . √ [""]
. . . . . . √ ["/'i"]
. . . . . . √ ["/&'i"]
. . . . . . × ["/%F0%AA%80%88&'i"]
. . . . . . . √ [""]
. . . . . . . √ ["/'i"]
. . . . . . . √ ["/&'i"]
. . . . . . . √ ["/%F0%A9%BF%BE&'i"]
. . . . . . . × ["/%F0%AA%80%83&'i"]
. . . . . . . . √ [""]
. . . . . . . . √ ["/'i"]
. . . . . . . . √ ["/&'i"]
. . . . . . . . × ["/%F0%AA%80%81&'i"]
. . . . . . . . . √ [""]
. . . . . . . . . √ ["/'i"]
. . . . . . . . . √ ["/&'i"]
. . . . . . . . . × ["/%F0%AA%80%80&'i"]
. . . . . . . . . . √ [""]
. . . . . . . . . . √ ["/'i"]
. . . . . . . . . . √ ["/&'i"]
. . . . . . . . . . √ ["/%F0%A9%BF%BF&'i"]
. . . . . . . . . . × ["/%F0%AA%80%80"]
. . . . . . . . . . . √ [""]
. . . . . . . . . . . √ ["/"]
. . . . . . . . . . . √ ["/%F0%A9%BF%BF"]]
. × ["//%F2%8C%AD%96"]
. . √ ["/%F2%8C%AD%96"]
. . √ ["/"]
. . × ["//"]
. . . √ ["/"]
. . . √ ["/"]]
`;

exports[`NoRegression > webQueryParameters 1`] = `
Expand Down Expand Up @@ -5214,9 +5132,9 @@ Shrunk 4 time(s)
Got error: Property failed by returning false

Execution summary:
× ["http://e.pv/p%EF%8D%9D"]
. × ["http://a.pv/p%EF%8D%9D"]
. . × ["http://a.av/p%EF%8D%9D"]
. . . × ["http://a.aa/p%EF%8D%9D"]
× ["http://e.pv//"]
. × ["http://a.pv//"]
. . × ["http://a.av//"]
. . . × ["http://a.aa//"]
. . . . × ["http://a.aa"]]
`;
Original file line number Diff line number Diff line change
@@ -1,5 +1,221 @@
// Vitest Snapshot v1, https://vitest.dev/guide/snapshot.html

exports[`webPath (integration) > should be able to shrink '//az' 1`] = `
""//az"
├> ""
├> "/az"
| ├> ""
| ├> "/"
| | └> ""
| ├> "/z"
| | ├> ""
| | ├> "/"
| | | └> ""
| | ├> "/a"
| | | ├> ""
| | | └> "/"
| | | └> ""
| | ├> "/n"
| | | ├> ""
| | | ├> "/"
| | | | └> ""
| | | ├> "/h"
| | | | ├> ""
| | | | ├> "/"
| | | | | └> ""
| | | | ├> "/e"
| | | | | ├> ""
| | | | | ├> "/"
| | | | | | └> ""
| | | | | ├> "/c"
| | | | | | ├> ""
| | | | | | ├> "/"
| | | | | | | └> ""
| | | | | | └> "/b"
| | | | | | ├> ""
| | | | | | ├> "/"
| | | | | | | └> ""
| | | | | | └> "/a"
| | | | | | ├> ""
| | | | | | └> "/"
| | | | | | └> ""
| | | | | └> "/d"
| | | | | ├> ""
| | | | | ├> "/"
| | | | | | └> ""
| | | | | └> "/c"
| | | | | ├> ""
| | | | | ├> "/"
| | | | | | └> ""
| | | | | ├> "/a"
| | | | | | ├> ""
| | | | | | └> "/"
| | | | | | └> ""
| | | | | └> "/b"
| | | | | ├> ""
| | | | | ├> "/"
| | | | | | └> ""
| | | | | └> "/a"
| | | | | ├> ""
| | | | | └> "/"
| | | | | └> ""
| | | | └> "/g"
| | | | ├> ""
| | | | ├> "/"
| | | | | └> ""
| | | | └> "/f"
| | | | ├> ""
| | | | ├> "/"
| | | | | └> ""
| | | | └> "/e"
| | | | ├> ""
| | | | ├> "/"
| | | | | └> ""
| | | | ├> "/a"
| | | | | ├> ""
| | | | | └> "/"
| | | | | └> ""
| | | | ├> "/c"
| | | | | ├> ""
| | | | | ├> "/"
| | | | | | └> ""
| | | | | └> "/b"
| | | | | ├> ""
| | | | | ├> "/"
| | | | | | └> ""
| | | | | └> "/a"
| | | | | ├> ""
| | | | | └> "/"
| | | | | └> ""
| | | | └> "/d"
| | | | ├> ""
| | | | ├> "/"
| | | | | └> ""
| | | | └> "/c"
| | | | ├> ""
| | | | ├> "/"
| | | | | └> ""
| | | | ├> "/a"
| | | | | ├> ""
| | | | | └> "/"
| | | | | └> ""
| | | | └> "/b"
| | | | ├> ""
| | | | └> …
| | | └> …
| | └> …
| └> …
└> …"
`;

exports[`webPath (integration) > should be able to shrink '/a//z' 1`] = `
""/a//z"
├> ""
├> "//z"
| ├> "/z"
| | ├> ""
| | ├> "/"
| | | └> ""
| | ├> "/a"
| | | ├> ""
| | | └> "/"
| | | └> ""
| | ├> "/n"
| | | ├> ""
| | | ├> "/"
| | | | └> ""
| | | ├> "/h"
| | | | ├> ""
| | | | ├> "/"
| | | | | └> ""
| | | | ├> "/e"
| | | | | ├> ""
| | | | | ├> "/"
| | | | | | └> ""
| | | | | ├> "/c"
| | | | | | ├> ""
| | | | | | ├> "/"
| | | | | | | └> ""
| | | | | | └> "/b"
| | | | | | ├> ""
| | | | | | ├> "/"
| | | | | | | └> ""
| | | | | | └> "/a"
| | | | | | ├> ""
| | | | | | └> "/"
| | | | | | └> ""
| | | | | └> "/d"
| | | | | ├> ""
| | | | | ├> "/"
| | | | | | └> ""
| | | | | └> "/c"
| | | | | ├> ""
| | | | | ├> "/"
| | | | | | └> ""
| | | | | ├> "/a"
| | | | | | ├> ""
| | | | | | └> "/"
| | | | | | └> ""
| | | | | └> "/b"
| | | | | ├> ""
| | | | | ├> "/"
| | | | | | └> ""
| | | | | └> "/a"
| | | | | ├> ""
| | | | | └> "/"
| | | | | └> ""
| | | | └> "/g"
| | | | ├> ""
| | | | ├> "/"
| | | | | └> ""
| | | | └> "/f"
| | | | ├> ""
| | | | ├> "/"
| | | | | └> ""
| | | | └> "/e"
| | | | ├> ""
| | | | ├> "/"
| | | | | └> ""
| | | | ├> "/a"
| | | | | ├> ""
| | | | | └> "/"
| | | | | └> ""
| | | | ├> "/c"
| | | | | ├> ""
| | | | | ├> "/"
| | | | | | └> ""
| | | | | └> "/b"
| | | | | ├> ""
| | | | | ├> "/"
| | | | | | └> ""
| | | | | └> "/a"
| | | | | ├> ""
| | | | | └> "/"
| | | | | └> ""
| | | | └> "/d"
| | | | ├> ""
| | | | ├> "/"
| | | | | └> ""
| | | | └> "/c"
| | | | ├> ""
| | | | ├> "/"
| | | | | └> ""
| | | | ├> "/a"
| | | | | ├> ""
| | | | | └> "/"
| | | | | └> ""
| | | | └> "/b"
| | | | ├> ""
| | | | ├> "/"
| | | | | └> ""
| | | | └> "/a"
| | | | └> …
| | | └> …
| | └> …
| └> …
└> …"
`;

exports[`webPath (integration) > should be able to shrink '/a/z' 1`] = `
""/a/z"
├> ""
Expand Down
Loading

0 comments on commit 043d6ef

Please sign in to comment.