# Azure ML Pipelines - Orchestration and Automation

**Last updated:** 2026-04
**Verified:** MCP 2026-04
**Status:** GA
**Category:** MLOps & GenAIOps

---

**Verified:** MCP 2026-04

## Introduksjon

Azure Machine Learning pipelines representerer et komplett orkestreringsrammeverk for machine learning-arbeidsflyter. En pipeline automatiserer en komplett ML-oppgave ved å dele den inn i flere håndterbare steg (components), hvor hvert steg kan utvikles, optimaliseres, konfigureres og automatiseres uavhengig. Azure ML håndterer dependencies mellom steg automatisk, og legger til rette for parallellisering, caching og gjenbruk.

Pipelines standardiserer MLOps-praksis ved å mappe hvert steg til en spesifikk oppgave, slik at team kan jobbe uavhengig på sine områder. Data engineers, data scientists og ML engineers kan hver eie sine pipeline-komponenter. Disse bygges best som reusable components, og integreres deretter i en enkelt workflow. Pipelines kan versjoneres, automatiseres og standardiseres gjennom DevOps-praksis.

Fra et kostnads- og effektivitetsperspektiv gir pipelines betydelige fordeler: de gjenbruker outputs fra uendrede steg, og lar deg kjøre hvert steg på den mest optimale compute-ressursen for oppgaven. Dette reduserer både tidsbruk og kostnader sammenlignet med å kjøre hele workflows fra scratch ved hver endring.

## Kjernekomponenter / Nøkkelegenskaper

### Pipeline Components (v2)


### Azure ML Pipelines — Python SDK v2 (Tutorial, Verified MCP 2026-04)

**Key benefits**: Standardized MLOps practice, scalable team collaboration, training efficiency, cost reduction.

**Pipeline creation pattern** (SDK v2 — from official tutorial):
```python
from azure.ai.ml import MLClient, dsl, Input, Output, command
from azure.identity import DefaultAzureCredential, InteractiveBrowserCredential

try:
    credential = DefaultAzureCredential()
    credential.get_token("https://management.azure.com/.default")
except Exception:
    credential = InteractiveBrowserCredential()

ml_client = MLClient(credential, subscription_id, resource_group, workspace)
# Note: MLClient initialization is lazy — no connection until first call

# 1. Create reusable components (programmatic definition)
data_prep_component = command(
    name="data_prep_credit_defaults",
    inputs={"data": Input(type="uri_folder"), "test_train_ratio": Input(type="number")},
    outputs={"train_data": Output(type="uri_folder", mode="rw_mount"),
             "test_data": Output(type="uri_folder", mode="rw_mount")},
    code="./components/data_prep",
    command="python data_prep.py --data ${{inputs.data}} --test_train_ratio ${{inputs.test_train_ratio}} ...",
    environment=f"{pipeline_job_env.name}:{pipeline_job_env.version}",
)
# Register for reuse
data_prep_component = ml_client.create_or_update(data_prep_component.component)

# 2. Define pipeline with @dsl.pipeline decorator
@dsl.pipeline(
    compute="serverless",  # "serverless" runs on serverless compute
    description="E2E data_prep-train pipeline",
)
def credit_defaults_pipeline(data_input, test_train_ratio, learning_rate, registered_model_name):
    prep_job = data_prep_component(data=data_input, test_train_ratio=test_train_ratio)
    train_job = train_component(
        train_data=prep_job.outputs.train_data,
        test_data=prep_job.outputs.test_data,
        learning_rate=learning_rate,
        registered_model_name=registered_model_name,
    )
    return {
        "pipeline_job_train_data": prep_job.outputs.train_data,
        "pipeline_job_test_data": prep_job.outputs.test_data,
    }

# 3. Submit pipeline
pipeline_job = ml_client.jobs.create_or_update(
    credit_defaults_pipeline(
        data_input=Input(type="uri_file", path=credit_data.path),
        test_train_ratio=0.25,
        learning_rate=0.05,
        registered_model_name="credit_defaults_model",
    ),
    experiment_name="e2e_registered_components"
)
ml_client.jobs.stream(pipeline_job.name)
```

