Skip to main content

fabric-data-pipelines

PyPI CI Python Downloads License: MIT Docs

Docs: fabric-data-pipelines.datalyft.io

fabric-data-pipelines is a Python library for authoring Microsoft Fabric data pipelines as code.

Microsoft Fabric pipelines are JSON definitions under the hood. Editing that JSON by hand is slow and brittle: activity payloads are deeply nested, dependency wiring is verbose, and expression strings are easy to break. This library lets you describe pipelines with typed Python objects and then generate the exact Fabric-compatible JSON or Git item folders that Fabric expects.

Full guides, API reference, and real-world examples live on the documentation site.

Who this is for

This package is designed for teams that want Microsoft Fabric pipelines to be:

  • declared in Python instead of assembled in the UI or hand-written JSON
  • reviewed and versioned in Git
  • exported into Fabric's *.DataPipeline folder format
  • validated before deployment or commit

Typical users are data engineers, analytics engineers, and platform teams building repeatable ETL or orchestration flows in Fabric.

Why use it

  • Typed activities instead of manually building nested Fabric payloads
  • Readable dependency helpers like .then(), .after(), and >>
  • Expression helpers for parameters, activity outputs, run metadata, and interpolation
  • First-class support for Fabric Git item folders, including .platform and .schedules
  • Validation of dependency graphs before serialization
  • An escape hatch via RawActivity when Fabric supports something not modeled yet

What it helps you build

You can use fabric-data-pipelines to build:

  • small pipelines such as Wait -> Notebook
  • ETL orchestration with Script, Copy, Lookup, and ExecutePipeline
  • control-flow pipelines with IfCondition, ForEach, Switch, and Until
  • scheduled Fabric items ready for Git integration

Installation

pip install fabric-data-pipelines
# or
uv add fabric-data-pipelines

Requires Python 3.10+.

from fabric_data_pipelines import Pipeline, Wait, Notebook

Quickstart

Create a tiny pipeline in Python and export the JSON definition:

from fabric_data_pipelines import Notebook, Pipeline, Wait

wait = Wait(name="Wait_For_Upstream", wait_time_in_seconds=30)
transform = Notebook(
    name="Transform_Silver_Sales",
    notebook_id="00000000-0000-0000-0000-000000000002",
    workspace_id="00000000-0000-0000-0000-000000000001",
)

wait.then(transform)

pipeline = Pipeline(
    name="Daily_Silver_Sales_Transform",
    activities=[wait, transform],
)
pipeline.save("daily_silver_sales_transform.json")

That produces a Fabric-compatible pipeline definition without manually assembling the underlying JSON.

Before / after

Hand-writing Fabric JSON means nested policies, dataset settings, and column mappings. The same landing truncate-and-copy in Python is compact; the generated definition is ~200 lines.

Python (see examples/landing_truncate_copy.py):

from fabric_data_pipelines import (
    AzureSqlMITable,
    ColumnMapping,
    ColumnRef,
    Copy,
    ExternalReferences,
    Pipeline,
    Script,
    ScriptBlock,
    SqlMISink,
    SqlMISource,
    TabularTranslator,
    TypeConversionSettings,
    expr,
)

LANDING = expr.library_variable("Demo_ETL_Library_Landing")
SOURCE = expr.library_variable("Demo_ETL_Library_SourceDb")
COLUMNS = ["customer_id", "region", "segment", "updated_at"]

truncate = Script(
    name="Truncate_Landing_customers",
    database="Landing",
    scripts=[
        ScriptBlock(
            text={"value": "TRUNCATE TABLE sales.customers", "type": "Expression"},
            type="Query",
        )
    ],
    external_references=ExternalReferences(connection=LANDING),
)
copy = Copy(
    name="Copy_customers_to_Landing",
    source=SqlMISource(
        sql_reader_query=SELECT_SQL,
        dataset_settings=AzureSqlMITable(database="SourceDb", connection=SOURCE),
    ),
    sink=SqlMISink(
        write_behavior="insert",
        dataset_settings=AzureSqlMITable(
            database="Landing",
            schema_name="sales",
            table="customers",
            connection=LANDING,
        ),
    ),
    translator=TabularTranslator(
        mappings=[
            ColumnMapping(
                source=ColumnRef(name=col, type="String", physical_type="nvarchar"),
                sink=ColumnRef(name=col, type="String", physical_type="nvarchar"),
            )
            for col in COLUMNS
        ],
        type_conversion=True,
        type_conversion_settings=TypeConversionSettings(allow_data_truncation=True),
    ),
)
truncate.then(copy)

