DEV: Ember 3.8.0

Co-Authored-By: majakomel <maja.komel@gmail.com>
This commit is contained in:
Maja Komel 2019-04-26 12:16:21 +02:00 committed by Joffrey JAFFEUX
parent c617e512ad
commit 4b455e741e
63 changed files with 573 additions and 438 deletions

View File

@ -49,7 +49,7 @@ gem 'onebox', '1.8.86'
gem 'http_accept_language', '~>2.0.5', require: false gem 'http_accept_language', '~>2.0.5', require: false
gem 'ember-rails', '0.18.5' gem 'ember-rails', '0.18.5'
gem 'discourse-ember-source', '~> 3.7.0' gem 'discourse-ember-source', '~> 3.8.0'
gem 'ember-handlebars-template', '0.8.0' gem 'ember-handlebars-template', '0.8.0'
gem 'barber' gem 'barber'

View File

@ -108,7 +108,7 @@ GEM
terminal-table (~> 1) terminal-table (~> 1)
debug_inspector (0.0.3) debug_inspector (0.0.3)
diff-lcs (1.3) diff-lcs (1.3)
discourse-ember-source (3.7.0.2) discourse-ember-source (3.8.0.1)
discourse_image_optim (0.26.2) discourse_image_optim (0.26.2)
exifr (~> 1.2, >= 1.2.2) exifr (~> 1.2, >= 1.2.2)
fspath (~> 3.0) fspath (~> 3.0)
@ -472,7 +472,7 @@ DEPENDENCIES
colored2 colored2
cppjieba_rb cppjieba_rb
danger danger
discourse-ember-source (~> 3.7.0) discourse-ember-source (~> 3.8.0)
discourse_image_optim discourse_image_optim
email_reply_trimmer (~> 0.1) email_reply_trimmer (~> 0.1)
ember-handlebars-template (= 0.8.0) ember-handlebars-template (= 0.8.0)

View File