**Component lifecycle**:
1. Write YAML spec (`train.yml`) or create programmatically (`CommandComponent` / `command()`)
2. Register with name+version: `ml_client.create_or_update(component)`
3. Load and compose into pipeline using `@dsl.pipeline` decorator
4. Submit via `ml_client.jobs.create_or_update()` with experiment name

**Compute options**: `serverless` (recommended — zero config), named compute cluster, or per-step compute override (e.g., `train_step.compute = "cpu-cluster"`).
**Environment**: Curated environments (`azureml://registries/azureml/environments/sklearn-1.0/labels/latest`) or custom conda/Docker (base image: `mcr.microsoft.com/azureml/openmpi4.1.0-ubuntu22.04:latest`).
**Output types**: `uri_folder` (data), `mlflow_model` (model), `uri_file` (file).

**MLflow integration**: Use `mlflow.start_run()` + `mlflow.sklearn.autolog()` in training scripts for automatic experiment tracking. Models registered via `mlflow.sklearn.log_model()` with `registered_model_name`.

**VNet note**: If workspace uses a managed virtual network, add outbound rules to allow access to public Python package repositories.

| Komponent-type | Beskrivelse | Bruksområde |
|----------------|-------------|-------------|
| **Command component** | Kjører et shell-script eller Python-script | Data prep, training, scoring, evaluation |
| **Pipeline component** | Multistep-komponent som inneholder flere sub-steps | Reusable sub-workflows, modulær arkitektur |
| **Parallel component** | Kjører batch-prosessering på partisjonert data | Store datasett, inferens i skala |
| **Spark component** | Kjører PySpark-kode på Spark clusters | Stordata-transformasjon, feature engineering |
| **AutoML component** | AutoML training-node | Automatisert modelltrening med hyperparameter-tuning |

### Pipeline Inputs og Outputs

| Type | Input/Output | Eksempel | Persistering |
|------|--------------|----------|--------------|
| **uri_file** | Single file | CSV, JSON, Parquet | Azure Storage (blob, datalake) |
| **uri_folder** | Folder/directory | Datasett, modell-artifacts | Azure Storage |
| **mlflow_model** | MLflow model format | Trained model | Azure ML Model Registry |
| **Literal inputs** | String, int, float, bool | Hyperparameters, config values | Passing som pipeline parameters |

### Scheduling Mekanismer

| Schedule-type | Trigger | Bruksområde | Eksempel |
|---------------|---------|-------------|----------|
| **Recurrence** | Tid-basert (minute, hour, day, week, month) | Regelmessig retraining, batch predictions | Daglig kl 04:00 UTC |
| **Cron expression** | Avansert tid-basert (crontab) | Fleksible mønstre | `15 10 * * 1` (hver mandag kl 10:15) |
| **Event-driven** (v1 only) | Blob storage change | Dataoppdateringer trigger pipeline | Ny fil i datastore |

**Merk:** V2 schedules støtter ikke event-driven triggers. For event-based orchestration, vurder Azure Data Factory eller Logic Apps som trigger for batch endpoints.

### Compute Targets

| Compute-type | Egenskaper | Best for | Kostnadsprofil |
|--------------|------------|----------|----------------|
| **Compute clusters** | Auto-scaling, multi-node | Training, parallel jobs | Betaler for aktiv bruk |
| **Compute instances** | Single VM, alltid-på | Development, interactive | Betaler 24/7 (med auto-shutdown) |
| **Serverless compute** | Zero-config, on-demand | Enkel start, prototyping | Betaler per sekund |
| **Kubernetes** | AKS-integrert | Enterprise, hybrid cloud | Mer kompleks, men fleksibel |

