speclogician 0.0.0b1__py3-none-any.whl → 0.0.0.dev1__py3-none-any.whl

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.
Files changed (153) hide show
  1. speclogician/agent/funcs.py +29 -0
  2. speclogician/cmd/agent_cmd.py +89 -0
  3. speclogician/cmd/data_cmd.py +24 -0
  4. speclogician/cmd/model_cmd.py +42 -0
  5. speclogician/cmd/overlay_cmd.py +30 -0
  6. speclogician/cmd/scenario_cmd.py +61 -0
  7. speclogician/cmd/state_cmd.py +52 -0
  8. speclogician/data/artifact.py +8 -50
  9. speclogician/data/container.py +18 -384
  10. speclogician/data/mapping.py +18 -17
  11. speclogician/data/refs.py +12 -11
  12. speclogician/data/reports.py +11 -0
  13. speclogician/data/traces.py +15 -6
  14. speclogician/llms/llmtools.py +102 -0
  15. speclogician/llms/overlay.py +264 -0
  16. speclogician/main.py +36 -102
  17. speclogician/modeling/__init__.py +0 -31
  18. speclogician/modeling/component.py +4 -60
  19. speclogician/modeling/conflict.py +5 -19
  20. speclogician/modeling/domain.py +93 -280
  21. speclogician/modeling/model.py +206 -0
  22. speclogician/modeling/predicates.py +20 -22
  23. speclogician/modeling/report.py +33 -0
  24. speclogician/modeling/scenario.py +119 -87
  25. speclogician/sl_cmd.py +76 -0
  26. speclogician/state/change.py +98 -378
  27. speclogician/state/state.py +183 -399
  28. speclogician/tui/box.tcss +10 -0
  29. speclogician/tui/tui.py +131 -0
  30. speclogician/utils/__init__.py +1 -70
  31. speclogician/utils/imx.py +195 -0
  32. speclogician/utils/load.py +25 -147
  33. speclogician/utils/prompt.md +1 -325
  34. speclogician-0.0.0.dev1.dist-info/METADATA +21 -0
  35. speclogician-0.0.0.dev1.dist-info/RECORD +43 -0
  36. speclogician/commands/__init__.py +0 -15
  37. speclogician/commands/cmd_ch.py +0 -616
  38. speclogician/commands/cmd_find.py +0 -256
  39. speclogician/commands/cmd_view.py +0 -202
  40. speclogician/commands/runner.py +0 -149
  41. speclogician/commands/utils.py +0 -101
  42. speclogician/demos/.DS_Store +0 -0
  43. speclogician/demos/cmd_demo.py +0 -278
  44. speclogician/demos/loader.py +0 -135
  45. speclogician/demos/model.py +0 -27
  46. speclogician/demos/runner.py +0 -51
  47. speclogician/logic/__init__.py +0 -11
  48. speclogician/logic/api/__init__.py +0 -29
  49. speclogician/logic/api/client.py +0 -606
  50. speclogician/logic/api/decomp.py +0 -67
  51. speclogician/logic/api/scenario.py +0 -102
  52. speclogician/logic/api/traces.py +0 -59
  53. speclogician/logic/lib/__init__.py +0 -19
  54. speclogician/logic/lib/complement.py +0 -107
  55. speclogician/logic/lib/domain_model.py +0 -59
  56. speclogician/logic/lib/predicates.py +0 -151
  57. speclogician/logic/lib/scenarios.py +0 -369
  58. speclogician/logic/lib/traces.py +0 -114
  59. speclogician/logic/lib/transitions.py +0 -104
  60. speclogician/logic/main.py +0 -246
  61. speclogician/logic/strings.py +0 -194
  62. speclogician/logic/utils.py +0 -135
  63. speclogician/modeling/complement.py +0 -104
  64. speclogician/modeling/spec.py +0 -306
  65. speclogician/modeling/spec_stats.py +0 -39
  66. speclogician/presentation/api.py +0 -244
  67. speclogician/presentation/builders/_links.py +0 -44
  68. speclogician/presentation/builders/container.py +0 -53
  69. speclogician/presentation/builders/data_artifact.py +0 -42
  70. speclogician/presentation/builders/domain.py +0 -54
  71. speclogician/presentation/builders/instances_list.py +0 -38
  72. speclogician/presentation/builders/predicate.py +0 -51
  73. speclogician/presentation/builders/recommendations.py +0 -41
  74. speclogician/presentation/builders/scenario.py +0 -41
  75. speclogician/presentation/builders/scenario_complement.py +0 -82
  76. speclogician/presentation/builders/smart_find.py +0 -39
  77. speclogician/presentation/builders/spec.py +0 -39
  78. speclogician/presentation/builders/state_diff.py +0 -150
  79. speclogician/presentation/builders/state_instance.py +0 -42
  80. speclogician/presentation/builders/state_instance_summary.py +0 -84
  81. speclogician/presentation/builders/trace.py +0 -58
  82. speclogician/presentation/ctx.py +0 -38
  83. speclogician/presentation/models/container.py +0 -44
  84. speclogician/presentation/models/data_artifact.py +0 -33
  85. speclogician/presentation/models/domain.py +0 -50
  86. speclogician/presentation/models/instances_list.py +0 -23
  87. speclogician/presentation/models/predicate.py +0 -60
  88. speclogician/presentation/models/recommendations.py +0 -34
  89. speclogician/presentation/models/scenario.py +0 -31
  90. speclogician/presentation/models/scenario_complement.py +0 -40
  91. speclogician/presentation/models/smart_find.py +0 -34
  92. speclogician/presentation/models/spec.py +0 -32
  93. speclogician/presentation/models/state_diff.py +0 -34
  94. speclogician/presentation/models/state_instance.py +0 -31
  95. speclogician/presentation/models/state_instance_summary.py +0 -102
  96. speclogician/presentation/models/trace.py +0 -42
  97. speclogician/presentation/preview/__init__.py +0 -13
  98. speclogician/presentation/preview/cli.py +0 -50
  99. speclogician/presentation/preview/fixtures/__init__.py +0 -205
  100. speclogician/presentation/preview/fixtures/artifact_container.py +0 -150
  101. speclogician/presentation/preview/fixtures/data_artifact.py +0 -144
  102. speclogician/presentation/preview/fixtures/domain_model.py +0 -162
  103. speclogician/presentation/preview/fixtures/instances_list.py +0 -162
  104. speclogician/presentation/preview/fixtures/predicate.py +0 -184
  105. speclogician/presentation/preview/fixtures/scenario.py +0 -84
  106. speclogician/presentation/preview/fixtures/scenario_complement.py +0 -81
  107. speclogician/presentation/preview/fixtures/smart_find.py +0 -140
  108. speclogician/presentation/preview/fixtures/spec.py +0 -95
  109. speclogician/presentation/preview/fixtures/state_diff.py +0 -158
  110. speclogician/presentation/preview/fixtures/state_instance.py +0 -128
  111. speclogician/presentation/preview/fixtures/state_instance_summary.py +0 -80
  112. speclogician/presentation/preview/fixtures/trace.py +0 -206
  113. speclogician/presentation/preview/registry.py +0 -42
  114. speclogician/presentation/renderers/__init__.py +0 -24
  115. speclogician/presentation/renderers/container.py +0 -136
  116. speclogician/presentation/renderers/data_artifact.py +0 -144
  117. speclogician/presentation/renderers/domain.py +0 -123
  118. speclogician/presentation/renderers/instances_list.py +0 -120
  119. speclogician/presentation/renderers/predicate.py +0 -180
  120. speclogician/presentation/renderers/recommendations.py +0 -90
  121. speclogician/presentation/renderers/scenario.py +0 -94
  122. speclogician/presentation/renderers/scenario_complement.py +0 -59
  123. speclogician/presentation/renderers/smart_find.py +0 -307
  124. speclogician/presentation/renderers/spec.py +0 -105
  125. speclogician/presentation/renderers/state_diff.py +0 -102
  126. speclogician/presentation/renderers/state_instance.py +0 -82
  127. speclogician/presentation/renderers/state_instance_summary.py +0 -143
  128. speclogician/presentation/renderers/trace.py +0 -122
  129. speclogician/shell/app.py +0 -170
  130. speclogician/shell/shell_ch.py +0 -263
  131. speclogician/shell/shell_view.py +0 -153
  132. speclogician/state/change_result.py +0 -32
  133. speclogician/state/diff.py +0 -191
  134. speclogician/state/inst.py +0 -574
  135. speclogician/state/recommendation.py +0 -13
  136. speclogician/state/recommender.py +0 -577
  137. speclogician/state/state_stats.py +0 -133
  138. speclogician/tui/__init__.py +0 -0
  139. speclogician/tui/app.py +0 -257
  140. speclogician/tui/app.tcss +0 -160
  141. speclogician/tui/demo.py +0 -45
  142. speclogician/tui/images/speclogician-full.png +0 -0
  143. speclogician/tui/images/speclogician-minimal.png +0 -0
  144. speclogician/tui/main_screen.py +0 -454
  145. speclogician/tui/splash_screen.py +0 -51
  146. speclogician/tui/stats_screen.py +0 -125
  147. speclogician/utils/testing.py +0 -151
  148. speclogician-0.0.0b1.dist-info/METADATA +0 -116
  149. speclogician-0.0.0b1.dist-info/RECORD +0 -139
  150. /speclogician/{presentation → agent}/__init__.py +0 -0
  151. /speclogician/{presentation/builders → cmd}/__init__.py +0 -0
  152. /speclogician/{presentation/models → llms}/__init__.py +0 -0
  153. {speclogician-0.0.0b1.dist-info → speclogician-0.0.0.dev1.dist-info}/WHEEL +0 -0
