#知识 #卡片盒 #笔记 #超文本 #学术界

libzettels

旨在作为实现 Niklas Luhmann 的 "卡片盒" 系统的应用的后端的库。

4 个版本

使用旧的 Rust 2015

0.4.1 2022年3月12日
0.4.0 2020年6月8日
0.3.1 2020年6月4日
0.3.0 2020年6月3日

#172 in 科学

27 每月下载
用于 卡片盒

GPL-3.0 或更高版本

355KB
5K SLoC

libzettels

Libzettels 是一个旨在作为实现 Niklas Luhmann 的 "卡片盒" 系统的应用的后端的库。

  • 如果您想开发一个卡片盒应用,请继续阅读这里。
  • 如果您已经使用此库开发软件,您可能想直接查看 API 文档
  • 如果您在寻找一个卡片盒应用,请查看 Zettels
  • 如果您对卡片盒一无所知,请查看 卡片盒的 README,特别是“什么是卡片盒?”这一部分。

代码和包

Libzettels 目前处于 alpha 阶段,可能存在错误。API 可能会更改,直到版本 1.0.0。Libzettels 使用 Rust 编写。在此处查看代码和 crate。

为应用程序开发者提供的信息

再次,下面详细介绍了卡片盒的工作原理和 Libzettel 的方法。

简而言之,Libzettel 接收一个目录(您的卡片盒的根目录),其中包含 Markdown 文件(可能位于子目录中),并带有 YAML 元数据块(由 pandoc 定义)。

为了实现卡片盒,libzettels 将这些文件(您的卡片)之间的关系信息捆绑到一个可查询的索引中。为了填充此索引,libzettels 做了两件事

  1. 它检查 YAML 元数据块的 titlekeywordsfollowups 字段。
---
title:  'Example Zettel'
keywords: [example, question]
followups: [file.md, subdir/anotherfile.md, ../yetanotherfile.md]
foo: 'Potentially more data ignored by libzettels.'
...
  1. 它解析 Markdown 文档正文的内联样式链接(如 [示例](afile.md)),并提取这些链接的目标。

对于这个后者的任务,libzettels 提供了三种方法

  1. 使用 UNIX 命令行工具 grep
  2. 使用 ripgrep
  3. libzettels的本地方法。它确实可以工作,但完全没有针对速度进行优化,因此(至少对于大量文件来说)可能比其他方法慢得多。

由于它适用于所有平台,因此本地方法是默认的。
然而,使用这个库的应用程序开发者应该考虑是否以及如何让用户选择他们偏好的方法。例如,grep在大多数平台(如GNU/Linux、macOS、各种BSD变体和其他UNIX变体)上都是现成的,因此应该是一个容易的选择。

libzettels做什么?

Libzettels旨在处理两种类型的zettel文件

但它能够处理许多不同的格式,只要存在可读的YAML头部(见README)。

基于Markdown的zettel文件

基于Markdown的zettel文件是一个带有由pandoc定义的YAML头部的Markdown文件)。大多数关于与其他Zettels之间相互关系的信息都是从YAML头部读取的。一个例外是字段links,它是通过解析文件中的Markdown链接生成的(只有"inline"语法)。
YAML元数据可能包含其他信息(如作者等)。然而,这里忽略此类附加数据。

示例

---
title:  'Some Zettel'
keywords: [example]
followups: [file2.md, file3.md]
...

Here begins the Zettel's actual content, possibly containing links to 
[other Zettels](file2.md). These links are used for internal links within 
the Zettelkasten. External links can be achieved by [reference style][id] 
links. These are ignored by the Zettelkasten. Lorem ipsum…

[id]: https://daringfireball.net/projects/markdown/syntax#link

基于图像的zettel文件

基于图像的zettel文件是将手写笔记的扫描件集成到Zettelkasten的一种方式。为此,用户将图像文件复制到Zettelkasten的根目录,并创建一个包含关于与其他zettel之间相互关系的YAML元数据和图像文件的某种引用的辅助文本文件。例如,这样的文本文件可以是一个带有YAML头部的Markdown文件,并包含指向图像文件的图像链接。由于links字段无法自动填充有意义的数据,因此需要在YAML中设置该字段(否则它将为空列表)。