### Data Modes

| Mode | Beskrivelse | Latency | Bruksområde |
|------|-------------|---------|-------------|
| **ro_mount** | Read-only mount (default) | Lav latency, streaming | Store datasett, training |
| **rw_mount** | Read-write mount | Lav latency | Mellomlagring av resultater |
| **download** | Download full datasett | Høy initial latency | Små datasett, caching |
| **direct** | Direct access (Spark) | Minimal overhead | Stordata, Spark-jobs |
| **upload** | Upload output etter job | Ingen latency under job | Finale resultater, modeller |

## Arkitekturmønstre

### 1. Simple Sequential Pipeline

**Pattern:** Lineær data-flow med avhengigheter mellom steg.

```
[Data Prep] → [Feature Engineering] → [Training] → [Evaluation] → [Registration]
```

**Når bruke:**
- Standard ML-workflows med klar sekvensiell logikk
- Retraining pipelines
- Enkel batch inference

**Eksempel SDK v2:**
```python
@pipeline()
def sequential_train_pipeline(raw_data, learning_rate):
    prep_step = data_prep_component(data=raw_data)
    train_step = train_component(
        train_data=prep_step.outputs.train_data,
        learning_rate=learning_rate
    )
    eval_step = eval_component(
        model=train_step.outputs.model,
        test_data=prep_step.outputs.test_data
    )
    return {
        "model": train_step.outputs.model,
        "metrics": eval_step.outputs.metrics
    }
```

**Trade-offs:**
- ✅ Enkelt å forstå og debugge
- ✅ Deterministisk execution order
- ❌ Ikke optimal for parallelle tasks
- ❌ Blokkering hvis ett steg feiler

### 2. Parallel Component Pipeline

**Pattern:** Parallellisering av uavhengige steg for å redusere total kjøretid.

```
                    ┌─→ [Feature Set A] ─┐
[Data Prep] ────────┼─→ [Feature Set B] ─┼─→ [Merge] → [Training]
                    └─→ [Feature Set C] ─┘
```

**Når bruke:**
- Feature engineering fra flere kilder
- Ensemble-modeller med separate training paths
- A/B-testing av ulike preprocessing-strategier

**Eksempel SDK v2:**
```python
@pipeline()
def parallel_feature_pipeline(raw_data):
    prep_step = data_prep_component(data=raw_data)

    # Parallelle feature engineering steps
    features_a = feature_set_a_component(data=prep_step.outputs.clean_data)
    features_b = feature_set_b_component(data=prep_step.outputs.clean_data)
    features_c = feature_set_c_component(data=prep_step.outputs.clean_data)

    # Merge og tren
    merged = merge_component(
        set_a=features_a.outputs.features,
        set_b=features_b.outputs.features,
        set_c=features_c.outputs.features
    )
    train_step = train_component(features=merged.outputs.combined)
    return {"model": train_step.outputs.model}
```

**Trade-offs:**
- ✅ Betydelig tidsbesparelse (parallell execution)
- ✅ Isolerer failures (ett steg kan feile uten å påvirke andre)
- ❌ Mer kompleks orchestration-logikk
- ❌ Krever flere compute-ressurser samtidig

### 3. Event-Driven Pipeline (v1) eller Batch Endpoint Pattern (v2)

**Pattern:** Pipeline trigges automatisk ved datahendelser eller på schedule.

**V1 (deprecated):**
- Change-based schedules på blob storage
- Pipeline startes automatisk ved nye filer

**V2 (anbefalt):**
- Batch Endpoint med pipeline component deployment
- Azure Data Factory eller Logic Apps trigger batch invocation
- Schedule-based execution (recurrence/cron)

**Når bruke:**
- Kontinuerlig retraining når nye data ankommer
- Batch inference på schedule (daglig predictions)
- Event-driven MLOps (CI/CD trigger)

