js-browser-architecture-contract_v2
| ID |
4 |
| UUID |
35d63221-a407-4ede-a60b-577f5fbfad61 |
| Version |
1.0 |
| Status |
active |
| Scope |
|
| Erstellt |
2025-12-20 10:59:58 von migration |
| Aktualisiert |
2025-12-20 10:59:58 |
YAML-Inhalt
meta:
document_type: architecture_contract
document_id: js-browser-architecture-contract
normative: true
binding: mandatory
effective_from: 2025-01-01
identity:
name: js-browser-architecture-contract
version: 2.0.0
status: active
stability: strict
changelog:
- version: 2.0.0
date: 2025-12-15
changes:
- added deps_shape to html_integration.entry
- added withBoundary interface definition
- added httpClient retry_policy
- added adapters.aggregation rules
- added runtime_apis.observers specification
- added storage.runtime_usage policy
intent:
purpose: >
Defines mandatory architectural, executional, and behavioral constraints
for native browser JavaScript produced by humans or AI systems.
goals:
- deterministic_execution
- architectural_consistency
- side_effect_control
- testability
- long_term_maintainability
applicability:
applies_to:
- human_authored_code
- ai_generated_code
runtime:
- native_browser_only
excluded_contexts:
- nodejs
- build_pipelines
- server_side_execution
authority:
precedence: highest
overrides:
- coding_guidelines
- styleguides
- framework_conventions
conflict_resolution: this_document_wins
compliance:
required_for_execution: true
violation_policy:
on_violation: reject_output
remediation: regenerate_or_refactor
partial_compliance: forbidden
evolution:
change_policy:
breaking_changes: explicit_version_bump_required
silent_behavior_changes: forbidden
review_required: true
audience:
primary:
- ai_code_generators
- automated_review_systems
secondary:
- senior_frontend_engineers
- system_architects
integrity:
checksum_algorithm: sha256
checksum: "726ab421592fe95d2c8b3ae344d091b7a306d2fc67ae4e484d0921709a84901e"
legal:
warranty: none
liability: excluded
context:
runtime: browser
execution: native
compatibility_target:
definition:
chrome_min: 120
firefox_min: 120
safari_min: 17
edge_min: 120
constraints:
build_tools: forbidden
bundler: forbidden
transpiler: forbidden
external_dependencies: forbidden
polyfills: forbidden
language:
standard: ECMAScript
year: 2024
baseline: ES6
module_system: ES_modules
execution_mode: native_browser
feature_policy:
allow_all_supported_by_target: true
imports:
module_system_required: true
commonjs: forbidden
require: forbidden
dynamic_import: forbidden
import_maps: forbidden
code_splitting: forbidden
lazy_loading: forbidden
specifier_rules:
relative_paths: required
explicit_file_extension: required
bare_specifiers: forbidden
modules:
scope: isolated
adapters:
location: "./src/adapters"
naming_rule: "*Adapter.js"
enforce_structure_in_output: true
only_adapters_may_access_allowed_direct_globals: true
aggregation:
allowed: true
preferred: true
recommended_minimal_set:
- runtimeAdapter
- eventAdapter
- httpClientAdapter
event_adapter:
required: true
only_place_where_addEventListener_is_called: true
must_wrap_handlers_with: withBoundary
global_variables:
forbid_creation: true
forbid_direct_access_outside_adapters: true
adapters_must_be_imported: true
allowed_direct_globals_in_adapters:
- window
- document
- location
- console
- setTimeout
- clearTimeout
- requestAnimationFrame
- cancelAnimationFrame
- AbortController
- URL
- URLSearchParams
- performance
- Date
date_usage_constraints:
forbid_date_now_outside_clock: true
forbid_new_date_without_explicit_input_outside_clock: true
allow_parsing_and_formatting_only: true
side_effects_on_import:
forbid:
dom_mutation: true
network_requests: true
storage_writes: true
timers_start: true
event_listener_registration: true
allow:
constant_initialization: true
pure_module_setup: true
initialization:
explicit_entrypoint_required: true
entry_export: init
auto_run_on_import: forbidden
caching: native_browser_cache
html_integration:
script_tag:
type: module
async_attribute: forbidden
defer: implicit
entry:
single_entry_script: required
forbid_additional_module_scripts: true
invocation_pattern: "import { init } from './PATH/TO/ENTRY.js'; init(deps);"
deps_shape:
clock: injected
rng: injected
httpClient: injected
ui: injected
logger: injected
runId: injected
syntax_rules:
strict_mode: implicit
declarations:
const: preferred
let: allowed
var: forbidden
equality:
double_equals: forbidden
triple_equals: required
truthiness:
abuse: forbidden
rules:
forbid_non_boolean_in_conditionals: true
require_explicit_null_checks: true
require_explicit_empty_string_checks: true
require_explicit_array_length_checks: true
coercion:
implicit: discouraged
explicit: preferred
classification: style_guideline
runtime_apis:
dom: allowed
window_usage:
allowed_via_adapters_only: true
fetch:
allowed: true
required: false
constraints:
direct_fetch_calls: forbidden
must_use_injected_http_client: true
abort_controller_required: true
timeout_required: true
fallback: forbidden
observers:
allowed: true
usage:
via_adapters_only: true
lifecycle:
disconnect_on_dispose: required
timeout_required: true
storage:
runtime_usage:
allowed: true
via_adapters_only: true
allowed_apis:
- localStorage
- sessionStorage
- cookies
constraints:
direct_access_outside_adapters: forbidden
must_handle_quota_exceeded: true
must_handle_unavailable: true
injection_contract:
storageClient:
get: "(key) => string|null"
set: "(key, value, options?) => void"
remove: "(key) => void"
clear: "() => void"
determinism:
reproducibility: required
non_deterministic_sources:
time:
injected_via: clock
enforcement:
forbid_direct_date_now_outside_clock: true
forbid_new_date_without_explicit_input_outside_clock: true
randomness:
injected_via: rng
network:
injected_via: httpClient
injection_contracts:
clock:
now_epoch_ms_utc: "() => number"
allowed_internal_time_source: "Date.now"
rng:
random_float_0_1: "() => number"
httpClient:
request: "(request, options) => Promise<response>"
request_shape:
method: "GET|POST|PUT|PATCH|DELETE"
url: "string"
headers: "Record<string,string>|undefined"
body: "string|FormData|ArrayBuffer|undefined"
response_shape:
status: "number"
headers: "Record<string,string>"
body: "unknown"
options:
signal: "AbortSignal"
timeout_ms: "number"
retry_policy:
max_attempts: "number"
backoff_strategy: "none|fixed|exponential"
retry_on_status:
- 408
- 429
- 500
- 502
- 503
- 504
retry_on_network_errors: true
ui:
showMessage: "(payload) => void"
disableFeature: "(featureKey) => void"
offerRetry: "(payload) => Promise<boolean>"
error_handling:
silent_failures: forbidden
strategy:
default: throw
boundaries:
top_level_event_boundary:
required: true
implementation_rule:
all_event_handlers_must_be_wrapped: true
wrapper_name: withBoundary
interface:
withBoundary: "(handler, meta) => wrappedHandler"
meta_shape:
code: "string"
featureKey: "string"
ui: "injected"
behavior:
catch: true
log: structured
user_feedback: controlled_message
cancellation:
network_operations:
abort_controller_required: true
external_waits:
observers:
timeout_required: true
must_disconnect_on_timeout: true
promises_waiting_on_external_state:
timeout_required: true
animation_frames:
cancel_required: true
user_events:
must_be_unsubscribable: true
unsubscribe_via_dispose: true
ui_workflows:
dispose_required: true
time_modeling:
internal_representation: epoch_ms_utc
display:
iso: allowed
intl:
allowed: true
timezone_must_be_explicit: true
degradation:
controlled_failure:
required: true
policy_labels:
on_missing_feature: show_user_message_and_disable_feature
on_network_error: show_user_message_and_retry_option
on_unexpected_error: show_user_message_and_log
required_ui_functions:
- ui.showMessage
- ui.disableFeature
- ui.offerRetry
observability:
logging:
structured: true
format:
required_fields:
- level
- code
- message
- runId
optional_fields:
- context
- error
empty_catch_blocks: forbidden
error_reproducibility: required
output:
allowed:
javascript: true
html: optional
format:
markdown: forbidden
prose: forbidden
code_comments:
allowed: true
constraints:
no_explanatory_blocks: true
only_files: true
Aktionen
← Zurück zur Übersicht