f-layer 2.0.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- f_layer-2.0.0/.gitattributes +1 -0
- f_layer-2.0.0/.github/ISSUE_TEMPLATE/bug_report.yml +41 -0
- f_layer-2.0.0/.github/ISSUE_TEMPLATE/config.yml +2 -0
- f_layer-2.0.0/.github/ISSUE_TEMPLATE/feature_request.yml +31 -0
- f_layer-2.0.0/.github/pull_request_template.md +15 -0
- f_layer-2.0.0/.github/workflows/close-linked-tasks.yml +86 -0
- f_layer-2.0.0/.github/workflows/documentation-gates.yml +78 -0
- f_layer-2.0.0/.github/workflows/python-quality.yml +60 -0
- f_layer-2.0.0/.github/workflows/release-publish.yml +111 -0
- f_layer-2.0.0/.github/workflows/release-validation.yml +72 -0
- f_layer-2.0.0/.gitignore +42 -0
- f_layer-2.0.0/AGENTS.md +67 -0
- f_layer-2.0.0/CHANGELOG.md +218 -0
- f_layer-2.0.0/CONTRIBUTING.md +15 -0
- f_layer-2.0.0/DEVELOPMENT_PROTOCOL.md +193 -0
- f_layer-2.0.0/LICENSE +201 -0
- f_layer-2.0.0/PKG-INFO +232 -0
- f_layer-2.0.0/README.md +199 -0
- f_layer-2.0.0/SECURITY.md +17 -0
- f_layer-2.0.0/docs/README.md +17 -0
- f_layer-2.0.0/docs/RELEASE_WORKFLOW.md +228 -0
- f_layer-2.0.0/docs/adr/0000-template.md +25 -0
- f_layer-2.0.0/docs/adr/0001-config-state-contracts.md +105 -0
- f_layer-2.0.0/docs/adr/0002-read-only-provider-boundary.md +44 -0
- f_layer-2.0.0/docs/adr/0003-safe-diagnostics.md +64 -0
- f_layer-2.0.0/docs/adr/0004-documentation-platform.md +65 -0
- f_layer-2.0.0/docs/adr/0005-durable-owned-lifecycle.md +108 -0
- f_layer-2.0.0/docs/adr/0006-yandex-lifecycle.md +51 -0
- f_layer-2.0.0/docs/adr/0007-secure-gateway-profile.md +115 -0
- f_layer-2.0.0/docs/adr/0008-reproducible-release-automation.md +64 -0
- f_layer-2.0.0/docs/adr/0009-distribution-version-source.md +41 -0
- f_layer-2.0.0/docs/adr/0010-documentation-completeness.md +71 -0
- f_layer-2.0.0/docs/adr/0011-explicit-extension-discovery.md +87 -0
- f_layer-2.0.0/docs/adr/0012-consumer-neutral-evidence-contracts.md +76 -0
- f_layer-2.0.0/docs/adr/0013-static-site-profile.md +114 -0
- f_layer-2.0.0/docs/adr/0014-scoped-releases-and-changelog.md +105 -0
- f_layer-2.0.0/docs/adr/0015-accountable-ai-translation-review.md +56 -0
- f_layer-2.0.0/docs/adr/0016-vpn-provisioning-contracts.md +170 -0
- f_layer-2.0.0/docs/adr/0017-package-installation.md +70 -0
- f_layer-2.0.0/docs/adr/0018-generated-documentation-translations.md +48 -0
- f_layer-2.0.0/docs/adr/0019-private-vpn-project-workflow.md +181 -0
- f_layer-2.0.0/docs/adr/README.md +57 -0
- f_layer-2.0.0/docs/architecture/README.md +20 -0
- f_layer-2.0.0/docs/architecture/amneziawg.md +140 -0
- f_layer-2.0.0/docs/architecture/configuration-state.md +149 -0
- f_layer-2.0.0/docs/architecture/diagnostics.md +105 -0
- f_layer-2.0.0/docs/architecture/ecosystem-integration.md +155 -0
- f_layer-2.0.0/docs/architecture/extensions.md +146 -0
- f_layer-2.0.0/docs/architecture/lifecycle.md +116 -0
- f_layer-2.0.0/docs/architecture/provider-contract.md +75 -0
- f_layer-2.0.0/docs/architecture/reference.md +91 -0
- f_layer-2.0.0/docs/architecture/secure-gateway.md +185 -0
- f_layer-2.0.0/docs/architecture/static-site.md +206 -0
- f_layer-2.0.0/docs/architecture/vless-reality.md +183 -0
- f_layer-2.0.0/docs/architecture/yandex-lifecycle.md +95 -0
- f_layer-2.0.0/docs/development/PYTHON_CODE_STYLE.md +78 -0
- f_layer-2.0.0/docs/development/README.md +11 -0
- f_layer-2.0.0/docs/development/distribution.md +145 -0
- f_layer-2.0.0/docs/development/documentation-coverage.md +108 -0
- f_layer-2.0.0/docs/development/validation.md +71 -0
- f_layer-2.0.0/docs/development/vpn-release-acceptance.md +194 -0
- f_layer-2.0.0/docs/i18n/README.md +95 -0
- f_layer-2.0.0/docs/i18n/api-labels.toml +105 -0
- f_layer-2.0.0/docs/i18n/fallbacks.toml +94 -0
- f_layer-2.0.0/docs/i18n/generated/ru/api-project.toml +329 -0
- f_layer-2.0.0/docs/i18n/generated/ru/api-resources.toml +23 -0
- f_layer-2.0.0/docs/i18n/generated/ru/api-vpn.toml +430 -0
- f_layer-2.0.0/docs/i18n/generated/ru/api.toml +2652 -0
- f_layer-2.0.0/docs/i18n/generated/ru/coverage.toml +276 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/.github/pull_request_template.md.toml +25 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/AGENTS.md.toml +77 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/CHANGELOG.md.toml +166 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/CONTRIBUTING.md.toml +25 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/DEVELOPMENT_PROTOCOL.md.toml +9 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/README.md.toml +207 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/SECURITY.md.toml +27 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/README.md.toml +22 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/RELEASE_WORKFLOW.md.toml +172 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/adr/0000-template.md.toml +35 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/adr/0001-config-state-contracts.md.toml +60 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/adr/0002-read-only-provider-boundary.md.toml +54 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/adr/0003-safe-diagnostics.md.toml +50 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/adr/0004-documentation-platform.md.toml +44 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/adr/0005-durable-owned-lifecycle.md.toml +54 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/adr/0006-yandex-lifecycle.md.toml +61 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/adr/0007-secure-gateway-profile.md.toml +68 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/adr/0008-reproducible-release-automation.md.toml +46 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/adr/0009-distribution-version-source.md.toml +37 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/adr/0010-documentation-completeness.md.toml +46 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/adr/0011-explicit-extension-discovery.md.toml +49 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/adr/0012-consumer-neutral-evidence-contracts.md.toml +53 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/adr/0013-static-site-profile.md.toml +58 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/adr/0014-scoped-releases-and-changelog.md.toml +73 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/adr/0015-accountable-ai-translation-review.md.toml +40 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/adr/0016-vpn-provisioning-contracts.md.toml +87 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/adr/0017-package-installation.md.toml +46 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/adr/0018-generated-documentation-translations.md.toml +36 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/adr/0019-private-vpn-project-workflow.md.toml +99 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/adr/README.md.toml +65 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/architecture/README.md.toml +30 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/architecture/amneziawg.md.toml +147 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/architecture/configuration-state.md.toml +157 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/architecture/diagnostics.md.toml +117 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/architecture/ecosystem-integration.md.toml +158 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/architecture/extensions.md.toml +152 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/architecture/lifecycle.md.toml +130 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/architecture/provider-contract.md.toml +141 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/architecture/reference.md.toml +103 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/architecture/secure-gateway.md.toml +197 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/architecture/static-site.md.toml +219 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/architecture/vless-reality.md.toml +199 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/architecture/yandex-lifecycle.md.toml +172 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/development/PYTHON_CODE_STYLE.md.toml +88 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/development/README.md.toml +21 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/development/distribution.md.toml +118 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/development/documentation-coverage.md.toml +65 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/development/validation.md.toml +61 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/development/vpn-release-acceptance.md.toml +140 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/i18n/README.md.toml +63 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/releases/1.0.0.md.toml +52 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/releases/1.1.0.md.toml +61 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/releases/1.2.0.md.toml +68 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/releases/1.2.1.md.toml +61 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/releases/2.0.0.md.toml +66 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/docs/site/README.md.toml +38 -0
- f_layer-2.0.0/docs/i18n/generated/ru/repository/examples/integrations/README.md.toml +36 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/api-project.toml +329 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/api-resources.toml +23 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/api-vpn.toml +430 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/api.toml +2652 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/coverage.toml +276 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/.github/pull_request_template.md.toml +25 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/AGENTS.md.toml +77 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/CHANGELOG.md.toml +166 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/CONTRIBUTING.md.toml +25 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/DEVELOPMENT_PROTOCOL.md.toml +9 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/README.md.toml +190 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/SECURITY.md.toml +27 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/README.md.toml +22 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/RELEASE_WORKFLOW.md.toml +172 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/adr/0000-template.md.toml +35 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/adr/0001-config-state-contracts.md.toml +60 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/adr/0002-read-only-provider-boundary.md.toml +54 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/adr/0003-safe-diagnostics.md.toml +50 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/adr/0004-documentation-platform.md.toml +44 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/adr/0005-durable-owned-lifecycle.md.toml +54 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/adr/0006-yandex-lifecycle.md.toml +61 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/adr/0007-secure-gateway-profile.md.toml +68 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/adr/0008-reproducible-release-automation.md.toml +46 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/adr/0009-distribution-version-source.md.toml +37 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/adr/0010-documentation-completeness.md.toml +46 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/adr/0011-explicit-extension-discovery.md.toml +49 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/adr/0012-consumer-neutral-evidence-contracts.md.toml +53 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/adr/0013-static-site-profile.md.toml +58 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/adr/0014-scoped-releases-and-changelog.md.toml +73 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/adr/0015-accountable-ai-translation-review.md.toml +40 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/adr/0016-vpn-provisioning-contracts.md.toml +87 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/adr/0017-package-installation.md.toml +46 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/adr/0018-generated-documentation-translations.md.toml +36 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/adr/0019-private-vpn-project-workflow.md.toml +99 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/adr/README.md.toml +65 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/architecture/README.md.toml +27 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/architecture/amneziawg.md.toml +123 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/architecture/configuration-state.md.toml +131 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/architecture/diagnostics.md.toml +100 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/architecture/ecosystem-integration.md.toml +133 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/architecture/extensions.md.toml +127 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/architecture/lifecycle.md.toml +114 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/architecture/provider-contract.md.toml +121 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/architecture/reference.md.toml +94 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/architecture/secure-gateway.md.toml +166 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/architecture/static-site.md.toml +182 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/architecture/vless-reality.md.toml +164 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/architecture/yandex-lifecycle.md.toml +134 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/development/PYTHON_CODE_STYLE.md.toml +88 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/development/README.md.toml +21 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/development/distribution.md.toml +116 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/development/documentation-coverage.md.toml +65 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/development/validation.md.toml +61 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/development/vpn-release-acceptance.md.toml +134 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/i18n/README.md.toml +63 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/releases/1.0.0.md.toml +52 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/releases/1.1.0.md.toml +61 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/releases/1.2.0.md.toml +68 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/releases/1.2.1.md.toml +61 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/releases/2.0.0.md.toml +66 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/docs/site/README.md.toml +38 -0
- f_layer-2.0.0/docs/i18n/generated/zh-CN/repository/examples/integrations/README.md.toml +31 -0
- f_layer-2.0.0/docs/i18n/glossaries/ru.toml +82 -0
- f_layer-2.0.0/docs/i18n/glossaries/zh-CN.toml +85 -0
- f_layer-2.0.0/docs/i18n/project.toml +21 -0
- f_layer-2.0.0/docs/i18n/units.toml +589 -0
- f_layer-2.0.0/docs/releases/1.0.0.md +54 -0
- f_layer-2.0.0/docs/releases/1.1.0.md +66 -0
- f_layer-2.0.0/docs/releases/1.2.0.md +77 -0
- f_layer-2.0.0/docs/releases/1.2.1.md +64 -0
- f_layer-2.0.0/docs/releases/2.0.0.md +75 -0
- f_layer-2.0.0/docs/requirements-api.txt +43 -0
- f_layer-2.0.0/docs/site/README.md +58 -0
- f_layer-2.0.0/docs/site/api-coverage.toml +8 -0
- f_layer-2.0.0/docs/site/content/en/api/index.md +13 -0
- f_layer-2.0.0/docs/site/content/en/architecture.md +32 -0
- f_layer-2.0.0/docs/site/content/en/assets/brand/FTech-card-F-Layer.png +0 -0
- f_layer-2.0.0/docs/site/content/en/assets/brand/flayer-horizontal.svg +35 -0
- f_layer-2.0.0/docs/site/content/en/assets/brand/flayer-sign.svg +26 -0
- f_layer-2.0.0/docs/site/content/en/assets/stylesheets/flayer.css +53 -0
- f_layer-2.0.0/docs/site/content/en/brand.md +19 -0
- f_layer-2.0.0/docs/site/content/en/development.md +54 -0
- f_layer-2.0.0/docs/site/content/en/documentation.md +67 -0
- f_layer-2.0.0/docs/site/content/en/guide/ai-operator.md +205 -0
- f_layer-2.0.0/docs/site/content/en/guide/cli.md +91 -0
- f_layer-2.0.0/docs/site/content/en/guide/configuration.md +150 -0
- f_layer-2.0.0/docs/site/content/en/guide/first-deployment.md +218 -0
- f_layer-2.0.0/docs/site/content/en/guide/index.md +172 -0
- f_layer-2.0.0/docs/site/content/en/guide/installation.md +72 -0
- f_layer-2.0.0/docs/site/content/en/index.md +60 -0
- f_layer-2.0.0/docs/site/content/ru/api/index.md +13 -0
- f_layer-2.0.0/docs/site/content/ru/architecture.md +35 -0
- f_layer-2.0.0/docs/site/content/ru/brand.md +18 -0
- f_layer-2.0.0/docs/site/content/ru/development.md +37 -0
- f_layer-2.0.0/docs/site/content/ru/documentation.md +70 -0
- f_layer-2.0.0/docs/site/content/ru/guide/ai-operator.md +210 -0
- f_layer-2.0.0/docs/site/content/ru/guide/cli.md +96 -0
- f_layer-2.0.0/docs/site/content/ru/guide/configuration.md +155 -0
- f_layer-2.0.0/docs/site/content/ru/guide/first-deployment.md +165 -0
- f_layer-2.0.0/docs/site/content/ru/guide/index.md +181 -0
- f_layer-2.0.0/docs/site/content/ru/guide/installation.md +72 -0
- f_layer-2.0.0/docs/site/content/ru/index.md +62 -0
- f_layer-2.0.0/docs/site/content/zh-CN/api/index.md +10 -0
- f_layer-2.0.0/docs/site/content/zh-CN/architecture.md +21 -0
- f_layer-2.0.0/docs/site/content/zh-CN/brand.md +16 -0
- f_layer-2.0.0/docs/site/content/zh-CN/development.md +37 -0
- f_layer-2.0.0/docs/site/content/zh-CN/documentation.md +37 -0
- f_layer-2.0.0/docs/site/content/zh-CN/guide/ai-operator.md +176 -0
- f_layer-2.0.0/docs/site/content/zh-CN/guide/cli.md +58 -0
- f_layer-2.0.0/docs/site/content/zh-CN/guide/configuration.md +124 -0
- f_layer-2.0.0/docs/site/content/zh-CN/guide/first-deployment.md +164 -0
- f_layer-2.0.0/docs/site/content/zh-CN/guide/index.md +159 -0
- f_layer-2.0.0/docs/site/content/zh-CN/guide/installation.md +66 -0
- f_layer-2.0.0/docs/site/content/zh-CN/index.md +54 -0
- f_layer-2.0.0/docs/site/mkdocs.yml +103 -0
- f_layer-2.0.0/docs/site/repository-coverage.toml +63 -0
- f_layer-2.0.0/examples/integrations/README.md +25 -0
- f_layer-2.0.0/examples/integrations/benchmark-request.json +13 -0
- f_layer-2.0.0/examples/integrations/benchmark-result.json +28 -0
- f_layer-2.0.0/examples/integrations/health-request.json +13 -0
- f_layer-2.0.0/examples/integrations/health-result.json +22 -0
- f_layer-2.0.0/examples/integrations/lifecycle-report-request.json +13 -0
- f_layer-2.0.0/examples/integrations/lifecycle-report-result.json +28 -0
- f_layer-2.0.0/examples/integrations/state-request.json +13 -0
- f_layer-2.0.0/examples/integrations/state-result.json +16 -0
- f_layer-2.0.0/examples/integrations/status-request.json +13 -0
- f_layer-2.0.0/examples/integrations/status-result.json +22 -0
- f_layer-2.0.0/examples/secure-gateway.toml +37 -0
- f_layer-2.0.0/examples/static-site.toml +30 -0
- f_layer-2.0.0/examples/vpn/amneziawg.toml +29 -0
- f_layer-2.0.0/pyproject.toml +93 -0
- f_layer-2.0.0/src/flayer/__init__.py +5 -0
- f_layer-2.0.0/src/flayer/__main__.py +247 -0
- f_layer-2.0.0/src/flayer/_vpn_guest.py +130 -0
- f_layer-2.0.0/src/flayer/core/__init__.py +1 -0
- f_layer-2.0.0/src/flayer/core/config.py +198 -0
- f_layer-2.0.0/src/flayer/core/contracts.py +114 -0
- f_layer-2.0.0/src/flayer/core/lifecycle.py +767 -0
- f_layer-2.0.0/src/flayer/core/state.py +351 -0
- f_layer-2.0.0/src/flayer/diagnostics/__init__.py +20 -0
- f_layer-2.0.0/src/flayer/diagnostics/benchmark.py +272 -0
- f_layer-2.0.0/src/flayer/diagnostics/contracts.py +167 -0
- f_layer-2.0.0/src/flayer/diagnostics/health.py +154 -0
- f_layer-2.0.0/src/flayer/diagnostics/reporting.py +24 -0
- f_layer-2.0.0/src/flayer/extensions/__init__.py +25 -0
- f_layer-2.0.0/src/flayer/extensions/builtins.py +165 -0
- f_layer-2.0.0/src/flayer/extensions/contracts.py +196 -0
- f_layer-2.0.0/src/flayer/extensions/discovery.py +152 -0
- f_layer-2.0.0/src/flayer/extensions/registry.py +347 -0
- f_layer-2.0.0/src/flayer/guest.py +270 -0
- f_layer-2.0.0/src/flayer/integrations/__init__.py +23 -0
- f_layer-2.0.0/src/flayer/integrations/adapters.py +92 -0
- f_layer-2.0.0/src/flayer/integrations/contracts.py +241 -0
- f_layer-2.0.0/src/flayer/integrations/wire.py +273 -0
- f_layer-2.0.0/src/flayer/profiles/__init__.py +33 -0
- f_layer-2.0.0/src/flayer/profiles/_amnezia_export.py +176 -0
- f_layer-2.0.0/src/flayer/profiles/_vless_guest.py +432 -0
- f_layer-2.0.0/src/flayer/profiles/amneziawg.py +555 -0
- f_layer-2.0.0/src/flayer/profiles/artifacts.py +609 -0
- f_layer-2.0.0/src/flayer/profiles/gateway.py +729 -0
- f_layer-2.0.0/src/flayer/profiles/static_site.py +596 -0
- f_layer-2.0.0/src/flayer/profiles/vless.py +422 -0
- f_layer-2.0.0/src/flayer/profiles/vpn.py +524 -0
- f_layer-2.0.0/src/flayer/providers/__init__.py +1 -0
- f_layer-2.0.0/src/flayer/providers/contracts.py +207 -0
- f_layer-2.0.0/src/flayer/providers/lifecycle.py +177 -0
- f_layer-2.0.0/src/flayer/providers/yandex.py +387 -0
- f_layer-2.0.0/src/flayer/providers/yandex_lifecycle.py +781 -0
- f_layer-2.0.0/src/flayer/py.typed +0 -0
- f_layer-2.0.0/src/flayer/vpn_export.py +72 -0
- f_layer-2.0.0/src/flayer/vpn_project.py +828 -0
- f_layer-2.0.0/tests/conftest.py +68 -0
- f_layer-2.0.0/tests/contract/test_integration_contracts.py +239 -0
- f_layer-2.0.0/tests/contract/test_release_validation.py +760 -0
- f_layer-2.0.0/tests/functional/test_ecosystem_reference.py +140 -0
- f_layer-2.0.0/tests/integration/test_distribution.py +266 -0
- f_layer-2.0.0/tests/integration/test_static_site_lifecycle.py +163 -0
- f_layer-2.0.0/tests/integration/test_vless_router.py +124 -0
- f_layer-2.0.0/tests/integration/test_vpn_distribution.py +127 -0
- f_layer-2.0.0/tests/unit/test_amneziawg_profile.py +323 -0
- f_layer-2.0.0/tests/unit/test_core_config.py +257 -0
- f_layer-2.0.0/tests/unit/test_core_state.py +566 -0
- f_layer-2.0.0/tests/unit/test_diagnostics.py +273 -0
- f_layer-2.0.0/tests/unit/test_diagnostics_benchmark.py +398 -0
- f_layer-2.0.0/tests/unit/test_documentation_coverage.py +434 -0
- f_layer-2.0.0/tests/unit/test_documentation_localization.py +343 -0
- f_layer-2.0.0/tests/unit/test_documentation_platform.py +295 -0
- f_layer-2.0.0/tests/unit/test_extensions.py +600 -0
- f_layer-2.0.0/tests/unit/test_gateway_artifacts.py +741 -0
- f_layer-2.0.0/tests/unit/test_gateway_profile.py +610 -0
- f_layer-2.0.0/tests/unit/test_integration_evidence.py +243 -0
- f_layer-2.0.0/tests/unit/test_lifecycle.py +1052 -0
- f_layer-2.0.0/tests/unit/test_lifecycle_cli.py +199 -0
- f_layer-2.0.0/tests/unit/test_locale_renderer.py +371 -0
- f_layer-2.0.0/tests/unit/test_markdown_tables.py +104 -0
- f_layer-2.0.0/tests/unit/test_owned_json_reader.py +138 -0
- f_layer-2.0.0/tests/unit/test_package.py +9 -0
- f_layer-2.0.0/tests/unit/test_pr_merge_links.py +49 -0
- f_layer-2.0.0/tests/unit/test_provider_contracts.py +103 -0
- f_layer-2.0.0/tests/unit/test_provider_lifecycle.py +93 -0
- f_layer-2.0.0/tests/unit/test_static_site_profile.py +599 -0
- f_layer-2.0.0/tests/unit/test_validation.py +462 -0
- f_layer-2.0.0/tests/unit/test_vless_profile.py +753 -0
- f_layer-2.0.0/tests/unit/test_vpn_contracts.py +486 -0
- f_layer-2.0.0/tests/unit/test_vpn_export.py +364 -0
- f_layer-2.0.0/tests/unit/test_vpn_guest.py +267 -0
- f_layer-2.0.0/tests/unit/test_vpn_project.py +925 -0
- f_layer-2.0.0/tests/unit/test_yandex_lifecycle.py +1105 -0
- f_layer-2.0.0/tests/unit/test_yandex_provider.py +579 -0
- f_layer-2.0.0/tools/__init__.py +1 -0
- f_layer-2.0.0/tools/build_api_reference.py +559 -0
- f_layer-2.0.0/tools/build_locale_sites.py +65 -0
- f_layer-2.0.0/tools/documentation_coverage.py +325 -0
- f_layer-2.0.0/tools/documentation_gates.py +316 -0
- f_layer-2.0.0/tools/generated_localization.py +464 -0
- f_layer-2.0.0/tools/locale_documentation.py +1034 -0
- f_layer-2.0.0/tools/locale_documentation.pyi +73 -0
- f_layer-2.0.0/tools/locale_renderer.py +467 -0
- f_layer-2.0.0/tools/markdown_tables.py +201 -0
- f_layer-2.0.0/tools/pr_merge_links.py +47 -0
- f_layer-2.0.0/tools/release_validation.py +629 -0
- f_layer-2.0.0/tools/translated_docstrings.py +24 -0
- f_layer-2.0.0/tools/translated_docstrings.pyi +16 -0
- f_layer-2.0.0/tools/validate.py +225 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
* text=auto eol=lf
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
name: Bug report
|
|
2
|
+
description: Report reproducible incorrect F-Layer behavior
|
|
3
|
+
title: ""
|
|
4
|
+
labels: []
|
|
5
|
+
body:
|
|
6
|
+
- type: markdown
|
|
7
|
+
attributes:
|
|
8
|
+
value: |
|
|
9
|
+
Do not include credentials, tokens, private keys, or private infrastructure identifiers.
|
|
10
|
+
- type: textarea
|
|
11
|
+
id: summary
|
|
12
|
+
attributes:
|
|
13
|
+
label: Summary
|
|
14
|
+
description: What went wrong?
|
|
15
|
+
validations:
|
|
16
|
+
required: true
|
|
17
|
+
- type: textarea
|
|
18
|
+
id: expected
|
|
19
|
+
attributes:
|
|
20
|
+
label: Expected behavior
|
|
21
|
+
validations:
|
|
22
|
+
required: true
|
|
23
|
+
- type: textarea
|
|
24
|
+
id: reproduce
|
|
25
|
+
attributes:
|
|
26
|
+
label: Reproduction
|
|
27
|
+
description: Provide the smallest safe reproduction that does not expose secrets or unrelated infrastructure.
|
|
28
|
+
validations:
|
|
29
|
+
required: true
|
|
30
|
+
- type: textarea
|
|
31
|
+
id: environment
|
|
32
|
+
attributes:
|
|
33
|
+
label: Environment
|
|
34
|
+
description: F-Layer version/commit, OS, runtime version, provider type, and other relevant non-secret context.
|
|
35
|
+
validations:
|
|
36
|
+
required: true
|
|
37
|
+
- type: textarea
|
|
38
|
+
id: evidence
|
|
39
|
+
attributes:
|
|
40
|
+
label: Evidence
|
|
41
|
+
description: Sanitized logs, trace output, failing test, or other deterministic evidence.
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
name: Feature request
|
|
2
|
+
description: Propose a new F-Layer capability or contract
|
|
3
|
+
title: ""
|
|
4
|
+
labels: []
|
|
5
|
+
body:
|
|
6
|
+
- type: textarea
|
|
7
|
+
id: outcome
|
|
8
|
+
attributes:
|
|
9
|
+
label: Desired outcome
|
|
10
|
+
description: What should become possible after this feature exists?
|
|
11
|
+
validations:
|
|
12
|
+
required: true
|
|
13
|
+
- type: textarea
|
|
14
|
+
id: scope
|
|
15
|
+
attributes:
|
|
16
|
+
label: Scope
|
|
17
|
+
description: Which core/provider/deployment/integration boundary does this affect?
|
|
18
|
+
validations:
|
|
19
|
+
required: true
|
|
20
|
+
- type: textarea
|
|
21
|
+
id: acceptance
|
|
22
|
+
attributes:
|
|
23
|
+
label: Acceptance criteria
|
|
24
|
+
description: What observable evidence would prove the feature complete?
|
|
25
|
+
validations:
|
|
26
|
+
required: true
|
|
27
|
+
- type: textarea
|
|
28
|
+
id: alternatives
|
|
29
|
+
attributes:
|
|
30
|
+
label: Alternatives considered
|
|
31
|
+
description: Existing approaches, workarounds, or related contracts.
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
## Summary
|
|
2
|
+
|
|
3
|
+
<!-- What changed and why? -->
|
|
4
|
+
|
|
5
|
+
## Validation
|
|
6
|
+
|
|
7
|
+
<!-- List the checks or tests actually run and their results. -->
|
|
8
|
+
|
|
9
|
+
## Security / infrastructure impact
|
|
10
|
+
|
|
11
|
+
<!-- Note any cloud mutation, credential, generated-artifact, routing, compatibility, or lifecycle implications. Write "None" when not applicable. -->
|
|
12
|
+
|
|
13
|
+
## Issue
|
|
14
|
+
|
|
15
|
+
Closes #
|
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
name: Close linked Tasks after merge
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
pull_request:
|
|
5
|
+
types:
|
|
6
|
+
- closed
|
|
7
|
+
branches:
|
|
8
|
+
- develop
|
|
9
|
+
- master
|
|
10
|
+
|
|
11
|
+
permissions:
|
|
12
|
+
contents: write
|
|
13
|
+
issues: write
|
|
14
|
+
pull-requests: read
|
|
15
|
+
|
|
16
|
+
jobs:
|
|
17
|
+
close-linked-tasks:
|
|
18
|
+
if: github.event.pull_request.merged == true
|
|
19
|
+
runs-on: ubuntu-latest
|
|
20
|
+
env:
|
|
21
|
+
GH_TOKEN: ${{ github.token }}
|
|
22
|
+
GH_REPO: ${{ github.repository }}
|
|
23
|
+
PR_NUMBER: ${{ github.event.pull_request.number }}
|
|
24
|
+
PR_URL: ${{ github.event.pull_request.html_url }}
|
|
25
|
+
PR_BODY: ${{ github.event.pull_request.body }}
|
|
26
|
+
HEAD_REF: ${{ github.event.pull_request.head.ref }}
|
|
27
|
+
BASE_REF: ${{ github.event.pull_request.base.ref }}
|
|
28
|
+
|
|
29
|
+
steps:
|
|
30
|
+
- name: Check out merged base
|
|
31
|
+
uses: actions/checkout@v5
|
|
32
|
+
with:
|
|
33
|
+
ref: ${{ github.event.pull_request.base.ref }}
|
|
34
|
+
|
|
35
|
+
- name: Set up Python
|
|
36
|
+
uses: actions/setup-python@v6
|
|
37
|
+
with:
|
|
38
|
+
python-version: "3.11"
|
|
39
|
+
|
|
40
|
+
- name: Close explicitly linked Task issues
|
|
41
|
+
shell: bash
|
|
42
|
+
run: |
|
|
43
|
+
set -euo pipefail
|
|
44
|
+
|
|
45
|
+
mapfile -t linked_issues < <(python tools/pr_merge_links.py)
|
|
46
|
+
|
|
47
|
+
for issue_number in "${linked_issues[@]}"; do
|
|
48
|
+
issue="$(gh api "repos/$GH_REPO/issues/$issue_number")"
|
|
49
|
+
|
|
50
|
+
if [ "$(printf '%s' "$issue" | jq -r 'has("pull_request")')" = "true" ]; then
|
|
51
|
+
continue
|
|
52
|
+
fi
|
|
53
|
+
|
|
54
|
+
issue_type="$(printf '%s' "$issue" | jq -r '.type.name // ""')"
|
|
55
|
+
issue_state="$(printf '%s' "$issue" | jq -r '.state')"
|
|
56
|
+
|
|
57
|
+
if [ "$issue_type" != "Task" ] || [ "$issue_state" = "closed" ]; then
|
|
58
|
+
continue
|
|
59
|
+
fi
|
|
60
|
+
|
|
61
|
+
comment="$(jq -nc \
|
|
62
|
+
--arg body "Implemented by merged PR #$PR_NUMBER ($PR_URL). Automatically marked completed after merge into $BASE_REF." \
|
|
63
|
+
'{body:$body}')"
|
|
64
|
+
|
|
65
|
+
printf '%s' "$comment" | gh api \
|
|
66
|
+
--method POST \
|
|
67
|
+
"repos/$GH_REPO/issues/$issue_number/comments" \
|
|
68
|
+
--input - >/dev/null
|
|
69
|
+
|
|
70
|
+
printf '%s' '{"state":"closed","state_reason":"completed"}' | gh api \
|
|
71
|
+
--method PATCH \
|
|
72
|
+
"repos/$GH_REPO/issues/$issue_number" \
|
|
73
|
+
--input - >/dev/null
|
|
74
|
+
done
|
|
75
|
+
|
|
76
|
+
- name: Delete merged same-repository branch
|
|
77
|
+
if: >-
|
|
78
|
+
github.event.pull_request.head.repo.full_name == github.repository &&
|
|
79
|
+
github.event.pull_request.head.ref != 'master' &&
|
|
80
|
+
github.event.pull_request.head.ref != 'develop' &&
|
|
81
|
+
github.event.pull_request.head.ref != github.event.pull_request.base.ref
|
|
82
|
+
shell: bash
|
|
83
|
+
run: |
|
|
84
|
+
set -euo pipefail
|
|
85
|
+
encoded_ref="${HEAD_REF//\//%2F}"
|
|
86
|
+
gh api --method DELETE "repos/$GH_REPO/git/refs/heads/$encoded_ref" || true
|
|
@@ -0,0 +1,78 @@
|
|
|
1
|
+
name: Documentation quality gates
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
pull_request:
|
|
5
|
+
branches: [develop, master]
|
|
6
|
+
push:
|
|
7
|
+
branches: [develop, master]
|
|
8
|
+
workflow_dispatch:
|
|
9
|
+
|
|
10
|
+
permissions:
|
|
11
|
+
contents: read
|
|
12
|
+
|
|
13
|
+
concurrency:
|
|
14
|
+
group: documentation-${{ github.ref }}
|
|
15
|
+
cancel-in-progress: true
|
|
16
|
+
|
|
17
|
+
jobs:
|
|
18
|
+
build-documentation:
|
|
19
|
+
runs-on: ubuntu-latest
|
|
20
|
+
timeout-minutes: 15
|
|
21
|
+
steps:
|
|
22
|
+
- uses: actions/checkout@v5
|
|
23
|
+
- uses: actions/setup-python@v6
|
|
24
|
+
with:
|
|
25
|
+
python-version: '3.12'
|
|
26
|
+
cache: pip
|
|
27
|
+
cache-dependency-path: docs/requirements-api.txt
|
|
28
|
+
- name: Install exact documentation and test tools
|
|
29
|
+
run: |
|
|
30
|
+
python -m pip install --requirement docs/requirements-api.txt
|
|
31
|
+
python -m pip install -e '.[dev]'
|
|
32
|
+
- name: Test documentation failure contracts
|
|
33
|
+
run: PYTHONPATH=src:. python -m pytest --no-cov tests/unit/test_documentation*.py tests/unit/test_locale*.py
|
|
34
|
+
- name: Validate authored locale identity and review evidence
|
|
35
|
+
run: |
|
|
36
|
+
python -m tools.locale_documentation validate \
|
|
37
|
+
--output _build/documentation-gates/locales.json
|
|
38
|
+
- name: Build strict reference from a clean installed wheel
|
|
39
|
+
run: python -m tools.build_locale_sites --require-complete-translations
|
|
40
|
+
- name: Upload previewable documentation
|
|
41
|
+
uses: actions/upload-artifact@v4
|
|
42
|
+
with:
|
|
43
|
+
name: flayer-documentation-preview
|
|
44
|
+
path: _build/api-reference/site
|
|
45
|
+
if-no-files-found: error
|
|
46
|
+
- name: Upload documentation evidence
|
|
47
|
+
if: always()
|
|
48
|
+
uses: actions/upload-artifact@v4
|
|
49
|
+
with:
|
|
50
|
+
name: flayer-documentation-evidence
|
|
51
|
+
path: |
|
|
52
|
+
_build/documentation-gates
|
|
53
|
+
_build/api-reference/build-evidence.json
|
|
54
|
+
_build/api-reference/api-locales.json
|
|
55
|
+
_build/api-reference/repository-coverage.json
|
|
56
|
+
if-no-files-found: warn
|
|
57
|
+
- name: Upload official Pages artifact
|
|
58
|
+
if: github.event_name == 'push' && github.ref == 'refs/heads/master'
|
|
59
|
+
uses: actions/upload-pages-artifact@v3
|
|
60
|
+
with:
|
|
61
|
+
path: _build/api-reference/site
|
|
62
|
+
|
|
63
|
+
deploy-pages:
|
|
64
|
+
if: github.event_name == 'push' && github.ref == 'refs/heads/master'
|
|
65
|
+
needs: build-documentation
|
|
66
|
+
runs-on: ubuntu-latest
|
|
67
|
+
timeout-minutes: 10
|
|
68
|
+
permissions:
|
|
69
|
+
contents: read
|
|
70
|
+
pages: write
|
|
71
|
+
id-token: write
|
|
72
|
+
environment:
|
|
73
|
+
name: github-pages
|
|
74
|
+
url: ${{ steps.deployment.outputs.page_url }}
|
|
75
|
+
steps:
|
|
76
|
+
- name: Deploy verified master-branch documentation
|
|
77
|
+
id: deployment
|
|
78
|
+
uses: actions/deploy-pages@v4
|
|
@@ -0,0 +1,60 @@
|
|
|
1
|
+
name: Python quality
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
pull_request:
|
|
5
|
+
branches:
|
|
6
|
+
- develop
|
|
7
|
+
- master
|
|
8
|
+
push:
|
|
9
|
+
branches:
|
|
10
|
+
- develop
|
|
11
|
+
- master
|
|
12
|
+
|
|
13
|
+
permissions:
|
|
14
|
+
contents: read
|
|
15
|
+
|
|
16
|
+
jobs:
|
|
17
|
+
quality:
|
|
18
|
+
name: Python quality
|
|
19
|
+
runs-on: ubuntu-latest
|
|
20
|
+
timeout-minutes: 15
|
|
21
|
+
|
|
22
|
+
steps:
|
|
23
|
+
- name: Check out repository
|
|
24
|
+
uses: actions/checkout@v5
|
|
25
|
+
|
|
26
|
+
- name: Set up Python
|
|
27
|
+
uses: actions/setup-python@v6
|
|
28
|
+
with:
|
|
29
|
+
python-version: "3.11"
|
|
30
|
+
|
|
31
|
+
- name: Install project and development dependencies
|
|
32
|
+
run: python -m pip install -e ".[dev]"
|
|
33
|
+
|
|
34
|
+
- name: Fetch checksum-pinned Xray for isolated routing tests
|
|
35
|
+
run: |
|
|
36
|
+
python - <<'PYTHON'
|
|
37
|
+
import hashlib
|
|
38
|
+
import io
|
|
39
|
+
from pathlib import Path
|
|
40
|
+
import urllib.request
|
|
41
|
+
import zipfile
|
|
42
|
+
from flayer.profiles._vless_guest import ARCHIVES, XRAY_VERSION
|
|
43
|
+
|
|
44
|
+
name, digest = ARCHIVES["x86_64"]
|
|
45
|
+
url = f"https://github.com/XTLS/Xray-core/releases/download/v{XRAY_VERSION}/{name}"
|
|
46
|
+
with urllib.request.urlopen(url, timeout=120) as response:
|
|
47
|
+
archive = response.read()
|
|
48
|
+
if hashlib.sha256(archive).hexdigest() != digest:
|
|
49
|
+
raise SystemExit("Xray archive checksum mismatch")
|
|
50
|
+
destination = Path("_build/xray/xray")
|
|
51
|
+
destination.parent.mkdir(parents=True, exist_ok=True)
|
|
52
|
+
with zipfile.ZipFile(io.BytesIO(archive)) as bundle:
|
|
53
|
+
destination.write_bytes(bundle.read("xray"))
|
|
54
|
+
destination.chmod(0o700)
|
|
55
|
+
PYTHON
|
|
56
|
+
|
|
57
|
+
- name: Run the canonical local and CI validation gate
|
|
58
|
+
env:
|
|
59
|
+
FLAYER_XRAY_BINARY: ${{ github.workspace }}/_build/xray/xray
|
|
60
|
+
run: python tools/validate.py
|
|
@@ -0,0 +1,111 @@
|
|
|
1
|
+
name: Publish an owner-approved PyPI release
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
workflow_dispatch:
|
|
5
|
+
inputs:
|
|
6
|
+
tag:
|
|
7
|
+
description: 'Existing annotated vX.Y.Z tag owning the current master commit'
|
|
8
|
+
required: true
|
|
9
|
+
type: string
|
|
10
|
+
milestone:
|
|
11
|
+
description: 'Native release-X.Y milestone number; must be closed with no open items'
|
|
12
|
+
required: true
|
|
13
|
+
type: string
|
|
14
|
+
confirm_publication:
|
|
15
|
+
description: 'Publish the validated distributions to production PyPI'
|
|
16
|
+
required: true
|
|
17
|
+
default: false
|
|
18
|
+
type: boolean
|
|
19
|
+
|
|
20
|
+
permissions:
|
|
21
|
+
contents: read
|
|
22
|
+
issues: read
|
|
23
|
+
|
|
24
|
+
concurrency:
|
|
25
|
+
group: flayer-pypi-publication
|
|
26
|
+
cancel-in-progress: false
|
|
27
|
+
|
|
28
|
+
jobs:
|
|
29
|
+
validate-release:
|
|
30
|
+
runs-on: ubuntu-latest
|
|
31
|
+
timeout-minutes: 20
|
|
32
|
+
steps:
|
|
33
|
+
- name: Check out the selected workflow revision and local tag history
|
|
34
|
+
uses: actions/checkout@fbc6f3992d24b796d5a048ff273f7fcc4a7b6c09 # v5
|
|
35
|
+
with:
|
|
36
|
+
fetch-depth: 0
|
|
37
|
+
persist-credentials: false
|
|
38
|
+
- name: Set up Python
|
|
39
|
+
uses: actions/setup-python@ece7cb06caefa5fff74198d8649806c4678c61a1 # v6
|
|
40
|
+
with:
|
|
41
|
+
python-version: '3.11'
|
|
42
|
+
- name: Install the pinned development and build tools
|
|
43
|
+
run: python -m pip install -e '.[dev]'
|
|
44
|
+
- name: Require completed milestone acceptance before validation or publication
|
|
45
|
+
env:
|
|
46
|
+
GH_TOKEN: ${{ github.token }}
|
|
47
|
+
FLAYER_RELEASE_MILESTONE: ${{ inputs.milestone }}
|
|
48
|
+
run: python tools/release_validation.py --check-milestone "$FLAYER_RELEASE_MILESTONE"
|
|
49
|
+
- name: Run the canonical full validation gate
|
|
50
|
+
run: python tools/validate.py
|
|
51
|
+
- name: Recheck milestone acceptance, owner consent, tag ownership and artifacts
|
|
52
|
+
env:
|
|
53
|
+
GH_TOKEN: ${{ github.token }}
|
|
54
|
+
FLAYER_RELEASE_MILESTONE: ${{ inputs.milestone }}
|
|
55
|
+
FLAYER_RELEASE_TAG: ${{ inputs.tag }}
|
|
56
|
+
FLAYER_CONFIRM_PUBLICATION: ${{ inputs.confirm_publication }}
|
|
57
|
+
FLAYER_RELEASE_OWNER: ${{ vars.FLAYER_RELEASE_OWNER }}
|
|
58
|
+
FLAYER_PYPI_ENABLED: ${{ vars.FLAYER_PYPI_ENABLED }}
|
|
59
|
+
run: python tools/release_validation.py --publication --tag "$FLAYER_RELEASE_TAG"
|
|
60
|
+
- name: Resolve VPN dependency wheels for an isolated installation
|
|
61
|
+
run: |
|
|
62
|
+
wheels=(_build/release/dist/*.whl)
|
|
63
|
+
test "${#wheels[@]}" -eq 1
|
|
64
|
+
python -m pip download --only-binary=:all: \
|
|
65
|
+
--dest "$RUNNER_TEMP/flayer-vpn-wheels" "${wheels[0]}[vpn]"
|
|
66
|
+
- name: Test the exact artifacts approved for publication
|
|
67
|
+
env:
|
|
68
|
+
FLAYER_DISTRIBUTION_DIRECTORY: _build/release/dist
|
|
69
|
+
FLAYER_DISTRIBUTION_WHEELHOUSE: ${{ runner.temp }}/flayer-vpn-wheels
|
|
70
|
+
run: |
|
|
71
|
+
export SOURCE_DATE_EPOCH="$(git show -s --format=%ct HEAD)"
|
|
72
|
+
python -m pytest tests/integration/test*distribution.py --no-cov
|
|
73
|
+
- name: Upload the validated distributions for this exact run
|
|
74
|
+
uses: actions/upload-artifact@ea165f8d65b6e75b540449e92b4886f43607fa02 # v4
|
|
75
|
+
with:
|
|
76
|
+
name: flayer-approved-pypi-distributions
|
|
77
|
+
path: _build/release/dist
|
|
78
|
+
if-no-files-found: error
|
|
79
|
+
- name: Upload release build evidence
|
|
80
|
+
uses: actions/upload-artifact@ea165f8d65b6e75b540449e92b4886f43607fa02 # v4
|
|
81
|
+
with:
|
|
82
|
+
name: flayer-approved-pypi-evidence
|
|
83
|
+
path: _build/release/build-evidence.json
|
|
84
|
+
if-no-files-found: error
|
|
85
|
+
|
|
86
|
+
publish-pypi:
|
|
87
|
+
needs: validate-release
|
|
88
|
+
if: >-
|
|
89
|
+
github.repository == 'Fuzzy-Technologies/F-Layer' &&
|
|
90
|
+
github.ref == 'refs/heads/master' &&
|
|
91
|
+
vars.FLAYER_PYPI_ENABLED == 'true' &&
|
|
92
|
+
vars.FLAYER_RELEASE_OWNER != '' &&
|
|
93
|
+
github.actor == vars.FLAYER_RELEASE_OWNER &&
|
|
94
|
+
inputs.confirm_publication == true
|
|
95
|
+
runs-on: ubuntu-latest
|
|
96
|
+
timeout-minutes: 10
|
|
97
|
+
permissions:
|
|
98
|
+
id-token: write
|
|
99
|
+
steps:
|
|
100
|
+
- name: Retrieve the validated artifacts from this workflow run
|
|
101
|
+
uses: actions/download-artifact@d3f86a106a0bac45b974a628896c90dbdf5c8093 # v4
|
|
102
|
+
with:
|
|
103
|
+
name: flayer-approved-pypi-distributions
|
|
104
|
+
path: dist
|
|
105
|
+
- name: Publish with the configured PyPI Trusted Publisher
|
|
106
|
+
uses: pypa/gh-action-pypi-publish@dc37677b2e1c63e2034f94d8a5b11f265b73ba33 # v1.14.2
|
|
107
|
+
with:
|
|
108
|
+
packages-dir: dist
|
|
109
|
+
repository-url: https://upload.pypi.org/legacy/
|
|
110
|
+
skip-existing: false
|
|
111
|
+
attestations: true
|
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
name: Release artifact validation
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
pull_request:
|
|
5
|
+
branches: [develop, master]
|
|
6
|
+
push:
|
|
7
|
+
branches: [develop, master]
|
|
8
|
+
tags: ['v*']
|
|
9
|
+
|
|
10
|
+
permissions:
|
|
11
|
+
contents: read
|
|
12
|
+
|
|
13
|
+
jobs:
|
|
14
|
+
validate-artifacts:
|
|
15
|
+
name: Release artifact validation
|
|
16
|
+
runs-on: ubuntu-latest
|
|
17
|
+
timeout-minutes: 15
|
|
18
|
+
steps:
|
|
19
|
+
- name: Check out the exact reviewed revision and local tag history
|
|
20
|
+
uses: actions/checkout@fbc6f3992d24b796d5a048ff273f7fcc4a7b6c09 # v5
|
|
21
|
+
with:
|
|
22
|
+
fetch-depth: 0
|
|
23
|
+
persist-credentials: false
|
|
24
|
+
- name: Set up Python
|
|
25
|
+
uses: actions/setup-python@ece7cb06caefa5fff74198d8649806c4678c61a1 # v6
|
|
26
|
+
with:
|
|
27
|
+
python-version: '3.11'
|
|
28
|
+
- name: Restore the remote annotated tag after checkout
|
|
29
|
+
if: startsWith(github.ref, 'refs/tags/')
|
|
30
|
+
env:
|
|
31
|
+
RELEASE_TAG: ${{ github.ref_name }}
|
|
32
|
+
run: git fetch --force origin "refs/tags/$RELEASE_TAG:refs/tags/$RELEASE_TAG"
|
|
33
|
+
- name: Install the pinned development and build tools
|
|
34
|
+
run: python -m pip install -e '.[dev]'
|
|
35
|
+
- name: Validate the complete release candidate on tag pushes
|
|
36
|
+
if: startsWith(github.ref, 'refs/tags/')
|
|
37
|
+
run: python tools/validate.py
|
|
38
|
+
- name: Build and audit reproducible wheel and source distributions
|
|
39
|
+
env:
|
|
40
|
+
RELEASE_REF_TYPE: ${{ github.ref_type }}
|
|
41
|
+
RELEASE_TAG: ${{ github.ref_name }}
|
|
42
|
+
run: |
|
|
43
|
+
if [ "$RELEASE_REF_TYPE" = "tag" ]; then
|
|
44
|
+
python tools/release_validation.py --tag "$RELEASE_TAG"
|
|
45
|
+
else
|
|
46
|
+
python tools/release_validation.py
|
|
47
|
+
fi
|
|
48
|
+
- name: Resolve VPN dependency wheels for an isolated installation
|
|
49
|
+
run: |
|
|
50
|
+
wheels=(_build/release/dist/*.whl)
|
|
51
|
+
test "${#wheels[@]}" -eq 1
|
|
52
|
+
python -m pip download --only-binary=:all: \
|
|
53
|
+
--dest "$RUNNER_TEMP/flayer-vpn-wheels" "${wheels[0]}[vpn]"
|
|
54
|
+
- name: Test the audited wheel as an installed application
|
|
55
|
+
env:
|
|
56
|
+
FLAYER_DISTRIBUTION_DIRECTORY: _build/release/dist
|
|
57
|
+
FLAYER_DISTRIBUTION_WHEELHOUSE: ${{ runner.temp }}/flayer-vpn-wheels
|
|
58
|
+
run: |
|
|
59
|
+
export SOURCE_DATE_EPOCH="$(git show -s --format=%ct HEAD)"
|
|
60
|
+
python -m pytest tests/integration/test*distribution.py --no-cov
|
|
61
|
+
- name: Upload audited distribution preview
|
|
62
|
+
uses: actions/upload-artifact@ea165f8d65b6e75b540449e92b4886f43607fa02 # v4
|
|
63
|
+
with:
|
|
64
|
+
name: flayer-release-preview
|
|
65
|
+
path: _build/release/dist
|
|
66
|
+
if-no-files-found: error
|
|
67
|
+
- name: Upload reproducibility and ownership evidence
|
|
68
|
+
uses: actions/upload-artifact@ea165f8d65b6e75b540449e92b4886f43607fa02 # v4
|
|
69
|
+
with:
|
|
70
|
+
name: flayer-release-evidence
|
|
71
|
+
path: _build/release/build-evidence.json
|
|
72
|
+
if-no-files-found: error
|
f_layer-2.0.0/.gitignore
ADDED
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
# Python
|
|
2
|
+
__pycache__/
|
|
3
|
+
*.py[cod]
|
|
4
|
+
*.pyo
|
|
5
|
+
*.pyd
|
|
6
|
+
*.egg-info/
|
|
7
|
+
.eggs/
|
|
8
|
+
build/
|
|
9
|
+
dist/
|
|
10
|
+
_build/
|
|
11
|
+
|
|
12
|
+
# Environments and secrets
|
|
13
|
+
.venv/
|
|
14
|
+
venv/
|
|
15
|
+
.env
|
|
16
|
+
.env.*
|
|
17
|
+
!.env.example
|
|
18
|
+
|
|
19
|
+
# Test and analysis output
|
|
20
|
+
.pytest_cache/
|
|
21
|
+
.mypy_cache/
|
|
22
|
+
.ruff_cache/
|
|
23
|
+
.coverage
|
|
24
|
+
coverage/
|
|
25
|
+
htmlcov/
|
|
26
|
+
|
|
27
|
+
# IDE and OS
|
|
28
|
+
.idea/
|
|
29
|
+
.vscode/
|
|
30
|
+
.DS_Store
|
|
31
|
+
Thumbs.db
|
|
32
|
+
|
|
33
|
+
# Runtime/local state
|
|
34
|
+
*.log
|
|
35
|
+
*.sqlite
|
|
36
|
+
*.sqlite3
|
|
37
|
+
.local/
|
|
38
|
+
state/
|
|
39
|
+
artifacts/
|
|
40
|
+
|
|
41
|
+
# Generated documentation output
|
|
42
|
+
_build/
|
f_layer-2.0.0/AGENTS.md
ADDED
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
# AGENTS.md
|
|
2
|
+
|
|
3
|
+
## Purpose
|
|
4
|
+
|
|
5
|
+
This file is the mandatory entry point for AI agents, Codex sessions, IDE assistants, automation, and other software agents working in F-Layer.
|
|
6
|
+
|
|
7
|
+
Before changing code or documentation, read and follow [DEVELOPMENT_PROTOCOL.md](DEVELOPMENT_PROTOCOL.md). It is the canonical repository development contract.
|
|
8
|
+
|
|
9
|
+
## Repository boundary
|
|
10
|
+
|
|
11
|
+
- Work only inside this repository unless the owner explicitly authorizes another repository or external system for the current task.
|
|
12
|
+
- Do not inspect or modify parent directories, sibling repositories, user home data, mounted shares, or unrelated local storage.
|
|
13
|
+
- Do not infer permission to access infrastructure merely because credentials or tooling are available.
|
|
14
|
+
- Read only the files required for the task; prefer targeted search and narrow excerpts over unrestricted context dumps.
|
|
15
|
+
|
|
16
|
+
## Infrastructure safety
|
|
17
|
+
|
|
18
|
+
F-Layer manages infrastructure. Tests and development must not mutate real cloud resources unless the owner explicitly authorizes that exact operation.
|
|
19
|
+
|
|
20
|
+
By default:
|
|
21
|
+
|
|
22
|
+
- provider tests use mocks, fakes, fixtures, or repository-defined isolated resources;
|
|
23
|
+
- destructive create/update/delete operations against real accounts are prohibited;
|
|
24
|
+
- credentials and secrets are never model context and are never committed;
|
|
25
|
+
- cleanup, rollback, idempotency, and failure behavior are first-class contracts.
|
|
26
|
+
|
|
27
|
+
## Language
|
|
28
|
+
|
|
29
|
+
- Source code, comments, docstrings, commit messages, ADRs, canonical documentation, schemas, CLI commands, and repository metadata are English-only.
|
|
30
|
+
- Localization assets may contain their target language.
|
|
31
|
+
- User-facing discussion may follow the user's language.
|
|
32
|
+
|
|
33
|
+
## Mandatory development rules
|
|
34
|
+
|
|
35
|
+
- Follow `DEVELOPMENT_PROTOCOL.md`.
|
|
36
|
+
- Architecture-impacting changes require an ADR or explicit design decision.
|
|
37
|
+
- Prefer deterministic tools and tests when they can answer the question.
|
|
38
|
+
- Keep changes small, reviewable, and scoped to one objective.
|
|
39
|
+
- Do not mix behavior changes with unrelated formatting or cleanup.
|
|
40
|
+
- Never claim completion without applicable tests and evidence.
|
|
41
|
+
- Never add private infrastructure identifiers, local paths, credentials, tokens, or secrets to tracked files.
|
|
42
|
+
|
|
43
|
+
## Git workflow
|
|
44
|
+
|
|
45
|
+
- `master` is the stable/released branch.
|
|
46
|
+
- `develop` is the integration branch.
|
|
47
|
+
- Normal work uses `feature/*`, `fix/*`, `release/*`, or `hotfix/*` branches.
|
|
48
|
+
- Do not push normal implementation work directly to `master` or `develop`.
|
|
49
|
+
- Automated agents may prepare branches, commits, and pull requests when authorized, but must not merge their own PRs unless the owner explicitly requests that merge.
|
|
50
|
+
- Do not force-push protected branches or rewrite published history.
|
|
51
|
+
|
|
52
|
+
## Protected policy files
|
|
53
|
+
|
|
54
|
+
`AGENTS.md` and `DEVELOPMENT_PROTOCOL.md` are owner-controlled policy files. Agents may read and cite them, but must not modify, replace, delete, or weaken them without explicit owner authorization.
|
|
55
|
+
|
|
56
|
+
## Completion
|
|
57
|
+
|
|
58
|
+
Before reporting completion:
|
|
59
|
+
|
|
60
|
+
1. inspect the exact diff;
|
|
61
|
+
2. run targeted tests;
|
|
62
|
+
3. run the canonical full gate when available;
|
|
63
|
+
4. verify no secret, private identifier, or unrelated file entered the change;
|
|
64
|
+
5. update documentation when required;
|
|
65
|
+
6. report actual evidence, failures, and remaining uncertainty.
|
|
66
|
+
|
|
67
|
+
If a required check cannot be run, report it as not run. Never convert an unexecuted check into PASS.
|