**Eksempel schedule (v2 CLI):**
```yaml
$schema: https://azuremlschemas.azureedge.net/latest/schedule.schema.json
name: daily_retrain_schedule
trigger:
  type: recurrence
  frequency: day
  interval: 1
  schedule:
    hours: [4]
    minutes: [0]
  time_zone: "UTC"
create_job: ./retrain-pipeline.yml
```

**Batch Endpoint Pattern:**
```python
# Deploy pipeline som batch endpoint
from azure.ai.ml.entities import BatchEndpoint, PipelineComponentBatchDeployment

endpoint = BatchEndpoint(name="retrain-endpoint")
deployment = PipelineComponentBatchDeployment(
    name="retrain-deployment",
    endpoint_name="retrain-endpoint",
    component=retrain_pipeline_component
)
ml_client.batch_endpoints.begin_create_or_update(endpoint).result()
ml_client.batch_deployments.begin_create_or_update(deployment).result()

# Invoke fra Azure Data Factory eller Logic Apps
job = ml_client.batch_endpoints.invoke(
    endpoint_name="retrain-endpoint",
    inputs={"new_data": Input(path="azureml://datastores/workspaceblobstore/paths/latest/")}
)
```

**Trade-offs:**
- ✅ Automatisering reduserer manuelt arbeid
- ✅ Raskere time-to-production for nye modeller
- ✅ Konsekvent kjøring på planlagt tidspunkt
- ❌ Krever ekstra infrastruktur (Logic Apps, schedules)
- ❌ Debugging av triggered jobs kan være mer komplekst

## Beslutningsveiledning

### Når bruke Pipeline Components vs. Standalone Jobs

| Scenario | Anbefaling | Begrunnelse |
|----------|------------|-------------|
| **Enkelt eksperiment** | Standalone job | Raskere å sette opp, mindre overhead |
| **Gjenbrukbar workflow** | Pipeline | Versjonering, deling, standardisering |
| **Team collaboration** | Pipeline med components | Modularitet, parallel utvikling |
| **Production MLOps** | Pipeline + batch endpoint | Durable API, scheduling, monitoring |

### Compute Target Valg

| Workload | Anbefalt Compute | Configurasjon |
|----------|------------------|---------------|
| **Data prep (CPU)** | Serverless eller compute cluster | Standard_DS3_v2, auto-scale 0-4 nodes |
| **Training (GPU)** | Compute cluster med GPU | Standard_NC6s_v3, auto-scale 0-2 nodes |
| **Batch inference** | Compute cluster (CPU) | Standard_D8s_v3, auto-scale basert på queue |
| **Development** | Compute instance | Standard_DS3_v2 med auto-shutdown |
| **Spark-jobs** | Synapse Spark eller Kubernetes | Avhenger av data volume |

### Pipeline vs. Azure Data Factory vs. Kubeflow

| Kriterium | Azure ML Pipeline | Azure Data Factory | Kubeflow Pipelines |
|-----------|-------------------|---------------------|---------------------|
| **Bruksområde** | ML-spesifikk orchestration | Data engineering pipelines | OSS ML orchestration |
| **Integrasjon** | Native Azure ML | Multi-service orchestration | Kubernetes-native |
| **Caching** | ✅ Step-level caching | ❌ Ingen ML-caching | ✅ Med tilleggskonfig |
| **Code-first** | ✅ Python SDK, CLI | ⚠️ Hybrid (GUI + JSON) | ✅ Python SDK |
| **ML-spesifikke features** | Model registry, datasets, experiments | ❌ Generell data orchestration | Model serving, metadata tracking |
| **Best for** | End-to-end ML workflows | ETL + ML pipeline trigger | Multi-cloud ML, K8s-miljø |

### Vanlige Feil