@ -1,5 +1,6 @@
import { iconHTML } from "discourse-common/lib/icon-library"; import { iconHTML } from "discourse-common/lib/icon-library";
import { bufferedRender } from "discourse-common/lib/buffered-render"; import { bufferedRender } from "discourse-common/lib/buffered-render";
import computed from "ember-addons/ember-computed-decorators";
/*global Resumable:true */ /*global Resumable:true */
@ -27,18 +28,19 @@ export default Ember.Component.extend(
rerenderTriggers: ["isUploading", "progress"], rerenderTriggers: ["isUploading", "progress"],
translatedTitle: function() { @computed("title", "text")
const title = this.get("title"); translatedTitle(title, text) {
return title ? I18n.t(title) : this.get("text"); return title ? I18n.t(title) : text;
}.property("title", "text"), },
text: function() { @computed("isUploading", "progress")
if (this.get("isUploading")) { text(isUploading, progress) {
return this.get("progress") + " %"; if (isUploading) {
return progress + " %";
} else { } else {
return this.get("uploadText"); return this.get("uploadText");
} }
}.property("isUploading", "progress"), },
buildBuffer(buffer) { buildBuffer(buffer) {
const icon = this.get("isUploading") ? "times" : "upload"; const icon = this.get("isUploading") ? "times" : "upload";

View File

@ -1,6 +1,7 @@
import { popupAjaxError } from "discourse/lib/ajax-error"; import { popupAjaxError } from "discourse/lib/ajax-error";
import { bufferedProperty } from "discourse/mixins/buffered-content"; import { bufferedProperty } from "discourse/mixins/buffered-content";
import { propertyNotEqual } from "discourse/lib/computed"; import { propertyNotEqual } from "discourse/lib/computed";
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Controller.extend(bufferedProperty("model"), { export default Ember.Controller.extend(bufferedProperty("model"), {
adminBadges: Ember.inject.controller(), adminBadges: Ember.inject.controller(),
@ -17,14 +18,13 @@ export default Ember.Controller.extend(bufferedProperty("model"), {
readOnly: Ember.computed.alias("buffered.system"), readOnly: Ember.computed.alias("buffered.system"),
showDisplayName: propertyNotEqual("name", "displayName"), showDisplayName: propertyNotEqual("name", "displayName"),
hasQuery: function() { @computed("model.query", "buffered.query")
const bQuery = this.get("buffered.query"); hasQuery(modelQuery, bufferedQuery) {
if (bQuery) { if (bufferedQuery) {
return bQuery.trim().length > 0; return bufferedQuery.trim().length > 0;
} }
const mQuery = this.get("model.query"); return modelQuery && modelQuery.trim().length > 0;
return mQuery && mQuery.trim().length > 0; },
}.property("model.query", "buffered.query"),
_resetSaving: function() { _resetSaving: function() {
this.set("saving", false); this.set("saving", false);

View File

@ -1,17 +1,18 @@
import { popupAjaxError } from "discourse/lib/ajax-error"; import { popupAjaxError } from "discourse/lib/ajax-error";
import { bufferedProperty } from "discourse/mixins/buffered-content"; import { bufferedProperty } from "discourse/mixins/buffered-content";
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Controller.extend(bufferedProperty("emailTemplate"), { export default Ember.Controller.extend(bufferedProperty("emailTemplate"), {
saved: false, saved: false,
hasMultipleSubjects: function() { @computed("buffered")
const buffered = this.get("buffered"); hasMultipleSubjects(buffered) {
if (buffered.getProperties("subject")["subject"]) { if (buffered.getProperties("subject")["subject"]) {
return false; return false;
} else { } else {
return buffered.getProperties("id")["id"]; return buffered.getProperties("id")["id"];
} }
}.property("buffered"), },
actions: { actions: {
saveChanges() { saveChanges() {

View File

@ -1,6 +1,7 @@
import { exportEntity } from "discourse/lib/export-csv"; import { exportEntity } from "discourse/lib/export-csv";
import { outputExportResult } from "discourse/lib/export-result"; import { outputExportResult } from "discourse/lib/export-result";
import StaffActionLog from "admin/models/staff-action-log"; import StaffActionLog from "admin/models/staff-action-log";
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Controller.extend({ export default Ember.Controller.extend({
loading: false, loading: false,
@ -20,14 +21,14 @@ export default Ember.Controller.extend({
} }
}.observes("filterActionId"), }.observes("filterActionId"),
actionFilter: function() { @computed("filters.action_name")
var name = this.get("filters.action_name"); actionFilter(name) {
if (name) { if (name) {
return I18n.t("admin.logs.staff_actions.actions." + name); return I18n.t("admin.logs.staff_actions.actions." + name);
} else { } else {
return null; return null;
} }
}.property("filters.action_name"), },
showInstructions: Ember.computed.gt("model.length", 0), showInstructions: Ember.computed.gt("model.length", 0),

View File

@ -1,4 +1,7 @@
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Controller.extend({ export default Ember.Controller.extend({
@computed
adminRoutes: function() { adminRoutes: function() {
return this.get("model") return this.get("model")
.map(p => { .map(p => {
@ -7,7 +10,8 @@ export default Ember.Controller.extend({
} }
}) })
.compact(); .compact();
}.property(), },
actions: { actions: {
clearFilter() { clearFilter() {
this.setProperties({ filter: "", onlyOverridden: false }); this.setProperties({ filter: "", onlyOverridden: false });

View File

@ -1,5 +1,6 @@
import GrantBadgeController from "discourse/mixins/grant-badge-controller"; import GrantBadgeController from "discourse/mixins/grant-badge-controller";
import { popupAjaxError } from "discourse/lib/ajax-error"; import { popupAjaxError } from "discourse/lib/ajax-error";
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Controller.extend(GrantBadgeController, { export default Ember.Controller.extend(GrantBadgeController, {
adminUser: Ember.inject.controller(), adminUser: Ember.inject.controller(),
@ -10,7 +11,8 @@ export default Ember.Controller.extend(GrantBadgeController, {
sortedBadges: Ember.computed.sort("model", "badgeSortOrder"), sortedBadges: Ember.computed.sort("model", "badgeSortOrder"),
badgeSortOrder: ["granted_at:desc"], badgeSortOrder: ["granted_at:desc"],
groupedBadges: function() { @computed("model", "model.[]", "model.expandedBadges.[]")
groupedBadges() {
const allBadges = this.get("model"); const allBadges = this.get("model");
var grouped = _.groupBy(allBadges, badge => badge.badge_id); var grouped = _.groupBy(allBadges, badge => badge.badge_id);
@ -46,7 +48,7 @@ export default Ember.Controller.extend(GrantBadgeController, {
.sortBy(group => group.granted_at) .sortBy(group => group.granted_at)
.reverse() .reverse()
.value(); .value();
}.property("model", "model.[]", "model.expandedBadges.[]"), },
actions: { actions: {
expandGroup: function(userBadge) { expandGroup: function(userBadge) {

View File

@ -2,6 +2,7 @@ import debounce from "discourse/lib/debounce";
import { i18n } from "discourse/lib/computed"; import { i18n } from "discourse/lib/computed";
import AdminUser from "admin/models/admin-user"; import AdminUser from "admin/models/admin-user";
import CanCheckEmails from "discourse/mixins/can-check-emails"; import CanCheckEmails from "discourse/mixins/can-check-emails";
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Controller.extend(CanCheckEmails, { export default Ember.Controller.extend(CanCheckEmails, {
model: null, model: null,
@ -14,9 +15,10 @@ export default Ember.Controller.extend(CanCheckEmails, {
selectAll: false, selectAll: false,
searchHint: i18n("search_hint"), searchHint: i18n("search_hint"),
title: function() { @computed("query")
return I18n.t("admin.users.titles." + this.get("query")); title(query) {
}.property("query"), return I18n.t("admin.users.titles." + query);
},
_filterUsers: debounce(function() { _filterUsers: debounce(function() {
this._refreshUsers(); this._refreshUsers();

View File

@ -1,19 +1,20 @@
export default Ember.Mixin.create({ import computed from "ember-addons/ember-computed-decorators";
overridden: function() {
let val = this.get("value"),
defaultVal = this.get("default");
export default Ember.Mixin.create({
@computed("value", "default")
overridden(val, defaultVal) {
if (val === null) val = ""; if (val === null) val = "";
if (defaultVal === null) defaultVal = ""; if (defaultVal === null) defaultVal = "";
return val.toString() !== defaultVal.toString(); return val.toString() !== defaultVal.toString();
}.property("value", "default"), },
validValues: function() { @computed("valid_values")
validValues(validValues) {
const vals = [], const vals = [],
translateNames = this.get("translate_names"); translateNames = this.get("translate_names");
this.get("valid_values").forEach(v => { validValues.forEach(v => {
if (v.name && v.name.length > 0 && translateNames) { if (v.name && v.name.length > 0 && translateNames) {
vals.addObject({ name: I18n.t(v.name), value: v.value }); vals.addObject({ name: I18n.t(v.name), value: v.value });
} else { } else {
@ -21,12 +22,12 @@ export default Ember.Mixin.create({
} }
}); });
return vals; return vals;
}.property("valid_values"), },
allowsNone: function() { @computed("valid_values")
const validValues = this.get("valid_values"); allowsNone(validValues) {
if (validValues && validValues.indexOf("") >= 0) { if (validValues && validValues.indexOf("") >= 0) {
return "admin.settings.none"; return "admin.settings.none";
} }
}.property("valid_values") }
}); });

View File

@ -293,17 +293,19 @@ const AdminUser = Discourse.User.extend({
}); });
}, },
canLockTrustLevel: function() { @computed("trust_level")
return this.get("trust_level") < 4; canLockTrustLevel(trustLevel) {
}.property("trust_level"), return trustLevel < 4;
},
canSuspend: Ember.computed.not("staff"), canSuspend: Ember.computed.not("staff"),
suspendDuration: function() { @computed("suspended_till", "suspended_at")
const suspended_at = moment(this.suspended_at), suspendDuration(suspendedTill, suspendedAt) {
suspended_till = moment(this.suspended_till); suspendedAt = moment(suspendedAt);
return suspended_at.format("L") + " - " + suspended_till.format("L"); suspendedTill = moment(suspendedTill);
}.property("suspended_till", "suspended_at"), return suspendedAt.format("L") + " - " + suspendedTill.format("L");
},
suspend(data) { suspend(data) {
return ajax(`/admin/users/${this.id}/suspend`, { return ajax(`/admin/users/${this.id}/suspend`, {

View File

@ -1,5 +1,6 @@
import { ajax } from "discourse/lib/ajax"; import { ajax } from "discourse/lib/ajax";
import ColorSchemeColor from "admin/models/color-scheme-color"; import ColorSchemeColor from "admin/models/color-scheme-color";
import computed from "ember-addons/ember-computed-decorators";
const ColorScheme = Discourse.Model.extend(Ember.Copyable, { const ColorScheme = Discourse.Model.extend(Ember.Copyable, {
init: function() { init: function() {
@ -7,9 +8,10 @@ const ColorScheme = Discourse.Model.extend(Ember.Copyable, {
this.startTrackingChanges(); this.startTrackingChanges();
}, },
description: function() { @computed
description() {
return "" + this.name; return "" + this.name;
}.property(), },
startTrackingChanges: function() { startTrackingChanges: function() {
this.set("originals", { this.set("originals", {
@ -44,7 +46,8 @@ const ColorScheme = Discourse.Model.extend(Ember.Copyable, {
return newScheme; return newScheme;
}, },
changed: function() { @computed("name", "colors.@each.changed", "saving")
changed() {
if (!this.originals) return false; if (!this.originals) return false;
if (this.originals["name"] !== this.get("name")) return true; if (this.originals["name"] !== this.get("name")) return true;
if ( if (
@ -54,24 +57,23 @@ const ColorScheme = Discourse.Model.extend(Ember.Copyable, {
) )
return true; return true;
return false; return false;
}.property("name", "colors.@each.changed", "saving"), },
disableSave: function() { @computed("changed")
disableSave(changed) {
if (this.get("theme_id")) { if (this.get("theme_id")) {
return false; return false;
} }
return ( return (
!this.get("changed") || !changed ||
this.get("saving") || this.get("saving") ||
_.any(this.get("colors"), function(c) { _.any(this.get("colors"), function(c) {
return !c.get("valid"); return !c.get("valid");
}) })
); );
}.property("changed"), },
newRecord: function() { newRecord: Ember.computed.not("id"),
return !this.get("id");
}.property("id"),
save: function(opts) { save: function(opts) {
if (this.get("is_base") || this.get("disableSave")) return; if (this.get("is_base") || this.get("disableSave")) return;

View File

@ -76,25 +76,35 @@ const Report = Discourse.Model.extend({
} }
}, },
todayCount: function() { @computed("data", "average")
todayCount() {
return this.valueAt(0); return this.valueAt(0);
}.property("data", "average"), },
yesterdayCount: function() {
return this.valueAt(1);
}.property("data", "average"),
sevenDaysAgoCount: function() {
return this.valueAt(7);
}.property("data", "average"),
thirtyDaysAgoCount: function() {
return this.valueAt(30);
}.property("data", "average"),
lastSevenDaysCount: function() { @computed("data", "average")
yesterdayCount() {
return this.valueAt(1);
},
@computed("data", "average")
sevenDaysAgoCount() {
return this.valueAt(7);
},
@computed("data", "average")
thirtyDaysAgoCount() {
return this.valueAt(30);
},
@computed("data", "average")
lastSevenDaysCount() {
return this.averageCount(7, this.valueFor(1, 7)); return this.averageCount(7, this.valueFor(1, 7));
}.property("data", "average"), },
lastThirtyDaysCount: function() {
@computed("data", "average")
lastThirtyDaysCount() {
return this.averageCount(30, this.valueFor(1, 30)); return this.averageCount(30, this.valueFor(1, 30));
}.property("data", "average"), },
averageCount(count, value) { averageCount(count, value) {
return this.get("average") ? value / count : value; return this.get("average") ? value / count : value;

View File

@ -1,8 +1,11 @@
import { ajax } from "discourse/lib/ajax"; import { ajax } from "discourse/lib/ajax";
import computed from "ember-addons/ember-computed-decorators";
const ScreenedEmail = Discourse.Model.extend({ const ScreenedEmail = Discourse.Model.extend({
actionName: function() { @computed("action")
return I18n.t("admin.logs.screened_actions." + this.get("action")); actionName(action) {
}.property("action"), return I18n.t("admin.logs.screened_actions." + action);
},
clearBlock: function() { clearBlock: function() {
return ajax("/admin/logs/screened_emails/" + this.get("id"), { return ajax("/admin/logs/screened_emails/" + this.get("id"), {

View File

@ -1,8 +1,11 @@
import { ajax } from "discourse/lib/ajax"; import { ajax } from "discourse/lib/ajax";
import computed from "ember-addons/ember-computed-decorators";
const ScreenedUrl = Discourse.Model.extend({ const ScreenedUrl = Discourse.Model.extend({
actionName: function() { @computed("action")
return I18n.t("admin.logs.screened_actions." + this.get("action")); actionName(action) {
}.property("action") return I18n.t("admin.logs.screened_actions." + action);
}
}); });
ScreenedUrl.reopenClass({ ScreenedUrl.reopenClass({

View File

@ -11,36 +11,7 @@ export default Discourse.Model.extend({
return Math.round((minDaysVisited * 100) / timePeriod); return Math.round((minDaysVisited * 100) / timePeriod);
}, },
met: function() { @computed(
return {
days_visited: this.get("days_visited") >= this.get("min_days_visited"),
topics_replied_to:
this.get("num_topics_replied_to") >= this.get("min_topics_replied_to"),
topics_viewed: this.get("topics_viewed") >= this.get("min_topics_viewed"),
posts_read: this.get("posts_read") >= this.get("min_posts_read"),
topics_viewed_all_time:
this.get("topics_viewed_all_time") >=
this.get("min_topics_viewed_all_time"),
posts_read_all_time:
this.get("posts_read_all_time") >= this.get("min_posts_read_all_time"),
flagged_posts:
this.get("num_flagged_posts") <= this.get("max_flagged_posts"),
flagged_by_users:
this.get("num_flagged_by_users") <= this.get("max_flagged_by_users"),
likes_given: this.get("num_likes_given") >= this.get("min_likes_given"),
likes_received:
this.get("num_likes_received") >= this.get("min_likes_received"),
likes_received_days:
this.get("num_likes_received_days") >=
this.get("min_likes_received_days"),
likes_received_users:
this.get("num_likes_received_users") >=
this.get("min_likes_received_users"),
level_locked: this.get("trust_level_locked"),
silenced: this.get("penalty_counts.silenced") === 0,
suspended: this.get("penalty_counts.suspended") === 0
};
}.property(
"days_visited", "days_visited",
"min_days_visited", "min_days_visited",
"num_topics_replied_to", "num_topics_replied_to",
@ -71,4 +42,34 @@ export default Discourse.Model.extend({
"penalty_counts.silenced", "penalty_counts.silenced",
"penalty_counts.suspended" "penalty_counts.suspended"
) )
met() {
return {
days_visited: this.get("days_visited") >= this.get("min_days_visited"),
topics_replied_to:
this.get("num_topics_replied_to") >= this.get("min_topics_replied_to"),
topics_viewed: this.get("topics_viewed") >= this.get("min_topics_viewed"),
posts_read: this.get("posts_read") >= this.get("min_posts_read"),
topics_viewed_all_time:
this.get("topics_viewed_all_time") >=
this.get("min_topics_viewed_all_time"),
posts_read_all_time:
this.get("posts_read_all_time") >= this.get("min_posts_read_all_time"),
flagged_posts:
this.get("num_flagged_posts") <= this.get("max_flagged_posts"),
flagged_by_users:
this.get("num_flagged_by_users") <= this.get("max_flagged_by_users"),
likes_given: this.get("num_likes_given") >= this.get("min_likes_given"),
likes_received:
this.get("num_likes_received") >= this.get("min_likes_received"),
likes_received_days:
this.get("num_likes_received_days") >=
this.get("min_likes_received_days"),
likes_received_users:
this.get("num_likes_received_users") >=
this.get("min_likes_received_users"),
level_locked: this.get("trust_level_locked"),
silenced: this.get("penalty_counts.silenced") === 0,
suspended: this.get("penalty_counts.suspended") === 0
};
}
}); });

View File

@ -1,3 +1,5 @@
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Component.extend({ export default Ember.Component.extend({
tagName: "span", tagName: "span",
classNameBindings: [ classNameBindings: [
@ -5,9 +7,12 @@ export default Ember.Component.extend({
"badge.badgeTypeClassName", "badge.badgeTypeClassName",
"badge.enabled::disabled" "badge.enabled::disabled"
], ],
title: function() {
return $("<div>" + this.get("badge.description") + "</div>").text(); @computed("badge.description")
}.property("badge.description"), title(badgeDescription) {
return $("<div>" + badgeDescription + "</div>").text();
},
attributeBindings: ["data-badge-name", "title"], attributeBindings: ["data-badge-name", "title"],
"data-badge-name": Ember.computed.alias("badge.name") "data-badge-name": Ember.computed.alias("badge.name")
}); });

View File

@ -1,15 +1,18 @@
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Component.extend({ export default Ember.Component.extend({
loadingMore: Ember.computed.alias("topicList.loadingMore"), loadingMore: Ember.computed.alias("topicList.loadingMore"),
loading: Ember.computed.not("loaded"), loading: Ember.computed.not("loaded"),
loaded: function() { @computed("topicList.loaded")
loaded() {
var topicList = this.get("topicList"); var topicList = this.get("topicList");
if (topicList) { if (topicList) {
return topicList.get("loaded"); return topicList.get("loaded");
} else { } else {
return true; return true;
} }
}.property("topicList.loaded"), },
_topicListChanged: function() { _topicListChanged: function() {
this._initFromTopicList(this.get("topicList")); this._initFromTopicList(this.get("topicList"));
@ -27,9 +30,6 @@ export default Ember.Component.extend({
const topicList = this.get("topicList"); const topicList = this.get("topicList");
if (topicList) { if (topicList) {
this._initFromTopicList(topicList); this._initFromTopicList(topicList);
} else {
// Without a topic list, we assume it's loaded always.
this.set("loaded", true);
} }
}, },

View File

@ -30,13 +30,25 @@ export default Ember.Component.extend({
noText: Ember.computed.empty("translatedLabel"), noText: Ember.computed.empty("translatedLabel"),
@computed("title") @computed("title")
translatedTitle(title) { translatedTitle: {
if (title) return I18n.t(title); get() {
if (this._translatedTitle) return this._translatedTitle;
if (this.title) return I18n.t(this.title);
},
set(value) {
return (this._translatedTitle = value);
}
}, },
@computed("label") @computed("label")
translatedLabel(label) { translatedLabel: {
if (label) return I18n.t(label); get() {
if (this._translatedLabel) return this._translatedLabel;
if (this.label) return I18n.t(this.label);
},
set(value) {
return (this._translatedLabel = value);
}
}, },
click() { click() {

View File

@ -1,9 +1,10 @@
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Component.extend({ export default Ember.Component.extend({
visible: function() { @computed("user.dismissed_banner_key", "banner.key", "hide")
var bannerKey = this.get("banner.key"), visible(dismissedBannerKey, bannerKey, hide) {
dismissedBannerKey = dismissedBannerKey =
this.get("user.dismissed_banner_key") || dismissedBannerKey || this.keyValueStore.get("dismissed_banner_key");
this.keyValueStore.get("dismissed_banner_key");
if (bannerKey) { if (bannerKey) {
bannerKey = parseInt(bannerKey, 10); bannerKey = parseInt(bannerKey, 10);
@ -12,8 +13,8 @@ export default Ember.Component.extend({
dismissedBannerKey = parseInt(dismissedBannerKey, 10); dismissedBannerKey = parseInt(dismissedBannerKey, 10);
} }
return !this.get("hide") && bannerKey && dismissedBannerKey !== bannerKey; return !hide && bannerKey && dismissedBannerKey !== bannerKey;
}.property("user.dismissed_banner_key", "banner.key", "hide"), },
actions: { actions: {
dismiss() { dismiss() {

View File

@ -1,13 +1,17 @@
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Component.extend({ export default Ember.Component.extend({
tagName: "a", tagName: "a",
classNameBindings: [":discourse-tag", "style", "tagClass"], classNameBindings: [":discourse-tag", "style", "tagClass"],
attributeBindings: ["href"], attributeBindings: ["href"],
tagClass: function() { @computed("tagRecord.id")
return "tag-" + this.get("tagRecord.id"); tagClass(tagRecordId) {
}.property("tagRecord.id"), return "tag-" + tagRecordId;
},
href: function() { @computed("tagRecord.id")
return Discourse.getURL("/tags/" + this.get("tagRecord.id")); href(tagRecordId) {
}.property("tagRecord.id") return Discourse.getURL("/tags/" + tagRecordId);
}
}); });

View File

@ -1,18 +1,21 @@
import { propertyEqual } from "discourse/lib/computed"; import { propertyEqual } from "discourse/lib/computed";
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Component.extend({ export default Ember.Component.extend({
tagName: "li", tagName: "li",
classNameBindings: ["active", "tabClassName"], classNameBindings: ["active", "tabClassName"],
tabClassName: function() { @computed("tab")
return "edit-category-" + this.get("tab"); tabClassName(tab) {
}.property("tab"), return "edit-category-" + tab;
},
active: propertyEqual("selectedTab", "tab"), active: propertyEqual("selectedTab", "tab"),
title: function() { @computed("tab")
return I18n.t("category." + this.get("tab").replace("-", "_")); title(tab) {
}.property("tab"), return I18n.t("category." + tab.replace("-", "_"));
},
didInsertElement() { didInsertElement() {
this._super(...arguments); this._super(...arguments);

View File

@ -1,9 +1,12 @@
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Component.extend({ export default Ember.Component.extend({
classNames: ["controls"], classNames: ["controls"],
label: function() { @computed("labelKey")
return I18n.t(this.get("labelKey")); label(labelKey) {
}.property("labelKey"), return I18n.t(labelKey);
},
change() { change() {
const warning = this.get("warning"); const warning = this.get("warning");

View File

@ -1,4 +1,5 @@
import DiscourseURL from "discourse/lib/url"; import DiscourseURL from "discourse/lib/url";
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Component.extend({ export default Ember.Component.extend({
tagName: "a", tagName: "a",
@ -10,17 +11,19 @@ export default Ember.Component.extend({
], ],
attributeBindings: ["href"], attributeBindings: ["href"],
href: function() { @computed("tagId", "category")
href(tagId, category) {
var url = "/tags"; var url = "/tags";
if (this.get("category")) { if (category) {
url += this.get("category.url"); url += category.url;
} }
return url + "/" + this.get("tagId"); return url + "/" + tagId;
}.property("tagId", "category"), },
tagClass: function() { @computed("tagId")
return "tag-" + this.get("tagId"); tagClass(tagId) {
}.property("tagId"), return "tag-" + tagId;
},
click(e) { click(e) {
e.preventDefault(); e.preventDefault();

View File

@ -38,7 +38,13 @@ export default Ember.TextField.extend({
}, },
@computed("placeholderKey") @computed("placeholderKey")
placeholder(placeholderKey) { placeholder: {
return placeholderKey ? I18n.t(placeholderKey) : ""; get() {
if (this._placeholder) return this._placeholder;
return this.placeholderKey ? I18n.t(this.placeholderKey) : "";
},
set(value) {
return (this._placeholder = value);
}
} }
}); });

View File

@ -1,10 +1,12 @@
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Component.extend({ export default Ember.Component.extend({
classNames: ["top-title-buttons"], classNames: ["top-title-buttons"],
periods: function() { @computed("period")
const period = this.get("period"); periods(period) {
return this.site.get("periods").filter(p => p !== period); return this.site.get("periods").filter(p => p !== period);
}.property("period"), },
actions: { actions: {
changePeriod(p) { changePeriod(p) {

View File

@ -1,4 +1,7 @@
import { observes } from "ember-addons/ember-computed-decorators"; import {
default as computed,
observes
} from "ember-addons/ember-computed-decorators";
export default Ember.Component.extend({ export default Ember.Component.extend({
tagName: "table", tagName: "table",
@ -16,25 +19,25 @@ export default Ember.Component.extend({
this.refreshLastVisited(); this.refreshLastVisited();
}.on("init"), }.on("init"),
toggleInTitle: function() { @computed("bulkSelectEnabled")
return !this.get("bulkSelectEnabled") && this.get("canBulkSelect"); toggleInTitle(bulkSelectEnabled) {
}.property("bulkSelectEnabled"), return !bulkSelectEnabled && this.get("canBulkSelect");
},
sortable: function() { @computed
sortable() {
return !!this.get("changeSort"); return !!this.get("changeSort");
}.property(), },
skipHeader: function() { @computed("order")
return this.site.mobileView; showLikes(order) {
}.property(), return order === "likes";
},
showLikes: function() { @computed("order")
return this.get("order") === "likes"; showOpLikes(order) {
}.property("order"), return order === "op_likes";
},
showOpLikes: function() {
return this.get("order") === "op_likes";
}.property("order"),
@observes("topics.[]") @observes("topics.[]")
topicsAdded() { topicsAdded() {

View File

@ -2,6 +2,7 @@ import { iconHTML } from "discourse-common/lib/icon-library";
import { bufferedRender } from "discourse-common/lib/buffered-render"; import { bufferedRender } from "discourse-common/lib/buffered-render";
import { escapeExpression } from "discourse/lib/utilities"; import { escapeExpression } from "discourse/lib/utilities";
import TopicStatusIcons from "discourse/helpers/topic-status-icons"; import TopicStatusIcons from "discourse/helpers/topic-status-icons";
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Component.extend( export default Ember.Component.extend(
bufferedRender({ bufferedRender({
@ -26,9 +27,10 @@ export default Ember.Component.extend(
return false; return false;
}, },
canAct: function() { @computed("disableActions")
return Discourse.User.current() && !this.get("disableActions"); canAct(disableActions) {
}.property("disableActions"), return Discourse.User.current() && !disableActions;
},
buildBuffer(buffer) { buildBuffer(buffer) {
const canAct = this.get("canAct"); const canAct = this.get("canAct");

View File

@ -1,14 +1,18 @@
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Component.extend({ export default Ember.Component.extend({
tagName: "span", tagName: "span",
showGrantCount: function() { @computed("count")
return this.get("count") && this.get("count") > 1; showGrantCount(count) {
}.property("count"), return count && count > 1;
},
badgeUrl: function() { @computed("badge", "user")
badgeUrl() {
// NOTE: I tried using a link-to helper here but the queryParams mean it fails // NOTE: I tried using a link-to helper here but the queryParams mean it fails
var username = this.get("user.username_lower") || ""; var username = this.get("user.username_lower") || "";
username = username !== "" ? "?username=" + username : ""; username = username !== "" ? "?username=" + username : "";
return this.get("badge.url") + username; return this.get("badge.url") + username;
}.property("badge", "user") }
}); });

View File

@ -1,10 +1,12 @@
import { fmt } from "discourse/lib/computed"; import { fmt } from "discourse/lib/computed";
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Component.extend({ export default Ember.Component.extend({
classNameBindings: [":user-field", "field.field_type"], classNameBindings: [":user-field", "field.field_type"],
layoutName: fmt("field.field_type", "components/user-fields/%@"), layoutName: fmt("field.field_type", "components/user-fields/%@"),
noneLabel: function() { @computed
noneLabel() {
return "user_fields.none"; return "user_fields.none";
}.property() }
}); });

View File

@ -1,7 +1,10 @@
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Controller.extend({ export default Ember.Controller.extend({
faqOverriden: Ember.computed.gt("siteSettings.faq_url.length", 0), faqOverriden: Ember.computed.gt("siteSettings.faq_url.length", 0),
contactInfo: function() { @computed
contactInfo() {
if (this.siteSettings.contact_url) { if (this.siteSettings.contact_url) {
return I18n.t("about.contact_info", { return I18n.t("about.contact_info", {
contact_info: contact_info:
@ -18,5 +21,5 @@ export default Ember.Controller.extend({
} else { } else {
return null; return null;
} }
}.property() }
}); });

View File

@ -1,6 +1,9 @@
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Controller.extend({ export default Ember.Controller.extend({
badgeGroups: function() { @computed("model")
var sorted = _.sortBy(this.get("model"), function(badge) { badgeGroups(model) {
var sorted = _.sortBy(model, function(badge) {
var pos = badge.get("badge_grouping.position"); var pos = badge.get("badge_grouping.position");
var type = badge.get("badge_type_id"); var type = badge.get("badge_type_id");
var name = badge.get("name"); var name = badge.get("name");
@ -31,5 +34,5 @@ export default Ember.Controller.extend({
} }
return grouped; return grouped;
}.property("model") }
}); });

View File

@ -12,9 +12,10 @@ export default Ember.Controller.extend(BadgeSelectController, {
application: Ember.inject.controller(), application: Ember.inject.controller(),
hiddenSetTitle: true, hiddenSetTitle: true,
filteredList: function() { @computed("userBadgesAll")
return this.get("userBadgesAll").filterBy("badge.allow_title", true); filteredList(userBadgesAll) {
}.property("userBadgesAll"), return userBadgesAll.filterBy("badge.allow_title", true);
},
@computed("username") @computed("username")
user(username) { user(username) {

View File

@ -39,6 +39,7 @@ function loadDraft(store, opts) {
((draft.title && draft.title !== "") || (draft.reply && draft.reply !== "")) ((draft.title && draft.title !== "") || (draft.reply && draft.reply !== ""))
) { ) {
const composer = store.createRecord("composer"); const composer = store.createRecord("composer");
composer.open({ composer.open({
draftKey, draftKey,
draftSequence, draftSequence,
@ -301,14 +302,12 @@ export default Ember.Controller.extend({
} }
}, },
showWarning: function() { @computed("model.creatingPrivateMessage", "model.targetUsernames")
showWarning(creatingPrivateMessage, usernames) {
if (!Discourse.User.currentProp("staff")) { if (!Discourse.User.currentProp("staff")) {
return false; return false;
} }
var usernames = this.get("model.targetUsernames");
var hasTargetGroups = this.get("model.hasTargetGroups"); var hasTargetGroups = this.get("model.hasTargetGroups");
// We need exactly one user to issue a warning // We need exactly one user to issue a warning
if ( if (
Ember.isEmpty(usernames) || Ember.isEmpty(usernames) ||
@ -317,8 +316,8 @@ export default Ember.Controller.extend({
) { ) {
return false; return false;
} }
return this.get("model.creatingPrivateMessage"); return creatingPrivateMessage;
}.property("model.creatingPrivateMessage", "model.targetUsernames"), },
@computed("model.topic") @computed("model.topic")
draftTitle(topic) { draftTitle(topic) {
@ -1102,15 +1101,13 @@ export default Ember.Controller.extend({
$(".d-editor-input").autocomplete({ cancel: true }); $(".d-editor-input").autocomplete({ cancel: true });
}, },
canEdit: function() { @computed("model.action")
return ( canEdit(action) {
this.get("model.action") === "edit" && return action === "edit" && Discourse.User.current().get("can_edit");
Discourse.User.current().get("can_edit") },
);
}.property("model.action"),
visible: function() { @computed("model.composeState")
var state = this.get("model.composeState"); visible(state) {
return state && state !== "closed"; return state && state !== "closed";
}.property("model.composeState") }
}); });

View File

@ -1,7 +1,10 @@
import { ajax } from "discourse/lib/ajax"; import { ajax } from "discourse/lib/ajax";
import ModalFunctionality from "discourse/mixins/modal-functionality"; import ModalFunctionality from "discourse/mixins/modal-functionality";
import { setting } from "discourse/lib/computed"; import { setting } from "discourse/lib/computed";
import { on } from "ember-addons/ember-computed-decorators"; import {
default as computed,
on
} from "ember-addons/ember-computed-decorators";
import { emailValid } from "discourse/lib/utilities"; import { emailValid } from "discourse/lib/utilities";
import InputValidation from "discourse/models/input-validation"; import InputValidation from "discourse/models/input-validation";
import PasswordValidation from "discourse/mixins/password-validation"; import PasswordValidation from "discourse/mixins/password-validation";
@ -51,7 +54,16 @@ export default Ember.Controller.extend(
this._createUserFields(); this._createUserFields();
}, },
submitDisabled: function() { @computed(
"passwordRequired",
"nameValidation.failed",
"emailValidation.failed",
"usernameValidation.failed",
"passwordValidation.failed",
"userFieldsValidation.failed",
"formSubmitted"
)
submitDisabled() {
if (!this.get("emailValidation.failed") && !this.get("passwordRequired")) if (!this.get("emailValidation.failed") && !this.get("passwordRequired"))
return false; // 3rd party auth return false; // 3rd party auth
if (this.get("formSubmitted")) return true; if (this.get("formSubmitted")) return true;
@ -62,51 +74,44 @@ export default Ember.Controller.extend(
if (this.get("userFieldsValidation.failed")) return true; if (this.get("userFieldsValidation.failed")) return true;
return false; return false;
}.property( },
"passwordRequired",
"nameValidation.failed",
"emailValidation.failed",
"usernameValidation.failed",
"passwordValidation.failed",
"userFieldsValidation.failed",
"formSubmitted"
),
usernameRequired: Ember.computed.not("authOptions.omit_username"), usernameRequired: Ember.computed.not("authOptions.omit_username"),
fullnameRequired: function() { @computed
fullnameRequired() {
return ( return (
this.get("siteSettings.full_name_required") || this.get("siteSettings.full_name_required") ||
this.get("siteSettings.enable_names") this.get("siteSettings.enable_names")
); );
}.property(), },
passwordRequired: function() { @computed("authOptions.auth_provider")
return Ember.isEmpty(this.get("authOptions.auth_provider")); passwordRequired(authProvider) {
}.property("authOptions.auth_provider"), return Ember.isEmpty(authProvider);
},
disclaimerHtml: function() { @computed
disclaimerHtml() {
return I18n.t("create_account.disclaimer", { return I18n.t("create_account.disclaimer", {
tos_link: this.get("siteSettings.tos_url") || Discourse.getURL("/tos"), tos_link: this.get("siteSettings.tos_url") || Discourse.getURL("/tos"),
privacy_link: privacy_link:
this.get("siteSettings.privacy_policy_url") || this.get("siteSettings.privacy_policy_url") ||
Discourse.getURL("/privacy") Discourse.getURL("/privacy")
}); });
}.property(), },
// Check the email address // Check the email address
emailValidation: function() { @computed("accountEmail", "rejectedEmails.[]")
emailValidation(email, rejectedEmails) {
// If blank, fail without a reason // If blank, fail without a reason
let email; if (Ember.isEmpty(email)) {
if (Ember.isEmpty(this.get("accountEmail"))) {
return InputValidation.create({ return InputValidation.create({
failed: true failed: true
}); });
} }
email = this.get("accountEmail"); if (rejectedEmails.includes(email)) {
if (this.get("rejectedEmails").includes(email)) {
return InputValidation.create({ return InputValidation.create({
failed: true, failed: true,
reason: I18n.t("user.email.invalid") reason: I18n.t("user.email.invalid")
@ -138,14 +143,15 @@ export default Ember.Controller.extend(
failed: true, failed: true,
reason: I18n.t("user.email.invalid") reason: I18n.t("user.email.invalid")
}); });
}.property("accountEmail", "rejectedEmails.[]"), },
emailValidated: function() { @computed("accountEmail", "authOptions.email", "authOptions.email_valid")
emailValidated() {
return ( return (
this.get("authOptions.email") === this.get("accountEmail") && this.get("authOptions.email") === this.get("accountEmail") &&
this.get("authOptions.email_valid") this.get("authOptions.email_valid")
); );
}.property("accountEmail", "authOptions.email", "authOptions.email_valid"), },
authProviderDisplayName(providerName) { authProviderDisplayName(providerName) {
const matchingProvider = findAll().find(provider => { const matchingProvider = findAll().find(provider => {
@ -178,9 +184,10 @@ export default Ember.Controller.extend(
}.observes("emailValidation", "accountEmail"), }.observes("emailValidation", "accountEmail"),
// Determines whether at least one login button is enabled // Determines whether at least one login button is enabled
hasAtLeastOneLoginButton: function() { @computed
hasAtLeastOneLoginButton() {
return findAll(this.siteSettings).length > 0; return findAll(this.siteSettings).length > 0;
}.property(), },
@on("init") @on("init")
fetchConfirmationValue() { fetchConfirmationValue() {

View File

@ -5,6 +5,7 @@ import { endWith } from "discourse/lib/computed";
import showModal from "discourse/lib/show-modal"; import showModal from "discourse/lib/show-modal";
import { userPath } from "discourse/lib/url"; import { userPath } from "discourse/lib/url";
import TopicList from "discourse/models/topic-list"; import TopicList from "discourse/models/topic-list";
import computed from "ember-addons/ember-computed-decorators";
const controllerOpts = { const controllerOpts = {
discovery: Ember.inject.controller(), discovery: Ember.inject.controller(),
@ -96,26 +97,24 @@ const controllerOpts = {
return filter.match(new RegExp(filterType + "$", "gi")) ? true : false; return filter.match(new RegExp(filterType + "$", "gi")) ? true : false;
}, },
showDismissRead: function() { @computed("model.filter", "model.topics.length")
return ( showDismissRead(filter, topicsLength) {
this.isFilterPage(this.get("model.filter"), "unread") && return this.isFilterPage(filter, "unread") && topicsLength > 0;
this.get("model.topics.length") > 0 },
);
}.property("model.filter", "model.topics.length"),
showResetNew: function() { @computed("model.filter", "model.topics.length")
return ( showResetNew(filter, topicsLength) {
this.get("model.filter") === "new" && this.get("model.topics.length") > 0 return filter === "new" && topicsLength > 0;
); },
}.property("model.filter", "model.topics.length"),
showDismissAtTop: function() { @computed("model.filter", "model.topics.length")
showDismissAtTop(filter, topicsLength) {
return ( return (
(this.isFilterPage(this.get("model.filter"), "new") || (this.isFilterPage(filter, "new") ||
this.isFilterPage(this.get("model.filter"), "unread")) && this.isFilterPage(filter, "unread")) &&
this.get("model.topics.length") >= 15 topicsLength >= 15
); );
}.property("model.filter", "model.topics.length"), },
hasTopics: Ember.computed.gt("model.topics.length", 0), hasTopics: Ember.computed.gt("model.topics.length", 0),
allLoaded: Ember.computed.empty("model.more_topics_url"), allLoaded: Ember.computed.empty("model.more_topics_url"),
@ -128,10 +127,9 @@ const controllerOpts = {
weekly: Ember.computed.equal("period", "weekly"), weekly: Ember.computed.equal("period", "weekly"),
daily: Ember.computed.equal("period", "daily"), daily: Ember.computed.equal("period", "daily"),
footerMessage: function() { @computed("allLoaded", "model.topics.length")
if (!this.get("allLoaded")) { footerMessage(allLoaded, topicsLength) {
return; if (!allLoaded) return;
}
const category = this.get("category"); const category = this.get("category");
if (category) { if (category) {
@ -140,7 +138,7 @@ const controllerOpts = {
}); });
} else { } else {
const split = (this.get("model.filter") || "").split("/"); const split = (this.get("model.filter") || "").split("/");
if (this.get("model.topics.length") === 0) { if (topicsLength === 0) {
return I18n.t("topics.none." + split[0], { return I18n.t("topics.none." + split[0], {
category: split[1] category: split[1]
}); });
@ -150,14 +148,11 @@ const controllerOpts = {
}); });
} }
} }
}.property("allLoaded", "model.topics.length"), },
footerEducation: function() { @computed("allLoaded", "model.topics.length")
if ( footerEducation(allLoaded, topicsLength) {
!this.get("allLoaded") || if (!allLoaded || topicsLength > 0 || !this.currentUser) {
this.get("model.topics.length") > 0 ||
!this.currentUser
) {
return; return;
} }
@ -173,7 +168,7 @@ const controllerOpts = {
`${this.currentUser.get("username_lower")}/preferences` `${this.currentUser.get("username_lower")}/preferences`
) )
}); });
}.property("allLoaded", "model.topics.length") }
}; };
Object.keys(queryParams).forEach(function(p) { Object.keys(queryParams).forEach(function(p) {

View File

@ -1,6 +1,7 @@
import ModalFunctionality from "discourse/mixins/modal-functionality"; import ModalFunctionality from "discourse/mixins/modal-functionality";
import DiscourseURL from "discourse/lib/url"; import DiscourseURL from "discourse/lib/url";
import { extractError } from "discourse/lib/ajax-error"; import { extractError } from "discourse/lib/ajax-error";
import computed from "ember-addons/ember-computed-decorators";
// Modal for editing / creating a category // Modal for editing / creating a category
export default Ember.Controller.extend(ModalFunctionality, { export default Ember.Controller.extend(ModalFunctionality, {
@ -28,39 +29,44 @@ export default Ember.Controller.extend(ModalFunctionality, {
} }
}.observes("model.description"), }.observes("model.description"),
title: function() { @computed("model.id", "model.name")
if (this.get("model.id")) { title(id, name) {
if (id) {
return I18n.t("category.edit_dialog_title", { return I18n.t("category.edit_dialog_title", {
categoryName: this.get("model.name") categoryName: name
}); });
} }
return I18n.t("category.create"); return I18n.t("category.create");
}.property("model.id", "model.name"), },
titleChanged: function() { titleChanged: function() {
this.set("modal.title", this.get("title")); this.set("modal.title", this.get("title"));
}.observes("title"), }.observes("title"),
disabled: function() { @computed("saving", "model.name", "model.color", "deleting")
if (this.get("saving") || this.get("deleting")) return true; disabled(saving, name, color, deleting) {
if (!this.get("model.name")) return true; if (saving || deleting) return true;
if (!this.get("model.color")) return true; if (!name) return true;
if (!color) return true;
return false; return false;
}.property("saving", "model.name", "model.color", "deleting"), },
deleteDisabled: function() { @computed("saving", "deleting")
return this.get("deleting") || this.get("saving") || false; deleteDisabled(saving, deleting) {
}.property("disabled", "saving", "deleting"), return deleting || saving || false;
},
categoryName: function() { @computed("name")
const name = this.get("name") || ""; categoryName(name) {
name = name || "";
return name.trim().length > 0 ? name : I18n.t("preview"); return name.trim().length > 0 ? name : I18n.t("preview");
}.property("name"), },
saveLabel: function() { @computed("saving", "model.id")
if (this.get("saving")) return "saving"; saveLabel(saving, id) {
return this.get("model.id") ? "category.save" : "category.create"; if (saving) return "saving";
}.property("saving", "model.id"), return id ? "category.save" : "category.create";
},
actions: { actions: {
saveCategory() { saveCategory() {

View File

@ -1,3 +1,5 @@
import computed from "ember-addons/ember-computed-decorators";
var ButtonBackBright = { var ButtonBackBright = {
classes: "btn-primary", classes: "btn-primary",
action: "back", action: "back",
@ -25,13 +27,14 @@ export default Ember.Controller.extend({
thrown: null, thrown: null,
lastTransition: null, lastTransition: null,
@computed
isNetwork: function() { isNetwork: function() {
// never made it on the wire // never made it on the wire
if (this.get("thrown.readyState") === 0) return true; if (this.get("thrown.readyState") === 0) return true;
// timed out // timed out
if (this.get("thrown.jqTextStatus") === "timeout") return true; if (this.get("thrown.jqTextStatus") === "timeout") return true;
return false; return false;
}.property(), },
isNotFound: Ember.computed.equal("thrown.status", 404), isNotFound: Ember.computed.equal("thrown.status", 404),
isForbidden: Ember.computed.equal("thrown.status", 403), isForbidden: Ember.computed.equal("thrown.status", 403),
@ -48,7 +51,8 @@ export default Ember.Controller.extend({
this.set("loading", false); this.set("loading", false);
}.on("init"), }.on("init"),
reason: function() { @computed("isNetwork", "isServer", "isUnknown")
reason() {
if (this.get("isNetwork")) { if (this.get("isNetwork")) {
return I18n.t("errors.reasons.network"); return I18n.t("errors.reasons.network");
} else if (this.get("isServer")) { } else if (this.get("isServer")) {
@ -61,11 +65,12 @@ export default Ember.Controller.extend({
// TODO // TODO
return I18n.t("errors.reasons.unknown"); return I18n.t("errors.reasons.unknown");
} }
}.property("isNetwork", "isServer", "isUnknown"), },
requestUrl: Ember.computed.alias("thrown.requestedUrl"), requestUrl: Ember.computed.alias("thrown.requestedUrl"),
desc: function() { @computed("networkFixed", "isNetwork", "isServer", "isUnknown")
desc() {
if (this.get("networkFixed")) { if (this.get("networkFixed")) {
return I18n.t("errors.desc.network_fixed"); return I18n.t("errors.desc.network_fixed");
} else if (this.get("isNetwork")) { } else if (this.get("isNetwork")) {
@ -80,9 +85,10 @@ export default Ember.Controller.extend({
// TODO // TODO
return I18n.t("errors.desc.unknown"); return I18n.t("errors.desc.unknown");
} }
}.property("networkFixed", "isNetwork", "isServer", "isUnknown"), },
enabledButtons: function() { @computed("networkFixed", "isNetwork", "isServer", "isUnknown")
enabledButtons() {
if (this.get("networkFixed")) { if (this.get("networkFixed")) {
return [ButtonLoadPage]; return [ButtonLoadPage];
} else if (this.get("isNetwork")) { } else if (this.get("isNetwork")) {
@ -90,7 +96,7 @@ export default Ember.Controller.extend({
} else { } else {
return [ButtonBackBright, ButtonTryAgain]; return [ButtonBackBright, ButtonTryAgain];
} }
}.property("networkFixed", "isNetwork", "isServer", "isUnknown"), },
actions: { actions: {
back: function() { back: function() {

View File

@ -39,7 +39,8 @@ export default Ember.Controller.extend(ModalFunctionality, {
return flagTopic ? "flagging_topic.title" : "flagging.title"; return flagTopic ? "flagging_topic.title" : "flagging.title";
}, },
flagsAvailable: function() { @computed("post", "flagTopic", "model.actions_summary.@each.can_act")
flagsAvailable() {
if (!this.get("flagTopic")) { if (!this.get("flagTopic")) {
// flagging post // flagging post
let flagsAvailable = this.get("model.flagsAvailable"); let flagsAvailable = this.get("model.flagsAvailable");
@ -71,16 +72,18 @@ export default Ember.Controller.extend(ModalFunctionality, {
}); });
}); });
} }
}.property("post", "flagTopic", "model.actions_summary.@each.can_act"), },
staffFlagsAvailable: function() { @computed("post", "flagTopic", "model.actions_summary.@each.can_act")
staffFlagsAvailable() {
return ( return (
this.get("model.flagsAvailable") && this.get("model.flagsAvailable") &&
this.get("model.flagsAvailable").length > 1 this.get("model.flagsAvailable").length > 1
); );
}.property("post", "flagTopic", "model.actions_summary.@each.can_act"), },
submitEnabled: function() { @computed("selected.is_custom_flag", "message.length")
submitEnabled() {
const selected = this.get("selected"); const selected = this.get("selected");
if (!selected) return false; if (!selected) return false;
@ -92,7 +95,7 @@ export default Ember.Controller.extend(ModalFunctionality, {
); );
} }
return true; return true;
}.property("selected.is_custom_flag", "message.length"), },
submitDisabled: Ember.computed.not("submitEnabled"), submitDisabled: Ember.computed.not("submitEnabled"),

View File

@ -284,17 +284,18 @@ export default Ember.Controller.extend(ModalFunctionality, {
} }
}, },
authMessage: function() { @computed("authenticate")
if (Ember.isEmpty(this.get("authenticate"))) return ""; authMessage(authenticate) {
if (Ember.isEmpty(authenticate)) return "";
const method = findAll( const method = findAll(
this.siteSettings, this.siteSettings,
this.capabilities, this.capabilities,
this.isMobileDevice this.isMobileDevice
).findBy("name", this.get("authenticate")); ).findBy("name", authenticate);
if (method) { if (method) {
return method.get("message"); return method.get("message");
} }
}.property("authenticate"), },
authenticationComplete(options) { authenticationComplete(options) {
const self = this; const self = this;

View File

@ -1,9 +1,11 @@
import NavigationDefaultController from "discourse/controllers/navigation/default"; import NavigationDefaultController from "discourse/controllers/navigation/default";
import computed from "ember-addons/ember-computed-decorators";
export default NavigationDefaultController.extend({ export default NavigationDefaultController.extend({
discoveryCategories: Ember.inject.controller("discovery/categories"), discoveryCategories: Ember.inject.controller("discovery/categories"),
draft: function() { @computed("discoveryCategories.model", "discoveryCategories.model.draft")
draft() {
return this.get("discoveryCategories.model.draft"); return this.get("discoveryCategories.model.draft");
}.property("discoveryCategories.model", "discoveryCategories.model.draft") }
}); });

View File

@ -1,8 +1,11 @@
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Controller.extend({ export default Ember.Controller.extend({
discovery: Ember.inject.controller(), discovery: Ember.inject.controller(),
discoveryTopics: Ember.inject.controller("discovery/topics"), discoveryTopics: Ember.inject.controller("discovery/topics"),
@computed("discoveryTopics.model", "discoveryTopics.model.draft")
draft: function() { draft: function() {
return this.get("discoveryTopics.model.draft"); return this.get("discoveryTopics.model.draft");
}.property("discoveryTopics.model", "discoveryTopics.model.draft") }
}); });

View File

@ -1,8 +1,11 @@
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Controller.extend({ export default Ember.Controller.extend({
saving: false, saving: false,
newBio: null, newBio: null,
saveButtonText: function() { @computed("saving")
return this.get("saving") ? I18n.t("saving") : I18n.t("user.change"); saveButtonText(saving) {
}.property("saving") return saving ? I18n.t("saving") : I18n.t("user.change");
}
}); });

View File

@ -77,9 +77,10 @@ export default Ember.Controller.extend(PreferencesTabController, {
}); });
}, },
userSelectableThemes: function() { @computed
userSelectableThemes() {
return listThemes(this.site); return listThemes(this.site);
}.property(), },
@computed("userSelectableThemes") @computed("userSelectableThemes")
showThemeSelector(themes) { showThemeSelector(themes) {

View File

@ -26,13 +26,14 @@ export default Ember.Controller.extend(ModalFunctionality, Ember.Evented, {
"categoriesSorting" "categoriesSorting"
), ),
showApplyAll: function() { @computed("categoriesBuffered.@each.hasBufferedChanges")
showApplyAll() {
let anyChanged = false; let anyChanged = false;
this.get("categoriesBuffered").forEach(bc => { this.get("categoriesBuffered").forEach(bc => {
anyChanged = anyChanged || bc.get("hasBufferedChanges"); anyChanged = anyChanged || bc.get("hasBufferedChanges");
}); });
return anyChanged; return anyChanged;
}.property("categoriesBuffered.@each.hasBufferedChanges"), },
moveDir(cat, dir) { moveDir(cat, dir) {
const cats = this.get("categoriesOrdered"); const cats = this.get("categoriesOrdered");

View File

@ -1,7 +1,9 @@
import ModalFunctionality from "discourse/mixins/modal-functionality"; import ModalFunctionality from "discourse/mixins/modal-functionality";
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Controller.extend(ModalFunctionality, { export default Ember.Controller.extend(ModalFunctionality, {
showGoogleSearch: function() { @computed
showGoogleSearch() {
return !Discourse.SiteSettings.login_required; return !Discourse.SiteSettings.login_required;
}.property() }
}); });

View File

@ -16,12 +16,12 @@ export default Ember.Controller.extend({
pmTaggingEnabled: Ember.computed.alias("site.can_tag_pms"), pmTaggingEnabled: Ember.computed.alias("site.can_tag_pms"),
tagId: null, tagId: null,
showNewPM: function() { @computed("user.viewingSelf")
showNewPM(viewingSelf) {
return ( return (
this.get("user.viewingSelf") && viewingSelf && Discourse.User.currentProp("can_send_private_messages")
Discourse.User.currentProp("can_send_private_messages")
); );
}.property("user.viewingSelf"), },
@computed("selected.[]", "bulkSelectEnabled") @computed("selected.[]", "bulkSelectEnabled")
hasSelection(selected, bulkSelectEnabled) { hasSelection(selected, bulkSelectEnabled) {

View File

@ -1,4 +1,5 @@
import addonFmt from "ember-addons/fmt"; import addonFmt from "ember-addons/fmt";
/** /**
Returns whether two properties are equal to each other. Returns whether two properties are equal to each other.
@ -7,10 +8,11 @@ import addonFmt from "ember-addons/fmt";
@params {String} p2 the second property @params {String} p2 the second property
@return {Function} computedProperty function @return {Function} computedProperty function
**/ **/
export function propertyEqual(p1, p2) { export function propertyEqual(p1, p2) {
return Ember.computed(function() { return Ember.computed(p1, p2, function() {
return this.get(p1) === this.get(p2); return this.get(p1) === this.get(p2);
}).property(p1, p2); });
} }
/** /**
@ -22,21 +24,21 @@ export function propertyEqual(p1, p2) {
@return {Function} computedProperty function @return {Function} computedProperty function
**/ **/
export function propertyNotEqual(p1, p2) { export function propertyNotEqual(p1, p2) {
return Ember.computed(function() { return Ember.computed(p1, p2, function() {
return this.get(p1) !== this.get(p2); return this.get(p1) !== this.get(p2);
}).property(p1, p2); });
} }
export function propertyGreaterThan(p1, p2) { export function propertyGreaterThan(p1, p2) {
return Ember.computed(function() { return Ember.computed(p1, p2, function() {
return this.get(p1) > this.get(p2); return this.get(p1) > this.get(p2);
}).property(p1, p2); });
} }
export function propertyLessThan(p1, p2) { export function propertyLessThan(p1, p2) {
return Ember.computed(function() { return Ember.computed(p1, p2, function() {
return this.get(p1) < this.get(p2); return this.get(p1) < this.get(p2);
}).property(p1, p2); });
} }
/** /**

View File

@ -1,11 +1,12 @@
import Badge from "discourse/models/badge"; import Badge from "discourse/models/badge";
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Mixin.create({ export default Ember.Mixin.create({
saving: false, saving: false,
saved: false, saved: false,
selectableUserBadges: function() { @computed("filteredList")
let items = this.get("filteredList"); selectableUserBadges(items) {
items = _.uniq(items, false, function(e) { items = _.uniq(items, false, function(e) {
return e.get("badge.name"); return e.get("badge.name");
}); });
@ -15,18 +16,16 @@ export default Ember.Mixin.create({
}) })
); );
return items; return items;
}.property("filteredList"), },
savingStatus: function() { @computed("saving")
if (this.get("saving")) { savingStatus(saving) {
return I18n.t("saving"); return saving ? I18n.t("saving") : I18n.t("save");
} else { },
return I18n.t("save");
}
}.property("saving"),
selectedUserBadge: function() { @computed("selectedUserBadgeId")
const selectedUserBadgeId = parseInt(this.get("selectedUserBadgeId")); selectedUserBadge(selectedUserBadgeId) {
selectedUserBadgeId = parseInt(selectedUserBadgeId);
let selectedUserBadge = null; let selectedUserBadge = null;
this.get("selectableUserBadges").forEach(function(userBadge) { this.get("selectableUserBadges").forEach(function(userBadge) {
if (userBadge.get("id") === selectedUserBadgeId) { if (userBadge.get("id") === selectedUserBadgeId) {
@ -34,7 +33,7 @@ export default Ember.Mixin.create({
} }
}); });
return selectedUserBadge; return selectedUserBadge;
}.property("selectedUserBadgeId"), },
disableSave: Ember.computed.alias("saving") disableSave: Ember.computed.alias("saving")
}); });

View File

@ -3,9 +3,7 @@ import RestModel from "discourse/models/rest";
import { popupAjaxError } from "discourse/lib/ajax-error"; import { popupAjaxError } from "discourse/lib/ajax-error";
export default RestModel.extend({ export default RestModel.extend({
canToggle: function() { canToggle: Ember.computed.or("can_undo", "can_act"),
return this.get("can_undo") || this.get("can_act");
}.property("can_undo", "can_act"),
// Remove it // Remove it
removeAction: function() { removeAction: function() {

View File

@ -1,13 +1,15 @@
import { ajax } from "discourse/lib/ajax"; import { ajax } from "discourse/lib/ajax";
import BadgeGrouping from "discourse/models/badge-grouping"; import BadgeGrouping from "discourse/models/badge-grouping";
import RestModel from "discourse/models/rest"; import RestModel from "discourse/models/rest";
import computed from "ember-addons/ember-computed-decorators";
const Badge = RestModel.extend({ const Badge = RestModel.extend({
newBadge: Ember.computed.none("id"), newBadge: Ember.computed.none("id"),
url: function() { @computed
url() {
return Discourse.getURL(`/badges/${this.get("id")}/${this.get("slug")}`); return Discourse.getURL(`/badges/${this.get("id")}/${this.get("slug")}`);
}.property(), },
/** /**
Update this badge with the response returned by the server on save. Update this badge with the response returned by the server on save.
@ -31,10 +33,11 @@ const Badge = RestModel.extend({
} }
}, },
badgeTypeClassName: function() { @computed("badge_type.name")
const type = this.get("badge_type.name") || ""; badgeTypeClassName(type) {
type = type || "";
return "badge-type-" + type.toLowerCase(); return "badge-type-" + type.toLowerCase();
}.property("badge_type.name"), },
/** /**
Save and update the badge from the server's response. Save and update the badge from the server's response.

View File

@ -77,9 +77,10 @@ const Composer = RestModel.extend({
draftSaving: false, draftSaving: false,
draftSaved: false, draftSaved: false,
archetypes: function() { @computed
archetypes() {
return this.site.get("archetypes"); return this.site.get("archetypes");
}.property(), },
@computed("action") @computed("action")
sharedDraft: action => action === CREATE_SHARED_DRAFT, sharedDraft: action => action === CREATE_SHARED_DRAFT,
@ -184,9 +185,10 @@ const Composer = RestModel.extend({
.property() .property()
.volatile(), .volatile(),
archetype: function() { @computed("archetypeId")
return this.get("archetypes").findBy("id", this.get("archetypeId")); archetype(archetypeId) {
}.property("archetypeId"), return this.get("archetypes").findBy("id", archetypeId);
},
archetypeChanged: function() { archetypeChanged: function() {
return this.set("metaData", Ember.Object.create()); return this.set("metaData", Ember.Object.create());
@ -377,30 +379,27 @@ const Composer = RestModel.extend({
); );
}, },
titleLengthValid: function() { @computed("minimumTitleLength", "titleLength", "post.static_doc")
if ( titleLengthValid(minTitleLength, titleLength, staticDoc) {
this.user.get("admin") && if (this.user.get("admin") && staticDoc && titleLength > 0) return true;
this.get("post.static_doc") && if (titleLength < minTitleLength) return false;
this.get("titleLength") > 0 return titleLength <= this.siteSettings.max_topic_title_length;
) },
return true;
if (this.get("titleLength") < this.get("minimumTitleLength")) return false;
return this.get("titleLength") <= this.siteSettings.max_topic_title_length;
}.property("minimumTitleLength", "titleLength", "post.static_doc"),
hasMetaData: function() { @computed("metaData")
const metaData = this.get("metaData"); hasMetaData(metaData) {
return metaData ? Ember.isEmpty(Ember.keys(this.get("metaData"))) : false; return metaData ? Ember.isEmpty(Ember.keys(this.get("metaData"))) : false;
}.property("metaData"), },
/** /**
Did the user make changes to the reply? Did the user make changes to the reply?
@property replyDirty @property replyDirty
**/ **/
replyDirty: function() { @computed("reply", "originalText")
return this.get("reply") !== this.get("originalText"); replyDirty(reply, originalText) {
}.property("reply", "originalText"), return reply !== originalText;
},
/** /**
Did the user make changes to the topic title? Did the user make changes to the topic title?
@ -417,9 +416,10 @@ const Composer = RestModel.extend({
@property missingTitleCharacters @property missingTitleCharacters
**/ **/
missingTitleCharacters: function() { @computed("minimumTitleLength", "titleLength")
return this.get("minimumTitleLength") - this.get("titleLength"); missingTitleCharacters(minimumTitleLength, titleLength) {
}.property("minimumTitleLength", "titleLength"), return minimumTitleLength - titleLength;
},
/** /**
Minimum number of characters for a title to be valid. Minimum number of characters for a title to be valid.
@ -474,23 +474,25 @@ const Composer = RestModel.extend({
@property titleLength @property titleLength
**/ **/
titleLength: function() { @computed("title")
const title = this.get("title") || ""; titleLength(title) {
title = title || "";
return title.replace(/\s+/gim, " ").trim().length; return title.replace(/\s+/gim, " ").trim().length;
}.property("title"), },
/** /**
Computes the length of the reply minus the quote(s) and non-significant whitespaces Computes the length of the reply minus the quote(s) and non-significant whitespaces
@property replyLength @property replyLength
**/ **/
replyLength: function() { @computed("reply")
let reply = this.get("reply") || ""; replyLength(reply) {
reply = reply || "";
while (Quote.REGEXP.test(reply)) { while (Quote.REGEXP.test(reply)) {
reply = reply.replace(Quote.REGEXP, ""); reply = reply.replace(Quote.REGEXP, "");
} }
return reply.replace(/\s+/gim, " ").trim().length; return reply.replace(/\s+/gim, " ").trim().length;
}.property("reply"), },
_setupComposer: function() { _setupComposer: function() {
this.set("archetypeId", this.site.get("default_archetype")); this.set("archetypeId", this.site.get("default_archetype"));

View File

@ -1,8 +1,11 @@
import computed from "ember-addons/ember-computed-decorators";
const PermissionType = Discourse.Model.extend({ const PermissionType = Discourse.Model.extend({
description: function() { @computed("id")
description(id) {
var key = ""; var key = "";
switch (this.get("id")) { switch (id) {
case 1: case 1:
key = "full"; key = "full";
break; break;
@ -14,7 +17,7 @@ const PermissionType = Discourse.Model.extend({
break; break;
} }
return I18n.t("permission_types." + key); return I18n.t("permission_types." + key);
}.property("id") }
}); });
PermissionType.FULL = 1; PermissionType.FULL = 1;

View File

@ -17,16 +17,17 @@ const Post = RestModel.extend({
return Discourse.SiteSettings; return Discourse.SiteSettings;
}, },
shareUrl: function() { @computed("url")
shareUrl(url) {
const user = Discourse.User.current(); const user = Discourse.User.current();
const userSuffix = user ? "?u=" + user.get("username_lower") : ""; const userSuffix = user ? "?u=" + user.get("username_lower") : "";
if (this.get("firstPost")) { if (this.get("firstPost")) {
return this.get("topic.url") + userSuffix; return this.get("topic.url") + userSuffix;
} else { } else {
return this.get("url") + userSuffix; return url + userSuffix;
} }
}.property("url"), },
new_user: Ember.computed.equal("trust_level", 0), new_user: Ember.computed.equal("trust_level", 0),
firstPost: Ember.computed.equal("post_number", 1), firstPost: Ember.computed.equal("post_number", 1),
@ -36,36 +37,31 @@ const Post = RestModel.extend({
deleted: Ember.computed.or("deleted_at", "deletedViaTopic"), deleted: Ember.computed.or("deleted_at", "deletedViaTopic"),
notDeleted: Ember.computed.not("deleted"), notDeleted: Ember.computed.not("deleted"),
showName: function() { @computed("name", "username")
const name = this.get("name"); showName(name, username) {
return ( return (
name && name && name !== username && Discourse.SiteSettings.display_name_on_posts
name !== this.get("username") &&
Discourse.SiteSettings.display_name_on_posts
); );
}.property("name", "username"), },
postDeletedBy: function() { @computed("firstPost", "deleted_by", "topic.deleted_by")
if (this.get("firstPost")) { postDeletedBy(firstPost, deletedBy, topicDeletedBy) {
return this.get("topic.deleted_by"); return firstPost ? topicDeletedBy : deletedBy;
} },
return this.get("deleted_by");
}.property("firstPost", "deleted_by", "topic.deleted_by"),
postDeletedAt: function() { @computed("firstPost", "deleted_at", "topic.deleted_at")
if (this.get("firstPost")) { postDeletedAt(firstPost, deletedAt, topicDeletedAt) {
return this.get("topic.deleted_at"); return firstPost ? topicDeletedAt : deletedAt;
} },
return this.get("deleted_at");
}.property("firstPost", "deleted_at", "topic.deleted_at"),
url: function() { @computed("post_number", "topic_id", "topic.slug")
url(postNr, topicId, slug) {
return postUrl( return postUrl(
this.get("topic.slug") || this.get("topic_slug"), slug || this.get("topic_slug"),
this.get("topic_id") || this.get("topic.id"), topicId || this.get("topic.id"),
this.get("post_number") postNr
); );
}.property("post_number", "topic_id", "topic.slug"), },
// Don't drop the /1 // Don't drop the /1
@computed("post_number", "url") @computed("post_number", "url")

View File

@ -1,3 +1,5 @@
import computed from "ember-addons/ember-computed-decorators";
export default Ember.ArrayProxy.extend({ export default Ember.ArrayProxy.extend({
loading: false, loading: false,
loadingMore: false, loadingMore: false,
@ -12,9 +14,10 @@ export default Ember.ArrayProxy.extend({
__type: null, __type: null,
resultSetMeta: null, resultSetMeta: null,
canLoadMore: function() { @computed("totalRows", "length")
return this.get("length") < this.get("totalRows"); canLoadMore(totalRows, length) {
}.property("totalRows", "length"), return length < totalRows;
},
loadMore() { loadMore() {
const loadMoreUrl = this.get("loadMoreUrl"); const loadMoreUrl = this.get("loadMoreUrl");

View File

@ -1,4 +1,6 @@
import { ajax } from "discourse/lib/ajax"; import { ajax } from "discourse/lib/ajax";
import computed from "ember-addons/ember-computed-decorators";
/** /**
A model representing a Topic's details that aren't always present, such as a list of participants. A model representing a Topic's details that aren't always present, such as a list of participants.
When showing topics in lists and such this information should not be required. When showing topics in lists and such this information should not be required.
@ -29,15 +31,15 @@ const TopicDetails = RestModel.extend({
this.set("loaded", true); this.set("loaded", true);
}, },
notificationReasonText: function() { @computed("notification_level", "notifications_reason_id")
let level = this.get("notification_level"); notificationReasonText(level, reason) {
if (typeof level !== "number") { if (typeof level !== "number") {
level = 1; level = 1;
} }
let localeString = `topic.notifications.reasons.${level}`; let localeString = `topic.notifications.reasons.${level}`;
if (typeof this.get("notifications_reason_id") === "number") { if (typeof reason === "number") {
const tmp = localeString + "_" + this.get("notifications_reason_id"); const tmp = localeString + "_" + reason;
// some sane protection for missing translations of edge cases // some sane protection for missing translations of edge cases
if (I18n.lookup(tmp)) { if (I18n.lookup(tmp)) {
localeString = tmp; localeString = tmp;
@ -55,7 +57,7 @@ const TopicDetails = RestModel.extend({
basePath: Discourse.BaseUri basePath: Discourse.BaseUri
}); });
} }
}.property("notification_level", "notifications_reason_id"), },
updateNotifications(v) { updateNotifications(v) {
this.set("notification_level", v); this.set("notification_level", v);

View File

@ -1,23 +1,24 @@
import RestModel from "discourse/models/rest"; import RestModel from "discourse/models/rest";
import UserAction from "discourse/models/user-action"; import UserAction from "discourse/models/user-action";
import { i18n } from "discourse/lib/computed"; import { i18n } from "discourse/lib/computed";
import computed from "ember-addons/ember-computed-decorators";
export default RestModel.extend({ export default RestModel.extend({
isPM: function() { @computed("action_type")
const actionType = this.get("action_type"); isPM(actionType) {
return ( return (
actionType === UserAction.TYPES.messages_sent || actionType === UserAction.TYPES.messages_sent ||
actionType === UserAction.TYPES.messages_received actionType === UserAction.TYPES.messages_received
); );
}.property("action_type"), },
description: i18n("action_type", "user_action_groups.%@"), description: i18n("action_type", "user_action_groups.%@"),
isResponse: function() { @computed("action_type")
const actionType = this.get("action_type"); isResponse(actionType) {
return ( return (
actionType === UserAction.TYPES.replies || actionType === UserAction.TYPES.replies ||
actionType === UserAction.TYPES.quotes actionType === UserAction.TYPES.quotes
); );
}.property("action_type") }
}); });

View File

@ -164,16 +164,7 @@ const UserAction = RestModel.extend({
} }
}, },
children: function() { @computed(
const g = this.get("childGroups");
let rval = [];
if (g) {
rval = [g.likes, g.stars, g.edits, g.bookmarks].filter(function(i) {
return i.get("items") && i.get("items").length > 0;
});
}
return rval;
}.property(
"childGroups", "childGroups",
"childGroups.likes.items", "childGroups.likes.items",
"childGroups.likes.items.[]", "childGroups.likes.items.[]",
@ -183,7 +174,17 @@ const UserAction = RestModel.extend({
"childGroups.edits.items.[]", "childGroups.edits.items.[]",
"childGroups.bookmarks.items", "childGroups.bookmarks.items",
"childGroups.bookmarks.items.[]" "childGroups.bookmarks.items.[]"
), )
children() {
const g = this.get("childGroups");
let rval = [];
if (g) {
rval = [g.likes, g.stars, g.edits, g.bookmarks].filter(function(i) {
return i.get("items") && i.get("items").length > 0;
});
}
return rval;
},
switchToActing() { switchToActing() {
this.setProperties({ this.setProperties({

View File

@ -1,12 +1,14 @@
import { ajax } from "discourse/lib/ajax"; import { ajax } from "discourse/lib/ajax";
import Badge from "discourse/models/badge"; import Badge from "discourse/models/badge";
import computed from "ember-addons/ember-computed-decorators";
const UserBadge = Discourse.Model.extend({ const UserBadge = Discourse.Model.extend({
@computed
postUrl: function() { postUrl: function() {
if (this.get("topic_title")) { if (this.get("topic_title")) {
return "/t/-/" + this.get("topic_id") + "/" + this.get("post_number"); return "/t/-/" + this.get("topic_id") + "/" + this.get("post_number");
} }
}.property(), // avoid the extra bindings for now }, // avoid the extra bindings for now
revoke() { revoke() {
return ajax("/user_badges/" + this.get("id"), { return ajax("/user_badges/" + this.get("id"), {

View File

@ -3,6 +3,7 @@ import { url } from "discourse/lib/computed";
import RestModel from "discourse/models/rest"; import RestModel from "discourse/models/rest";
import UserAction from "discourse/models/user-action"; import UserAction from "discourse/models/user-action";
import { emojiUnescape } from "discourse/lib/text"; import { emojiUnescape } from "discourse/lib/text";
import computed from "ember-addons/ember-computed-decorators";
export default RestModel.extend({ export default RestModel.extend({
loaded: false, loaded: false,
@ -11,8 +12,8 @@ export default RestModel.extend({
this.setProperties({ itemsLoaded: 0, content: [] }); this.setProperties({ itemsLoaded: 0, content: [] });
}.on("init"), }.on("init"),
filterParam: function() { @computed("filter")
const filter = this.get("filter"); filterParam(filter) {
if (filter === Discourse.UserAction.TYPES.replies) { if (filter === Discourse.UserAction.TYPES.replies) {
return [UserAction.TYPES.replies, UserAction.TYPES.quotes].join(","); return [UserAction.TYPES.replies, UserAction.TYPES.quotes].join(",");
} }
@ -22,7 +23,7 @@ export default RestModel.extend({
} }
return filter; return filter;
}.property("filter"), },
baseUrl: url( baseUrl: url(
"itemsLoaded", "itemsLoaded",
@ -45,9 +46,10 @@ export default RestModel.extend({
return this.findItems(); return this.findItems();
}, },
noContent: function() { @computed("loaded", "content.[]")
noContent() {
return this.get("loaded") && this.get("content").length === 0; return this.get("loaded") && this.get("content").length === 0;
}.property("loaded", "content.[]"), },
remove(userAction) { remove(userAction) {
// 1) remove the user action from the child groups // 1) remove the user action from the child groups

View File

@ -1,5 +1,8 @@
import computed from "ember-addons/ember-computed-decorators";
export default Ember.Object.extend({ export default Ember.Object.extend({
@computed
isLastVisited: function() { isLastVisited: function() {
return this.get("lastVisitedTopic") === this.get("topic"); return this.get("lastVisitedTopic") === this.get("topic");
}.property() }
}); });

View File

@ -17,7 +17,7 @@
bulkSelectEnabled=bulkSelectEnabled bulkSelectEnabled=bulkSelectEnabled
canBulkSelect=canBulkSelect canBulkSelect=canBulkSelect
selected=selected selected=selected
skipHeader=skipHeader skipHeader=site.mobileView
tagsForUser=tagsForUser}} tagsForUser=tagsForUser}}
{{else}} {{else}}
{{#unless loadingMore}} {{#unless loadingMore}}

View File

@ -1,4 +1,4 @@
{{#unless skipHeader}} {{#unless site.mobileView}}
<thead> <thead>
{{raw "topic-list-header" {{raw "topic-list-header"
canBulkSelect=canBulkSelect canBulkSelect=canBulkSelect