Discourse Plugins entwickeln - Teil 3 - Eigene Site-Einstellungen hinzufügen

Vorheriges Tutorial: Developing Discourse Plugins - Part 2 - Connect to a plugin outlet


Site Settings (Site-Einstellungen)

Wenn Sie /admin/site_settings auf einer Discourse-Instanz besuchen, auf der Sie Administratorrechte haben, sehen Sie eine Liste von Konfigurationseinstellungen. Standardmäßig liefern wir die Einstellungen, die unserer Meinung nach für eine Discourse-Installation am besten geeignet sind, aber wir verstehen auch, dass Benutzer ihre Installationen anpassen möchten, um ihr Forum genau so zu gestalten, wie sie es wünschen.

Wenn Ihr Plugin nicht sehr einfach ist, möchten Sie wahrscheinlich Einstellungen hinzufügen, die die Benutzer Ihres Plugins ändern und zur Konfiguration der Funktionalität verwenden können. Glücklicherweise ist dies recht einfach zu bewerkstelligen!

config/settings.yml

Das Erste, was Sie tun müssen, ist, config/settings.yml in Ihrem Plugin-Ordner zu erstellen. Diese Datei listet alle Einstellungen auf, die Ihr Plugin benötigt. Hier ist eine Beispiel-Datei:

plugins:
  awesomeness_enabled:
    default: true
    client: true
  awesomeness_max_volume:
    default: 10
    client: true

Die Datei muss im YAML-Format vorliegen. YAML kann sehr heikel sein. Wenn Discourse Probleme beim Laden Ihrer Einstellungen hat, empfehle ich Ihnen, Ihr YAML mit einem Tool wie YAMLint zu validieren.

Ich werde die Beispieldatei im Detail erläutern. Die oberste Ebene ist plugins, und das teilt Discourse mit, dass wir möchten, dass diese Einstellungen unter „Plugins“ in den Site-Einstellungen angezeigt werden.

Danach werden zwei Einstellungen deklariert: awesomeness_enabled und awesomeness_max_volume. Discourse leitet den Typ der Einstellungen vom Standardwert ab, daher ist awesomeness_enabled ein Boolescher Wert und awesomeness_max_volume eine Zahl.

Das client: true ist wichtig zu verstehen. Discourse besteht aus zwei Hauptanwendungen: der serverseitigen API, geschrieben in Ruby on Rails, und der clientseitigen Anwendung, geschrieben in Ember.js. Standardmäßig stellen wir Einstellungen der Ember.js-Clientanwendung nicht zur Verfügung, es sei denn, Sie fügen client: true hinzu. Wir tun dies, weil einige Einstellungen privat sind, wie z. B. API-Schlüssel, und nicht an Endbenutzer gesendet werden sollten. Außerdem könnte das Senden jeder Einstellung an den Client für Endbenutzer eine große Downloadmenge bedeuten!

In unserem Beispiel möchten wir, dass beide Einstellungen sowohl in der JavaScript-Welt als auch in der serverseitigen Welt zugänglich sind.

Ein wichtiger zweiter Schritt

Bevor Sie Ihre neu hinzugefügten Site-Einstellungen verwenden können, müssen Sie Übersetzungen dafür hinzufügen. Da Discourse viele Sprachen unterstützt, muss jeder von Ihnen hinzugefügte Text die Übersetzung in andere Sprachen unterstützen.

Erstellen wir die Übersetzungen für unsere Einstellungen auf Englisch:

config/locales/server.en.yml

en:
  site_settings:
    awesomeness_enabled: "Is this plugin awesome?"
    awesomeness_max_volume: "What is the maximum volume possible?"

Die in dieser Datei hinzugefügten Bezeichnungen werden im Admin-Bereich angezeigt. Es ist eine gute Idee, so klar wie möglich zu beschreiben, was die Einstellung bewirkt.

Deklarieren der Einstellung als „aktivierte Einstellung“

Nachdem wir nun unsere Site-Einstellung haben, sollten wir Discourse mitteilen, dass dies die Einstellung ist, die unsere Funktionen ein- und ausschaltet.

Öffnen Sie Ihre plugin.rb-Datei und fügen Sie die folgende Zeile unter den Metadaten-Kommentaren hinzu:

enabled_site_setting :awesomeness_enabled

Stellen Sie sicher, dass alle Ihre anderen Einstellungen mit „awesomeness_“ beginnen, damit die Einstellungs-Schaltfläche unter /admin/plugins korrekt funktioniert.

Zugriff auf Ihre neuen Einstellungen

Zuerst müssen Sie Ihren Entwicklungsserver neu starten, damit die Einstellungen wirksam werden. Sobald Sie dies getan haben, sollten die Einstellungen für Ihren Server- und Client-Code verfügbar sein.

Wir injizieren die Site-Einstellungen automatisch in die meisten JavaScript-Objekte. Wenn Sie also eine Component, Controller, Route, View oder Model deklarieren, sollten Sie auf die Site-Einstellung zugreifen können, indem Sie einfach this.siteSettings.awesomeness_enabled verwenden. In den meisten Handlebars-Vorlagen sollten Sie auch {{siteSettings.awesomeness_enabled}} sagen können, und der Einstellungswert wird angezeigt.