| Feil | Symptom | Løsning |
|------|---------|---------|
| **Pipeline re-runs all steps** | Caching fungerer ikke | Sjekk at `force_rerun=False` og at inputs ikke endres |
| **Out of memory i step** | Job crashes med OOM | Øk compute-størrelse, reduser batch size, bruk `ro_mount` mode |
| **Slow pipeline start** | Lange kø-tider | Bruk serverless compute eller øk `max_instances` på cluster |
| **Output ikke tilgjengelig** | Neste step finner ikke data | Sjekk `mode` (må være `upload` eller `rw_mount` for persistering) |
| **Schedule ikke trigger** | Job kjører aldri | Verifiser `is_enabled=True`, sjekk `start_time` og `time_zone` |
| **Permission denied** | Job kan ikke lese/skrive data | Verifiser identity-konfigurasjon (ManagedIdentity eller AmlToken) |

### Røde Flagg (Anti-patterns)

- ❌ **Monolittiske pipelines:** Alle steg i én stor komponent → splitt i reusable components
- ❌ **Hard-coded paths:** Paths uten parameterisering → bruk pipeline inputs
- ❌ **No output registration:** Output lagres men ikke registreres → bruk `name` og `version` på outputs
- ❌ **Ignore caching:** Setter alltid `force_rerun=True` → la caching optimalisere re-runs
- ❌ **Overly complex parallel steps:** For mange parallelle steg → vurder compute capacity

## Integrasjon med Microsoft-stakken

### Azure ML Workspace

- **Experiments:** Alle pipeline-kjøringer grouperes under experiments for tracking
- **Model Registry:** Outputs kan registreres direkte som modeller (`type: mlflow_model`)
- **Datasets:** Pipeline inputs kan referere til registrerte datasett (versjonering)
- **Compute:** Pipelines kjører på workspace compute targets
- **Datastores:** Default-datastore for outputs (workspaceblobstore)

### Azure DevOps / GitHub Actions

**Pattern:** CI/CD for pipeline deployment

```yaml
# GitHub Actions example
- name: Deploy ML Pipeline
  run: |
    az ml job create --file pipeline.yml --resource-group $RG --workspace-name $WORKSPACE
```

**Bruksområde:**
- Automatisk deploy av pipeline-definisjoner ved commit
- Trigger pipeline-kjøring fra PR merge
- Valider pipeline syntax i CI

### Azure Data Factory

**Pattern:** ADF som orchestrator, Azure ML som executor

```json
{
  "name": "ExecuteMLPipeline",
  "type": "AzureMLExecutePipeline",
  "linkedServiceName": "AzureMLService",
  "typeProperties": {
    "mlPipelineEndpointId": "/subscriptions/.../batchEndpoints/my-endpoint"
  }
}
```

**Bruksområde:**
- Integrere ML-pipelines i bredere ETL-workflows
- Trigger ML-pipeline etter data-ingestion
- Koordinere ML + data engineering pipelines

### Azure Event Grid

**Pattern:** Event-driven triggering

- Blob storage event → Logic App → Batch Endpoint invocation
- Bruk for nær-sanntids retraining ved dataoppdateringer

### Microsoft Fabric

**Pattern:** Fabric Notebook → Batch Endpoint

- Kjør Azure ML batch inference fra Fabric
- Integrer ML-modeller i Fabric data workflows
- Preview-funksjonalitet per feb 2026

### Azure Monitor & Application Insights

- **Pipeline metrics:** Duration, success rate, step-level metrics
- **Custom logging:** Log metrics fra components til Application Insights
- **Alerts:** Sett opp alerts på pipeline failures

## Offentlig sektor (Norge)

### Compliance og Datasuverenitet

| Krav | Implementasjon | Verifisering |
|------|----------------|--------------|
| **Data residency** | Azure regions: Norway East/West | Sjekk workspace region + datastore locations |
| **Audit logging** | Azure Monitor Logs for all pipeline executions | Aktivér diagnostics settings på workspace |
| **GDPR-compliance** | Data minimization i pipelines | Anonymiser/pseudonymiser i prep-steps |
| **Access control** | RBAC på pipeline schedules og endpoints | Begrenset `write`-tilgang til schedules |

