Skip to content

Commit 8b1a2c2

Browse files
poozaclaude
andcommitted
refactor: PUT /api/v1/statuses/:id に X-Mulukhiya-Purpose ベースのフィルタリングを導入
デフォルト(Purpose なし)は media_attributes のみ許可。 Purpose: tag で status パラメータも許可(#3877 ハッシュタグ付け替え用)。 不明な Purpose は 422 で拒否。 nginx サンプルから冗長な if ブロックを削除。 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
1 parent bc0c683 commit 8b1a2c2

File tree

3 files changed

+24
-5
lines changed

3 files changed

+24
-5
lines changed

app/lib/mulukhiya/controller/mastodon_controller.rb

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,15 @@ class MastodonController < Controller
5656

5757
put '/api/:version/statuses/:id' do
5858
verify_token_integrity!
59-
body = {media_attributes: params[:media_attributes]}.compact
59+
purpose = request.env['HTTP_X_MULUKHIYA_PURPOSE']
60+
body = case purpose
61+
when nil, ''
62+
{media_attributes: params[:media_attributes]}.compact
63+
when 'tag'
64+
{status: params[:status], media_attributes: params[:media_attributes]}.compact
65+
else
66+
raise Ginseng::ValidateError, "unknown purpose: #{purpose}"
67+
end
6068
raise Ginseng::ValidateError, 'media_attributes is required' if body.empty?
6169
reporter.response = sns.update_status(params[:id], body, {headers: @headers})
6270
@renderer.message = reporter.response.parsed_response

config/sample/mastodon/mulukhiya.nginx

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -28,9 +28,6 @@ location ~ ^/api/v[0-9]+/media/[0-9]+$ {
2828
}
2929
location ~ ^/api/v[0-9]+/statuses/[0-9]+$ {
3030
include /path/to/mulukhiya_proxy.conf;
31-
if ($http_x_mulukhiya_purpose != '') {
32-
proxy_pass http://localhost:3008;
33-
}
3431
proxy_pass $status_put_backend;
3532
}
3633
location = /api/v1/timelines/public {

docs/api.md

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -159,6 +159,20 @@ HTTP ステータス 200 なら全サービス正常、503 なら一部サービ
159159
- モロヘイヤが SNS に転送する際に自動的に `X-Mulukhiya: {パッケージ名}` を付与する
160160
- クライアントがこのヘッダを送信する必要はない
161161

162+
### X-Mulukhiya-Purpose ヘッダ
163+
164+
`PUT /api/v{version}/statuses/{id}` で本文更新の可否を制御するヘッダ。
165+
SNS における「発言の責任」の観点から、本文の自由な編集はデフォルトで禁止している。
166+
167+
| X-Mulukhiya-Purpose | 許可されるパラメータ | 用途 |
168+
| --- | --- | --- |
169+
| (なし / 空) | `media_attributes` のみ | メディア説明(ALT)の編集 |
170+
| `tag` | `status`, `media_attributes` | ハッシュタグの付け替え(モロヘイヤ内部用) |
171+
172+
- Purpose ヘッダなし: クライアントからの通常リクエスト。`media_attributes` 以外は除去される
173+
- Purpose が `tag`: モロヘイヤ自身がハッシュタグを書き換える際に使用(将来の #3877 対応)
174+
- 不明な Purpose: 422 Unprocessable Entity を返す
175+
162176
### パイプライン処理
163177

164178
以下の処理が**透過的に**適用される。クライアントは標準 API を呼ぶだけでよい。
@@ -182,7 +196,7 @@ URL 正規化、短縮 URL 展開、NowPlaying 検出(iTunes/Spotify/YouTube
182196
| エンドポイント | メソッド | 処理内容 |
183197
|---------------|---------|---------|
184198
| `/api/v{version}/statuses` | POST | 投稿作成(pre_toot → SNS → post_toot) |
185-
| `/api/v{version}/statuses/{id}` | PUT | メディア説明更新(`media_attributes` のみ許可、本文編集は不可|
199+
| `/api/v{version}/statuses/{id}` | PUT | 投稿更新(`X-Mulukhiya-Purpose` ヘッダで許可範囲を制御、下記参照|
186200
| `/api/v{version}/media` | POST | メディアアップロード(pre_upload → SNS → post_upload) |
187201
| `/api/v{version}/media/{id}` | PUT | メディア更新(サムネイル変換) |
188202
| `/api/v{version}/statuses/{id}/favourite` | POST | お気に入り(SNS → post_fav) |

0 commit comments

Comments
 (0)