wandb 0.19.9__py3-none-any.whl → 0.19.10__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.
- wandb/__init__.py +1 -1
- wandb/__init__.pyi +4 -1
- wandb/_pydantic/__init__.py +14 -7
- wandb/_pydantic/base.py +44 -9
- wandb/_pydantic/utils.py +66 -0
- wandb/_pydantic/v1_compat.py +78 -56
- wandb/apis/public/__init__.py +2 -2
- wandb/apis/public/api.py +114 -2
- wandb/apis/public/artifacts.py +365 -673
- wandb/apis/public/automations.py +69 -0
- wandb/apis/public/integrations.py +168 -0
- wandb/apis/public/projects.py +29 -0
- wandb/apis/public/utils.py +107 -1
- wandb/automations/__init__.py +81 -0
- wandb/automations/_filters/__init__.py +40 -0
- wandb/automations/_filters/expressions.py +179 -0
- wandb/automations/_filters/operators.py +267 -0
- wandb/automations/_filters/run_metrics.py +183 -0
- wandb/automations/_generated/__init__.py +184 -0
- wandb/automations/_generated/create_filter_trigger.py +21 -0
- wandb/automations/_generated/create_generic_webhook_integration.py +43 -0
- wandb/automations/_generated/delete_trigger.py +19 -0
- wandb/automations/_generated/enums.py +33 -0
- wandb/automations/_generated/fragments.py +343 -0
- wandb/automations/_generated/generic_webhook_integrations_by_entity.py +22 -0
- wandb/automations/_generated/get_triggers.py +24 -0
- wandb/automations/_generated/get_triggers_by_entity.py +24 -0
- wandb/automations/_generated/input_types.py +104 -0
- wandb/automations/_generated/integrations_by_entity.py +22 -0
- wandb/automations/_generated/operations.py +710 -0
- wandb/automations/_generated/slack_integrations_by_entity.py +22 -0
- wandb/automations/_generated/update_filter_trigger.py +21 -0
- wandb/automations/_utils.py +123 -0
- wandb/automations/_validators.py +73 -0
- wandb/automations/actions.py +205 -0
- wandb/automations/automations.py +109 -0
- wandb/automations/events.py +235 -0
- wandb/automations/integrations.py +26 -0
- wandb/automations/scopes.py +76 -0
- wandb/beta/workflows.py +9 -10
- wandb/bin/gpu_stats +0 -0
- wandb/cli/cli.py +3 -3
- wandb/integration/keras/keras.py +2 -1
- wandb/integration/langchain/wandb_tracer.py +2 -1
- wandb/jupyter.py +137 -118
- wandb/old/summary.py +0 -2
- wandb/proto/v3/wandb_internal_pb2.py +293 -292
- wandb/proto/v3/wandb_settings_pb2.py +2 -2
- wandb/proto/v3/wandb_telemetry_pb2.py +10 -10
- wandb/proto/v4/wandb_internal_pb2.py +292 -292
- wandb/proto/v4/wandb_settings_pb2.py +2 -2
- wandb/proto/v4/wandb_telemetry_pb2.py +10 -10
- wandb/proto/v5/wandb_internal_pb2.py +292 -292
- wandb/proto/v5/wandb_settings_pb2.py +2 -2
- wandb/proto/v5/wandb_telemetry_pb2.py +10 -10
- wandb/proto/v6/wandb_base_pb2.py +41 -0
- wandb/proto/v6/wandb_internal_pb2.py +393 -0
- wandb/proto/v6/wandb_server_pb2.py +78 -0
- wandb/proto/v6/wandb_settings_pb2.py +58 -0
- wandb/proto/v6/wandb_telemetry_pb2.py +52 -0
- wandb/proto/wandb_base_pb2.py +2 -0
- wandb/proto/wandb_deprecated.py +8 -0
- wandb/proto/wandb_internal_pb2.py +3 -1
- wandb/proto/wandb_server_pb2.py +2 -0
- wandb/proto/wandb_settings_pb2.py +2 -0
- wandb/proto/wandb_telemetry_pb2.py +2 -0
- wandb/sdk/artifacts/_generated/__init__.py +248 -0
- wandb/sdk/artifacts/_generated/artifact_collection_membership_files.py +43 -0
- wandb/sdk/artifacts/_generated/artifact_version_files.py +36 -0
- wandb/sdk/artifacts/_generated/create_artifact_collection_tag_assignments.py +36 -0
- wandb/sdk/artifacts/_generated/delete_artifact_collection_tag_assignments.py +25 -0
- wandb/sdk/artifacts/_generated/delete_artifact_portfolio.py +35 -0
- wandb/sdk/artifacts/_generated/delete_artifact_sequence.py +35 -0
- wandb/sdk/artifacts/_generated/enums.py +17 -0
- wandb/sdk/artifacts/_generated/fragments.py +186 -0
- wandb/sdk/artifacts/_generated/input_types.py +16 -0
- wandb/sdk/artifacts/_generated/move_artifact_collection.py +35 -0
- wandb/sdk/artifacts/_generated/operations.py +510 -0
- wandb/sdk/artifacts/_generated/project_artifact_collection.py +101 -0
- wandb/sdk/artifacts/_generated/project_artifact_collections.py +33 -0
- wandb/sdk/artifacts/_generated/project_artifact_type.py +24 -0
- wandb/sdk/artifacts/_generated/project_artifact_types.py +24 -0
- wandb/sdk/artifacts/_generated/project_artifacts.py +42 -0
- wandb/sdk/artifacts/_generated/run_input_artifacts.py +51 -0
- wandb/sdk/artifacts/_generated/run_output_artifacts.py +51 -0
- wandb/sdk/artifacts/_generated/update_artifact_portfolio.py +35 -0
- wandb/sdk/artifacts/_generated/update_artifact_sequence.py +35 -0
- wandb/sdk/artifacts/_graphql_fragments.py +56 -79
- wandb/sdk/artifacts/artifact.py +40 -13
- wandb/sdk/artifacts/artifact_manifest_entry.py +2 -1
- wandb/sdk/artifacts/storage_handlers/azure_handler.py +1 -0
- wandb/sdk/data_types/base_types/media.py +2 -3
- wandb/sdk/data_types/base_types/wb_value.py +34 -11
- wandb/sdk/data_types/html.py +36 -9
- wandb/sdk/data_types/image.py +12 -12
- wandb/sdk/data_types/table.py +5 -0
- wandb/sdk/data_types/trace_tree.py +2 -0
- wandb/sdk/data_types/utils.py +1 -1
- wandb/sdk/data_types/video.py +14 -26
- wandb/sdk/interface/interface.py +2 -0
- wandb/sdk/internal/profiler.py +6 -5
- wandb/sdk/internal/run.py +13 -6
- wandb/sdk/lib/apikey.py +25 -4
- wandb/sdk/lib/asyncio_compat.py +1 -1
- wandb/sdk/lib/deprecate.py +13 -22
- wandb/sdk/lib/disabled.py +2 -1
- wandb/sdk/lib/printer.py +37 -8
- wandb/sdk/lib/printer_asyncio.py +46 -0
- wandb/sdk/lib/redirect.py +10 -5
- wandb/sdk/service/server_sock.py +19 -14
- wandb/sdk/service/service.py +9 -7
- wandb/sdk/service/streams.py +5 -0
- wandb/sdk/verify/verify.py +6 -3
- wandb/sdk/wandb_init.py +185 -65
- wandb/sdk/wandb_login.py +13 -4
- wandb/sdk/wandb_run.py +382 -286
- wandb/sdk/wandb_settings.py +21 -3
- wandb/sdk/wandb_setup.py +49 -0
- wandb/util.py +29 -29
- {wandb-0.19.9.dist-info → wandb-0.19.10.dist-info}/METADATA +5 -5
- {wandb-0.19.9.dist-info → wandb-0.19.10.dist-info}/RECORD +124 -71
- wandb/_globals.py +0 -19
- wandb/sdk/internal/_generated/base.py +0 -226
- wandb/sdk/internal/_generated/typing_compat.py +0 -14
- {wandb-0.19.9.dist-info → wandb-0.19.10.dist-info}/WHEEL +0 -0
- {wandb-0.19.9.dist-info → wandb-0.19.10.dist-info}/entry_points.txt +0 -0
- {wandb-0.19.9.dist-info → wandb-0.19.10.dist-info}/licenses/LICENSE +0 -0
@@ -0,0 +1,235 @@
|
|
1
|
+
"""Events that trigger W&B Automations."""
|
2
|
+
|
3
|
+
# ruff: noqa: UP007 # Avoid using `X | Y` for union fields, as this can cause issues with pydantic < 2.6
|
4
|
+
|
5
|
+
from __future__ import annotations
|
6
|
+
|
7
|
+
from typing import TYPE_CHECKING, Any, Literal, Optional, Union
|
8
|
+
|
9
|
+
from pydantic import Field
|
10
|
+
from typing_extensions import Self, TypeAlias, get_args
|
11
|
+
|
12
|
+
from wandb._pydantic import (
|
13
|
+
GQLBase,
|
14
|
+
SerializedToJson,
|
15
|
+
field_validator,
|
16
|
+
model_validator,
|
17
|
+
pydantic_isinstance,
|
18
|
+
)
|
19
|
+
|
20
|
+
from ._filters import And, MongoLikeFilter, Or
|
21
|
+
from ._filters.expressions import FilterableField
|
22
|
+
from ._filters.run_metrics import (
|
23
|
+
Agg,
|
24
|
+
MetricChangeFilter,
|
25
|
+
MetricOperand,
|
26
|
+
MetricThresholdFilter,
|
27
|
+
)
|
28
|
+
from ._generated import EventTriggeringConditionType, FilterEventFields
|
29
|
+
from ._validators import simplify_op
|
30
|
+
from .actions import InputAction, InputActionTypes
|
31
|
+
from .scopes import ArtifactCollectionScope, InputScope, ProjectScope
|
32
|
+
|
33
|
+
if TYPE_CHECKING:
|
34
|
+
from .automations import NewAutomation
|
35
|
+
|
36
|
+
|
37
|
+
# NOTE: Re-defined publicly with a more readable name for easier access
|
38
|
+
EventType = EventTriggeringConditionType
|
39
|
+
"""The type of event that triggers an automation."""
|
40
|
+
|
41
|
+
Agg = Agg
|
42
|
+
|
43
|
+
|
44
|
+
# ------------------------------------------------------------------------------
|
45
|
+
# Saved types: for parsing response data from saved automations
|
46
|
+
|
47
|
+
|
48
|
+
# Note: In GQL responses containing saved automation data, the filter is wrapped in an extra `filter` key.
|
49
|
+
class SavedEventFilter(GQLBase):
|
50
|
+
filter: SerializedToJson[MongoLikeFilter] = Field(default_factory=And)
|
51
|
+
|
52
|
+
|
53
|
+
class _InnerRunMetricFilter(GQLBase): # from `RunMetricFilter`
|
54
|
+
threshold_filter: Optional[MetricThresholdFilter] = None
|
55
|
+
change_filter: Optional[MetricChangeFilter] = None
|
56
|
+
|
57
|
+
@model_validator(mode="before")
|
58
|
+
@classmethod
|
59
|
+
def _wrap_metric_filter(cls, v: Any) -> Any:
|
60
|
+
if pydantic_isinstance(v, MetricThresholdFilter):
|
61
|
+
return cls(threshold_filter=v)
|
62
|
+
if pydantic_isinstance(v, MetricChangeFilter):
|
63
|
+
return cls(change_filter=v)
|
64
|
+
return v
|
65
|
+
|
66
|
+
@model_validator(mode="after")
|
67
|
+
def _ensure_exactly_one_set(self) -> Self:
|
68
|
+
set_field_names = [name for name, val in self if (val is not None)]
|
69
|
+
if not set_field_names:
|
70
|
+
raise ValueError("Must specify a run metric filter")
|
71
|
+
if len(set_field_names) > 1:
|
72
|
+
names = ", ".join(map(repr, set_field_names))
|
73
|
+
raise ValueError(f"Must specify a single run metric filter, got: {names}")
|
74
|
+
return self
|
75
|
+
|
76
|
+
|
77
|
+
class RunMetricFilter(GQLBase): # from `RunMetricEvent`
|
78
|
+
run_filter: SerializedToJson[MongoLikeFilter] = Field(default_factory=And)
|
79
|
+
run_metric_filter: _InnerRunMetricFilter
|
80
|
+
|
81
|
+
#: Legacy field to define triggers on run metrics from absolute thresholds. Use `run_metric_filter` instead.
|
82
|
+
metric_filter: Optional[SerializedToJson[MetricThresholdFilter]] = Field(
|
83
|
+
default=None,
|
84
|
+
deprecated="The `metric_filter` field is deprecated: use `run_metric_filter` instead.",
|
85
|
+
)
|
86
|
+
|
87
|
+
@model_validator(mode="before")
|
88
|
+
@classmethod
|
89
|
+
def _wrap_metric_filter(cls, v: Any) -> Any:
|
90
|
+
if pydantic_isinstance(v, (MetricThresholdFilter, MetricChangeFilter)):
|
91
|
+
# If we're only given an (unwrapped) metric filter, automatically wrap it
|
92
|
+
# in the appropriate nested structure, and use the default run filter.
|
93
|
+
|
94
|
+
# Delegate to the inner validator to further wrap the filter as appropriate.
|
95
|
+
return cls(run_metric_filter=_InnerRunMetricFilter.model_validate(v))
|
96
|
+
return v
|
97
|
+
|
98
|
+
@field_validator("run_filter", mode="after")
|
99
|
+
@classmethod
|
100
|
+
def _wrap_run_filter(cls, v: MongoLikeFilter) -> Any:
|
101
|
+
v_new = simplify_op(v)
|
102
|
+
return (
|
103
|
+
And.model_validate(v_new)
|
104
|
+
if pydantic_isinstance(v_new, And)
|
105
|
+
else And(and_=[v_new])
|
106
|
+
)
|
107
|
+
|
108
|
+
|
109
|
+
# type alias defined for naming consistency/clarity
|
110
|
+
SavedRunMetricFilter: TypeAlias = RunMetricFilter
|
111
|
+
|
112
|
+
|
113
|
+
class SavedEvent(FilterEventFields): # from `FilterEventTriggeringCondition`
|
114
|
+
"""A more introspection-friendly representation of a triggering event from a saved automation."""
|
115
|
+
|
116
|
+
# We override the type of the `filter` field since the original GraphQL
|
117
|
+
# schema (and generated class) defines it as a JSONString (str), but we
|
118
|
+
# have more specific expectations for the structure of the JSON data.
|
119
|
+
filter: SerializedToJson[Union[SavedEventFilter, SavedRunMetricFilter]]
|
120
|
+
|
121
|
+
|
122
|
+
# ------------------------------------------------------------------------------
|
123
|
+
# Input types: for creating or updating automations
|
124
|
+
|
125
|
+
|
126
|
+
# Note: The GQL input for "eventFilter" does NOT wrap the filter in an extra `filter` key, unlike the
|
127
|
+
# eventFilter returned in responses for saved automations.
|
128
|
+
class _BaseEventInput(GQLBase):
|
129
|
+
event_type: EventType
|
130
|
+
scope: InputScope
|
131
|
+
filter: SerializedToJson[Any]
|
132
|
+
|
133
|
+
def add_action(self, action: InputAction) -> NewAutomation:
|
134
|
+
"""Define an executed action to be triggered by this event."""
|
135
|
+
from .automations import NewAutomation
|
136
|
+
|
137
|
+
if isinstance(action, InputActionTypes):
|
138
|
+
return NewAutomation(scope=self.scope, event=self, action=action)
|
139
|
+
|
140
|
+
raise TypeError(f"Expected a valid action, got: {type(action).__qualname__!r}")
|
141
|
+
|
142
|
+
def __rshift__(self, other: InputAction) -> NewAutomation:
|
143
|
+
"""Supports `event >> action` as syntactic sugar to combine an event and action."""
|
144
|
+
return self.add_action(other)
|
145
|
+
|
146
|
+
|
147
|
+
class _BaseMutationEventInput(_BaseEventInput):
|
148
|
+
event_type: EventType
|
149
|
+
scope: InputScope
|
150
|
+
filter: SerializedToJson[MongoLikeFilter] = Field(default_factory=And)
|
151
|
+
|
152
|
+
@field_validator("filter", mode="after")
|
153
|
+
@classmethod
|
154
|
+
def _wrap_filter(cls, v: Any) -> Any:
|
155
|
+
"""Ensure the given filter is wrapped like: `{"$or": [{"$and": [<original_filter>]}]}`.
|
156
|
+
|
157
|
+
This is awkward but necessary, because the frontend expects this format.
|
158
|
+
"""
|
159
|
+
v_new = simplify_op(v)
|
160
|
+
v_new = (
|
161
|
+
And.model_validate(v_new)
|
162
|
+
if pydantic_isinstance(v_new, And)
|
163
|
+
else And(and_=[v_new])
|
164
|
+
)
|
165
|
+
v_new = Or(or_=[v_new])
|
166
|
+
return v_new
|
167
|
+
|
168
|
+
|
169
|
+
class OnLinkArtifact(_BaseMutationEventInput):
|
170
|
+
"""A new artifact is linked to a collection."""
|
171
|
+
|
172
|
+
event_type: Literal[EventType.LINK_MODEL] = EventType.LINK_MODEL
|
173
|
+
scope: InputScope
|
174
|
+
|
175
|
+
|
176
|
+
class OnAddArtifactAlias(_BaseMutationEventInput):
|
177
|
+
"""A new alias is assigned to an artifact."""
|
178
|
+
|
179
|
+
event_type: Literal[EventType.ADD_ARTIFACT_ALIAS] = EventType.ADD_ARTIFACT_ALIAS
|
180
|
+
scope: InputScope
|
181
|
+
|
182
|
+
|
183
|
+
class OnCreateArtifact(_BaseMutationEventInput):
|
184
|
+
"""A new artifact is created."""
|
185
|
+
|
186
|
+
event_type: Literal[EventType.CREATE_ARTIFACT] = EventType.CREATE_ARTIFACT
|
187
|
+
scope: ArtifactCollectionScope
|
188
|
+
|
189
|
+
|
190
|
+
class OnRunMetric(_BaseEventInput):
|
191
|
+
"""A run metric satisfies a user-defined absolute threshold."""
|
192
|
+
|
193
|
+
event_type: Literal[EventType.RUN_METRIC] = EventType.RUN_METRIC
|
194
|
+
scope: ProjectScope
|
195
|
+
filter: SerializedToJson[RunMetricFilter]
|
196
|
+
|
197
|
+
|
198
|
+
# for type annotations
|
199
|
+
InputEvent = Union[
|
200
|
+
OnLinkArtifact,
|
201
|
+
OnAddArtifactAlias,
|
202
|
+
OnCreateArtifact,
|
203
|
+
OnRunMetric,
|
204
|
+
]
|
205
|
+
# for runtime type checks
|
206
|
+
InputEventTypes: tuple[type, ...] = get_args(InputEvent)
|
207
|
+
|
208
|
+
|
209
|
+
# ----------------------------------------------------------------------------
|
210
|
+
|
211
|
+
|
212
|
+
class RunEvent:
|
213
|
+
name = FilterableField("display_name")
|
214
|
+
# `Run.name` is actually filtered on `Run.display_name` in the backend.
|
215
|
+
# We can't reasonably expect users to know this a priori, so
|
216
|
+
# automatically fix it here.
|
217
|
+
|
218
|
+
@staticmethod
|
219
|
+
def metric(name: str) -> MetricOperand:
|
220
|
+
"""Define a metric filter condition."""
|
221
|
+
return MetricOperand(name=name)
|
222
|
+
|
223
|
+
|
224
|
+
class ArtifactEvent:
|
225
|
+
alias = FilterableField()
|
226
|
+
|
227
|
+
|
228
|
+
MetricThresholdFilter.model_rebuild()
|
229
|
+
RunMetricFilter.model_rebuild()
|
230
|
+
SavedEventFilter.model_rebuild()
|
231
|
+
|
232
|
+
OnLinkArtifact.model_rebuild()
|
233
|
+
OnAddArtifactAlias.model_rebuild()
|
234
|
+
OnCreateArtifact.model_rebuild()
|
235
|
+
OnRunMetric.model_rebuild()
|
@@ -0,0 +1,26 @@
|
|
1
|
+
from typing import Union
|
2
|
+
|
3
|
+
from pydantic import Field
|
4
|
+
|
5
|
+
from wandb._pydantic import GQLBase
|
6
|
+
from wandb.automations._generated import (
|
7
|
+
GenericWebhookIntegrationFields,
|
8
|
+
SlackIntegrationFields,
|
9
|
+
)
|
10
|
+
|
11
|
+
|
12
|
+
class SlackIntegration(SlackIntegrationFields):
|
13
|
+
pass
|
14
|
+
|
15
|
+
|
16
|
+
class WebhookIntegration(GenericWebhookIntegrationFields):
|
17
|
+
pass
|
18
|
+
|
19
|
+
|
20
|
+
Integration = Union[SlackIntegration, WebhookIntegration]
|
21
|
+
|
22
|
+
|
23
|
+
# For parsing integration instances from paginated responses
|
24
|
+
class _IntegrationEdge(GQLBase):
|
25
|
+
cursor: str
|
26
|
+
node: Integration = Field(discriminator="typename__")
|
@@ -0,0 +1,76 @@
|
|
1
|
+
"""Scopes in which a W&B Automation can be triggered."""
|
2
|
+
|
3
|
+
from __future__ import annotations
|
4
|
+
|
5
|
+
from typing import Literal, Union
|
6
|
+
|
7
|
+
from pydantic import BeforeValidator, Field
|
8
|
+
from typing_extensions import Annotated, TypeAlias, get_args
|
9
|
+
|
10
|
+
from wandb._pydantic import GQLBase
|
11
|
+
from wandb.automations._generated import (
|
12
|
+
ArtifactPortfolioScopeFields,
|
13
|
+
ArtifactSequenceScopeFields,
|
14
|
+
ProjectScopeFields,
|
15
|
+
)
|
16
|
+
|
17
|
+
from ._generated import TriggerScopeType
|
18
|
+
from ._validators import validate_scope
|
19
|
+
|
20
|
+
# NOTE: Re-defined publicly with a more readable name for easier access
|
21
|
+
ScopeType = TriggerScopeType
|
22
|
+
"""The type of scope that triggers an automation."""
|
23
|
+
|
24
|
+
|
25
|
+
class _BaseScope(GQLBase):
|
26
|
+
scope_type: ScopeType
|
27
|
+
|
28
|
+
|
29
|
+
class _ArtifactSequenceScope(_BaseScope, ArtifactSequenceScopeFields):
|
30
|
+
"""The ID and name of a "sequence"-type ArtifactCollection scope of an automation."""
|
31
|
+
|
32
|
+
scope_type: Literal[ScopeType.ARTIFACT_COLLECTION] = ScopeType.ARTIFACT_COLLECTION
|
33
|
+
|
34
|
+
|
35
|
+
class _ArtifactPortfolioScope(_BaseScope, ArtifactPortfolioScopeFields):
|
36
|
+
"""The ID and name of a "portfolio"-type ArtifactCollection scope of an automation."""
|
37
|
+
|
38
|
+
scope_type: Literal[ScopeType.ARTIFACT_COLLECTION] = ScopeType.ARTIFACT_COLLECTION
|
39
|
+
|
40
|
+
|
41
|
+
# for type annotations
|
42
|
+
ArtifactCollectionScope = Annotated[
|
43
|
+
Union[_ArtifactSequenceScope, _ArtifactPortfolioScope],
|
44
|
+
BeforeValidator(validate_scope),
|
45
|
+
Field(discriminator="typename__"),
|
46
|
+
]
|
47
|
+
"""The ID and name of the ArtifactCollection scope of an automation."""
|
48
|
+
|
49
|
+
# for runtime type checks
|
50
|
+
ArtifactCollectionScopeTypes: tuple[type, ...] = (
|
51
|
+
_ArtifactSequenceScope,
|
52
|
+
_ArtifactPortfolioScope,
|
53
|
+
)
|
54
|
+
|
55
|
+
|
56
|
+
class ProjectScope(_BaseScope, ProjectScopeFields):
|
57
|
+
"""The ID and name of the Project scope of an automation."""
|
58
|
+
|
59
|
+
scope_type: Literal[ScopeType.PROJECT] = ScopeType.PROJECT
|
60
|
+
|
61
|
+
|
62
|
+
# for type annotations
|
63
|
+
AutomationScope: TypeAlias = Annotated[
|
64
|
+
Union[_ArtifactSequenceScope, _ArtifactPortfolioScope, ProjectScope],
|
65
|
+
BeforeValidator(validate_scope),
|
66
|
+
Field(discriminator="typename__"),
|
67
|
+
]
|
68
|
+
# for runtime type checks
|
69
|
+
AutomationScopeTypes: tuple[type, ...] = get_args(AutomationScope)
|
70
|
+
|
71
|
+
# Aliases for naming clarity/consistency
|
72
|
+
SavedScope: TypeAlias = AutomationScope
|
73
|
+
InputScope: TypeAlias = AutomationScope
|
74
|
+
|
75
|
+
SavedScopeTypes: tuple[type, ...] = get_args(SavedScope)
|
76
|
+
InputScopeTypes: tuple[type, ...] = get_args(InputScope)
|
wandb/beta/workflows.py
CHANGED
@@ -5,6 +5,7 @@ from typing import Any, Dict, List, Optional, Union
|
|
5
5
|
import wandb
|
6
6
|
import wandb.data_types as data_types
|
7
7
|
from wandb.data_types import _SavedModel
|
8
|
+
from wandb.sdk import wandb_setup
|
8
9
|
from wandb.sdk.artifacts.artifact import Artifact
|
9
10
|
from wandb.sdk.artifacts.artifact_manifest_entry import ArtifactManifestEntry
|
10
11
|
|
@@ -85,12 +86,13 @@ def _log_artifact_version(
|
|
85
86
|
Artifact
|
86
87
|
|
87
88
|
"""
|
88
|
-
|
89
|
+
run = wandb_setup._setup(start_service=False).most_recent_active_run
|
90
|
+
if not run:
|
89
91
|
run = wandb.init(
|
90
|
-
project=project,
|
92
|
+
project=project,
|
93
|
+
job_type=job_type,
|
94
|
+
settings=wandb.Settings(silent=True),
|
91
95
|
)
|
92
|
-
else:
|
93
|
-
run = wandb.run
|
94
96
|
|
95
97
|
if not scope_project:
|
96
98
|
name = f"{name}-{run.id}"
|
@@ -124,7 +126,7 @@ def log_model(
|
|
124
126
|
|
125
127
|
Supported frameworks include PyTorch, Keras, Tensorflow, Scikit-learn, etc. Under
|
126
128
|
the hood, we create a model artifact, bind it to the run that produced this model,
|
127
|
-
associate it with the latest metrics logged with `
|
129
|
+
associate it with the latest metrics logged with `run.log(...)` and more.
|
128
130
|
|
129
131
|
Args:
|
130
132
|
model_obj: any model object created with the following ML frameworks: PyTorch,
|
@@ -215,8 +217,7 @@ def use_model(aliased_path: str, unsafe: bool = False) -> "_SavedModel":
|
|
215
217
|
)
|
216
218
|
|
217
219
|
# Returns a _SavedModel instance
|
218
|
-
if
|
219
|
-
run = wandb.run
|
220
|
+
if run := wandb_setup._setup(start_service=False).most_recent_active_run:
|
220
221
|
artifact = run.use_artifact(aliased_path)
|
221
222
|
sm = artifact.get("index")
|
222
223
|
|
@@ -261,9 +262,7 @@ def link_model(
|
|
261
262
|
"""
|
262
263
|
aliases = wandb.util._resolve_aliases(aliases)
|
263
264
|
|
264
|
-
if
|
265
|
-
run = wandb.run
|
266
|
-
|
265
|
+
if run := wandb_setup._setup(start_service=False).most_recent_active_run:
|
267
266
|
# _artifact_source, if it exists, points to a Public Artifact.
|
268
267
|
# Its existence means that _SavedModel was deserialized from a logged artifact, most likely from `use_model`.
|
269
268
|
if model._artifact_source:
|
wandb/bin/gpu_stats
CHANGED
Binary file
|
wandb/cli/cli.py
CHANGED
@@ -83,14 +83,13 @@ def cli_unsupported(argument):
|
|
83
83
|
|
84
84
|
class ClickWandbException(ClickException):
|
85
85
|
def format_message(self):
|
86
|
-
# log_file = util.get_log_file_path()
|
87
|
-
log_file = ""
|
88
86
|
orig_type = f"{self.orig_type.__module__}.{self.orig_type.__name__}"
|
89
87
|
if issubclass(self.orig_type, Error):
|
90
88
|
return click.style(str(self.message), fg="red")
|
91
89
|
else:
|
92
90
|
return (
|
93
|
-
f"An Exception was raised, see {
|
91
|
+
f"An Exception was raised, see {_wandb_log_path} for full"
|
92
|
+
" traceback.\n"
|
94
93
|
f"{orig_type}: {self.message}"
|
95
94
|
)
|
96
95
|
|
@@ -257,6 +256,7 @@ def login(key, host, cloud, relogin, anonymously, verify, no_offline=False):
|
|
257
256
|
key=key,
|
258
257
|
relogin=relogin,
|
259
258
|
verify=verify,
|
259
|
+
referrer="models",
|
260
260
|
)
|
261
261
|
|
262
262
|
|
wandb/integration/keras/keras.py
CHANGED
@@ -12,8 +12,9 @@ import tensorflow as tf
|
|
12
12
|
import tensorflow.keras.backend as K # noqa: N812
|
13
13
|
|
14
14
|
import wandb
|
15
|
+
from wandb.proto.wandb_deprecated import Deprecated
|
15
16
|
from wandb.sdk.integration_utils.data_logging import ValidationDataLogger
|
16
|
-
from wandb.sdk.lib.deprecate import
|
17
|
+
from wandb.sdk.lib.deprecate import deprecate
|
17
18
|
from wandb.util import add_import_hook
|
18
19
|
|
19
20
|
|
@@ -18,6 +18,7 @@ will be raised when importing this module.
|
|
18
18
|
from packaging import version
|
19
19
|
|
20
20
|
import wandb.util
|
21
|
+
from wandb.proto.wandb_deprecated import Deprecated
|
21
22
|
from wandb.sdk.lib import deprecate
|
22
23
|
|
23
24
|
langchain = wandb.util.get_module(
|
@@ -40,7 +41,7 @@ class WandbTracer(WandbTracer):
|
|
40
41
|
def __init__(self, *args, **kwargs):
|
41
42
|
super().__init__(*args, **kwargs)
|
42
43
|
deprecate.deprecate(
|
43
|
-
field_name=
|
44
|
+
field_name=Deprecated.langchain_tracer,
|
44
45
|
warning_message="This feature is deprecated and has been moved to `langchain`. Enable tracing by setting "
|
45
46
|
"LANGCHAIN_WANDB_TRACING=true in your environment. See the documentation at "
|
46
47
|
"https://python.langchain.com/docs/ecosystem/integrations/agent_with_wandb_tracing for guidance. "
|