#+TITLE: pin
#+DESCRIPTION: A command-line Pinboard client
#+AUTHOR: Michael Herstine
#+EMAIL: <sp1ff@pobox.com>
#+DATE: <2026-05-19 Tue 09:02>
#+AUTODATE: t
#+STARTUP: overview

* Introduction

[[https://pinboard.in/][Pinboard]] is "social bookmarking for introverts"-- a social bookmarking web service along the lines of (the now defunct) [[https://en.wikipedia.org/wiki/Delicious_(website)][del.icio.us]]. [[https://github.com/sp1ff/pin][pin]] is a command-line client for [[https://pinboard.in][Pinboard]]. It is by no means complete; it supports a few operations which I have found useful in my workflow. Here are a few examples:

You can send a link =http://foo.com/bar= to [[https://pinboard.in][Pinboard]] with title "splat" & tags =a=, =b= & =c= like so:
 
#+BEGIN_SRC bash
pin send -t a -t b -t c "http://foo.com/bar | splat"
#+END_SRC

You can setup canned tag clouds you use repeatedly & refer to them by name:

#+BEGIN_SRC bash
$> cat ~/.pin
token = "you:XXX"

[targets]

[targets.frobnitz]
tags = ["@review", "frobinate"]
read_later = true
...
# This link will get tags @review & frobinate, and have the "read later" flag set:
$> pin send -r frobnitz "http://foo.com/bar | splat"
#+END_SRC

You can send the link to [[https://www.instapaper.com][Instapaper]] at the same time:

#+BEGIN_SRC bash
$> pin send -r frobnitz --with-instapaper "http://foo.com/bar | splat"
#+END_SRC

I use it for curating my tags:

#+BEGIN_SRC bash
$> pin get-tags 
| Tag                            | Use Count |
+--------------------------------+-----------+
| flapdoodl                      |         1 |
| flapdoodle                     |     10000 |
...
# Hmmm... likely a mis-spelling
$> pin rename-tag flapdoodl flapdoodle
#+END_SRC

or, say, deleting all links with a given combination of tags when they're no longer useful:

#+BEGIN_SRC bash
ping delete old-company+jira
#+END_SRC

Type =pin --help= for a description of all flags & sub-commands.
* License

[[https://github.com/sp1ff/pin][pin]] is GPL v3 software.
* Prerequistes

The Rust [[https://rustup.rs/][toolchain]] (Rust version 1.88 at minimum) & a Pinboard.in API [[https://pinboard.in/api][token]].
* Installation

This crate is available on [[https://crates.io][crates.io]], but you can also download an Autotools tarball:

#+BEGIN_SRC bash
cd /tmp
curl -O https://www.unwoundstack.com/dist/pin-0.3.0.tar.xz
tar xf pin-0.3.0.tar.xz
cd pin-0.3.0
./configure
make
make check
sudo make install
#+END_SRC
* Status & Roadmap

[[https://github.com/sp1ff/pin][pin]] is still early code; I have chosen the version number (0.2) in the hopes of conveying that this is a preliminary release. [[https://github.com/lionheart/pinboard.py][pinboard.py]] provides far more complete coverage of the Pinboard API, albeit at the cost of forcing users to navigate Python's package management. Still, [[https://github.com/sp1ff/pin][pin]] provides an interface that is task-oriented, not API-oriented. For instance, deleting all links with a given tag combination is actually a complex operation; one needs to:

  - ask the API for all links that have that combination of tags
  - delete those links one at a time (because that is what the API allows)
  - while respecting the API's rate limits

In other words, this package is intended to provide an interface organized around user operations, not API endpoints. Documentation is available [[https://www.unwoundstack.com/doc/pin/curr][here]].

Bugs, comments, problems, PRs, feature requests &c welcome at [[mailto:sp1ff@pobox.com][sp1ff@pobox.com]] and in the [[https://github.com/sp1ff/pin/issues][issues]].
