This directory contains the common infrastructure for the following tests (also referred below as projects).
- referrer-policy/
- mixed-content/
- upgrade-insecure-requests/
Subdirectories:
- `resources`:
Serves JavaScript test helpers.
- `subresource`:
Serves subresources, with support for redirects, stash, etc.
The subresource paths are managed by `subresourceMap` and
fetched in `requestVia*()` functions in `resources/common.js`.
- `scope`:
Serves nested contexts, such as iframe documents or workers.
Used from `invokeFrom*()` functions in `resources/common.js`.
- `tools`:
Scripts that generate test HTML files. Not used while running tests.
- `/referrer-policy/generic/subresource-test`:
Sanity checking tests for subresource invocation
(This is still placed outside common/)
# Test generator
The test generator ([common/security-features/tools/generate.py](tools/generate.py)) generates test HTML files from templates and a seed (`spec.src.json`) that defines all the test scenarios.
The project (i.e. a WPT subdirectory, for example `referrer-policy/`) that uses the generator should define per-project data and invoke the common generator logic in `common/security-features/tools`.
This is the overview of the project structure:
```
common/security-features/
└── tools/ - the common test generator logic
├── spec.src.json
└── template/ - the test files templates
project-directory/ (e.g. referrer-policy/)
├── spec.src.json
├── generic/
│ ├── test-case.sub.js - Per-project test helper
│ ├── sanity-checker.js (Used by debug target only)
│ └── spec_json.js (Used by debug target only)
└── gen/ - generated tests
```
## Generating the tests
Note: When the repository already contains generated tests, [remove all generated tests](#removing-all-generated-tests) first.
```bash
# Install json5 module if needed.
pip install --user json5
# Generate the test files under gen/ (HTMLs and .headers files).
path/to/common/security-features/tools/generate.py --spec path/to/project-directory/
# Add all generated tests to the repo.
git add path/to/project-directory/gen/ && git commit -m "Add generated tests"
```
This will parse the spec JSON5 files and determine which tests to generate (or skip) while using templates.
- The default spec JSON5: `common/security-features/tools/spec.src.json`.
- Describes common configurations, such as subresource types, source context types, etc.
- The per-project spec JSON5: `project-directory/spec.src.json`.
- Describes project-specific configurations, particularly those related to test generation patterns (`specification`), policy deliveries (e.g. `delivery_type`, `delivery_value`) and `expectation`.
For how these two spec JSON5 files are merged, see [Sub projects](#sub-projects) section.
Note: `spec.src.json` is transitioning to JSON5 [#21710](https://github.com/web-platform-tests/wpt/issues/21710).
During the generation, the spec is validated by ```common/security-features/tools/spec_validator.py```. This is specially important when you're making changes to `spec.src.json`. Make sure it's a valid JSON (no comments or trailing commas). The validator reports specific errors (missing keys etc.), if any.
### Removing all generated tests
Simply remove all files under `project-directory/gen/`.
```bash
rm -r path/to/project-directory/gen/
```
### Options for generating tests
Note: this section is currently obsolete. Only the release template is working.
The generator script has two targets: ```release``` and ```debug```.
* Using **release** for the target will produce tests using a template for optimizing size and performance. The release template is intended for the official web-platform-tests and possibly other test suites. No sanity checking is done in release mode. Use this option whenever you're checking into web-platform-tests.
* When generating for ```debug```, the produced tests will contain more verbosity and sanity checks. Use this target to identify problems with the test suites when making changes locally. Make sure you don't check in tests generated with the debug target.
Note that **release** is the default target when invoking ```generate.py```.
## Sub projects
Projects can be nested, for example to reuse a single `spec.src.json` across similar but slightly different sets of generated tests.
The directory structure would look like:
```
project-directory/ (e.g. referrer-policy/)
├── spec.src.json - Parent project's spec JSON
├── generic/
│ └── test-case.sub.js - Parent project's test helper
├── gen/ - parent project's generated tests
└── sub-project-directory/ (e.g. 4K)
├── spec.src.json - Child project's spec JSON
├── generic/
│ └── test-case.sub.js - Child project's test helper
└── gen/ - child project's generated tests
```
`generate.py --spec project-directory/sub-project-directory` generates test files under `project-directory/sub-project-directory/gen`, based on `project-directory/spec.src.json` and `project-directory/sub-project-directory/spec.src.json`.
- The child project's `spec.src.json` is merged into parent project's `spec.src.json`.
- Two spec JSON objects are merged recursively.
- If a same key exists in both objects, the child's value overwrites the parent's value.
- If both (child's and parent's) values are arrays, then the child's value is concatenated to the parent's value.
- For debugging, `generate.py` dumps the merged spec JSON object as `generic/debug-output.spec.src.json`.
- The child project's generated tests include both of the parent and child project's `test-case.sub.js`:
```html
```
## Updating the tests
The main test logic lives in ```project-directory/generic/test-case.sub.js``` with helper functions defined in ```/common/security-features/resources/common.js``` so you should probably start there.
For updating the test suites you will most likely do **a subset** of the following:
* Add a new subresource type:
* Add a new sub-resource python script to `/common/security-features/subresource/`.
* Add a sanity check test for a sub-resource to `referrer-policy/generic/subresource-test/`.
* Add a new entry to `subresourceMap` in `/common/security-features/resources/common.js`.
* Add a new entry to `valid_subresource_names` in `/common/security-features/tools/spec_validator.py`.
* Add a new entry to `subresource_schema` in `spec.src.json`.
* Update `source_context_schema` to specify in which source context the subresource can be used.
* Add a new subresource redirection type
* TODO: to be documented. Example: [https://github.com/web-platform-tests/wpt/pull/18939](https://github.com/web-platform-tests/wpt/pull/18939)
* Add a new subresource origin type
* TODO: to be documented. Example: [https://github.com/web-platform-tests/wpt/pull/18940](https://github.com/web-platform-tests/wpt/pull/18940)
* Add a new source context (e.g. "module sharedworker global scope")
* TODO: to be documented. Example: [https://github.com/web-platform-tests/wpt/pull/18904](https://github.com/web-platform-tests/wpt/pull/18904)
* Add a new source context list (e.g. "subresource request from a dedicated worker in a `