UncountablePythonSDK 0.0.173.dev2__py3-none-any.whl → 0.0.174__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.
docs/.flowmarkignore ADDED
@@ -0,0 +1,9 @@
1
+ # Flowmark collapses the MyST {tab-set}/{tab-item} directives in index.md,
2
+ # which breaks the Sphinx build. flowmark-rs 0.3.1 ignores file patterns in
3
+ # [tool.flowmark] extend-exclude, so the exclusion lives here instead.
4
+ # Both pattern forms are required: the anchored form applies to directory
5
+ # walks (relative to this directory); the repo-root-relative form applies
6
+ # when the file is passed explicitly under --force-exclude (matched against
7
+ # the cwd-relative path, and just recipes always run from the repo root).
8
+ /index.md
9
+ sdk/docs/index.md
@@ -1,6 +1,7 @@
1
1
  # Add a File to a Folder
2
2
 
3
- This is a two-step workflow: first upload the file using `upload_files`, then place it in a target folder using `add_file_to_folder`.
3
+ This is a two-step workflow: first upload the file using `upload_files`, then place it in a target
4
+ folder using `add_file_to_folder`.
4
5
 
5
6
  ## Step 1: Upload the file
6
7
 
@@ -54,4 +55,3 @@ response = client.add_file_to_folder(
54
55
  folder_key=identifier_t.IdentifierKeyRefName(ref_name="root"),
55
56
  )
56
57
  ```
57
-
@@ -4,7 +4,8 @@ Use the `create_or_update_entity` method to create Ingredients.
4
4
 
5
5
  The following fields are required when creating an Ingredient:
6
6
  - `name`: The name of the Ingredient
7
- - `core_ingredient_ingredientMaterialFamilies`: The list of material families in which to include the Ingredient
7
+ - `core_ingredient_ingredientMaterialFamilies`: The list of material families in which to include
8
+ the Ingredient
8
9
 
9
10
  The reference name of the default definition of Ingredients is `uncIngredient`
10
11
 
@@ -1,6 +1,7 @@
1
1
  # Upload Files
2
2
 
3
- This example demonstrates the efficient way to upload files using the External API SDK's `client.upload_files()` method.
3
+ This example demonstrates the efficient way to upload files using the External API SDKs
4
+ `client.upload_files()` method.
4
5
 
5
6
  ```python
6
7
  from io import BytesIO
@@ -135,7 +135,9 @@ def _get_cgroup_memory_limit_bytes() -> int | None:
135
135
  def run_queued_job(
136
136
  queued_job: queued_job_t.QueuedJob,
137
137
  ) -> job_definition_t.JobResult:
138
- with get_otel_tracer().start_as_current_span(name="run_queued_job") as span:
138
+ with get_otel_tracer().start_as_current_span(
139
+ name=f"run_queued_job: {queued_job.job_ref_name}"
140
+ ) as span:
139
141
  if resource is not None:
140
142
  cgroup_limit = _get_cgroup_memory_limit_bytes()
141
143
  if cgroup_limit is not None:
@@ -51,6 +51,20 @@ def _cast_attributes(attributes: dict[str, base_t.JsonValue]) -> Attributes:
51
51
  return cast(Attributes, attributes)
52
52
 
53
53
 
54
+ def _dd_log_correlation_attributes(
55
+ span_context: trace.SpanContext,
56
+ ) -> dict[str, base_t.JsonValue]:
57
+ # Integration server logs export via ConsoleLogExporter
58
+ # (stdout), not OTLP, so we inject the dd.trace_id / dd.span_id
59
+ # correlation keys manually (hex trace, decimal span).
60
+ if not span_context.is_valid:
61
+ return {}
62
+ return {
63
+ "dd.trace_id": trace.format_trace_id(span_context.trace_id),
64
+ "dd.span_id": str(span_context.span_id),
65
+ }
66
+
67
+
54
68
  def one_line_formatter(record: ReadableLogRecord) -> str:
55
69
  json_data = record.to_json()
56
70
  return json.dumps(json.loads(json_data), separators=(",", ":")) + "\n"
@@ -114,22 +128,28 @@ def _get_severity_number(severity: LogSeverity) -> _logs.SeverityNumber:
114
128
 
115
129
 
116
130
  class Logger:
117
- current_span: Span
131
+ base_span: Span
118
132
  _bound_attributes: dict[str, base_t.JsonValue]
119
133
  _scope_attributes_stack: list[dict[str, base_t.JsonValue]]
120
134
 
121
135
  def __init__(self, base_span: Span) -> None:
122
- self.current_span = base_span
136
+ self.base_span = base_span
123
137
  self._bound_attributes = {}
