mlrun 1.10.0rc40__py3-none-any.whl → 1.11.0rc16__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.
Potentially problematic release.
This version of mlrun might be problematic. Click here for more details.
- mlrun/__init__.py +3 -2
- mlrun/__main__.py +0 -4
- mlrun/artifacts/dataset.py +2 -2
- mlrun/artifacts/plots.py +1 -1
- mlrun/{model_monitoring/db/tsdb/tdengine → auth}/__init__.py +2 -3
- mlrun/auth/nuclio.py +89 -0
- mlrun/auth/providers.py +429 -0
- mlrun/auth/utils.py +415 -0
- mlrun/common/constants.py +7 -0
- mlrun/common/model_monitoring/helpers.py +41 -4
- mlrun/common/runtimes/constants.py +28 -0
- mlrun/common/schemas/__init__.py +13 -3
- mlrun/common/schemas/alert.py +2 -2
- mlrun/common/schemas/api_gateway.py +3 -0
- mlrun/common/schemas/auth.py +10 -10
- mlrun/common/schemas/client_spec.py +4 -0
- mlrun/common/schemas/constants.py +25 -0
- mlrun/common/schemas/frontend_spec.py +1 -8
- mlrun/common/schemas/function.py +24 -0
- mlrun/common/schemas/hub.py +3 -2
- mlrun/common/schemas/model_monitoring/__init__.py +1 -1
- mlrun/common/schemas/model_monitoring/constants.py +2 -2
- mlrun/common/schemas/secret.py +17 -2
- mlrun/common/secrets.py +95 -1
- mlrun/common/types.py +10 -10
- mlrun/config.py +53 -15
- mlrun/data_types/infer.py +2 -2
- mlrun/datastore/__init__.py +2 -3
- mlrun/datastore/base.py +274 -10
- mlrun/datastore/datastore.py +1 -1
- mlrun/datastore/datastore_profile.py +49 -17
- mlrun/datastore/model_provider/huggingface_provider.py +6 -2
- mlrun/datastore/model_provider/model_provider.py +2 -2
- mlrun/datastore/model_provider/openai_provider.py +2 -2
- mlrun/datastore/s3.py +15 -16
- mlrun/datastore/sources.py +1 -1
- mlrun/datastore/store_resources.py +4 -4
- mlrun/datastore/storeytargets.py +16 -10
- mlrun/datastore/targets.py +1 -1
- mlrun/datastore/utils.py +16 -3
- mlrun/datastore/v3io.py +1 -1
- mlrun/db/base.py +36 -12
- mlrun/db/httpdb.py +316 -101
- mlrun/db/nopdb.py +29 -11
- mlrun/errors.py +4 -2
- mlrun/execution.py +11 -12
- mlrun/feature_store/api.py +1 -1
- mlrun/feature_store/common.py +1 -1
- mlrun/feature_store/feature_vector_utils.py +1 -1
- mlrun/feature_store/steps.py +8 -6
- mlrun/frameworks/_common/utils.py +3 -3
- mlrun/frameworks/_dl_common/loggers/logger.py +1 -1
- mlrun/frameworks/_dl_common/loggers/tensorboard_logger.py +2 -1
- mlrun/frameworks/_ml_common/loggers/mlrun_logger.py +1 -1
- mlrun/frameworks/_ml_common/utils.py +2 -1
- mlrun/frameworks/auto_mlrun/auto_mlrun.py +4 -3
- mlrun/frameworks/lgbm/mlrun_interfaces/mlrun_interface.py +2 -1
- mlrun/frameworks/onnx/dataset.py +2 -1
- mlrun/frameworks/onnx/mlrun_interface.py +2 -1
- mlrun/frameworks/pytorch/callbacks/logging_callback.py +5 -4
- mlrun/frameworks/pytorch/callbacks/mlrun_logging_callback.py +2 -1
- mlrun/frameworks/pytorch/callbacks/tensorboard_logging_callback.py +2 -1
- mlrun/frameworks/pytorch/utils.py +2 -1
- mlrun/frameworks/sklearn/metric.py +2 -1
- mlrun/frameworks/tf_keras/callbacks/logging_callback.py +5 -4
- mlrun/frameworks/tf_keras/callbacks/mlrun_logging_callback.py +2 -1
- mlrun/frameworks/tf_keras/callbacks/tensorboard_logging_callback.py +2 -1
- mlrun/hub/__init__.py +37 -0
- mlrun/hub/base.py +142 -0
- mlrun/hub/module.py +67 -76
- mlrun/hub/step.py +113 -0
- mlrun/launcher/base.py +2 -1
- mlrun/launcher/local.py +2 -1
- mlrun/model.py +12 -2
- mlrun/model_monitoring/__init__.py +0 -1
- mlrun/model_monitoring/api.py +2 -2
- mlrun/model_monitoring/applications/base.py +20 -6
- mlrun/model_monitoring/applications/context.py +1 -0
- mlrun/model_monitoring/controller.py +7 -17
- mlrun/model_monitoring/db/_schedules.py +2 -16
- mlrun/model_monitoring/db/_stats.py +2 -13
- mlrun/model_monitoring/db/tsdb/__init__.py +9 -7
- mlrun/model_monitoring/db/tsdb/base.py +2 -4
- mlrun/model_monitoring/db/tsdb/preaggregate.py +234 -0
- mlrun/model_monitoring/db/tsdb/stream_graph_steps.py +63 -0
- mlrun/model_monitoring/db/tsdb/timescaledb/queries/timescaledb_metrics_queries.py +414 -0
- mlrun/model_monitoring/db/tsdb/timescaledb/queries/timescaledb_predictions_queries.py +376 -0
- mlrun/model_monitoring/db/tsdb/timescaledb/queries/timescaledb_results_queries.py +590 -0
- mlrun/model_monitoring/db/tsdb/timescaledb/timescaledb_connection.py +434 -0
- mlrun/model_monitoring/db/tsdb/timescaledb/timescaledb_connector.py +541 -0
- mlrun/model_monitoring/db/tsdb/timescaledb/timescaledb_operations.py +808 -0
- mlrun/model_monitoring/db/tsdb/timescaledb/timescaledb_schema.py +502 -0
- mlrun/model_monitoring/db/tsdb/timescaledb/timescaledb_stream.py +163 -0
- mlrun/model_monitoring/db/tsdb/timescaledb/timescaledb_stream_graph_steps.py +60 -0
- mlrun/model_monitoring/db/tsdb/timescaledb/utils/timescaledb_dataframe_processor.py +141 -0
- mlrun/model_monitoring/db/tsdb/timescaledb/utils/timescaledb_query_builder.py +585 -0
- mlrun/model_monitoring/db/tsdb/timescaledb/writer_graph_steps.py +73 -0
- mlrun/model_monitoring/db/tsdb/v3io/stream_graph_steps.py +4 -6
- mlrun/model_monitoring/db/tsdb/v3io/v3io_connector.py +147 -79
- mlrun/model_monitoring/features_drift_table.py +2 -1
- mlrun/model_monitoring/helpers.py +2 -1
- mlrun/model_monitoring/stream_processing.py +18 -16
- mlrun/model_monitoring/writer.py +4 -3
- mlrun/package/__init__.py +2 -1
- mlrun/platforms/__init__.py +0 -44
- mlrun/platforms/iguazio.py +1 -1
- mlrun/projects/operations.py +11 -10
- mlrun/projects/project.py +81 -82
- mlrun/run.py +4 -7
- mlrun/runtimes/__init__.py +2 -204
- mlrun/runtimes/base.py +89 -21
- mlrun/runtimes/constants.py +225 -0
- mlrun/runtimes/daskjob.py +4 -2
- mlrun/runtimes/databricks_job/databricks_runtime.py +2 -1
- mlrun/runtimes/mounts.py +5 -0
- mlrun/runtimes/nuclio/__init__.py +12 -8
- mlrun/runtimes/nuclio/api_gateway.py +36 -6
- mlrun/runtimes/nuclio/application/application.py +200 -32
- mlrun/runtimes/nuclio/function.py +154 -49
- mlrun/runtimes/nuclio/serving.py +55 -42
- mlrun/runtimes/pod.py +59 -10
- mlrun/secrets.py +46 -2
- mlrun/serving/__init__.py +2 -0
- mlrun/serving/remote.py +5 -5
- mlrun/serving/routers.py +3 -3
- mlrun/serving/server.py +46 -43
- mlrun/serving/serving_wrapper.py +6 -2
- mlrun/serving/states.py +554 -207
- mlrun/serving/steps.py +1 -1
- mlrun/serving/system_steps.py +42 -33
- mlrun/track/trackers/mlflow_tracker.py +29 -31
- mlrun/utils/helpers.py +89 -16
- mlrun/utils/http.py +9 -2
- mlrun/utils/notifications/notification/git.py +1 -1
- mlrun/utils/notifications/notification/mail.py +39 -16
- mlrun/utils/notifications/notification_pusher.py +2 -2
- mlrun/utils/version/version.json +2 -2
- mlrun/utils/version/version.py +3 -4
- {mlrun-1.10.0rc40.dist-info → mlrun-1.11.0rc16.dist-info}/METADATA +39 -49
- {mlrun-1.10.0rc40.dist-info → mlrun-1.11.0rc16.dist-info}/RECORD +144 -130
- mlrun/db/auth_utils.py +0 -152
- mlrun/model_monitoring/db/tsdb/tdengine/schemas.py +0 -343
- mlrun/model_monitoring/db/tsdb/tdengine/stream_graph_steps.py +0 -75
- mlrun/model_monitoring/db/tsdb/tdengine/tdengine_connection.py +0 -281
- mlrun/model_monitoring/db/tsdb/tdengine/tdengine_connector.py +0 -1368
- mlrun/model_monitoring/db/tsdb/tdengine/writer_graph_steps.py +0 -51
- {mlrun-1.10.0rc40.dist-info → mlrun-1.11.0rc16.dist-info}/WHEEL +0 -0
- {mlrun-1.10.0rc40.dist-info → mlrun-1.11.0rc16.dist-info}/entry_points.txt +0 -0
- {mlrun-1.10.0rc40.dist-info → mlrun-1.11.0rc16.dist-info}/licenses/LICENSE +0 -0
- {mlrun-1.10.0rc40.dist-info → mlrun-1.11.0rc16.dist-info}/top_level.txt +0 -0
|
@@ -11,6 +11,7 @@
|
|
|
11
11
|
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
12
|
# See the License for the specific language governing permissions and
|
|
13
13
|
# limitations under the License.
|
|
14
|
+
import copy
|
|
14
15
|
import pathlib
|
|
15
16
|
import typing
|
|
16
17
|
|
|
@@ -20,23 +21,18 @@ import nuclio.auth
|
|
|
20
21
|
import mlrun.common.schemas as schemas
|
|
21
22
|
import mlrun.errors
|
|
22
23
|
import mlrun.run
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
from mlrun.runtimes.
|
|
26
|
-
|
|
27
|
-
|
|
24
|
+
import mlrun.runtimes.nuclio.api_gateway as nuclio_api_gateway
|
|
25
|
+
import mlrun.runtimes.nuclio.function as nuclio_function
|
|
26
|
+
from mlrun.common.runtimes.constants import (
|
|
27
|
+
NuclioIngressAddTemplatedIngressModes,
|
|
28
|
+
ProbeTimeConfig,
|
|
29
|
+
ProbeType,
|
|
28
30
|
)
|
|
29
|
-
from mlrun.runtimes.nuclio.api_gateway import (
|
|
30
|
-
APIGateway,
|
|
31
|
-
APIGatewayMetadata,
|
|
32
|
-
APIGatewaySpec,
|
|
33
|
-
)
|
|
34
|
-
from mlrun.runtimes.nuclio.function import NuclioSpec, NuclioStatus
|
|
35
31
|
from mlrun.utils import is_valid_port, logger, update_in
|
|
36
32
|
|
|
37
33
|
|
|
38
|
-
class ApplicationSpec(NuclioSpec):
|
|
39
|
-
_dict_fields = NuclioSpec._dict_fields + [
|
|
34
|
+
class ApplicationSpec(nuclio_function.NuclioSpec):
|
|
35
|
+
_dict_fields = nuclio_function.NuclioSpec._dict_fields + [
|
|
40
36
|
"internal_application_port",
|
|
41
37
|
"application_ports",
|
|
42
38
|
]
|
|
@@ -88,6 +84,7 @@ class ApplicationSpec(NuclioSpec):
|
|
|
88
84
|
track_models=None,
|
|
89
85
|
internal_application_port=None,
|
|
90
86
|
application_ports=None,
|
|
87
|
+
auth=None,
|
|
91
88
|
):
|
|
92
89
|
super().__init__(
|
|
93
90
|
command=command,
|
|
@@ -133,6 +130,7 @@ class ApplicationSpec(NuclioSpec):
|
|
|
133
130
|
track_models=track_models,
|
|
134
131
|
state_thresholds=state_thresholds,
|
|
135
132
|
disable_default_http_trigger=disable_default_http_trigger,
|
|
133
|
+
auth=auth,
|
|
136
134
|
)
|
|
137
135
|
|
|
138
136
|
# Override default min/max replicas (don't assume application is stateless)
|
|
@@ -189,7 +187,7 @@ class ApplicationSpec(NuclioSpec):
|
|
|
189
187
|
|
|
190
188
|
# ensure multiple ports are supported in Nuclio
|
|
191
189
|
if len(application_ports) > 1:
|
|
192
|
-
multiple_port_sidecar_is_supported()
|
|
190
|
+
nuclio_function.multiple_port_sidecar_is_supported()
|
|
193
191
|
|
|
194
192
|
self._application_ports = application_ports
|
|
195
193
|
|
|
@@ -215,7 +213,7 @@ class ApplicationSpec(NuclioSpec):
|
|
|
215
213
|
self.application_ports = self._application_ports
|
|
216
214
|
|
|
217
215
|
|
|
218
|
-
class ApplicationStatus(NuclioStatus):
|
|
216
|
+
class ApplicationStatus(nuclio_function.NuclioStatus):
|
|
219
217
|
def __init__(
|
|
220
218
|
self,
|
|
221
219
|
state=None,
|
|
@@ -245,15 +243,17 @@ class ApplicationStatus(NuclioStatus):
|
|
|
245
243
|
self.application_source = application_source or None
|
|
246
244
|
self.sidecar_name = sidecar_name or None
|
|
247
245
|
self.api_gateway_name = api_gateway_name or None
|
|
248
|
-
self.api_gateway: typing.Optional[APIGateway] =
|
|
246
|
+
self.api_gateway: typing.Optional[nuclio_api_gateway.APIGateway] = (
|
|
247
|
+
api_gateway or None
|
|
248
|
+
)
|
|
249
249
|
self.url = url or None
|
|
250
250
|
|
|
251
251
|
|
|
252
|
-
class ApplicationRuntime(RemoteRuntime):
|
|
252
|
+
class ApplicationRuntime(nuclio_function.RemoteRuntime):
|
|
253
253
|
kind = "application"
|
|
254
254
|
reverse_proxy_image = None
|
|
255
255
|
|
|
256
|
-
@min_nuclio_versions("1.13.1")
|
|
256
|
+
@nuclio_function.min_nuclio_versions("1.13.1")
|
|
257
257
|
def __init__(self, spec=None, metadata=None):
|
|
258
258
|
super().__init__(spec=spec, metadata=metadata)
|
|
259
259
|
|
|
@@ -278,7 +278,7 @@ class ApplicationRuntime(RemoteRuntime):
|
|
|
278
278
|
return self.status.api_gateway
|
|
279
279
|
|
|
280
280
|
@api_gateway.setter
|
|
281
|
-
def api_gateway(self, api_gateway: APIGateway):
|
|
281
|
+
def api_gateway(self, api_gateway: nuclio_api_gateway.APIGateway):
|
|
282
282
|
self.status.api_gateway = api_gateway
|
|
283
283
|
|
|
284
284
|
@property
|
|
@@ -294,6 +294,96 @@ class ApplicationRuntime(RemoteRuntime):
|
|
|
294
294
|
def set_internal_application_port(self, port: int):
|
|
295
295
|
self.spec.internal_application_port = port
|
|
296
296
|
|
|
297
|
+
def set_probe(
|
|
298
|
+
self,
|
|
299
|
+
type: str,
|
|
300
|
+
initial_delay_seconds: int | None = None,
|
|
301
|
+
period_seconds: int | None = None,
|
|
302
|
+
failure_threshold: int | None = None,
|
|
303
|
+
timeout_seconds: int | None = None,
|
|
304
|
+
http_path: str | None = None,
|
|
305
|
+
http_port: int | None = None,
|
|
306
|
+
http_scheme: str | None = None,
|
|
307
|
+
config: dict | None = None,
|
|
308
|
+
):
|
|
309
|
+
"""Set a Kubernetes probe configuration for the sidecar container
|
|
310
|
+
|
|
311
|
+
The config parameter serves as the base configuration, and individual parameters
|
|
312
|
+
override values in config. If http_path is provided without http_port and config
|
|
313
|
+
is not provided, the port will be enriched from the internal application port
|
|
314
|
+
just before deployment.
|
|
315
|
+
|
|
316
|
+
:param type: Probe type - one of "readiness", "liveness", "startup"
|
|
317
|
+
:param initial_delay_seconds: Number of seconds after the container has started before probes are initiated
|
|
318
|
+
:param period_seconds: How often (in seconds) to perform the probe
|
|
319
|
+
:param failure_threshold: Minimum consecutive failures for the probe to be considered failed
|
|
320
|
+
:param timeout_seconds: Number of seconds after which the probe times out
|
|
321
|
+
:param http_path: If provided, use an HTTP probe with this path
|
|
322
|
+
:param http_port: If HTTP probe is used and no port provided,
|
|
323
|
+
the internal application port will be used
|
|
324
|
+
:param http_scheme: "http" or "https" for HTTP probe. Defaults to "http"
|
|
325
|
+
:param config: A full dict with the probe configuration
|
|
326
|
+
(used as base, overridden by individual parameters)
|
|
327
|
+
|
|
328
|
+
:return: function object (self)
|
|
329
|
+
"""
|
|
330
|
+
self._validate_set_probes_input(locals())
|
|
331
|
+
type = ProbeType(type)
|
|
332
|
+
|
|
333
|
+
# Start with config as base
|
|
334
|
+
probe_config = copy.deepcopy(config) if config else {}
|
|
335
|
+
|
|
336
|
+
# Build HTTP probe configuration if http_path is provided
|
|
337
|
+
# Note: If http_path is None, all HTTP-related parameters (http_port, http_scheme) are ignored
|
|
338
|
+
if http_path:
|
|
339
|
+
http_probe = probe_config.get("httpGet", {})
|
|
340
|
+
http_probe["path"] = http_path
|
|
341
|
+
if http_port is not None:
|
|
342
|
+
http_probe["port"] = http_port
|
|
343
|
+
http_probe["scheme"] = http_scheme or http_probe.get("scheme", "HTTP")
|
|
344
|
+
probe_config["httpGet"] = http_probe
|
|
345
|
+
|
|
346
|
+
# Override timing parameters from explicit arguments
|
|
347
|
+
probe_config.update(
|
|
348
|
+
{
|
|
349
|
+
config.value: value
|
|
350
|
+
for config, value in {
|
|
351
|
+
ProbeTimeConfig.INITIAL_DELAY_SECONDS: initial_delay_seconds,
|
|
352
|
+
ProbeTimeConfig.PERIOD_SECONDS: period_seconds,
|
|
353
|
+
ProbeTimeConfig.FAILURE_THRESHOLD: failure_threshold,
|
|
354
|
+
ProbeTimeConfig.TIMEOUT_SECONDS: timeout_seconds,
|
|
355
|
+
}.items()
|
|
356
|
+
if value is not None
|
|
357
|
+
}
|
|
358
|
+
)
|
|
359
|
+
|
|
360
|
+
# Store probe configuration in the sidecar
|
|
361
|
+
sidecar = self._set_sidecar(self._get_sidecar_name())
|
|
362
|
+
sidecar[type.key] = probe_config
|
|
363
|
+
|
|
364
|
+
return self
|
|
365
|
+
|
|
366
|
+
def delete_probe(
|
|
367
|
+
self,
|
|
368
|
+
type: str,
|
|
369
|
+
):
|
|
370
|
+
"""Delete a Kubernetes probe configuration from the sidecar container
|
|
371
|
+
|
|
372
|
+
:param type: Probe type - one of "readiness", "liveness", "startup"
|
|
373
|
+
|
|
374
|
+
:return: function object (self)
|
|
375
|
+
"""
|
|
376
|
+
# Validate probe type
|
|
377
|
+
ProbeType.is_valid(type, raise_on_error=True)
|
|
378
|
+
type = ProbeType(type)
|
|
379
|
+
|
|
380
|
+
sidecar = self._get_sidecar()
|
|
381
|
+
if sidecar:
|
|
382
|
+
if type.key in sidecar:
|
|
383
|
+
del sidecar[type.key]
|
|
384
|
+
|
|
385
|
+
return self
|
|
386
|
+
|
|
297
387
|
def with_sidecar(
|
|
298
388
|
self,
|
|
299
389
|
name: typing.Optional[str] = None,
|
|
@@ -400,7 +490,6 @@ class ApplicationRuntime(RemoteRuntime):
|
|
|
400
490
|
|
|
401
491
|
:return: The default API gateway URL if created or True if the function is ready (deployed)
|
|
402
492
|
"""
|
|
403
|
-
mlrun.utils.helpers.validate_function_name(self.metadata.name)
|
|
404
493
|
|
|
405
494
|
if (self.requires_build() and not self.spec.image) or force_build:
|
|
406
495
|
self._fill_credentials()
|
|
@@ -422,6 +511,7 @@ class ApplicationRuntime(RemoteRuntime):
|
|
|
422
511
|
self.spec.add_templated_ingress_host_mode = (
|
|
423
512
|
NuclioIngressAddTemplatedIngressModes.never
|
|
424
513
|
)
|
|
514
|
+
self._enrich_sidecar_probe_ports()
|
|
425
515
|
|
|
426
516
|
super().deploy(
|
|
427
517
|
project=project,
|
|
@@ -569,23 +659,23 @@ class ApplicationRuntime(RemoteRuntime):
|
|
|
569
659
|
"Authentication credentials not provided"
|
|
570
660
|
)
|
|
571
661
|
|
|
572
|
-
if direct_port_access and port:
|
|
662
|
+
if not direct_port_access and port:
|
|
573
663
|
logger.warning(
|
|
574
|
-
"Ignoring 'port' because 'direct_port_access' is enabled. "
|
|
575
|
-
"The 'port' setting is only applicable when 'direct_port_access' is
|
|
664
|
+
"Ignoring 'port' because 'direct_port_access' is not enabled. "
|
|
665
|
+
"The 'port' setting is only applicable when 'direct_port_access' is enabled."
|
|
576
666
|
)
|
|
577
667
|
|
|
578
668
|
ports = (
|
|
579
669
|
port or self.spec.internal_application_port if direct_port_access else []
|
|
580
670
|
)
|
|
581
671
|
|
|
582
|
-
api_gateway = APIGateway(
|
|
583
|
-
APIGatewayMetadata(
|
|
672
|
+
api_gateway = nuclio_api_gateway.APIGateway(
|
|
673
|
+
nuclio_api_gateway.APIGatewayMetadata(
|
|
584
674
|
name=name,
|
|
585
675
|
namespace=self.metadata.namespace,
|
|
586
676
|
labels=self.metadata.labels.copy(),
|
|
587
677
|
),
|
|
588
|
-
APIGatewaySpec(
|
|
678
|
+
nuclio_api_gateway.APIGatewaySpec(
|
|
589
679
|
functions=[self],
|
|
590
680
|
project=self.metadata.project,
|
|
591
681
|
path=path,
|
|
@@ -609,6 +699,8 @@ class ApplicationRuntime(RemoteRuntime):
|
|
|
609
699
|
api_gateway.with_access_key_auth()
|
|
610
700
|
elif authentication_mode == schemas.APIGatewayAuthenticationMode.basic:
|
|
611
701
|
api_gateway.with_basic_auth(*authentication_creds)
|
|
702
|
+
elif authentication_mode == schemas.APIGatewayAuthenticationMode.iguazio:
|
|
703
|
+
api_gateway.with_iguazio_auth()
|
|
612
704
|
|
|
613
705
|
db = self._get_db()
|
|
614
706
|
api_gateway_scheme = db.store_api_gateway(
|
|
@@ -617,12 +709,14 @@ class ApplicationRuntime(RemoteRuntime):
|
|
|
617
709
|
|
|
618
710
|
if set_as_default:
|
|
619
711
|
self.status.api_gateway_name = api_gateway_scheme.metadata.name
|
|
620
|
-
self.status.api_gateway = APIGateway.from_scheme(
|
|
712
|
+
self.status.api_gateway = nuclio_api_gateway.APIGateway.from_scheme(
|
|
713
|
+
api_gateway_scheme
|
|
714
|
+
)
|
|
621
715
|
self.status.api_gateway.wait_for_readiness()
|
|
622
716
|
self.url = self.status.api_gateway.invoke_url
|
|
623
717
|
url = self.url
|
|
624
718
|
else:
|
|
625
|
-
api_gateway = APIGateway.from_scheme(api_gateway_scheme)
|
|
719
|
+
api_gateway = nuclio_api_gateway.APIGateway.from_scheme(api_gateway_scheme)
|
|
626
720
|
api_gateway.wait_for_readiness()
|
|
627
721
|
url = api_gateway.invoke_url
|
|
628
722
|
# Update application status (enriches invocation url)
|
|
@@ -646,7 +740,7 @@ class ApplicationRuntime(RemoteRuntime):
|
|
|
646
740
|
def invoke(
|
|
647
741
|
self,
|
|
648
742
|
path: str = "",
|
|
649
|
-
body: typing.Optional[typing.Union[str, bytes, dict]] = None,
|
|
743
|
+
body: typing.Optional[typing.Union[str, bytes, dict, list]] = None,
|
|
650
744
|
method: typing.Optional[str] = None,
|
|
651
745
|
headers: typing.Optional[dict] = None,
|
|
652
746
|
force_external_address: bool = False,
|
|
@@ -740,7 +834,7 @@ class ApplicationRuntime(RemoteRuntime):
|
|
|
740
834
|
else self.metadata.name
|
|
741
835
|
)
|
|
742
836
|
|
|
743
|
-
@min_nuclio_versions("1.13.1")
|
|
837
|
+
@nuclio_function.min_nuclio_versions("1.13.1")
|
|
744
838
|
def disable_default_http_trigger(
|
|
745
839
|
self,
|
|
746
840
|
):
|
|
@@ -748,7 +842,7 @@ class ApplicationRuntime(RemoteRuntime):
|
|
|
748
842
|
"Application runtime does not support disabling the default HTTP trigger"
|
|
749
843
|
)
|
|
750
844
|
|
|
751
|
-
@min_nuclio_versions("1.13.1")
|
|
845
|
+
@nuclio_function.min_nuclio_versions("1.13.1")
|
|
752
846
|
def enable_default_http_trigger(
|
|
753
847
|
self,
|
|
754
848
|
):
|
|
@@ -879,6 +973,80 @@ class ApplicationRuntime(RemoteRuntime):
|
|
|
879
973
|
api_gateway_scheme = db.get_api_gateway(
|
|
880
974
|
name=self.status.api_gateway_name, project=self.metadata.project
|
|
881
975
|
)
|
|
882
|
-
self.status.api_gateway = APIGateway.from_scheme(
|
|
976
|
+
self.status.api_gateway = nuclio_api_gateway.APIGateway.from_scheme(
|
|
977
|
+
api_gateway_scheme
|
|
978
|
+
)
|
|
883
979
|
self.status.api_gateway.wait_for_readiness()
|
|
884
980
|
self.url = self.status.api_gateway.invoke_url
|
|
981
|
+
|
|
982
|
+
def _enrich_sidecar_probe_ports(self):
|
|
983
|
+
"""Enrich sidecar probe configurations with internal application port if needed
|
|
984
|
+
|
|
985
|
+
This method is called just before deployment to automatically enrich HTTP probes
|
|
986
|
+
in the sidecar container that were configured without an explicit port.
|
|
987
|
+
|
|
988
|
+
Enrichment logic:
|
|
989
|
+
- Only enriches HTTP probes (httpGet) that don't already have a port specified
|
|
990
|
+
- If the user explicitly provided http_port in set_probe(), enrichment is skipped
|
|
991
|
+
- If the user provided a port in the config dict, enrichment is skipped
|
|
992
|
+
- Enrichment happens just before deployment to ensure the latest internal_application_port
|
|
993
|
+
value is used, even if it was modified after set_probe() was called
|
|
994
|
+
"""
|
|
995
|
+
# Check each probe type and enrich missing HTTP ports
|
|
996
|
+
sidecar = self._get_sidecar()
|
|
997
|
+
if not sidecar:
|
|
998
|
+
return
|
|
999
|
+
|
|
1000
|
+
for probe_type in ProbeType:
|
|
1001
|
+
probe_config = sidecar.get(probe_type.key)
|
|
1002
|
+
|
|
1003
|
+
if probe_config and isinstance(probe_config, dict):
|
|
1004
|
+
http_get = probe_config.get("httpGet")
|
|
1005
|
+
if http_get and isinstance(http_get, dict) and "port" not in http_get:
|
|
1006
|
+
if self.spec.internal_application_port is None:
|
|
1007
|
+
raise ValueError(
|
|
1008
|
+
f"Cannot enrich {probe_type.value} probe: HTTP probe requires a port, "
|
|
1009
|
+
"but internal_application_port is not set. "
|
|
1010
|
+
"Please set the internal_application_port or provide http_port in set_probe()."
|
|
1011
|
+
)
|
|
1012
|
+
http_get["port"] = self.spec.internal_application_port
|
|
1013
|
+
logger.debug(
|
|
1014
|
+
"Enriched sidecar probe port",
|
|
1015
|
+
probe_type=probe_type.value,
|
|
1016
|
+
port=http_get["port"],
|
|
1017
|
+
application_name=self.metadata.name,
|
|
1018
|
+
)
|
|
1019
|
+
sidecar[probe_type.key] = probe_config
|
|
1020
|
+
|
|
1021
|
+
def _get_sidecar(self) -> dict | None:
|
|
1022
|
+
"""Get the sidecar container for ApplicationRuntime
|
|
1023
|
+
|
|
1024
|
+
Returns the sidecar dict if found, None otherwise.
|
|
1025
|
+
"""
|
|
1026
|
+
sidecar_name = self._get_sidecar_name()
|
|
1027
|
+
if not hasattr(self.spec, "config") or "spec.sidecars" not in self.spec.config:
|
|
1028
|
+
return None
|
|
1029
|
+
|
|
1030
|
+
sidecars = self.spec.config["spec.sidecars"]
|
|
1031
|
+
for sidecar in sidecars:
|
|
1032
|
+
if sidecar.get("name") == sidecar_name:
|
|
1033
|
+
return sidecar
|
|
1034
|
+
|
|
1035
|
+
return None
|
|
1036
|
+
|
|
1037
|
+
def _get_sidecar_name(self) -> str:
|
|
1038
|
+
return f"{self.metadata.name}-sidecar"
|
|
1039
|
+
|
|
1040
|
+
@staticmethod
|
|
1041
|
+
def _validate_set_probes_input(params: dict):
|
|
1042
|
+
# Validate probe type
|
|
1043
|
+
ProbeType.is_valid(params.get("type"), raise_on_error=True)
|
|
1044
|
+
|
|
1045
|
+
# At least one optional parameter must be provided
|
|
1046
|
+
optional_params = {
|
|
1047
|
+
k: v for k, v in params.items() if (k != "type" and k != "self")
|
|
1048
|
+
}
|
|
1049
|
+
if all(v is None for v in optional_params.values()):
|
|
1050
|
+
raise ValueError(
|
|
1051
|
+
"Empty probe configuration: at least one parameter must be set"
|
|
1052
|
+
)
|