# Install Obs Migrate

> Use when obs-migrate is missing, doctor fails, the user asks how to install/set up the CLI, uvx/pip fails, Python is too old, extras are missing, or any other migration skill cannot run because the tool is not Ready — owns getting elastic-observability-migration installed and verified before connect/migrate skills proceed. Not for Grafana/Datadog/Elastic credentials (use connect-to-o11y-source).

- Skill: `elastic/install-obs-migrate` (Agent Skill)
- Install (CLI): `npx skillmds@latest add elastic/install-obs-migrate`
- Raw SKILL.md: https://api.skillmd.com/api/skills/elastic/install-obs-migrate/raw
- Safety review: pending
- Works with: Claude Code, Claude.ai, OpenAI Codex
- Category: Coding & Dev Tools
- Author: elastic (https://skillmd.com/u/elastic)
- Updated: 2026-09-17
- Page: https://skillmd.com/skills/elastic/install-obs-migrate

---


# Install and verify `obs-migrate`

**Audience:** operators who need a working `obs-migrate` before any migration.
Other skills defer here so install guidance stays in one place.

Goal: get a **Ready** `obs-migrate` on this machine, then hand off to the skill
the user actually wanted (`connect-to-o11y-source`, `scan-o11y-environment`,
migrate skills, etc.). This skill is the **only** place that owns install
commands, extras, and doctor gotchas — other skills must defer here instead of
inventing install steps.

## When to run this skill

Run **before** any other migration skill when any of these are true:

- `obs-migrate` / `uvx … obs-migrate` is not found
- `obs-migrate doctor` exits non-zero or is not `Ready`
- User asks how to install, which extra to use, or why Datadog/Grafana tooling is missing
- Default system Python is too old (common on macOS)

Do **not** use this skill for vendor/Elastic credentials — that is
`connect-to-o11y-source`.

## Supported platforms

- **macOS and Linux** only. Windows is not supported.
- **Python 3.11+** required (3.11–3.13 is the tested range).
- Canonical docs: `https://github.com/elastic/observability-migration-platform/blob/main/docs/command-contract.md` → Install And Setup; `README.md`.

## Step 0 — Detect current state

```bash
command -v uvx
command -v uv
command -v obs-migrate
python3 --version
```

Then run doctor with the recommended launcher first (uvx never needs
`obs-migrate` on `PATH`). Only use the bare command when Step 0 already found
it on `PATH`:

```bash
uvx --from 'elastic-observability-migration[all]' obs-migrate doctor
# or, if `command -v obs-migrate` succeeded above:
# obs-migrate doctor
```

Interpret:

| Observation | Action |
|---|---|
| `doctor` prints `Ready.` | Install is done — hand off to the calling skill |
| `command not found: obs-migrate` and no `uv`/`uvx` | Install `uv`, then Step 1 |
| `command not found: obs-migrate` but `uvx` works | The bare command was run without a launcher — re-run as `uvx --from 'elastic-observability-migration[all]' obs-migrate …`, `.venv/bin/obs-migrate …`, or after `source .venv/bin/activate` (spell the package out: `PKG` may be unset in this shell) |
| Python `<3.11` | Install/use a newer Python (pyenv, python.org, Homebrew `python@3.12`), then retry |
| doctor notes Datadog client not installed | Reinstall with `[datadog]` or `[all]` if the user needs Datadog **API** mode |
| doctor prints `uv on PATH: no` / `uvx on PATH: no` | Informational, not a blocker — no command shells out to `uvx` at runtime. Install `uv` only if you want the `uvx` launcher |

## Step 1 — Install `uv` (recommended path)

[`uv`](https://docs.astral.sh/uv/) provides `uv` + `uvx` (no global pip required):

```bash
# https://docs.astral.sh/uv/getting-started/installation/
curl -LsSf https://astral.sh/uv/install.sh | sh
# then open a new shell or source the installer hint so uv/uvx are on PATH
command -v uvx
```

## Step 2 — Choose the footprint

| User needs | Extra | Notes |
|---|---|---|
| First-time / unsure / both sources | `[all]` (**default**) | Grafana + Datadog + tooling together |
| Grafana / Prometheus only | `[grafana]` or `[all]` | Base package already includes Grafana translation deps; `[all]` is still simplest |
| Datadog live API (`--input-mode api`) | `[datadog]` or `[all]` | File-mode Datadog works without the client; API mode needs `datadog-api-client` |
| Contributor / repo checkout | `.[all,dev]` via `make sync` | Not the operator path |

**Default recommendation:** `[all]` via `uvx` so you are not blocked mid-migration by a missing extra.

## Step 3 — Install and verify (operator path)

### Recommended: ephemeral `uvx` (no venv)

```bash
PKG='elastic-observability-migration[all]'
# Optional pin: PKG='elastic-observability-migration[all]==1.0.0'
uvx --from "$PKG" obs-migrate doctor
uvx --from "$PKG" obs-migrate list-samples
```

Always prefix commands with `uvx --from "$PKG"` unless the user wants a
persistent install.

### Persistent venv

```bash
PKG='elastic-observability-migration[all]'
python3 -m venv .venv
.venv/bin/pip install "$PKG"
.venv/bin/obs-migrate doctor
# Or activate once per shell, then use bare obs-migrate:
# source .venv/bin/activate && obs-migrate doctor
```

A bare `obs-migrate` only resolves when its install location is on `PATH` —
after `source .venv/bin/activate`, or a `pipx install` / `uv tool install`
(next section). Otherwise use a launcher: `.venv/bin/obs-migrate …` (explicit
path, no activate) or `uvx --from "$PKG" …`.

Both venv launchers are relative paths. If the user is not in the directory
that holds `.venv`, they get `no such file or directory` instead of
`command not found` — have them `cd` there or use the absolute path.

If the user hits `command not found: obs-migrate`, they most likely ran the
bare command without one of those, in a shell where `PKG` may also be unset —
so re-state the launcher with the package spelled out in full, e.g.
`uvx --from 'elastic-observability-migration[all]' obs-migrate doctor`. See
`README.md` → “If you see command not found”.

### Persistent tool install (bare command, no prefix)

When the user wants `obs-migrate` on `PATH` for every shell:

```bash
uv tool install 'elastic-observability-migration[all]'
export PATH="$HOME/.local/bin:$PATH"
obs-migrate doctor
```

The shim lands in `~/.local/bin` (`uv tool dir --bin` prints the real path).
Do not drop the `export`: `uv` cannot change the `PATH` of the shell that
invoked it, so without it the very next `obs-migrate doctor` fails with the
same `command not found` — `uv` only prints a warning. Run
`uv tool update-shell` once so later shells work without the export.
`pipx install 'elastic-observability-migration[all]'` is equivalent.
`uv` resolves against the newest Python present, so add `--python 3.13` when the
default is above the tested 3.11–3.13 range.

### GitHub tag fallback (never `@main`)

Only if PyPI is unreachable:

```bash
PKG='elastic-observability-migration[all]@git+https://github.com/elastic/observability-migration-platform.git@v1.0.0'
uvx --from "$PKG" obs-migrate doctor
```

### Repo checkout (contributors only — not the operator path)

```bash
make sync
uv run obs-migrate doctor
# or: .venv/bin/pip install -e ".[all,dev]"
```

## Step 4 — Ready checklist (must pass)

`obs-migrate doctor` must show:

- `Ready.`
- Required dependencies `ok`
- For Datadog API work: `datadog (datadog-api-client): ok`
- `uv`/`uvx` on `PATH` is reported for information only — no command needs it at runtime

Then run one offline smoke (still no source credentials needed):

```bash
uvx --from 'elastic-observability-migration[all]' obs-migrate list-samples
```

Exit `0` + sample JSON ⇒ install verified. **Hand off** to the skill the user
originally asked for.

## Kibana tooling note

No external Kibana tool is needed. `obs-migrate migrate` writes native
Dashboard-as-Code artifacts (`dashboards/native/*.native.json`) and
`obs-migrate upload --artifact-dir <dir>` sends them through the typed Kibana
Dashboards API (`PUT /api/dashboards/{id}`) — there is no dashboard-YAML
compile step, so nothing installs or fetches `kb-dashboard-cli` /
`kb-dashboard-lint`, and `doctor` does not check for them. Migrate and upload
work without the `[kibana]` extra.

## Honest limits / Do NOT

- **Do NOT** send users to Docker or Windows install paths (unsupported).
- **Do NOT** document `@main` git installs — pin a release tag.
- **Do NOT** fold Grafana/Datadog/Elastic credential setup into this skill —
  hand off to `connect-to-o11y-source`.
- **Do NOT** duplicate long install blocks in other skills — point here.
- **Do NOT** claim install success without a `Ready` doctor (or explain the
  exact doctor failure and fix it).

## See also

- `connect-to-o11y-source` — credentials and live source proof after install.
- `evaluate-o11y-permissions` — Elastic/Kibana key capabilities.
- `https://github.com/elastic/observability-migration-platform/blob/main/docs/command-contract.md` — Install And Setup (canonical).
- `README.md` — short operator install.
- PyPI: https://pypi.org/project/elastic-observability-migration/

