ActivityPubを使ってFediverseにたどり着く

2023/7/12 [02:17:04] (水) 天気

いや、なんのこっちゃだけど。

2023年、ツイッター亡き後の世界となった。ネット空間には祖国を奪われた難民たちで溢れかえり…というB級サイバーパンクSFの設定。


そこで再評価されることになった、実は古より存在するFediverseというネットの連合空間。ActivityPubという共通の言語で繋がるネット世界、ということになった。


てことで、「いっちょかみ」できるかなあ、とここ数日あれこれ検索しまくって試して、とりあえずmastdonで検索して仲間として検索結果に出るところまではたどり着いた。

image

最小限のActivityPub、いわゆるお一人様で、もちろん喋ることもフォローなどアクションをすることもできない。ただ、連合空間に顔を出した、だけなんだけど。


「mastodonなどに認識してもらえる」のがまずはゴールだったんで、ここまでやったことをメモ。

(すべてはネットで検索して得られたもので、先人たちに大感謝)


ActivityPubに参加するため用意するもの

サーバーやドメインをもっていることが前提。わたしはいつものlolipopサーバー。


どうやら以下の5つがあればActivityPubに顔を出すことはできる、っぽい。

nodeinfo(json)

まず最初サーバー情報のありかをこれで返す。

{                                                                                                                                                           
    "links":[
    {
        "rel": "http://nodeinfo.diaspora.software/ns/schema/2.1",
        "href": "https://tokoroten.doncha.net/nodeinfo/2.1"
    }
    ]
}


nodeinfo2.1(json)

サーバーの情報、でいいのかな。ここにGETでアクセスされて、ウチはactivitypubやってますよ、ユーザーは1人ですけどね、というのを返す。

{                                                                                                                                                            
  "openRegistrations": false,
  "protocols": [
    "activitypub"
  ],
  "software": {
    "name": "tokoroten",
    "version": "0.1.0"
  },
  "usage": {
    "users": {
      "total": 1
    }
  },
  "version": "2.1"
}


host-meta(xml)

webfingerのURLを返す。uriは検索対象のユーザー名の文字列に置換される。


<?xml version="1.0"?>                                                                                                                                        
<XRD xmlns="http://docs.oasis-open.org/ns/xri/xrd-1.0">
<Link rel="lrdd" type="application/xrd+xml" template="https://tokoroten.doncaha.net/.well-known/webfinger?resource={uri}" />
</XRD>


webfinger(json)

host-metaで得られたwebfingerのURLにGETでアクセスされるのでユーザー情報のエンドポイントを返す。


具体的にはこんなGETリクエストが飛んでくる。

https://tokoroten.doncaha.net/.well-known/webfinger?resource={uri}

https://tokoroten.doncaha.net/.well-known/webfinger?resource=@t2aki@tokoroten.doncha.net


{                                                                                                                                                            
  "subject": "acct:t2aki@tokoroten.doncha.net",
  "links": [
    {
      "rel": "self",
      "type": "application/activity+json",
      "href": "https://tokoroten.doncha.net/t2aki"
    }
  ]
}


とりあえず確認するには、

「WebFinger」https://webfinger.net/

↑たとえばこんなページがあるので、ここの検索窓にユーザー名を入れて、以上の情報が表示されたらwebfingerは正しく設定されている。


actor(json)

webfingerで取得したユーザーのURLにアクセスするとこの情報を返す。


{                                                                                                                                                            
  "@context": [
    "https://www.w3.org/ns/activitystreams",
    "https://w3id.org/security/v1"
  ],
  "id": "https://tokoroten.doncha.net/t2aki",
  "type": "Person",
  "url": "https://tokoroten.doncha.net/t2aki",
  "inbox": "https://tokoroten.doncha.net/t2aki/inbox",
  "outbox": "https://tokoroten.doncha.net/t2aki/outbox",
  "followers": "https://tokoroten.doncha.net/t2aki/followers",
  "following": "https://tokoroten.doncha.net/t2aki/following",
  "name": "t2aki",
  "preferredUsername": "t2aki",
  "summary": "@t2aki@tokoroten.doncha.net",
  "icon": {
      "type": "Image",
      "mediaType": "image/jpeg",
      "url": "https://tokoroten.doncha.net/images/prof-image.jpg"
  },
  "pubKicKey": {
      "id": "https://tokoroten.doncha.net/t2aki#main-key",
      "owner": "https://tokoroten.doncha.net/t2aki",
      "publicKeyPem": "-----BEGIN PUBLIC KEY-----\n略==\n-----END PUBLIC KEY-----",
      "type": "Key"
  }
}


nodeinfoやhost-metaはわかってないまま設置。

たぶん、webfingerでユーザー情報のURLを返して、そのURLにアクセスするとユーザー情報を得ることができますよ、というやりとりがあればまずは第一関門突破だと思われる。


HTTPでリクエストの投げ合いをして相互理解を深める。WEBの基本。


と、わかったようなことを書いたけど、ここにいたるまでハマりまくった。


サイトの構成をどうすればいいのか、そもそもそこから。

結論。考える必要はまったくなかった。

ActivitiyPubはディレクトリ構造とか拘束しないというか全然関係ない。全部jsonやxmlの設定ファイルでリクエストに返答できればいいだけだった。


アクセスされて、ActivityPubを構成するファイルを返す時のヘッダは以下がMUST

Content-Type: application/activity+json; charset=utf-8

てことは動的にヘッダをつけて返答する必要があるのか、ということで、スクリプトで対応。そのために.htaccessのrewriteruleで振り分けることにした。※1


.htaccess

RewriteEngine On                                                                                                                                             
RewriteCond %{QUERY_STRING} ^resource=(.*)$
RewriteRule webfinger.* script-finger%1 [L]
RewriteRule nodeinfo$ script-nodeinfo0 [L]
RewriteRule nodeinfo/2\.1$ script-nodeinfo [L]
RewriteRule host-meta$ script-hostmeta [L]
RewriteRule t2aki$ script-actor [L]

ここでのハマり。

apacheのrewriteruleはそのままだと「クエリを含まない」

fingerはresourceというクエリをつけてやってくる。そのクエリが分からないんじゃ何を求められてるのかわからない。それを解決するにはRewriteCondでクエリを判定させてやれば良い、てことにたどり着くのに2時間弱。


この先、フォローしたり投稿したりするには公開鍵秘密鍵で署名する必要があって、わたしの脳みそで理解できるレベルではない。そもそもlolipopではCrypt::OpenSSL::RSAのモジュールが使えないのでないものねだり。


手元、ローカルで作って手作業で鍵を作ってリクエストを投げる、ということを考えるしかなさそう。それもHTTPのヘッダ構成を調べる必要があって、高いハードルを見上げすぎて首を痛めるレベル。

とはいえ、せっかくだし、もう少し頑張ってみるかなあ。


※1

検索していてビックリしたのが静的ファイルだけでActivityPub実装してるかたいらっしゃった。

NetlifyとSupabaseでほぼ静的なActivityPubサーバ


今回まででとても参考になったサイト

Fediverse入門―非中央集権型SNSサーバを作ろう!

田舎の昼のサイレンbotをActivityPubで実装する(マストドンにアカウントを認識してもらう編)

ActivityPubの実装についてのメモ

本当に助かりました。多謝!!!


さっそく、ひとり言掲示板「ところてんx10」が役に立った、ぞ。


[2024/09/04 22:55:57]

nodeinfo→nodeinfo2.1のフェーズを追記。

<<2026/1>>
    123
45678910
11121314151617
18192021222324
25262728293031
検索:

【最近の20件】