<!--
SPDX-FileCopyrightText: Amolith <amolith@secluded.site>

SPDX-License-Identifier: CC0-1.0
-->

# lune

[![REUSE status](https://api.reuse.software/badge/git.secluded.site/lune)](https://api.reuse.software/info/git.secluded.site/lune)
[![Go Report Card](https://goreportcard.com/badge/git.secluded.site/lune)](https://goreportcard.com/report/git.secluded.site/lune)
[![Liberapay donation status](https://img.shields.io/liberapay/receives/Amolith.svg?logo=liberapay)](https://liberapay.com/Amolith/)

Lune (/lyn/, French for "moon" and rhymes with it) is a delightful CLI
for [Lunatask](https://lunatask.app).

## tl;dr

```bash
lune init                              # Interactive setup wizard
lune add "Review PR" -a work -s next   # Create task in work area
lune done ID                           # Mark task completed
lune jrnl "Productive day!"            # Quick journal entry
lune habit track meditation            # Track a habit
```

## Features

- **Interactive setup** — guided wizard configures areas, goals,
  notebooks, habits, and your access token
- **Secure storage** — access token lives in the system keyring, not a
  file
- **Natural language dates** — "yesterday", "-2 days", "next Monday" all
  work
- **Deep link support** — paste `lunatask://` URLs or plain IDs
- **Stdin-friendly** — use `-` to pipe content into tasks, notes, and
  journal entries
- **Shell completion** — tab-complete areas, goals, notebooks, and
  habits
- **JSON output** — most commands support `--json` for scripting
- **Config keys** — use short aliases like `work` instead of UUIDs

## Installation

- Using [mise](https://mise.jdx.dev/) (recommended to centralise and automate
  updating of binaries/CLI tools like this, but still requires the Go
  toolchain):
  ```bash
  mise use -g go:git.secluded.site/lune@latest
  ```
- Using the [Go toolchain](https://go.dev/dl) without bin (requires
  tracking updates manually):
  ```bash
  go install git.secluded.site/lune@latest
  ```

Then run `lune init` to configure your access token and copy areas,
goals, notebooks, and habits from the Lunatask desktop app.

## Usage

### Shortcuts

Quick commands for the most common actions:

| Command          | Description                        |
| ---------------- | ---------------------------------- |
| `lune add NAME`  | Create task (alias for `task add`) |
| `lune done ID`   | Mark task completed                |
| `lune jrnl TEXT` | Add journal entry                  |

### Resources

Full CRUD for Lunatask resources:

```bash
# Tasks
lune task add "Name" -a AREA -g GOAL -s STATUS -n "note" -p PRIORITY
lune task list [-a AREA] [-s STATUS] [--all] [--json]
lune task show ID [--json]
lune task update ID [-s STATUS] [--name "new name"] [--schedule "tomorrow"]
lune task delete ID [-f]

# Notes
lune note add "Title" -b NOTEBOOK -c "content"
lune note list [-b NOTEBOOK] [--json]
lune note show ID [--json]
lune note update ID [-c "new content"]
lune note delete ID [-f]

# Journal
lune journal add [CONTENT] [-d DATE] [-n NAME]

# Habits
lune habit track KEY [-d DATE]

# People (relationship tracker)
lune person add FIRST LAST [-r RELATIONSHIP]
lune person list [--json]
lune person show ID [--json]
lune person timeline ID -c "Met for coffee" [-d DATE]
lune person update ID [-r RELATIONSHIP]
lune person delete ID [-f]

# Config inspection
lune area list [--json]
lune area show KEY [--json]
lune goal list [-a AREA] [--all] [--json]
lune goal show KEY [--json]
```

### Flag reference

**Task flags:**

- `-a, --area` — area key from config
- `-g, --goal` — goal key (requires area)
- `-s, --status` — later, next, in-progress, waiting, completed
- `-n, --note` — task note (use `-` for stdin)
- `-p, --priority` — lowest, low, normal, high, highest
- `-e, --estimate` — time estimate in minutes (0-720)
- `-m, --motivation` — must, should, want
- `--important`, `--not-important` — Eisenhower matrix
- `--urgent`, `--not-urgent` — Eisenhower matrix
- `--schedule` — scheduled date (natural language)

**Habit flags:**

- `-d, --date` — date performed (default: today)

**Journal flags:**

- `-d, --date` — entry date (default: today)
- `-n, --name` — entry title (default: weekday name)

**Person flags:**

- `-r, --relationship` — family, intimate-friends, close-friends,
  casual-friends, acquaintances, business-contacts, almost-strangers

### Stdin support

Read content from stdin using `-`:

```bash
# Task name from stdin
echo "Review quarterly report" | lune add -

# Note content from stdin
cat meeting-notes.md | lune note add "Meeting Notes" -b work -c -

# Journal entry from stdin
echo "Wrapped up the project" | lune jrnl -
```

### Configuration

Config lives at `~/.config/lune/config.toml`. Run `lune init` anytime to
modify it through the interactive wizard, or edit directly:

```toml
[ui]
color = "auto"  # "always", "never", or "auto"

[defaults]
area = "work"
notebook = "notes"

[[areas]]
id = "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx"
name = "Work"
key = "work"

  [[areas.goals]]
  id = "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx"
  name = "Q1 Goals"
  key = "q1"

[[notebooks]]
id = "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx"
name = "Work Notes"
key = "notes"

[[habits]]
id = "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx"
name = "Meditation"
key = "meditation"
```

**Where to find IDs:** In the Lunatask desktop app, open any item's settings
modal and click "Copy [Item] ID" in the bottom left.

## A note on end-to-end encryption

Lunatask is end-to-end encrypted, which means lune can only access metadata
(IDs, timestamps, status, etc.)—not the names or contents of your tasks, notes,
habits, etc. This is by design. When listing items, you'll see IDs and dates
but not titles.

Creating items works because you provide the plain content and the desktop app
encrypts it. The API can't decrypt anything so it can't read encrypted content
back to you.

## Contributions

Patch requests are in [amolith/lune](https://pr.pico.sh/r/amolith/lune) on
[pr.pico.sh](https://pr.pico.sh). You don't need a new account to contribute,
you don't need to fork this repo, you don't need to fiddle with `git
send-email`, you don't need to faff with your email client to get `git
request-pull` working...

You just need:

- Git
- SSH
- An SSH key

```bash
# Clone this repo, make your changes, and commit them
# Create a new patch request with
git format-patch origin/main --stdout | ssh pr.pico.sh pr create amolith/lune
# After potential feedback, submit a revision to an existing patch request with
git format-patch origin/main --stdout | ssh pr.pico.sh pr add {prID}
# List patch requests
ssh pr.pico.sh pr ls amolith/lune
```

See "How do Patch Requests work?" on [pr.pico.sh](https://pr.pico.sh)'s home
page for a more complete example workflow.

---

Some other tools if this one interested you:

- [go-lunatask](https://git.secluded.site/go-lunatask) — the Go client library lune is built with
- [agent-skills](https://git.secluded.site/agent-skills) — collection of Agent Skills for extending LLM capabilities
- [git-format](https://git.secluded.site/git-format) — CLI that turns LLM input into well-formatted conventional commits and tags