Generated Fabric JSON (excerpt of ~200 lines):

{
  "properties": {
    "activities": [
      {
        "name": "Truncate_Landing_customers",
        "type": "Script",
        "typeProperties": {
          "database": "Landing",
          "scripts": [
            {
              "text": { "value": "TRUNCATE TABLE sales.customers", "type": "Expression" },
              "type": "Query"
            }
          ]
        },
        "externalReferences": {
          "connection": "@pipeline().libraryVariables.Demo_ETL_Library_Landing"
        }
      },
      {
        "name": "Copy_customers_to_Landing",
        "type": "Copy",
        "dependsOn": [
          { "activity": "Truncate_Landing_customers", "dependencyConditions": ["Succeeded"] }
        ],
        "typeProperties": {
          "source": { "type": "SqlMISource", "datasetSettings": { "...": "..." }, "sqlReaderQuery": "..." },
          "sink": { "type": "SqlMISink", "datasetSettings": { "typeProperties": { "table": "customers", "schema": "sales" } } },
          "translator": { "type": "TabularTranslator", "mappings": ["... 4 column mappings ..."] }
        }
      }
    ],
    "libraryVariables": { "...": "..." }
  }
}

Full generated payload: docs/snippets/before_after_pipeline.json.

Real-world examples

The examples/ folder contains pipelines that mirror common Fabric workloads:

Example Pattern
daily_notebook_transform.py WaitNotebook
landing_truncate_copy.py Truncate + Sql MI Copy with column mappings
scheduled_gold_refresh.py Weekly schedule + save_item() Git folder
lakehouse_lookup_to_warehouse.py LookupSetVariable → Warehouse Copy
parameterized_elt_controller.py ForEach + Switch + Dataflow / stored procedure
etl_with_lock_pattern.py Lock acquire / retry / invoke child / release
uv run python examples/landing_truncate_copy.py
uv run python examples/scheduled_gold_refresh.py

See the ETL Patterns guide for walkthroughs of each pattern.

How it fits into Fabric

This library supports two main output shapes:

1. Raw pipeline JSON

Use Pipeline.to_json() or Pipeline.save() when you want the pipeline definition itself.

json_text = pipeline.to_json()
pipeline.save("daily_load.json")

2. Fabric Git item folders

Use Pipeline.save_item() or save_workspace() when your repository is the source of truth and Fabric should consume item folders.

Fabric expects each pipeline item to live in a directory such as:

Gold_Finance_Metrics_Refresh.DataPipeline/
  pipeline-content.json
  .platform
  .schedules

This package generates those files for you, including schedule configuration when present.

Commit the folders into a Git-connected Fabric workspace and sync — see Deploy to Fabric. For validate-on-PR / export-on-merge, see CI with GitHub Actions.

How this compares

Tool Role vs this library
Fabric UI + Git Explore and debug in the portal; author typed, validated definitions here
fabricflow Live REST API / templates / execute-monitor; this library is offline Git-first authoring
fabric-cicd Deploy/promote items; this library authors the item folders it ships
Terraform Fabric provider Infra and resource lifecycle; this library owns pipeline JSON/item content

Longer write-up: How this compares.

Core concepts

Activities

Supported activity models include:

Class Fabric type Notes
Copy Copy Typed SQL MI / Lakehouse / Warehouse sources and sinks
Lookup Lookup
Notebook TridentNotebook
Dataflow RefreshDataFlow Dataflow Gen2
StoredProcedure SqlServerStoredProcedure
Script Script Query / NonQuery blocks
ExecutePipeline ExecutePipeline
SetVariable / AppendVariable SetVariable / AppendVariable
IfCondition IfCondition Nested activities
ForEach ForEach Nested activities
Switch Switch Cases + default
Until Until Nested activities
Wait Wait
Fail Fail
Web WebActivity HTTP via Fabric connection
RawActivity (any) Escape hatch for unmodeled types

Not modeled yet (use RawActivity): GetMetadata, Azure Function, Teams/Outlook, and others. Track or request work via GitHub Issues.

Dependency chaining

lookup.then(copy).then(notebook)  # Succeeded (default)
copy.then(notify, on="Failed")  # Failed / Completed / Skipped
join.after(copy_a, copy_b)  # fan-in
lookup >> copy  # same as .then()

