intract 0.1.1__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.
- intract-0.1.1/.gitignore +22 -0
- intract-0.1.1/.idea/.gitignore +5 -0
- intract-0.1.1/.idea/workspace.xml +10 -0
- intract-0.1.1/CHANGELOG.md +36 -0
- intract-0.1.1/LICENSE +7 -0
- intract-0.1.1/Makefile +13 -0
- intract-0.1.1/PKG-INFO +141 -0
- intract-0.1.1/README.md +111 -0
- intract-0.1.1/VERSION +1 -0
- intract-0.1.1/docs/contract-format.md +13 -0
- intract-0.1.1/docs/examples.md +10 -0
- intract-0.1.1/docs/intent-yaml.md +14 -0
- intract-0.1.1/docs/validation.md +12 -0
- intract-0.1.1/examples/configs/intent.yaml +22 -0
- intract-0.1.1/examples/csharp/ScanPipeline.cs +7 -0
- intract-0.1.1/examples/python/parse_extensions.py +8 -0
- intract-0.1.1/examples/typescript/permission.ts +5 -0
- intract-0.1.1/goal.yaml +510 -0
- intract-0.1.1/pyproject.toml +77 -0
- intract-0.1.1/src/intract/__init__.py +31 -0
- intract-0.1.1/src/intract/__main__.py +4 -0
- intract-0.1.1/src/intract/cli.py +93 -0
- intract-0.1.1/src/intract/effects.py +21 -0
- intract-0.1.1/src/intract/models.py +153 -0
- intract-0.1.1/src/intract/normalizer.py +69 -0
- intract-0.1.1/src/intract/parser.py +194 -0
- intract-0.1.1/src/intract/project.py +88 -0
- intract-0.1.1/src/intract/signature.py +78 -0
- intract-0.1.1/src/intract/validation.py +102 -0
- intract-0.1.1/src/intract/yaml_manifest.py +113 -0
- intract-0.1.1/tests/test_manifest.py +26 -0
- intract-0.1.1/tests/test_parser.py +29 -0
- intract-0.1.1/tests/test_validation.py +39 -0
- intract-0.1.1/uv.lock +3596 -0
intract-0.1.1/.gitignore
ADDED
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
.env.example
|
|
2
|
+
.idea/inspectionProfiles/Project_Default.xml
|
|
3
|
+
.idea/inspectionProfiles/profiles_settings.xml
|
|
4
|
+
.idea/intract.iml
|
|
5
|
+
.idea/modules.xml
|
|
6
|
+
.idea/pyProjectModel.xml
|
|
7
|
+
.idea/vcs.xml
|
|
8
|
+
__pycache__/
|
|
9
|
+
*.py[cod]
|
|
10
|
+
.pytest_cache/
|
|
11
|
+
.ruff_cache/
|
|
12
|
+
.mypy_cache/
|
|
13
|
+
.venv/
|
|
14
|
+
venv/
|
|
15
|
+
dist/
|
|
16
|
+
build/
|
|
17
|
+
*.egg-info/
|
|
18
|
+
.coverage
|
|
19
|
+
htmlcov/
|
|
20
|
+
|
|
21
|
+
# Environment variables
|
|
22
|
+
.env
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
<?xml version="1.0" encoding="UTF-8"?>
|
|
2
|
+
<project version="4">
|
|
3
|
+
<component name="ProjectViewState">
|
|
4
|
+
<option name="autoscrollFromSource" value="true" />
|
|
5
|
+
<option name="autoscrollToSource" value="true" />
|
|
6
|
+
<option name="hideEmptyMiddlePackages" value="true" />
|
|
7
|
+
<option name="showLibraryContents" value="true" />
|
|
8
|
+
</component>
|
|
9
|
+
<component name="PropertiesComponent">{}</component>
|
|
10
|
+
</project>
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
# Changelog
|
|
2
|
+
|
|
3
|
+
All notable changes to this project will be documented in this file.
|
|
4
|
+
|
|
5
|
+
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
|
6
|
+
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
7
|
+
|
|
8
|
+
## [Unreleased]
|
|
9
|
+
|
|
10
|
+
## [0.1.1] - 2026-05-29
|
|
11
|
+
|
|
12
|
+
### Docs
|
|
13
|
+
- Update README.md
|
|
14
|
+
- Update docs/contract-format.md
|
|
15
|
+
- Update docs/examples.md
|
|
16
|
+
- Update docs/intent-yaml.md
|
|
17
|
+
- Update docs/validation.md
|
|
18
|
+
|
|
19
|
+
### Test
|
|
20
|
+
- Update tests/test_manifest.py
|
|
21
|
+
- Update tests/test_parser.py
|
|
22
|
+
- Update tests/test_validation.py
|
|
23
|
+
|
|
24
|
+
### Other
|
|
25
|
+
- Update .env.example
|
|
26
|
+
- Update .gitignore
|
|
27
|
+
- Update .idea/.gitignore
|
|
28
|
+
- Update .idea/inspectionProfiles/Project_Default.xml
|
|
29
|
+
- Update .idea/inspectionProfiles/profiles_settings.xml
|
|
30
|
+
- Update .idea/intract.iml
|
|
31
|
+
- Update .idea/modules.xml
|
|
32
|
+
- Update .idea/pyProjectModel.xml
|
|
33
|
+
- Update .idea/vcs.xml
|
|
34
|
+
- Update LICENSE
|
|
35
|
+
- ... and 6 more files
|
|
36
|
+
|
intract-0.1.1/LICENSE
ADDED
intract-0.1.1/Makefile
ADDED
intract-0.1.1/PKG-INFO
ADDED
|
@@ -0,0 +1,141 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: intract
|
|
3
|
+
Version: 0.1.1
|
|
4
|
+
Summary: Intent contract tagging, validation and semantic mapping for codebases.
|
|
5
|
+
Author: Intract Contributors
|
|
6
|
+
Author-email: Tom Sapletta <tom@sapletta.com>
|
|
7
|
+
License-Expression: Apache-2.0
|
|
8
|
+
License-File: LICENSE
|
|
9
|
+
Keywords: code-quality,contract,intent,refactoring,static-analysis,validation
|
|
10
|
+
Classifier: Development Status :: 3 - Alpha
|
|
11
|
+
Classifier: Environment :: Console
|
|
12
|
+
Classifier: Intended Audience :: Developers
|
|
13
|
+
Classifier: Programming Language :: Python :: 3
|
|
14
|
+
Classifier: Programming Language :: Python :: 3.10
|
|
15
|
+
Classifier: Programming Language :: Python :: 3.11
|
|
16
|
+
Classifier: Programming Language :: Python :: 3.12
|
|
17
|
+
Classifier: Topic :: Software Development :: Quality Assurance
|
|
18
|
+
Requires-Python: >=3.10
|
|
19
|
+
Requires-Dist: pyyaml>=6.0
|
|
20
|
+
Requires-Dist: rich>=13.0
|
|
21
|
+
Requires-Dist: typer>=0.12.0
|
|
22
|
+
Provides-Extra: dev
|
|
23
|
+
Requires-Dist: costs>=0.1.20; extra == 'dev'
|
|
24
|
+
Requires-Dist: goal>=2.1.0; extra == 'dev'
|
|
25
|
+
Requires-Dist: mypy>=1.8; extra == 'dev'
|
|
26
|
+
Requires-Dist: pfix>=0.1.60; extra == 'dev'
|
|
27
|
+
Requires-Dist: pytest>=7.0; extra == 'dev'
|
|
28
|
+
Requires-Dist: ruff>=0.4; extra == 'dev'
|
|
29
|
+
Description-Content-Type: text/markdown
|
|
30
|
+
|
|
31
|
+
# Intract
|
|
32
|
+
|
|
33
|
+
|
|
34
|
+
## AI Cost Tracking
|
|
35
|
+
|
|
36
|
+
   
