PluginStore の適切な使用用途は何ですか?

Slack のスレッドレスポンスに対してスレッド ID を記憶する機能を実装するには、PluginStore が最も簡単な方法のようですが、discourse-chat-integration 全体での PluginStore の使用は孤立しており、実際に取得された値が使用されていないことに気づきました。

これは非推奨になっているのでしょうか、それとも別の方法で行われているのでしょうか?

トピックあたり最大 1 つの値のみを保存するため、全体的に見ればこれは比較的低カーディナリティであると思われます。これは PluginStore にとって妥当でしょうか?

トピックあたり最大 1 つの値を保存する場合、このユースケースにはトピックのカスタムフィールドを使用する方が適している可能性があります。

PluginStore は、データのカーディナリティが既存のカスタムフィールドテーブルには不適切であるため、プラグインで使用されるシンプルな KV ストアです。過去数年間、データ信頼性を向上させるために、適切な場合にプラグインを独自のテーブルに移行しています。例えば、poll プラグインで行ったようにです。ご自身のユースケースに合致する場合は、引き続き PluginStore を使用することも可能です。

ありがとうございます、そうすべきですね。私はまだ新しいので、迷惑にならない程度に、プラグイン内のトピックのカスタムフィールドの例を教えていただけないでしょうか?:smiling_face:

投票プラグインは、トピックのカスタムフィールドを少し使用します。例えば、discourse-topic-voting/plugin.rb at main · discourse/discourse-topic-voting · GitHubhttps://github.com/discourse/discourse-voting/blob/master/app/jobs/onceoff/voting_ensure_consistency.rb#L53 のようにです。

それが正しい方向を示していると思います。ありがとうございます!

この分野に初めて触れる方で、この情報にたどり着いた方のために、Ruby on Rails を全くの初心者として私が犯したいくつかの間違いを共有します。

  • isolate_namespace が模倣すべきパターンの一部だと誤解し、それが指す名前空間はデータベース内のものではなく、ルート の名前空間であると気づきませんでした。これが私を悩ませました。:smiling_face:
  • カスタムフィールドを設定しても保存されません。そのオブジェクト全体を保存する(例: topic.save!)か、カスタムフィールドのみを保存する(例: topic.save_custom_fields)必要があります。

はい、HasCustomFieldsミックスインには、save_custom_fieldsや自動型キャストなどの利点があります。

長期的には、プラグインストアとカスタムフィールドの両方を廃止し、より制限の厳しく管理されたシステムに置き換えまたは修正する可能性があると見ています。これらは、役に立つことよりもトラブルを引き起こすことが多いためです。

現在、カスタムフィールドを本当に必要としている唯一の用途は、シリアライザーに対して投稿に「特別な」情報が存在することをフラグ立てすること、あるいは例外的なケースとして、システム内の投稿の50%を装飾する必要がある場合に、そのデータもそこに配置することです。

カスタムフィールドは柔軟性が高すぎるため、多数の同時実行性の問題を引き起こします。

リッチなデータを追加する最善の方法は、プラグインが自身で必要なテーブルを作成し、それを所有することです。これが最初に行うべきことです。N+1問題やその他の問題に直面した場合は、それらを回避するためにカスタムフィールドを活用してください。

おっと、既存のプラグインエコシステムの大部分が壊れてしまわないでしょうか?

私は Discourse Chat Integration にスレッドサポートを追加する貢献を行いました(トピックを参照)。その際、ここでのアドバイスに基づいてカスタムフィールドを使用しました。

プラグインのモデルとマイグレーションは通常どのように作成していますか?メインの Rails ジェネレーターを使って作成し、プラグインフォルダにコピーしていますか?私は、プラグイン固有のプレフィックス付きでモデルとマイグレーションを作成するジェネレーターを自作しました。GitHub - spirobel/discourse at plugin_model_and_migrations · GitHub これも他の人にとって役立つかもしれませんね。:smiley:

discourse-policyと polls プラグインを参照して、移行の進め方の例を確認することをお勧めします。それが従うべきパターンです。

この変更は時間をかけて行われ、ガイドラインも提供されます。現在のシステムはプラグインストアとカスタムフィールドへの過度な依存により、毎週無数の問題を引き起こしています。

投票プラグインを確認し、それを基にプラグイン用のモデルジェネレーターと、以下のマイグレーションジェネレーターを作成しました:

私の理解が正しければ、プラグインストアが当初作られた理由の一つは、プラグインが独自のテーブルを作成した場合、テーブル名が衝突する可能性があるという懸念でした。
私が作成したジェネレーターは、モデルとマイグレーションの名前にプラグイン名をプレフィックスとして付与します。
これらのジェネレーターを主に作成した理由は、マイグレーションには予測可能な順序を確保するために日付番号を先頭に付ける必要があるためです。そのため、手動で作成したくなかったのです。

理論的には問題となり得る衝突ですが、それが主な動機ではありませんでした。大きな動機は、マイグレーションの実行方法が少し不明確だったことで、非常に手間のかからない仕組みを望んでいたからです。現在では、プラグイン内でマイグレーションを作成するのは簡単で、マイグレーションフォルダにファイルを置くだけです。

それでも、投稿のカスタムフィールドでは衝突が発生する可能性があります。