### RBAC for Pipelines og Schedules

| Rolle | Tilgang | Bruksområde |
|-------|---------|-------------|
| **Data Scientist** | Read/Write jobs, read schedules | Utvikle og teste pipelines |
| **ML Engineer** | Write schedules, deploy batch endpoints | Produksjonssette pipelines |
| **Auditor** | Read jobs, read schedules | Compliance-sjekker |

**RBAC Actions:**
- `Microsoft.MachineLearningServices/workspaces/schedules/read`
- `Microsoft.MachineLearningServices/workspaces/schedules/write`
- `Microsoft.MachineLearningServices/workspaces/schedules/delete`

### Revisjonslogging

**Best practice:**
- Aktiver diagnostics settings på workspace level
- Send logs til Log Analytics Workspace (Norge-region)
- Behold logs i minimum 90 dager (ofte lovkrav)

**Query eksempel (KQL):**
```kusto
AzureDiagnostics
| where ResourceProvider == "MICROSOFT.MACHINELEARNINGSERVICES"
| where OperationName contains "Pipeline"
| project TimeGenerated, OperationName, CallerIdentity, ResultType
```

### Klassifisering og Beskyttelse

- **Begrenset (offentlig):** Standard pipelines, ingen ekstra tiltak
- **Konfidensielt:** Pipelines med PII → bruk private endpoints, disable public access
- **Strengt konfidensielt:** Ikke anbefalt i Azure ML (vurder on-prem)

## Kostnad og lisensiering

### Kostnadsdrivere

| Komponent | Fakturering | Estimert kostnad (NOK/måned) | Optimaliseringstips |
|-----------|-------------|-------------------------------|---------------------|
| **Compute clusters** | Per sekund, per node | 5 000-50 000 (avhenger av VM-type) | Auto-scale min=0, bruk serverless for dev |
| **Schedules** | Per schedule (Logic Apps HOBO) | ~100 per schedule | Begrenset antall schedules, bruk cron for multi-trigger |
| **Storage (outputs)** | Per GB (blob storage) | 50-500 (avhenger av data volume) | Slett gamle pipeline outputs, bruk lifecycle policies |
| **Pipeline runs** | Ingen direkte kostnad | Gratis (betaler for compute/storage) | N/A |
| **Batch endpoints** | Ingen deployment-kostnad | Gratis (betaler for invocation compute) | N/A |

### Kostnadsestimat for Typiske Scenarios

**Scenario 1: Daglig retraining pipeline**
- Schedule: 1x daglig, 30 kjøringer/måned
- Compute: Standard_NC6s_v3 (GPU), 2 timer/kjøring
- Storage: 50 GB outputs
- **Totalt:** ~12 000 NOK/måned

**Scenario 2: Batch inference pipeline**
- Schedule: 4x daglig, 120 kjøringer/måned
- Compute: Standard_D8s_v3 (CPU), 30 min/kjøring
- Storage: 100 GB outputs
- **Totalt:** ~8 000 NOK/måned

**Scenario 3: Development pipelines (no schedule)**
- Ad-hoc kjøringer: ~20/måned
- Compute: Serverless
- Storage: 10 GB outputs
- **Totalt:** ~1 500 NOK/måned

### Optimaliseringsstrategier

1. **Caching:** Re-bruk outputs fra uendrede steg (kan redusere compute med 30-70%)
2. **Serverless compute:** Bruk for dev/test → ingen idle-time costs
3. **Auto-scaling:** Sett `min_instances=0` på compute clusters
4. **Storage lifecycle policies:** Slett gamle pipeline outputs etter 30/90 dager
5. **Spot instances:** Bruk low-priority VMs for ikke-kritiske pipelines (opptil 80% rabatt)

