mirror of
https://github.com/discourse/discourse.git
synced 2026-08-04 10:23:17 -05:00
FEATURE: Remove experimental label & setting toggle for what's new (#38008)
We now have upcoming changes which makes the related setting toggle and experimental label for the what's new page redundant. This commit removes both as a first step towards merging these two pages together.
This commit is contained in:
@@ -741,17 +741,6 @@
|
||||
}
|
||||
}
|
||||
|
||||
.admin-new-feature-item__header-experimental {
|
||||
color: var(--tertiary);
|
||||
background-color: var(--tertiary-very-low);
|
||||
padding: 0.5em;
|
||||
font-size: var(--font-down-3);
|
||||
margin-left: 0.5rem;
|
||||
font-weight: 400;
|
||||
border-radius: var(--d-border-radius);
|
||||
display: inline-block;
|
||||
}
|
||||
|
||||
.admin-new-feature-item__body {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
@@ -825,13 +814,3 @@
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.admin-new-features__experiments-filter {
|
||||
display: flex;
|
||||
margin-bottom: 1em;
|
||||
align-items: center;
|
||||
|
||||
.d-toggle-switch {
|
||||
margin-right: 0.5em;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -6490,23 +6490,6 @@ en:
|
||||
no_new_features_found: "There are no items in the feed or your selected filter returned no results. You can see previous new feature announcements on <a href='%{url}' target='_blank'>the Discourse Meta community</a>."
|
||||
no_new_features_error: "There was an error loading the feed. You can see previous new feature announcements on <a href='%{url}' target='_blank'>the Discourse Meta community</a>."
|
||||
learn_more: "Learn more..."
|
||||
experimental: "Experimental"
|
||||
only_experiments: "Only show experimental features"
|
||||
experiment_enabled: "You have enabled the experimental feature."
|
||||
experiment_disabled: "You have disabled the experimental feature."
|
||||
feature_enabled: "You have enabled the feature."
|
||||
feature_disabled: "You have disabled the feature."
|
||||
toggled_too_fast: "You have switched the toggle too fast. Please wait a few seconds before trying again."
|
||||
experiment_tooltip:
|
||||
title_disabled: "Try this experimental feature"
|
||||
title_enabled: "Turn off experimental feature"
|
||||
content_disabled: "Give our newest feature in development a spin! It's still in the experimental stage, so we might remove it at any time. You can opt out whenever you like.<br/><br/>Changing this will enable the feature for all users."
|
||||
content_enabled: "Changing this will disable the feature for all users."
|
||||
feature_tooltip:
|
||||
title_disabled: "Try this feature"
|
||||
title_enabled: "Turn off feature"
|
||||
content_disabled: "Give this new feature a spin! You can opt out whenever you like.<br/><br/>Changing this will enable the feature for all users."
|
||||
content_enabled: "Changing this will disable the feature for all users."
|
||||
|
||||
last_checked: "Last checked"
|
||||
refresh_problems: "Refresh"
|
||||
|
||||
@@ -1,115 +1,14 @@
|
||||
/* eslint-disable ember/no-tracked-properties-from-args */
|
||||
import Component from "@glimmer/component";
|
||||
import { tracked } from "@glimmer/tracking";
|
||||
import { on } from "@ember/modifier";
|
||||
import { action } from "@ember/object";
|
||||
import { service } from "@ember/service";
|
||||
import { dasherize } from "@ember/string";
|
||||
import { htmlSafe } from "@ember/template";
|
||||
import CookText from "discourse/components/cook-text";
|
||||
import DToggleSwitch from "discourse/components/d-toggle-switch";
|
||||
import DTooltip from "discourse/float-kit/components/d-tooltip";
|
||||
import icon from "discourse/helpers/d-icon";
|
||||
import { ajax } from "discourse/lib/ajax";
|
||||
import { popupAjaxError } from "discourse/lib/ajax-error";
|
||||
import { and, not } from "discourse/truth-helpers";
|
||||
import { i18n } from "discourse-i18n";
|
||||
|
||||
export default class DiscourseNewFeatureItem extends Component {
|
||||
@service toasts;
|
||||
|
||||
@tracked settingEnabled = this.args.item.setting_enabled;
|
||||
@tracked toggleSettingDisabled = false;
|
||||
|
||||
get isExperiment() {
|
||||
return this.args.item.experiment;
|
||||
}
|
||||
|
||||
get identifier() {
|
||||
return this.args.item.title ? dasherize(this.args.item.title) : null;
|
||||
}
|
||||
|
||||
@action
|
||||
async toggleExperiment() {
|
||||
if (this.toggleSettingDisabled) {
|
||||
this.toasts.error({
|
||||
duration: "short",
|
||||
data: {
|
||||
message: i18n("admin.dashboard.new_features.toggled_too_fast"),
|
||||
},
|
||||
});
|
||||
return;
|
||||
}
|
||||
this.settingEnabled = !this.settingEnabled;
|
||||
this.toggleSettingDisabled = true;
|
||||
|
||||
setTimeout(() => {
|
||||
this.toggleSettingDisabled = false;
|
||||
}, 5000);
|
||||
try {
|
||||
await ajax("/admin/toggle-feature", {
|
||||
type: "POST",
|
||||
data: {
|
||||
setting_name: this.args.item.related_site_setting,
|
||||
enabled: this.settingEnabled,
|
||||
},
|
||||
});
|
||||
|
||||
const enabledMsg = this.isExperiment
|
||||
? "admin.dashboard.new_features.experiment_enabled"
|
||||
: "admin.dashboard.new_features.feature_enabled";
|
||||
const disabledMsg = this.isExperiment
|
||||
? "admin.dashboard.new_features.experiment_disabled"
|
||||
: "admin.dashboard.new_features.feature_disabled";
|
||||
|
||||
this.toasts.success({
|
||||
duration: "short",
|
||||
data: {
|
||||
message: this.settingEnabled ? i18n(enabledMsg) : i18n(disabledMsg),
|
||||
},
|
||||
});
|
||||
} catch (error) {
|
||||
this.settingEnabled = !this.settingEnabled;
|
||||
return popupAjaxError(error);
|
||||
}
|
||||
}
|
||||
|
||||
get tooltipTitle() {
|
||||
const experimentalTitleEnabled = this.isExperiment
|
||||
? "admin.dashboard.new_features.experiment_tooltip.title_enabled"
|
||||
: "admin.dashboard.new_features.feature_tooltip.title_enabled";
|
||||
|
||||
const experimentalTitleDisabled = this.isExperiment
|
||||
? "admin.dashboard.new_features.feature_tooltip.title_disabled"
|
||||
: "admin.dashboard.new_features.feature_tooltip.title_disabled";
|
||||
|
||||
return htmlSafe(
|
||||
i18n(
|
||||
this.settingEnabled
|
||||
? experimentalTitleEnabled
|
||||
: experimentalTitleDisabled
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
get tooltipDescription() {
|
||||
const experimentalDescriptionEnabled = this.isExperiment
|
||||
? "admin.dashboard.new_features.experiment_tooltip.content_enabled"
|
||||
: "admin.dashboard.new_features.feature_tooltip.content_enabled";
|
||||
|
||||
const experimentalDescriptionDisabled = this.isExperiment
|
||||
? "admin.dashboard.new_features.experiment_tooltip.content_disabled"
|
||||
: "admin.dashboard.new_features.feature_tooltip.content_disabled";
|
||||
|
||||
return htmlSafe(
|
||||
i18n(
|
||||
this.settingEnabled
|
||||
? experimentalDescriptionEnabled
|
||||
: experimentalDescriptionDisabled
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
<template>
|
||||
<div
|
||||
class="admin-new-feature-item"
|
||||
@@ -124,12 +23,6 @@ export default class DiscourseNewFeatureItem extends Component {
|
||||
{{/if}}
|
||||
<h3>
|
||||
{{@item.title}}
|
||||
{{#if @item.experiment}}
|
||||
<span class="admin-new-feature-item__header-experimental">
|
||||
{{icon "flask"}}
|
||||
{{i18n "admin.dashboard.new_features.experimental"}}
|
||||
</span>
|
||||
{{/if}}
|
||||
</h3>
|
||||
</div>
|
||||
|
||||
@@ -159,28 +52,6 @@ export default class DiscourseNewFeatureItem extends Component {
|
||||
</a>
|
||||
{{/if}}
|
||||
</div>
|
||||
{{#if @item.related_site_setting}}
|
||||
<div class="admin-new-feature-item__feature-toggle">
|
||||
<DTooltip>
|
||||
<:trigger>
|
||||
<DToggleSwitch
|
||||
@state={{this.settingEnabled}}
|
||||
{{on "click" this.toggleExperiment}}
|
||||
/>
|
||||
</:trigger>
|
||||
<:content>
|
||||
<div class="admin-new-feature-item__tooltip">
|
||||
<div class="admin-new-feature-item__tooltip-header">
|
||||
{{this.tooltipTitle}}
|
||||
</div>
|
||||
<div class="admin-new-feature-item__tooltip-content">
|
||||
{{this.tooltipDescription}}
|
||||
</div>
|
||||
</div>
|
||||
</:content>
|
||||
</DTooltip>
|
||||
</div>
|
||||
{{/if}}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -1,14 +1,11 @@
|
||||
import Component from "@glimmer/component";
|
||||
import { tracked } from "@glimmer/tracking";
|
||||
import { on } from "@ember/modifier";
|
||||
import { action } from "@ember/object";
|
||||
import didInsert from "@ember/render-modifiers/modifiers/did-insert";
|
||||
import { service } from "@ember/service";
|
||||
import AdminConfigAreaCard from "discourse/admin/components/admin-config-area-card";
|
||||
import AdminConfigAreaEmptyList from "discourse/admin/components/admin-config-area-empty-list";
|
||||
import DashboardNewFeatureItem from "discourse/admin/components/dashboard-new-feature-item";
|
||||
import ConditionalLoadingSpinner from "discourse/components/conditional-loading-spinner";
|
||||
import DToggleSwitch from "discourse/components/d-toggle-switch";
|
||||
import { ajax } from "discourse/lib/ajax";
|
||||
import { popupAjaxError } from "discourse/lib/ajax-error";
|
||||
import { bind } from "discourse/lib/decorators";
|
||||
@@ -20,7 +17,6 @@ export default class DashboardNewFeatures extends Component {
|
||||
@tracked newFeatures = null;
|
||||
@tracked isLoading = true;
|
||||
@tracked feedError = false;
|
||||
@tracked onlyExperiments = false;
|
||||
|
||||
constructor() {
|
||||
super(...arguments);
|
||||
@@ -62,7 +58,7 @@ export default class DashboardNewFeatures extends Component {
|
||||
get groupedNewFeatures() {
|
||||
return Object.keys(this.newFeatures)
|
||||
.map((date) => {
|
||||
const visibleFeatures = this.newFeatures[date].filter(this.showFeature);
|
||||
const visibleFeatures = this.newFeatures[date];
|
||||
|
||||
if (visibleFeatures.length === 0) {
|
||||
return null;
|
||||
@@ -94,35 +90,12 @@ export default class DashboardNewFeatures extends Component {
|
||||
return "";
|
||||
}
|
||||
|
||||
@bind
|
||||
showFeature(feature) {
|
||||
if (!this.onlyExperiments) {
|
||||
return true;
|
||||
}
|
||||
|
||||
return feature.experiment === true;
|
||||
}
|
||||
|
||||
@action
|
||||
toggleOnlyExperiments() {
|
||||
this.onlyExperiments = !this.onlyExperiments;
|
||||
}
|
||||
|
||||
<template>
|
||||
<div
|
||||
class="admin-config-area__primary-content"
|
||||
{{didInsert this.loadNewFeatures}}
|
||||
>
|
||||
<ConditionalLoadingSpinner @condition={{this.isLoading}}>
|
||||
<div class="admin-new-features__experiments-filter">
|
||||
<DToggleSwitch
|
||||
@state={{this.onlyExperiments}}
|
||||
{{on "click" this.toggleOnlyExperiments}}
|
||||
/>
|
||||
<span>
|
||||
{{i18n "admin.dashboard.new_features.only_experiments"}}
|
||||
</span>
|
||||
</div>
|
||||
{{#each this.groupedNewFeatures as |groupedFeatures|}}
|
||||
<AdminConfigAreaCard
|
||||
class="admin-new-features__group"
|
||||
|
||||
@@ -153,20 +153,6 @@ module DiscourseUpdates
|
||||
end
|
||||
return nil if entries.nil?
|
||||
|
||||
entries.map! do |item|
|
||||
next item if !item["related_site_setting"]
|
||||
|
||||
if !SiteSetting.respond_to?(item["related_site_setting"]) ||
|
||||
SiteSetting.type_supervisor.get_type(item["related_site_setting"].to_sym) != :bool
|
||||
item["related_site_setting"] = nil
|
||||
item["setting_enabled"] = false
|
||||
else
|
||||
item["setting_enabled"] = SiteSetting.send(item["related_site_setting"].to_sym) if item
|
||||
end
|
||||
|
||||
item
|
||||
end
|
||||
|
||||
entries.select! do |item|
|
||||
begin
|
||||
valid_version =
|
||||
|
||||
@@ -277,41 +277,6 @@ RSpec.describe DiscourseUpdates do
|
||||
expect(result[1]["title"]).to eq("Bells")
|
||||
end
|
||||
|
||||
it "correctly shows features with correct boolean site settings" do
|
||||
features_with_versions = [
|
||||
{
|
||||
"emoji" => "🤾",
|
||||
"title" => "Bells",
|
||||
"created_at" => 2.days.ago,
|
||||
"related_site_setting" => "enable_mobile_theme",
|
||||
},
|
||||
{
|
||||
"emoji" => "🙈",
|
||||
"title" => "Whistles",
|
||||
"created_at" => 3.days.ago,
|
||||
"related_site_setting" => "default_theme_id",
|
||||
},
|
||||
{
|
||||
"emoji" => "🙈",
|
||||
"title" => "Confetti",
|
||||
"created_at" => 4.days.ago,
|
||||
"related_site_setting" => "wrong value",
|
||||
},
|
||||
]
|
||||
|
||||
Discourse.redis.set("new_features", MultiJson.dump(features_with_versions))
|
||||
DiscourseUpdates.last_installed_version = "2.7.0.beta2"
|
||||
result = DiscourseUpdates.new_features
|
||||
|
||||
expect(result.length).to eq(3)
|
||||
expect(result[0]["setting_enabled"]).to eq(true)
|
||||
expect(result[0]["related_site_setting"]).to eq("enable_mobile_theme")
|
||||
expect(result[1]["setting_enabled"]).to eq(false)
|
||||
expect(result[1]["related_site_setting"]).to be_nil
|
||||
expect(result[2]["setting_enabled"]).to eq(false)
|
||||
expect(result[2]["related_site_setting"]).to be_nil
|
||||
end
|
||||
|
||||
it "correctly shows features when related plugins are installed" do
|
||||
Discourse.stubs(:plugins_by_name).returns({ "discourse-ai" => true })
|
||||
|
||||
|
||||
@@ -128,146 +128,4 @@ describe "Admin What's New Page", type: :system do
|
||||
expect(whats_new_page).to have_emoji
|
||||
expect(whats_new_page).to have_no_screenshot
|
||||
end
|
||||
|
||||
describe "items with a related_site_setting" do
|
||||
before do
|
||||
set_new_features_payload(
|
||||
[
|
||||
{
|
||||
"id" => 7,
|
||||
"user_id" => 1,
|
||||
"emoji" => "😍",
|
||||
"title" => "New feature",
|
||||
"description" => "New feature description",
|
||||
"link" => "https://meta.discourse.org",
|
||||
"tier" => [],
|
||||
"discourse_version" => "",
|
||||
"created_at" => "2023-11-10T02:52:41.462Z",
|
||||
"updated_at" => "2023-11-10T04:28:47.020Z",
|
||||
"related_site_setting" => "enable_form_templates",
|
||||
"experiment" => false,
|
||||
},
|
||||
],
|
||||
)
|
||||
end
|
||||
|
||||
it "toggles the attached site setting and shows the correct state" do
|
||||
whats_new_page.visit
|
||||
whats_new_page.within_new_feature_item("New feature") do
|
||||
expect(whats_new_page.enable_item_toggle.unchecked?).to be_truthy
|
||||
whats_new_page.enable_item_toggle.toggle
|
||||
end
|
||||
expect(page).to have_content(I18n.t("admin_js.admin.dashboard.new_features.feature_enabled"))
|
||||
whats_new_page.visit
|
||||
expect(SiteSetting.enable_form_templates).to be true
|
||||
expect(whats_new_page.enable_item_toggle.checked?).to be_truthy
|
||||
end
|
||||
end
|
||||
|
||||
describe "experimental items" do
|
||||
it "displays experimental feature toggle and has the correct state" do
|
||||
set_new_features_payload(
|
||||
[
|
||||
{
|
||||
"id" => 7,
|
||||
"user_id" => 1,
|
||||
"emoji" => "😍",
|
||||
"title" => "New feature",
|
||||
"description" => "New feature description",
|
||||
"link" => "https://meta.discourse.org",
|
||||
"tier" => [],
|
||||
"discourse_version" => "",
|
||||
"created_at" => "2023-11-10T02:52:41.462Z",
|
||||
"updated_at" => "2023-11-10T04:28:47.020Z",
|
||||
"related_site_setting" => "enable_form_templates",
|
||||
"experiment" => false,
|
||||
},
|
||||
],
|
||||
)
|
||||
whats_new_page.visit
|
||||
expect(whats_new_page).to have_toggle_feature_button()
|
||||
end
|
||||
|
||||
it "displays experimental text next to feature title when feature is experimental" do
|
||||
set_new_features_payload(
|
||||
[
|
||||
{
|
||||
"id" => 7,
|
||||
"user_id" => 1,
|
||||
"emoji" => "😍",
|
||||
"title" => "New feature",
|
||||
"description" => "New feature description",
|
||||
"link" => "https://meta.discourse.org",
|
||||
"tier" => [],
|
||||
"discourse_version" => "",
|
||||
"created_at" => "2023-11-10T02:52:41.462Z",
|
||||
"updated_at" => "2023-11-10T04:28:47.020Z",
|
||||
"related_site_setting" => "enable_form_templates",
|
||||
"experiment" => true,
|
||||
},
|
||||
],
|
||||
)
|
||||
whats_new_page.visit
|
||||
expect(whats_new_page).to have_experimental_text
|
||||
end
|
||||
|
||||
it "does not display experimental text next to feature title when feature is not experimental" do
|
||||
set_new_features_payload(
|
||||
[
|
||||
{
|
||||
"id" => 7,
|
||||
"user_id" => 1,
|
||||
"emoji" => "😍",
|
||||
"title" => "New feature",
|
||||
"description" => "New feature description",
|
||||
"link" => "https://meta.discourse.org",
|
||||
"tier" => [],
|
||||
"discourse_version" => "",
|
||||
"created_at" => "2023-11-10T02:52:41.462Z",
|
||||
"updated_at" => "2023-11-10T04:28:47.020Z",
|
||||
},
|
||||
],
|
||||
)
|
||||
whats_new_page.visit
|
||||
expect(whats_new_page).to have_no_experimental_text
|
||||
end
|
||||
|
||||
it "allows filtering to only show experimental items" do
|
||||
set_new_features_payload(
|
||||
[
|
||||
{
|
||||
"id" => 7,
|
||||
"user_id" => 1,
|
||||
"emoji" => "😍",
|
||||
"title" => "New feature",
|
||||
"description" => "New feature description",
|
||||
"link" => "https://meta.discourse.org",
|
||||
"tier" => [],
|
||||
"discourse_version" => "",
|
||||
"created_at" => "2023-11-10T02:52:41.462Z",
|
||||
"updated_at" => "2023-11-10T04:28:47.020Z",
|
||||
"related_site_setting" => "enable_form_templates",
|
||||
"experiment" => true,
|
||||
},
|
||||
{
|
||||
"id" => 8,
|
||||
"user_id" => 1,
|
||||
"emoji" => "🥹",
|
||||
"title" => "Non experimental feature",
|
||||
"description" => "Cool description",
|
||||
"link" => "https://meta.discourse.org",
|
||||
"tier" => [],
|
||||
"discourse_version" => "",
|
||||
"created_at" => "2023-11-10T02:52:41.462Z",
|
||||
"updated_at" => "2023-11-10T04:28:47.020Z",
|
||||
"related_site_setting" => nil,
|
||||
"experiment" => false,
|
||||
},
|
||||
],
|
||||
)
|
||||
whats_new_page.visit
|
||||
whats_new_page.toggle_experiments_only
|
||||
expect(whats_new_page).to have_experimental_text
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
Reference in New Issue
Block a user