# Examples
Copy-paste-ready scenarios for common yconn setups.
---
## Project-layer only
**When to use:** Your whole team works with the same set of servers and you want the connection
list checked into the project repository.
Create a project config file at the root of your repository:
```
your-project/
└── .yconn/
└── connections.yaml
```
**`.yconn/connections.yaml`**
```yaml
version: 1
connections:
prod-web:
host: 10.0.1.50
user: deploy
port: 22
auth: key
key: ~/.ssh/prod_deploy_key
description: "Primary production web server"
link: https://wiki.internal/servers/prod-web
staging-db:
host: staging.internal
user: dbadmin
auth: password
description: "Staging database server — use with caution"
link: https://wiki.internal/servers/staging-db
bastion:
host: bastion.example.com
user: ec2-user
port: 2222
auth: key
key: ~/.ssh/bastion_key
description: "Bastion host — jump point for internal network"
```
**Commands:**
```bash
# Scaffold the .yconn/ directory and connections.yaml in the current directory
yconn init
# List all connections
yconn list
# Show full details for a connection
yconn show prod-web
# Connect
yconn connect prod-web
yconn connect bastion
```
**Notes:**
- The `key` paths (e.g. `~/.ssh/prod_deploy_key`) are resolved on each developer's local
machine. Every developer must have the referenced key files in place.
- Do not put passwords or key passphrases in this file — it lives in git. Key passphrases
are handled by `ssh-agent`.
- Commit `.yconn/connections.yaml` to version control. All team members get the connection
list automatically after `git pull`.
---
## Project + user layers
**When to use:** The team shares a project config, but you want to override one connection
locally — for example to use a different SSH key or a personal jump host.
**`.yconn/connections.yaml`** (committed to git — shared by the whole team)
```yaml
version: 1
connections:
prod-web:
host: 10.0.1.50
user: deploy
auth: key
key: ~/.ssh/team_deploy_key
description: "Primary production web server"
staging-db:
host: staging.internal
user: dbadmin
auth: password
description: "Staging database server"
```
**`~/.config/yconn/connections.yaml`** (local to your machine — not in git)
```yaml
version: 1
connections:
# Override the shared prod-web entry with your personal key
prod-web:
host: 10.0.1.50
user: deploy
auth: key
key: ~/.ssh/my_personal_deploy_key
description: "Primary production web server (personal key override)"
# Add a private entry that only you need
dev-vm:
host: 192.168.1.5
user: root
auth: key
key: ~/.ssh/id_rsa
description: "Local development VM"
```
**Commands:**
```bash
# List connections — prod-web shows from user layer (your override wins)
yconn list
# See where prod-web comes from
yconn show prod-web
# Source: user (/home/you/.config/yconn/connections.yaml)
# See all entries including the shadowed team version
yconn list --all
# prod-web appears twice: user layer (active) and project layer (shadowed)
# Connect using your overridden key
yconn connect prod-web
```
**Notes:**
- The user layer (`~/.config/yconn/`) takes higher priority than the project layer
(`.yconn/`). Any connection defined in both layers will use the user-layer values.
- The project layer entry for `prod-web` is still present — `yconn list --all` shows it
with a `[shadowed]` tag.
- Unique connection names (like `dev-vm`) are simply merged in alongside project entries.
---
## Docker-enabled setup
**When to use:** You want SSH keys to live inside a Docker image rather than on developer
machines. Developers pull the image and connect without needing the key files locally.
**`.yconn/connections.yaml`** (committed to git)
```yaml
version: 1
docker:
image: ghcr.io/myorg/yconn-keys:latest
pull: missing # pull if not already present locally
args:
- "--network=host"
connections:
prod-web:
host: 10.0.1.50
user: deploy
auth: key
key: /keys/prod_deploy_key # path inside the Docker image
description: "Primary production web server"
staging-db:
host: staging.internal
user: dbadmin
auth: password
description: "Staging database server"
bastion:
host: bastion.example.com
user: ec2-user
port: 2222
auth: key
key: /keys/bastion_key # path inside the Docker image
description: "Bastion host"
```
**Commands:**
```bash
# Connect — yconn detects the docker block, pulls the image if needed,
# and re-invokes itself inside the container
yconn connect prod-web
# See the full docker run command before execution
yconn connect --verbose prod-web
# Check Docker status and which image would be used
yconn config
```
**How it works:**
1. yconn starts on the host, loads the config, and finds `docker.image` set.
2. It checks whether it is already running inside a container (`/.dockerenv` or
`CONN_IN_DOCKER=1`). It is not, so it builds a `docker run` command.
3. The container gets the yconn binary, all config layers, and the current working
directory mounted. The original command (`connect prod-web`) is passed through.
4. Inside the container, yconn sees `CONN_IN_DOCKER=1` and skips the Docker step.
It invokes SSH directly using the key at `/keys/prod_deploy_key` inside the image.
**Building the keys image** (example Dockerfile):
```dockerfile
FROM alpine:3.21
RUN apk add --no-cache openssh-client
COPY keys/prod_deploy_key /keys/prod_deploy_key
COPY keys/bastion_key /keys/bastion_key
RUN chmod 600 /keys/prod_deploy_key /keys/bastion_key
```
**Notes:**
- The `docker` block is only trusted from the project (`.yconn/`) and system
(`/etc/yconn/`) layers. A `docker` block in `~/.config/yconn/` is ignored with a warning.
- Key paths in the connection entries (e.g. `/keys/prod_deploy_key`) are resolved
inside the container, not on the host.
- Pass `--network=host` in `docker.args` only when the container needs to reach hosts
on the host network directly.
---
## Inline group field usage
**When to use:** You have logically separate sets of connections — for example `work` and
`private` — and want to switch between them cleanly. All connections live in one
`connections.yaml` file; a `group:` field on each entry determines which set it belongs to.
**`~/.config/yconn/connections.yaml`**
```yaml
version: 1
connections:
work-web:
host: 10.10.0.5
user: deploy
auth: key
key: ~/.ssh/work_key
description: "Work production web server"
group: work
work-db:
host: 10.10.0.10
user: dbadmin
auth: password
description: "Work database server"
group: work
home-server:
host: 192.168.1.100
user: mans
auth: key
key: ~/.ssh/id_ed25519
description: "Home server"
group: private
vps:
host: vps.example.com
user: root
auth: key
key: ~/.ssh/vps_key
description: "Personal VPS"
group: private
```
**Commands:**
```bash
# List all available group values found across connections
yconn group list
# Show all connections (no group filter)
yconn list
# Switch to the work group — subsequent list/connect only shows work connections
yconn group use work
# List only work connections
yconn list
# Connect to a work server
yconn connect work-web
# Switch to the private group
yconn group use private
# List only private connections
yconn list
# Connect to the home server
yconn connect home-server
# Show connections from a specific group without changing the active group
yconn list --group work
# Show all connections regardless of active group
yconn list --all
# Check which group is currently active
yconn group current
# Revert to no group filter (show all connections)
yconn group clear
```
**Notes:**
- All connections live in `connections.yaml`. The `group:` field is just a tag — no
separate files per group.
- The active group is stored in `~/.config/yconn/session.yml` and persists across
terminal sessions until changed.
- Connections without a `group:` field are always shown when no group filter is active.
When a group is locked, only tagged connections matching the group are shown.
- `yconn list --all` always overrides any group filter and shows every connection.
- `yconn group use <name>` warns if no connections with that group value exist in any
layer, but it still sets the group.
---
## Wildcard pattern usage
**When to use:** You manage many similarly-named hosts (e.g. a fleet of web servers) and
want a single connection entry to cover all of them, using the input hostname directly.
**`.yconn/connections.yaml`**
```yaml
version: 1
connections:
web-prod-*:
host: "" # ignored — the matched input becomes the SSH hostname
user: deploy
auth: key
key: ~/.ssh/web_prod_key
description: "Production web fleet (web-prod-01, web-prod-02, ...)"
db-staging-?:
host: "" # ignored — the matched input becomes the SSH hostname
user: dbadmin
auth: key
key: ~/.ssh/db_staging_key
description: "Staging database servers (db-staging-a, db-staging-b, ...)"
bastion:
host: bastion.example.com
user: ec2-user
port: 2222
auth: key
key: ~/.ssh/bastion_key
description: "Bastion host (exact match — takes priority over any pattern)"
```
**Commands:**
```bash
# Connect to web-prod-01 — matches web-prod-* pattern; input becomes the SSH hostname
yconn connect web-prod-01
# Connect to web-prod-07 — same pattern, different host
yconn connect web-prod-07
# Connect to db-staging-a — matches db-staging-? pattern
yconn connect db-staging-a
# Connect to bastion — exact match wins over any wildcard pattern
yconn connect bastion
# Show which pattern covers a given input (shows pattern name in source field)
yconn show web-prod-01
```
**How wildcard matching works:**
1. yconn first checks whether the input is an exact connection name. If found, it wins
immediately — no pattern check is done.
2. All connection names are tested as glob patterns against the input. `*` matches any
sequence of characters; `?` matches any single character.
3. The matched input string (`web-prod-01`) becomes the SSH hostname directly. The
`host:` field in the YAML entry is overridden by the matched input.
4. If two different patterns both match the same input (e.g. `web-*` and `web-prod-*`
both match `web-prod-01`), yconn exits with a conflict error naming each pattern
and its source file. Resolve this by making your patterns non-overlapping.
**Notes:**
- The `host:` field in wildcard entries is overridden at connect time. You can leave it
blank or set it to a placeholder value — it will not be used for SSH.
- Wildcard entries appear in `yconn list` with their pattern name (e.g. `web-prod-*`) in
the NAME column.
- Same-pattern names across layers follow normal priority rules (higher layer wins) and
do not trigger conflict detection.
---
## Multi-location init
**When to use:** You want to scaffold a `connections.yaml` at a specific location to match
your project conventions — the default `.yconn/` subdirectory, a dotfile, or a plain file.
The three `--location` values and their resulting paths:
| `yconn` (default) | `.yconn/connections.yaml` | Isolated in subdirectory; git-trackable; recommended |
| `dotfile` | `.connections.yaml` | Hidden file in project root |
| `plain` | `connections.yaml` | Plain file in project root; may conflict with other tools |
**Commands:**
```bash
# Default — creates .yconn/connections.yaml
yconn init
# Dotfile convention — creates .connections.yaml in the current directory
yconn init --location dotfile
# Plain — creates connections.yaml in the current directory
yconn init --location plain
```
**Resulting file trees:**
```
# yconn init (default)
your-project/
└── .yconn/
└── connections.yaml
# yconn init --location dotfile
your-project/
└── .connections.yaml
# yconn init --location plain
your-project/
└── connections.yaml
```
**Upward walk priority:**
When yconn searches upward from the working directory, it checks all three conventions
in each directory in this order:
1. `.yconn/connections.yaml`
2. `.connections.yaml`
3. `connections.yaml`
The first match in a given directory wins. The walk then moves up to the parent
directory and checks again.
**Notes:**
- All three conventions are recognised by the upward walk — you can mix conventions
across different projects.
- `yconn init` fails with a clear error if the target file already exists.
- After running `yconn init`, edit the scaffolded file and run `yconn list` to verify.
---
## See also
- [Configuration reference](configuration.md) — full field reference and layer system
- `man yconn` — full command reference