セキュアなアップロード

完全な非公開フォーラム(匿名アクセスなし)において、デフォルトのローカルストレージ設定に安全なメディアオプションが存在しないことは、私にとって大きな見落としに思えます。多くの非公開フォーラム運営者が、すべての投稿添付ファイルが(URL が分かれば)公にアクセス可能であることを認識していないとしても、不思議ではありません。投稿本文が匿名でアクセスできないなら、直感的には添付ファイルもアクセスできないはずだと考えるでしょう。

この機能へのサポートを確認するために、issue を提出する価値はあるでしょうか?すでに存在する issue はありますか?この問題は、すでに所有しているホスティングハードウェア上で Discourse を立ち上げ、クラウドストレージ(特に AWS S3 の価格)に支払ってまでメディアを匿名で閲覧できないようにしたくない、小規模で資金の乏しいグループにとって、現在のところ決定的な障害となっています。

また、もしこの質問が単純すぎるようであればお許しください。すでにアップロード用とバックアップ用で別々のバケットを使用するサポートはありますよね?安全なアップロード用の第 3 のバケットをサポートするのは難しいでしょうか?公開アップロードはパブリックバケットに、安全なアップロードはセキュアバケットに格納し、個々のオブジェクト ACL は不要という仕組みです。そして、オブジェクトのセキュリティステータスが変更された場合は、単にバケット間を移動させるだけでよいはずです。

「いいね!」 5

かなり手間がかかると思います。少なくとも1日、もしかしたら1週間かかるかもしれません。

開発費を賄っているCdckホスティングは、S3へのアップロードで運用されているため、S3の予算がなく、ログインのみで自ホストできるサイトに関心があるだけです。

もしあなたのユーザーがアセットの共有リンクを見れば、それをダウンロードして共有することも可能です。大きな問題には思えません。

「いいね!」 3

「投稿本文は保護されているのに添付ファイルは保護されていないのが変だ」と私が考えているのは、おかしいことだと思いませんか?

意図的な共有と偶発的な共有には大きな違いがあります。前者を防ぐ現実的な方法はないのは確かです。しかし、後者は現在、人々が基盤となる技術を理解していないために発生してしまいます。例えば、添付画像へのリンクを含む投稿のメール通知が、無意識のうちに非メンバーに転送されるようなケースです。セキュアメディア機能に依存しない形で、メールから添付ファイルを抹消するオプションがあれば、良い代替案になるかもしれません。

意図的に添付ファイルのリンクを共有する場合でも、それが保護されたカテゴリからのものだったことを単に忘れてしまっているだけかもしれません。理想的な世界では、そのカテゴリへのアクセス権を持たない人にとって、添付ファイルのリンクは無価値であるべきです。

S3 実装のいずれかに現在または将来バグが存在すれば、匿名でバケット内のリソースを列挙したり、オブジェクト URL を推測してブルートフォース攻撃を行ったりする可能性も出てきます。理想的には、オンプレミス環境の S3 インターフェースはインターネット全体からファイアウォールで遮断し、Discourse サーバーからのみ直接アクセスできるようにしたいものです。

「いいね!」 4

気の狂った人ではありません。S3 以外の環境向けのセキュアなアップロード機能を実装することに反対しているわけではありません。ただ、この機能の構築を急ぐ必要があるという圧力がないことと、変更が単純ではないことが理由です。

私たちは定期的にインターンやオーディションプロジェクトを行っていますので、これはそのようなカテゴリに当てはまるプロジェクトの一種と言えます。

「いいね!」 14

AWS 以外の S3 互換ストレージにおいて、安全なメディアを扱うためのより簡単な手段として、このアプローチの実現性についてご意見をお聞かせください。

「いいね!」 1

ログインが必要なサイト向けに安全なアップロードを提供する簡単なハックがあります。

基本的には、アップロード用に Authentication Based on Subrequest Result | NGINX Documentation の設定を行います。唯一の問題は、ログイン必須がオンになっている場合に 403/401 を返す URL を見つけられず、ログインせずにアップロードにアクセスすると 500 エラーが発生してしまうことです。これは、アップロード URL を持っている人がログインせずにアクセスした場合にのみ発生するため、それほど深刻ではないように思われます。

大まかには以下のようになります:

# JP
    location = /auth {
        internal;
        proxy_pass http://discourse/categories;
        proxy_pass_request_body off;
        proxy_set_header Content-Length "";
        proxy_set_header X-Original-URI $request_uri;
    } 
    # END JP
    location ~ ^/uploads/ {

      auth_request /auth; #$JP
      # NOTE: it is really annoying that we can't just define headers
      # at the top level and inherit.
      #
「いいね!」 2

安全なアップロード用の個別のバケット機能を実装する計画はありません。また、S3 以外の環境や ACL が存在しない環境で安全なアップロードを動作させる計画もありません。将来的に、この作業に対する需要が十分に高まり、時間とリソースを投入する価値があると判断される場合は、検討する可能性があります。

「いいね!」 5

なぜ https://hashhackersforum.s3.us-east-2.amazonaws.com/optimized/2X/3/3204e85df407adfce19e105308248aee8b3b3f57_2_690x424.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Credential=AKIAU5WBGG5Z7FNHQEIS%2F20210415%2Fus-east-2%2Fs3%2Faws4_request&X-Amz-Date=20210415T025617Z&X-Amz-Expires=300&X-Amz-SignedHeaders=host&X-Amz-Signature=15c9118929ccd9c24a9594ab02a47e900269b9d921d41679a317e29d6174c2bc が使用され、https://forum.cdn.hashhackers.com/optimized/2X/3/3204e85df407adfce19e105308248aee8b3b3f57_2_690x424.png?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Credential=AKIAU5WBGG5Z7FNHQEIS%2F20210415%2Fus-east-2%2Fs3%2Faws4_request&X-Amz-Date=20210415T025617Z&X-Amz-Expires=300&X-Amz-SignedHeaders=host&X-Amz-Signature=15c9118929ccd9c24a9594ab02a47e900269b9d921d41679a317e29d6174c2bc が使用されないのでしょうか。

私は CDN の URL を正しく入力したはずです。

「セキュアメディアアップロード」を有効にすると、CDN は使用されません。

「いいね!」 5

気づいた点として、管理セクションに以下の警告が表示されます。

\u003e サーバーは S3 へのファイルアップロードを設定していますが、S3 CDN が設定されていません。これにより、S3 のコストが高額になったり、サイトのパフォーマンスが低下したりする可能性があります。詳しくは「アップロード用のオブジェクトストレージの使用」をご覧ください (Configure an S3 compatible object storage provider for uploads)。

この警告を無視しても構いませんが、secure_media が有効になっている場合、CDN を使用することはできません。このメッセージは secure_media が有効なサイトでは表示されないべきでしょう。

「いいね!」 1

すべての JS アセットには引き続き CDN を使用でき、世界中のユーザーに対してサイトの描画を大幅に高速化できます。

「いいね!」 3

それは面白いですね。Discourse が静的アセットを別様に扱うとは、私には明確ではありませんでした。もう一度ここにあるすべてのスレッドを読み直す必要があると思います。

「いいね!」 2

2.8.0.beta1バージョンにアップグレードした後、認証付きS3 URLを使用するバッジが機能しなくなりました。アップグレード前は問題ありませんでした。

uploadsテーブルを確認したところ、secureカラムの値はtrueでした。

New Badgeオプションを使用してファイルをアップロードした後でも、画像プレビューは空のままです。

S3 URLを使用する他のファイルにはこれまで問題はありません。

ご助力いただけますでしょうか?よろしくお願いいたします!:wink:

「いいね!」 2

ああ…またもや、本来安全にする必要のないアップロードを安全として扱っている場所ですね。バッジはアバターやカテゴリのロゴなどと同様に、本質的に公開画像であるため、安全としてマークすべきではありません。バッジ画像が安全としてマークされないように修正し、すでに安全としてマークされているものを修正するマイグレーションスクリプトを作成する必要があります。

2.8.0 の変更がこれに影響を与えるはずはないので、なぜこれで動作していたのか驚きです。

「いいね!」 5

@martin さん、こんにちは。

ご返信ありがとうございます。Ruby を使うのは初めてですが、この言語の明確さに大変感動しています。数時間デバッグを行った結果、どこを見ればよいか見当がついたと思います。おそらく、私があなたがおっしゃったことと逆のことをしてしまったようですね :slight_smile: Badge モデルにいくつかの行を追加したところ、画像が読み込めるようになりました。また、そこに for_site_setting というフラグがあることも確認できました。これは S3 上のオブジェクトに対する ACL の調整にこの情報を利用しているのだと思いますが、そのカラムを false に設定しました。

app/models/badge.rb

  def image_url
    if image_upload_id.present?
      return upload_cdn_path(image_upload.url) if !image_upload.url.include?(SiteSetting.Upload.absolute_base_url)
      uri = URI.parse(image_upload.url)
      Rails.application.routes.url_for(
        controller: "uploads",
        action: "show_secure",
        path: uri.path[1..-1],
        only_path: true
      )
    end
  end

今後のアップグレードで何が変わるかを確認し、さらに詳しく学んでみたいと思います。
本番環境で使用するのに最適なバージョンは何でしょうか?

ありがとうございます!

将来的にコードベースにより多く貢献できることを願っています。

「いいね!」 6

@danilogit さん、こんにちは。

バッジモデルに行った変更は確かに機能するでしょうし、Ruby を初めて使った時点でそれを実現できたのは素晴らしいですね。ただ、バッジが「secure」とマークされるべきではないという根本的な問題については、私が修正を進めます。

本番環境で使用するのに最適なバージョンは tests-passed ブランチです。このブランチは、修正が利用可能になった時点で最新の修正をすべて適用します。ただし、数週間ごとに修正や変更が適用される beta ブランチに留まることを好む人もいます。

バッジが「secure」とマークされる問題の修正が完了したら、お知らせします。

「いいね!」 5

本件に関する修正を本日完了しました:

cc @danilogit

「いいね!」 8

これは先ほど投稿したものです。

しかし、ここでのご指摘のコメントと関連があるのではないかと疑問に思っています。

セキュアなメディアアップロードが有効になっている状態で、ユーザーがアバターをアップロードすることはサポートされていますか?現在エラーが発生しているのですが、アバターがパブリックアクセスが許可されていない同じバケットにアップロードされていることが原因ではないかと考えています。

「いいね!」 1

3件の投稿が新しいトピックに分割されました: Can I use secure media and page publishing simultaneously in Discourse?

「セキュアメディア」および関連設定を「セキュアアップロード」に名称変更しました。これは画像や動画などに限定されず、一般的にセキュアアップロードと呼ばれているためです。関連するコアコミットはこちらです。

このトピックのOPは、この変更を反映するように更新されました。

「いいね!」 6