@@ -1,102 +0,0 @@
1
- #
2
- # Imandra Inc.
3
- #
4
- # speclogician/presentation/models/state_instance_summary.py
5
- #
6
-
7
- from __future__ import annotations
8
-
9
- from pydantic import BaseModel
10
- from typing import Optional
11
-
12
-
13
- class StateInstanceSummaryPM(BaseModel):
14
- # -----------------
15
- # metadata
16
- # -----------------
17
- created_at: Optional[str] = None
18
-
19
- # -----------------
20
- # changes
21
- # -----------------
22
- num_changes: int = 0
23
-
24
- # -----------------
25
- # Domain model (base)
26
- # -----------------
27
- base_status: Optional[str] = None
28
- base_has_state: Optional[bool] = None
29
- base_has_action: Optional[bool] = None
30
-
31
- # -----------------
32
- # Domain model (state predicates)
33
- # -----------------
34
- num_state_preds_total: Optional[int] = None
35
- num_state_preds_matched: Optional[int] = None
36
- num_state_preds_valid_logic: Optional[int] = None
37
- num_state_preds_errored: Optional[int] = None
38
-
39
- # -----------------
40
- # Domain model (action predicates)
41
- # -----------------
42
- num_action_preds_total: Optional[int] = None
43
- num_action_preds_matched: Optional[int] = None
44
- num_action_preds_valid_logic: Optional[int] = None
45
- num_action_preds_errored: Optional[int] = None
46
-
47
- # -----------------
48
- # Domain model (predicate totals)
49
- # -----------------
50
- num_preds_total: Optional[int] = None
51
- num_preds_matched: Optional[int] = None
52
- num_preds_valid_logic: Optional[int] = None
53
- num_preds_errored: Optional[int] = None
54
-
55
- # -----------------
56
- # Domain model (transitions)
57
- # -----------------
58
- num_trans_total: Optional[int] = None
59
- num_trans_matched: Optional[int] = None
60
- num_trans_valid_logic: Optional[int] = None
61
- num_trans_errored: Optional[int] = None
62
-
63
- # -----------------
64
- # Scenarios
65
- # -----------------
66
- num_sc_total: Optional[int] = None
67
- num_sc_missing: Optional[int] = None
68
- num_sc_matched: Optional[int] = None
69
- num_sc_inconsistent: Optional[int] = None
70
-
71
- # -----------------
72
- # Conflicts (spec-level)
73
- # -----------------
74
- num_sc_conflicted: Optional[int] = None
75
- num_sc_overlap: Optional[int] = None
76
- num_sc_consumed: Optional[int] = None
77
-
78
- # -----------------
79
- # Test traces
80
- # -----------------
81
- num_test_traces_total: Optional[int] = None
82
- num_test_traces_matched: Optional[int] = None
83
- num_test_traces_logic_good: Optional[int] = None
84
-
85
- # -----------------
86
- # Log traces
87
- # -----------------
88
- num_log_traces_total: Optional[int] = None
89
- num_log_traces_matched: Optional[int] = None
90
- num_log_traces_logic_good: Optional[int] = None
91
-
92
- # -----------------
93
- # Source code artifacts
94
- # -----------------
95
- num_src_code_arts_total: Optional[int] = None
96
- num_src_code_arts_matched: Optional[int] = None
97
-
98
- # -----------------
99
- # Doc artifacts
100
- # -----------------
101
- num_doc_arts_total: Optional[int] = None
102
- num_doc_arts_matched: Optional[int] = None
@@ -1,42 +0,0 @@
1
- #
2
- # Imandra Inc.
3
- #
4
- # speclogician/presentation/models/trace.py
5
- #
6
-
7
- from __future__ import annotations
8
-
9
- from typing import Literal
10
- from pydantic import BaseModel
11
-
12
-
13
- class TraceIMLValidityPM(BaseModel):
14
- iml_valid: str # "unknown" | "valid" | "invalid"
15
- err: str | None = None
16
-
17
-
18
- class TraceCorePM(BaseModel):
19
- art_id: str
20
- given: str
21
- when: str | None = None
22
- then: str | None = None
23
- time: str = ""
24
- iml_validity: TraceIMLValidityPM
25
-
26
-
27
- class TestTracePM(BaseModel):
28
- kind: Literal["test_trace"] = "test_trace"
29
- core: TraceCorePM
30
-
31
- name: str
32
- filepath: str = ""
33
- language: str | None = None
34
- contents: str | None = None # optional / heavy
35
-
36
-
37
- class LogTracePM(BaseModel):
38
- kind: Literal["log_trace"] = "log_trace"
39
- core: TraceCorePM
40
-
41
- filename: str
42
- contents: str | None = None # optional / heavy
@@ -1,13 +0,0 @@
1
- #
2
- # Imandra Inc.
3
- #
4
- # speclogician/presentation/preview/__init__.py
5
- #
6
-
7
- from __future__ import annotations
8
-
9
- from .cli import app as preview_app
10
-
11
- __all__ = [
12
- "preview_app"
13
- ]
@@ -1,50 +0,0 @@
1
- #
2
- # Imandra Inc.
3
- #
4
- # speclogician/presentation/preview/cli.py
5
- #
6
-
7
- from __future__ import annotations
8
-
9
- import json
10
- import typer
11
-
12
- from speclogician.presentation.ctx import RenderCtx
13
- from speclogician.presentation.preview.registry import get, list_previews
14
- from speclogician.presentation.preview.fixtures import register_fixtures
15
- from speclogician.utils import console # your rich console
16
-
17
-
18
- app = typer.Typer(help="Preview PM renderers using synthetic fixtures.")
19
-
20
-
21
- @app.command("list")
22
- def list_cmd() -> None:
23
- register_fixtures()
24
- for spec in sorted(list_previews(), key=lambda s: s.name):
25
- console.print(f"[bold]{spec.name}[/bold] variants={', '.join(spec.variants)}")
26
-
27
-
28
- @app.command("show")
29
- def show_cmd(
30
- name: str = typer.Argument(..., help="Preview name (see: preview list)"),
31
- variant: str = typer.Argument("typical", help="Variant: typical|minimal|edge"),
32
- json_only: bool = typer.Option(False, "--json", help="Dump PM as JSON instead of rendering."),
33
- compact: bool = typer.Option(False, "--compact", help="Use compact rendering."),
34
- ) -> None:
35
- register_fixtures()
36
-
37
- ctx = RenderCtx(compact=compact)
38
- spec = get(name)
39
-
40
- if variant not in spec.variants:
41
- raise typer.BadParameter(f"Unknown variant '{variant}'. Choose one of: {', '.join(spec.variants)}")
42
-
43
- pm = spec.make(ctx, variant)
44
-
45
- if json_only:
46
- # Pydantic v2
47
- typer.echo(json.dumps(pm.model_dump(), indent=2, default=str))
48
- raise typer.Exit(0)
49
-
50
- console.print(spec.render(pm, ctx))
@@ -1,205 +0,0 @@
1
- #
2
- # Imandra Inc.
3
- #
4
- # speclogician/presentation/preview/fixtures/__init__.py
5
- #
6
-
7
- from __future__ import annotations
8
-
9
- from speclogician.presentation.preview.registry import PreviewSpec, register
10
-
11
- from . import state_diff
12
- from . import state_instance_summary
13
- from . import trace
14
- from . import data_artifact
15
- from . import artifact_container
16
- from . import predicate
17
- from . import scenario
18
- from . import domain_model
19
- from . import instances_list
20
- from . import spec
21
- from . import smart_find
22
- from . import state_instance
23
-
24
-
25
- def register_fixtures() -> None:
26
-
27
- # ------------------------------------------------------------------
28
- # State-level fixtures (already present)
29
- # ------------------------------------------------------------------
30
-
31
- register(
32
- PreviewSpec(
33
- name="state-diff",
34
- variants=("typical", "minimal", "edge"),
35
- make=state_diff.make_state_diff_pm,
36
- render=state_diff.render,
37
- )
38
- )
39
-
40
- register(
41
- PreviewSpec(
42
- name="state-instance-summary",
43
- variants=("typical", "minimal", "edge"),
44
- make=state_instance_summary.make_state_instance_summary_pm,
45
- render=state_instance_summary.render,
46
- )
47
- )
48
-
49
- # ------------------------------------------------------------------
50
- # Trace fixtures
51
- # ------------------------------------------------------------------
52
-
53
- register(
54
- PreviewSpec(
55
- name="test-trace",
56
- variants=("typical", "minimal", "edge"),
57
- make=trace.make_test_trace_pm,
58
- render=trace.render_test,
59
- )
60
- )
61
-
62
- register(
63
- PreviewSpec(
64
- name="log-trace",
65
- variants=("typical", "minimal", "edge"),
66
- make=trace.make_log_trace_pm,
67
- render=trace.render_log,
68
- )
69
- )
70
-
71
- # ------------------------------------------------------------------
72
- # Data artifact fixtures
73
- # ------------------------------------------------------------------
74
-
75
-
76
- register(
77
- PreviewSpec(
78
- name="doc-ref",
79
- variants=("typical", "minimal", "edge"),
80
- make=data_artifact.make_doc_ref_pm,
81
- render=data_artifact.render_doc,
82
- )
83
- )
84
-
85
- register(
86
- PreviewSpec(
87
- name="src-code-ref",
88
- variants=("typical", "minimal", "edge"),
89
- make=data_artifact.make_src_code_ref_pm,
90
- render=data_artifact.render_src,
91
- )
92
- )
93
-
94
- # ------------------------------------------------------------------
95
- # Artifact container fixtures
96
- # ------------------------------------------------------------------
97
-
98
- register(
99
- PreviewSpec(
100
- name="artifact-container",
101
- variants=("typical", "minimal", "edge"),
102
- make=artifact_container.make_artifact_container_pm,
103
- render=artifact_container.render,
104
- )
105
- )
106
-
107
- # ------------------------------------------------------------------
108
- # Predicate/Transition fixtures
109
- # ------------------------------------------------------------------
110
-
111
- register(
112
- PreviewSpec(
113
- name="predicate",
114
- variants=("typical", "minimal", "edge"),
115
- make=predicate.make_predicate_pm,
116
- render=predicate.render_predicate,
117
- )
118
- )
119
-
120
- register(
121
- PreviewSpec(
122
- name="transition",
123
- variants=("typical", "minimal", "edge"),
124
- make=predicate.make_transition_pm,
125
- render=predicate.render_transition,
126
- )
127
- )
128
-
129
- # ------------------------------------------------------------------
130
- # Scenario fixture
131
- # ------------------------------------------------------------------
132
-
133
- register(
134
- PreviewSpec(
135
- name="scenario",
136
- variants=("typical", "minimal", "edge"),
137
- make=scenario.make_scenario_pm,
138
- render=scenario.render,
139
- )
140
- )
141
-
142
- # ------------------------------------------------------------------
143
- # DomainModel fixture
144
- # ------------------------------------------------------------------
145
-
146
- register(
147
- PreviewSpec(
148
- name="domain-model",
149
- variants=("typical", "minimal", "edge"),
150
- make=domain_model.make_domain_model_pm,
151
- render=domain_model.render,
152
- )
153
- )
154
-
155
- # ------------------------------------------------------------------
156
- # InstancesList fixture
157
- # ------------------------------------------------------------------
158
-
159
- register(
160
- PreviewSpec(
161
- name="instances-list",
162
- variants=("typical", "minimal", "edge"),
163
- make=instances_list.make_instances_list_pm,
164
- render=instances_list.render,
165
- )
166
- )
167
-
168
- # ------------------------------------------------------------------
169
- # Spec fixture
170
- # ------------------------------------------------------------------
171
-
172
- register(
173
- PreviewSpec(
174
- name="spec",
175
- variants=("typical", "minimal", "edge"),
176
- make=spec.make_spec_pm,
177
- render=spec.render,
178
- )
179
- )
180
-
181
- # ------------------------------------------------------------------
182
- # SmartFind
183
- # ------------------------------------------------------------------
184
- register(
185
- PreviewSpec(
186
- name="smart-find",
187
- variants=("typical", "minimal", "edge"),
188
- make=smart_find.make_smart_find_pm,
189
- render=smart_find.render,
190
- )
191
- )
192
-
193
-
194
- # ------------------------------------------------------------------
195
- # SmartFind
196
- # ------------------------------------------------------------------
197
-
198
- register(
199
- PreviewSpec(
200
- name="state-instance",
201
- variants=("typical", "minimal", "edge"),
202
- make=state_instance.make_state_instance_pm,
203
- render=state_instance.render,
204
- )
205
- )
@@ -1,150 +0,0 @@
1
- #
2
- # Imandra Inc.
3
- #
4
- # speclogician/presentation/preview/fixtures/artifact_container.py
5
- #
6
-
7
- from __future__ import annotations
8
- from speclogician.presentation.ctx import RenderCtx
9
-
10
- from speclogician.presentation.models.container import (
11
- ArtifactContainerPM,
12
- ArtifactContainerCountsPM,
13
- ArtifactContainerItemsPM,
14
- )
15
-
16
- # reuse existing fixtures
17
- from speclogician.presentation.preview.fixtures.trace import (
18
- minimal_test_trace_pm,
19
- typical_test_trace_pm,
20
- edge_test_trace_pm,
21
- minimal_log_trace_pm,
22
- typical_log_trace_pm,
23
- edge_log_trace_pm,
24
- )
25
-
26
- from speclogician.presentation.preview.fixtures.data_artifact import (
27
- minimal_doc_ref_pm,
28
- typical_doc_ref_pm,
29
- edge_doc_ref_pm,
30
- minimal_src_code_ref_pm,
31
- typical_src_code_ref_pm,
32
- edge_src_code_ref_pm,
33
- )
34
-
35
-
36
- # -----------------------------------------------------------------------------
37
- # helpers
38
- # -----------------------------------------------------------------------------
39
-
40
- def _counts_from_items(items: ArtifactContainerItemsPM) -> ArtifactContainerCountsPM:
41
- # totals
42
- num_test_total = len(items.test_traces)
43
- num_log_total = len(items.log_traces)
44
- num_doc_total = len(items.doc_refs)
45
- num_src_total = len(items.src_code_refs)
46
-
47
- # matched / logic_good are not explicitly present on PMs yet,
48
- # so we keep these deterministic for fixtures. You can refine
49
- # this later once you encode matched flags in PMs.
50
- def _half(n: int) -> int:
51
- return 0 if n == 0 else max(1, n // 2)
52
-
53
- return ArtifactContainerCountsPM(
54
- num_test_traces_total=num_test_total,
55
- num_test_traces_matched=_half(num_test_total),
56
- num_test_traces_logic_good=_half(num_test_total),
57
-
58
- num_log_traces_total=num_log_total,
59
- num_log_traces_matched=_half(num_log_total),
60
- num_log_traces_logic_good=_half(num_log_total),
61
-
62
- num_src_code_arts_total=num_src_total,
63
- num_src_code_arts_matched=_half(num_src_total),
64
-
65
- num_doc_arts_total=num_doc_total,
66
- num_doc_arts_matched=_half(num_doc_total),
67
- )
68
-
69
-
70
- # -----------------------------------------------------------------------------
71
- # main fixture entrypoint (matches PreviewSpec.make signature)
72
- # -----------------------------------------------------------------------------
73
-
74
- def make_artifact_container_pm(ctx: RenderCtx, variant: str = "typical") -> ArtifactContainerPM:
75
- v = (variant or "typical").lower().strip()
76
-
77
- # -------------------------
78
- # minimal
79
- # -------------------------
80
- if v == "minimal":
81
- items = ArtifactContainerItemsPM(
82
- test_traces=[],
83
- log_traces=[],
84
- doc_refs=[],
85
- src_code_refs=[],
86
- )
87
- return ArtifactContainerPM(
88
- counts=_counts_from_items(items),
89
- items=items,
90
- )
91
-
92
- # -------------------------
93
- # edge (stress: long content, many items)
94
- # -------------------------
95
- if v == "edge":
96
- items = ArtifactContainerItemsPM(
97
- test_traces=[
98
- edge_test_trace_pm(),
99
- typical_test_trace_pm(with_contents=True, invalid=True),
100
- typical_test_trace_pm(with_contents=False, invalid=False),
101
- ],
102
- log_traces=[
103
- edge_log_trace_pm(),
104
- typical_log_trace_pm(with_contents=True, invalid=True),
105
- ],
106
- doc_refs=[
107
- edge_doc_ref_pm(),
108
- typical_doc_ref_pm(),
109
- ],
110
- src_code_refs=[
111
- edge_src_code_ref_pm(),
112
- typical_src_code_ref_pm(),
113
- ],
114
- )
115
- return ArtifactContainerPM(
116
- counts=_counts_from_items(items),
117
- items=items,
118
- )
119
-
120
- # -------------------------
121
- # typical
122
- # -------------------------
123
- items = ArtifactContainerItemsPM(
124
- test_traces=[
125
- typical_test_trace_pm(with_contents=False, invalid=False),
126
- typical_test_trace_pm(with_contents=True, invalid=True),
127
- ],
128
- log_traces=[
129
- typical_log_trace_pm(with_contents=False, invalid=False),
130
- ],
131
- doc_refs=[
132
- typical_doc_ref_pm(),
133
- ],
134
- src_code_refs=[
135
- typical_src_code_ref_pm(),
136
- ],
137
- )
138
- return ArtifactContainerPM(
139
- counts=_counts_from_items(items),
140
- items=items,
141
- )
142
-
143
-
144
- # -----------------------------------------------------------------------------
145
- # renderer adapter (matches other fixtures style)
146
- # -----------------------------------------------------------------------------
147
-
148
- def render(pm: ArtifactContainerPM, ctx : RenderCtx):
149
- from speclogician.presentation.renderers.container import render_artifact_container
150
- return render_artifact_container(pm, ctx=ctx)
@@ -1,144 +0,0 @@
1
- #
2
- # Imandra Inc.
3
- #
4
- # speclogician/presentation/preview/fixtures/data_artifact.py
5
- #
6
-
7
- from __future__ import annotations
8
-
9
- from speclogician.presentation.ctx import RenderCtx
10
- from speclogician.presentation.models.data_artifact import DataArtifactCorePM, DocRefPM, SrcCodeRefPM
11
- from speclogician.presentation.renderers.data_artifact import (
12
- render_doc_ref,
13
- render_src_code_ref,
14
- )
15
-
16
- # -----------------------------------------------------------------------------
17
- # Shared helpers
18
- # -----------------------------------------------------------------------------
19
-
20
- def _core(*, art_id: str) -> DataArtifactCorePM:
21
- return DataArtifactCorePM(art_id=art_id)
22
-
23
-
24
- # -----------------------------------------------------------------------------
25
- # DocRefPM fixtures
26
- # -----------------------------------------------------------------------------
27
-
28
- def minimal_doc_ref_pm() -> DocRefPM:
29
- return DocRefPM(
30
- core=_core(art_id="00000000-0000-0000-0000-000000000000"),
31
- text="",
32
- meta=None,
33
- )
34
-
35
-
36
- def typical_doc_ref_pm() -> DocRefPM:
37
- return DocRefPM(
38
- core=_core(art_id="11111111-1111-1111-1111-111111111111"),
39
- text="Order must be rejected if quantity exceeds max order size.",
40
- meta="spec:order_limits; source=confluence; section=Risk Checks",
41
- )
42
-
43
-
44
- def edge_doc_ref_pm() -> DocRefPM:
45
- return DocRefPM(
46
- core=_core(art_id="99999999-9999-9999-9999-999999999999"),
47
- text=(
48
- "A very long doc note that should wrap nicely and still be readable. "
49
- "It may contain bullet-like text, punctuation, and ‘quoted’ phrases.\n\n"
50
- "- Must preserve meaning\n"
51
- "- Must keep formatting\n"
52
- "- Should not overflow tables\n"
53
- ),
54
- meta=(
55
- "url=https://example.com/really/long/path/to/a/doc\n"
56
- "tags=risk,limits,edge-case\n"
57
- "owner=QA\n"
58
- ),
59
- )
60
-
61
-
62
- def make_doc_ref_pm(ctx: RenderCtx, variant: str) -> DocRefPM:
63
- match variant:
64
- case "minimal":
65
- return minimal_doc_ref_pm()
66
- case "edge":
67
- return edge_doc_ref_pm()
68
- case _:
69
- return typical_doc_ref_pm()
70
-
71
-
72
- # -----------------------------------------------------------------------------
73
- # SrcCodeRefPM fixtures
74
- # -----------------------------------------------------------------------------
75
-
76
- def minimal_src_code_ref_pm() -> SrcCodeRefPM:
77
- return SrcCodeRefPM(
78
- core=_core(art_id="00000000-0000-0000-0000-000000000000"),
79
- src_code="",
80
- language=None,
81
- file_path=None,
82
- iml_code=None,
83
- meta=None,
84
- )
85
-
86
-
87
- def typical_src_code_ref_pm(*, with_iml: bool = True) -> SrcCodeRefPM:
88
- return SrcCodeRefPM(
89
- core=_core(art_id="22222222-2222-2222-2222-222222222222"),
90
- src_code=(
91
- "def check_qty(order):\n"
92
- " return order.qty <= 10000\n"
93
- ),
94
- language="python",
95
- file_path="risk/checks/order_limits.py",
96
- iml_code=(
97
- "let check_qty (o: order) : bool = o.qty <= 10000"
98
- if with_iml
99
- else None
100
- ),
101
- meta="repo=speclogician; commit=abc123; kind=snippet",
102
- )
103
-
104
-
105
- def edge_src_code_ref_pm() -> SrcCodeRefPM:
106
- return SrcCodeRefPM(
107
- core=_core(art_id="aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa"),
108
- src_code=(
109
- "class RiskEngine:\n"
110
- " def check(self, order, market_data, limits):\n"
111
- " # extremely long snippet to stress wrapping\n"
112
- + (" # line\n" * 60)
113
- + " return True\n"
114
- ),
115
- language="python",
116
- file_path=("very/long/path/" * 6) + "risk_engine.py",
117
- iml_code=(
118
- "type order = { qty : int }\n"
119
- "let check (o: order) : bool = o.qty > 0\n"
120
- + ("(* comment *)\n" * 40)
121
- ),
122
- meta=(
123
- "repo=monorepo\n"
124
- "component=risk_engine\n"
125
- "note=this meta is multi-line to stress rendering\n"
126
- ),
127
- )
128
-
129
-
130
- def make_src_code_ref_pm(ctx: RenderCtx, variant: str) -> SrcCodeRefPM:
131
- match variant:
132
- case "minimal":
133
- return minimal_src_code_ref_pm()
134
- case "edge":
135
- return edge_src_code_ref_pm()
136
- case _:
137
- return typical_src_code_ref_pm()
138
-
139
- def render_doc(pm: DocRefPM, ctx: RenderCtx):
140
- return render_doc_ref(pm, ctx=ctx)
141
-
142
-
143
- def render_src(pm: SrcCodeRefPM, ctx: RenderCtx):
144
- return render_src_code_ref(pm, ctx=ctx)