I tiedied up readme

quietlight
Apr 30, 2026, 10:55 PM
XO5DF6WRNO263YCK3X6NMD4E6WIRWBYZBXEH2QULI65LGPAY2PPQC

Dependencies

  • [2] LQLC7S3A trying gemini: Inconsistent Standards in @utils/ refactoring
  • [3] KZKLAINJ run out of space on nest, cleaned out

Change contents

  • edit in me.txt at line 561
    [3.772785]
    [2.6916]
  • edit in me.txt at line 564
    [2.6940]
  • replacement in README.md at line 28
    [3.1179026][3.1179026:1179175]()
    ./skraak import segments --db ./db/skraak.duckdb --dataset abc123 --location loc456 --cluster clust789 --folder /path/to/data --mapping mapping.json
    [3.1179026]
    [3.1179175]
    ./skraak import segments --db ./db/skraak.duckdb --dataset abc123 --location loc456 --cluster clust789 --folder /path/to/data --mapping mapping.json # requires mapping.json
  • replacement in README.md at line 39
    [3.1179685][3.1179685:1179850]()
    # Call analysis (extract from ML predictions, review/classify)
    ./skraak calls from-preds --csv predictions.csv # Extract calls, write .data files
    [3.1179685]
    [3.1179850]
    # Create .data files
    ./skraak calls from-preds --csv predictions.csv # Extract calls from OPSO, write .data files
  • replacement in README.md at line 42
    [3.1179942][3.1179942:1180250]()
    ./skraak calls show-images --file recording.wav.data # Display spectrograms
    ./skraak calls classify --folder ./data # Interactive classification (reviewer + bindings from ~/.skraak/config.json)
    ./skraak calls classify --folder ./data --filter opensoundscape-kiwi-1.0
    [3.1179942]
    [3.1180250]
    # Summarise .data files
  • edit in README.md at line 46
    [3.1180443]
    [3.1180443]
    # Display spectrograms
    ./skraak calls show-images --file recording.wav.data
  • edit in README.md at line 50
    [3.1180444]
    [3.1180444]
    # TUI for manual classification (reviewer + bindings from ~/.skraak/config.json)
    ./skraak calls classify --folder ./data # Interactive classification
    ./skraak calls classify --folder ./data --filter opensoundscape-kiwi-1.0
  • edit in README.md at line 55
    [3.1180601]
    [3.1180601]
  • edit in README.md at line 57
    [3.1180602]
    [3.1180602]
    # Agentic call analysis
  • replacement in README.md at line 68
    [3.1181601][3.1181601:1181665]()
    # Export OpenSoundScape clip_labels-format CSV from .data files
    [3.1181601]
    [3.1181665]
    # .data files to OPSO multihot csv (requires mapping.json)
  • edit in README.md at line 75
    [3.1181991]
    [3.1181991]
  • edit in README.md at line 81
    [3.1182435][3.1182435:1182499]()
    ./skraak time # Current time as JSON
  • edit in README.md at line 86
    [3.1182830]
    [3.1182830]
    # Get current time
    ./skraak time # Current time as JSON
  • edit in README.md at line 90
    [3.1182834][3.1182834:1183528]()
    **`isnight`** — Night detection for bioacoustic recordings. Determines if a WAV file was recorded at night (between sunset and sunrise) at the given GPS coordinates. The recording timestamp is read from the WAV file metadata, not from the filename — this works reliably because bioacoustic recorders (AudioMoth, BAR-LT, Song Meter, etc.) embed an accurate timestamp in the WAV header at the time of recording. AudioMoth comments are parsed automatically including the embedded UTC offset. For non-AudioMoth files without a recognized filename pattern, the timestamp falls back to the file modification time. Use `--brief` for batch/agent use to return only `file_path` and `solar_night`.
  • replacement in README.md at line 207
    [3.1186740][3.1186740:1186805]()
    Secondary bindings for a, eurbla, are accessed by shift-a, a/c/s
    [3.1186740]
    [3.1186805]
    **Secondary bindings for a, eurbla, are accessed by shift-a, a/c/s**
  • replacement in README.md at line 268
    [3.1189485][3.1189485:1189538]()
    6. **Export OpenSoundScape clip_labels-format CSV:**
    [3.1189485]
    [3.1189538]
    6. **Export .data files to OpenSoundScape multihot CSV:**
  • edit in README.md at line 276
    [3.1189802][3.1189802:1190630]()
    Reproduces OpenSoundScape's `BoxedAnnotations.clip_labels()` output
    exactly — same row layout, byte-identical CSVs — but in Go, fast, and
    without round-tripping through Raven `selections.txt`.
    **Algorithm.** For every `.data` file, generate fixed-duration clip
    windows from `[0, Duration]` using OPSO's `generate_clip_times_df`
    (supports `--final-clip` of `full | remainder | extend | none`). Every
    window is emitted as a row; for each output class column, the value is
    `True` when at least one cert-100 annotation of that class overlaps the
    window by ≥ `--min-label-overlap` seconds, else `False`. Gaps just emit
    all-`False` rows.
    Only certainty=100 labels participate. `mapping.json` (from the
    `/data-mapping` skill) translates `.data` species strings to canonical
    class names. Two sentinels with distinct semantics:
  • replacement in README.md at line 277
    [3.1190631][3.1190631:1191194]()
    - **`"__NEGATIVE__"`** — clip IS emitted, **all class columns False**.
    Overrides any positive labels in the same clip's union. Use for
    confirmed-negative training examples (e.g. `Noise`, `Not`, rain, wind,
    silence, chainsaw, helicopter).
    - **`"__IGNORE__"`** — the segment is dropped from output. Any
    segment whose species maps to `__IGNORE__` triggers the drop, regardless
    of filter. Use for files whose annotation set is incomplete: emitting any
    clip from them as confirmed-False would poison the training set with
    possibly-wrong negatives.
    [3.1190631]
    [3.1191194]
    - **`"__NEGATIVE__"`** — segmens IS emitted, **all class columns False**.
    - **`"__IGNORE__"`** — the segment is not in the dataset.
  • replacement in README.md at line 280
    [3.1191195][3.1191195:1191327]()
    Override order within a clip: `__NEGATIVE__` beats real classes. (File-level
    `__IGNORE__` is checked before any clip is generated.)
    [3.1191195]
    [3.1191327]
    ```
    {
    "Kiwi": {"species": "Kiwi"},
    "Geese": {"species": "__NEGATIVE__"},
    "Not": {"species": "__NEGATIVE__"},
    "Don't Know": {"species": "__IGNORE__"}
    }
    ```
  • replacement in README.md at line 295
    [3.1191594][3.1191594:1191935]()
    If `--output` exists, the run **appends**. Column-set mismatch with the
    existing header → hard error. Duplicate `(file, start_time, end_time)`
    row (within the run, or vs existing rows) → hard error on first
    occurrence. Any `.data` parse error, missing `Duration`, or species
    missing from `mapping.json` aborts before any row is written.
    [3.1191594]
    [3.1191935]
    If `--output` file already exists, the run **appends** to the file.
  • replacement in README.md at line 297
    [3.1191936][3.1191936:1191955]()
    ## Segments Import
    [3.1191936]
    [3.1191955]
    ## Import .data files to database
  • replacement in README.md at line 309
    [3.1192394][3.1192394:1192476]()
    use claude skill to guide user through creation of species calltype mapping to db
    [3.1192394]
    [3.1192476]
    use agent skill to create mapping
  • edit in README.md at line 361
    [3.1193492]
    [3.1193492]
    ```bash
    # All Makefile
    make test
    # Lines of code
    make count
    # Go unit tests
    make unit
    # Shell script integration tests (make sure db/test.duckdb available and FK's applied)
    make shell
    ```