ホームページをユーザーの興味に合わせてトピック表示にカスタマイズ

このプラグインについてのご意見をお聞かせください。訪問者が興味に応じてホームページに表示する新しいトピックを選択できるプラグインを開発しています。アイデアを書き留めてこのステップを描きましたが、まだ試していません。

plugin.rb

# plugins/custom_homepage/plugin.rb
# frozen_string_literal: true

# name: custom-homepage
# about: Customizes the homepage to show topics based on user interests
# version: 0.1
# authors: MHAT
# url: https://domain.com

enabled_site_setting :custom_homepage_enabled

after_initialize do
  # コードは初期化後に実行されます
end
// plugins/custom_homepage/assets/javascripts/discourse/initializers/custom-homepage.js.es6

import { withPluginApi } from 'discourse/lib/plugin-api';

export default {
  name: 'custom-homepage',
  initialize(container) {
    withPluginApi('0.8', api => {
      api.modifyClass('component:topic-list', {
        didInsertElement() {
          this._super(...arguments);

          if (this.currentUser) {
            this.loadUserInterests();
          }
        },

        loadUserInterests() {
          const userId = this.currentUser.id;

          fetch(`/u/${userId}/preferences/interests`)
            .then(response => response.json())
            .then(data => {
              this.set('topics', this.sortTopicsByInterests(this.topics, data.interests));
            });
        },

        sortTopicsByInterests(topics, interests) {
          return topics.sort((a, b) => {
            const aScore = interests.includes(a.category_id) ? 1 : 0;
            const bScore = interests.includes(b.category_id) ? 1 : 0;

            return bScore - aScore;
          });
        }
      });
    });
  }
};
# plugins/custom_homepage/config/locales/server.en.yml
en:
  site_settings:
    custom_homepage_enabled: "カスタムホームページを有効にする"

  user:
    preferences:
      interests: "興味"

# plugins/custom_homepage/config/discourse_plugin.yml
enabled_site_setting: custom_homepage_enabled

設定用のHTML

<script type="text/x-handlebars" data-template-name="/connectors/user-preferences/interests">
  <div class="control-group">
    <label class="control-label">{{i18n 'user.preferences.interests'}}</label>
    <div class="controls">
      {{input value=currentUser.custom_fields.interests class="form-control"}}
    </div>
  </div>
</script>
# plugins/custom_homepage/plugin.rb

after_initialize do
  User.register_custom_field_type('interests', :string)

  add_to_serializer(:current_user, :interests) do
    object.custom_fields['interests']
  end
end

フィードバックと改善のための提案をありがとうございます。

私はタイ人です。私の英語力はあまり良くないかもしれません。Discourseを開発しながら英語を学ぼうとしました。

/preferences/interests はどこで実装されていますか?

ユーザーの興味を処理し、ユーザー設定に統合するためには、必要なルート、コントローラーのアクション、およびテンプレートを作成する必要があると考えています。

ただし、それは私の見解であり、単に設計されたものです。まだ構築に着手していません。試みても計画通りに進まない可能性があります。

ユーザー設定のルートを追加する:
- /u/:username/preferences/interests へのリクエストを処理するルートを追加します。

```ruby
# plugins/custom_homepage/config/routes.rb
Discourse::Application.routes.append do
  get '/u/:username/preferences/interests' => 'custom_homepage#interests', constraints: { username: /[^\\/]+/ }
end
```

コントローラーのアクションを作成する:
- リクエストを処理し、ユーザーの興味を取得するコントローラーを定義します。

```ruby
# plugins/custom_homepage/app/controllers/custom_homepage_controller.rb
class CustomHomepageController < ApplicationController
  requires_login
  
  def interests
    username = params[:username]
    user = User.find_by(username: username)
    
    if user
      render json: {
        interests: user.custom_fields['interests']
      }
    else
      render json: { error: 'User not found' }, status: 404
    end
  end
end
```

ユーザー設定に興味フィールドを追加する:
- 興味のための入力を含めるように、ユーザー設定テンプレートを変更します。

```html
<!-- plugins/custom_homepage/assets/javascripts/discourse/connectors/user-preferences/interests.hbs -->
<div class="control-group">
  <label class="control-label">{{i18n 'user.preferences.interests'}}</label>
  <div class="controls">
    {{input value=model.custom_fields.interests class="form-control"}}
  </div>
</div>
```

シリアライザーを拡張する:
- 興味フィールドを含めるようにユーザーシリアライザーを拡張します。

```ruby
# plugins/custom_homepage/plugin.rb

after_initialize do
  User.register_custom_field_type('interests', :string)
  
  add_to_serializer(:current_user, :interests) do
    object.custom_fields['interests']
  end

  add_to_serializer(:admin_detailed_user, :interests) do
    object.custom_fields['interests']
  end
end
```

興味を処理するための JavaScript を変更する:
- JavaScript を使用して、興味を取得し、ユーザープロファイルに保存します。

```javascript
// plugins/custom_homepage/assets/javascripts/discourse/initializers/custom-homepage.js.es6

import { withPluginApi } from 'discourse/lib/plugin-api';

export default {
  name: 'custom-homepage',
  initialize(container) {
    withPluginApi('0.8', api => {
      api.modifyClass('controller:preferences/account', {
        save() {
          const interests = this.model.custom_fields.interests;
          this.model.save().then(() => {
            fetch(`/u/${this.model.username}/preferences/interests`, {
              method: 'PUT',
              headers: {
                'Content-Type': 'application/json',
                'X-CSRF-Token': Discourse.CSRFToken
              },
              body: JSON.stringify({ interests })
            }).then(response => response.json()).then(() => {
              this.flash('Your preferences have been saved.');
            });
          });
        }
      });
    });
  }
};
```
  1. PUT リクエストを処理する:

    • コントローラーで PUT リクエストを処理し、興味を保存するロジックを実装します。
    # plugins/custom_homepage/app/controllers/custom_homepage_controller.rb
    class CustomHomepageController < ApplicationController
      requires_login
    
      def interests
        if request.get?
          username = params[:username]
          user = User.find_by(username: username)
          
          if user
            render json: {
              interests: user.custom_fields['interests']
            }
          else
            render json: { error: 'User not found' }, status: 404
          end
        elsif request.put?
          user = current_user
          interests = params[:interests]
          user.custom_fields['interests'] = interests
          user.save_custom_fields
          render json: success_json
        end
      end
    end
    
「いいね!」 2

面白そうですね。このプラグインにもいくつかアイデアがあるかもしれません。