evorthon-data 1.0.0__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.
- evorthon_data/__init__.py +5 -0
- evorthon_data/boundary_patterns.py +353 -0
- evorthon_data/cli.py +551 -0
- evorthon_data/composition.py +3103 -0
- evorthon_data/delivery/__init__.py +100 -0
- evorthon_data/delivery/autobuild.py +365 -0
- evorthon_data/delivery/declaration_draft.py +933 -0
- evorthon_data/delivery/ergasterion.py +886 -0
- evorthon_data/delivery/pinax.py +1168 -0
- evorthon_data/dependencies.py +16 -0
- evorthon_data/engagement/__init__.py +128 -0
- evorthon_data/engagement/aggregate.py +882 -0
- evorthon_data/engagement/stages.py +11 -0
- evorthon_data/engagement/use_case.py +1696 -0
- evorthon_data/engagement/versions.py +313 -0
- evorthon_data/koine_projection.py +183 -0
- evorthon_data/koine_session.py +2688 -0
- evorthon_data/lifecycle.py +749 -0
- evorthon_data/presentation/__init__.py +34 -0
- evorthon_data/presentation/use_case.py +138 -0
- evorthon_data/public_boundary.py +681 -0
- evorthon_data/pytest_reporter.py +68 -0
- evorthon_data/readiness/__init__.py +58 -0
- evorthon_data/readiness/projection.py +793 -0
- evorthon_data/runtime_adapters.py +40 -0
- evorthon_data/security/__init__.py +31 -0
- evorthon_data/security/model_egress.py +328 -0
- evorthon_data/stages.py +11 -0
- evorthon_data/synthetic/__init__.py +58 -0
- evorthon_data/synthetic/generator.py +924 -0
- evorthon_data/synthetic/request.py +179 -0
- evorthon_data/verification/__init__.py +8 -0
- evorthon_data/verification/adapters/__init__.py +87 -0
- evorthon_data/verification/adapters/conformance.py +784 -0
- evorthon_data/verification/adapters/declaration.py +126 -0
- evorthon_data/verification/adapters/fixtures.py +374 -0
- evorthon_data/verification/adapters/material.py +95 -0
- evorthon_data/verification/adapters/memory.py +123 -0
- evorthon_data/verification/core/__init__.py +56 -0
- evorthon_data/verification/core/canonical.py +716 -0
- evorthon_data/verification/core/fault.py +726 -0
- evorthon_data/verification/core/localisation.py +605 -0
- evorthon_data/verification/core/reconciliation.py +1617 -0
- evorthon_data/verification/domain/__init__.py +150 -0
- evorthon_data/verification/domain/contracts.py +919 -0
- evorthon_data/verification/enforcement/__init__.py +85 -0
- evorthon_data/verification/enforcement/privacy.py +448 -0
- evorthon_data/verification/enforcement/schema.py +188 -0
- evorthon_data/verification/enforcement/serialization.py +206 -0
- evorthon_data/verification/enforcement/validation.py +1566 -0
- evorthon_data/verification/ports/__init__.py +38 -0
- evorthon_data/verification/ports/contracts.py +187 -0
- evorthon_data/verification/presentation/__init__.py +144 -0
- evorthon_data/verification/presentation/remediation.py +354 -0
- evorthon_data/verification/presentation/report.py +492 -0
- evorthon_data/verification/workflows/__init__.py +214 -0
- evorthon_data/verification/workflows/adviser.py +560 -0
- evorthon_data/verification/workflows/delivery_contract.py +1005 -0
- evorthon_data/verification/workflows/diagnosis.py +134 -0
- evorthon_data/verification/workflows/intake.py +567 -0
- evorthon_data/verification/workflows/reconciliation.py +221 -0
- evorthon_data/verification/workflows/remediation.py +717 -0
- evorthon_data/verification/workflows/replay.py +321 -0
- evorthon_data-1.0.0.dist-info/METADATA +186 -0
- evorthon_data-1.0.0.dist-info/RECORD +68 -0
- evorthon_data-1.0.0.dist-info/WHEEL +4 -0
- evorthon_data-1.0.0.dist-info/entry_points.txt +2 -0
- evorthon_data-1.0.0.dist-info/licenses/LICENSE +15 -0
|
@@ -0,0 +1,353 @@
|
|
|
1
|
+
"""The closed shapes every boundary of this product reads the same way.
|
|
2
|
+
|
|
3
|
+
Four places in this product decide whether a text carries a route to somebody's
|
|
4
|
+
machine, a credential, or a row of written data: the use-case aggregate reading
|
|
5
|
+
a fact locator, the privacy gate reading a fault packet, the public-candidate
|
|
6
|
+
scan reading a shipped file, and the tracker adapter reading a note. A fifth,
|
|
7
|
+
the intake credential scan, reads an artefact. When each of them wrote its own
|
|
8
|
+
rule they disagreed, and the weakest of them decided what a record kept and
|
|
9
|
+
what crossed to a model.
|
|
10
|
+
|
|
11
|
+
This module is the one owner of those shapes. It declares them as named
|
|
12
|
+
compiled patterns and it reads them. It refuses nothing and it decides nothing:
|
|
13
|
+
each boundary keeps its own refusal, its own reason and its own message,
|
|
14
|
+
because what a refusal means is the boundary's to say.
|
|
15
|
+
|
|
16
|
+
A boundary names the shapes it reads. It reads every shape it can, and where it
|
|
17
|
+
cannot read one it says so in its own docstring with the reason. The subject
|
|
18
|
+
differs: three of the boundaries read one declared value that this product
|
|
19
|
+
wrote, while the public-candidate scan reads whole files of source, fixtures
|
|
20
|
+
and documentation, where a backslash writes a character escape and a slash
|
|
21
|
+
after a space is ordinary prose. A shape that is unambiguous in a declared
|
|
22
|
+
value is not always unambiguous in a page of shipped text, and pretending
|
|
23
|
+
otherwise would either blind a boundary or flood it.
|
|
24
|
+
|
|
25
|
+
The shapes are assembled from character codes, so this file carries no drive
|
|
26
|
+
letter, no address scheme and no machine path of its own, and the scan that
|
|
27
|
+
reads it finds nothing to report.
|
|
28
|
+
|
|
29
|
+
Some shapes therefore come in two readings, a prose one and a declared-value
|
|
30
|
+
one, and both are declared here. The prose reading of a traversal wants the
|
|
31
|
+
value or the line to begin with it, and the prose reading of an absolute path
|
|
32
|
+
wants a first segment that continues into another one or ends in a suffix,
|
|
33
|
+
because shipped documentation links with a traversal segment inside a longer
|
|
34
|
+
relative link and writes a bare slash between two names for a rate or a pair of
|
|
35
|
+
sides. The declared-value reading of each wants neither: a locator this product
|
|
36
|
+
wrote is one value, so a traversal anywhere in it, a single-segment path from
|
|
37
|
+
the root, a lettered volume with no separator after it and a share host with
|
|
38
|
+
nothing after it are all routes. A bare word and a bare whole number cannot be
|
|
39
|
+
told apart from a name and a count by reading them, so nothing here claims to.
|
|
40
|
+
A credential shape names a written secret, not a high-entropy token with no name
|
|
41
|
+
beside it.
|
|
42
|
+
|
|
43
|
+
Two forms these shapes do not read at all, at any boundary, so that what is
|
|
44
|
+
missed is missed in one place and can be closed in one place.
|
|
45
|
+
|
|
46
|
+
* A home path written with the character that stands for one. The shapes read
|
|
47
|
+
the written words for a home directory, not that character.
|
|
48
|
+
* A traversal or a separator written in percent-encoded form. Nothing here
|
|
49
|
+
decodes an encoding before reading, so an encoded route reads as text.
|
|
50
|
+
|
|
51
|
+
A fourth family is advisory. It is read for a warning and never for a refusal,
|
|
52
|
+
and no boundary keeps a refusal reason for it. It holds two forms. A bare host
|
|
53
|
+
is a dotted name with a path or a port after it and no scheme in front of it;
|
|
54
|
+
the dotted name alone is not read, because it cannot be told from an ordinary
|
|
55
|
+
written name at all, and refusing it would refuse names a team has every reason
|
|
56
|
+
to write. A connection string is a connection key written against a value. A
|
|
57
|
+
boundary that reads this family labels what it found and admits it, and says in
|
|
58
|
+
its own docstring what it does with the label.
|
|
59
|
+
|
|
60
|
+
Two machine-route shapes read less than their names suggest, and each stops
|
|
61
|
+
short for a stated reason. A lettered volume with no separator after it does
|
|
62
|
+
not read a single letter or digit after the mark, because a spreadsheet column
|
|
63
|
+
range and a short written value are both written that way and name ordinary
|
|
64
|
+
positions inside an artefact; a volume followed by one character and nothing
|
|
65
|
+
else is admitted with them. The declared reading of a path from the root does
|
|
66
|
+
not read a separator that follows a space and a number, because that is how a
|
|
67
|
+
rate is written in a sentence; a path from the root written straight after a
|
|
68
|
+
number is admitted with it. Each narrowing leaves the route it was written for
|
|
69
|
+
still read, and what each gives up is named here and nowhere else.
|
|
70
|
+
|
|
71
|
+
Six further forms are read at the three boundaries that read one declared value
|
|
72
|
+
and stay unread at the one boundary that reads whole shipped files, because in
|
|
73
|
+
a page of prose they would report the product's own documentation rather than a
|
|
74
|
+
leak. They are the prose and the declared-value readings of an absolute path,
|
|
75
|
+
the declared-value reading of a traversal, a lettered volume with no separator
|
|
76
|
+
after it, a share host with nothing after it, and, in program source and the
|
|
77
|
+
JSON family only, a relative path written with a machine path's separator,
|
|
78
|
+
where those bytes write a character escape instead. The scan states each
|
|
79
|
+
allowance with its reason in its own module.
|
|
80
|
+
|
|
81
|
+
Three address forms are allowed at that same scan and at no other boundary,
|
|
82
|
+
because no declared value and no tracker note has any reason to carry an
|
|
83
|
+
address at all. They are declared below: the secure web scheme, which is how
|
|
84
|
+
this product's documentation links to published material; the insecure web
|
|
85
|
+
scheme where the drawing namespace follows it, which every generated diagram
|
|
86
|
+
declares; and this product's own logical reference scheme, which names a record
|
|
87
|
+
inside this product and no host. The file scheme and the insecure web scheme
|
|
88
|
+
are named below too, because the scan reports each of them under a finding of
|
|
89
|
+
its own rather than as a generic address.
|
|
90
|
+
"""
|
|
91
|
+
from __future__ import annotations
|
|
92
|
+
|
|
93
|
+
# evorthon-component: boundary_patterns
|
|
94
|
+
|
|
95
|
+
import re
|
|
96
|
+
from collections.abc import Mapping, Sequence
|
|
97
|
+
from types import MappingProxyType
|
|
98
|
+
|
|
99
|
+
# The characters a machine route is written from, by code point, so no route
|
|
100
|
+
# is spelled out in this file.
|
|
101
|
+
_ESCAPE = chr(92)
|
|
102
|
+
_MARK = chr(58)
|
|
103
|
+
_STOP = chr(46)
|
|
104
|
+
# One separator of a machine path, and one segment of a relative one.
|
|
105
|
+
_SEPARATOR = "[" + _ESCAPE * 2 + "/]"
|
|
106
|
+
_SEGMENT = "[A-Za-z0-9_" + _STOP + "-]"
|
|
107
|
+
# The two steps upward a traversal is written with, escaped for a pattern.
|
|
108
|
+
_UPWARD = _ESCAPE + _STOP + _ESCAPE + _STOP
|
|
109
|
+
# One part of a written address, up to the next mark, separator or host sign.
|
|
110
|
+
_ADDRESS_PART = r"[^/\s" + _MARK + "@]+"
|
|
111
|
+
|
|
112
|
+
DRIVE_PATH = "drive path"
|
|
113
|
+
DRIVE_RELATIVE_PATH = "drive-relative path"
|
|
114
|
+
NETWORK_SHARE_PATH = "network share path"
|
|
115
|
+
NETWORK_SHARE_HOST = "network share host"
|
|
116
|
+
USER_HOME_PATH = "user home path"
|
|
117
|
+
ABSOLUTE_PATH = "absolute path"
|
|
118
|
+
DECLARED_ABSOLUTE_PATH = "declared absolute path"
|
|
119
|
+
LOCAL_FILE_ADDRESS = "local file address"
|
|
120
|
+
WEB_ADDRESS = "web address"
|
|
121
|
+
SCHEME_ADDRESS = "scheme address"
|
|
122
|
+
TRAVERSAL = "traversal"
|
|
123
|
+
DECLARED_TRAVERSAL = "declared traversal"
|
|
124
|
+
BACKSLASH_RELATIVE_PATH = "backslash-relative path"
|
|
125
|
+
|
|
126
|
+
MACHINE_ROUTE_PATTERNS: Mapping[str, re.Pattern[str]] = MappingProxyType(
|
|
127
|
+
{
|
|
128
|
+
# A lettered volume on a machine.
|
|
129
|
+
DRIVE_PATH: re.compile(r"\b[a-z]" + _MARK + _SEPARATOR, re.I),
|
|
130
|
+
# The same volume with no separator after it, which names wherever the
|
|
131
|
+
# machine stands on that volume. A single letter or digit that ends
|
|
132
|
+
# there is not read: that is a column range or a short written value,
|
|
133
|
+
# not a volume.
|
|
134
|
+
DRIVE_RELATIVE_PATH: re.compile(
|
|
135
|
+
r"\b[a-z]" + _MARK + r"(?![a-z0-9]\b)[^" + _ESCAPE * 2 + r"/\s]", re.I
|
|
136
|
+
),
|
|
137
|
+
# A share on another machine, named by two separators and a host.
|
|
138
|
+
NETWORK_SHARE_PATH: re.compile(
|
|
139
|
+
_ESCAPE * 4 + "[^" + _ESCAPE * 2 + "/]+" + _SEPARATOR
|
|
140
|
+
),
|
|
141
|
+
# The host half of that share, with nothing after it. It names the
|
|
142
|
+
# machine even when no share on it is named yet.
|
|
143
|
+
NETWORK_SHARE_HOST: re.compile(
|
|
144
|
+
_ESCAPE * 4 + "[^" + _ESCAPE * 2 + r"/\s]"
|
|
145
|
+
),
|
|
146
|
+
# One person's directory on a machine.
|
|
147
|
+
USER_HOME_PATH: re.compile(r"/(?:home|users)/[^/\s]+", re.I),
|
|
148
|
+
# A path from the root of a machine, read in prose. The first segment
|
|
149
|
+
# must continue into another one or end in a suffix, because a bare
|
|
150
|
+
# slash between two names is how a rate or a pair of sides is written
|
|
151
|
+
# in a sentence.
|
|
152
|
+
ABSOLUTE_PATH: re.compile(
|
|
153
|
+
r"(?m)(?:^|\s)/" + _SEGMENT + "+(?:" + _SEPARATOR + "|" + _ESCAPE + _STOP + "[A-Za-z0-9]{1,8}" + r"\b)"
|
|
154
|
+
),
|
|
155
|
+
# The same path read in a declared value, where one segment is enough
|
|
156
|
+
# because the value is not a sentence. A separator that follows a space
|
|
157
|
+
# and a number is not read: that is a rate, not a path.
|
|
158
|
+
DECLARED_ABSOLUTE_PATH: re.compile(r"(?m)(?:^|(?<![0-9])\s)/" + _SEGMENT),
|
|
159
|
+
# A file on a machine, written as an address.
|
|
160
|
+
LOCAL_FILE_ADDRESS: re.compile(r"\bfile" + _MARK + r"\s*//", re.I),
|
|
161
|
+
# A host reached over the network, written as an address.
|
|
162
|
+
WEB_ADDRESS: re.compile(r"\bhttps?" + _MARK + "//", re.I),
|
|
163
|
+
# An address under any scheme at all, which is how a cloud store, a
|
|
164
|
+
# transfer, a share, a database and a lake are all written. The forms
|
|
165
|
+
# one boundary allows are declared below and nowhere else.
|
|
166
|
+
SCHEME_ADDRESS: re.compile(r"\b[a-z][a-z0-9]*" + _MARK + "//", re.I),
|
|
167
|
+
# A route that climbs out of where it starts, read in prose at the
|
|
168
|
+
# start of a value or a line.
|
|
169
|
+
TRAVERSAL: re.compile(r"(?m)(?:^|\s)" + _UPWARD + _SEPARATOR),
|
|
170
|
+
# The same climb read in a declared value, wherever it sits in it.
|
|
171
|
+
DECLARED_TRAVERSAL: re.compile(_UPWARD + _SEPARATOR),
|
|
172
|
+
# A relative path written with the separator a machine path uses.
|
|
173
|
+
BACKSLASH_RELATIVE_PATH: re.compile(_SEGMENT + _ESCAPE * 2 + _SEGMENT),
|
|
174
|
+
}
|
|
175
|
+
)
|
|
176
|
+
|
|
177
|
+
# The address forms one boundary allows, declared once here so the scan that
|
|
178
|
+
# allows them and the boundaries that refuse them read the same text. A
|
|
179
|
+
# declared value and a tracker note carry no address at all, so every boundary
|
|
180
|
+
# but the shipped-file scan refuses each of these too.
|
|
181
|
+
SECURE_WEB_SCHEME = "https" + _MARK + "//"
|
|
182
|
+
INSECURE_WEB_SCHEME = "http" + _MARK + "//"
|
|
183
|
+
LOCAL_FILE_SCHEME = "file" + _MARK + "//"
|
|
184
|
+
LOGICAL_REFERENCE_SCHEME = "koine" + _MARK + "//"
|
|
185
|
+
# The one root this product writes after that scheme. The scheme alone names no
|
|
186
|
+
# record, so the allowance below is the composed form and not the prefix.
|
|
187
|
+
LOGICAL_REFERENCE_ROOT = "use-case/"
|
|
188
|
+
LOGICAL_REFERENCE_FORM = LOGICAL_REFERENCE_SCHEME + LOGICAL_REFERENCE_ROOT
|
|
189
|
+
DRAWING_NAMESPACE = "www" + _STOP + "w3" + _STOP + "org/2000/svg"
|
|
190
|
+
# The three schemes a boundary may name in a finding of its own rather than as
|
|
191
|
+
# a generic address, and the one form that is not a route to any machine.
|
|
192
|
+
NAMED_SCHEME_FORMS: tuple[str, ...] = (
|
|
193
|
+
SECURE_WEB_SCHEME,
|
|
194
|
+
INSECURE_WEB_SCHEME,
|
|
195
|
+
LOCAL_FILE_SCHEME,
|
|
196
|
+
)
|
|
197
|
+
ALLOWED_SCHEME_FORMS: tuple[str, ...] = (SECURE_WEB_SCHEME, LOGICAL_REFERENCE_FORM)
|
|
198
|
+
|
|
199
|
+
BARE_HOST = "bare host"
|
|
200
|
+
CONNECTION_STRING = "connection string"
|
|
201
|
+
|
|
202
|
+
# The advisory family. Nothing refuses on these; a boundary that reads them
|
|
203
|
+
# labels what it found. Both forms are written by people who mean no harm as
|
|
204
|
+
# often as by a leak, which is why the reading stops at a label.
|
|
205
|
+
ADVISORY_PATTERNS: Mapping[str, re.Pattern[str]] = MappingProxyType(
|
|
206
|
+
{
|
|
207
|
+
# A dotted name that reads like a server. Three or more labels in front
|
|
208
|
+
# of a separator, because two labels in front of one is how an ordinary
|
|
209
|
+
# file inside a directory is written; or a dotted name in front of a
|
|
210
|
+
# port, where the port is the part that makes it an address.
|
|
211
|
+
BARE_HOST: re.compile(
|
|
212
|
+
r"\b(?:[a-z0-9-]+" + _ESCAPE + _STOP + r"){2,}[a-z0-9-]+(?=" + _SEPARATOR + ")"
|
|
213
|
+
r"|\b(?:[a-z0-9-]+" + _ESCAPE + _STOP + r")+[a-z0-9-]+" + _MARK + r"[0-9]{1,5}\b",
|
|
214
|
+
re.I,
|
|
215
|
+
),
|
|
216
|
+
# A connection key written against a value, which is how a driver is
|
|
217
|
+
# told where to connect.
|
|
218
|
+
CONNECTION_STRING: re.compile(
|
|
219
|
+
r"\b(?:server|host|hostname|data[ _-]?source|initial[ _-]?catalog|endpoint|dsn)"
|
|
220
|
+
r"[ \t]*=[ \t]*[\"']?\S",
|
|
221
|
+
re.I,
|
|
222
|
+
),
|
|
223
|
+
}
|
|
224
|
+
)
|
|
225
|
+
|
|
226
|
+
NAMED_SECRET = "named secret"
|
|
227
|
+
NAMED_KEY = "named key"
|
|
228
|
+
PRESENTED_TOKEN = "presented token"
|
|
229
|
+
KEY_BLOCK = "key block"
|
|
230
|
+
ASSIGNED_SECRET = "assigned secret"
|
|
231
|
+
CONNECTION_CREDENTIAL = "connection credential"
|
|
232
|
+
BEARER_AUTHORIZATION = "bearer authorization"
|
|
233
|
+
|
|
234
|
+
CREDENTIAL_PATTERNS: Mapping[str, re.Pattern[str]] = MappingProxyType(
|
|
235
|
+
{
|
|
236
|
+
# The word for a secret, written in a sentence.
|
|
237
|
+
NAMED_SECRET: re.compile(r"\b(?:password|passphrase|secret|credential)s?\b", re.I),
|
|
238
|
+
# The word for a key, written in a sentence.
|
|
239
|
+
NAMED_KEY: re.compile(r"\b(?:api|access|private|signing)[_ -]?key\b", re.I),
|
|
240
|
+
# A token presented for authorization.
|
|
241
|
+
PRESENTED_TOKEN: re.compile(r"\b(?:bearer|basic)\s+\S{8,}", re.I),
|
|
242
|
+
# The opening line of a stored key of any kind. The shape reads what it
|
|
243
|
+
# catches: a private key most of the time, a public one sometimes, and
|
|
244
|
+
# the name says so rather than claiming the narrower thing.
|
|
245
|
+
KEY_BLOCK: re.compile("-{5}begin[a-z ]*key-{5}", re.I),
|
|
246
|
+
# A named secret with a value written against it.
|
|
247
|
+
ASSIGNED_SECRET: re.compile(
|
|
248
|
+
r"\b(?:password|passwd|secret|api[_-]?key|access[_-]?key|"
|
|
249
|
+
r"client[_-]?secret|auth[_-]?token|credential)\b[ \t]*[" + _MARK + r"=][ \t]*"
|
|
250
|
+
r"[\"']?[^\s\"']{8,}",
|
|
251
|
+
re.I,
|
|
252
|
+
),
|
|
253
|
+
# A user and a secret written inside an address.
|
|
254
|
+
CONNECTION_CREDENTIAL: re.compile(
|
|
255
|
+
_MARK + "//" + _ADDRESS_PART + _MARK + _ADDRESS_PART + "@"
|
|
256
|
+
),
|
|
257
|
+
# A presented token written against the header that carries it.
|
|
258
|
+
BEARER_AUTHORIZATION: re.compile(
|
|
259
|
+
r"\bauthorization\b[ \t]*[" + _MARK + r"=][ \t]*[\"']?bearer[ \t]+\S+", re.I
|
|
260
|
+
),
|
|
261
|
+
}
|
|
262
|
+
)
|
|
263
|
+
|
|
264
|
+
CONTROL_CHARACTER = "control character"
|
|
265
|
+
WRITTEN_OBJECT = "written object"
|
|
266
|
+
DELIMITED_FIELDS = "delimited fields"
|
|
267
|
+
|
|
268
|
+
RAW_ROW_PATTERNS: Mapping[str, re.Pattern[str]] = MappingProxyType(
|
|
269
|
+
{
|
|
270
|
+
# A record separator, or anything else below the printable range.
|
|
271
|
+
CONTROL_CHARACTER: re.compile(r"[\x00-\x1f]"),
|
|
272
|
+
# A written object with quoted field names.
|
|
273
|
+
WRITTEN_OBJECT: re.compile(r"\{\s*[\"']"),
|
|
274
|
+
# A run of fields written between delimiters.
|
|
275
|
+
DELIMITED_FIELDS: re.compile(r"\|[^|]*\|"),
|
|
276
|
+
}
|
|
277
|
+
)
|
|
278
|
+
|
|
279
|
+
MACHINE_ROUTE_SHAPES: tuple[str, ...] = tuple(MACHINE_ROUTE_PATTERNS)
|
|
280
|
+
CREDENTIAL_SHAPES: tuple[str, ...] = tuple(CREDENTIAL_PATTERNS)
|
|
281
|
+
RAW_ROW_SHAPES: tuple[str, ...] = tuple(RAW_ROW_PATTERNS)
|
|
282
|
+
ADVISORY_SHAPES: tuple[str, ...] = tuple(ADVISORY_PATTERNS)
|
|
283
|
+
|
|
284
|
+
|
|
285
|
+
def shapes(
|
|
286
|
+
patterns: Mapping[str, re.Pattern[str]], names: Sequence[str]
|
|
287
|
+
) -> tuple[tuple[str, re.Pattern[str]], ...]:
|
|
288
|
+
"""Return the named shapes of one family, in the order a boundary named them.
|
|
289
|
+
|
|
290
|
+
A name this module does not declare raises, so a boundary cannot read a
|
|
291
|
+
shape that has no owner and cannot quietly lose one to a rename.
|
|
292
|
+
"""
|
|
293
|
+
return tuple((name, patterns[name]) for name in names)
|
|
294
|
+
|
|
295
|
+
|
|
296
|
+
def shape_carried(read: Sequence[tuple[str, re.Pattern[str]]], value: str) -> str | None:
|
|
297
|
+
"""Name the first of the given shapes a text carries, or nothing.
|
|
298
|
+
|
|
299
|
+
This reads. What a carried shape means, and what to do about it, belongs to
|
|
300
|
+
the boundary that asked.
|
|
301
|
+
"""
|
|
302
|
+
for name, pattern in read:
|
|
303
|
+
if pattern.search(value):
|
|
304
|
+
return name
|
|
305
|
+
return None
|
|
306
|
+
|
|
307
|
+
|
|
308
|
+
__all__ = [
|
|
309
|
+
"ABSOLUTE_PATH",
|
|
310
|
+
"ADVISORY_PATTERNS",
|
|
311
|
+
"ADVISORY_SHAPES",
|
|
312
|
+
"ALLOWED_SCHEME_FORMS",
|
|
313
|
+
"ASSIGNED_SECRET",
|
|
314
|
+
"BACKSLASH_RELATIVE_PATH",
|
|
315
|
+
"BARE_HOST",
|
|
316
|
+
"BEARER_AUTHORIZATION",
|
|
317
|
+
"CONNECTION_CREDENTIAL",
|
|
318
|
+
"CONNECTION_STRING",
|
|
319
|
+
"CONTROL_CHARACTER",
|
|
320
|
+
"CREDENTIAL_PATTERNS",
|
|
321
|
+
"CREDENTIAL_SHAPES",
|
|
322
|
+
"DECLARED_ABSOLUTE_PATH",
|
|
323
|
+
"DECLARED_TRAVERSAL",
|
|
324
|
+
"DELIMITED_FIELDS",
|
|
325
|
+
"DRAWING_NAMESPACE",
|
|
326
|
+
"DRIVE_PATH",
|
|
327
|
+
"DRIVE_RELATIVE_PATH",
|
|
328
|
+
"INSECURE_WEB_SCHEME",
|
|
329
|
+
"LOCAL_FILE_ADDRESS",
|
|
330
|
+
"LOCAL_FILE_SCHEME",
|
|
331
|
+
"LOGICAL_REFERENCE_FORM",
|
|
332
|
+
"LOGICAL_REFERENCE_ROOT",
|
|
333
|
+
"LOGICAL_REFERENCE_SCHEME",
|
|
334
|
+
"MACHINE_ROUTE_PATTERNS",
|
|
335
|
+
"MACHINE_ROUTE_SHAPES",
|
|
336
|
+
"NAMED_KEY",
|
|
337
|
+
"NAMED_SCHEME_FORMS",
|
|
338
|
+
"NAMED_SECRET",
|
|
339
|
+
"NETWORK_SHARE_HOST",
|
|
340
|
+
"NETWORK_SHARE_PATH",
|
|
341
|
+
"PRESENTED_TOKEN",
|
|
342
|
+
"KEY_BLOCK",
|
|
343
|
+
"RAW_ROW_PATTERNS",
|
|
344
|
+
"RAW_ROW_SHAPES",
|
|
345
|
+
"SCHEME_ADDRESS",
|
|
346
|
+
"SECURE_WEB_SCHEME",
|
|
347
|
+
"TRAVERSAL",
|
|
348
|
+
"USER_HOME_PATH",
|
|
349
|
+
"WEB_ADDRESS",
|
|
350
|
+
"WRITTEN_OBJECT",
|
|
351
|
+
"shape_carried",
|
|
352
|
+
"shapes",
|
|
353
|
+
]
|