|
|
37
|
+
  
|
|
38
|
+
|
|
39
|
+
- 🤖 **LLM usage:** $0.1500 (1 commits)
|
|
40
|
+
- 👤 **Human dev:** ~$100 (1.0h @ $100/h, 30min dedup)
|
|
41
|
+
|
|
42
|
+
Generated on 2026-05-29 using [openrouter/qwen/qwen3-coder-next](https://openrouter.ai/qwen/qwen3-coder-next)
|
|
43
|
+
|
|
44
|
+
---
|
|
45
|
+
|
|
46
|
+
|
|
47
|
+
|
|
48
|
+
**Intract** is a lightweight intent-contract system for codebases.
|
|
49
|
+
|
|
50
|
+
Intract is not primarily a programming language. It is a **contract layer** for code intent.
|
|
51
|
+
A contract may be a single line, an inline comment, or a multi-file `intent.yaml` manifest.
|
|
52
|
+
|
|
53
|
+
## Inline contract
|
|
54
|
+
|
|
55
|
+
```python
|
|
56
|
+
# @intract.v1 scope:function intent:validate:user_permission priority:1 domain:security input:user,resource output:allowed effect:none forbid:write,network require:none validate:input_presence,return_value,no_forbidden_effect meaning:"check whether user can modify resource without changing state"
|
|
57
|
+
def can_update_resource(user, resource):
|
|
58
|
+
return user.is_admin or resource.owner_id == user.id
|
|
59
|
+
```
|
|
60
|
+
|
|
61
|
+
## Multi-file manifest
|
|
62
|
+
|
|
63
|
+
```yaml
|
|
64
|
+
project:
|
|
65
|
+
name: redup
|
|
66
|
+
|
|
67
|
+
contracts:
|
|
68
|
+
- id: project.analysis
|
|
69
|
+
scope: project
|
|
70
|
+
intent: analyze:code_duplication
|
|
71
|
+
priority: 1
|
|
72
|
+
domain: project
|
|
73
|
+
input: [source_tree]
|
|
74
|
+
output: [DuplicationMap, RefactorSuggestion]
|
|
75
|
+
effect: [read]
|
|
76
|
+
forbid: [network]
|
|
77
|
+
require:
|
|
78
|
+
- scan.project_files
|
|
79
|
+
- extract.code_blocks
|
|
80
|
+
- detect.duplicates
|
|
81
|
+
- group.duplicates
|
|
82
|
+
- render.report
|
|
83
|
+
validate:
|
|
84
|
+
- required_intents
|
|
85
|
+
- no_forbidden_effect
|
|
86
|
+
meaning: "Project should analyze source code duplication and produce refactoring guidance."
|
|
87
|
+
|
|
88
|
+
files:
|
|
89
|
+
src/redup/core/scanner/__init__.py:
|
|
90
|
+
- scope: file
|
|
91
|
+
intent: scan:project_files
|
|
92
|
+
priority: 1
|
|
93
|
+
domain: scanner
|
|
94
|
+
input: [ScanConfig]
|
|
95
|
+
output: [file_list]
|
|
96
|
+
effect: [read]
|
|
97
|
+
forbid: [network]
|
|
98
|
+
meaning: "Scanner file should collect project source files."
|
|
99
|
+
```
|
|
100
|
+
|
|
101
|
+
## CLI
|
|
102
|
+
|
|
103
|
+
```bash
|
|
104
|
+
pip install -e .[dev]
|
|
105
|
+
|
|
106
|
+
intract scan .
|
|
107
|
+
intract validate .
|
|
108
|
+
intract validate . --manifest intent.yaml --json
|
|
109
|
+
intract init .
|
|
110
|
+
```
|
|
111
|
+
|
|
112
|
+
## Validation statuses
|
|
113
|
+
|
|
114
|
+
| Status | Meaning |
|
|
115
|
+
|---|---|
|
|
116
|
+
| `pass` | Contract is satisfied. |
|
|
117
|
+
| `partial` | Contract is partly satisfied but missing evidence or sub-intents. |
|
|
118
|
+
| `fail` | Contract is not satisfied. |
|
|
119
|
+
| `violation` | Contract matches but violates a forbidden constraint. |
|
|
120
|
+
| `unknown` | Not enough information to decide. |
|
|
121
|
+
|
|
122
|
+
## Contract fields
|
|
123
|
+
|
|
124
|
+
| Field | Example | Meaning |
|
|
125
|
+
|---|---|---|
|
|
126
|
+
| `scope` | `function` | Level: `line`, `block`, `function`, `class`, `file`, `module`, `project`. |
|
|
127
|
+
| `intent` | `validate:user_permission` | Main action and object. |
|
|
128
|
+
| `priority` | `1` | Importance from 1 to 5. |
|
|
129
|
+
| `domain` | `security` | Architectural/business domain. |
|
|
130
|
+
| `input` | `user,resource` | Expected inputs. |
|
|
131
|
+
| `output` | `allowed` | Expected output. |
|
|
132
|
+
| `effect` | `read` | Allowed/declared side effects. |
|
|
133
|
+
| `forbid` | `write,network` | Forbidden effects. |
|
|
134
|
+
| `require` | `scan.project_files` | Required sub-intents. |
|
|
135
|
+
| `validate` | `input_presence,no_forbidden_effect` | Validation rules to apply. |
|
|
136
|
+
| `meaning` | `"..."` | Human-readable explanation. |
|
|
137
|
+
|
|
138
|
+
|
|
139
|
+
## License
|
|
140
|
+
|
|
141
|
+
Licensed under Apache-2.0.
|
intract-0.1.1/README.md
ADDED
|
@@ -0,0 +1,111 @@
|
|
|
1
|
+
# Intract
|
|
2
|
+
|
|
3
|
+
|
|
4
|
+
## AI Cost Tracking
|
|
5
|
+
|
|
6
|
+
   
|
|
7
|
+
  
|
|
8
|
+
|
|
9
|
+
- 🤖 **LLM usage:** $0.1500 (1 commits)
|
|
10
|
+
- 👤 **Human dev:** ~$100 (1.0h @ $100/h, 30min dedup)
|
|
11
|
+
|
|
12
|
+
Generated on 2026-05-29 using [openrouter/qwen/qwen3-coder-next](https://openrouter.ai/qwen/qwen3-coder-next)
|
|
13
|
+
|
|
14
|
+
---
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
|
|
18
|
+
**Intract** is a lightweight intent-contract system for codebases.
|
|
19
|
+
|
|
20
|
+
Intract is not primarily a programming language. It is a **contract layer** for code intent.
|
|
21
|
+
A contract may be a single line, an inline comment, or a multi-file `intent.yaml` manifest.
|
|
22
|
+
|
|
23
|
+
## Inline contract
|
|
24
|
+
|
|
25
|
+
```python
|
|
26
|
+
# @intract.v1 scope:function intent:validate:user_permission priority:1 domain:security input:user,resource output:allowed effect:none forbid:write,network require:none validate:input_presence,return_value,no_forbidden_effect meaning:"check whether user can modify resource without changing state"
|
|
27
|
+
def can_update_resource(user, resource):
|
|
28
|
+
return user.is_admin or resource.owner_id == user.id
|
|
29
|
+
```
|
|
30
|
+
|
|
31
|
+
## Multi-file manifest
|
|
32
|
+
|
|
33
|
+
```yaml
|
|
34
|
+
project:
|
|
35
|
+
name: redup
|
|
36
|
+
|
|
37
|
+
contracts:
|
|
38
|
+
- id: project.analysis
|
|
39
|
+
scope: project
|
|
40
|
+
intent: analyze:code_duplication
|
|
41
|
+
priority: 1
|
|
42
|
+
domain: project
|
|
43
|
+
input: [source_tree]
|
|
44
|
+
output: [DuplicationMap, RefactorSuggestion]
|
|
45
|
+
effect: [read]
|
|
46
|
+
forbid: [network]
|
|
47
|
+
require:
|
|
48
|
+
- scan.project_files
|
|
49
|
+
- extract.code_blocks
|
|
50
|
+
- detect.duplicates
|
|
51
|
+
- group.duplicates
|
|
52
|
+
- render.report
|
|
53
|
+
validate:
|
|
54
|
+
- required_intents
|
|
55
|
+
- no_forbidden_effect
|
|
56
|
+
meaning: "Project should analyze source code duplication and produce refactoring guidance."
|
|
57
|
+
|
|
58
|
+
files:
|
|
59
|
+
src/redup/core/scanner/__init__.py:
|
|
60
|
+
- scope: file
|
|
61
|
+
intent: scan:project_files
|
|
62
|
+
priority: 1
|
|
63
|
+
domain: scanner
|
|
64
|
+
input: [ScanConfig]
|
|
65
|
+
output: [file_list]
|
|
66
|
+
effect: [read]
|
|
67
|
+
forbid: [network]
|
|
68
|
+
meaning: "Scanner file should collect project source files."
|
|
69
|
+
```
|
|
70
|
+
|
|
71
|
+
## CLI
|
|
72
|
+
|
|
73
|
+
```bash
|
|
74
|
+
pip install -e .[dev]
|
|
75
|
+
|
|
76
|
+
intract scan .
|
|
77
|
+
intract validate .
|
|
78
|
+
intract validate . --manifest intent.yaml --json
|
|
79
|
+
intract init .
|
|
80
|
+
```
|
|
81
|
+
|
|
82
|
+
## Validation statuses
|
|
83
|
+
|
|
84
|
+
| Status | Meaning |
|
|
85
|
+
|---|---|
|
|
86
|
+
| `pass` | Contract is satisfied. |
|
|
87
|
+
| `partial` | Contract is partly satisfied but missing evidence or sub-intents. |
|
|
88
|
+
| `fail` | Contract is not satisfied. |
|
|
89
|
+
| `violation` | Contract matches but violates a forbidden constraint. |
|
|
90
|
+
| `unknown` | Not enough information to decide. |
|
|
91
|
+
|
|
92
|
+
## Contract fields
|
|
93
|
+
|
|
94
|
+
| Field | Example | Meaning |
|
|
95
|
+
|---|---|---|
|
|
96
|
+
| `scope` | `function` | Level: `line`, `block`, `function`, `class`, `file`, `module`, `project`. |
|
|
97
|
+
| `intent` | `validate:user_permission` | Main action and object. |
|
|
98
|
+
| `priority` | `1` | Importance from 1 to 5. |
|
|
99
|
+
| `domain` | `security` | Architectural/business domain. |
|
|
100
|
+
| `input` | `user,resource` | Expected inputs. |
|
|
101
|
+
| `output` | `allowed` | Expected output. |
|
|
102
|
+
| `effect` | `read` | Allowed/declared side effects. |
|
|
103
|
+
| `forbid` | `write,network` | Forbidden effects. |
|
|
104
|
+
| `require` | `scan.project_files` | Required sub-intents. |
|
|
105
|
+
| `validate` | `input_presence,no_forbidden_effect` | Validation rules to apply. |
|
|
106
|
+
| `meaning` | `"..."` | Human-readable explanation. |
|
|
107
|
+
|
|
108
|
+
|
|
109
|
+
## License
|
|
110
|
+
|
|
111
|
+
Licensed under Apache-2.0.
|
intract-0.1.1/VERSION
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
0.1.1
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
# Intract Contract Format
|
|
2
|
+
|
|
3
|
+
An Intract contract is a one-line, self-describing validation contract.
|
|
4
|
+
|
|
5
|
+
```text
|
|
6
|
+
@intract.v1 scope:<scope> intent:<action>:<object> priority:<1-5> domain:<domain> input:<inputs> output:<outputs> effect:<effects> forbid:<effects> require:<subintents> validate:<rules> meaning:"plain explanation"
|
|
7
|
+
```
|
|
8
|
+
|
|
9
|
+
Example:
|
|
10
|
+
|
|
11
|
+
```python
|
|
12
|
+
# @intract.v1 scope:function intent:validate:user_permission priority:1 domain:security input:user,resource output:allowed effect:none forbid:write,network require:none validate:input_presence,return_value,no_forbidden_effect meaning:"check if user may modify resource without changing state"
|
|
13
|
+
```
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
# Examples
|
|
2
|
+
|
|
3
|
+
## Python
|
|
4
|
+
|
|
5
|
+
```python
|
|
6
|
+
# @intract.v1 scope:function intent:parse:extensions priority:2 domain:cli input:raw_extensions output:extension_list effect:none forbid:network,write validate:input_presence,output_presence,return_value,no_forbidden_effect meaning:"parse raw extension string into normalized extension list"
|
|
7
|
+
def parse_extensions(raw_extensions: str) -> list[str]:
|
|
8
|
+
extension_list = [item.strip().lower() for item in raw_extensions.split(",") if item.strip()]
|
|
9
|
+
return extension_list
|
|
10
|
+
```
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
# `intent.yaml` / `intract.yaml`
|
|
2
|
+
|
|
3
|
+
A manifest allows tagging multiple files and expressing nested project contracts.
|
|
4
|
+
|
|
5
|
+
```yaml
|
|
6
|
+
contracts:
|
|
7
|
+
- id: project.analysis
|
|
8
|
+
scope: project
|
|
9
|
+
intent: analyze:code_duplication
|
|
10
|
+
require:
|
|
11
|
+
- scan.project_files
|
|
12
|
+
- extract.code_blocks
|
|
13
|
+
- detect.duplicates
|
|
14
|
+
```
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
# Validation Model
|
|
2
|
+
|
|
3
|
+
Supported validation rules:
|
|
4
|
+
|
|
5
|
+
| Rule | Meaning |
|
|
6
|
+
|---|---|
|
|
7
|
+
| `input_presence` | Required inputs appear in the source. |
|
|
8
|
+
| `output_presence` | Required outputs appear in the source. |
|
|
9
|
+
| `return_value` | The code appears to return/yield a value. |
|
|
10
|
+
| `no_forbidden_effect` | Forbidden effects such as `network` or `write` are not detected. |
|
|
11
|
+
| `effect_match` | Observed effects match declared effects. |
|
|
12
|
+
| `required_intents` | Required sub-intents are present in the project. |
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
project:
|
|
2
|
+
name: sample-intract-project
|
|
3
|
+
|
|
4
|
+
contracts:
|
|
5
|
+
- id: project.analysis
|
|
6
|
+
scope: project
|
|
7
|
+
intent: analyze:code_duplication
|
|
8
|
+
priority: 1
|
|
9
|
+
domain: project
|
|
10
|
+
input: [source_tree]
|
|
11
|
+
output: [DuplicationMap, RefactorSuggestion]
|
|
12
|
+
effect: [read]
|
|
13
|
+
forbid: [network]
|
|
14
|
+
require:
|
|
15
|
+
- scan.project_files
|
|
16
|
+
- extract.code_blocks
|
|
17
|
+
- detect.duplicates
|
|
18
|
+
- render.report
|
|
19
|
+
validate:
|
|
20
|
+
- required_intents
|
|
21
|
+
- no_forbidden_effect
|
|
22
|
+
meaning: "Project should analyze source code duplication and produce refactoring guidance."
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
// @intract.v1 scope:file intent:implement:scan_pipeline priority:1 domain:analysis input:sourceTree output:duplicationMap effect:read forbid:network require:scan.project_files,extract.code_blocks,detect.duplicates,render.report validate:required_intents,no_forbidden_effect meaning:"file should implement scan pipeline from files to duplication report"
|
|
2
|
+
|
|
3
|
+
// @intract.v1 scope:function intent:scan:project_files priority:1 domain:scanner input:sourceTree output:fileList effect:read forbid:network validate:input_presence,output_presence,return_value,no_forbidden_effect meaning:"collect source files from project tree"
|
|
4
|
+
public List<string> CollectFiles(string sourceTree) {
|
|
5
|
+
var fileList = Directory.GetFiles(sourceTree, "*.cs").ToList();
|
|
6
|
+
return fileList;
|
|
7
|
+
}
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
# @intract.v1 scope:function intent:parse:extensions priority:2 domain:cli input:raw_extensions output:extension_list effect:none forbid:network,write require:none validate:input_presence,output_presence,return_value,no_forbidden_effect meaning:"parse raw extension string into normalized extension list"
|
|
2
|
+
def parse_extensions(raw_extensions: str) -> list[str]:
|
|
3
|
+
extension_list = [
|
|
4
|
+
item.strip().lower()
|
|
5
|
+
for item in raw_extensions.split(",")
|
|
6
|
+
if item.strip()
|
|
7
|
+
]
|
|
8
|
+
return extension_list
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
// @intract.v1 scope:function intent:validate:user_permission priority:1 domain:security input:user,resource output:allowed effect:none forbid:network,write require:none validate:input_presence,output_presence,return_value,no_forbidden_effect meaning:"check if user can modify resource without network or writes"
|
|
2
|
+
function canUpdateResource(user: User, resource: Resource): boolean {
|
|
3
|
+
const allowed = user.isAdmin || resource.ownerId === user.id;
|
|
4
|
+
return allowed;
|
|
5
|
+
}
|