### Lisensiering

- **Azure ML workspace:** Gratis (betaler for underliggende ressurser)
- **Azure ML SDK/CLI:** Gratis, open source
- **Logic Apps (for schedules):** HOBO-model, fakturert via workspace

## For arkitekten (Cosmo)

### Spørsmål å stille kunden

1. **Workflow-kompleksitet:** "Hvor mange steg har deres ML-workflow? Er det klare avhengigheter mellom steg?"
   - Hvis <3 steg: Vurder om pipeline er overkill (standalone jobs kan holde)
   - Hvis >5 steg: Pipeline er definitivt riktig valg

2. **Retraining-frekvens:** "Hvor ofte trenger modellen retraining? Trigges det av data-events eller schedule?"
   - Daglig/ukentlig: Recurrence schedule
   - Ved nye data: Event-driven pattern (Batch Endpoint + Logic Apps)
   - Ad-hoc: Ingen schedule, manual trigger

3. **Team-struktur:** "Jobber flere team på samme ML-workflow? Hvem eier hvert steg?"
   - Multi-team: Bruk pipeline components for modularitet
   - Single team: Kan vurdere enklere struktur

4. **Compute-krav:** "Hvilke compute-ressurser trengs for hvert steg? GPU for training?"
   - Heterogene krav: Pipeline med ulike compute per step
   - Homogene krav: Default compute for hele pipeline

5. **Produksjonsmodning:** "Er dette for utvikling, testing eller produksjon?"
   - Dev: Serverless compute, ad-hoc kjøring
   - Prod: Compute clusters, schedules, batch endpoints

6. **Data volume:** "Hvor stort er datasettet? Kreves parallellisering?"
   - <10 GB: Standard sequential pipeline
   - 10-100 GB: Vurder parallel components
   - >100 GB: Parallel components med Spark-integrasjon

7. **Compliance:** "Er det krav til audit-logging, data residency eller tilgangskontroll?"
   - Ja: Aktiver diagnostics, bruk RBAC, deploy i Norge-region

8. **Kostnadsbudsjett:** "Hva er månedlig budsjett for compute og storage?"
   - Begrenset: Serverless, caching, auto-scaling
   - Fleksibelt: Dedikerte clusters for ytelse

### Fallgruver å unngå

1. **Over-engineering:** Ikke lag pipeline for en 2-stegs workflow → bruk standalone jobs
2. **Under-engineering:** Ikke kjør manuelt hver gang → sett opp schedule for prod
3. **Ignorer caching:** Pipeline re-runs alt selv om ingen inputs endret → aktiver caching
4. **Hard-coded secrets:** API keys i component-kode → bruk Key Vault references
5. **No monitoring:** Pipeline feiler stille → sett opp alerts i Azure Monitor
6. **Overly complex schedules:** 10+ schedules for samme pipeline → bruk én schedule med parameterisering
7. **No versioning:** Pipeline-definisjoner ikke versjonskontrollert → bruk Git + CI/CD

### Anbefalinger per modenhetsnivå

**Nivå 1: Ad-hoc (Low maturity)**
- ✅ Start med standalone command jobs
- ✅ Bruk serverless compute for eksperimentering
- ✅ Manuell kjøring, ingen schedules
- ⏭️ Når klar: Wrap i pipeline for gjenbruk

**Nivå 2: Strukturert (Medium maturity)**
- ✅ Pipeline med 3-5 components
- ✅ Compute clusters med auto-scaling
- ✅ Schedule for daglig/ukentlig retraining
- ✅ Basis monitoring (alerts på failures)
- ⏭️ Når klar: Batch endpoints for durable API

**Nivå 3: Industrialisert (High maturity)**
- ✅ Pipeline component library (reusable)
- ✅ Batch endpoints med versjonering
- ✅ CI/CD for pipeline deployment
- ✅ Event-driven orchestration (Logic Apps/ADF)
- ✅ Avansert monitoring (custom metrics, dashboards)
- ✅ Cost optimization (caching, spot instances)

