atprotoモデレーション概論 label編
atprotoのlabel仕様1について概説する。詳細は公式ドキュメント参照。
注意: 現在のlabel仕様(v1)はまだ若く、将来の更新が示唆されている。
ここではlexicon/実装固有の話には触れないため、抽象度高めの話になる。一度軽く読み流して、必要になってから戻ってきてもいい。
labelデータ
atprotoは汎用のモデレーション機能としてlabelというものを持っている。これはアカウントやコンテンツに付随するメタデータで、例えば「botアカウント」「ブラクラ」「フェイクニュース」のような属性を表す。2
この情報を誰が付けるか、どう扱うかはサービス依存となっている。ここではサービス非依存の仕様のみ説明し、Bluesky Socialの場合については別で説明する。
labelのデータ構造はatproto層で定義されており、特徴は以下の通り。
- at-uri(≒recordかアカウント)を対象にとる
- 発行者のDIDと最大128バイトの文字列(以後labal値と呼ぶ)で識別する
- 異なる発行者の同名labelは区別される
- 署名をlabel毎に付与する
- label自体はrecordではなく、様々な場所に埋め込まれるため、repositoryの署名は使えない
- 後から取り消しが可能
- labelに有効期限をつける方法と、キャンセル(
neg
)labelを発行する方法がある
- labelに有効期限をつける方法と、キャンセル(
特殊なlabel値として、!takedown
と!suspend
が定義されている。これらは、appviewによるtakedownと同様の効果が期待される。
!takedown
と!suspend
の明確な差異は定義されていないが、!suspend
はアカウント単位でのみ適用することが想定されている模様。また、一時的な停止であるというニュアンスも強そう。
labeler
labelの付け方は大別して2種類が想定されており、その一つがlabelerを使う方法である。
labelerはlabelを作成・配布する手段を持つサーバで、自身を表すDIDを持つ。エンドポイントやlabel署名の公開鍵はこのDIDドキュメントで指定される。
一般的には、appviewがlabelerからlabelを取得し、APIレスポンスに反映する形で適用する。
label配布の手段は自由で、相手に伝わりさえすればなんでもよい。標準として以下の2つのXRPC APIが定義されているが、必須ではない。
- subscribeLabels: subscribeReposのようなsubscription APIで、発行したラベルをストリームする
- queryLabels: 指定されたat-uriに付けたlabelを返す
ここから分かるように、標準では指定したlabelが付いた対象を列挙する方法は無い。が、誰かがsubscribeLabelsの出力を全部溜め込めば列挙することもできる。3
クライアントによるlabeler指定
labelerはappview指定のものが自動的に適用される場合もありうるが、一般的にクライアントから指定することが想定されている。具体的には、クライアントがXRPC APIを呼ぶ際のHTTPヘッダでatproto-accept-labelers
としてlabelerのDIDを指定する。
atproto-accept-labelers
が指定されたAPIを実行するサーバ(≒appview)は、そのlabelerからlabelを取得し、サービス毎の方法で適用することが期待される。
ただし、!takedown
と!suspend
に関しては、単にatproto-accept-labelers
で指定しただけでは反映されない。これらの特殊なlabelも反映したい場合は、labeler指定時にredact
パラメータを付ける必要がある。4
atproto-accept-labelers
は複数形になっていることからも分かるように、複数labelerを指定できる。とはいえ、無制限に許してしまうと処理が大変だし、その全てが利用可能か分からない。appviewがlabeler非対応の可能性だってある。ということで、実際に適用されたlablerはレスポンスのatproto-content-labelers
ヘッダから確認できる。
self label
もう一つのlabel発行方法は、recordの持ち主がrecordにlabelを埋め込むこと。これをself labelと呼ぶ。
self labelは、recordの適当なフィールドにcom.atproto.label.defs#selfLabel
を含めることで実現する。
普通のlabelと違い、selfLabel
は文字列しか持たない。発行者はrecordの持ち主であることが自明だし、署名もrepositoryの署名があるため、label用にわざわざ書く必要が無いというだけで、情報量としてはほぼ変わらない。
self label可否やフィールド名はcollection毎に異なるため、各lexiconを参照すること。self labelの扱いがappviewやクライアントに依存するのは普通のlabelと同じ。
Next
Footnotes
-
なお、ここでは
com.atproto.label.defs#labelValueDefinition
には言及しない。atproto lexiconで定義されてはいるが、atproto仕様では言及が無い。中身としてもbskyに引っ張られていそうなので、bskyにおけるlabelの説明をする際に触れる。 ↩ -
「成人向けコンテンツの警告もこれか」と思った人は少し待ってほしい。間違いではないのだが、厳密なことを言うとここはもう少し面倒な話がある。 ↩
-
この辺りの是非は少し議論されている。プライベートブロックの検討記事も参考になるかもしれない。 ↩
-
任意で
redact
を付けられるクライアントも、!takedown
/!suspend
を発行するサードパーティlabelerも、実際に見たことはない。 ↩