Expressions

from fabric_data_pipelines import expr

expr.parameter("run_date")
# '@pipeline().parameters.run_date'

expr.activity_output("get_tables", "value")
# "@activity('get_tables').output.value"

expr.library_variable("MyConnection")
expr.interp(expr.run_id())  # '@{pipeline().RunId}' for SQL interpolation

Schedules

Fabric stores schedules in a separate .schedules file alongside pipeline-content.json and .platform. Schedules must be attached on the pipeline via Pipeline(schedules=[...]) (multiple allowed, max 20) and are written by Pipeline.save_item().

from fabric_data_pipelines import Pipeline, Schedule, Wait, Weekly

schedule = Schedule(
    enabled=True,
    job_type="Execute",
    configuration=Weekly(
        start_date_time="2026-07-10T00:00:00",
        end_date_time="2027-07-10T00:00:00",
        local_time_zone_id="Romance Standard Time",
        times=["21:30"],
        weekdays=["Monday", "Tuesday", "Wednesday", "Thursday", "Friday"],
    ),
)

pipeline = Pipeline(
    name="daily_load",
    activities=[Wait(name="pause", wait_time_in_seconds=5)],
    schedules=[schedule],
)
pipeline.save_item("out")

Validation

Pipeline.to_json() and Pipeline.save() call validate_graph() before serializing. That catches:

  • duplicate activity names, including nested scopes
  • unknown dependsOn targets
  • cross-scope dependencies
  • cycles in the dependency graph

Attaching more than 20 schedules on Pipeline(schedules=[...]) is rejected at construction time (Fabric limit).

Stable Fabric identity

When exporting Fabric item folders, logicalId handling matters:

  • If you set Pipeline(logical_id=...), that logicalId stays stable across renames.
  • If you omit logical_id, the library derives it deterministically from Pipeline.name.
  • If a .platform file already exists on disk, rewrites preserve its existing logicalId.

If you rely on the derived value and later rename the pipeline, Fabric will treat it as a new item. Pin logical_id if identity continuity matters.

Documentation

fabric-data-pipelines.datalyft.io — guides, API reference, and pattern walkthroughs.

Feedback

Outside pull requests are closed for now. Prefer GitHub Issues — see CONTRIBUTING.md for what to include in bug reports and feature requests.

Development

uv sync
uv run ruff check
uv run ruff format --check
uv run mypy src tests
uv run pytest

Maintainer notes (releases, Amplify docs hosting): maintainers/.

License

MIT

Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

fabric_data_pipelines-0.2.2.tar.gz (51.5 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

fabric_data_pipelines-0.2.2-py3-none-any.whl (45.6 kB view details)

Uploaded Python 3

File details

Details for the file fabric_data_pipelines-0.2.2.tar.gz.

File metadata

  • Download URL: fabric_data_pipelines-0.2.2.tar.gz
  • Upload date:
  • Size: 51.5 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/7.0.0 CPython/3.13.14

File hashes

Hashes for fabric_data_pipelines-0.2.2.tar.gz
Algorithm Hash digest
SHA256 7ccc69c2fcc96f155670885ead5e2816f9c7206b822cd982b517784fd01db415
MD5 6e8e0ec3a0af230ac8a9188fe0b0188d
BLAKE2b-256 0e9783960260627e2487a7d9e4f92c6e7522f6486bf84d6e6825f7df95143ebc

See more details on using hashes here.

Provenance

The following attestation bundles were made for fabric_data_pipelines-0.2.2.tar.gz:

Publisher: release.yml on datalyft/fabric-data-pipelines

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file fabric_data_pipelines-0.2.2-py3-none-any.whl.

File metadata

File hashes

Hashes for fabric_data_pipelines-0.2.2-py3-none-any.whl
Algorithm Hash digest
SHA256 55b5616d2904b80600428041f751427af4f1f132005492197a55edf05c98fe6d
MD5 2cf94bfe7f53cd69d26dae798cd0c592
BLAKE2b-256 178f742f1067e9f8e9b67beda59aa7f1d18b65e19c705f105a897ef1f24af682

See more details on using hashes here.

Provenance

The following attestation bundles were made for fabric_data_pipelines-0.2.2-py3-none-any.whl:

Publisher: release.yml on datalyft/fabric-data-pipelines

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Release history Release notifications | RSS feed

0.3.0

2 files

This release

0.2.2 This release

2 files

0.2.1

2 files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page