124
138
  self._scope_attributes_stack = []
125
139
 
126
140
  @property
127
- def current_span_id(self) -> int:
128
- return self.current_span.get_span_context().span_id
141
+ def base_span_id(self) -> int:
142
+ return self.base_span.get_span_context().span_id
129
143
 
130
144
  @property
131
- def current_trace_id(self) -> int | None:
132
- return self.current_span.get_span_context().trace_id
145
+ def base_trace_id(self) -> int | None:
146
+ return self.base_span.get_span_context().trace_id
147
+
148
+ def _correlation_span(self) -> Span:
149
+ active_span = trace.get_current_span()
150
+ if active_span.get_span_context().is_valid:
151
+ return active_span
152
+ return self.base_span
133
153
 
134
154
  def _patch_attributes(
135
155
  self,
@@ -138,9 +158,7 @@ class Logger:
138
158
  message: str | None = None,
139
159
  severity: LogSeverity | None = None,
140
160
  ) -> Attributes:
141
- patched_attributes: dict[str, base_t.JsonValue] = {
142
- **self._bound_attributes,
143
- }
161
+ patched_attributes: dict[str, base_t.JsonValue] = {**self._bound_attributes}
144
162
  for scope_attrs in self._scope_attributes_stack:
145
163
  patched_attributes.update(scope_attrs)
146
164
  if attributes is not None:
@@ -163,13 +181,19 @@ class Logger:
163
181
  self, message: str, *, severity: LogSeverity, attributes: Attributes | None
164
182
  ) -> None:
165
183
  otel_logger = get_otel_logger()
184
+ log_attributes: dict[str, base_t.JsonValue] = dict(
185
+ self._patch_attributes(
186
+ message=message, severity=severity, attributes=attributes
187
+ )
188
+ )
189
+ log_attributes.update(
190
+ _dd_log_correlation_attributes(self._correlation_span().get_span_context())
191
+ )
166
192
  log_record = LogRecord(
167
193
  body=message,
168
194
  severity_text=severity,
169
195
  timestamp=time.time_ns(),
170
- attributes=self._patch_attributes(
171
- message=message, severity=severity, attributes=attributes
172
- ),
196
+ attributes=_cast_attributes(log_attributes),
173
197
  context=get_current(),
174
198
  severity_number=_get_severity_number(severity),
175
199
  )
@@ -218,7 +242,7 @@ class Logger:
218
242
  patched_attributes = self._patch_attributes(
219
243
  message=message, severity=severity, attributes=attributes
220
244
  )
