FEATURE: Allow the user to select a custom home page (#5268)
* Add user_home configuration option * Use the new user_home preference to actually show the right home page * Fix trailing whitespace * Update user_option_serializer.rb * Fix JavaScript default homepage tests * Use an object instead of a giant switch * Remove trailing whitespace * Make the default `user_home` set to `null` instead of `0` * Rename user_home to homepage_id
This commit is contained in:
parent
162932114e
commit
38b8d68c68
|
@ -1,8 +1,11 @@
|
|||
import PreferencesTabController from "discourse/mixins/preferences-tab-controller";
|
||||
import { setDefaultHomepage } from "discourse/lib/utilities";
|
||||
import { default as computed, observes } from "ember-addons/ember-computed-decorators";
|
||||
import { currentThemeKey, listThemes, previewTheme, setLocalTheme } from 'discourse/lib/theme-selector';
|
||||
import { popupAjaxError } from 'discourse/lib/ajax-error';
|
||||
|
||||
const USER_HOMES = { 1: "latest", 2: "categories", 3: "unread", 4: "new", 5: "top" };
|
||||
|
||||
export default Ember.Controller.extend(PreferencesTabController, {
|
||||
|
||||
@computed("makeThemeDefault")
|
||||
|
@ -14,6 +17,8 @@ export default Ember.Controller.extend(PreferencesTabController, {
|
|||
'enable_quoting',
|
||||
'disable_jump_reply',
|
||||
'automatically_unpin_topics',
|
||||
'allow_private_messages',
|
||||
'homepage_id',
|
||||
];
|
||||
|
||||
if (makeDefault) {
|
||||
|
@ -51,6 +56,19 @@ export default Ember.Controller.extend(PreferencesTabController, {
|
|||
previewTheme(key);
|
||||
},
|
||||
|
||||
homeChanged() {
|
||||
const siteHome = Discourse.SiteSettings.top_menu.split("|")[0].split(",")[0];
|
||||
const userHome = USER_HOMES[this.get('model.user_option.homepage_id')];
|
||||
setDefaultHomepage(userHome || siteHome);
|
||||
},
|
||||
|
||||
@computed()
|
||||
userSelectableHome() {
|
||||
return _.map(USER_HOMES, (name, num) => {
|
||||
return {name: I18n.t('filters.' + name + '.title'), value: num};
|
||||
});
|
||||
},
|
||||
|
||||
actions: {
|
||||
save() {
|
||||
this.set('saved', false);
|
||||
|
@ -66,6 +84,8 @@ export default Ember.Controller.extend(PreferencesTabController, {
|
|||
setLocalTheme(this.get('themeKey'), this.get('model.user_option.theme_key_seq'));
|
||||
}
|
||||
|
||||
this.homeChanged();
|
||||
|
||||
}).catch(popupAjaxError);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,5 +1,7 @@
|
|||
import { escape } from 'pretty-text/sanitizer';
|
||||
|
||||
const homepageSelector = 'meta[name=discourse_current_homepage]';
|
||||
|
||||
export function translateSize(size) {
|
||||
switch (size) {
|
||||
case 'tiny': return 20;
|
||||
|
@ -349,8 +351,22 @@ export function displayErrorForUpload(data) {
|
|||
}
|
||||
|
||||
export function defaultHomepage() {
|
||||
// the homepage is the first item of the 'top_menu' site setting
|
||||
return Discourse.SiteSettings.top_menu.split("|")[0].split(",")[0];
|
||||
let homepage = null;
|
||||
let elem = _.first($(homepageSelector));
|
||||
if (elem) {
|
||||
homepage = elem.content;
|
||||
}
|
||||
if (!homepage) {
|
||||
homepage = Discourse.SiteSettings.top_menu.split("|")[0].split(",")[0];
|
||||
}
|
||||
return homepage;
|
||||
}
|
||||
|
||||
export function setDefaultHomepage(homepage) {
|
||||
let elem = _.first($(homepageSelector));
|
||||
if (elem) {
|
||||
elem.content = homepage;
|
||||
}
|
||||
}
|
||||
|
||||
export function determinePostReplaceSelection({ selection, needle, replacement }) {
|
||||
|
|
|
@ -249,6 +249,7 @@ const User = RestModel.extend({
|
|||
'include_tl0_in_digests',
|
||||
'theme_key',
|
||||
'allow_private_messages',
|
||||
'homepage_id',
|
||||
];
|
||||
|
||||
if (fields) {
|
||||
|
|
|
@ -23,6 +23,13 @@
|
|||
{{/if}}
|
||||
|
||||
|
||||
<div class="control-group home">
|
||||
<label class="control-label">{{i18n 'user.home'}}</label>
|
||||
<div class="controls">
|
||||
{{combo-box content=userSelectableHome valueAttribute="value" value=model.user_option.homepage_id}}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="control-group other">
|
||||
<label class="control-label">{{i18n 'user.other_settings'}}</label>
|
||||
|
||||
|
|
|
@ -308,7 +308,7 @@ class ApplicationController < ActionController::Base
|
|||
end
|
||||
|
||||
def current_homepage
|
||||
current_user ? SiteSetting.homepage : SiteSetting.anonymous_homepage
|
||||
current_user&.user_option&.homepage || SiteSetting.anonymous_homepage
|
||||
end
|
||||
|
||||
def serialize_data(obj, serializer, opts = nil)
|
||||
|
|
|
@ -347,6 +347,10 @@ module ApplicationHelper
|
|||
end
|
||||
end
|
||||
|
||||
def current_homepage
|
||||
current_user&.user_option&.homepage || SiteSetting.anonymous_homepage
|
||||
end
|
||||
|
||||
def build_plugin_html(name)
|
||||
return "" unless allow_plugins?
|
||||
DiscoursePluginRegistry.build_html(name, controller) || ""
|
||||
|
|
|
@ -128,6 +128,17 @@ class UserOption < ActiveRecord::Base
|
|||
times.max
|
||||
end
|
||||
|
||||
def homepage
|
||||
case homepage_id
|
||||
when 1 then "latest"
|
||||
when 2 then "categories"
|
||||
when 3 then "unread"
|
||||
when 4 then "new"
|
||||
when 5 then "top"
|
||||
else SiteSetting.homepage
|
||||
end
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def update_tracked_topics
|
||||
|
@ -165,6 +176,7 @@ end
|
|||
# theme_key :string
|
||||
# theme_key_seq :integer default(0), not null
|
||||
# allow_private_messages :boolean default(TRUE), not null
|
||||
# homepage_id :integer default(null)
|
||||
#
|
||||
# Indexes
|
||||
#
|
||||
|
|
|
@ -22,6 +22,7 @@ class UserOptionSerializer < ApplicationSerializer
|
|||
:theme_key,
|
||||
:theme_key_seq,
|
||||
:allow_private_messages,
|
||||
:homepage_id,
|
||||
|
||||
def auto_track_topics_after_msecs
|
||||
object.auto_track_topics_after_msecs || SiteSetting.default_other_auto_track_topics_after_msecs
|
||||
|
|
|
@ -36,6 +36,7 @@ class UserUpdater
|
|||
:include_tl0_in_digests,
|
||||
:theme_key,
|
||||
:allow_private_messages,
|
||||
:homepage_id,
|
||||
]
|
||||
|
||||
def initialize(actor, user)
|
||||
|
|
|
@ -5,6 +5,7 @@
|
|||
<title><%= content_for?(:title) ? yield(:title) : SiteSetting.title %></title>
|
||||
<meta name="description" content="<%= @description_meta || SiteSetting.site_description %>">
|
||||
<meta name="discourse_theme_key" content="<%= theme_key %>">
|
||||
<meta name="discourse_current_homepage" content="<%= current_homepage %>">
|
||||
<%= render partial: "layouts/head" %>
|
||||
<%= discourse_csrf_tags %>
|
||||
|
||||
|
|
|
@ -658,6 +658,7 @@ en:
|
|||
undo_revoke_access: "Undo Revoke Access"
|
||||
api_approved: "Approved:"
|
||||
theme: "Theme"
|
||||
home: "Default Home Page"
|
||||
|
||||
staff_counters:
|
||||
flags_given: "helpful flags"
|
||||
|
|
|
@ -0,0 +1,5 @@
|
|||
class AddUserOptionHome < ActiveRecord::Migration[5.1]
|
||||
def change
|
||||
add_column :user_options, :homepage_id, :integer, null: true, default: nil
|
||||
end
|
||||
end
|
|
@ -7,7 +7,7 @@ class HomePageConstraint
|
|||
return @filter == 'finish_installation' if SiteSetting.has_login_hint?
|
||||
|
||||
provider = Discourse.current_user_provider.new(request.env)
|
||||
homepage = provider.current_user ? SiteSetting.homepage : SiteSetting.anonymous_homepage
|
||||
homepage = provider&.current_user&.user_option&.homepage || SiteSetting.anonymous_homepage
|
||||
homepage == @filter
|
||||
rescue Discourse::InvalidAccess
|
||||
false
|
||||
|
|
|
@ -10,6 +10,7 @@ import {
|
|||
getRawSize,
|
||||
avatarImg,
|
||||
defaultHomepage,
|
||||
setDefaultHomepage,
|
||||
validateUploadedFiles,
|
||||
getUploadMarkdown,
|
||||
caretRowCol,
|
||||
|
@ -204,6 +205,22 @@ QUnit.test("allowsAttachments", assert => {
|
|||
QUnit.test("defaultHomepage", assert => {
|
||||
Discourse.SiteSettings.top_menu = "latest|top|hot";
|
||||
assert.equal(defaultHomepage(), "latest", "default homepage is the first item in the top_menu site setting");
|
||||
var meta = document.createElement("meta");
|
||||
meta.name = "discourse_current_homepage";
|
||||
meta.content = "hot";
|
||||
document.body.appendChild(meta);
|
||||
assert.equal(defaultHomepage(), "hot", "default homepage is pulled from <meta name=discourse_current_homepage>");
|
||||
document.body.removeChild(meta);
|
||||
});
|
||||
|
||||
QUnit.test("setDefaultHomepage", assert => {
|
||||
var meta = document.createElement("meta");
|
||||
meta.name = "discourse_current_homepage";
|
||||
meta.content = "hot";
|
||||
document.body.appendChild(meta);
|
||||
setDefaultHomepage("top");
|
||||
assert.equal(meta.content, "top", "default homepage set by setDefaultHomepage");
|
||||
document.body.removeChild(meta);
|
||||
});
|
||||
|
||||
QUnit.test("caretRowCol", assert => {
|
||||
|
|
Loading…
Reference in New Issue