Wir haben in dieser Reihe noch nicht viel über Ruby-Sachen behandelt, aber wenn Sie in der Ruby-Anwendung auf die Site-Einstellungen zugreifen möchten, können Sie dies über tun: SiteSetting.awesomeness_enabled

Gehen Sie nun vor und fügen Sie Ihren Plugins benutzerdefinierte Einstellungen hinzu!


Mehr in der Serie

Teil 1: Plugin Basics
Teil 2: Plugin Outlets
Teil 3: Dieses Thema
Teil 4: git setup
Teil 5: Admin interfaces
Teil 6: Acceptance tests
Teil 7: Publish your plugin


Dieses Dokument wird versioniert – schlagen Sie Änderungen auf github vor.

34 „Gefällt mir“

For those more familiar with YAML, this was probably obvious, and thanks to YAMLint that you referenced I was able to figure this out pretty quick, but I thought it was worth mentioning that the format for the config/locales/server.en.yml needs to specifically be:

en:
  site_settings:
    awesomeness_enabled: "Is this plugin awesome?"
    max_volume: "What is the maximum volume possible?"

Correct?

Another quick question, it’s great that I can get to the settings by clicking on the Change Settings button, but how do I get the plugin specific Settings button directly to the right of the plugin like the poll plugin?

https://s3.amazonaws.com/f.cl.ly/items/162n220f0M0P3e0j2U3M/Image%202015-07-29%20at%207.29.28%20PM.png

Or is that a little too much for a Beginner’s Guide?

4 „Gefällt mir“

I updated the guide to fix both of those :smile:

4 „Gefällt mir“

How do you get the settings button to pre-populate the search field like Discourse Tagging does? I feel like I’m missing something obvious.

Edit: Nevermind, I figured it out. You had to use *_enabled to get it to filter. I originally didn’t have an enabled setting because the URL was simply the factor for determining if it is enabled.

1 „Gefällt mir“

For some reason, {{siteSettings}} in the poster-name-right outlet returns undefined. I tested with other outlets and the return the expected value. I’m not sure why :sadpanda:

Had to work around it by using {{Discourse.SiteSettings}}

1 „Gefällt mir“

This isn’t working because the Post view code path is some of the oldest code we have and it doesn’t do all the automatic stuff newer code can do :frowning:

I’ve come up with a fix that I think will solve your problem:

In the future I’ll be able to remove this hack and it’ll just work.

3 „Gefällt mir“

Hey @eviltrout how can I add a user setting? I mean a setting for a plugin that every user can change on his profile? Can I set a default too?

I guess is the same as an Custom User Field, so can I create a new User Field from a plugin?

Unfortunately there’s no easy way to do this right now. There is probably a good argument to be made for such an API for plugin authors.

Until then the way to do it is to add the fields via plugin outlets to the user preferences, tap into serializers and saving logic to store the setting the PluginStore.

1 „Gefällt mir“

I ran into this a while back too. We have to expose the field in the site settings too. I’ll see if I can add a PR to make this easier.

1 „Gefällt mir“

For anyone following this tutorial and trying to get SiteSettings.awesomeness_enabled to return anything in a rails console, be aware that the tutorial is wrong. It should be SiteSetting.awesomeness_enabled (Setting without the s at the end!)

1 „Gefällt mir“

Hmmm, this works for me in the hbs files

{{#if siteSettings.plugin_outlet_locations_enabled}}

Different syntax depending on where it’s being called from?

EDIT
Ah, the singular - plural Rails “magic” thing.

Nope, your first guess was correct >.>

JS has Discourse.SiteSettings but Rails has SiteSetting.

3 „Gefällt mir“

Oops! Thanks for letting me know. I’ve updated the tutorial.

2 „Gefällt mir“

Well, I believe some infrastructure are not complete yet. But I am refurnishing old login plugins while it’s worthwhile to asking the future change to plugin infra. Shall I move settings from login to plugin prefix?

I would recommend to do that, yes.

1 „Gefällt mir“

Just to clarify, this is only the case if you say client: true, right?

Yes, that is correct. Javascript gets access to the “client side” site settings.

2 „Gefällt mir“

I do not completely understand this statement. I set it to client: false but it was still visible in admin settings. What exactly happens if you set client to false.

Thank you.

We ship up a big JSON object of all the site settings that have client: true to all users, so those are considered public and viewable.

If they don’t have client: true then they are meant to be available from the server side. The admin section is an exception - we need to return all site settings to admin users so they can be changed! It uses a different API to get them all.

9 „Gefällt mir“

Work for me! 2018-4-28

Code

config/settings.yml

config/locales/server.en.yml

plugin.rb

Result

http://localhost:3000/admin/site_settings/category/plugins


(oh, I saw the translation missing hint)

Thanks!

3 „Gefällt mir“