### Quick Decision Tree

```
Er det >3 steg i workflow?
├─ Nei → Vurder standalone job
└─ Ja → Bruk pipeline
    └─ Trengs det scheduling?
        ├─ Nei → Ad-hoc pipeline
        └─ Ja → Bruk recurrence/cron schedule
            └─ Trengs det durable API?
                ├─ Nei → Schedule alene
                └─ Ja → Deploy som Batch Endpoint
```

## Kilder og verifisering

### Microsoft Learn Documentation (Verified)

1. **What are Azure Machine Learning pipelines?**
   https://learn.microsoft.com/en-us/azure/machine-learning/concept-ml-pipelines?view=azureml-api-2
   *Confidence: Verified (April 2026)*

2. **Schedule machine learning pipeline jobs**
   https://learn.microsoft.com/en-us/azure/machine-learning/how-to-schedule-pipeline-job?view=azureml-api-2
   *Confidence: Verified (April 2026)*

3. **Create and run machine learning pipelines using components with the Azure Machine Learning SDK v2**
   https://learn.microsoft.com/en-us/azure/machine-learning/how-to-create-component-pipeline-python?view=azureml-api-2
   *Confidence: Verified (April 2026)*

4. **Tutorial: Create production machine learning pipelines**
   https://learn.microsoft.com/en-us/azure/machine-learning/tutorial-pipeline-python-sdk?view=azureml-api-2
   *Confidence: Verified (April 2026)*

5. **Use parallel jobs in pipelines**
   https://learn.microsoft.com/en-us/azure/machine-learning/how-to-use-parallel-job-in-pipeline?view=azureml-api-2
   *Confidence: Verified (April 2026)*

6. **Manage inputs and outputs for components and pipelines**
   https://learn.microsoft.com/en-us/azure/machine-learning/how-to-manage-inputs-outputs-pipeline?view=azureml-api-2
   *Confidence: Verified (April 2026)*

7. **Create jobs and input data for batch endpoints**
   https://learn.microsoft.com/en-us/azure/machine-learning/how-to-access-data-batch-endpoints-jobs?view=azureml-api-2
   *Confidence: Verified (April 2026)*

8. **Upgrade pipeline endpoints to SDK v2**
   https://learn.microsoft.com/en-us/azure/machine-learning/migrate-to-v2-deploy-pipelines?view=azureml-api-2
   *Confidence: Verified (April 2026)*

### Code Samples (Verified)

- **Azure ML Examples Repository (azureml-examples/sdk/python/schedules):**
  https://github.com/Azure/azureml-examples
  *Confidence: Verified (April 2026)*

### Konfidensgradering per seksjon

| Seksjon | Konfidensnivå | Kilde |
|---------|---------------|-------|
| Introduksjon | Verified | MS Learn: concept-ml-pipelines |
| Kjernekomponenter | Verified | MS Learn: component-pipeline docs + code samples |
| Arkitekturmønstre | Verified + Baseline | MS Learn examples + arkitekturerfaring |
| Beslutningsveiledning | Baseline + Verified | Kombinasjon av best practices + MS Learn guidance |
| Integrasjon med Microsoft-stakken | Verified | MS Learn: ADF integration, Fabric docs |
| Offentlig sektor | Baseline | Norsk compliance-erfaring + Azure RBAC docs |
| Kostnad og lisensiering | Verified + Baseline | MS Learn: cost considerations + Azure pricing |
| For arkitekten | Baseline | Arkitekturkonsulent-erfaring |

**Verified:** Informasjon hentet direkte fra Microsoft Learn MCP-dokumentasjon (april 2026).
**Baseline:** Informasjon basert på modellkunnskap og arkitekturerfaring, konsistent med Azure ML prinsipper.
