MacBookPro.lan 2026-5-11:12:42:57
This commit is contained in:
+172
@@ -0,0 +1,172 @@
|
||||
---
|
||||
link: "https://github.com/dhanushka2001/citeorder"
|
||||
created: 2026-05-11
|
||||
tags:
|
||||
- "#t/clippings/github"
|
||||
---
|
||||
[](https://github.com/user-attachments/assets/43f400c2-ba67-45a9-b196-53757bf9931b#gh-dark-mode-only)## citeorder
|
||||
|
||||
Simple command-line tool to correctly reorder Footnotes in Markdown files.
|
||||
|
||||
> [!tip] Tip
|
||||
> For those who don't wish to use the command-line, I have made a [Chrome Extension](https://github.com/dhanushka2001/citeorder-github) which adds a toolbar inside GitHub's README.md text editor with a button to reorder footnotes.
|
||||
|
||||
## Motivation
|
||||
|
||||
Markdown processors that support footnotes (e.g. [GitHub’s Markdown engine](https://github.com/github/cmark-gfm), which implements the [GitHub Flavored Markdown](https://github.github.com/gfm) spec) automatically reorder footnotes when converting `.md` files to HTML. However, `citeorder` fixes the ordering in the `.md` file itself, making it neater and easier to manage lots of footnotes. Especially useful when needing to add new footnotes in the middle of a long `.md` file and not having to spend ages reordering every in-text and full-entry footnote manually (🥲).
|
||||
|
||||
In-text footnotes (`"Alice here",[^1]`) and full-entry footnotes (`[^1]: Alice`) are a many-to-one relationship. `citeorder` assumes the connections are correct, and relabels them according to the order in which the **in-text footnotes** appear.
|
||||
|
||||
## How to use
|
||||
|
||||
1. Download the precompiled executable from the latest [release](https://github.com/dhanushka2001/citeorder/releases).
|
||||
Installation via [Homebrew](https://github.com/dhanushka2001/homebrew-citeorder) (macOS/Ubuntu):
|
||||
```
|
||||
brew install dhanushka2001/citeorder/citeorder
|
||||
```
|
||||
Installation via the [AUR](https://aur.archlinux.org/packages/citeorder) (Arch):
|
||||
```
|
||||
yay -S citeorder
|
||||
```
|
||||
Or clone the repo and compile source code
|
||||
If you want to compile the source code yourself, clone the repo and compile `citeorder.c`:
|
||||
```
|
||||
git clone https://github.com/dhanushka2001/citeorder
|
||||
```
|
||||
```
|
||||
gcc -Wall -O2 citeorder.c -o citeorder
|
||||
```
|
||||
2. To run, simply enter into the terminal:
|
||||
```
|
||||
citeorder input.md
|
||||
```
|
||||
where `input.md` is the Markdown file whose Footnotes you want reordered. `citeorder` will keep the original file as is and output the changes to a new file, `input-fixed.md`.
|
||||
To allow relaxed quote handling, do:
|
||||
```
|
||||
citeorder -q input.md
|
||||
```
|
||||
For more info and options, run:
|
||||
```
|
||||
citeorder -h
|
||||
```
|
||||
|
||||
## Example
|
||||
|
||||
`example.md`:
|
||||
|
||||
```
|
||||
"Alice says hi".[^1]
|
||||
|
||||
[^1]: Alice
|
||||
|
||||
"Bob is here".[^7] "I'm Charlie",[^4] "Daniel!",[^5] here.
|
||||
|
||||
[^4]: Charlie
|
||||
[^3]: Gary
|
||||
[^5]: Daniel
|
||||
[^7]: Bob
|
||||
|
||||
Is "Ethan"[^8] here?
|
||||
|
||||
[^8]: Ethan
|
||||
|
||||
"Bob and Charlie here again"[^7][^4]
|
||||
|
||||
[^6]: Fred
|
||||
```
|
||||
|
||||
Running:
|
||||
|
||||
```
|
||||
citeorder example.md
|
||||
```
|
||||
|
||||
will produce `example-fixed.md`:
|
||||
|
||||
```
|
||||
"Alice says hi".[^1]
|
||||
|
||||
[^1]: Alice
|
||||
|
||||
"Bob is here".[^2] "I'm Charlie",[^3] "Daniel!",[^4] here.
|
||||
|
||||
[^2]: Bob
|
||||
[^3]: Charlie
|
||||
[^4]: Daniel
|
||||
[^6]: Gary
|
||||
|
||||
Is "Ethan"[^5] here?
|
||||
|
||||
[^5]: Ethan
|
||||
|
||||
"Bob and Charlie here again"[^2][^3]
|
||||
|
||||
[^7]: Fred
|
||||
```
|
||||
|
||||
## Cases handled
|
||||
|
||||
- No changes needed.
|
||||
- Stacked in-text footnotes, e.g. `"hello",[^3][^1][^5]` → `"hello",[^1][^2][^3]`.
|
||||
- Single punctuation (or none) after end quote, e.g. `"A"[^3] "B",[^2] "C".[^6] "D"![^5]` → `"A"[^1] "B",[^2] "C".[^3] "D"![^4]`.
|
||||
- Improper quote, e.g. `"hello[^1]`, `"hello",,[^1]`, `hello"[^1]`, `"hello" [^1]` produces an error message like: `ERROR: in-text citation [^1] not properly quoted (line 5)`. Can ignore this error with the `-q` / `--relaxed-quotes` flag.
|
||||
- Full-entry footnotes with no matching in-text footnotes simply get bubbled to the end of the ordering.
|
||||
- In-text footnotes with no matching full-entry footnote produce an error message like: `ERROR: in-text citation [^2] without full-entry (line 3)`.
|
||||
- Duplicate full-entry footnotes, e.g.
|
||||
```
|
||||
[^4]: Alice
|
||||
[^4]: Bob
|
||||
```
|
||||
produces an error message like: `ERROR: duplicate [^4] full-entry citations (line 7 and 8)`.
|
||||
- Footnotes inside inline code (`"A"[^1]`) and fenced code blocks:
|
||||
```
|
||||
"A"[^1]
|
||||
[^1]: A
|
||||
[^2]: B
|
||||
```
|
||||
are ignored.
|
||||
- Footnote labels with letters/symbols are supported, and will be relabeled accordingly, e.g. `"A"[^6b]` → `"A"[^1]`.
|
||||
- Spaces in the in-text or full-entry footnotes. Spaces outside the label for in-text footnotes, e.g. `"A"[^ Alice ]` are accepted by Markdown processors, and `citeorder` will convert that to `"A"[^1]`. However, for full-entry footnotes, e.g. `[^ 4b ]: Alice`, it is not accepted, and in `citeorder` it will produce an error message like: `ERROR: [^ 4b ] full-entry citation contains a space (line 3)`. For both in-text and full-entry footnotes, spaces **in** the label itself, e.g. `"A"[^4 b]`, `[^4 b]: Alice`, are not accepted, and in `citeorder` you will get an error message.
|
||||
- In-text or full-entry footnote missing a label, e.g. `"A"[^]`, will produce an error message like: `ERROR: in-text citation [^] missing label (line 7)`.
|
||||
- Multiline quote:
|
||||
```
|
||||
"T"[^4]
|
||||
"This quote takes
|
||||
up multiple lines
|
||||
but is still valid",[^3]
|
||||
"H",[^6]
|
||||
[^4]: T
|
||||
[^6]: H
|
||||
[^3]: Multiline quote
|
||||
```
|
||||
becomes:
|
||||
```
|
||||
"T"[^1]
|
||||
"This quote takes
|
||||
up multiple lines
|
||||
but is still valid",[^2]
|
||||
"H",[^3]
|
||||
[^1]: T
|
||||
[^2]: Multiline quote
|
||||
[^3]: H
|
||||
```
|
||||
- Duplicate full-entry footnotes, e.g.
|
||||
```
|
||||
"A"[^dupe], "B"[^dupe]
|
||||
[^dupe]: A
|
||||
[^dupe]: B
|
||||
"C"[^dupe]
|
||||
[^dupe]: C
|
||||
"D"[^1]
|
||||
[^1]: D
|
||||
```
|
||||
can be auto-incremented using the `-d` / `--relaxed-duplicates` flag (must be only ONE duplicate footnote label, and must have an equal number of full-entry and in-text duplicates):
|
||||
```
|
||||
"A"[^1], "B"[^2]
|
||||
[^1]: A
|
||||
[^2]: B
|
||||
"C"[^3]
|
||||
[^3]: C
|
||||
"D"[^4]
|
||||
[^4]: D
|
||||
```
|
||||
Reference in New Issue
Block a user