|
41 | 41 | from pathlib import Path, PurePosixPath |
42 | 42 | from typing import Iterable, Optional, Sequence |
43 | 43 |
|
| 44 | +import edgtest |
| 45 | + |
44 | 46 | from edgacknowledg.forge import Forge, PullRequestInfo |
45 | 47 | from edgacknowledg.forge.runner.roles import BUILD_STAGING_DIR, REVIEWS_DIR |
| 48 | +from edgtest.runtest import get_bare_name |
46 | 49 |
|
47 | 50 | _log = logging.getLogger(__name__) |
48 | 51 |
|
|
57 | 60 |
|
58 | 61 | BENCH_BASELINE_PATTERNS = ('/benchmarks/baselines/',) |
59 | 62 |
|
60 | | -# The longest file name (in bytes) a test can have; a longer one names no |
61 | | -# file, so it needs no pattern (and its patterns would be quadratic in its |
62 | | -# length, one per dot, each as long as the name). |
63 | | -_NAME_MAX = 255 |
64 | 63 | # The most sparse-checkout patterns a checkout may have: matching costs |
65 | | -# patterns x paths, and they are built from pull request content. |
| 64 | +# patterns x paths, and they are built from pull request content. Their |
| 65 | +# total size must also stay within a small multiple of the diff's (see |
| 66 | +# MAX_DIFF_BYTES): a test gets at most two patterns, each about as long as |
| 67 | +# its path, and the only text that is part of many patterns, a suite's |
| 68 | +# name, is short. |
66 | 69 | MAX_PATTERNS = 20_000 |
67 | 70 | # The largest diff (of tests/, in bytes) a pull request may have: it is |
68 | 71 | # held in memory, and copied and split into lines more than once. |
@@ -94,28 +97,21 @@ def _escape_pattern(path: str) -> str: |
94 | 97 | return re.sub(r'([\\*?\[\]!#])', r'\\\1', path) |
95 | 98 |
|
96 | 99 |
|
97 | | -def _test_base_names(file_name: str) -> list[str]: |
98 | | - '''Return the candidate base names of a test file (for its '.<base>.rto' |
99 | | - recordings directory), e.g. 'a.b.sft.cpp' -> ['a.b.sft', 'a.b', 'a']. |
100 | | - ''' |
101 | | - parts = file_name.split('.') |
102 | | - return ['.'.join(parts[:count]) for count in range(len(parts) - 1, 0, -1)] |
103 | | - |
104 | | - |
105 | 100 | def patterns_for_test(test_path: PurePosixPath) -> list[str]: |
106 | 101 | '''Sparse-checkout patterns for one test (a repository-relative path such |
107 | | - as 'tests/tests/suite/dir/name.sft.cpp'): the test file and its recordings, |
108 | | - or the whole directory of a multi-file test. |
| 102 | + as 'tests/tests/suite/dir/name.sft.cpp'): the test file and its recordings |
| 103 | + (where the test runner keeps them, '.<bare name>.rto'), or the whole |
| 104 | + directory of a multi-file test. At most two, each about as long as the |
| 105 | + path, however it is named (see MAX_PATTERNS). |
109 | 106 | ''' |
110 | | - if len(test_path.name.encode()) > _NAME_MAX: |
111 | | - return [] |
112 | 107 | directory = _escape_pattern(str(test_path.parent)) |
113 | 108 | if '.mft.' in test_path.name: |
114 | 109 | return [f"/{directory}/"] |
115 | | - patterns = [f"/{_escape_pattern(str(test_path))}"] |
116 | | - for base_name in _test_base_names(test_path.name): |
117 | | - patterns.append(f"/{directory}/.{_escape_pattern(base_name)}.rto/") |
118 | | - return patterns |
| 110 | + bare_name = _escape_pattern(get_bare_name(test_path)) |
| 111 | + return [ |
| 112 | + f"/{_escape_pattern(str(test_path))}", |
| 113 | + f"/{directory}/.{bare_name}.rto/", |
| 114 | + ] |
119 | 115 |
|
120 | 116 |
|
121 | 117 | def _patterns_for_changed_test_file(path: PurePosixPath) -> list[str]: |
@@ -163,8 +159,11 @@ def changes_patterns(diff: str) -> list[str]: |
163 | 159 | _add_patterns(patterns, _patterns_for_changed_test_file(path)) |
164 | 160 | elif (path.parts[:2] == ('tests', 'expectations') and |
165 | 161 | path.suffix == '.log'): |
166 | | - # Expectation lines name tests relative to the suite. |
167 | | - current_suite = path.stem |
| 162 | + # Expectation lines name tests relative to the suite, so its name is |
| 163 | + # part of the patterns of each (see MAX_PATTERNS). A file whose name |
| 164 | + # no suite may have (e.g. too long) names no tests. |
| 165 | + if edgtest.is_valid_suite_name(path.stem): |
| 166 | + current_suite = path.stem |
168 | 167 | continue |
169 | 168 | if current_suite is None or line.startswith(('---', '+++')): |
170 | 169 | continue |
|
0 commit comments