221
- self.current_span.record_exception(
245
+ self._correlation_span().record_exception(
222
246
  exception=exception, attributes=patched_attributes
223
247
  )
224
248
  log_message = f"{message}\nexception: {exception}{traceback_str}"
@@ -154,6 +154,7 @@ class RecipeStep:
154
154
  name: str | None
155
155
  recipe_step_id: base_t.ObjectId
156
156
  recipe_step_number: int
157
+ display_mix_order_number: int | None = None
157
158
  instructions: str | None = None
158
159
 
159
160
 
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: UncountablePythonSDK
3
- Version: 0.0.173.dev2
3
+ Version: 0.0.174
4
4
  Summary: Uncountable SDK
5
5
  Project-URL: Homepage, https://github.com/uncountableinc/uncountable-python-sdk
6
6
  Project-URL: Repository, https://github.com/uncountableinc/uncountable-python-sdk.git
@@ -53,7 +53,8 @@ Requires-Dist: pytest-xdist==3.*; extra == "test"
53
53
  # Uncountable Python SDK
54
54
 
55
55
  ## Documentation
56
- [https://uncountableinc.github.io/uncountable-python-sdk/](https://uncountableinc.github.io/uncountable-python-sdk/)
56
+
57
+ https://uncountableinc.github.io/uncountable-python-sdk/
57
58
 
58
59
  ## Installation
59
60
 
@@ -62,4 +63,3 @@ Install from PyPI:
62
63
  ```console
63
64
  pip install UncountablePythonSDK
64
65
  ```
65
-
@@ -1,13 +1,14 @@
1
+ docs/.flowmarkignore,sha256=gmJziQDpI3zbfHFgM73BE9iaLn04Oqya_7QCjJ749o8,548
1
2
  docs/.gitignore,sha256=_ebkZUcwfvfnGEJ95rfj1lxoBNd6EE9ZvtOc7FsbfFE,7
2
3
  docs/conf.py,sha256=Ky-_Y76T7pwN2aBG-dSF79Av70e7ASgcOXEdQ1qyor4,3542
3
4
  docs/index.md,sha256=g4Yi5831fEkywYkkcFohYLkKzSI91SOZF7DxKsm9zgI,3193
4
5
  docs/justfile,sha256=WymCEQ6W2A8Ak79iUPmecmuaUNN2htb7STUrz5K7ELE,273
5
6
  docs/requirements.txt,sha256=8aqtVaNV4AlzUZ7nAM8kxOF1ccAcujhQ_ayU9Whksf8,172
6
- docs/integration_examples/add_file_to_folder.md,sha256=-8mSReDFaPyDQeAkWyY0x5oFR_NkF81K6PpMKmhNMXY,1557
7
- docs/integration_examples/create_ingredient.md,sha256=bzTQ943YhINxa3HQylEA26rbAsjr6HvvN_HkVkrzUeA,1547
7
+ docs/integration_examples/add_file_to_folder.md,sha256=ZCv8miP7ZlPjor-ZGDwy2oucyopqMPa3aXlmOEfbX10,1556
8
+ docs/integration_examples/create_ingredient.md,sha256=ufzAzPyGaDr9rCBDMGQAE8xahsCMkVfG8VLs1pb3qr0,1549
8
9
  docs/integration_examples/create_output.md,sha256=aDn2TjzKgY-HnxnvgsZS578cvajmHpF1y2HKkHfdtd4,2104
9
10
  docs/integration_examples/index.md,sha256=V0vJKMIqDadsSRW0wkUa4CQ2cq5RUWM4gMlPHz_18t4,104
10
- docs/integration_examples/upload_file.md,sha256=UdDoJasJQkI36iHjLKCFoAfDV4sxzmpg9TqzrfzQbWs,909
11
+ docs/integration_examples/upload_file.md,sha256=eWtWTRnuV6EvhnnagnJ2o0RF9XkPWzX4izIqDWt1NZg,911
11
12
  docs/static/logo_blue.png,sha256=SyYpMTVhhBbhF5Wl8lWaVwz-_p1MIR6dW6bVhufQRME,46708
12
13
  docs/static/favicons/android-chrome-192x192.png,sha256=XoF-AhD55JlSBDGsEPJKfT_VeXT-awhwKyZnxLhrwvk,1369
13
14
  docs/static/favicons/android-chrome-512x512.png,sha256=1S4xwY9YtJQ5ifFsZ-DOzssoyBYs0t9uwdOUmYx0Xso,3888
@@ -136,7 +137,7 @@ uncountable/integration/request_context.py,sha256=N_FJJxqvfUJ0yV9h3I3vFTGNJiDfyL
136
137
  uncountable/integration/scan_profiles.py,sha256=iTpzYKBHarlhYG6CKYtyAmQ7vUhEUbj2icGVHell8AU,3059
137
138
  uncountable/integration/scheduler.py,sha256=BajQ4txvgEBw8S9x1P0eGm-uBkKp_oecJK65SQd2hNw,8477
138
139
  uncountable/integration/server.py,sha256=P4RRGwU9jMselHPWbU6GxhRLgVtN7Ydcxr18sFn2zI8,5778
139
- uncountable/integration/telemetry.py,sha256=PjhwT55KSYuswQS5rqNDYFIU2MWDqNXHF42gKp5kQBs,15534
140
+ uncountable/integration/telemetry.py,sha256=vCIw73OBfxzAaXhPz6VdMqUtWEW70QVoXZ5Q9RIJsU0,16431
140
141
  uncountable/integration/db/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
141
142
  uncountable/integration/db/connect.py,sha256=mE3bdV0huclH2iT_dXCQdRL4LkjIuf_myAR64RTWXEs,498
142
143
  uncountable/integration/db/session.py,sha256=96cGQXpe6IugBTdSsjdP0S5yhJ6toSmbVB6qhc3FJzE,693
@@ -150,7 +151,7 @@ uncountable/integration/queue_runner/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeu
150
151
  uncountable/integration/queue_runner/job_scheduler.py,sha256=MrQLYB4UqkUXKRPDHTqc6C6ZlQ3i8Cy-qopnqZQZbWE,9897
151
152
  uncountable/integration/queue_runner/queue_runner.py,sha256=N4sUXmlGzVquybiJ7NQZavCJOBGrxBj6k7mb-TITaN0,1139
152
153
  uncountable/integration/queue_runner/types.py,sha256=8HS6KnYMS_vc5XHeMpg0BFAQC-5P3QLzd-aDYDMMt3E,244
153
- uncountable/integration/queue_runner/worker.py,sha256=YU1qRGCYF7vrEcsV4zGnNslYGc6XM9WMCpoATtXB_g0,7314
154
+ uncountable/integration/queue_runner/worker.py,sha256=mAA-NAxjMH3q1pooIbCzNBN6pIPAlSOn4eO1UITayeQ,7356
154
155
  uncountable/integration/queue_runner/command_server/__init__.py,sha256=hMCDLWct8zW4B2a9BaIAsMhtaEgFlxONjeow-6nf6dg,675
155
156
  uncountable/integration/queue_runner/command_server/command_client.py,sha256=Gb-BdCXa6YSSHHN-SbLvtcSf5CgDUJ3cUWQevmb1o4g,5682
156
157
  uncountable/integration/queue_runner/command_server/command_server.py,sha256=Q9tYkJXfjq1yNIUwDmHIDdX70HVOaTWtZLMDhWN5C0k,7867
@@ -384,7 +385,7 @@ uncountable/types/api/recipes/get_recipe_calculations.py,sha256=Nx00qf4rOfe8bNUN
384
385
  uncountable/types/api/recipes/get_recipe_links.py,sha256=ousQ2zrAmNg7rIxT4kwD5FlOmG0XMnVVPNFn3V7vePU,1484
385
386
  uncountable/types/api/recipes/get_recipe_names.py,sha256=rv3-Dv0gy_Ylo6c_irKco0GdKP5_QHHQdOh67qkSCMY,1511
386
387
  uncountable/types/api/recipes/get_recipe_output_metadata.py,sha256=IYm4DA7RN8gvxkhA5dfBInpH0h-TOGGrMpWwDmJbYsw,2045
387
- uncountable/types/api/recipes/get_recipes_data.py,sha256=-FIV2dOP1qAib4LoIKcn4mkdsC8EGKZdPZYO3p9HHQw,8670
388
+ uncountable/types/api/recipes/get_recipes_data.py,sha256=BKHOa2_oXzm-UP14czZSwS8crZqc1MXSzoKRdtT55Sg,8718
388
389
  uncountable/types/api/recipes/lock_recipes.py,sha256=Ez5oWRwq_n16RHli56uaEURGrRYxyIS2VLOJEUQ9kaY,1885
389
390
  uncountable/types/api/recipes/remove_recipe_from_project.py,sha256=h1I3cLUb_zZ3QjpK7IKPT_1gTDPTPbGWg0OJN_rUn6o,1186
390
391
  uncountable/types/api/recipes/set_recipe_inputs.py,sha256=2NhVAfkIjVTtUKeV1aPLb42wP6XZBerbYKJ_K_HH3kA,2040
@@ -408,7 +409,7 @@ uncountable/types/api/uploader/complete_async_parse.py,sha256=Os1HAubxTlbut6Gylj
408
409
  uncountable/types/api/uploader/invoke_uploader.py,sha256=QU1KmAFgGHSWskZEKfaAww8rCj-hVNP0i4kMQE3x3Fc,1822
409
410
  uncountable/types/api/user/__init__.py,sha256=gCgbynxG3jA8FQHzercKtrHKHkiIKr8APdZYUniAor8,55
410
411
  uncountable/types/api/user/get_current_user_info.py,sha256=BT7bGp5SOHz3XdKWhhdZ6acnInafT2PgdJ-H4YH3W7c,1181
411
- uncountablepythonsdk-0.0.173.dev2.dist-info/METADATA,sha256=Qsqk-cRXZaJOR1FhuzNn41TKnWaXrbAjJvbynm4IOQA,2237
412
- uncountablepythonsdk-0.0.173.dev2.dist-info/WHEEL,sha256=aeYiig01lYGDzBgS8HxWXOg3uV61G9ijOsup-k9o1sk,91
413
- uncountablepythonsdk-0.0.173.dev2.dist-info/top_level.txt,sha256=1UVGjAU-6hJY9qw2iJ7nCBeEwZ793AEN5ZfKX9A1uj4,31
414
- uncountablepythonsdk-0.0.173.dev2.dist-info/RECORD,,
412
+ uncountablepythonsdk-0.0.174.dist-info/METADATA,sha256=IgpDlDYzY8guCjmz-ROa_2rEA2Vs5uqJepWThvfDAPc,2172
413
+ uncountablepythonsdk-0.0.174.dist-info/WHEEL,sha256=aeYiig01lYGDzBgS8HxWXOg3uV61G9ijOsup-k9o1sk,91
414
+ uncountablepythonsdk-0.0.174.dist-info/top_level.txt,sha256=1UVGjAU-6hJY9qw2iJ7nCBeEwZ793AEN5ZfKX9A1uj4,31
415
+ uncountablepythonsdk-0.0.174.dist-info/RECORD,,