图像文件(所有非文本格式如png、jpg等,加上svg)会被Zettelkasten忽略,因此它们可以安全地保存在与辅助文本文件和其他zettel文件相同的文件夹中。

示例

---
title:  'An image-based Zettel'
keywords: [example]
followups: [file2.md, file3.md]
links: [file1.md]
...
![](imagefile.png)

其他文件作为zettel文件

其他文件也可以使用。实际上,上面描述的两种标准文件类型只是两种可能方法中的两种示例

  1. 带有YAML头部(如基于Markdown的zettel文件)的文件
  2. 带有辅助YAML元数据文件(如基于图像的zettel文件)的文件

带有YAML头部的文件

此方法有以下要求

  • 必须能够将Rust标准库中的BufRead特质的方法lines()应用于文件。
  • 文件应包含以---开头并以...---结尾的有效YAML文档。如果文件包含多个YAML文档,libzettels将忽略除第一个之外的所有文档。

如果您更喜欢将zettel的实际内容编写为其他格式(如LaTeX、HTML、dokuwiki等),那将完全没问题。然而,对于非Markdown文件,links字段将不会自动填充,因此——就像基于图像的zettel一样——您将需要手动在该YAML字段的该字段中指定链接。

---
title: 'A Zettel with LaTeX-Markup'
keywords: [example]
followups: [another-zettel.tex]
links: [yet-another-zettel.tex]
...

\section{A thought}
The actual \emph{content} of the Zettel is in LaTeX. Maybe I'll just paste
it into a LaTeX-document, later...

需要考虑的另一问题是您的工具链。Libzettels可以接受带有YAML头部的LaTeX文件,但您的LaTeX引擎可能不行。但是,对于libzettels来说,使用您喜欢的标记语言编写Zettels的内容,完全可能拥有一个工作的Zettelkasten。

说到工具链:如果您正在阅读本节,可能需要关注一下pandoc。它可能为您提供将YAML和您喜欢的标记语言混合转换为纯您喜欢的标记语言文件的方法。例如,上面的YAML-LaTeX混合可以通过以下命令转换为纯LaTeX:

pandoc -f markdown -o output.tex input.tex

您注意到我们没有告诉pandoc将其输入作为markdown处理吗?是的,这有效。如果输出是LaTeX,pandoc将保持所有LaTeX标记不变。实际上,libzettels的作者用markdown和LaTeX的疯狂混合编写自己的Zettels,并且运行良好。

最后一点:请注意,上述要求中的“包含”,而不是“必须”。如果没有这样的文档,libzettels仍然会为该文件在索引中写入一个条目,但它将使用默认值,这些值是“空”值。

---
title: 'untitled'
keywords: []
followups: []
links: []
...

这不会有什么意义,因为您无法更改这些。但是没有YAML头部的文件可以是Zettel到Zettel关系的端点。其他Zettels可以链接到它,并声明其为后续内容。但仅此而已。

带有附带YAML元数据文件的文件

此方法有以下要求

  • Libzettels必须忽略您的实际Zettel文件,并不要尝试对其进行索引。对于非文本文件类型(即Rust标准库中的BufRead-Trait的lines方法无法使用的所有内容),您不需要做任何事情。Libzettels将默认忽略它。同样,对于SVG文件也是如此。其他基于XML的格式需要通过ignore文件进行过滤(见这里
  • 附带的YAML元数据文件(如基于图像的Zettels)需要存在,这样libzettels才能对其进行索引。此外,您可能希望对您的实际Zettel文件(如基于图像的Zettels的图像链接)有一些参考。这样的参考可以是YAML中的另一个字段。这没问题,因为libzettels将忽略除其自身之外的所有YAML字段。

例如,假设您的Zettel格式为foo zettel1.foo,则zettel1.yaml的内容可能如下所示:

---
title: 'My Zettel'
keywords: [example]
followups: [another-zettel.yaml]
links: [yet-another-zettel.yaml]
zettel: zettel1.foo
...

请注意,链接和后续操作将指向其他YAML元数据文件,而不是实际的foo文件。

依赖项

~4–6MB
~112K SLoC