Date: Thu, 7 Nov 2019 15:38:28 -0600
Subject: [PATCH 025/408] DEV: Move computed to discourseComputed (#8312)
---
.../admin/components/ace-editor.js.es6 | 2 +-
.../components/admin-backups-logs.js.es6 | 2 +-
.../admin-report-storage-stats.js.es6 | 14 ++--
.../components/admin-report-table-cell.js.es6 | 4 +-
.../admin-report-table-header.js.es6 | 6 +-
.../components/admin-report-table.js.es6 | 32 ++++++----
.../admin/components/admin-report.js.es6 | 18 +++---
.../components/admin-theme-editor.js.es6 | 20 +++---
.../components/admin-user-field-item.js.es6 | 10 +--
.../admin-web-hook-event-chooser.js.es6 | 10 +--
.../components/admin-web-hook-event.js.es6 | 12 ++--
.../components/admin-web-hook-status.js.es6 | 8 +--
.../components/email-styles-editor.js.es6 | 8 +--
.../admin/components/embeddable-host.js.es6 | 6 +-
.../admin/components/embedding-setting.js.es6 | 10 +--
.../admin/components/highlighted-code.js.es6 | 2 +-
.../components/inline-edit-checkbox.js.es6 | 8 +--
.../admin/components/ip-lookup.js.es6 | 4 +-
.../components/penalty-post-action.js.es6 | 4 +-
.../admin/components/permalink-form.js.es6 | 4 +-
.../components/report-filters/category.js.es6 | 4 +-
.../components/report-filters/group.js.es6 | 6 +-
.../admin/components/resumable-upload.js.es6 | 8 +--
.../admin/components/save-controls.js.es6 | 4 +-
.../screened-ip-address-form.js.es6 | 8 +--
.../admin/components/secret-value-list.js.es6 | 2 +-
.../components/site-settings/bool.js.es6 | 4 +-
.../site-settings/category-list.js.es6 | 4 +-
.../site-settings/group-list.js.es6 | 4 +-
.../components/site-settings/tag-list.js.es6 | 4 +-
.../admin/components/site-text-summary.js.es6 | 2 +-
.../admin/components/themes-list-item.js.es6 | 10 +--
.../admin/components/themes-list.js.es6 | 8 +--
.../admin/components/value-list.js.es6 | 6 +-
.../admin/components/watched-word-form.js.es6 | 8 +--
.../components/watched-word-uploader.js.es6 | 4 +-
.../controllers/admin-api-keys-new.js.es6 | 6 +-
.../controllers/admin-backups-index.js.es6 | 4 +-
.../controllers/admin-badges-show.js.es6 | 4 +-
.../admin-customize-colors-show.js.es6 | 4 +-
.../controllers/admin-customize-colors.js.es6 | 8 +--
.../admin-customize-email-style-edit.js.es6 | 6 +-
...dmin-customize-email-templates-edit.js.es6 | 6 +-
.../admin-customize-themes-edit.js.es6 | 8 +--
.../admin-customize-themes-show.js.es6 | 22 +++----
.../controllers/admin-customize-themes.js.es6 | 8 +--
.../admin-dashboard-general.js.es6 | 18 +++---
.../admin-dashboard-moderation.js.es6 | 10 +--
.../admin-dashboard-reports.js.es6 | 5 +-
.../admin/controllers/admin-dashboard.js.es6 | 6 +-
.../admin/controllers/admin-embedding.js.es6 | 6 +-
.../admin-logs-staff-action-logs.js.es6 | 6 +-
.../admin/controllers/admin-plugins.js.es6 | 4 +-
.../controllers/admin-reports-show.js.es6 | 4 +-
.../admin-site-settings-category.js.es6 | 6 +-
.../controllers/admin-site-text-edit.js.es6 | 4 +-
.../controllers/admin-user-badges.js.es6 | 4 +-
.../admin/controllers/admin-user-index.js.es6 | 22 ++++---
.../controllers/admin-users-list-show.js.es6 | 4 +-
.../admin-watched-words-action.js.es6 | 10 +--
.../admin-web-hooks-show-events.js.es6 | 4 +-
.../controllers/admin-web-hooks-show.js.es6 | 14 ++--
.../admin/controllers/admin.js.es6 | 8 +--
.../modals/admin-add-upload.js.es6 | 8 +--
.../modals/admin-badge-preview.js.es6 | 8 +--
.../modals/admin-edit-badge-groupings.js.es6 | 2 +-
.../modals/admin-incoming-email.js.es6 | 4 +-
.../modals/admin-install-theme.js.es6 | 16 ++---
.../modals/admin-silence-user.js.es6 | 4 +-
.../modals/admin-suspend-user.js.es6 | 4 +-
.../modals/admin-uploaded-image-list.js.es6 | 2 +-
.../modals/admin-watched-word-test.js.es6 | 4 +-
.../admin/mixins/period-computation.js.es6 | 12 ++--
.../admin/mixins/setting-component.js.es6 | 18 +++---
.../admin/mixins/setting-object.js.es6 | 8 +--
.../admin/models/admin-user.js.es6 | 18 +++---
.../javascripts/admin/models/api-key.js.es6 | 8 +--
.../admin/models/backup-status.js.es6 | 4 +-
.../admin/models/color-scheme-color.js.es6 | 16 ++---
.../admin/models/color-scheme.js.es6 | 8 +--
.../javascripts/admin/models/flag-type.js.es6 | 4 +-
.../javascripts/admin/models/report.js.es6 | 59 +++++++++--------
.../admin/models/screened-email.js.es6 | 4 +-
.../admin/models/screened-ip-address.js.es6 | 6 +-
.../admin/models/screened-url.js.es6 | 4 +-
.../admin/models/staff-action-log.js.es6 | 10 +--
.../javascripts/admin/models/theme.js.es6 | 26 ++++----
.../admin/models/tl3-requirements.js.es6 | 8 +--
.../admin/models/version-check.js.es6 | 12 ++--
.../javascripts/admin/models/web-hook.js.es6 | 10 +--
app/assets/javascripts/application.js | 3 +-
.../lib/raw-handlebars.js.es6 | 2 +-
.../utils/decorators.js.es6} | 14 ++--
app/assets/javascripts/discourse-loader.js | 11 +++-
app/assets/javascripts/discourse.js.es6 | 8 +--
.../add-category-tag-classes.js.es6 | 2 +-
.../discourse/components/avatar-flair.js.es6 | 2 +-
.../components/avatar-uploader.js.es6 | 4 +-
.../discourse/components/backup-codes.js.es6 | 6 +-
.../components/backup-uploader.js.es6 | 4 +-
.../discourse/components/badge-button.js.es6 | 4 +-
.../discourse/components/badge-card.js.es6 | 8 +--
.../components/badge-selector.js.es6 | 6 +-
.../discourse/components/badge-title.js.es6 | 4 +-
.../components/basic-topic-list.js.es6 | 6 +-
.../discourse/components/bread-crumbs.js.es6 | 10 +--
.../components/categories-boxes-topic.js.es6 | 4 +-
.../categories-boxes-with-topics.js.es6 | 4 +-
.../components/categories-boxes.js.es6 | 6 +-
.../discourse/components/cdn-img.js.es6 | 6 +-
.../components/choose-message.js.es6 | 2 +-
.../discourse/components/choose-topic.js.es6 | 2 +-
.../components/color-picker-choice.js.es6 | 8 +--
.../components/composer-action-title.js.es6 | 4 +-
.../discourse/components/composer-body.js.es6 | 8 +--
.../components/composer-editor.js.es6 | 17 +++--
.../components/composer-message.js.es6 | 4 +-
.../components/composer-title.js.es6 | 10 +--
.../components/composer-toggles.js.es6 | 10 +--
.../components/composer-user-selector.js.es6 | 10 +--
.../conditional-loading-spinner.js.es6 | 4 +-
.../components/create-topics-notice.js.es6 | 15 +++--
.../discourse/components/csv-uploader.js.es6 | 6 +-
.../discourse/components/d-button.js.es6 | 8 +--
.../discourse/components/d-editor.js.es6 | 8 +--
.../discourse/components/d-modal.js.es6 | 2 +-
.../discourse/components/d-navigation.js.es6 | 12 ++--
.../discourse/components/date-input.js.es6 | 8 +--
.../discourse/components/date-picker.js.es6 | 8 +--
.../desktop-notification-config.js.es6 | 16 ++---
.../components/directory-toggle.js.es6 | 4 +-
.../components/discourse-banner.js.es6 | 4 +-
.../components/discourse-linked-text.js.es6 | 4 +-
.../components/discourse-tag-bound.js.es6 | 6 +-
.../components/discourse-topic.js.es6 | 2 +-
.../components/discovery-categories.js.es6 | 2 +-
.../components/discovery-topics-list.js.es6 | 2 +-
.../components/edit-category-general.js.es6 | 16 ++---
.../components/edit-category-images.js.es6 | 6 +-
.../components/edit-category-security.js.es6 | 2 +-
.../components/edit-category-settings.js.es6 | 14 ++--
.../components/edit-category-tab.js.es6 | 6 +-
.../components/edit-topic-timer-form.js.es6 | 9 ++-
.../discourse/components/emoji-picker.js.es6 | 3 +-
.../components/emoji-uploader.js.es6 | 4 +-
.../components/expanding-text-area.js.es6 | 2 +-
.../components/flag-action-type.js.es6 | 19 ++++--
.../components/flag-selection.js.es6 | 2 +-
.../discourse/components/flat-button.js.es6 | 4 +-
.../discourse/components/footer-nav.js.es6 | 2 +-
.../components/future-date-input.js.es6 | 14 ++--
.../discourse/components/global-notice.js.es6 | 2 +-
.../discourse/components/google-search.js.es6 | 4 +-
.../components/group-card-contents.js.es6 | 8 +--
.../components/group-flair-inputs.js.es6 | 18 +++---
.../group-manage-logs-filter.js.es6 | 6 +-
.../group-manage-save-button.js.es6 | 4 +-
.../components/group-member-dropdown.js.es6 | 4 +-
.../components/group-members-input.js.es6 | 8 +--
.../components/group-membership-button.js.es6 | 10 +--
.../discourse/components/group-post.js.es6 | 4 +-
.../components/group-selector.js.es6 | 6 +-
.../groups-form-interaction-fields.js.es6 | 8 ++-
.../groups-form-membership-fields.js.es6 | 9 ++-
.../groups-form-profile-fields.js.es6 | 6 +-
.../discourse/components/groups-info.js.es6 | 4 +-
.../components/honeypot-input.js.es6 | 2 +-
.../components/image-uploader.js.es6 | 12 ++--
.../components/images-uploader.js.es6 | 4 +-
.../discourse/components/invite-panel.js.es6 | 30 ++++-----
.../discourse/components/login-buttons.js.es6 | 6 +-
.../discourse/components/mobile-nav.js.es6 | 2 +-
.../discourse/components/nav-item.js.es6 | 6 +-
.../components/navigation-bar.js.es6 | 6 +-
.../components/navigation-item.js.es6 | 4 +-
.../notification-consent-banner.js.es6 | 8 +--
.../discourse/components/number-field.js.es6 | 6 +-
.../components/plugin-connector.js.es6 | 2 +-
.../components/popup-input-tip.js.es6 | 6 +-
.../components/preference-checkbox.js.es6 | 4 +-
.../components/pwa-install-banner.js.es6 | 8 +--
.../discourse/components/radio-button.js.es6 | 4 +-
.../components/related-messages.js.es6 | 8 +--
.../reviewable-claimed-topic.js.es6 | 4 +-
.../components/reviewable-flagged-post.js.es6 | 6 +-
.../components/reviewable-item.js.es6 | 15 +++--
.../components/reviewable-user.js.es6 | 4 +-
.../components/search-advanced-options.js.es6 | 2 +-
.../components/search-text-field.js.es6 | 6 +-
.../components/second-factor-form.js.es6 | 10 +--
.../components/second-factor-input.js.es6 | 8 +--
.../discourse/components/share-panel.js.es6 | 8 +--
.../discourse/components/share-popup.js.es6 | 10 +--
.../components/shared-draft-controls.js.es6 | 4 +-
.../discourse/components/site-header.js.es6 | 2 +-
.../components/suggested-topics.js.es6 | 6 +-
.../discourse/components/tag-drop-link.js.es6 | 6 +-
.../components/tag-groups-form.js.es6 | 4 +-
.../discourse/components/tag-list.js.es6 | 10 +--
.../discourse/components/text-field.js.es6 | 6 +-
.../components/top-period-buttons.js.es6 | 4 +-
.../components/topic-entrance.js.es6 | 12 ++--
.../components/topic-footer-buttons.js.es6 | 18 +++---
.../components/topic-join-group-notice.js.es6 | 6 +-
.../components/topic-list-item.js.es6 | 14 ++--
.../discourse/components/topic-list.js.es6 | 12 ++--
.../components/topic-navigation.js.es6 | 2 +-
.../components/topic-progress.js.es6 | 16 ++---
.../discourse/components/topic-status.js.es6 | 4 +-
.../components/topic-timeline.js.es6 | 2 +-
.../components/topic-timer-info.js.es6 | 4 +-
.../discourse/components/user-badge.js.es6 | 6 +-
.../components/user-card-contents.js.es6 | 26 ++++----
.../discourse/components/user-field.js.es6 | 6 +-
.../components/user-flag-percentage.js.es6 | 6 +-
.../discourse/components/user-info.js.es6 | 6 +-
.../user-notifications-large.js.es6 | 2 +-
.../discourse/components/user-selector.js.es6 | 2 +-
.../user-summary-category-search.js.es6 | 4 +-
.../user-summary-topics-list.js.es6 | 4 +-
.../discourse/controllers/about.js.es6 | 4 +-
.../account-created-edit-email.js.es6 | 4 +-
.../controllers/activation-edit.js.es6 | 4 +-
.../controllers/add-post-notice.js.es6 | 4 +-
.../discourse/controllers/application.js.es6 | 8 +--
.../controllers/avatar-selector.js.es6 | 8 +--
.../discourse/controllers/badges/index.js.es6 | 4 +-
.../discourse/controllers/badges/show.js.es6 | 20 +++---
.../bulk-notification-level.js.es6 | 4 +-
.../discourse/controllers/change-owner.js.es6 | 4 +-
.../controllers/change-timestamp.js.es6 | 10 +--
.../discourse/controllers/composer.js.es6 | 42 ++++++------
.../controllers/create-account.js.es6 | 22 ++++---
.../controllers/discovery/categories.js.es6 | 6 +-
.../controllers/discovery/topics.js.es6 | 12 ++--
.../controllers/edit-category.js.es6 | 14 ++--
.../controllers/edit-topic-timer.js.es6 | 14 ++--
.../discourse/controllers/email-login.js.es6 | 6 +-
.../discourse/controllers/exception.js.es6 | 12 ++--
.../controllers/feature-topic.js.es6 | 26 ++++----
.../discourse/controllers/flag.js.es6 | 20 +++---
.../controllers/forgot-password.js.es6 | 4 +-
.../controllers/full-page-search.js.es6 | 32 +++++-----
.../discourse/controllers/grant-badge.js.es6 | 8 +--
.../controllers/group-activity-posts.js.es6 | 2 +-
.../controllers/group-add-members.js.es6 | 4 +-
.../controllers/group-bulk-add.js.es6 | 4 +-
.../discourse/controllers/group-index.js.es6 | 12 ++--
.../controllers/group-manage-logs.js.es6 | 6 +-
.../discourse/controllers/group-manage.js.es6 | 4 +-
.../controllers/group-requests.js.es6 | 8 +--
.../discourse/controllers/group.js.es6 | 16 ++---
.../discourse/controllers/groups-index.js.es6 | 6 +-
.../discourse/controllers/history.js.es6 | 48 ++++++++------
.../discourse/controllers/invites-show.js.es6 | 12 ++--
.../discourse/controllers/login.js.es6 | 18 +++---
.../controllers/move-to-topic.js.es6 | 10 +--
.../controllers/navigation/categories.js.es6 | 7 +-
.../controllers/navigation/default.js.es6 | 4 +-
.../controllers/password-reset.js.es6 | 8 +--
.../controllers/preferences/account.js.es6 | 16 ++---
.../controllers/preferences/categories.js.es6 | 8 +--
.../controllers/preferences/email.js.es6 | 10 +--
.../controllers/preferences/emails.js.es6 | 8 +--
.../controllers/preferences/interface.js.es6 | 26 ++++----
.../controllers/preferences/profile.js.es6 | 6 +-
.../preferences/second-factor.js.es6 | 6 +-
.../controllers/preferences/tags.js.es6 | 4 +-
.../controllers/preferences/username.js.es6 | 6 +-
.../discourse/controllers/rename-tag.js.es6 | 4 +-
.../controllers/reorder-categories.js.es6 | 8 +--
.../request-group-membership-form.js.es6 | 6 +-
.../discourse/controllers/review-index.js.es6 | 12 ++--
.../discourse/controllers/search-help.js.es6 | 4 +-
.../second-factor-backup-edit.js.es6 | 4 +-
.../discourse/controllers/static.js.es6 | 6 +-
.../discourse/controllers/tags-index.js.es6 | 6 +-
.../discourse/controllers/tags-show.js.es6 | 16 ++---
.../discourse/controllers/topic.js.es6 | 49 ++++++++------
.../controllers/upload-selector.js.es6 | 10 +--
.../controllers/user-invited-show.js.es6 | 10 +--
.../controllers/user-notifications.js.es6 | 8 +--
.../controllers/user-private-messages.js.es6 | 8 +--
.../discourse/controllers/user-summary.js.es6 | 10 +--
.../controllers/user-topics-list.js.es6 | 4 +-
.../discourse/controllers/user.js.es6 | 35 +++++-----
.../helpers/reviewable-status.js.es6 | 1 -
.../javascripts/discourse/lib/computed.js.es6 | 12 ++--
.../lib/posts-with-placeholders.js.es6 | 4 +-
.../lib/register-topic-footer-button.js.es6 | 26 ++++----
.../mixins/add-archetype-class.js.es6 | 2 +-
.../mixins/bulk-topic-selection.js.es6 | 2 +-
.../mixins/grant-badge-controller.js.es6 | 6 +-
.../discourse/mixins/load-more.js.es6 | 2 +-
.../discourse/mixins/name-validation.js.es6 | 6 +-
.../mixins/password-validation.js.es6 | 8 +--
.../mixins/preferences-tab-controller.js.es6 | 4 +-
.../discourse/mixins/upload.js.es6 | 1 -
.../mixins/user-fields-validation.js.es6 | 6 +-
.../mixins/username-validation.js.es6 | 6 +-
.../discourse/models/badge-grouping.js.es6 | 6 +-
.../javascripts/discourse/models/badge.js.es6 | 6 +-
.../discourse/models/category.js.es6 | 36 +++++------
.../discourse/models/composer.js.es6 | 56 +++++++++-------
.../discourse/models/group-history.js.es6 | 4 +-
.../javascripts/discourse/models/group.js.es6 | 18 +++---
.../discourse/models/login-method.js.es6 | 8 +--
.../discourse/models/nav-item.js.es6 | 18 +++---
.../discourse/models/permission-type.js.es6 | 4 +-
.../discourse/models/post-stream.js.es6 | 28 ++++----
.../javascripts/discourse/models/post.js.es6 | 20 +++---
.../discourse/models/result-set.js.es6 | 4 +-
.../discourse/models/reviewable.js.es6 | 4 +-
.../javascripts/discourse/models/site.js.es6 | 12 ++--
.../discourse/models/tag-group.js.es6 | 4 +-
.../javascripts/discourse/models/tag.js.es6 | 6 +-
.../discourse/models/topic-details.js.es6 | 4 +-
.../models/topic-tracking-state.js.es6 | 6 +-
.../javascripts/discourse/models/topic.js.es6 | 64 +++++++++----------
.../discourse/models/user-action-stat.js.es6 | 6 +-
.../discourse/models/user-action.js.es6 | 22 +++----
.../discourse/models/user-badge.js.es6 | 4 +-
.../discourse/models/user-draft.js.es6 | 11 ++--
.../models/user-drafts-stream.js.es6 | 4 +-
.../discourse/models/user-posts-stream.js.es6 | 2 +-
.../discourse/models/user-stream.js.es6 | 8 +--
.../javascripts/discourse/models/user.js.es6 | 62 +++++++++---------
.../list/post-count-or-badges.js.es6 | 4 +-
.../raw-views/list/posts-count-column.js.es6 | 8 +--
.../raw-views/list/visited-line.js.es6 | 4 +-
.../raw-views/topic-list-header-column.js.es6 | 10 +--
.../discourse/raw-views/topic-status.js.es6 | 6 +-
.../discourse/services/logs-notice.js.es6 | 14 ++--
.../discourse/services/search.js.es6 | 6 +-
.../components/reviewable-score.js.es6 | 4 +-
.../ember-addons/decorator-alias.js.es6 | 2 +-
.../engines/discourse-markdown/onebox.js.es6 | 1 -
.../components/admin-group-selector.js.es6 | 5 +-
.../components/category-chooser.js.es6 | 4 +-
.../components/category-drop.js.es6 | 17 +++--
.../category-drop/category-drop-header.js.es6 | 10 +--
.../select-kit/components/category-row.js.es6 | 26 ++++----
.../color-palettes/color-palettes-row.js.es6 | 4 +-
.../select-kit/components/combo-box.js.es6 | 6 +-
.../components/composer-actions.js.es6 | 4 +-
.../components/dropdown-select-box.js.es6 | 2 +-
.../dropdown-select-box-header.js.es6 | 4 +-
.../components/group-dropdown.js.es6 | 6 +-
.../components/mini-tag-chooser.js.es6 | 10 +--
.../select-kit/components/multi-select.js.es6 | 22 ++++---
.../multi-select/multi-select-filter.js.es6 | 6 +-
.../multi-select/multi-select-header.js.es6 | 8 +--
.../multi-select/selected-category.js.es6 | 4 +-
.../multi-select/selected-color.js.es6 | 4 +-
.../multi-select/selected-name.js.es6 | 8 +--
.../components/none-category-row.js.es6 | 4 +-
.../components/notifications-button.js.es6 | 8 +--
.../notifications-button-row.js.es6 | 15 +++--
.../components/period-chooser.js.es6 | 4 +-
.../period-chooser/period-chooser-row.js.es6 | 4 +-
.../components/pinned-button.js.es6 | 6 +-
.../components/pinned-options.js.es6 | 2 +-
.../select-kit/components/select-kit.js.es6 | 45 ++++++++-----
.../select-kit/select-kit-filter.js.es6 | 7 +-
.../select-kit/select-kit-header.js.es6 | 9 +--
.../select-kit/select-kit-row.js.es6 | 15 +++--
.../components/single-select.js.es6 | 19 ++++--
.../select-kit/components/tag-chooser.js.es6 | 6 +-
.../select-kit/components/tag-drop.js.es6 | 22 +++----
.../components/tag-group-chooser.js.es6 | 7 +-
.../tag-notifications-button.js.es6 | 4 +-
.../components/timezone-input.js.es6 | 4 +-
.../toolbar-popup-menu-options.js.es6 | 4 +-
.../topic-notifications-options.js.es6 | 6 +-
.../user-notifications-dropdown.js.es6 | 6 +-
.../select-kit/mixins/dom-helpers.js.es6 | 2 +-
.../select-kit/mixins/events.js.es6 | 2 +-
app/assets/javascripts/wizard-application.js | 2 +-
.../wizard/components/homepage-preview.js.es6 | 2 +-
.../components/image-preview-favicon.js.es6 | 3 +-
.../image-preview-large-icon.js.es6 | 2 +-
.../image-preview-logo-small.js.es6 | 3 +-
.../components/image-preview-logo.js.es6 | 3 +-
.../wizard/components/invite-list-user.js.es6 | 4 +-
.../wizard/components/radio-button.js.es6 | 2 +-
.../wizard/components/staff-count.js.es6 | 4 +-
.../wizard/components/theme-preview.js.es6 | 7 +-
.../components/wizard-field-image.js.es6 | 4 +-
.../wizard/components/wizard-field.js.es6 | 8 +--
.../wizard/components/wizard-step-form.js.es6 | 4 +-
.../wizard/components/wizard-step.js.es6 | 18 +++---
.../wizard/controllers/application.js.es6 | 4 +-
.../wizard/mixins/valid-state.js.es6 | 8 +--
.../javascripts/wizard/models/step.js.es6 | 6 +-
.../javascripts/wizard/models/wizard.js.es6 | 4 +-
395 files changed, 1770 insertions(+), 1649 deletions(-)
rename app/assets/javascripts/{ember-addons/ember-computed-decorators.js.es6 => discourse-common/utils/decorators.js.es6} (82%)
diff --git a/app/assets/javascripts/admin/components/ace-editor.js.es6 b/app/assets/javascripts/admin/components/ace-editor.js.es6
index 60498a0bdb..4fc881dae4 100644
--- a/app/assets/javascripts/admin/components/ace-editor.js.es6
+++ b/app/assets/javascripts/admin/components/ace-editor.js.es6
@@ -1,6 +1,6 @@
import Component from "@ember/component";
import loadScript from "discourse/lib/load-script";
-import { observes } from "ember-addons/ember-computed-decorators";
+import { observes } from "discourse-common/utils/decorators";
import { on } from "@ember/object/evented";
export default Component.extend({
diff --git a/app/assets/javascripts/admin/components/admin-backups-logs.js.es6 b/app/assets/javascripts/admin/components/admin-backups-logs.js.es6
index ccacb2e705..72706af79f 100644
--- a/app/assets/javascripts/admin/components/admin-backups-logs.js.es6
+++ b/app/assets/javascripts/admin/components/admin-backups-logs.js.es6
@@ -4,7 +4,7 @@ import debounce from "discourse/lib/debounce";
import { renderSpinner } from "discourse/helpers/loading-spinner";
import { escapeExpression } from "discourse/lib/utilities";
import { bufferedRender } from "discourse-common/lib/buffered-render";
-import { observes, on } from "ember-addons/ember-computed-decorators";
+import { observes, on } from "discourse-common/utils/decorators";
export default Component.extend(
bufferedRender({
diff --git a/app/assets/javascripts/admin/components/admin-report-storage-stats.js.es6 b/app/assets/javascripts/admin/components/admin-report-storage-stats.js.es6
index 948ecf1e87..61629c626e 100644
--- a/app/assets/javascripts/admin/components/admin-report-storage-stats.js.es6
+++ b/app/assets/javascripts/admin/components/admin-report-storage-stats.js.es6
@@ -1,7 +1,7 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { alias } from "@ember/object/computed";
import Component from "@ember/component";
import { setting } from "discourse/lib/computed";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
classNames: ["admin-report-storage-stats"],
@@ -10,32 +10,32 @@ export default Component.extend({
backupStats: alias("model.data.backups"),
uploadStats: alias("model.data.uploads"),
- @computed("backupStats")
+ @discourseComputed("backupStats")
showBackupStats(stats) {
return stats && this.currentUser.admin;
},
- @computed("backupLocation")
+ @discourseComputed("backupLocation")
backupLocationName(backupLocation) {
return I18n.t(`admin.backups.location.${backupLocation}`);
},
- @computed("backupStats.used_bytes")
+ @discourseComputed("backupStats.used_bytes")
usedBackupSpace(bytes) {
return I18n.toHumanSize(bytes);
},
- @computed("backupStats.free_bytes")
+ @discourseComputed("backupStats.free_bytes")
freeBackupSpace(bytes) {
return I18n.toHumanSize(bytes);
},
- @computed("uploadStats.used_bytes")
+ @discourseComputed("uploadStats.used_bytes")
usedUploadSpace(bytes) {
return I18n.toHumanSize(bytes);
},
- @computed("uploadStats.free_bytes")
+ @discourseComputed("uploadStats.free_bytes")
freeUploadSpace(bytes) {
return I18n.toHumanSize(bytes);
}
diff --git a/app/assets/javascripts/admin/components/admin-report-table-cell.js.es6 b/app/assets/javascripts/admin/components/admin-report-table-cell.js.es6
index f83a33dbfb..e7bf688f2f 100644
--- a/app/assets/javascripts/admin/components/admin-report-table-cell.js.es6
+++ b/app/assets/javascripts/admin/components/admin-report-table-cell.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { alias } from "@ember/object/computed";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
tagName: "td",
@@ -8,7 +8,7 @@ export default Component.extend({
classNameBindings: ["type", "property"],
options: null,
- @computed("label", "data", "options")
+ @discourseComputed("label", "data", "options")
computedLabel(label, data, options) {
return label.compute(data, options || {});
},
diff --git a/app/assets/javascripts/admin/components/admin-report-table-header.js.es6 b/app/assets/javascripts/admin/components/admin-report-table-header.js.es6
index 9317ef1f66..bc5633b21d 100644
--- a/app/assets/javascripts/admin/components/admin-report-table-header.js.es6
+++ b/app/assets/javascripts/admin/components/admin-report-table-header.js.es6
@@ -1,5 +1,5 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
tagName: "th",
@@ -7,12 +7,12 @@ export default Component.extend({
classNameBindings: ["label.mainProperty", "label.type", "isCurrentSort"],
attributeBindings: ["label.title:title"],
- @computed("currentSortLabel.sortProperty", "label.sortProperty")
+ @discourseComputed("currentSortLabel.sortProperty", "label.sortProperty")
isCurrentSort(currentSortField, labelSortField) {
return currentSortField === labelSortField;
},
- @computed("currentSortDirection")
+ @discourseComputed("currentSortDirection")
sortIcon(currentSortDirection) {
return currentSortDirection === 1 ? "caret-up" : "caret-down";
}
diff --git a/app/assets/javascripts/admin/components/admin-report-table.js.es6 b/app/assets/javascripts/admin/components/admin-report-table.js.es6
index 38e00c8ab8..aa636224d4 100644
--- a/app/assets/javascripts/admin/components/admin-report-table.js.es6
+++ b/app/assets/javascripts/admin/components/admin-report-table.js.es6
@@ -1,7 +1,7 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { makeArray } from "discourse-common/lib/helpers";
import { alias } from "@ember/object/computed";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
const PAGES_LIMIT = 8;
@@ -13,12 +13,16 @@ export default Component.extend({
perPage: alias("options.perPage"),
page: 0,
- @computed("model.computedLabels.length")
+ @discourseComputed("model.computedLabels.length")
twoColumns(labelsLength) {
return labelsLength === 2;
},
- @computed("totalsForSample", "options.total", "model.dates_filtering")
+ @discourseComputed(
+ "totalsForSample",
+ "options.total",
+ "model.dates_filtering"
+ )
showTotalForSample(totalsForSample, total, datesFiltering) {
// check if we have at least one cell which contains a value
const sum = totalsForSample
@@ -29,12 +33,16 @@ export default Component.extend({
return sum >= 1 && total && datesFiltering;
},
- @computed("model.total", "options.total", "twoColumns")
+ @discourseComputed("model.total", "options.total", "twoColumns")
showTotal(reportTotal, total, twoColumns) {
return reportTotal && total && twoColumns;
},
- @computed("model.{average,data}", "totalsForSample.1.value", "twoColumns")
+ @discourseComputed(
+ "model.{average,data}",
+ "totalsForSample.1.value",
+ "twoColumns"
+ )
showAverage(model, sampleTotalValue, hasTwoColumns) {
return (
model.average &&
@@ -44,17 +52,17 @@ export default Component.extend({
);
},
- @computed("totalsForSample.1.value", "model.data.length")
+ @discourseComputed("totalsForSample.1.value", "model.data.length")
averageForSample(totals, count) {
return (totals / count).toFixed(0);
},
- @computed("model.data.length")
+ @discourseComputed("model.data.length")
showSortingUI(dataLength) {
return dataLength >= 5;
},
- @computed("totalsForSampleRow", "model.computedLabels")
+ @discourseComputed("totalsForSampleRow", "model.computedLabels")
totalsForSample(row, labels) {
return labels.map(label => {
const computedLabel = label.compute(row);
@@ -64,7 +72,7 @@ export default Component.extend({
});
},
- @computed("model.data", "model.computedLabels")
+ @discourseComputed("model.data", "model.computedLabels")
totalsForSampleRow(rows, labels) {
if (!rows || !rows.length) return {};
@@ -90,7 +98,7 @@ export default Component.extend({
return totalsRow;
},
- @computed("sortLabel", "sortDirection", "model.data.[]")
+ @discourseComputed("sortLabel", "sortDirection", "model.data.[]")
sortedData(sortLabel, sortDirection, data) {
data = makeArray(data);
@@ -110,7 +118,7 @@ export default Component.extend({
return data;
},
- @computed("sortedData.[]", "perPage", "page")
+ @discourseComputed("sortedData.[]", "perPage", "page")
paginatedData(data, perPage, page) {
if (perPage < data.length) {
const start = perPage * page;
@@ -120,7 +128,7 @@ export default Component.extend({
return data;
},
- @computed("model.data", "perPage", "page")
+ @discourseComputed("model.data", "perPage", "page")
pages(data, perPage, page) {
if (!data || data.length <= perPage) return [];
diff --git a/app/assets/javascripts/admin/components/admin-report.js.es6 b/app/assets/javascripts/admin/components/admin-report.js.es6
index 59aaf29c3b..cb70fc07ff 100644
--- a/app/assets/javascripts/admin/components/admin-report.js.es6
+++ b/app/assets/javascripts/admin/components/admin-report.js.es6
@@ -1,3 +1,4 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { makeArray } from "discourse-common/lib/helpers";
import { alias, or, and, reads, equal, notEmpty } from "@ember/object/computed";
import EmberObject from "@ember/object";
@@ -8,7 +9,6 @@ import { exportEntity } from "discourse/lib/export-csv";
import { outputExportResult } from "discourse/lib/export-result";
import { isNumeric } from "discourse/lib/utilities";
import { SCHEMA_VERSION, default as Report } from "admin/models/report";
-import computed from "ember-addons/ember-computed-decorators";
import ENV from "discourse-common/config/environment";
const TABLE_OPTIONS = {
@@ -90,23 +90,23 @@ export default Component.extend({
hasData: notEmpty("model.data"),
- @computed("dataSourceName", "model.type")
+ @discourseComputed("dataSourceName", "model.type")
dasherizedDataSourceName(dataSourceName, type) {
return (dataSourceName || type || "undefined").replace(/_/g, "-");
},
- @computed("dataSourceName", "model.type")
+ @discourseComputed("dataSourceName", "model.type")
dataSource(dataSourceName, type) {
dataSourceName = dataSourceName || type;
return `/admin/reports/${dataSourceName}`;
},
- @computed("displayedModes.length")
+ @discourseComputed("displayedModes.length")
showModes(displayedModesLength) {
return displayedModesLength > 1;
},
- @computed("currentMode", "model.modes", "forcedModes")
+ @discourseComputed("currentMode", "model.modes", "forcedModes")
displayedModes(currentMode, reportModes, forcedModes) {
const modes = forcedModes ? forcedModes.split(",") : reportModes;
@@ -122,12 +122,12 @@ export default Component.extend({
});
},
- @computed("currentMode")
+ @discourseComputed("currentMode")
modeComponent(currentMode) {
return `admin-report-${currentMode}`;
},
- @computed("startDate")
+ @discourseComputed("startDate")
normalizedStartDate(startDate) {
return startDate && typeof startDate.isValid === "function"
? moment
@@ -139,7 +139,7 @@ export default Component.extend({
.format("YYYYMMDD");
},
- @computed("endDate")
+ @discourseComputed("endDate")
normalizedEndDate(endDate) {
return endDate && typeof endDate.isValid === "function"
? moment
@@ -151,7 +151,7 @@ export default Component.extend({
.format("YYYYMMDD");
},
- @computed(
+ @discourseComputed(
"dataSourceName",
"normalizedStartDate",
"normalizedEndDate",
diff --git a/app/assets/javascripts/admin/components/admin-theme-editor.js.es6 b/app/assets/javascripts/admin/components/admin-theme-editor.js.es6
index 1dec9fce37..381ac0ca47 100644
--- a/app/assets/javascripts/admin/components/admin-theme-editor.js.es6
+++ b/app/assets/javascripts/admin/components/admin-theme-editor.js.es6
@@ -1,10 +1,10 @@
import { next } from "@ember/runloop";
import Component from "@ember/component";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import { fmt } from "discourse/lib/computed";
export default Component.extend({
- @computed("theme.targets", "onlyOverridden", "showAdvanced")
+ @discourseComputed("theme.targets", "onlyOverridden", "showAdvanced")
visibleTargets(targets, onlyOverridden, showAdvanced) {
return targets.filter(target => {
if (target.advanced && !showAdvanced) {
@@ -17,7 +17,7 @@ export default Component.extend({
});
},
- @computed("currentTargetName", "onlyOverridden", "theme.fields")
+ @discourseComputed("currentTargetName", "onlyOverridden", "theme.fields")
visibleFields(targetName, onlyOverridden, fields) {
fields = fields[targetName];
if (onlyOverridden) {
@@ -26,14 +26,14 @@ export default Component.extend({
return fields;
},
- @computed("currentTargetName", "fieldName")
+ @discourseComputed("currentTargetName", "fieldName")
activeSectionMode(targetName, fieldName) {
if (["settings", "translations"].includes(targetName)) return "yaml";
if (["extra_scss"].includes(targetName)) return "scss";
return fieldName && fieldName.indexOf("scss") > -1 ? "scss" : "html";
},
- @computed("fieldName", "currentTargetName", "theme")
+ @discourseComputed("fieldName", "currentTargetName", "theme")
activeSection: {
get(fieldName, target, model) {
return model.getField(target, fieldName);
@@ -46,17 +46,21 @@ export default Component.extend({
editorId: fmt("fieldName", "currentTargetName", "%@|%@"),
- @computed("maximized")
+ @discourseComputed("maximized")
maximizeIcon(maximized) {
return maximized ? "discourse-compress" : "discourse-expand";
},
- @computed("currentTargetName", "theme.targets")
+ @discourseComputed("currentTargetName", "theme.targets")
showAddField(currentTargetName, targets) {
return targets.find(t => t.name === currentTargetName).customNames;
},
- @computed("currentTargetName", "fieldName", "theme.theme_fields.@each.error")
+ @discourseComputed(
+ "currentTargetName",
+ "fieldName",
+ "theme.theme_fields.@each.error"
+ )
error(target, fieldName) {
return this.theme.getError(target, fieldName);
},
diff --git a/app/assets/javascripts/admin/components/admin-user-field-item.js.es6 b/app/assets/javascripts/admin/components/admin-user-field-item.js.es6
index 23bfac19b4..a392196f8a 100644
--- a/app/assets/javascripts/admin/components/admin-user-field-item.js.es6
+++ b/app/assets/javascripts/admin/components/admin-user-field-item.js.es6
@@ -8,10 +8,10 @@ import { popupAjaxError } from "discourse/lib/ajax-error";
import { propertyEqual } from "discourse/lib/computed";
import { i18n } from "discourse/lib/computed";
import {
- default as computed,
+ default as discourseComputed,
observes,
on
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
export default Component.extend(bufferedProperty("userField"), {
editing: empty("userField.id"),
@@ -22,7 +22,7 @@ export default Component.extend(bufferedProperty("userField"), {
userFieldsDescription: i18n("admin.user_fields.description"),
- @computed("buffered.field_type")
+ @discourseComputed("buffered.field_type")
bufferedFieldType(fieldType) {
return UserField.fieldTypeById(fieldType);
},
@@ -39,12 +39,12 @@ export default Component.extend(bufferedProperty("userField"), {
$(".user-field-name").select();
},
- @computed("userField.field_type")
+ @discourseComputed("userField.field_type")
fieldName(fieldType) {
return UserField.fieldTypeById(fieldType).get("name");
},
- @computed(
+ @discourseComputed(
"userField.editable",
"userField.required",
"userField.show_on_profile",
diff --git a/app/assets/javascripts/admin/components/admin-web-hook-event-chooser.js.es6 b/app/assets/javascripts/admin/components/admin-web-hook-event-chooser.js.es6
index 1c7f6f05a0..a38695c735 100644
--- a/app/assets/javascripts/admin/components/admin-web-hook-event-chooser.js.es6
+++ b/app/assets/javascripts/admin/components/admin-web-hook-event-chooser.js.es6
@@ -1,27 +1,27 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { alias } from "@ember/object/computed";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
classNames: ["hook-event"],
typeName: alias("type.name"),
- @computed("typeName")
+ @discourseComputed("typeName")
name(typeName) {
return I18n.t(`admin.web_hooks.${typeName}_event.name`);
},
- @computed("typeName")
+ @discourseComputed("typeName")
details(typeName) {
return I18n.t(`admin.web_hooks.${typeName}_event.details`);
},
- @computed("model.[]", "typeName")
+ @discourseComputed("model.[]", "typeName")
eventTypeExists(eventTypes, typeName) {
return eventTypes.any(event => event.name === typeName);
},
- @computed("eventTypeExists")
+ @discourseComputed("eventTypeExists")
enabled: {
get(eventTypeExists) {
return eventTypeExists;
diff --git a/app/assets/javascripts/admin/components/admin-web-hook-event.js.es6 b/app/assets/javascripts/admin/components/admin-web-hook-event.js.es6
index 693e6502ff..365e22aa67 100644
--- a/app/assets/javascripts/admin/components/admin-web-hook-event.js.es6
+++ b/app/assets/javascripts/admin/components/admin-web-hook-event.js.es6
@@ -1,5 +1,5 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import { ajax } from "discourse/lib/ajax";
import { popupAjaxError } from "discourse/lib/ajax-error";
import { ensureJSON, plainJSON, prettyJSON } from "discourse/lib/formatter";
@@ -10,7 +10,7 @@ export default Component.extend({
expandDetailsRequestKey: "request",
expandDetailsResponseKey: "response",
- @computed("model.status")
+ @discourseComputed("model.status")
statusColorClasses(status) {
if (!status) return "";
@@ -21,25 +21,25 @@ export default Component.extend({
}
},
- @computed("model.created_at")
+ @discourseComputed("model.created_at")
createdAt(createdAt) {
return moment(createdAt).format("YYYY-MM-DD HH:mm:ss");
},
- @computed("model.duration")
+ @discourseComputed("model.duration")
completion(duration) {
const seconds = Math.floor(duration / 10.0) / 100.0;
return I18n.t("admin.web_hooks.events.completed_in", { count: seconds });
},
- @computed("expandDetails")
+ @discourseComputed("expandDetails")
expandRequestIcon(expandDetails) {
return expandDetails === this.expandDetailsRequestKey
? "ellipsis-h"
: "ellipsis-v";
},
- @computed("expandDetails")
+ @discourseComputed("expandDetails")
expandResponseIcon(expandDetails) {
return expandDetails === this.expandDetailsResponseKey
? "ellipsis-h"
diff --git a/app/assets/javascripts/admin/components/admin-web-hook-status.js.es6 b/app/assets/javascripts/admin/components/admin-web-hook-status.js.es6
index 0d8e80cc81..b023a330c7 100644
--- a/app/assets/javascripts/admin/components/admin-web-hook-status.js.es6
+++ b/app/assets/javascripts/admin/components/admin-web-hook-status.js.es6
@@ -1,5 +1,5 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import { iconHTML } from "discourse-common/lib/icon-library";
import { bufferedRender } from "discourse-common/lib/buffered-render";
@@ -8,17 +8,17 @@ export default Component.extend(
classes: ["text-muted", "text-danger", "text-successful", "text-muted"],
icons: ["far-circle", "times-circle", "circle", "circle"],
- @computed("deliveryStatuses", "model.last_delivery_status")
+ @discourseComputed("deliveryStatuses", "model.last_delivery_status")
status(deliveryStatuses, lastDeliveryStatus) {
return deliveryStatuses.find(s => s.id === lastDeliveryStatus);
},
- @computed("status.id", "icons")
+ @discourseComputed("status.id", "icons")
icon(statusId, icons) {
return icons[statusId - 1];
},
- @computed("status.id", "classes")
+ @discourseComputed("status.id", "classes")
class(statusId, classes) {
return classes[statusId - 1];
},
diff --git a/app/assets/javascripts/admin/components/email-styles-editor.js.es6 b/app/assets/javascripts/admin/components/email-styles-editor.js.es6
index e465c04cba..ef5cdb077e 100644
--- a/app/assets/javascripts/admin/components/email-styles-editor.js.es6
+++ b/app/assets/javascripts/admin/components/email-styles-editor.js.es6
@@ -1,16 +1,16 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { reads } from "@ember/object/computed";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
editorId: reads("fieldName"),
- @computed("fieldName")
+ @discourseComputed("fieldName")
currentEditorMode(fieldName) {
return fieldName === "css" ? "scss" : fieldName;
},
- @computed("fieldName", "styles.html", "styles.css")
+ @discourseComputed("fieldName", "styles.html", "styles.css")
resetDisabled(fieldName) {
return (
this.get(`styles.${fieldName}`) ===
@@ -18,7 +18,7 @@ export default Component.extend({
);
},
- @computed("styles", "fieldName")
+ @discourseComputed("styles", "fieldName")
editorContents: {
get(styles, fieldName) {
return styles[fieldName];
diff --git a/app/assets/javascripts/admin/components/embeddable-host.js.es6 b/app/assets/javascripts/admin/components/embeddable-host.js.es6
index 57829b45fb..054acc744c 100644
--- a/app/assets/javascripts/admin/components/embeddable-host.js.es6
+++ b/app/assets/javascripts/admin/components/embeddable-host.js.es6
@@ -1,10 +1,10 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { isEmpty } from "@ember/utils";
import { or } from "@ember/object/computed";
import { schedule } from "@ember/runloop";
import Component from "@ember/component";
import { bufferedProperty } from "discourse/mixins/buffered-content";
-import computed from "ember-addons/ember-computed-decorators";
-import { on, observes } from "ember-addons/ember-computed-decorators";
+import { on, observes } from "discourse-common/utils/decorators";
import { popupAjaxError } from "discourse/lib/ajax-error";
export default Component.extend(bufferedProperty("host"), {
@@ -22,7 +22,7 @@ export default Component.extend(bufferedProperty("host"), {
});
},
- @computed("buffered.host", "host.isSaving")
+ @discourseComputed("buffered.host", "host.isSaving")
cantSave(host, isSaving) {
return isSaving || isEmpty(host);
},
diff --git a/app/assets/javascripts/admin/components/embedding-setting.js.es6 b/app/assets/javascripts/admin/components/embedding-setting.js.es6
index da7f9abb7f..517e37f4f9 100644
--- a/app/assets/javascripts/admin/components/embedding-setting.js.es6
+++ b/app/assets/javascripts/admin/components/embedding-setting.js.es6
@@ -1,25 +1,25 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
classNames: ["embed-setting"],
- @computed("field")
+ @discourseComputed("field")
inputId(field) {
return field.dasherize();
},
- @computed("field")
+ @discourseComputed("field")
translationKey(field) {
return `admin.embedding.${field}`;
},
- @computed("type")
+ @discourseComputed("type")
isCheckbox(type) {
return type === "checkbox";
},
- @computed("value")
+ @discourseComputed("value")
checked: {
get(value) {
return !!value;
diff --git a/app/assets/javascripts/admin/components/highlighted-code.js.es6 b/app/assets/javascripts/admin/components/highlighted-code.js.es6
index d182d7e2a1..9159bb574a 100644
--- a/app/assets/javascripts/admin/components/highlighted-code.js.es6
+++ b/app/assets/javascripts/admin/components/highlighted-code.js.es6
@@ -1,5 +1,5 @@
import Component from "@ember/component";
-import { on, observes } from "ember-addons/ember-computed-decorators";
+import { on, observes } from "discourse-common/utils/decorators";
import highlightSyntax from "discourse/lib/highlight-syntax";
export default Component.extend({
diff --git a/app/assets/javascripts/admin/components/inline-edit-checkbox.js.es6 b/app/assets/javascripts/admin/components/inline-edit-checkbox.js.es6
index e88c2bc3b7..ff3cb98ffc 100644
--- a/app/assets/javascripts/admin/components/inline-edit-checkbox.js.es6
+++ b/app/assets/javascripts/admin/components/inline-edit-checkbox.js.es6
@@ -1,8 +1,8 @@
import Component from "@ember/component";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
export default Component.extend({
classNames: ["inline-edit"],
@@ -21,12 +21,12 @@ export default Component.extend({
this.set("checkedInternal", this.checked);
},
- @computed("labelKey")
+ @discourseComputed("labelKey")
label(key) {
return I18n.t(key);
},
- @computed("checked", "checkedInternal")
+ @discourseComputed("checked", "checkedInternal")
changed(checked, checkedInternal) {
return !!checked !== !!checkedInternal;
},
diff --git a/app/assets/javascripts/admin/components/ip-lookup.js.es6 b/app/assets/javascripts/admin/components/ip-lookup.js.es6
index 8438a4ee5c..06421e2e90 100644
--- a/app/assets/javascripts/admin/components/ip-lookup.js.es6
+++ b/app/assets/javascripts/admin/components/ip-lookup.js.es6
@@ -1,7 +1,7 @@
import EmberObject from "@ember/object";
import { later } from "@ember/runloop";
import Component from "@ember/component";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import { ajax } from "discourse/lib/ajax";
import AdminUser from "admin/models/admin-user";
import copyText from "discourse/lib/copy-text";
@@ -9,7 +9,7 @@ import copyText from "discourse/lib/copy-text";
export default Component.extend({
classNames: ["ip-lookup"],
- @computed("other_accounts.length", "totalOthersWithSameIP")
+ @discourseComputed("other_accounts.length", "totalOthersWithSameIP")
otherAccountsToDelete(otherAccountsLength, totalOthersWithSameIP) {
// can only delete up to 50 accounts at a time
const total = Math.min(50, totalOthersWithSameIP || 0);
diff --git a/app/assets/javascripts/admin/components/penalty-post-action.js.es6 b/app/assets/javascripts/admin/components/penalty-post-action.js.es6
index 8af1f83b16..6a703105fb 100644
--- a/app/assets/javascripts/admin/components/penalty-post-action.js.es6
+++ b/app/assets/javascripts/admin/components/penalty-post-action.js.es6
@@ -1,7 +1,7 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { equal } from "@ember/object/computed";
import { scheduleOnce } from "@ember/runloop";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
const ACTIONS = ["delete", "delete_replies", "edit", "none"];
@@ -10,7 +10,7 @@ export default Component.extend({
postAction: null,
postEdit: null,
- @computed
+ @discourseComputed
penaltyActions() {
return ACTIONS.map(id => {
return { id, name: I18n.t(`admin.user.penalty_post_${id}`) };
diff --git a/app/assets/javascripts/admin/components/permalink-form.js.es6 b/app/assets/javascripts/admin/components/permalink-form.js.es6
index b1f82ea295..5a90dd9913 100644
--- a/app/assets/javascripts/admin/components/permalink-form.js.es6
+++ b/app/assets/javascripts/admin/components/permalink-form.js.es6
@@ -1,6 +1,6 @@
import { schedule } from "@ember/runloop";
import Component from "@ember/component";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import { fmt } from "discourse/lib/computed";
import Permalink from "admin/models/permalink";
@@ -10,7 +10,7 @@ export default Component.extend({
permalinkType: "topic_id",
permalinkTypePlaceholder: fmt("permalinkType", "admin.permalink.%@"),
- @computed
+ @discourseComputed
permalinkTypes() {
return [
{ id: "topic_id", name: I18n.t("admin.permalink.topic_id") },
diff --git a/app/assets/javascripts/admin/components/report-filters/category.js.es6 b/app/assets/javascripts/admin/components/report-filters/category.js.es6
index 7efdd4a465..60fb61be9b 100644
--- a/app/assets/javascripts/admin/components/report-filters/category.js.es6
+++ b/app/assets/javascripts/admin/components/report-filters/category.js.es6
@@ -1,5 +1,5 @@
import Category from "discourse/models/category";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import FilterComponent from "admin/components/report-filters/filter";
export default FilterComponent.extend({
@@ -7,7 +7,7 @@ export default FilterComponent.extend({
layoutName: "admin/templates/components/report-filters/category",
- @computed("filter.default")
+ @discourseComputed("filter.default")
category(categoryId) {
return Category.findById(categoryId);
},
diff --git a/app/assets/javascripts/admin/components/report-filters/group.js.es6 b/app/assets/javascripts/admin/components/report-filters/group.js.es6
index 54523f9446..0821cb084e 100644
--- a/app/assets/javascripts/admin/components/report-filters/group.js.es6
+++ b/app/assets/javascripts/admin/components/report-filters/group.js.es6
@@ -1,19 +1,19 @@
import FilterComponent from "admin/components/report-filters/filter";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
export default FilterComponent.extend({
classNames: ["group-filter"],
layoutName: "admin/templates/components/report-filters/group",
- @computed()
+ @discourseComputed()
groupOptions() {
return (this.site.groups || []).map(group => {
return { name: group["name"], value: group["id"] };
});
},
- @computed("filter.default")
+ @discourseComputed("filter.default")
groupId(filterDefault) {
return filterDefault ? parseInt(filterDefault, 10) : null;
}
diff --git a/app/assets/javascripts/admin/components/resumable-upload.js.es6 b/app/assets/javascripts/admin/components/resumable-upload.js.es6
index d63a1a651d..925bdf0de9 100644
--- a/app/assets/javascripts/admin/components/resumable-upload.js.es6
+++ b/app/assets/javascripts/admin/components/resumable-upload.js.es6
@@ -4,9 +4,9 @@ import Component from "@ember/component";
import { iconHTML } from "discourse-common/lib/icon-library";
import { bufferedRender } from "discourse-common/lib/buffered-render";
import {
- default as computed,
+ default as discourseComputed,
on
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
/*global Resumable:true */
@@ -91,12 +91,12 @@ export default Component.extend(
}
},
- @computed("title", "text")
+ @discourseComputed("title", "text")
translatedTitle(title, text) {
return title ? I18n.t(title) : text;
},
- @computed("isUploading", "progress")
+ @discourseComputed("isUploading", "progress")
text(isUploading, progress) {
if (isUploading) {
return progress + " %";
diff --git a/app/assets/javascripts/admin/components/save-controls.js.es6 b/app/assets/javascripts/admin/components/save-controls.js.es6
index b039b0158c..9da4e49fe2 100644
--- a/app/assets/javascripts/admin/components/save-controls.js.es6
+++ b/app/assets/javascripts/admin/components/save-controls.js.es6
@@ -1,13 +1,13 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { or } from "@ember/object/computed";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
classNames: ["controls"],
buttonDisabled: or("model.isSaving", "saveDisabled"),
- @computed("model.isSaving")
+ @discourseComputed("model.isSaving")
savingText(saving) {
return saving ? "saving" : "save";
}
diff --git a/app/assets/javascripts/admin/components/screened-ip-address-form.js.es6 b/app/assets/javascripts/admin/components/screened-ip-address-form.js.es6
index 8b6db57764..48b92641b4 100644
--- a/app/assets/javascripts/admin/components/screened-ip-address-form.js.es6
+++ b/app/assets/javascripts/admin/components/screened-ip-address-form.js.es6
@@ -1,3 +1,4 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { schedule } from "@ember/runloop";
import Component from "@ember/component";
/**
@@ -12,20 +13,19 @@ import Component from "@ember/component";
**/
import ScreenedIpAddress from "admin/models/screened-ip-address";
-import computed from "ember-addons/ember-computed-decorators";
-import { on } from "ember-addons/ember-computed-decorators";
+import { on } from "discourse-common/utils/decorators";
export default Component.extend({
classNames: ["screened-ip-address-form"],
formSubmitted: false,
actionName: "block",
- @computed
+ @discourseComputed
adminWhitelistEnabled() {
return Discourse.SiteSettings.use_admin_ip_whitelist;
},
- @computed("adminWhitelistEnabled")
+ @discourseComputed("adminWhitelistEnabled")
actionNames(adminWhitelistEnabled) {
if (adminWhitelistEnabled) {
return [
diff --git a/app/assets/javascripts/admin/components/secret-value-list.js.es6 b/app/assets/javascripts/admin/components/secret-value-list.js.es6
index 4327f62f80..ea4ecf792c 100644
--- a/app/assets/javascripts/admin/components/secret-value-list.js.es6
+++ b/app/assets/javascripts/admin/components/secret-value-list.js.es6
@@ -1,6 +1,6 @@
import { isEmpty } from "@ember/utils";
import Component from "@ember/component";
-import { on } from "ember-addons/ember-computed-decorators";
+import { on } from "discourse-common/utils/decorators";
import { set } from "@ember/object";
export default Component.extend({
diff --git a/app/assets/javascripts/admin/components/site-settings/bool.js.es6 b/app/assets/javascripts/admin/components/site-settings/bool.js.es6
index 2b2fdaca8e..88f4387601 100644
--- a/app/assets/javascripts/admin/components/site-settings/bool.js.es6
+++ b/app/assets/javascripts/admin/components/site-settings/bool.js.es6
@@ -1,9 +1,9 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { isEmpty } from "@ember/utils";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
- @computed("value")
+ @discourseComputed("value")
enabled: {
get(value) {
if (isEmpty(value)) {
diff --git a/app/assets/javascripts/admin/components/site-settings/category-list.js.es6 b/app/assets/javascripts/admin/components/site-settings/category-list.js.es6
index d4476ddf13..5d4b68b19b 100644
--- a/app/assets/javascripts/admin/components/site-settings/category-list.js.es6
+++ b/app/assets/javascripts/admin/components/site-settings/category-list.js.es6
@@ -1,8 +1,8 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
- @computed("value")
+ @discourseComputed("value")
selectedCategories: {
get(value) {
return Discourse.Category.findByIds(value.split("|"));
diff --git a/app/assets/javascripts/admin/components/site-settings/group-list.js.es6 b/app/assets/javascripts/admin/components/site-settings/group-list.js.es6
index 21af030269..97736c36ca 100644
--- a/app/assets/javascripts/admin/components/site-settings/group-list.js.es6
+++ b/app/assets/javascripts/admin/components/site-settings/group-list.js.es6
@@ -1,8 +1,8 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
- @computed()
+ @discourseComputed()
groupChoices() {
return this.site.get("groups").map(g => {
return { name: g.name, id: g.id.toString() };
diff --git a/app/assets/javascripts/admin/components/site-settings/tag-list.js.es6 b/app/assets/javascripts/admin/components/site-settings/tag-list.js.es6
index 417ad622cb..c8a8e0a06f 100644
--- a/app/assets/javascripts/admin/components/site-settings/tag-list.js.es6
+++ b/app/assets/javascripts/admin/components/site-settings/tag-list.js.es6
@@ -1,8 +1,8 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
- @computed("value")
+ @discourseComputed("value")
selectedTags: {
get(value) {
return value.split("|");
diff --git a/app/assets/javascripts/admin/components/site-text-summary.js.es6 b/app/assets/javascripts/admin/components/site-text-summary.js.es6
index 4467a092d1..11c6bc45eb 100644
--- a/app/assets/javascripts/admin/components/site-text-summary.js.es6
+++ b/app/assets/javascripts/admin/components/site-text-summary.js.es6
@@ -1,5 +1,5 @@
import Component from "@ember/component";
-import { on } from "ember-addons/ember-computed-decorators";
+import { on } from "discourse-common/utils/decorators";
export default Component.extend({
classNames: ["site-text"],
diff --git a/app/assets/javascripts/admin/components/themes-list-item.js.es6 b/app/assets/javascripts/admin/components/themes-list-item.js.es6
index 2c4a5265b8..cfc1b63a36 100644
--- a/app/assets/javascripts/admin/components/themes-list-item.js.es6
+++ b/app/assets/javascripts/admin/components/themes-list-item.js.es6
@@ -2,9 +2,9 @@ import { gt, and } from "@ember/object/computed";
import { schedule } from "@ember/runloop";
import Component from "@ember/component";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import { iconHTML } from "discourse-common/lib/icon-library";
import { escape } from "pretty-text/sanitizer";
import ENV from "discourse-common/config/environment";
@@ -55,7 +55,7 @@ export default Component.extend({
}
},
- @computed(
+ @discourseComputed(
"theme.component",
"theme.childThemes.@each.name",
"theme.childThemes.length",
@@ -76,12 +76,12 @@ export default Component.extend({
});
},
- @computed("children")
+ @discourseComputed("children")
childrenString(children) {
return children.join(", ");
},
- @computed(
+ @discourseComputed(
"theme.childThemes.length",
"theme.component",
"childrenExpanded",
diff --git a/app/assets/javascripts/admin/components/themes-list.js.es6 b/app/assets/javascripts/admin/components/themes-list.js.es6
index 1a420eeba8..ae883a115d 100644
--- a/app/assets/javascripts/admin/components/themes-list.js.es6
+++ b/app/assets/javascripts/admin/components/themes-list.js.es6
@@ -1,7 +1,7 @@
import { gt, equal } from "@ember/object/computed";
import Component from "@ember/component";
import { THEMES, COMPONENTS } from "admin/models/theme";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
import { getOwner } from "@ember/application";
export default Component.extend({
@@ -17,7 +17,7 @@ export default Component.extend({
themesTabActive: equal("currentTab", THEMES),
componentsTabActive: equal("currentTab", COMPONENTS),
- @computed("themes", "components", "currentTab")
+ @discourseComputed("themes", "components", "currentTab")
themesList(themes, components) {
if (this.themesTabActive) {
return themes;
@@ -26,7 +26,7 @@ export default Component.extend({
}
},
- @computed(
+ @discourseComputed(
"themesList",
"currentTab",
"themesList.@each.user_selectable",
@@ -41,7 +41,7 @@ export default Component.extend({
);
},
- @computed(
+ @discourseComputed(
"themesList",
"currentTab",
"themesList.@each.user_selectable",
diff --git a/app/assets/javascripts/admin/components/value-list.js.es6 b/app/assets/javascripts/admin/components/value-list.js.es6
index 31ef93932e..6582f20e7f 100644
--- a/app/assets/javascripts/admin/components/value-list.js.es6
+++ b/app/assets/javascripts/admin/components/value-list.js.es6
@@ -1,8 +1,8 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { makeArray } from "discourse-common/lib/helpers";
import { empty, alias } from "@ember/object/computed";
import Component from "@ember/component";
-import { on } from "ember-addons/ember-computed-decorators";
-import computed from "ember-addons/ember-computed-decorators";
+import { on } from "discourse-common/utils/decorators";
export default Component.extend({
classNameBindings: [":value-list"],
@@ -30,7 +30,7 @@ export default Component.extend({
);
},
- @computed("choices.[]", "collection.[]")
+ @discourseComputed("choices.[]", "collection.[]")
filteredChoices(choices, collection) {
return makeArray(choices).filter(i => collection.indexOf(i) < 0);
},
diff --git a/app/assets/javascripts/admin/components/watched-word-form.js.es6 b/app/assets/javascripts/admin/components/watched-word-form.js.es6
index 629c5a2b6a..2359320ad6 100644
--- a/app/assets/javascripts/admin/components/watched-word-form.js.es6
+++ b/app/assets/javascripts/admin/components/watched-word-form.js.es6
@@ -3,10 +3,10 @@ import { schedule } from "@ember/runloop";
import Component from "@ember/component";
import WatchedWord from "admin/models/watched-word";
import {
- default as computed,
+ default as discourseComputed,
on,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
export default Component.extend({
classNames: ["watched-word-form"],
@@ -14,7 +14,7 @@ export default Component.extend({
actionKey: null,
showMessage: false,
- @computed("regularExpressions")
+ @discourseComputed("regularExpressions")
placeholderKey(regularExpressions) {
return (
"admin.watched_words.form.placeholder" +
@@ -29,7 +29,7 @@ export default Component.extend({
}
},
- @computed("word")
+ @discourseComputed("word")
isUniqueWord(word) {
const words = this.filteredContent || [];
const filtered = words.filter(content => content.action === this.actionKey);
diff --git a/app/assets/javascripts/admin/components/watched-word-uploader.js.es6 b/app/assets/javascripts/admin/components/watched-word-uploader.js.es6
index 417f3d5bbf..05dc41c207 100644
--- a/app/assets/javascripts/admin/components/watched-word-uploader.js.es6
+++ b/app/assets/javascripts/admin/components/watched-word-uploader.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { alias } from "@ember/object/computed";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import UploadMixin from "discourse/mixins/upload";
export default Component.extend(UploadMixin, {
@@ -13,7 +13,7 @@ export default Component.extend(UploadMixin, {
return { skipValidation: true };
},
- @computed("actionKey")
+ @discourseComputed("actionKey")
data(actionKey) {
return { action_key: actionKey };
},
diff --git a/app/assets/javascripts/admin/controllers/admin-api-keys-new.js.es6 b/app/assets/javascripts/admin/controllers/admin-api-keys-new.js.es6
index f4d56c0a05..c04e6abec9 100644
--- a/app/assets/javascripts/admin/controllers/admin-api-keys-new.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-api-keys-new.js.es6
@@ -1,4 +1,4 @@
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import { popupAjaxError } from "discourse/lib/ajax-error";
export default Ember.Controller.extend({
@@ -7,12 +7,12 @@ export default Ember.Controller.extend({
{ id: "single", name: I18n.t("admin.api.single_user") }
],
- @computed("userMode")
+ @discourseComputed("userMode")
showUserSelector(mode) {
return mode === "single";
},
- @computed("model.description", "model.username", "userMode")
+ @discourseComputed("model.description", "model.username", "userMode")
saveDisabled(description, username, userMode) {
if (Ember.isBlank(description)) return true;
if (userMode === "single" && Ember.isBlank(username)) return true;
diff --git a/app/assets/javascripts/admin/controllers/admin-backups-index.js.es6 b/app/assets/javascripts/admin/controllers/admin-backups-index.js.es6
index 6b69eaea72..e4e7c24d43 100644
--- a/app/assets/javascripts/admin/controllers/admin-backups-index.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-backups-index.js.es6
@@ -2,7 +2,7 @@ import { alias, equal } from "@ember/object/computed";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
import { ajax } from "discourse/lib/ajax";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import { setting, i18n } from "discourse/lib/computed";
export default Controller.extend({
@@ -12,7 +12,7 @@ export default Controller.extend({
backupLocation: setting("backup_location"),
localBackupStorage: equal("backupLocation", "local"),
- @computed("status.allowRestore", "status.isOperationRunning")
+ @discourseComputed("status.allowRestore", "status.isOperationRunning")
restoreTitle(allowRestore, isOperationRunning) {
if (!allowRestore) {
return "admin.backups.operations.restore.is_disabled";
diff --git a/app/assets/javascripts/admin/controllers/admin-badges-show.js.es6 b/app/assets/javascripts/admin/controllers/admin-badges-show.js.es6
index 733f4589fe..2511dcead1 100644
--- a/app/assets/javascripts/admin/controllers/admin-badges-show.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-badges-show.js.es6
@@ -1,10 +1,10 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { alias } from "@ember/object/computed";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
import { popupAjaxError } from "discourse/lib/ajax-error";
import { bufferedProperty } from "discourse/mixins/buffered-content";
import { propertyNotEqual } from "discourse/lib/computed";
-import computed from "ember-addons/ember-computed-decorators";
export default Controller.extend(bufferedProperty("model"), {
adminBadges: inject(),
@@ -19,7 +19,7 @@ export default Controller.extend(bufferedProperty("model"), {
readOnly: alias("buffered.system"),
showDisplayName: propertyNotEqual("name", "displayName"),
- @computed("model.query", "buffered.query")
+ @discourseComputed("model.query", "buffered.query")
hasQuery(modelQuery, bufferedQuery) {
if (bufferedQuery) {
return bufferedQuery.trim().length > 0;
diff --git a/app/assets/javascripts/admin/controllers/admin-customize-colors-show.js.es6 b/app/assets/javascripts/admin/controllers/admin-customize-colors-show.js.es6
index ce99c2cfea..9cdca3f098 100644
--- a/app/assets/javascripts/admin/controllers/admin-customize-colors-show.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-customize-colors-show.js.es6
@@ -1,9 +1,9 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { later } from "@ember/runloop";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
export default Controller.extend({
- @computed("model.colors", "onlyOverridden")
+ @discourseComputed("model.colors", "onlyOverridden")
colors(allColors, onlyOverridden) {
if (onlyOverridden) {
return allColors.filter(color => color.get("overridden"));
diff --git a/app/assets/javascripts/admin/controllers/admin-customize-colors.js.es6 b/app/assets/javascripts/admin/controllers/admin-customize-colors.js.es6
index 21c628be24..4fc2cf34f0 100644
--- a/app/assets/javascripts/admin/controllers/admin-customize-colors.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-customize-colors.js.es6
@@ -1,20 +1,20 @@
import EmberObject from "@ember/object";
import Controller from "@ember/controller";
import showModal from "discourse/lib/show-modal";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
export default Controller.extend({
- @computed("model.@each.id")
+ @discourseComputed("model.@each.id")
baseColorScheme() {
return this.model.findBy("is_base", true);
},
- @computed("model.@each.id")
+ @discourseComputed("model.@each.id")
baseColorSchemes() {
return this.model.filterBy("is_base", true);
},
- @computed("baseColorScheme")
+ @discourseComputed("baseColorScheme")
baseColors(baseColorScheme) {
const baseColorsHash = EmberObject.create({});
baseColorScheme.get("colors").forEach(color => {
diff --git a/app/assets/javascripts/admin/controllers/admin-customize-email-style-edit.js.es6 b/app/assets/javascripts/admin/controllers/admin-customize-email-style-edit.js.es6
index f48f46eff0..d534792b00 100644
--- a/app/assets/javascripts/admin/controllers/admin-customize-email-style-edit.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-customize-email-style-edit.js.es6
@@ -1,13 +1,13 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
export default Controller.extend({
- @computed("model.isSaving")
+ @discourseComputed("model.isSaving")
saveButtonText(isSaving) {
return isSaving ? I18n.t("saving") : I18n.t("admin.customize.save");
},
- @computed("model.changed", "model.isSaving")
+ @discourseComputed("model.changed", "model.isSaving")
saveDisabled(changed, isSaving) {
return !changed || isSaving;
},
diff --git a/app/assets/javascripts/admin/controllers/admin-customize-email-templates-edit.js.es6 b/app/assets/javascripts/admin/controllers/admin-customize-email-templates-edit.js.es6
index 5ec405594a..3617edca75 100644
--- a/app/assets/javascripts/admin/controllers/admin-customize-email-templates-edit.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-customize-email-templates-edit.js.es6
@@ -1,19 +1,19 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Controller from "@ember/controller";
import { popupAjaxError } from "discourse/lib/ajax-error";
import { bufferedProperty } from "discourse/mixins/buffered-content";
-import computed from "ember-addons/ember-computed-decorators";
export default Controller.extend(bufferedProperty("emailTemplate"), {
saved: false,
- @computed("buffered.body", "buffered.subject")
+ @discourseComputed("buffered.body", "buffered.subject")
saveDisabled(body, subject) {
return (
this.emailTemplate.body === body && this.emailTemplate.subject === subject
);
},
- @computed("buffered")
+ @discourseComputed("buffered")
hasMultipleSubjects(buffered) {
if (buffered.getProperties("subject")["subject"]) {
return false;
diff --git a/app/assets/javascripts/admin/controllers/admin-customize-themes-edit.js.es6 b/app/assets/javascripts/admin/controllers/admin-customize-themes-edit.js.es6
index a5a286bf80..75d7a486f2 100644
--- a/app/assets/javascripts/admin/controllers/admin-customize-themes-edit.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-customize-themes-edit.js.es6
@@ -1,6 +1,6 @@
import Controller from "@ember/controller";
import { url } from "discourse/lib/computed";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
export default Controller.extend({
section: null,
@@ -16,7 +16,7 @@ export default Controller.extend({
this.set("currentTarget", target && target.id);
},
- @computed("currentTarget")
+ @discourseComputed("currentTarget")
currentTargetName(id) {
const target = this.get("model.targets").find(
t => t.id === parseInt(id, 10)
@@ -24,12 +24,12 @@ export default Controller.extend({
return target && target.name;
},
- @computed("model.isSaving")
+ @discourseComputed("model.isSaving")
saveButtonText(isSaving) {
return isSaving ? I18n.t("saving") : I18n.t("admin.customize.save");
},
- @computed("model.changed", "model.isSaving")
+ @discourseComputed("model.changed", "model.isSaving")
saveDisabled(changed, isSaving) {
return !changed || isSaving;
},
diff --git a/app/assets/javascripts/admin/controllers/admin-customize-themes-show.js.es6 b/app/assets/javascripts/admin/controllers/admin-customize-themes-show.js.es6
index d4622e21d8..aa4c32ce33 100644
--- a/app/assets/javascripts/admin/controllers/admin-customize-themes-show.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-customize-themes-show.js.es6
@@ -1,7 +1,7 @@
import { makeArray } from "discourse-common/lib/helpers";
import { empty, notEmpty, match } from "@ember/object/computed";
import Controller from "@ember/controller";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import { url } from "discourse/lib/computed";
import { popupAjaxError } from "discourse/lib/ajax-error";
import showModal from "discourse/lib/show-modal";
@@ -16,7 +16,7 @@ export default Controller.extend({
addButtonDisabled: empty("selectedChildThemeId"),
editRouteName: "adminCustomizeThemes.edit",
- @computed("model.editedFields")
+ @discourseComputed("model.editedFields")
editedFieldsFormatted() {
const descriptions = [];
["common", "desktop", "mobile"].forEach(target => {
@@ -34,13 +34,13 @@ export default Controller.extend({
return descriptions;
},
- @computed("colorSchemeId", "model.color_scheme_id")
+ @discourseComputed("colorSchemeId", "model.color_scheme_id")
colorSchemeChanged(colorSchemeId, existingId) {
colorSchemeId = colorSchemeId === null ? null : parseInt(colorSchemeId);
return colorSchemeId !== existingId;
},
- @computed("availableChildThemes", "model.childThemes.[]", "model")
+ @discourseComputed("availableChildThemes", "model.childThemes.[]", "model")
selectableChildThemes(available, childThemes) {
if (available) {
const themes = !childThemes
@@ -50,7 +50,7 @@ export default Controller.extend({
}
},
- @computed("allThemes", "model.component", "model")
+ @discourseComputed("allThemes", "model.component", "model")
availableChildThemes(allThemes) {
if (!this.get("model.component")) {
const themeId = this.get("model.id");
@@ -60,38 +60,38 @@ export default Controller.extend({
}
},
- @computed("model.component")
+ @discourseComputed("model.component")
convertKey(component) {
const type = component ? "component" : "theme";
return `admin.customize.theme.convert_${type}`;
},
- @computed("model.component")
+ @discourseComputed("model.component")
convertIcon(component) {
return component ? "cube" : "";
},
- @computed("model.component")
+ @discourseComputed("model.component")
convertTooltip(component) {
const type = component ? "component" : "theme";
return `admin.customize.theme.convert_${type}_tooltip`;
},
- @computed("model.settings")
+ @discourseComputed("model.settings")
settings(settings) {
return settings.map(setting => ThemeSettings.create(setting));
},
hasSettings: notEmpty("settings"),
- @computed("model.translations")
+ @discourseComputed("model.translations")
translations(translations) {
return translations.map(setting => ThemeSettings.create(setting));
},
hasTranslations: notEmpty("translations"),
- @computed("model.remoteError", "updatingRemote")
+ @discourseComputed("model.remoteError", "updatingRemote")
showRemoteError(errorMessage, updating) {
return errorMessage && !updating;
},
diff --git a/app/assets/javascripts/admin/controllers/admin-customize-themes.js.es6 b/app/assets/javascripts/admin/controllers/admin-customize-themes.js.es6
index 6727df97f3..f1d1f0d715 100644
--- a/app/assets/javascripts/admin/controllers/admin-customize-themes.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-customize-themes.js.es6
@@ -1,21 +1,21 @@
import Controller from "@ember/controller";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import { THEMES } from "admin/models/theme";
export default Controller.extend({
currentTab: THEMES,
- @computed("model", "model.@each.component")
+ @discourseComputed("model", "model.@each.component")
fullThemes(themes) {
return themes.filter(t => !t.get("component"));
},
- @computed("model", "model.@each.component")
+ @discourseComputed("model", "model.@each.component")
childThemes(themes) {
return themes.filter(t => t.get("component"));
},
- @computed("model", "model.@each.component")
+ @discourseComputed("model", "model.@each.component")
installedThemes(themes) {
return themes.map(t => t.name);
}
diff --git a/app/assets/javascripts/admin/controllers/admin-dashboard-general.js.es6 b/app/assets/javascripts/admin/controllers/admin-dashboard-general.js.es6
index 24884b0ba6..c91f09350d 100644
--- a/app/assets/javascripts/admin/controllers/admin-dashboard-general.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-dashboard-general.js.es6
@@ -1,8 +1,8 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { makeArray } from "discourse-common/lib/helpers";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
import { setting } from "discourse/lib/computed";
-import computed from "ember-addons/ember-computed-decorators";
import AdminDashboard from "admin/models/admin-dashboard";
import Report from "admin/models/report";
import PeriodComputationMixin from "admin/mixins/period-computation";
@@ -20,12 +20,12 @@ export default Controller.extend(PeriodComputationMixin, {
logSearchQueriesEnabled: setting("log_search_queries"),
basePath: Discourse.BaseUri,
- @computed("siteSettings.dashboard_general_tab_activity_metrics")
+ @discourseComputed("siteSettings.dashboard_general_tab_activity_metrics")
activityMetrics(metrics) {
return (metrics || "").split("|").filter(m => m);
},
- @computed
+ @discourseComputed
activityMetricsFilters() {
return {
startDate: this.lastMonth,
@@ -33,14 +33,14 @@ export default Controller.extend(PeriodComputationMixin, {
};
},
- @computed
+ @discourseComputed
topReferredTopicsOptions() {
return {
table: { total: false, limit: 8 }
};
},
- @computed
+ @discourseComputed
topReferredTopicsFilters() {
return {
startDate: moment()
@@ -50,7 +50,7 @@ export default Controller.extend(PeriodComputationMixin, {
};
},
- @computed
+ @discourseComputed
trendingSearchFilters() {
return {
startDate: moment()
@@ -60,14 +60,14 @@ export default Controller.extend(PeriodComputationMixin, {
};
},
- @computed
+ @discourseComputed
trendingSearchOptions() {
return {
table: { total: false, limit: 8 }
};
},
- @computed
+ @discourseComputed
trendingSearchDisabledLabel() {
return I18n.t("admin.dashboard.reports.trending_search.disabled", {
basePath: Discourse.BaseUri
@@ -107,7 +107,7 @@ export default Controller.extend(PeriodComputationMixin, {
}
},
- @computed("startDate", "endDate")
+ @discourseComputed("startDate", "endDate")
filters(startDate, endDate) {
return { startDate, endDate };
},
diff --git a/app/assets/javascripts/admin/controllers/admin-dashboard-moderation.js.es6 b/app/assets/javascripts/admin/controllers/admin-dashboard-moderation.js.es6
index e5d8dae25a..8925825fba 100644
--- a/app/assets/javascripts/admin/controllers/admin-dashboard-moderation.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-dashboard-moderation.js.es6
@@ -1,9 +1,9 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
import PeriodComputationMixin from "admin/mixins/period-computation";
export default Controller.extend(PeriodComputationMixin, {
- @computed
+ @discourseComputed
flagsStatusOptions() {
return {
table: {
@@ -13,7 +13,7 @@ export default Controller.extend(PeriodComputationMixin, {
};
},
- @computed
+ @discourseComputed
userFlaggingRatioOptions() {
return {
table: {
@@ -23,12 +23,12 @@ export default Controller.extend(PeriodComputationMixin, {
};
},
- @computed("startDate", "endDate")
+ @discourseComputed("startDate", "endDate")
filters(startDate, endDate) {
return { startDate, endDate };
},
- @computed("lastWeek", "endDate")
+ @discourseComputed("lastWeek", "endDate")
lastWeekfilters(startDate, endDate) {
return { startDate, endDate };
},
diff --git a/app/assets/javascripts/admin/controllers/admin-dashboard-reports.js.es6 b/app/assets/javascripts/admin/controllers/admin-dashboard-reports.js.es6
index b582f733aa..9a57b9cf32 100644
--- a/app/assets/javascripts/admin/controllers/admin-dashboard-reports.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-dashboard-reports.js.es6
@@ -1,12 +1,13 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { debounce } from "@ember/runloop";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
+
const { get } = Ember;
export default Controller.extend({
filter: null,
- @computed("model.[]", "filter")
+ @discourseComputed("model.[]", "filter")
filterReports(reports, filter) {
if (filter) {
filter = filter.toLowerCase();
diff --git a/app/assets/javascripts/admin/controllers/admin-dashboard.js.es6 b/app/assets/javascripts/admin/controllers/admin-dashboard.js.es6
index 0f214d6f2d..bd8561abc1 100644
--- a/app/assets/javascripts/admin/controllers/admin-dashboard.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-dashboard.js.es6
@@ -1,7 +1,7 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
import { setting } from "discourse/lib/computed";
-import computed from "ember-addons/ember-computed-decorators";
import AdminDashboard from "admin/models/admin-dashboard";
import VersionCheck from "admin/models/version-check";
@@ -13,7 +13,7 @@ export default Controller.extend({
exceptionController: inject("exception"),
showVersionChecks: setting("version_checks"),
- @computed("problems.length")
+ @discourseComputed("problems.length")
foundProblems(problemsLength) {
return this.currentUser.get("admin") && (problemsLength || 0) > 0;
},
@@ -77,7 +77,7 @@ export default Controller.extend({
.finally(() => this.set("loadingProblems", false));
},
- @computed("problemsFetchedAt")
+ @discourseComputed("problemsFetchedAt")
problemsTimestamp(problemsFetchedAt) {
return moment(problemsFetchedAt)
.locale("en")
diff --git a/app/assets/javascripts/admin/controllers/admin-embedding.js.es6 b/app/assets/javascripts/admin/controllers/admin-embedding.js.es6
index 7e185e9d12..b71c173e36 100644
--- a/app/assets/javascripts/admin/controllers/admin-embedding.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-embedding.js.es6
@@ -1,5 +1,5 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
import { popupAjaxError } from "discourse/lib/ajax-error";
export default Controller.extend({
@@ -7,13 +7,13 @@ export default Controller.extend({
embedding: null,
// show settings if we have at least one created host
- @computed("embedding.embeddable_hosts.@each.isCreated")
+ @discourseComputed("embedding.embeddable_hosts.@each.isCreated")
showSecondary() {
const hosts = this.get("embedding.embeddable_hosts");
return hosts.length && hosts.findBy("isCreated");
},
- @computed("embedding.base_url")
+ @discourseComputed("embedding.base_url")
embeddingCode(baseUrl) {
const html = `
diff --git a/app/assets/javascripts/admin/controllers/admin-logs-staff-action-logs.js.es6 b/app/assets/javascripts/admin/controllers/admin-logs-staff-action-logs.js.es6
index a375379fc0..e559bc846f 100644
--- a/app/assets/javascripts/admin/controllers/admin-logs-staff-action-logs.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-logs-staff-action-logs.js.es6
@@ -5,9 +5,9 @@ import Controller from "@ember/controller";
import { exportEntity } from "discourse/lib/export-csv";
import { outputExportResult } from "discourse/lib/export-result";
import {
- default as computed,
+ default as discourseComputed,
on
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
export default Controller.extend({
model: null,
@@ -15,7 +15,7 @@ export default Controller.extend({
filtersExists: gt("filterCount", 0),
userHistoryActions: null,
- @computed("filters.action_name")
+ @discourseComputed("filters.action_name")
actionFilter(name) {
return name ? I18n.t("admin.logs.staff_actions.actions." + name) : null;
},
diff --git a/app/assets/javascripts/admin/controllers/admin-plugins.js.es6 b/app/assets/javascripts/admin/controllers/admin-plugins.js.es6
index c0322317e5..f9b34e70a4 100644
--- a/app/assets/javascripts/admin/controllers/admin-plugins.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-plugins.js.es6
@@ -1,8 +1,8 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
export default Controller.extend({
- @computed
+ @discourseComputed
adminRoutes: function() {
return this.model
.map(p => {
diff --git a/app/assets/javascripts/admin/controllers/admin-reports-show.js.es6 b/app/assets/javascripts/admin/controllers/admin-reports-show.js.es6
index 359be15f1d..6d302204ce 100644
--- a/app/assets/javascripts/admin/controllers/admin-reports-show.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-reports-show.js.es6
@@ -1,5 +1,5 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
export default Controller.extend({
queryParams: ["start_date", "end_date", "filters"],
@@ -7,7 +7,7 @@ export default Controller.extend({
end_date: null,
filters: null,
- @computed("model.type")
+ @discourseComputed("model.type")
reportOptions(type) {
let options = { table: { perPage: 50, limit: 50, formatNumbers: false } };
diff --git a/app/assets/javascripts/admin/controllers/admin-site-settings-category.js.es6 b/app/assets/javascripts/admin/controllers/admin-site-settings-category.js.es6
index 3fd10f15d1..bfd727e6ea 100644
--- a/app/assets/javascripts/admin/controllers/admin-site-settings-category.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-site-settings-category.js.es6
@@ -1,17 +1,17 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
export default Controller.extend({
categoryNameKey: null,
adminSiteSettings: inject(),
- @computed("adminSiteSettings.visibleSiteSettings", "categoryNameKey")
+ @discourseComputed("adminSiteSettings.visibleSiteSettings", "categoryNameKey")
category(categories, nameKey) {
return (categories || []).findBy("nameKey", nameKey);
},
- @computed("category")
+ @discourseComputed("category")
filteredContent(category) {
return category ? category.siteSettings : [];
}
diff --git a/app/assets/javascripts/admin/controllers/admin-site-text-edit.js.es6 b/app/assets/javascripts/admin/controllers/admin-site-text-edit.js.es6
index cd815b9ae8..d24a172910 100644
--- a/app/assets/javascripts/admin/controllers/admin-site-text-edit.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-site-text-edit.js.es6
@@ -1,12 +1,12 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Controller from "@ember/controller";
import { popupAjaxError } from "discourse/lib/ajax-error";
import { bufferedProperty } from "discourse/mixins/buffered-content";
-import computed from "ember-addons/ember-computed-decorators";
export default Controller.extend(bufferedProperty("siteText"), {
saved: false,
- @computed("buffered.value")
+ @discourseComputed("buffered.value")
saveDisabled(value) {
return this.siteText.value === value;
},
diff --git a/app/assets/javascripts/admin/controllers/admin-user-badges.js.es6 b/app/assets/javascripts/admin/controllers/admin-user-badges.js.es6
index fac3436c6e..3bedafb45c 100644
--- a/app/assets/javascripts/admin/controllers/admin-user-badges.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-user-badges.js.es6
@@ -1,10 +1,10 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { alias, sort } from "@ember/object/computed";
import { next } from "@ember/runloop";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
import GrantBadgeController from "discourse/mixins/grant-badge-controller";
import { popupAjaxError } from "discourse/lib/ajax-error";
-import computed from "ember-addons/ember-computed-decorators";
export default Controller.extend(GrantBadgeController, {
adminUser: inject(),
@@ -19,7 +19,7 @@ export default Controller.extend(GrantBadgeController, {
this.badgeSortOrder = ["granted_at:desc"];
},
- @computed("model", "model.[]", "model.expandedBadges.[]")
+ @discourseComputed("model", "model.[]", "model.expandedBadges.[]")
groupedBadges() {
const allBadges = this.model;
diff --git a/app/assets/javascripts/admin/controllers/admin-user-index.js.es6 b/app/assets/javascripts/admin/controllers/admin-user-index.js.es6
index de2e37668f..765e8d3686 100644
--- a/app/assets/javascripts/admin/controllers/admin-user-index.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-user-index.js.es6
@@ -6,7 +6,7 @@ import CanCheckEmails from "discourse/mixins/can-check-emails";
import { propertyNotEqual, setting } from "discourse/lib/computed";
import { userPath } from "discourse/lib/url";
import { popupAjaxError } from "discourse/lib/ajax-error";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import { fmt } from "discourse/lib/computed";
import { htmlSafe } from "@ember/template";
@@ -30,12 +30,12 @@ export default Controller.extend(CanCheckEmails, {
"model.can_disable_second_factor"
),
- @computed("model.customGroups")
+ @discourseComputed("model.customGroups")
customGroupIds(customGroups) {
return customGroups.mapBy("id");
},
- @computed("customGroupIdsBuffer", "customGroupIds")
+ @discourseComputed("customGroupIdsBuffer", "customGroupIds")
customGroupsDirty(buffer, original) {
if (buffer === null) return false;
@@ -44,7 +44,7 @@ export default Controller.extend(CanCheckEmails, {
: true;
},
- @computed("model.automaticGroups")
+ @discourseComputed("model.automaticGroups")
automaticGroups(automaticGroups) {
return automaticGroups
.map(group => {
@@ -54,26 +54,30 @@ export default Controller.extend(CanCheckEmails, {
.join(", ");
},
- @computed("model.associated_accounts")
+ @discourseComputed("model.associated_accounts")
associatedAccountsLoaded(associatedAccounts) {
return typeof associatedAccounts !== "undefined";
},
- @computed("model.associated_accounts")
+ @discourseComputed("model.associated_accounts")
associatedAccounts(associatedAccounts) {
return associatedAccounts
.map(provider => `${provider.name} (${provider.description})`)
.join(", ");
},
- @computed("model.user_fields.[]")
+ @discourseComputed("model.user_fields.[]")
userFields(userFields) {
return this.site.collectUserFields(userFields);
},
preferencesPath: fmt("model.username_lower", userPath("%@/preferences")),
- @computed("model.can_delete_all_posts", "model.staff", "model.post_count")
+ @discourseComputed(
+ "model.can_delete_all_posts",
+ "model.staff",
+ "model.post_count"
+ )
deleteAllPostsExplanation(canDeleteAllPosts, staff, postCount) {
if (canDeleteAllPosts) {
return null;
@@ -93,7 +97,7 @@ export default Controller.extend(CanCheckEmails, {
}
},
- @computed("model.canBeDeleted", "model.staff")
+ @discourseComputed("model.canBeDeleted", "model.staff")
deleteExplanation(canBeDeleted, staff) {
if (canBeDeleted) {
return null;
diff --git a/app/assets/javascripts/admin/controllers/admin-users-list-show.js.es6 b/app/assets/javascripts/admin/controllers/admin-users-list-show.js.es6
index 944b0d9485..87380235e3 100644
--- a/app/assets/javascripts/admin/controllers/admin-users-list-show.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-users-list-show.js.es6
@@ -1,9 +1,9 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Controller from "@ember/controller";
import debounce from "discourse/lib/debounce";
import { i18n } from "discourse/lib/computed";
import AdminUser from "admin/models/admin-user";
import CanCheckEmails from "discourse/mixins/can-check-emails";
-import computed from "ember-addons/ember-computed-decorators";
export default Controller.extend(CanCheckEmails, {
model: null,
@@ -24,7 +24,7 @@ export default Controller.extend(CanCheckEmails, {
this._canLoadMore = true;
},
- @computed("query")
+ @discourseComputed("query")
title(query) {
return I18n.t("admin.users.titles." + query);
},
diff --git a/app/assets/javascripts/admin/controllers/admin-watched-words-action.js.es6 b/app/assets/javascripts/admin/controllers/admin-watched-words-action.js.es6
index 1726446d8c..d6f52c13fd 100644
--- a/app/assets/javascripts/admin/controllers/admin-watched-words-action.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-watched-words-action.js.es6
@@ -1,8 +1,8 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { or } from "@ember/object/computed";
import { schedule } from "@ember/runloop";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
import WatchedWord from "admin/models/watched-word";
import { ajax } from "discourse/lib/ajax";
import { fmt } from "discourse/lib/computed";
@@ -27,22 +27,22 @@ export default Controller.extend({
);
},
- @computed("actionNameKey", "adminWatchedWords.model")
+ @discourseComputed("actionNameKey", "adminWatchedWords.model")
currentAction(actionName) {
return this.findAction(actionName);
},
- @computed("currentAction.words.[]", "adminWatchedWords.model")
+ @discourseComputed("currentAction.words.[]", "adminWatchedWords.model")
filteredContent(words) {
return words || [];
},
- @computed("actionNameKey")
+ @discourseComputed("actionNameKey")
actionDescription(actionNameKey) {
return I18n.t("admin.watched_words.action_descriptions." + actionNameKey);
},
- @computed("currentAction.count")
+ @discourseComputed("currentAction.count")
wordCount(count) {
return count || 0;
},
diff --git a/app/assets/javascripts/admin/controllers/admin-web-hooks-show-events.js.es6 b/app/assets/javascripts/admin/controllers/admin-web-hooks-show-events.js.es6
index e550a79069..6cd94efb68 100644
--- a/app/assets/javascripts/admin/controllers/admin-web-hooks-show-events.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-web-hooks-show-events.js.es6
@@ -1,8 +1,8 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { alias } from "@ember/object/computed";
import Controller from "@ember/controller";
import { ajax } from "discourse/lib/ajax";
import { popupAjaxError } from "discourse/lib/ajax-error";
-import computed from "ember-addons/ember-computed-decorators";
export default Controller.extend({
pingDisabled: false,
@@ -14,7 +14,7 @@ export default Controller.extend({
this.incomingEventIds = [];
},
- @computed("incomingCount")
+ @discourseComputed("incomingCount")
hasIncoming(incomingCount) {
return incomingCount > 0;
},
diff --git a/app/assets/javascripts/admin/controllers/admin-web-hooks-show.js.es6 b/app/assets/javascripts/admin/controllers/admin-web-hooks-show.js.es6
index 83de79e1f0..b07806f6fa 100644
--- a/app/assets/javascripts/admin/controllers/admin-web-hooks-show.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-web-hooks-show.js.es6
@@ -1,10 +1,10 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { isEmpty } from "@ember/utils";
import { alias } from "@ember/object/computed";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
import { popupAjaxError } from "discourse/lib/ajax-error";
import { extractDomainFromUrl } from "discourse/lib/utilities";
-import computed from "ember-addons/ember-computed-decorators";
import InputValidation from "discourse/models/input-validation";
export default Controller.extend({
@@ -13,12 +13,12 @@ export default Controller.extend({
defaultEventTypes: alias("adminWebHooks.defaultEventTypes"),
contentTypes: alias("adminWebHooks.contentTypes"),
- @computed
+ @discourseComputed
showTagsFilter() {
return this.siteSettings.tagging_enabled;
},
- @computed("model.isSaving", "saved", "saveButtonDisabled")
+ @discourseComputed("model.isSaving", "saved", "saveButtonDisabled")
savingStatus(isSaving, saved, saveButtonDisabled) {
if (isSaving) {
return I18n.t("saving");
@@ -30,14 +30,14 @@ export default Controller.extend({
return "";
},
- @computed("model.isNew")
+ @discourseComputed("model.isNew")
saveButtonText(isNew) {
return isNew
? I18n.t("admin.web_hooks.create")
: I18n.t("admin.web_hooks.save");
},
- @computed("model.secret")
+ @discourseComputed("model.secret")
secretValidation(secret) {
if (!isEmpty(secret)) {
if (secret.indexOf(" ") !== -1) {
@@ -56,7 +56,7 @@ export default Controller.extend({
}
},
- @computed("model.wildcard_web_hook", "model.web_hook_event_types.[]")
+ @discourseComputed("model.wildcard_web_hook", "model.web_hook_event_types.[]")
eventTypeValidation(isWildcard, eventTypes) {
if (!isWildcard && isEmpty(eventTypes)) {
return InputValidation.create({
@@ -66,7 +66,7 @@ export default Controller.extend({
}
},
- @computed(
+ @discourseComputed(
"model.isSaving",
"secretValidation",
"eventTypeValidation",
diff --git a/app/assets/javascripts/admin/controllers/admin.js.es6 b/app/assets/javascripts/admin/controllers/admin.js.es6
index f01a898b0c..641643d573 100644
--- a/app/assets/javascripts/admin/controllers/admin.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin.js.es6
@@ -1,22 +1,22 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { inject as service } from "@ember/service";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
import { dasherize } from "@ember/string";
export default Controller.extend({
router: service(),
- @computed("siteSettings.enable_group_directory")
+ @discourseComputed("siteSettings.enable_group_directory")
showGroups(enableGroupDirectory) {
return !enableGroupDirectory;
},
- @computed("siteSettings.enable_badges")
+ @discourseComputed("siteSettings.enable_badges")
showBadges(enableBadges) {
return this.currentUser.get("admin") && enableBadges;
},
- @computed("router._router.currentPath")
+ @discourseComputed("router._router.currentPath")
adminContentsClassName(currentPath) {
let cssClasses = currentPath
.split(".")
diff --git a/app/assets/javascripts/admin/controllers/modals/admin-add-upload.js.es6 b/app/assets/javascripts/admin/controllers/modals/admin-add-upload.js.es6
index d53278c856..bd246d9371 100644
--- a/app/assets/javascripts/admin/controllers/modals/admin-add-upload.js.es6
+++ b/app/assets/javascripts/admin/controllers/modals/admin-add-upload.js.es6
@@ -5,9 +5,9 @@ import Controller from "@ember/controller";
import ModalFunctionality from "discourse/mixins/modal-functionality";
import { ajax } from "discourse/lib/ajax";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import { popupAjaxError } from "discourse/lib/ajax-error";
const THEME_FIELD_VARIABLE_TYPE_IDS = [2, 3, 4];
@@ -69,7 +69,7 @@ export default Controller.extend(ModalFunctionality, {
enabled: and("nameValid", "fileSelected"),
disabled: not("enabled"),
- @computed("name", "adminCustomizeThemesShow.model.theme_fields")
+ @discourseComputed("name", "adminCustomizeThemesShow.model.theme_fields")
errorMessage(name, themeFields) {
if (name) {
if (!name.match(/^[a-z_][a-z0-9_-]*$/i)) {
@@ -94,7 +94,7 @@ export default Controller.extend(ModalFunctionality, {
return null;
},
- @computed("errorMessage")
+ @discourseComputed("errorMessage")
nameValid(errorMessage) {
return null === errorMessage;
},
diff --git a/app/assets/javascripts/admin/controllers/modals/admin-badge-preview.js.es6 b/app/assets/javascripts/admin/controllers/modals/admin-badge-preview.js.es6
index b6419c8e04..67450978d7 100644
--- a/app/assets/javascripts/admin/controllers/modals/admin-badge-preview.js.es6
+++ b/app/assets/javascripts/admin/controllers/modals/admin-badge-preview.js.es6
@@ -1,6 +1,6 @@
import { alias, map } from "@ember/object/computed";
import Controller from "@ember/controller";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import { escapeExpression } from "discourse/lib/utilities";
export default Controller.extend({
@@ -8,7 +8,7 @@ export default Controller.extend({
errors: alias("model.errors"),
count: alias("model.grant_count"),
- @computed("count", "sample.length")
+ @discourseComputed("count", "sample.length")
countWarning(count, sampleLength) {
if (count <= 10) {
return sampleLength !== count;
@@ -17,12 +17,12 @@ export default Controller.extend({
}
},
- @computed("model.query_plan")
+ @discourseComputed("model.query_plan")
hasQueryPlan(queryPlan) {
return !!queryPlan;
},
- @computed("model.query_plan")
+ @discourseComputed("model.query_plan")
queryPlanHtml(queryPlan) {
let output = ``;
diff --git a/app/assets/javascripts/admin/controllers/modals/admin-edit-badge-groupings.js.es6 b/app/assets/javascripts/admin/controllers/modals/admin-edit-badge-groupings.js.es6
index 4d0c66143c..1629aab70b 100644
--- a/app/assets/javascripts/admin/controllers/modals/admin-edit-badge-groupings.js.es6
+++ b/app/assets/javascripts/admin/controllers/modals/admin-edit-badge-groupings.js.es6
@@ -1,7 +1,7 @@
import Controller from "@ember/controller";
import { ajax } from "discourse/lib/ajax";
import ModalFunctionality from "discourse/mixins/modal-functionality";
-import { observes } from "ember-addons/ember-computed-decorators";
+import { observes } from "discourse-common/utils/decorators";
export default Controller.extend(ModalFunctionality, {
@observes("model")
diff --git a/app/assets/javascripts/admin/controllers/modals/admin-incoming-email.js.es6 b/app/assets/javascripts/admin/controllers/modals/admin-incoming-email.js.es6
index 210d664cda..cca2cc54bf 100644
--- a/app/assets/javascripts/admin/controllers/modals/admin-incoming-email.js.es6
+++ b/app/assets/javascripts/admin/controllers/modals/admin-incoming-email.js.es6
@@ -1,12 +1,12 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Controller from "@ember/controller";
import ModalFunctionality from "discourse/mixins/modal-functionality";
import IncomingEmail from "admin/models/incoming-email";
-import computed from "ember-addons/ember-computed-decorators";
import { longDate } from "discourse/lib/formatter";
import { popupAjaxError } from "discourse/lib/ajax-error";
export default Controller.extend(ModalFunctionality, {
- @computed("model.date")
+ @discourseComputed("model.date")
date(d) {
return longDate(d);
},
diff --git a/app/assets/javascripts/admin/controllers/modals/admin-install-theme.js.es6 b/app/assets/javascripts/admin/controllers/modals/admin-install-theme.js.es6
index 81055d733d..9aee44f72e 100644
--- a/app/assets/javascripts/admin/controllers/modals/admin-install-theme.js.es6
+++ b/app/assets/javascripts/admin/controllers/modals/admin-install-theme.js.es6
@@ -5,9 +5,9 @@ import ModalFunctionality from "discourse/mixins/modal-functionality";
import { ajax } from "discourse/lib/ajax";
import { popupAjaxError } from "discourse/lib/ajax-error";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import { THEMES, COMPONENTS } from "admin/models/theme";
import { POPULAR_THEMES } from "discourse-common/helpers/popular-themes";
import { set } from "@ember/object";
@@ -43,7 +43,7 @@ export default Controller.extend(ModalFunctionality, {
];
},
- @computed("themesController.installedThemes")
+ @discourseComputed("themesController.installedThemes")
themes(installedThemes) {
return POPULAR_THEMES.map(t => {
if (installedThemes.includes(t.name)) {
@@ -53,7 +53,7 @@ export default Controller.extend(ModalFunctionality, {
});
},
- @computed(
+ @discourseComputed(
"loading",
"remote",
"uploadUrl",
@@ -102,12 +102,12 @@ export default Controller.extend(ModalFunctionality, {
}
},
- @computed("name")
+ @discourseComputed("name")
nameTooShort(name) {
return !name || name.length < MIN_NAME_LENGTH;
},
- @computed("component")
+ @discourseComputed("component")
placeholder(component) {
if (component) {
return I18n.t("admin.customize.theme.component_name");
@@ -116,14 +116,14 @@ export default Controller.extend(ModalFunctionality, {
}
},
- @computed("selection")
+ @discourseComputed("selection")
submitLabel(selection) {
return `admin.customize.theme.${
selection === "create" ? "create" : "install"
}`;
},
- @computed("privateChecked", "checkPrivate", "publicKey")
+ @discourseComputed("privateChecked", "checkPrivate", "publicKey")
showPublicKey(privateChecked, checkPrivate, publicKey) {
return privateChecked && checkPrivate && publicKey;
},
diff --git a/app/assets/javascripts/admin/controllers/modals/admin-silence-user.js.es6 b/app/assets/javascripts/admin/controllers/modals/admin-silence-user.js.es6
index 5c04066941..d15264f46b 100644
--- a/app/assets/javascripts/admin/controllers/modals/admin-silence-user.js.es6
+++ b/app/assets/javascripts/admin/controllers/modals/admin-silence-user.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { isEmpty } from "@ember/utils";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
import PenaltyController from "admin/mixins/penalty-controller";
export default Controller.extend(PenaltyController, {
@@ -12,7 +12,7 @@ export default Controller.extend(PenaltyController, {
this.setProperties({ silenceUntil: null, silencing: false });
},
- @computed("silenceUntil", "reason", "silencing")
+ @discourseComputed("silenceUntil", "reason", "silencing")
submitDisabled(silenceUntil, reason, silencing) {
return silencing || isEmpty(silenceUntil) || !reason || reason.length < 1;
},
diff --git a/app/assets/javascripts/admin/controllers/modals/admin-suspend-user.js.es6 b/app/assets/javascripts/admin/controllers/modals/admin-suspend-user.js.es6
index c5afea9d88..03fa9fbc83 100644
--- a/app/assets/javascripts/admin/controllers/modals/admin-suspend-user.js.es6
+++ b/app/assets/javascripts/admin/controllers/modals/admin-suspend-user.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { isEmpty } from "@ember/utils";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
import PenaltyController from "admin/mixins/penalty-controller";
export default Controller.extend(PenaltyController, {
@@ -12,7 +12,7 @@ export default Controller.extend(PenaltyController, {
this.setProperties({ suspendUntil: null, suspending: false });
},
- @computed("suspendUntil", "reason", "suspending")
+ @discourseComputed("suspendUntil", "reason", "suspending")
submitDisabled(suspendUntil, reason, suspending) {
return suspending || isEmpty(suspendUntil) || !reason || reason.length < 1;
},
diff --git a/app/assets/javascripts/admin/controllers/modals/admin-uploaded-image-list.js.es6 b/app/assets/javascripts/admin/controllers/modals/admin-uploaded-image-list.js.es6
index a5ac891c21..08e1e178e4 100644
--- a/app/assets/javascripts/admin/controllers/modals/admin-uploaded-image-list.js.es6
+++ b/app/assets/javascripts/admin/controllers/modals/admin-uploaded-image-list.js.es6
@@ -1,5 +1,5 @@
import Controller from "@ember/controller";
-import { on, observes } from "ember-addons/ember-computed-decorators";
+import { on, observes } from "discourse-common/utils/decorators";
import ModalFunctionality from "discourse/mixins/modal-functionality";
export default Controller.extend(ModalFunctionality, {
diff --git a/app/assets/javascripts/admin/controllers/modals/admin-watched-word-test.js.es6 b/app/assets/javascripts/admin/controllers/modals/admin-watched-word-test.js.es6
index 10f90ee615..9d9b73072d 100644
--- a/app/assets/javascripts/admin/controllers/modals/admin-watched-word-test.js.es6
+++ b/app/assets/javascripts/admin/controllers/modals/admin-watched-word-test.js.es6
@@ -1,9 +1,9 @@
import Controller from "@ember/controller";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import ModalFunctionality from "discourse/mixins/modal-functionality";
export default Controller.extend(ModalFunctionality, {
- @computed("value", "model.compiledRegularExpression")
+ @discourseComputed("value", "model.compiledRegularExpression")
matches(value, regexpString) {
if (!value || !regexpString) return;
let censorRegexp = new RegExp(regexpString, "ig");
diff --git a/app/assets/javascripts/admin/mixins/period-computation.js.es6 b/app/assets/javascripts/admin/mixins/period-computation.js.es6
index 354fd0ad85..c7af0e4cb3 100644
--- a/app/assets/javascripts/admin/mixins/period-computation.js.es6
+++ b/app/assets/javascripts/admin/mixins/period-computation.js.es6
@@ -1,5 +1,5 @@
+import discourseComputed from "discourse-common/utils/decorators";
import DiscourseURL from "discourse/lib/url";
-import computed from "ember-addons/ember-computed-decorators";
import Mixin from "@ember/object/mixin";
export default Mixin.create({
@@ -12,7 +12,7 @@ export default Mixin.create({
this.availablePeriods = ["yearly", "quarterly", "monthly", "weekly"];
},
- @computed("period")
+ @discourseComputed("period")
startDate(period) {
let fullDay = moment()
.locale("en")
@@ -37,7 +37,7 @@ export default Mixin.create({
}
},
- @computed()
+ @discourseComputed()
lastWeek() {
return moment()
.locale("en")
@@ -46,7 +46,7 @@ export default Mixin.create({
.subtract(1, "week");
},
- @computed()
+ @discourseComputed()
lastMonth() {
return moment()
.locale("en")
@@ -55,7 +55,7 @@ export default Mixin.create({
.subtract(1, "month");
},
- @computed()
+ @discourseComputed()
endDate() {
return moment()
.locale("en")
@@ -64,7 +64,7 @@ export default Mixin.create({
.endOf("day");
},
- @computed()
+ @discourseComputed()
today() {
return moment()
.locale("en")
diff --git a/app/assets/javascripts/admin/mixins/setting-component.js.es6 b/app/assets/javascripts/admin/mixins/setting-component.js.es6
index 762d5cfa2b..eaf5b356b6 100644
--- a/app/assets/javascripts/admin/mixins/setting-component.js.es6
+++ b/app/assets/javascripts/admin/mixins/setting-component.js.es6
@@ -1,5 +1,5 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { alias, oneWay } from "@ember/object/computed";
-import computed from "ember-addons/ember-computed-decorators";
import { categoryLinkHTML } from "discourse/helpers/category-link";
import { on } from "@ember/object/evented";
import Mixin from "@ember/object/mixin";
@@ -32,7 +32,7 @@ export default Mixin.create({
validationMessage: null,
isSecret: oneWay("setting.secret"),
- @computed("buffered.value", "setting.value")
+ @discourseComputed("buffered.value", "setting.value")
dirty(bufferVal, settingVal) {
if (bufferVal === null || bufferVal === undefined) bufferVal = "";
if (settingVal === null || settingVal === undefined) settingVal = "";
@@ -40,7 +40,7 @@ export default Mixin.create({
return bufferVal.toString() !== settingVal.toString();
},
- @computed("setting", "buffered.value")
+ @discourseComputed("setting", "buffered.value")
preview(setting, value) {
// A bit hacky, but allows us to use helpers
if (setting.get("setting") === "category_style") {
@@ -62,22 +62,22 @@ export default Mixin.create({
}
},
- @computed("componentType")
+ @discourseComputed("componentType")
typeClass(componentType) {
return componentType.replace(/\_/g, "-");
},
- @computed("setting.setting")
+ @discourseComputed("setting.setting")
settingName(setting) {
return setting.replace(/\_/g, " ");
},
- @computed("type")
+ @discourseComputed("type")
componentType(type) {
return CUSTOM_TYPES.indexOf(type) !== -1 ? type : "string";
},
- @computed("setting")
+ @discourseComputed("setting")
type(setting) {
if (setting.type === "list" && setting.list_type) {
return `${setting.list_type}_list`;
@@ -86,12 +86,12 @@ export default Mixin.create({
return setting.type;
},
- @computed("typeClass")
+ @discourseComputed("typeClass")
componentName(typeClass) {
return "site-settings/" + typeClass;
},
- @computed("setting.default", "buffered.value")
+ @discourseComputed("setting.default", "buffered.value")
overridden(settingDefault, bufferedValue) {
return settingDefault !== bufferedValue;
},
diff --git a/app/assets/javascripts/admin/mixins/setting-object.js.es6 b/app/assets/javascripts/admin/mixins/setting-object.js.es6
index c02004cea8..f0296e6c55 100644
--- a/app/assets/javascripts/admin/mixins/setting-object.js.es6
+++ b/app/assets/javascripts/admin/mixins/setting-object.js.es6
@@ -1,8 +1,8 @@
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
import Mixin from "@ember/object/mixin";
export default Mixin.create({
- @computed("value", "default")
+ @discourseComputed("value", "default")
overridden(val, defaultVal) {
if (val === null) val = "";
if (defaultVal === null) defaultVal = "";
@@ -10,7 +10,7 @@ export default Mixin.create({
return val.toString() !== defaultVal.toString();
},
- @computed("valid_values")
+ @discourseComputed("valid_values")
validValues(validValues) {
const vals = [],
translateNames = this.translate_names;
@@ -25,7 +25,7 @@ export default Mixin.create({
return vals;
},
- @computed("valid_values")
+ @discourseComputed("valid_values")
allowsNone(validValues) {
if (validValues && validValues.indexOf("") >= 0) {
return "admin.settings.none";
diff --git a/app/assets/javascripts/admin/models/admin-user.js.es6 b/app/assets/javascripts/admin/models/admin-user.js.es6
index 880cb44c39..5447070185 100644
--- a/app/assets/javascripts/admin/models/admin-user.js.es6
+++ b/app/assets/javascripts/admin/models/admin-user.js.es6
@@ -1,7 +1,7 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { filter, or, gt, lt, not } from "@ember/object/computed";
import { iconHTML } from "discourse-common/lib/icon-library";
import { ajax } from "discourse/lib/ajax";
-import computed from "ember-addons/ember-computed-decorators";
import { propertyNotEqual } from "discourse/lib/computed";
import { popupAjaxError } from "discourse/lib/ajax-error";
import Group from "discourse/models/group";
@@ -17,7 +17,7 @@ const AdminUser = Discourse.User.extend({
canViewProfile: or("active", "staged"),
- @computed("bounce_score", "reset_bounce_score_after")
+ @discourseComputed("bounce_score", "reset_bounce_score_after")
bounceScore(bounce_score, reset_bounce_score_after) {
if (bounce_score > 0) {
return `${bounce_score} - ${moment(reset_bounce_score_after).format(
@@ -28,7 +28,7 @@ const AdminUser = Discourse.User.extend({
}
},
- @computed("bounce_score")
+ @discourseComputed("bounce_score")
bounceScoreExplanation(bounce_score) {
if (bounce_score === 0) {
return I18n.t("admin.user.bounce_score_explanation.none");
@@ -39,7 +39,7 @@ const AdminUser = Discourse.User.extend({
}
},
- @computed
+ @discourseComputed
bounceLink() {
return Discourse.getURL("/admin/email/bounced");
},
@@ -278,7 +278,7 @@ const AdminUser = Discourse.User.extend({
canSuspend: not("staff"),
- @computed("suspended_till", "suspended_at")
+ @discourseComputed("suspended_till", "suspended_at")
suspendDuration(suspendedTill, suspendedAt) {
suspendedAt = moment(suspendedAt);
suspendedTill = moment(suspendedTill);
@@ -513,20 +513,20 @@ const AdminUser = Discourse.User.extend({
});
},
- @computed("tl3_requirements")
+ @discourseComputed("tl3_requirements")
tl3Requirements(requirements) {
if (requirements) {
return this.store.createRecord("tl3Requirements", requirements);
}
},
- @computed("suspended_by")
+ @discourseComputed("suspended_by")
suspendedBy: wrapAdmin,
- @computed("silenced_by")
+ @discourseComputed("silenced_by")
silencedBy: wrapAdmin,
- @computed("approved_by")
+ @discourseComputed("approved_by")
approvedBy: wrapAdmin,
_formatError(event) {
diff --git a/app/assets/javascripts/admin/models/api-key.js.es6 b/app/assets/javascripts/admin/models/api-key.js.es6
index 95d8e1914c..4b77e23c4a 100644
--- a/app/assets/javascripts/admin/models/api-key.js.es6
+++ b/app/assets/javascripts/admin/models/api-key.js.es6
@@ -1,7 +1,7 @@
+import discourseComputed from "discourse-common/utils/decorators";
import AdminUser from "admin/models/admin-user";
import RestModel from "discourse/models/rest";
import { ajax } from "discourse/lib/ajax";
-import computed from "ember-addons/ember-computed-decorators";
const ApiKey = RestModel.extend({
user: Ember.computed("_user", {
@@ -18,12 +18,12 @@ const ApiKey = RestModel.extend({
}
}),
- @computed("key")
+ @discourseComputed("key")
shortKey(key) {
return `${key.substring(0, 4)}...`;
},
- @computed("description")
+ @discourseComputed("description")
shortDescription(description) {
if (!description || description.length < 40) return description;
return `${description.substring(0, 40)}...`;
@@ -45,7 +45,7 @@ const ApiKey = RestModel.extend({
return this.getProperties("description", "username");
},
- @computed()
+ @discourseComputed()
basePath() {
return this.store
.adapterFor("api-key")
diff --git a/app/assets/javascripts/admin/models/backup-status.js.es6 b/app/assets/javascripts/admin/models/backup-status.js.es6
index b7deec1c10..b31d1cb176 100644
--- a/app/assets/javascripts/admin/models/backup-status.js.es6
+++ b/app/assets/javascripts/admin/models/backup-status.js.es6
@@ -1,10 +1,10 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { not } from "@ember/object/computed";
-import computed from "ember-addons/ember-computed-decorators";
export default Discourse.Model.extend({
restoreDisabled: not("restoreEnabled"),
- @computed("allowRestore", "isOperationRunning")
+ @discourseComputed("allowRestore", "isOperationRunning")
restoreEnabled(allowRestore, isOperationRunning) {
return allowRestore && !isOperationRunning;
}
diff --git a/app/assets/javascripts/admin/models/color-scheme-color.js.es6 b/app/assets/javascripts/admin/models/color-scheme-color.js.es6
index a3b22d23bc..d023295ce5 100644
--- a/app/assets/javascripts/admin/models/color-scheme-color.js.es6
+++ b/app/assets/javascripts/admin/models/color-scheme-color.js.es6
@@ -1,8 +1,8 @@
import {
- default as computed,
+ default as discourseComputed,
observes,
on
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import { propertyNotEqual } from "discourse/lib/computed";
const ColorSchemeColor = Discourse.Model.extend({
@@ -15,7 +15,7 @@ const ColorSchemeColor = Discourse.Model.extend({
},
// Whether value has changed since it was last saved.
- @computed("hex")
+ @discourseComputed("hex")
changed(hex) {
if (!this.originals) return false;
if (hex !== this.originals.hex) return true;
@@ -27,7 +27,7 @@ const ColorSchemeColor = Discourse.Model.extend({
overridden: propertyNotEqual("hex", "default_hex"),
// Whether the saved value is different than Discourse's default color scheme.
- @computed("default_hex", "hex")
+ @discourseComputed("default_hex", "hex")
savedIsOverriden(defaultHex) {
return this.originals.hex !== defaultHex;
},
@@ -42,7 +42,7 @@ const ColorSchemeColor = Discourse.Model.extend({
}
},
- @computed("name")
+ @discourseComputed("name")
translatedName(name) {
if (!this.is_advanced) {
return I18n.t(`admin.customize.colors.${name}.name`);
@@ -51,7 +51,7 @@ const ColorSchemeColor = Discourse.Model.extend({
}
},
- @computed("name")
+ @discourseComputed("name")
description(name) {
if (!this.is_advanced) {
return I18n.t(`admin.customize.colors.${name}.description`);
@@ -66,7 +66,7 @@ const ColorSchemeColor = Discourse.Model.extend({
@property brightness
**/
- @computed("hex")
+ @discourseComputed("hex")
brightness(hex) {
if (hex.length === 6 || hex.length === 3) {
if (hex.length === 3) {
@@ -94,7 +94,7 @@ const ColorSchemeColor = Discourse.Model.extend({
}
},
- @computed("hex")
+ @discourseComputed("hex")
valid(hex) {
return hex.match(/^([0-9a-fA-F]{3}|[0-9a-fA-F]{6})$/) !== null;
}
diff --git a/app/assets/javascripts/admin/models/color-scheme.js.es6 b/app/assets/javascripts/admin/models/color-scheme.js.es6
index 8875bf2e5e..5d0550d2e0 100644
--- a/app/assets/javascripts/admin/models/color-scheme.js.es6
+++ b/app/assets/javascripts/admin/models/color-scheme.js.es6
@@ -1,7 +1,7 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { not } from "@ember/object/computed";
import { ajax } from "discourse/lib/ajax";
import ColorSchemeColor from "admin/models/color-scheme-color";
-import computed from "ember-addons/ember-computed-decorators";
const ColorScheme = Discourse.Model.extend(Ember.Copyable, {
init() {
@@ -10,7 +10,7 @@ const ColorScheme = Discourse.Model.extend(Ember.Copyable, {
this.startTrackingChanges();
},
- @computed
+ @discourseComputed
description() {
return "" + this.name;
},
@@ -42,7 +42,7 @@ const ColorScheme = Discourse.Model.extend(Ember.Copyable, {
return newScheme;
},
- @computed("name", "colors.@each.changed", "saving")
+ @discourseComputed("name", "colors.@each.changed", "saving")
changed(name) {
if (!this.originals) return false;
if (this.originals.name !== name) return true;
@@ -51,7 +51,7 @@ const ColorScheme = Discourse.Model.extend(Ember.Copyable, {
return false;
},
- @computed("changed")
+ @discourseComputed("changed")
disableSave(changed) {
if (this.theme_id) {
return false;
diff --git a/app/assets/javascripts/admin/models/flag-type.js.es6 b/app/assets/javascripts/admin/models/flag-type.js.es6
index b1bf1ca828..93fb2eacc9 100644
--- a/app/assets/javascripts/admin/models/flag-type.js.es6
+++ b/app/assets/javascripts/admin/models/flag-type.js.es6
@@ -1,8 +1,8 @@
+import discourseComputed from "discourse-common/utils/decorators";
import RestModel from "discourse/models/rest";
-import computed from "ember-addons/ember-computed-decorators";
export default RestModel.extend({
- @computed("id")
+ @discourseComputed("id")
name(id) {
return I18n.t(`admin.flags.summary.action_type_${id}`, { count: 1 });
}
diff --git a/app/assets/javascripts/admin/models/report.js.es6 b/app/assets/javascripts/admin/models/report.js.es6
index 37c495e06f..bb745b1302 100644
--- a/app/assets/javascripts/admin/models/report.js.es6
+++ b/app/assets/javascripts/admin/models/report.js.es6
@@ -1,3 +1,4 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { makeArray } from "discourse-common/lib/helpers";
import { isEmpty } from "@ember/utils";
import EmberObject from "@ember/object";
@@ -9,7 +10,6 @@ import {
formatUsername,
toNumber
} from "discourse/lib/utilities";
-import computed from "ember-addons/ember-computed-decorators";
import { number, durationTiny } from "discourse/lib/formatter";
import { renderAvatar } from "discourse/helpers/user-avatar";
@@ -22,12 +22,12 @@ const Report = Discourse.Model.extend({
percent: false,
higher_is_better: true,
- @computed("modes")
+ @discourseComputed("modes")
isTable(modes) {
return modes.some(mode => mode === "table");
},
- @computed("type", "start_date", "end_date")
+ @discourseComputed("type", "start_date", "end_date")
reportUrl(type, start_date, end_date) {
start_date = moment
.utc(start_date)
@@ -83,32 +83,32 @@ const Report = Discourse.Model.extend({
}
},
- @computed("data", "average")
+ @discourseComputed("data", "average")
todayCount() {
return this.valueAt(0);
},
- @computed("data", "average")
+ @discourseComputed("data", "average")
yesterdayCount() {
return this.valueAt(1);
},
- @computed("data", "average")
+ @discourseComputed("data", "average")
sevenDaysAgoCount() {
return this.valueAt(7);
},
- @computed("data", "average")
+ @discourseComputed("data", "average")
thirtyDaysAgoCount() {
return this.valueAt(30);
},
- @computed("data", "average")
+ @discourseComputed("data", "average")
lastSevenDaysCount() {
return this.averageCount(7, this.valueFor(1, 7));
},
- @computed("data", "average")
+ @discourseComputed("data", "average")
lastThirtyDaysCount() {
return this.averageCount(30, this.valueFor(1, 30));
},
@@ -117,12 +117,12 @@ const Report = Discourse.Model.extend({
return this.average ? value / count : value;
},
- @computed("yesterdayCount", "higher_is_better")
+ @discourseComputed("yesterdayCount", "higher_is_better")
yesterdayTrend(yesterdayCount, higherIsBetter) {
return this._computeTrend(this.valueAt(2), yesterdayCount, higherIsBetter);
},
- @computed("lastSevenDaysCount", "higher_is_better")
+ @discourseComputed("lastSevenDaysCount", "higher_is_better")
sevenDaysTrend(lastSevenDaysCount, higherIsBetter) {
return this._computeTrend(
this.valueFor(8, 14),
@@ -131,50 +131,55 @@ const Report = Discourse.Model.extend({
);
},
- @computed("data")
+ @discourseComputed("data")
currentTotal(data) {
return data.reduce((cur, pair) => cur + pair.y, 0);
},
- @computed("data", "currentTotal")
+ @discourseComputed("data", "currentTotal")
currentAverage(data, total) {
return makeArray(data).length === 0
? 0
: parseFloat((total / parseFloat(data.length)).toFixed(1));
},
- @computed("trend", "higher_is_better")
+ @discourseComputed("trend", "higher_is_better")
trendIcon(trend, higherIsBetter) {
return this._iconForTrend(trend, higherIsBetter);
},
- @computed("sevenDaysTrend", "higher_is_better")
+ @discourseComputed("sevenDaysTrend", "higher_is_better")
sevenDaysTrendIcon(sevenDaysTrend, higherIsBetter) {
return this._iconForTrend(sevenDaysTrend, higherIsBetter);
},
- @computed("thirtyDaysTrend", "higher_is_better")
+ @discourseComputed("thirtyDaysTrend", "higher_is_better")
thirtyDaysTrendIcon(thirtyDaysTrend, higherIsBetter) {
return this._iconForTrend(thirtyDaysTrend, higherIsBetter);
},
- @computed("yesterdayTrend", "higher_is_better")
+ @discourseComputed("yesterdayTrend", "higher_is_better")
yesterdayTrendIcon(yesterdayTrend, higherIsBetter) {
return this._iconForTrend(yesterdayTrend, higherIsBetter);
},
- @computed("prev_period", "currentTotal", "currentAverage", "higher_is_better")
+ @discourseComputed(
+ "prev_period",
+ "currentTotal",
+ "currentAverage",
+ "higher_is_better"
+ )
trend(prev, currentTotal, currentAverage, higherIsBetter) {
const total = this.average ? currentAverage : currentTotal;
return this._computeTrend(prev, total, higherIsBetter);
},
- @computed("prev30Days", "lastThirtyDaysCount", "higher_is_better")
+ @discourseComputed("prev30Days", "lastThirtyDaysCount", "higher_is_better")
thirtyDaysTrend(prev30Days, lastThirtyDaysCount, higherIsBetter) {
return this._computeTrend(prev30Days, lastThirtyDaysCount, higherIsBetter);
},
- @computed("type")
+ @discourseComputed("type")
method(type) {
if (type === "time_to_first_response") {
return "average";
@@ -195,7 +200,7 @@ const Report = Discourse.Model.extend({
}
},
- @computed("prev_period", "currentTotal", "currentAverage")
+ @discourseComputed("prev_period", "currentTotal", "currentAverage")
trendTitle(prev, currentTotal, currentAverage) {
let current = this.average ? currentAverage : currentTotal;
let percent = this.percentChangeString(prev, current);
@@ -228,12 +233,12 @@ const Report = Discourse.Model.extend({
return title;
},
- @computed("yesterdayCount")
+ @discourseComputed("yesterdayCount")
yesterdayCountTitle(yesterdayCount) {
return this.changeTitle(this.valueAt(2), yesterdayCount, "two days ago");
},
- @computed("lastSevenDaysCount")
+ @discourseComputed("lastSevenDaysCount")
sevenDaysCountTitle(lastSevenDaysCount) {
return this.changeTitle(
this.valueFor(8, 14),
@@ -242,7 +247,7 @@ const Report = Discourse.Model.extend({
);
},
- @computed("prev30Days", "lastThirtyDaysCount")
+ @discourseComputed("prev30Days", "lastThirtyDaysCount")
thirtyDaysCountTitle(prev30Days, lastThirtyDaysCount) {
return this.changeTitle(
prev30Days,
@@ -251,18 +256,18 @@ const Report = Discourse.Model.extend({
);
},
- @computed("data")
+ @discourseComputed("data")
sortedData(data) {
return this.xAxisIsDate ? data.toArray().reverse() : data.toArray();
},
- @computed("data")
+ @discourseComputed("data")
xAxisIsDate() {
if (!this.data[0]) return false;
return this.data && this.data[0].x.match(/\d{4}-\d{1,2}-\d{1,2}/);
},
- @computed("labels")
+ @discourseComputed("labels")
computedLabels(labels) {
return labels.map(label => {
const type = label.type || "string";
diff --git a/app/assets/javascripts/admin/models/screened-email.js.es6 b/app/assets/javascripts/admin/models/screened-email.js.es6
index 6eb014c484..0d20f2c7d1 100644
--- a/app/assets/javascripts/admin/models/screened-email.js.es6
+++ b/app/assets/javascripts/admin/models/screened-email.js.es6
@@ -1,8 +1,8 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { ajax } from "discourse/lib/ajax";
-import computed from "ember-addons/ember-computed-decorators";
const ScreenedEmail = Discourse.Model.extend({
- @computed("action")
+ @discourseComputed("action")
actionName(action) {
return I18n.t("admin.logs.screened_actions." + action);
},
diff --git a/app/assets/javascripts/admin/models/screened-ip-address.js.es6 b/app/assets/javascripts/admin/models/screened-ip-address.js.es6
index 0449a666f3..e2b60a2108 100644
--- a/app/assets/javascripts/admin/models/screened-ip-address.js.es6
+++ b/app/assets/javascripts/admin/models/screened-ip-address.js.es6
@@ -1,16 +1,16 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { equal } from "@ember/object/computed";
import { ajax } from "discourse/lib/ajax";
-import computed from "ember-addons/ember-computed-decorators";
const ScreenedIpAddress = Discourse.Model.extend({
- @computed("action_name")
+ @discourseComputed("action_name")
actionName(actionName) {
return I18n.t(`admin.logs.screened_ips.actions.${actionName}`);
},
isBlocked: equal("action_name", "block"),
- @computed("ip_address")
+ @discourseComputed("ip_address")
isRange(ipAddress) {
return ipAddress.indexOf("/") > 0;
},
diff --git a/app/assets/javascripts/admin/models/screened-url.js.es6 b/app/assets/javascripts/admin/models/screened-url.js.es6
index b899c61962..515ef6e82c 100644
--- a/app/assets/javascripts/admin/models/screened-url.js.es6
+++ b/app/assets/javascripts/admin/models/screened-url.js.es6
@@ -1,8 +1,8 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { ajax } from "discourse/lib/ajax";
-import computed from "ember-addons/ember-computed-decorators";
const ScreenedUrl = Discourse.Model.extend({
- @computed("action")
+ @discourseComputed("action")
actionName(action) {
return I18n.t("admin.logs.screened_actions." + action);
}
diff --git a/app/assets/javascripts/admin/models/staff-action-log.js.es6 b/app/assets/javascripts/admin/models/staff-action-log.js.es6
index 2d63019dda..45330b13fc 100644
--- a/app/assets/javascripts/admin/models/staff-action-log.js.es6
+++ b/app/assets/javascripts/admin/models/staff-action-log.js.es6
@@ -1,4 +1,4 @@
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
import { ajax } from "discourse/lib/ajax";
import AdminUser from "admin/models/admin-user";
import { escapeExpression } from "discourse/lib/utilities";
@@ -13,12 +13,12 @@ function format(label, value, escape = true) {
const StaffActionLog = RestModel.extend({
showFullDetails: false,
- @computed("action_name")
+ @discourseComputed("action_name")
actionName(actionName) {
return I18n.t(`admin.logs.staff_actions.actions.${actionName}`);
},
- @computed(
+ @discourseComputed(
"email",
"ip_address",
"topic_id",
@@ -69,12 +69,12 @@ const StaffActionLog = RestModel.extend({
return formatted.length > 0 ? formatted + "
" : "";
},
- @computed("details")
+ @discourseComputed("details")
useModalForDetails(details) {
return details && details.length > 100;
},
- @computed("action_name")
+ @discourseComputed("action_name")
useCustomModalForDetails(actionName) {
return ["change_theme", "delete_theme"].includes(actionName);
}
diff --git a/app/assets/javascripts/admin/models/theme.js.es6 b/app/assets/javascripts/admin/models/theme.js.es6
index 4ea3d3e216..94ccf5f9b0 100644
--- a/app/assets/javascripts/admin/models/theme.js.es6
+++ b/app/assets/javascripts/admin/models/theme.js.es6
@@ -2,7 +2,7 @@ import { get } from "@ember/object";
import { isEmpty } from "@ember/utils";
import { or, gt } from "@ember/object/computed";
import RestModel from "discourse/models/rest";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import { popupAjaxError } from "discourse/lib/ajax-error";
import { ajax } from "discourse/lib/ajax";
import { escapeExpression } from "discourse/lib/utilities";
@@ -20,7 +20,7 @@ const Theme = RestModel.extend({
isPendingUpdates: gt("remote_theme.commits_behind", 0),
hasEditedFields: gt("editedFields.length", 0),
- @computed("theme_fields.[]")
+ @discourseComputed("theme_fields.[]")
targets() {
return [
{ id: 0, name: "common" },
@@ -48,7 +48,7 @@ const Theme = RestModel.extend({
});
},
- @computed("theme_fields.[]")
+ @discourseComputed("theme_fields.[]")
fieldNames() {
const common = [
"scss",
@@ -82,7 +82,11 @@ const Theme = RestModel.extend({
};
},
- @computed("fieldNames", "theme_fields.[]", "theme_fields.@each.error")
+ @discourseComputed(
+ "fieldNames",
+ "theme_fields.[]",
+ "theme_fields.@each.error"
+ )
fields(fieldNames) {
const hash = {};
Object.keys(fieldNames).forEach(target => {
@@ -112,7 +116,7 @@ const Theme = RestModel.extend({
return hash;
},
- @computed("theme_fields")
+ @discourseComputed("theme_fields")
themeFields(fields) {
if (!fields) {
this.set("theme_fields", []);
@@ -128,7 +132,7 @@ const Theme = RestModel.extend({
return hash;
},
- @computed("theme_fields", "theme_fields.[]")
+ @discourseComputed("theme_fields", "theme_fields.[]")
uploads(fields) {
if (!fields) {
return [];
@@ -138,19 +142,19 @@ const Theme = RestModel.extend({
);
},
- @computed("theme_fields", "theme_fields.@each.error")
+ @discourseComputed("theme_fields", "theme_fields.@each.error")
isBroken(fields) {
return fields && fields.any(field => field.error && field.error.length > 0);
},
- @computed("theme_fields.[]")
+ @discourseComputed("theme_fields.[]")
editedFields(fields) {
return fields.filter(
field => !Ember.isBlank(field.value) && field.type_id !== SETTINGS_TYPE_ID
);
},
- @computed("remote_theme.last_error_text")
+ @discourseComputed("remote_theme.last_error_text")
remoteError(errorText) {
if (errorText && errorText.length > 0) {
return errorText;
@@ -241,7 +245,7 @@ const Theme = RestModel.extend({
}
},
- @computed("childThemes.[]")
+ @discourseComputed("childThemes.[]")
child_theme_ids(childThemes) {
if (childThemes) {
return childThemes.map(theme => get(theme, "id"));
@@ -265,7 +269,7 @@ const Theme = RestModel.extend({
return this.saveChanges("child_theme_ids");
},
- @computed("name", "default")
+ @discourseComputed("name", "default")
description: function(name, isDefault) {
if (isDefault) {
return I18n.t("admin.customize.theme.default_name", { name: name });
diff --git a/app/assets/javascripts/admin/models/tl3-requirements.js.es6 b/app/assets/javascripts/admin/models/tl3-requirements.js.es6
index 222c8077d7..966410b41c 100644
--- a/app/assets/javascripts/admin/models/tl3-requirements.js.es6
+++ b/app/assets/javascripts/admin/models/tl3-requirements.js.es6
@@ -1,17 +1,17 @@
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
export default Discourse.Model.extend({
- @computed("days_visited", "time_period")
+ @discourseComputed("days_visited", "time_period")
days_visited_percent(daysVisited, timePeriod) {
return Math.round((daysVisited * 100) / timePeriod);
},
- @computed("min_days_visited", "time_period")
+ @discourseComputed("min_days_visited", "time_period")
min_days_visited_percent(minDaysVisited, timePeriod) {
return Math.round((minDaysVisited * 100) / timePeriod);
},
- @computed(
+ @discourseComputed(
"days_visited",
"min_days_visited",
"num_topics_replied_to",
diff --git a/app/assets/javascripts/admin/models/version-check.js.es6 b/app/assets/javascripts/admin/models/version-check.js.es6
index 2012d0ff08..54ef9844fe 100644
--- a/app/assets/javascripts/admin/models/version-check.js.es6
+++ b/app/assets/javascripts/admin/models/version-check.js.es6
@@ -1,30 +1,30 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { ajax } from "discourse/lib/ajax";
-import computed from "ember-addons/ember-computed-decorators";
const VersionCheck = Discourse.Model.extend({
- @computed("updated_at")
+ @discourseComputed("updated_at")
noCheckPerformed(updatedAt) {
return updatedAt === null;
},
- @computed("missing_versions_count")
+ @discourseComputed("missing_versions_count")
upToDate(missingVersionsCount) {
return missingVersionsCount === 0 || missingVersionsCount === null;
},
- @computed("missing_versions_count")
+ @discourseComputed("missing_versions_count")
behindByOneVersion(missingVersionsCount) {
return missingVersionsCount === 1;
},
- @computed("installed_sha")
+ @discourseComputed("installed_sha")
gitLink(installedSHA) {
if (installedSHA) {
return `https://github.com/discourse/discourse/commits/${installedSHA}`;
}
},
- @computed("installed_sha")
+ @discourseComputed("installed_sha")
shortSha(installedSHA) {
if (installedSHA) {
return installedSHA.substr(0, 10);
diff --git a/app/assets/javascripts/admin/models/web-hook.js.es6 b/app/assets/javascripts/admin/models/web-hook.js.es6
index 84111591fa..df3ac54918 100644
--- a/app/assets/javascripts/admin/models/web-hook.js.es6
+++ b/app/assets/javascripts/admin/models/web-hook.js.es6
@@ -3,9 +3,9 @@ import RestModel from "discourse/models/rest";
import Category from "discourse/models/category";
import Group from "discourse/models/group";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
export default RestModel.extend({
content_type: 1, // json
@@ -16,7 +16,7 @@ export default RestModel.extend({
web_hook_event_types: null,
groupsFilterInName: null,
- @computed("wildcard_web_hook")
+ @discourseComputed("wildcard_web_hook")
webHookType: {
get(wildcard) {
return wildcard ? "wildcard" : "individual";
@@ -26,7 +26,7 @@ export default RestModel.extend({
}
},
- @computed("category_ids")
+ @discourseComputed("category_ids")
categories(categoryIds) {
return Category.findByIds(categoryIds);
},
@@ -49,7 +49,7 @@ export default RestModel.extend({
return Group.findAll({ term: term, ignore_automatic: false });
},
- @computed("wildcard_web_hook", "web_hook_event_types.[]")
+ @discourseComputed("wildcard_web_hook", "web_hook_event_types.[]")
description(isWildcardWebHook, types) {
let desc = "";
diff --git a/app/assets/javascripts/application.js b/app/assets/javascripts/application.js
index 46bf682576..290f920789 100644
--- a/app/assets/javascripts/application.js
+++ b/app/assets/javascripts/application.js
@@ -1,10 +1,9 @@
//= require_tree ./ember-addons/utils
+//= require_tree ./discourse-common
//= require ./ember-addons/decorator-alias
//= require ./ember-addons/macro-alias
-//= require ./ember-addons/ember-computed-decorators
//= require ./ember-addons/fmt
//= require ./polyfills
-//= require_tree ./discourse-common
//= require_tree ./select-kit
//= require ./discourse
//= require ./deprecated
diff --git a/app/assets/javascripts/discourse-common/lib/raw-handlebars.js.es6 b/app/assets/javascripts/discourse-common/lib/raw-handlebars.js.es6
index eed8ec09a0..ca08cfd476 100644
--- a/app/assets/javascripts/discourse-common/lib/raw-handlebars.js.es6
+++ b/app/assets/javascripts/discourse-common/lib/raw-handlebars.js.es6
@@ -1,6 +1,6 @@
// This is a mechanism for quickly rendering templates which is Ember aware
// templates are highly compatible with Ember so you don't need to worry about calling "get"
-// and computed properties function, additionally it uses stringParams like Ember does
+// and discourseComputed properties function, additionally it uses stringParams like Ember does
const RawHandlebars = Handlebars.create();
diff --git a/app/assets/javascripts/ember-addons/ember-computed-decorators.js.es6 b/app/assets/javascripts/discourse-common/utils/decorators.js.es6
similarity index 82%
rename from app/assets/javascripts/ember-addons/ember-computed-decorators.js.es6
rename to app/assets/javascripts/discourse-common/utils/decorators.js.es6
index eaa78d5063..053eefe341 100644
--- a/app/assets/javascripts/ember-addons/ember-computed-decorators.js.es6
+++ b/app/assets/javascripts/discourse-common/utils/decorators.js.es6
@@ -1,9 +1,9 @@
-import handleDescriptor from "./utils/handle-descriptor";
-import isDescriptor from "./utils/is-descriptor";
-import extractValue from "./utils/extract-value";
+import handleDescriptor from "ember-addons/utils/handle-descriptor";
+import isDescriptor from "ember-addons/utils/is-descriptor";
+import extractValue from "ember-addons/utils/extract-value";
-export default function computedDecorator(...params) {
- // determine if user called as @computed('blah', 'blah') or @computed
+export default function discourseComputedDecorator(...params) {
+ // determine if user called as @discourseComputed('blah', 'blah') or @discourseComputed
if (isDescriptor(params[params.length - 1])) {
return handleDescriptor(...arguments);
} else {
@@ -25,7 +25,7 @@ export function readOnly(target, name, desc) {
};
}
-import decoratorAlias from "./decorator-alias";
+import decoratorAlias from "ember-addons/decorator-alias";
export var on = decoratorAlias(Ember.on, "Can not `on` without event names");
export var observes = decoratorAlias(
@@ -33,7 +33,7 @@ export var observes = decoratorAlias(
"Can not `observe` without property names"
);
-import macroAlias from "./macro-alias";
+import macroAlias from "ember-addons/macro-alias";
export var alias = macroAlias(Ember.computed.alias);
export var and = macroAlias(Ember.computed.and);
diff --git a/app/assets/javascripts/discourse-loader.js b/app/assets/javascripts/discourse-loader.js
index cb402832e8..fc3a0613f8 100644
--- a/app/assets/javascripts/discourse-loader.js
+++ b/app/assets/javascripts/discourse-loader.js
@@ -3,6 +3,10 @@ var define, requirejs;
(function() {
// In future versions of ember we don't need this
var EMBER_MODULES = {};
+ var ALIASES = {
+ "ember-addons/ember-computed-decorators":
+ "discourse-common/utils/decorators"
+ };
if (typeof Ember !== "undefined") {
EMBER_MODULES = {
jquery: { default: $ },
@@ -76,7 +80,7 @@ var define, requirejs;
"@ember/utils": {
isEmpty: Ember.isEmpty
},
- "rsvp": {
+ rsvp: {
Promise: Ember.RSVP.Promise,
hash: Ember.RSVP.hash,
all: Ember.RSVP.all
@@ -213,6 +217,7 @@ var define, requirejs;
}
function requireFrom(name, origin) {
+ name = checkForAlias(name);
var mod = EMBER_MODULES[name] || registry[name];
if (!mod) {
throw new Error(
@@ -226,6 +231,10 @@ var define, requirejs;
throw new Error("Could not find module " + name);
}
+ function checkForAlias(name) {
+ return ALIASES[name] ? ALIASES[name] : name;
+ }
+
requirejs = require = function(name) {
if (EMBER_MODULES[name]) {
return EMBER_MODULES[name];
diff --git a/app/assets/javascripts/discourse.js.es6 b/app/assets/javascripts/discourse.js.es6
index d993e3b983..2f45653ed1 100644
--- a/app/assets/javascripts/discourse.js.es6
+++ b/app/assets/javascripts/discourse.js.es6
@@ -1,9 +1,9 @@
/*global Mousetrap:true*/
import { buildResolver } from "discourse-common/resolver";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import FocusEvent from "discourse-common/mixins/focus-event";
const _pluginCallbacks = [];
@@ -66,7 +66,7 @@ const Discourse = Ember.Application.extend(FocusEvent, {
document.title = title;
},
- @computed("contextCount", "notificationCount")
+ @discourseComputed("contextCount", "notificationCount")
displayCount() {
return Discourse.User.current() &&
Discourse.User.currentProp("title_count_mode") === "notifications"
@@ -179,7 +179,7 @@ const Discourse = Ember.Application.extend(FocusEvent, {
});
},
- @computed("currentAssetVersion", "desiredAssetVersion")
+ @discourseComputed("currentAssetVersion", "desiredAssetVersion")
requiresRefresh(currentAssetVersion, desiredAssetVersion) {
return desiredAssetVersion && currentAssetVersion !== desiredAssetVersion;
},
diff --git a/app/assets/javascripts/discourse/components/add-category-tag-classes.js.es6 b/app/assets/javascripts/discourse/components/add-category-tag-classes.js.es6
index d4a75e6ebe..50d93f3a95 100644
--- a/app/assets/javascripts/discourse/components/add-category-tag-classes.js.es6
+++ b/app/assets/javascripts/discourse/components/add-category-tag-classes.js.es6
@@ -1,6 +1,6 @@
import { scheduleOnce } from "@ember/runloop";
import Component from "@ember/component";
-import { observes } from "ember-addons/ember-computed-decorators";
+import { observes } from "discourse-common/utils/decorators";
export default Component.extend({
_slug: null,
diff --git a/app/assets/javascripts/discourse/components/avatar-flair.js.es6 b/app/assets/javascripts/discourse/components/avatar-flair.js.es6
index 4d0bd2e131..f25d596ba7 100644
--- a/app/assets/javascripts/discourse/components/avatar-flair.js.es6
+++ b/app/assets/javascripts/discourse/components/avatar-flair.js.es6
@@ -1,4 +1,4 @@
-import { observes } from "ember-addons/ember-computed-decorators";
+import { observes } from "discourse-common/utils/decorators";
import MountWidget from "discourse/components/mount-widget";
export default MountWidget.extend({
diff --git a/app/assets/javascripts/discourse/components/avatar-uploader.js.es6 b/app/assets/javascripts/discourse/components/avatar-uploader.js.es6
index 3350ddff31..f9144abe59 100644
--- a/app/assets/javascripts/discourse/components/avatar-uploader.js.es6
+++ b/app/assets/javascripts/discourse/components/avatar-uploader.js.es6
@@ -1,5 +1,5 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import UploadMixin from "discourse/mixins/upload";
export default Component.extend(UploadMixin, {
@@ -21,7 +21,7 @@ export default Component.extend(UploadMixin, {
this.done();
},
- @computed("user_id")
+ @discourseComputed("user_id")
data(user_id) {
return { user_id };
}
diff --git a/app/assets/javascripts/discourse/components/backup-codes.js.es6 b/app/assets/javascripts/discourse/components/backup-codes.js.es6
index 5e80cc3e3b..1109c4cde6 100644
--- a/app/assets/javascripts/discourse/components/backup-codes.js.es6
+++ b/app/assets/javascripts/discourse/components/backup-codes.js.es6
@@ -1,5 +1,5 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
// https://developer.mozilla.org/en-US/docs/Web/API/WindowBase64/Base64_encoding_and_decoding
function b64EncodeUnicode(str) {
@@ -32,10 +32,10 @@ export default Component.extend({
}
},
- @computed("formattedBackupCodes")
+ @discourseComputed("formattedBackupCodes")
base64BackupCode: b64EncodeUnicode,
- @computed("backupCodes")
+ @discourseComputed("backupCodes")
formattedBackupCodes(backupCodes) {
if (!backupCodes) return null;
diff --git a/app/assets/javascripts/discourse/components/backup-uploader.js.es6 b/app/assets/javascripts/discourse/components/backup-uploader.js.es6
index e75470439d..331684ee25 100644
--- a/app/assets/javascripts/discourse/components/backup-uploader.js.es6
+++ b/app/assets/javascripts/discourse/components/backup-uploader.js.es6
@@ -1,14 +1,14 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
import { ajax } from "discourse/lib/ajax";
import { popupAjaxError } from "discourse/lib/ajax-error";
-import computed from "ember-addons/ember-computed-decorators";
import UploadMixin from "discourse/mixins/upload";
import { on } from "@ember/object/evented";
export default Component.extend(UploadMixin, {
tagName: "span",
- @computed("uploading", "uploadProgress")
+ @discourseComputed("uploading", "uploadProgress")
uploadButtonText(uploading, progress) {
return uploading
? I18n.t("admin.backups.upload.uploading_progress", { progress })
diff --git a/app/assets/javascripts/discourse/components/badge-button.js.es6 b/app/assets/javascripts/discourse/components/badge-button.js.es6
index dde5bfb804..9204a1cf7b 100644
--- a/app/assets/javascripts/discourse/components/badge-button.js.es6
+++ b/app/assets/javascripts/discourse/components/badge-button.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { alias } from "@ember/object/computed";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
tagName: "span",
@@ -10,7 +10,7 @@ export default Component.extend({
"badge.enabled::disabled"
],
- @computed("badge.description")
+ @discourseComputed("badge.description")
title(badgeDescription) {
return $("" + badgeDescription + "
").text();
},
diff --git a/app/assets/javascripts/discourse/components/badge-card.js.es6 b/app/assets/javascripts/discourse/components/badge-card.js.es6
index f9380b11eb..e0b192895b 100644
--- a/app/assets/javascripts/discourse/components/badge-card.js.es6
+++ b/app/assets/javascripts/discourse/components/badge-card.js.es6
@@ -1,17 +1,17 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import { sanitize, emojiUnescape } from "discourse/lib/text";
export default Component.extend({
size: "medium",
classNameBindings: [":badge-card", "size", "badge.slug"],
- @computed("badge.url", "filterUser", "username")
+ @discourseComputed("badge.url", "filterUser", "username")
url(badgeUrl, filterUser, username) {
return filterUser ? `${badgeUrl}?username=${username}` : badgeUrl;
},
- @computed("count", "badge.grant_count")
+ @discourseComputed("count", "badge.grant_count")
displayCount(count, grantCount) {
if (count == null) {
return grantCount;
@@ -21,7 +21,7 @@ export default Component.extend({
}
},
- @computed("size")
+ @discourseComputed("size")
summary(size) {
if (size === "large") {
const longDescription = this.get("badge.long_description");
diff --git a/app/assets/javascripts/discourse/components/badge-selector.js.es6 b/app/assets/javascripts/discourse/components/badge-selector.js.es6
index 94c08c95ca..3e02b0740e 100644
--- a/app/assets/javascripts/discourse/components/badge-selector.js.es6
+++ b/app/assets/javascripts/discourse/components/badge-selector.js.es6
@@ -2,13 +2,13 @@ import Component from "@ember/component";
import {
on,
observes,
- default as computed
-} from "ember-addons/ember-computed-decorators";
+ default as discourseComputed
+} from "discourse-common/utils/decorators";
import { findRawTemplate } from "discourse/lib/raw-templates";
const { makeArray } = Ember;
export default Component.extend({
- @computed("placeholderKey")
+ @discourseComputed("placeholderKey")
placeholder(placeholderKey) {
return placeholderKey ? I18n.t(placeholderKey) : "";
},
diff --git a/app/assets/javascripts/discourse/components/badge-title.js.es6 b/app/assets/javascripts/discourse/components/badge-title.js.es6
index d7fd08c318..7f1292e2e7 100644
--- a/app/assets/javascripts/discourse/components/badge-title.js.es6
+++ b/app/assets/javascripts/discourse/components/badge-title.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
import { ajax } from "discourse/lib/ajax";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
classNames: ["badge-title"],
@@ -8,7 +8,7 @@ export default Component.extend({
saved: false,
saving: false,
- @computed("selectableUserBadges", "selectedUserBadgeId")
+ @discourseComputed("selectableUserBadges", "selectedUserBadgeId")
selectedUserBadge(selectableUserBadges, selectedUserBadgeId) {
return selectableUserBadges.findBy("id", parseInt(selectedUserBadgeId));
},
diff --git a/app/assets/javascripts/discourse/components/basic-topic-list.js.es6 b/app/assets/javascripts/discourse/components/basic-topic-list.js.es6
index 64942198ed..c9ce38c339 100644
--- a/app/assets/javascripts/discourse/components/basic-topic-list.js.es6
+++ b/app/assets/javascripts/discourse/components/basic-topic-list.js.es6
@@ -1,12 +1,12 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { alias, not } from "@ember/object/computed";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
loadingMore: alias("topicList.loadingMore"),
loading: not("loaded"),
- @computed("topicList.loaded")
+ @discourseComputed("topicList.loaded")
loaded() {
var topicList = this.topicList;
if (topicList) {
@@ -73,7 +73,7 @@ export default Component.extend({
});
},
- @computed("topics")
+ @discourseComputed("topics")
showUnreadIndicator(topics) {
return topics.some(
topic => typeof topic.unread_by_group_member !== "undefined"
diff --git a/app/assets/javascripts/discourse/components/bread-crumbs.js.es6 b/app/assets/javascripts/discourse/components/bread-crumbs.js.es6
index e420fcce7c..c1e013cac9 100644
--- a/app/assets/javascripts/discourse/components/bread-crumbs.js.es6
+++ b/app/assets/javascripts/discourse/components/bread-crumbs.js.es6
@@ -1,6 +1,6 @@
import { alias, filter, or } from "@ember/object/computed";
import Component from "@ember/component";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
// A breadcrumb including category drop downs
export default Component.extend({
@@ -21,7 +21,7 @@ export default Component.extend({
return !c.get("parentCategory");
}),
- @computed("parentCategories")
+ @discourseComputed("parentCategories")
parentCategoriesSorted(parentCategories) {
if (this.siteSettings.fixed_category_positions) {
return parentCategories;
@@ -30,20 +30,20 @@ export default Component.extend({
return parentCategories.sortBy("totalTopicCount").reverse();
},
- @computed("category")
+ @discourseComputed("category")
hidden(category) {
return this.site.mobileView && !category;
},
firstCategory: or("{parentCategory,category}"),
- @computed("category", "parentCategory")
+ @discourseComputed("category", "parentCategory")
secondCategory(category, parentCategory) {
if (parentCategory) return category;
return null;
},
- @computed("firstCategory", "hideSubcategories")
+ @discourseComputed("firstCategory", "hideSubcategories")
childCategories(firstCategory, hideSubcategories) {
if (hideSubcategories) {
return [];
diff --git a/app/assets/javascripts/discourse/components/categories-boxes-topic.js.es6 b/app/assets/javascripts/discourse/components/categories-boxes-topic.js.es6
index b5536923ec..ed2af66cad 100644
--- a/app/assets/javascripts/discourse/components/categories-boxes-topic.js.es6
+++ b/app/assets/javascripts/discourse/components/categories-boxes-topic.js.es6
@@ -1,10 +1,10 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
tagName: "li",
- @computed("topic.pinned", "topic.closed", "topic.archived")
+ @discourseComputed("topic.pinned", "topic.closed", "topic.archived")
topicStatusIcon(pinned, closed, archived) {
if (pinned) {
return "thumbtack";
diff --git a/app/assets/javascripts/discourse/components/categories-boxes-with-topics.js.es6 b/app/assets/javascripts/discourse/components/categories-boxes-with-topics.js.es6
index 40b16d03fa..ffd3a77ca8 100644
--- a/app/assets/javascripts/discourse/components/categories-boxes-with-topics.js.es6
+++ b/app/assets/javascripts/discourse/components/categories-boxes-with-topics.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { isEmpty } from "@ember/utils";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
tagName: "section",
@@ -9,7 +9,7 @@ export default Component.extend({
"anyLogos:with-logos:no-logos"
],
- @computed("categories.[].uploaded_logo.url")
+ @discourseComputed("categories.[].uploaded_logo.url")
anyLogos() {
return this.categories.any(c => {
return !isEmpty(c.get("uploaded_logo.url"));
diff --git a/app/assets/javascripts/discourse/components/categories-boxes.js.es6 b/app/assets/javascripts/discourse/components/categories-boxes.js.es6
index 11b76ed1d4..b4dcfde7e8 100644
--- a/app/assets/javascripts/discourse/components/categories-boxes.js.es6
+++ b/app/assets/javascripts/discourse/components/categories-boxes.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { isEmpty } from "@ember/utils";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import DiscourseURL from "discourse/lib/url";
export default Component.extend({
@@ -11,12 +11,12 @@ export default Component.extend({
"hasSubcategories:with-subcategories"
],
- @computed("categories.[].uploaded_logo.url")
+ @discourseComputed("categories.[].uploaded_logo.url")
anyLogos() {
return this.categories.any(c => !isEmpty(c.get("uploaded_logo.url")));
},
- @computed("categories.[].subcategories")
+ @discourseComputed("categories.[].subcategories")
hasSubcategories() {
return this.categories.any(c => !isEmpty(c.get("subcategories")));
},
diff --git a/app/assets/javascripts/discourse/components/cdn-img.js.es6 b/app/assets/javascripts/discourse/components/cdn-img.js.es6
index 338c71a1ee..a5c7a2642a 100644
--- a/app/assets/javascripts/discourse/components/cdn-img.js.es6
+++ b/app/assets/javascripts/discourse/components/cdn-img.js.es6
@@ -1,16 +1,16 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import { htmlSafe } from "@ember/template";
export default Component.extend({
tagName: "",
- @computed("src")
+ @discourseComputed("src")
cdnSrc(src) {
return Discourse.getURLWithCDN(src);
},
- @computed("width", "height")
+ @discourseComputed("width", "height")
style(width, height) {
if (width && height) {
return htmlSafe(`--aspect-ratio: ${width / height};`);
diff --git a/app/assets/javascripts/discourse/components/choose-message.js.es6 b/app/assets/javascripts/discourse/components/choose-message.js.es6
index cb6c251355..e47618dbef 100644
--- a/app/assets/javascripts/discourse/components/choose-message.js.es6
+++ b/app/assets/javascripts/discourse/components/choose-message.js.es6
@@ -4,7 +4,7 @@ import { next } from "@ember/runloop";
import Component from "@ember/component";
import debounce from "discourse/lib/debounce";
import { searchForTerm } from "discourse/lib/search";
-import { observes } from "ember-addons/ember-computed-decorators";
+import { observes } from "discourse-common/utils/decorators";
export default Component.extend({
loading: null,
diff --git a/app/assets/javascripts/discourse/components/choose-topic.js.es6 b/app/assets/javascripts/discourse/components/choose-topic.js.es6
index f2d4792414..557b30d9a0 100644
--- a/app/assets/javascripts/discourse/components/choose-topic.js.es6
+++ b/app/assets/javascripts/discourse/components/choose-topic.js.es6
@@ -3,7 +3,7 @@ import { next } from "@ember/runloop";
import Component from "@ember/component";
import debounce from "discourse/lib/debounce";
import { searchForTerm } from "discourse/lib/search";
-import { observes } from "ember-addons/ember-computed-decorators";
+import { observes } from "discourse-common/utils/decorators";
export default Component.extend({
loading: null,
diff --git a/app/assets/javascripts/discourse/components/color-picker-choice.js.es6 b/app/assets/javascripts/discourse/components/color-picker-choice.js.es6
index a1933193d2..a384ca1920 100644
--- a/app/assets/javascripts/discourse/components/color-picker-choice.js.es6
+++ b/app/assets/javascripts/discourse/components/color-picker-choice.js.es6
@@ -1,22 +1,22 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
tagName: "button",
attributeBindings: ["style", "title"],
classNameBindings: [":colorpicker", "isUsed:used-color:unused-color"],
- @computed("color", "usedColors")
+ @discourseComputed("color", "usedColors")
isUsed(color, usedColors) {
return (usedColors || []).indexOf(color.toUpperCase()) >= 0;
},
- @computed("isUsed")
+ @discourseComputed("isUsed")
title(isUsed) {
return isUsed ? I18n.t("category.already_used") : null;
},
- @computed("color")
+ @discourseComputed("color")
style(color) {
return `background-color: #${color};`.htmlSafe();
},
diff --git a/app/assets/javascripts/discourse/components/composer-action-title.js.es6 b/app/assets/javascripts/discourse/components/composer-action-title.js.es6
index 8e4fd6c9f7..996b409f6b 100644
--- a/app/assets/javascripts/discourse/components/composer-action-title.js.es6
+++ b/app/assets/javascripts/discourse/components/composer-action-title.js.es6
@@ -1,6 +1,6 @@
import { alias, equal } from "@ember/object/computed";
import Component from "@ember/component";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import {
PRIVATE_MESSAGE,
CREATE_TOPIC,
@@ -24,7 +24,7 @@ export default Component.extend({
action: alias("model.action"),
isEditing: equal("action", EDIT),
- @computed("options", "action")
+ @discourseComputed("options", "action")
actionTitle(opts, action) {
if (TITLES[action]) {
return I18n.t(TITLES[action]);
diff --git a/app/assets/javascripts/discourse/components/composer-body.js.es6 b/app/assets/javascripts/discourse/components/composer-body.js.es6
index f265917279..f2a6ae3bc8 100644
--- a/app/assets/javascripts/discourse/components/composer-body.js.es6
+++ b/app/assets/javascripts/discourse/components/composer-body.js.es6
@@ -5,9 +5,9 @@ import { scheduleOnce } from "@ember/runloop";
import { later } from "@ember/runloop";
import Component from "@ember/component";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import Composer from "discourse/models/composer";
import afterTransition from "discourse/lib/after-transition";
import positioningWorkaround from "discourse/lib/safari-hacks";
@@ -42,12 +42,12 @@ export default Component.extend(KeyEnterEscape, {
"currentUserPrimaryGroupClass"
],
- @computed("currentUser.primary_group_name")
+ @discourseComputed("currentUser.primary_group_name")
currentUserPrimaryGroupClass(primaryGroupName) {
return primaryGroupName && `group-${primaryGroupName}`;
},
- @computed("composer.composeState")
+ @discourseComputed("composer.composeState")
composeState(composeState) {
return composeState || Composer.CLOSED;
},
diff --git a/app/assets/javascripts/discourse/components/composer-editor.js.es6 b/app/assets/javascripts/discourse/components/composer-editor.js.es6
index d1aa32d046..75f8edd4f0 100644
--- a/app/assets/javascripts/discourse/components/composer-editor.js.es6
+++ b/app/assets/javascripts/discourse/components/composer-editor.js.es6
@@ -6,10 +6,10 @@ import { later } from "@ember/runloop";
import Component from "@ember/component";
import userSearch from "discourse/lib/user-search";
import {
- default as computed,
+ default as discourseComputed,
observes,
on
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import {
linkSeenMentions,
fetchUnseenMentions
@@ -43,7 +43,6 @@ import {
cacheShortUploadUrl,
resolveAllShortUrls
} from "pretty-text/upload-short-url";
-
import {
INLINE_ONEBOX_LOADING_CSS_CLASS,
INLINE_ONEBOX_CSS_CLASS
@@ -69,7 +68,7 @@ export default Component.extend({
scrollMap: null,
uploadFilenamePlaceholder: null,
- @computed("uploadFilenamePlaceholder")
+ @discourseComputed("uploadFilenamePlaceholder")
uploadPlaceholder(uploadFilenamePlaceholder) {
const clipboard = I18n.t("clipboard");
const filename = uploadFilenamePlaceholder
@@ -78,7 +77,7 @@ export default Component.extend({
return `[${I18n.t("uploading_filename", { filename })}]() `;
},
- @computed("composer.requiredCategoryMissing")
+ @discourseComputed("composer.requiredCategoryMissing")
replyPlaceholder(requiredCategoryMissing) {
if (requiredCategoryMissing) {
return "composer.reply_placeholder_choose_category";
@@ -90,14 +89,14 @@ export default Component.extend({
}
},
- @computed
+ @discourseComputed
showLink() {
return (
this.currentUser && this.currentUser.get("link_posting_access") !== "none"
);
},
- @computed("composer.requiredCategoryMissing", "composer.replyLength")
+ @discourseComputed("composer.requiredCategoryMissing", "composer.replyLength")
disableTextarea(requiredCategoryMissing, replyLength) {
return requiredCategoryMissing && replyLength === 0;
},
@@ -123,7 +122,7 @@ export default Component.extend({
}
},
- @computed
+ @discourseComputed
markdownOptions() {
return {
previewing: true,
@@ -214,7 +213,7 @@ export default Component.extend({
this.appEvents.trigger("composer:will-open");
},
- @computed(
+ @discourseComputed(
"composer.reply",
"composer.replyLength",
"composer.missingReplyCharacters",
diff --git a/app/assets/javascripts/discourse/components/composer-message.js.es6 b/app/assets/javascripts/discourse/components/composer-message.js.es6
index 6cb98b8018..ce42d201c9 100644
--- a/app/assets/javascripts/discourse/components/composer-message.js.es6
+++ b/app/assets/javascripts/discourse/components/composer-message.js.es6
@@ -1,11 +1,11 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import { getOwner } from "discourse-common/lib/get-owner";
export default Component.extend({
classNameBindings: [":composer-popup", ":hidden", "message.extraClass"],
- @computed("message.templateName")
+ @discourseComputed("message.templateName")
layout(templateName) {
return getOwner(this).lookup(`template:composer/${templateName}`);
},
diff --git a/app/assets/javascripts/discourse/components/composer-title.js.es6 b/app/assets/javascripts/discourse/components/composer-title.js.es6
index ecbe5216bc..da012442f7 100644
--- a/app/assets/javascripts/discourse/components/composer-title.js.es6
+++ b/app/assets/javascripts/discourse/components/composer-title.js.es6
@@ -4,9 +4,9 @@ import { debounce } from "@ember/runloop";
import { schedule } from "@ember/runloop";
import Component from "@ember/component";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import InputValidation from "discourse/models/input-validation";
import { load } from "pretty-text/oneboxer";
import { lookupCache } from "pretty-text/oneboxer-cache";
@@ -34,7 +34,7 @@ export default Component.extend({
}
},
- @computed(
+ @discourseComputed(
"composer.titleLength",
"composer.missingTitleCharacters",
"composer.minimumTitleLength",
@@ -68,7 +68,7 @@ export default Component.extend({
}
},
- @computed("watchForLink")
+ @discourseComputed("watchForLink")
titleMaxLength() {
// maxLength gets in the way of pasting long links, so don't use it if featured links are allowed.
// Validation will display a message if titles are too long.
@@ -182,7 +182,7 @@ export default Component.extend({
}
},
- @computed("composer.title", "composer.titleLength")
+ @discourseComputed("composer.title", "composer.titleLength")
isAbsoluteUrl(title, titleLength) {
return (
titleLength > 0 &&
diff --git a/app/assets/javascripts/discourse/components/composer-toggles.js.es6 b/app/assets/javascripts/discourse/components/composer-toggles.js.es6
index 9f0547d641..e08e50fa3f 100644
--- a/app/assets/javascripts/discourse/components/composer-toggles.js.es6
+++ b/app/assets/javascripts/discourse/components/composer-toggles.js.es6
@@ -1,17 +1,17 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
tagName: "",
- @computed("composeState")
+ @discourseComputed("composeState")
toggleTitle(composeState) {
return composeState === "draft" || composeState === "saving"
? "composer.abandon"
: "composer.collapse";
},
- @computed("composeState")
+ @discourseComputed("composeState")
fullscreenTitle(composeState) {
return composeState === "draft"
? "composer.open"
@@ -20,14 +20,14 @@ export default Component.extend({
: "composer.enter_fullscreen";
},
- @computed("composeState")
+ @discourseComputed("composeState")
toggleIcon(composeState) {
return composeState === "draft" || composeState === "saving"
? "times"
: "chevron-down";
},
- @computed("composeState")
+ @discourseComputed("composeState")
fullscreenIcon(composeState) {
return composeState === "draft"
? "chevron-up"
diff --git a/app/assets/javascripts/discourse/components/composer-user-selector.js.es6 b/app/assets/javascripts/discourse/components/composer-user-selector.js.es6
index 3e9aa03784..14ca7e3556 100644
--- a/app/assets/javascripts/discourse/components/composer-user-selector.js.es6
+++ b/app/assets/javascripts/discourse/components/composer-user-selector.js.es6
@@ -1,9 +1,9 @@
import { schedule } from "@ember/runloop";
import Component from "@ember/component";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
export default Component.extend({
showSelector: true,
@@ -58,17 +58,17 @@ export default Component.extend({
}
},
- @computed("usernames")
+ @discourseComputed("usernames")
splitUsernames(usernames) {
return usernames.split(",");
},
- @computed("splitUsernames", "defaultUsernameCount")
+ @discourseComputed("splitUsernames", "defaultUsernameCount")
limitedUsernames(splitUsernames, count) {
return splitUsernames.slice(0, count).join(", ");
},
- @computed("splitUsernames", "defaultUsernameCount")
+ @discourseComputed("splitUsernames", "defaultUsernameCount")
hiddenUsersCount(splitUsernames, count) {
return `${splitUsernames.length - count} ${I18n.t("more")}`;
},
diff --git a/app/assets/javascripts/discourse/components/conditional-loading-spinner.js.es6 b/app/assets/javascripts/discourse/components/conditional-loading-spinner.js.es6
index 1c6e37ec03..c98075275f 100644
--- a/app/assets/javascripts/discourse/components/conditional-loading-spinner.js.es6
+++ b/app/assets/javascripts/discourse/components/conditional-loading-spinner.js.es6
@@ -1,5 +1,5 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
classNameBindings: [
@@ -8,7 +8,7 @@ export default Component.extend({
"condition:visible"
],
- @computed("size")
+ @discourseComputed("size")
containerClass(size) {
return size === "small" ? "inline-spinner" : undefined;
}
diff --git a/app/assets/javascripts/discourse/components/create-topics-notice.js.es6 b/app/assets/javascripts/discourse/components/create-topics-notice.js.es6
index 96c29f9081..5622cfab94 100644
--- a/app/assets/javascripts/discourse/components/create-topics-notice.js.es6
+++ b/app/assets/javascripts/discourse/components/create-topics-notice.js.es6
@@ -1,7 +1,7 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { alias } from "@ember/object/computed";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
-import { observes } from "ember-addons/ember-computed-decorators";
+import { observes } from "discourse-common/utils/decorators";
import LivePostCounts from "discourse/models/live-post-counts";
export default Component.extend({
@@ -36,7 +36,7 @@ export default Component.extend({
}
},
- @computed()
+ @discourseComputed()
shouldSee() {
const user = this.currentUser;
return (
@@ -47,7 +47,12 @@ export default Component.extend({
);
},
- @computed("enabled", "shouldSee", "publicTopicCount", "publicPostCount")
+ @discourseComputed(
+ "enabled",
+ "shouldSee",
+ "publicTopicCount",
+ "publicPostCount"
+ )
hidden() {
return (
!this.enabled ||
@@ -57,7 +62,7 @@ export default Component.extend({
);
},
- @computed(
+ @discourseComputed(
"publicTopicCount",
"publicPostCount",
"topicTrackingState.incomingCount"
diff --git a/app/assets/javascripts/discourse/components/csv-uploader.js.es6 b/app/assets/javascripts/discourse/components/csv-uploader.js.es6
index 6fa3792d36..b3bb4e8d1f 100644
--- a/app/assets/javascripts/discourse/components/csv-uploader.js.es6
+++ b/app/assets/javascripts/discourse/components/csv-uploader.js.es6
@@ -1,5 +1,5 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import UploadMixin from "discourse/mixins/upload";
import { on } from "@ember/object/evented";
@@ -12,14 +12,14 @@ export default Component.extend(UploadMixin, {
return { csvOnly: true };
},
- @computed("uploading")
+ @discourseComputed("uploading")
uploadButtonText(uploading) {
return uploading
? I18n.t("uploading")
: I18n.t("user.invited.bulk_invite.text");
},
- @computed("uploading")
+ @discourseComputed("uploading")
uploadButtonDisabled(uploading) {
// https://github.com/emberjs/ember.js/issues/10976#issuecomment-132417731
return uploading ? true : null;
diff --git a/app/assets/javascripts/discourse/components/d-button.js.es6 b/app/assets/javascripts/discourse/components/d-button.js.es6
index 130e4ae458..1d0c9d04f8 100644
--- a/app/assets/javascripts/discourse/components/d-button.js.es6
+++ b/app/assets/javascripts/discourse/components/d-button.js.es6
@@ -1,6 +1,6 @@
import { notEmpty, empty, equal } from "@ember/object/computed";
import Component from "@ember/component";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import DiscourseURL from "discourse/lib/url";
export default Component.extend({
@@ -26,7 +26,7 @@ export default Component.extend({
btnLink: equal("display", "link"),
- @computed("icon", "translatedLabel")
+ @discourseComputed("icon", "translatedLabel")
btnType(icon, translatedLabel) {
if (icon) {
return translatedLabel ? "btn-icon-text" : "btn-icon";
@@ -37,7 +37,7 @@ export default Component.extend({
noText: empty("translatedLabel"),
- @computed("title")
+ @discourseComputed("title")
translatedTitle: {
get() {
if (this._translatedTitle) return this._translatedTitle;
@@ -48,7 +48,7 @@ export default Component.extend({
}
},
- @computed("label")
+ @discourseComputed("label")
translatedLabel: {
get() {
if (this._translatedLabel) return this._translatedLabel;
diff --git a/app/assets/javascripts/discourse/components/d-editor.js.es6 b/app/assets/javascripts/discourse/components/d-editor.js.es6
index b60fdf88a3..f102a47886 100644
--- a/app/assets/javascripts/discourse/components/d-editor.js.es6
+++ b/app/assets/javascripts/discourse/components/d-editor.js.es6
@@ -7,10 +7,10 @@ import { inject as service } from "@ember/service";
import Component from "@ember/component";
/*global Mousetrap:true */
import {
- default as computed,
+ default as discourseComputed,
on,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import { categoryHashtagTriggerRule } from "discourse/lib/category-hashtags";
import { search as searchCategoryTag } from "discourse/lib/category-tag-search";
import { cookAsync } from "discourse/lib/text";
@@ -229,7 +229,7 @@ export default Component.extend({
emojiPickerIsActive: false,
emojiStore: service("emoji-store"),
- @computed("placeholder")
+ @discourseComputed("placeholder")
placeholderTranslated(placeholder) {
if (placeholder) return I18n.t(placeholder);
return null;
@@ -327,7 +327,7 @@ export default Component.extend({
$(this.element.querySelector(".d-editor-preview")).off("click.preview");
},
- @computed
+ @discourseComputed
toolbar() {
const toolbar = new Toolbar(
this.getProperties("site", "siteSettings", "showLink")
diff --git a/app/assets/javascripts/discourse/components/d-modal.js.es6 b/app/assets/javascripts/discourse/components/d-modal.js.es6
index 19d4d2264c..300a3e585c 100644
--- a/app/assets/javascripts/discourse/components/d-modal.js.es6
+++ b/app/assets/javascripts/discourse/components/d-modal.js.es6
@@ -1,5 +1,5 @@
import { next } from "@ember/runloop";
-import { on } from "ember-addons/ember-computed-decorators";
+import { on } from "discourse-common/utils/decorators";
import Component from "@ember/component";
export default Component.extend({
diff --git a/app/assets/javascripts/discourse/components/d-navigation.js.es6 b/app/assets/javascripts/discourse/components/d-navigation.js.es6
index b44ad95efd..0fe007a1ed 100644
--- a/app/assets/javascripts/discourse/components/d-navigation.js.es6
+++ b/app/assets/javascripts/discourse/components/d-navigation.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { inject as service } from "@ember/service";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
router: service(),
@@ -8,25 +8,25 @@ export default Component.extend({
tagName: "",
- @computed("category")
+ @discourseComputed("category")
showCategoryNotifications(category) {
return category && this.currentUser;
},
- @computed()
+ @discourseComputed()
categories() {
return this.site.get("categoriesList");
},
- @computed("hasDraft")
+ @discourseComputed("hasDraft")
createTopicLabel(hasDraft) {
return hasDraft ? "topic.open_draft" : "topic.create";
},
- @computed("category.can_edit")
+ @discourseComputed("category.can_edit")
showCategoryEdit: canEdit => canEdit,
- @computed("filterMode", "category", "noSubcategories")
+ @discourseComputed("filterMode", "category", "noSubcategories")
navItems(filterMode, category, noSubcategories) {
// we don't want to show the period in the navigation bar since it's in a dropdown
if (filterMode.indexOf("top/") === 0) {
diff --git a/app/assets/javascripts/discourse/components/date-input.js.es6 b/app/assets/javascripts/discourse/components/date-input.js.es6
index 927be37881..b095781b82 100644
--- a/app/assets/javascripts/discourse/components/date-input.js.es6
+++ b/app/assets/javascripts/discourse/components/date-input.js.es6
@@ -3,16 +3,16 @@ import Component from "@ember/component";
/* global Pikaday:true */
import loadScript from "discourse/lib/load-script";
import {
- default as computed,
+ default as discourseComputed,
on
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
export default Component.extend({
classNames: ["d-date-input"],
date: null,
_picker: null,
- @computed("site.mobileView")
+ @discourseComputed("site.mobileView")
inputType(mobileView) {
return mobileView ? "date" : "text";
},
@@ -92,7 +92,7 @@ export default Component.extend({
this._picker = null;
},
- @computed()
+ @discourseComputed()
placeholder() {
return I18n.t("dates.placeholder");
},
diff --git a/app/assets/javascripts/discourse/components/date-picker.js.es6 b/app/assets/javascripts/discourse/components/date-picker.js.es6
index e9403326bb..8ca644e952 100644
--- a/app/assets/javascripts/discourse/components/date-picker.js.es6
+++ b/app/assets/javascripts/discourse/components/date-picker.js.es6
@@ -3,9 +3,9 @@ import Component from "@ember/component";
/* global Pikaday:true */
import loadScript from "discourse/lib/load-script";
import {
- default as computed,
+ default as discourseComputed,
on
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
const DATE_FORMAT = "YYYY-MM-DD";
@@ -14,7 +14,7 @@ export default Component.extend({
_picker: null,
value: null,
- @computed("site.mobileView")
+ @discourseComputed("site.mobileView")
inputType(mobileView) {
return mobileView ? "date" : "text";
},
@@ -83,7 +83,7 @@ export default Component.extend({
}
},
- @computed()
+ @discourseComputed()
placeholder() {
return I18n.t("dates.placeholder");
},
diff --git a/app/assets/javascripts/discourse/components/desktop-notification-config.js.es6 b/app/assets/javascripts/discourse/components/desktop-notification-config.js.es6
index 112723ba12..ecd11c2a6e 100644
--- a/app/assets/javascripts/discourse/components/desktop-notification-config.js.es6
+++ b/app/assets/javascripts/discourse/components/desktop-notification-config.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { or } from "@ember/object/computed";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import KeyValueStore from "discourse/lib/key-value-store";
import {
context,
@@ -19,12 +19,12 @@ const keyValueStore = new KeyValueStore(context);
export default Component.extend({
classNames: ["controls"],
- @computed("isNotSupported")
+ @discourseComputed("isNotSupported")
notificationsPermission(isNotSupported) {
return isNotSupported ? "" : Notification.permission;
},
- @computed
+ @discourseComputed
notificationsDisabled: {
set(value) {
keyValueStore.setItem("notifications-disabled", value);
@@ -35,27 +35,27 @@ export default Component.extend({
}
},
- @computed
+ @discourseComputed
isNotSupported() {
return typeof window.Notification === "undefined";
},
- @computed("isNotSupported", "notificationsPermission")
+ @discourseComputed("isNotSupported", "notificationsPermission")
isDeniedPermission(isNotSupported, notificationsPermission) {
return isNotSupported ? false : notificationsPermission === "denied";
},
- @computed("isNotSupported", "notificationsPermission")
+ @discourseComputed("isNotSupported", "notificationsPermission")
isGrantedPermission(isNotSupported, notificationsPermission) {
return isNotSupported ? false : notificationsPermission === "granted";
},
- @computed("isGrantedPermission", "notificationsDisabled")
+ @discourseComputed("isGrantedPermission", "notificationsDisabled")
isEnabledDesktop(isGrantedPermission, notificationsDisabled) {
return isGrantedPermission ? !notificationsDisabled : false;
},
- @computed
+ @discourseComputed
isEnabledPush: {
set(value) {
const user = this.currentUser;
diff --git a/app/assets/javascripts/discourse/components/directory-toggle.js.es6 b/app/assets/javascripts/discourse/components/directory-toggle.js.es6
index d45e9ce9e7..2b761c99b9 100644
--- a/app/assets/javascripts/discourse/components/directory-toggle.js.es6
+++ b/app/assets/javascripts/discourse/components/directory-toggle.js.es6
@@ -1,7 +1,7 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
import { iconHTML } from "discourse-common/lib/icon-library";
import { bufferedRender } from "discourse-common/lib/buffered-render";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend(
bufferedRender({
@@ -11,7 +11,7 @@ export default Component.extend(
rerenderTriggers: ["order", "asc"],
labelKey: null,
- @computed("field", "labelKey")
+ @discourseComputed("field", "labelKey")
title(field, labelKey) {
if (!labelKey) {
labelKey = `directory.${this.field}`;
diff --git a/app/assets/javascripts/discourse/components/discourse-banner.js.es6 b/app/assets/javascripts/discourse/components/discourse-banner.js.es6
index 6c8b18ea1e..9182998d76 100644
--- a/app/assets/javascripts/discourse/components/discourse-banner.js.es6
+++ b/app/assets/javascripts/discourse/components/discourse-banner.js.es6
@@ -1,8 +1,8 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
- @computed("user.dismissed_banner_key", "banner.key", "hide")
+ @discourseComputed("user.dismissed_banner_key", "banner.key", "hide")
visible(dismissedBannerKey, bannerKey, hide) {
dismissedBannerKey =
dismissedBannerKey || this.keyValueStore.get("dismissed_banner_key");
diff --git a/app/assets/javascripts/discourse/components/discourse-linked-text.js.es6 b/app/assets/javascripts/discourse/components/discourse-linked-text.js.es6
index fe4e7fd9c8..85d6fd3cb9 100644
--- a/app/assets/javascripts/discourse/components/discourse-linked-text.js.es6
+++ b/app/assets/javascripts/discourse/components/discourse-linked-text.js.es6
@@ -1,10 +1,10 @@
import Component from "@ember/component";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
export default Component.extend({
tagName: "span",
- @computed("text")
+ @discourseComputed("text")
translatedText(text) {
if (text) return I18n.t(text);
},
diff --git a/app/assets/javascripts/discourse/components/discourse-tag-bound.js.es6 b/app/assets/javascripts/discourse/components/discourse-tag-bound.js.es6
index ea07e0d5fe..57e5c1841a 100644
--- a/app/assets/javascripts/discourse/components/discourse-tag-bound.js.es6
+++ b/app/assets/javascripts/discourse/components/discourse-tag-bound.js.es6
@@ -1,17 +1,17 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
tagName: "a",
classNameBindings: [":discourse-tag", "style", "tagClass"],
attributeBindings: ["href"],
- @computed("tagRecord.id")
+ @discourseComputed("tagRecord.id")
tagClass(tagRecordId) {
return "tag-" + tagRecordId;
},
- @computed("tagRecord.id")
+ @discourseComputed("tagRecord.id")
href(tagRecordId) {
return Discourse.getURL("/tags/" + tagRecordId);
}
diff --git a/app/assets/javascripts/discourse/components/discourse-topic.js.es6 b/app/assets/javascripts/discourse/components/discourse-topic.js.es6
index c9484f6264..83e7bf6fa1 100644
--- a/app/assets/javascripts/discourse/components/discourse-topic.js.es6
+++ b/app/assets/javascripts/discourse/components/discourse-topic.js.es6
@@ -9,7 +9,7 @@ import AddArchetypeClass from "discourse/mixins/add-archetype-class";
import ClickTrack from "discourse/lib/click-track";
import Scrolling from "discourse/mixins/scrolling";
import MobileScrollDirection from "discourse/mixins/mobile-scroll-direction";
-import { observes } from "ember-addons/ember-computed-decorators";
+import { observes } from "discourse-common/utils/decorators";
const MOBILE_SCROLL_DIRECTION_CHECK_THROTTLE = 300;
diff --git a/app/assets/javascripts/discourse/components/discovery-categories.js.es6 b/app/assets/javascripts/discourse/components/discovery-categories.js.es6
index d5c70bbf9a..bd4f34a2e7 100644
--- a/app/assets/javascripts/discourse/components/discovery-categories.js.es6
+++ b/app/assets/javascripts/discourse/components/discovery-categories.js.es6
@@ -1,6 +1,6 @@
import Component from "@ember/component";
import UrlRefresh from "discourse/mixins/url-refresh";
-import { on } from "ember-addons/ember-computed-decorators";
+import { on } from "discourse-common/utils/decorators";
const CATEGORIES_LIST_BODY_CLASS = "categories-list";
diff --git a/app/assets/javascripts/discourse/components/discovery-topics-list.js.es6 b/app/assets/javascripts/discourse/components/discovery-topics-list.js.es6
index 6706cacd4a..f4329ba2f2 100644
--- a/app/assets/javascripts/discourse/components/discovery-topics-list.js.es6
+++ b/app/assets/javascripts/discourse/components/discovery-topics-list.js.es6
@@ -1,7 +1,7 @@
import { schedule } from "@ember/runloop";
import { scheduleOnce } from "@ember/runloop";
import Component from "@ember/component";
-import { on, observes } from "ember-addons/ember-computed-decorators";
+import { on, observes } from "discourse-common/utils/decorators";
import LoadMore from "discourse/mixins/load-more";
import UrlRefresh from "discourse/mixins/url-refresh";
diff --git a/app/assets/javascripts/discourse/components/edit-category-general.js.es6 b/app/assets/javascripts/discourse/components/edit-category-general.js.es6
index e94e2a77d2..a1f95d117a 100644
--- a/app/assets/javascripts/discourse/components/edit-category-general.js.es6
+++ b/app/assets/javascripts/discourse/components/edit-category-general.js.es6
@@ -1,9 +1,9 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { isEmpty } from "@ember/utils";
import { not } from "@ember/object/computed";
import { buildCategoryPanel } from "discourse/components/edit-category-panel";
import { categoryBadgeHTML } from "discourse/helpers/category-link";
import Category from "discourse/models/category";
-import computed from "ember-addons/ember-computed-decorators";
export default buildCategoryPanel("general", {
init() {
@@ -21,7 +21,7 @@ export default buildCategoryPanel("general", {
),
// background colors are available as a pipe-separated string
- @computed
+ @discourseComputed
backgroundColors() {
const categories = this.site.get("categoriesList");
return this.siteSettings.category_colors
@@ -37,12 +37,12 @@ export default buildCategoryPanel("general", {
.uniq();
},
- @computed
+ @discourseComputed
noCategoryStyle() {
return this.siteSettings.category_style === "none";
},
- @computed("category.id", "category.color")
+ @discourseComputed("category.id", "category.color")
usedBackgroundColors(categoryId, categoryColor) {
const categories = this.site.get("categoriesList");
@@ -57,14 +57,14 @@ export default buildCategoryPanel("general", {
.compact();
},
- @computed
+ @discourseComputed
parentCategories() {
return this.site
.get("categoriesList")
.filter(c => !c.get("parentCategory"));
},
- @computed(
+ @discourseComputed(
"category.parent_category_id",
"category.categoryName",
"category.color",
@@ -83,7 +83,7 @@ export default buildCategoryPanel("general", {
},
// We can change the parent if there are no children
- @computed("category.id")
+ @discourseComputed("category.id")
subCategories(categoryId) {
if (isEmpty(categoryId)) {
return null;
@@ -91,7 +91,7 @@ export default buildCategoryPanel("general", {
return Category.list().filterBy("parent_category_id", categoryId);
},
- @computed("category.isUncategorizedCategory", "category.id")
+ @discourseComputed("category.isUncategorizedCategory", "category.id")
showDescription(isUncategorizedCategory, categoryId) {
return !isUncategorizedCategory && categoryId;
},
diff --git a/app/assets/javascripts/discourse/components/edit-category-images.js.es6 b/app/assets/javascripts/discourse/components/edit-category-images.js.es6
index 2e12268885..94956edf36 100644
--- a/app/assets/javascripts/discourse/components/edit-category-images.js.es6
+++ b/app/assets/javascripts/discourse/components/edit-category-images.js.es6
@@ -1,14 +1,14 @@
import EmberObject from "@ember/object";
import { buildCategoryPanel } from "discourse/components/edit-category-panel";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
export default buildCategoryPanel("images").extend({
- @computed("category.uploaded_background.url")
+ @discourseComputed("category.uploaded_background.url")
backgroundImageUrl(uploadedBackgroundUrl) {
return uploadedBackgroundUrl || "";
},
- @computed("category.uploaded_logo.url")
+ @discourseComputed("category.uploaded_logo.url")
logoImageUrl(uploadedLogoUrl) {
return uploadedLogoUrl || "";
},
diff --git a/app/assets/javascripts/discourse/components/edit-category-security.js.es6 b/app/assets/javascripts/discourse/components/edit-category-security.js.es6
index be41b0a09c..013e620671 100644
--- a/app/assets/javascripts/discourse/components/edit-category-security.js.es6
+++ b/app/assets/javascripts/discourse/components/edit-category-security.js.es6
@@ -1,6 +1,6 @@
import { buildCategoryPanel } from "discourse/components/edit-category-panel";
import PermissionType from "discourse/models/permission-type";
-import { on } from "ember-addons/ember-computed-decorators";
+import { on } from "discourse-common/utils/decorators";
export default buildCategoryPanel("security", {
editingPermissions: false,
diff --git a/app/assets/javascripts/discourse/components/edit-category-settings.js.es6 b/app/assets/javascripts/discourse/components/edit-category-settings.js.es6
index 5d692cc6eb..29556d2c9a 100644
--- a/app/assets/javascripts/discourse/components/edit-category-settings.js.es6
+++ b/app/assets/javascripts/discourse/components/edit-category-settings.js.es6
@@ -1,7 +1,7 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { empty, and } from "@ember/object/computed";
import { setting } from "discourse/lib/computed";
import { buildCategoryPanel } from "discourse/components/edit-category-panel";
-import computed from "ember-addons/ember-computed-decorators";
import { searchPriorities } from "discourse/components/concerns/category-search-priorities";
import Group from "discourse/models/group";
@@ -20,7 +20,7 @@ export default buildCategoryPanel("settings", {
),
isDefaultSortOrder: empty("category.sort_order"),
- @computed
+ @discourseComputed
availableSubcategoryListStyles() {
return [
{ name: I18n.t("category.subcategory_list_styles.rows"), value: "rows" },
@@ -47,7 +47,7 @@ export default buildCategoryPanel("settings", {
return Group.findAll({ term, ignore_automatic: true });
},
- @computed
+ @discourseComputed
availableViews() {
return [
{ name: I18n.t("filters.latest.title"), value: "latest" },
@@ -55,7 +55,7 @@ export default buildCategoryPanel("settings", {
];
},
- @computed
+ @discourseComputed
availableTopPeriods() {
return ["all", "yearly", "quarterly", "monthly", "weekly", "daily"].map(
p => {
@@ -64,7 +64,7 @@ export default buildCategoryPanel("settings", {
);
},
- @computed
+ @discourseComputed
searchPrioritiesOptions() {
const options = [];
@@ -80,7 +80,7 @@ export default buildCategoryPanel("settings", {
return options;
},
- @computed
+ @discourseComputed
availableSorts() {
return [
"likes",
@@ -97,7 +97,7 @@ export default buildCategoryPanel("settings", {
.sort((a, b) => a.name.localeCompare(b.name));
},
- @computed
+ @discourseComputed
sortAscendingOptions() {
return [
{ name: I18n.t("category.sort_ascending"), value: "true" },
diff --git a/app/assets/javascripts/discourse/components/edit-category-tab.js.es6 b/app/assets/javascripts/discourse/components/edit-category-tab.js.es6
index 42be7233af..9fa7984533 100644
--- a/app/assets/javascripts/discourse/components/edit-category-tab.js.es6
+++ b/app/assets/javascripts/discourse/components/edit-category-tab.js.es6
@@ -1,20 +1,20 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { scheduleOnce } from "@ember/runloop";
import Component from "@ember/component";
import { propertyEqual } from "discourse/lib/computed";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
tagName: "li",
classNameBindings: ["active", "tabClassName"],
- @computed("tab")
+ @discourseComputed("tab")
tabClassName(tab) {
return "edit-category-" + tab;
},
active: propertyEqual("selectedTab", "tab"),
- @computed("tab")
+ @discourseComputed("tab")
title(tab) {
return I18n.t("category." + tab.replace("-", "_"));
},
diff --git a/app/assets/javascripts/discourse/components/edit-topic-timer-form.js.es6 b/app/assets/javascripts/discourse/components/edit-topic-timer-form.js.es6
index 5b774ca667..00fa6b2bad 100644
--- a/app/assets/javascripts/discourse/components/edit-topic-timer-form.js.es6
+++ b/app/assets/javascripts/discourse/components/edit-topic-timer-form.js.es6
@@ -3,11 +3,10 @@ import { alias, equal, or } from "@ember/object/computed";
import { schedule } from "@ember/runloop";
import Component from "@ember/component";
import {
- default as computed,
+ default as discourseComputed,
observes,
on
-} from "ember-addons/ember-computed-decorators";
-
+} from "discourse-common/utils/decorators";
import {
PUBLISH_TO_CATEGORY_STATUS_TYPE,
OPEN_STATUS_TYPE,
@@ -27,7 +26,7 @@ export default Component.extend({
reminder: equal("selection", REMINDER_TYPE),
showTimeOnly: or("autoOpen", "autoDelete", "reminder", "autoBump"),
- @computed(
+ @discourseComputed(
"topicTimer.updateTime",
"loading",
"publishToCategory",
@@ -41,7 +40,7 @@ export default Component.extend({
);
},
- @computed("topic.visible")
+ @discourseComputed("topic.visible")
excludeCategoryId(visible) {
if (visible) return this.get("topic.category_id");
},
diff --git a/app/assets/javascripts/discourse/components/emoji-picker.js.es6 b/app/assets/javascripts/discourse/components/emoji-picker.js.es6
index 6ad97bebc8..7d4d92e7ee 100644
--- a/app/assets/javascripts/discourse/components/emoji-picker.js.es6
+++ b/app/assets/javascripts/discourse/components/emoji-picker.js.es6
@@ -1,9 +1,8 @@
import { inject as service } from "@ember/service";
import Component from "@ember/component";
-import { on, observes } from "ember-addons/ember-computed-decorators";
+import { on, observes } from "discourse-common/utils/decorators";
import { findRawTemplate } from "discourse/lib/raw-templates";
import { emojiUrlFor } from "discourse/lib/text";
-
import {
extendedEmojiList,
isSkinTonableEmoji,
diff --git a/app/assets/javascripts/discourse/components/emoji-uploader.js.es6 b/app/assets/javascripts/discourse/components/emoji-uploader.js.es6
index 37dfd5ea10..fa7ee8fd10 100644
--- a/app/assets/javascripts/discourse/components/emoji-uploader.js.es6
+++ b/app/assets/javascripts/discourse/components/emoji-uploader.js.es6
@@ -1,6 +1,6 @@
import { notEmpty, not } from "@ember/object/computed";
import Component from "@ember/component";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import UploadMixin from "discourse/mixins/upload";
export default Component.extend(UploadMixin, {
@@ -15,7 +15,7 @@ export default Component.extend(UploadMixin, {
};
},
- @computed("hasName", "name")
+ @discourseComputed("hasName", "name")
data(hasName, name) {
return hasName ? { name } : {};
},
diff --git a/app/assets/javascripts/discourse/components/expanding-text-area.js.es6 b/app/assets/javascripts/discourse/components/expanding-text-area.js.es6
index d2b980a8f2..4c3432f277 100644
--- a/app/assets/javascripts/discourse/components/expanding-text-area.js.es6
+++ b/app/assets/javascripts/discourse/components/expanding-text-area.js.es6
@@ -1,5 +1,5 @@
import { scheduleOnce } from "@ember/runloop";
-import { on, observes } from "ember-addons/ember-computed-decorators";
+import { on, observes } from "discourse-common/utils/decorators";
import autosize from "discourse/lib/autosize";
export default Ember.TextArea.extend({
diff --git a/app/assets/javascripts/discourse/components/flag-action-type.js.es6 b/app/assets/javascripts/discourse/components/flag-action-type.js.es6
index c42818914d..a88356c9a9 100644
--- a/app/assets/javascripts/discourse/components/flag-action-type.js.es6
+++ b/app/assets/javascripts/discourse/components/flag-action-type.js.es6
@@ -1,17 +1,22 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { and, not, equal } from "@ember/object/computed";
import Component from "@ember/component";
import { MAX_MESSAGE_LENGTH } from "discourse/models/post-action-type";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
classNames: ["flag-action-type"],
- @computed("flag.name_key")
+ @discourseComputed("flag.name_key")
customPlaceholder(nameKey) {
return I18n.t("flagging.custom_placeholder_" + nameKey);
},
- @computed("flag.name", "flag.name_key", "flag.is_custom_flag", "username")
+ @discourseComputed(
+ "flag.name",
+ "flag.name_key",
+ "flag.is_custom_flag",
+ "username"
+ )
formattedName(name, nameKey, isCustomFlag, username) {
if (isCustomFlag) {
return name.replace("{{username}}", username);
@@ -20,7 +25,7 @@ export default Component.extend({
}
},
- @computed("flag", "selectedFlag")
+ @discourseComputed("flag", "selectedFlag")
selected(flag, selectedFlag) {
return flag === selectedFlag;
},
@@ -29,12 +34,12 @@ export default Component.extend({
showDescription: not("showMessageInput"),
isNotifyUser: equal("flag.name_key", "notify_user"),
- @computed("flag.description", "flag.short_description")
+ @discourseComputed("flag.description", "flag.short_description")
description(long_description, short_description) {
return this.site.mobileView ? short_description : long_description;
},
- @computed("message.length")
+ @discourseComputed("message.length")
customMessageLengthClasses(messageLength) {
return messageLength <
Discourse.SiteSettings.min_personal_message_post_length
@@ -42,7 +47,7 @@ export default Component.extend({
: "ok";
},
- @computed("message.length")
+ @discourseComputed("message.length")
customMessageLength(messageLength) {
const len = messageLength || 0;
const minLen = Discourse.SiteSettings.min_personal_message_post_length;
diff --git a/app/assets/javascripts/discourse/components/flag-selection.js.es6 b/app/assets/javascripts/discourse/components/flag-selection.js.es6
index b52f544907..39548b045f 100644
--- a/app/assets/javascripts/discourse/components/flag-selection.js.es6
+++ b/app/assets/javascripts/discourse/components/flag-selection.js.es6
@@ -1,6 +1,6 @@
import { next } from "@ember/runloop";
import Component from "@ember/component";
-import { observes } from "ember-addons/ember-computed-decorators";
+import { observes } from "discourse-common/utils/decorators";
// Mostly hacks because `flag.hbs` didn't use `radio-button`
export default Component.extend({
diff --git a/app/assets/javascripts/discourse/components/flat-button.js.es6 b/app/assets/javascripts/discourse/components/flat-button.js.es6
index 1348836907..af44422025 100644
--- a/app/assets/javascripts/discourse/components/flat-button.js.es6
+++ b/app/assets/javascripts/discourse/components/flat-button.js.es6
@@ -1,12 +1,12 @@
import Component from "@ember/component";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
export default Component.extend({
tagName: "button",
classNames: ["btn-flat"],
attributeBindings: ["disabled", "translatedTitle:title"],
- @computed("title")
+ @discourseComputed("title")
translatedTitle(title) {
if (title) return I18n.t(title);
},
diff --git a/app/assets/javascripts/discourse/components/footer-nav.js.es6 b/app/assets/javascripts/discourse/components/footer-nav.js.es6
index d94910364e..c4d412346e 100644
--- a/app/assets/javascripts/discourse/components/footer-nav.js.es6
+++ b/app/assets/javascripts/discourse/components/footer-nav.js.es6
@@ -2,7 +2,7 @@ import { throttle } from "@ember/runloop";
import MountWidget from "discourse/components/mount-widget";
import MobileScrollDirection from "discourse/mixins/mobile-scroll-direction";
import Scrolling from "discourse/mixins/scrolling";
-import { observes } from "ember-addons/ember-computed-decorators";
+import { observes } from "discourse-common/utils/decorators";
import { isAppWebview, postRNWebviewMessage } from "discourse/lib/utilities";
const MOBILE_SCROLL_DIRECTION_CHECK_THROTTLE = 150;
diff --git a/app/assets/javascripts/discourse/components/future-date-input.js.es6 b/app/assets/javascripts/discourse/components/future-date-input.js.es6
index 8746cfb0ef..05313f8ea0 100644
--- a/app/assets/javascripts/discourse/components/future-date-input.js.es6
+++ b/app/assets/javascripts/discourse/components/future-date-input.js.es6
@@ -2,9 +2,9 @@ import { isEmpty } from "@ember/utils";
import { equal, and, empty } from "@ember/object/computed";
import Component from "@ember/component";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import { FORMAT } from "select-kit/components/future-date-input-selector";
import { PUBLISH_TO_CATEGORY_STATUS_TYPE } from "discourse/controllers/edit-topic-timer";
@@ -59,7 +59,7 @@ export default Component.extend({
this.set("basedOnLastPost", this.isBasedOnLastPost);
},
- @computed("input", "isBasedOnLastPost")
+ @discourseComputed("input", "isBasedOnLastPost")
duration(input, isBasedOnLastPost) {
const now = moment();
@@ -70,7 +70,7 @@ export default Component.extend({
}
},
- @computed("input", "isBasedOnLastPost")
+ @discourseComputed("input", "isBasedOnLastPost")
executeAt(input, isBasedOnLastPost) {
if (isBasedOnLastPost) {
return moment()
@@ -87,7 +87,7 @@ export default Component.extend({
if (this.label) this.set("displayLabel", I18n.t(this.label));
},
- @computed(
+ @discourseComputed(
"statusType",
"input",
"isCustom",
@@ -118,7 +118,7 @@ export default Component.extend({
}
},
- @computed("isBasedOnLastPost", "input", "lastPostedAt")
+ @discourseComputed("isBasedOnLastPost", "input", "lastPostedAt")
willCloseImmediately(isBasedOnLastPost, input, lastPostedAt) {
if (isBasedOnLastPost && input) {
let closeDate = moment(lastPostedAt);
@@ -127,7 +127,7 @@ export default Component.extend({
}
},
- @computed("isBasedOnLastPost", "lastPostedAt")
+ @discourseComputed("isBasedOnLastPost", "lastPostedAt")
willCloseI18n(isBasedOnLastPost, lastPostedAt) {
if (isBasedOnLastPost) {
const diff = Math.round(
diff --git a/app/assets/javascripts/discourse/components/global-notice.js.es6 b/app/assets/javascripts/discourse/components/global-notice.js.es6
index e16243f207..c7006016a6 100644
--- a/app/assets/javascripts/discourse/components/global-notice.js.es6
+++ b/app/assets/javascripts/discourse/components/global-notice.js.es6
@@ -1,6 +1,6 @@
import { bind } from "@ember/runloop";
import Component from "@ember/component";
-import { on } from "ember-addons/ember-computed-decorators";
+import { on } from "discourse-common/utils/decorators";
import { iconHTML } from "discourse-common/lib/icon-library";
import LogsNotice from "discourse/services/logs-notice";
import { bufferedRender } from "discourse-common/lib/buffered-render";
diff --git a/app/assets/javascripts/discourse/components/google-search.js.es6 b/app/assets/javascripts/discourse/components/google-search.js.es6
index 246e7ab2a3..43db648e81 100644
--- a/app/assets/javascripts/discourse/components/google-search.js.es6
+++ b/app/assets/javascripts/discourse/components/google-search.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { alias } from "@ember/object/computed";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
classNames: ["google-search-form"],
@@ -8,7 +8,7 @@ export default Component.extend({
hidden: alias("siteSettings.login_required"),
- @computed
+ @discourseComputed
siteUrl() {
return `${location.protocol}//${location.host}${Discourse.getURL("/")}`;
}
diff --git a/app/assets/javascripts/discourse/components/group-card-contents.js.es6 b/app/assets/javascripts/discourse/components/group-card-contents.js.es6
index bd6d029e49..50ea8b9ab2 100644
--- a/app/assets/javascripts/discourse/components/group-card-contents.js.es6
+++ b/app/assets/javascripts/discourse/components/group-card-contents.js.es6
@@ -1,7 +1,7 @@
import { alias, match, gt, or } from "@ember/object/computed";
import Component from "@ember/component";
import { setting } from "discourse/lib/computed";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import CardContentsBase from "discourse/mixins/card-contents-base";
import CleansUp from "discourse/mixins/cleans-up";
import { groupPath } from "discourse/lib/url";
@@ -34,14 +34,14 @@ export default Component.extend(CardContentsBase, CleansUp, {
group: null,
- @computed("group.user_count", "group.members.length")
+ @discourseComputed("group.user_count", "group.members.length")
moreMembersCount: (memberCount, maxMemberDisplay) =>
memberCount - maxMemberDisplay,
- @computed("group.name")
+ @discourseComputed("group.name")
groupClass: name => (name ? `group-card-${name}` : ""),
- @computed("group")
+ @discourseComputed("group")
groupPath(group) {
return groupPath(group.name);
},
diff --git a/app/assets/javascripts/discourse/components/group-flair-inputs.js.es6 b/app/assets/javascripts/discourse/components/group-flair-inputs.js.es6
index 7b2b7110a0..81b17bcb8d 100644
--- a/app/assets/javascripts/discourse/components/group-flair-inputs.js.es6
+++ b/app/assets/javascripts/discourse/components/group-flair-inputs.js.es6
@@ -1,7 +1,7 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { debounce } from "@ember/runloop";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
-import { observes } from "ember-addons/ember-computed-decorators";
+import { observes } from "discourse-common/utils/decorators";
import { escapeExpression } from "discourse/lib/utilities";
import { convertIconClass } from "discourse-common/lib/icon-library";
import { ajax } from "discourse/lib/ajax";
@@ -10,17 +10,17 @@ import { htmlSafe } from "@ember/template";
export default Component.extend({
classNames: ["group-flair-inputs"],
- @computed
+ @discourseComputed
demoAvatarUrl() {
return Discourse.getURL("/images/avatar.png");
},
- @computed("model.flair_url")
+ @discourseComputed("model.flair_url")
flairPreviewIcon(flairURL) {
return flairURL && /fa(r|b?)-/.test(flairURL);
},
- @computed("model.flair_url", "flairPreviewIcon")
+ @discourseComputed("model.flair_url", "flairPreviewIcon")
flairPreviewIconUrl(flairURL, flairPreviewIcon) {
return flairPreviewIcon ? convertIconClass(flairURL) : "";
},
@@ -49,12 +49,12 @@ export default Component.extend({
}
},
- @computed("model.flair_url", "flairPreviewIcon")
+ @discourseComputed("model.flair_url", "flairPreviewIcon")
flairPreviewImage(flairURL, flairPreviewIcon) {
return flairURL && !flairPreviewIcon;
},
- @computed(
+ @discourseComputed(
"model.flair_url",
"flairPreviewImage",
"model.flairBackgroundHexColor",
@@ -81,12 +81,12 @@ export default Component.extend({
return htmlSafe(style);
},
- @computed("model.flairBackgroundHexColor")
+ @discourseComputed("model.flairBackgroundHexColor")
flairPreviewClasses(flairBackgroundHexColor) {
if (flairBackgroundHexColor) return "rounded";
},
- @computed("flairPreviewImage")
+ @discourseComputed("flairPreviewImage")
flairPreviewLabel(flairPreviewImage) {
const key = flairPreviewImage ? "image" : "icon";
return I18n.t(`groups.flair_preview_${key}`);
diff --git a/app/assets/javascripts/discourse/components/group-manage-logs-filter.js.es6 b/app/assets/javascripts/discourse/components/group-manage-logs-filter.js.es6
index a6712bf498..98e0c16cdd 100644
--- a/app/assets/javascripts/discourse/components/group-manage-logs-filter.js.es6
+++ b/app/assets/javascripts/discourse/components/group-manage-logs-filter.js.es6
@@ -1,15 +1,15 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
tagName: "",
- @computed("type")
+ @discourseComputed("type")
label(type) {
return I18n.t(`groups.manage.logs.${type}`);
},
- @computed("value", "type")
+ @discourseComputed("value", "type")
filterText(value, type) {
return type === "action"
? I18n.t(`group_histories.actions.${value}`)
diff --git a/app/assets/javascripts/discourse/components/group-manage-save-button.js.es6 b/app/assets/javascripts/discourse/components/group-manage-save-button.js.es6
index 726bfede36..9adcf9ea82 100644
--- a/app/assets/javascripts/discourse/components/group-manage-save-button.js.es6
+++ b/app/assets/javascripts/discourse/components/group-manage-save-button.js.es6
@@ -1,11 +1,11 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
import { popupAjaxError } from "discourse/lib/ajax-error";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
saving: null,
- @computed("saving")
+ @discourseComputed("saving")
savingText(saving) {
if (saving) return I18n.t("saving");
return saving ? I18n.t("saving") : I18n.t("save");
diff --git a/app/assets/javascripts/discourse/components/group-member-dropdown.js.es6 b/app/assets/javascripts/discourse/components/group-member-dropdown.js.es6
index 5cb7099058..7a860c29de 100644
--- a/app/assets/javascripts/discourse/components/group-member-dropdown.js.es6
+++ b/app/assets/javascripts/discourse/components/group-member-dropdown.js.es6
@@ -1,4 +1,4 @@
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
import DropdownSelectBoxComponent from "select-kit/components/dropdown-select-box";
export default DropdownSelectBoxComponent.extend({
@@ -16,7 +16,7 @@ export default DropdownSelectBoxComponent.extend({
autoHighlight() {},
- @computed("member.owner")
+ @discourseComputed("member.owner")
content(isOwner) {
const items = [
{
diff --git a/app/assets/javascripts/discourse/components/group-members-input.js.es6 b/app/assets/javascripts/discourse/components/group-members-input.js.es6
index e1f701f96c..aedb43f2a6 100644
--- a/app/assets/javascripts/discourse/components/group-members-input.js.es6
+++ b/app/assets/javascripts/discourse/components/group-members-input.js.es6
@@ -1,7 +1,7 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { isEmpty } from "@ember/utils";
import { lte } from "@ember/object/computed";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import { popupAjaxError } from "discourse/lib/ajax-error";
import { propertyEqual } from "discourse/lib/computed";
@@ -9,7 +9,7 @@ export default Component.extend({
classNames: ["group-members-input"],
addButton: true,
- @computed("model.limit", "model.offset", "model.user_count")
+ @discourseComputed("model.limit", "model.offset", "model.user_count")
currentPage(limit, offset, userCount) {
if (userCount === 0) {
return 0;
@@ -18,7 +18,7 @@ export default Component.extend({
return Math.floor(offset / limit) + 1;
},
- @computed("model.limit", "model.user_count")
+ @discourseComputed("model.limit", "model.user_count")
totalPages(limit, userCount) {
if (userCount === 0) {
return 0;
@@ -26,7 +26,7 @@ export default Component.extend({
return Math.ceil(userCount / limit);
},
- @computed("model.usernames")
+ @discourseComputed("model.usernames")
disableAddButton(usernames) {
return !usernames || !(usernames.length > 0);
},
diff --git a/app/assets/javascripts/discourse/components/group-membership-button.js.es6 b/app/assets/javascripts/discourse/components/group-membership-button.js.es6
index 6b58c5370d..7c4abeda18 100644
--- a/app/assets/javascripts/discourse/components/group-membership-button.js.es6
+++ b/app/assets/javascripts/discourse/components/group-membership-button.js.es6
@@ -1,27 +1,27 @@
import Component from "@ember/component";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import { popupAjaxError } from "discourse/lib/ajax-error";
import showModal from "discourse/lib/show-modal";
export default Component.extend({
classNames: ["group-membership-button"],
- @computed("model.public_admission", "userIsGroupUser")
+ @discourseComputed("model.public_admission", "userIsGroupUser")
canJoinGroup(publicAdmission, userIsGroupUser) {
return publicAdmission && !userIsGroupUser;
},
- @computed("model.public_exit", "userIsGroupUser")
+ @discourseComputed("model.public_exit", "userIsGroupUser")
canLeaveGroup(publicExit, userIsGroupUser) {
return publicExit && userIsGroupUser;
},
- @computed("model.allow_membership_requests", "userIsGroupUser")
+ @discourseComputed("model.allow_membership_requests", "userIsGroupUser")
canRequestMembership(allowMembershipRequests, userIsGroupUser) {
return allowMembershipRequests && !userIsGroupUser;
},
- @computed("model.is_group_user")
+ @discourseComputed("model.is_group_user")
userIsGroupUser(isGroupUser) {
return !!isGroupUser;
},
diff --git a/app/assets/javascripts/discourse/components/group-post.js.es6 b/app/assets/javascripts/discourse/components/group-post.js.es6
index 5a3a096f49..34c83529ef 100644
--- a/app/assets/javascripts/discourse/components/group-post.js.es6
+++ b/app/assets/javascripts/discourse/components/group-post.js.es6
@@ -1,7 +1,7 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
- @computed("post.url")
+ @discourseComputed("post.url")
postUrl: Discourse.getURL
});
diff --git a/app/assets/javascripts/discourse/components/group-selector.js.es6 b/app/assets/javascripts/discourse/components/group-selector.js.es6
index 4d4b431888..54b789664b 100644
--- a/app/assets/javascripts/discourse/components/group-selector.js.es6
+++ b/app/assets/javascripts/discourse/components/group-selector.js.es6
@@ -3,12 +3,12 @@ import Component from "@ember/component";
import {
on,
observes,
- default as computed
-} from "ember-addons/ember-computed-decorators";
+ default as discourseComputed
+} from "discourse-common/utils/decorators";
import { findRawTemplate } from "discourse/lib/raw-templates";
export default Component.extend({
- @computed("placeholderKey")
+ @discourseComputed("placeholderKey")
placeholder(placeholderKey) {
return placeholderKey ? I18n.t(placeholderKey) : "";
},
diff --git a/app/assets/javascripts/discourse/components/groups-form-interaction-fields.js.es6 b/app/assets/javascripts/discourse/components/groups-form-interaction-fields.js.es6
index e4d1e6bb79..f3ba2d92a4 100644
--- a/app/assets/javascripts/discourse/components/groups-form-interaction-fields.js.es6
+++ b/app/assets/javascripts/discourse/components/groups-form-interaction-fields.js.es6
@@ -1,5 +1,5 @@
import Component from "@ember/component";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
export default Component.extend({
init() {
@@ -46,7 +46,11 @@ export default Component.extend({
];
},
- @computed("siteSettings.email_in", "model.automatic", "currentUser.admin")
+ @discourseComputed(
+ "siteSettings.email_in",
+ "model.automatic",
+ "currentUser.admin"
+ )
showEmailSettings(emailIn, automatic, isAdmin) {
return emailIn && isAdmin && !automatic;
}
diff --git a/app/assets/javascripts/discourse/components/groups-form-membership-fields.js.es6 b/app/assets/javascripts/discourse/components/groups-form-membership-fields.js.es6
index 1115786b08..1b5be47e6a 100644
--- a/app/assets/javascripts/discourse/components/groups-form-membership-fields.js.es6
+++ b/app/assets/javascripts/discourse/components/groups-form-membership-fields.js.es6
@@ -1,5 +1,5 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
init() {
@@ -17,13 +17,16 @@ export default Component.extend({
];
},
- @computed("model.visibility_level", "model.public_admission")
+ @discourseComputed("model.visibility_level", "model.public_admission")
disableMembershipRequestSetting(visibility_level, publicAdmission) {
visibility_level = parseInt(visibility_level);
return publicAdmission || visibility_level > 1;
},
- @computed("model.visibility_level", "model.allow_membership_requests")
+ @discourseComputed(
+ "model.visibility_level",
+ "model.allow_membership_requests"
+ )
disablePublicSetting(visibility_level, allowMembershipRequests) {
visibility_level = parseInt(visibility_level);
return allowMembershipRequests || visibility_level > 1;
diff --git a/app/assets/javascripts/discourse/components/groups-form-profile-fields.js.es6 b/app/assets/javascripts/discourse/components/groups-form-profile-fields.js.es6
index 98eabcea3f..082cfcc584 100644
--- a/app/assets/javascripts/discourse/components/groups-form-profile-fields.js.es6
+++ b/app/assets/javascripts/discourse/components/groups-form-profile-fields.js.es6
@@ -2,9 +2,9 @@ import { isEmpty } from "@ember/utils";
import { not } from "@ember/object/computed";
import Component from "@ember/component";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import Group from "discourse/models/group";
import InputValidation from "discourse/models/input-validation";
import debounce from "discourse/lib/debounce";
@@ -26,7 +26,7 @@ export default Component.extend({
canEdit: not("model.automatic"),
- @computed("basicNameValidation", "uniqueNameValidation")
+ @discourseComputed("basicNameValidation", "uniqueNameValidation")
nameValidation(basicNameValidation, uniqueNameValidation) {
return uniqueNameValidation ? uniqueNameValidation : basicNameValidation;
},
diff --git a/app/assets/javascripts/discourse/components/groups-info.js.es6 b/app/assets/javascripts/discourse/components/groups-info.js.es6
index cf439ef7d0..336e826b80 100644
--- a/app/assets/javascripts/discourse/components/groups-info.js.es6
+++ b/app/assets/javascripts/discourse/components/groups-info.js.es6
@@ -1,11 +1,11 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
tagName: "span",
classNames: ["group-info-details"],
- @computed("group.full_name", "group.title")
+ @discourseComputed("group.full_name", "group.title")
showFullName(fullName, title) {
return fullName && fullName.length && fullName !== title;
}
diff --git a/app/assets/javascripts/discourse/components/honeypot-input.js.es6 b/app/assets/javascripts/discourse/components/honeypot-input.js.es6
index 06895b0586..8231303da5 100644
--- a/app/assets/javascripts/discourse/components/honeypot-input.js.es6
+++ b/app/assets/javascripts/discourse/components/honeypot-input.js.es6
@@ -1,4 +1,4 @@
-import { on } from "ember-addons/ember-computed-decorators";
+import { on } from "discourse-common/utils/decorators";
export default Ember.TextField.extend({
@on("init")
diff --git a/app/assets/javascripts/discourse/components/image-uploader.js.es6 b/app/assets/javascripts/discourse/components/image-uploader.js.es6
index 514a985223..6db47602ad 100644
--- a/app/assets/javascripts/discourse/components/image-uploader.js.es6
+++ b/app/assets/javascripts/discourse/components/image-uploader.js.es6
@@ -1,7 +1,7 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { isEmpty } from "@ember/utils";
import { next } from "@ember/runloop";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import UploadMixin from "discourse/mixins/upload";
import lightbox from "discourse/lib/lightbox";
import { ajax } from "discourse/lib/ajax";
@@ -24,12 +24,12 @@ export default Component.extend(UploadMixin, {
}
},
- @computed("imageUrl", "placeholderUrl")
+ @discourseComputed("imageUrl", "placeholderUrl")
showingPlaceholder(imageUrl, placeholderUrl) {
return !imageUrl && placeholderUrl;
},
- @computed("placeholderUrl")
+ @discourseComputed("placeholderUrl")
placeholderStyle(url) {
if (isEmpty(url)) {
return "".htmlSafe();
@@ -37,7 +37,7 @@ export default Component.extend(UploadMixin, {
return `background-image: url(${url})`.htmlSafe();
},
- @computed("imageUrl")
+ @discourseComputed("imageUrl")
imageCDNURL(url) {
if (isEmpty(url)) {
return "".htmlSafe();
@@ -46,12 +46,12 @@ export default Component.extend(UploadMixin, {
return Discourse.getURLWithCDN(url);
},
- @computed("imageCDNURL")
+ @discourseComputed("imageCDNURL")
backgroundStyle(url) {
return `background-image: url(${url})`.htmlSafe();
},
- @computed("imageUrl")
+ @discourseComputed("imageUrl")
imageBaseName(imageUrl) {
if (isEmpty(imageUrl)) return;
return imageUrl.split("/").slice(-1)[0];
diff --git a/app/assets/javascripts/discourse/components/images-uploader.js.es6 b/app/assets/javascripts/discourse/components/images-uploader.js.es6
index d3a9d6c3b7..4e68324b0c 100644
--- a/app/assets/javascripts/discourse/components/images-uploader.js.es6
+++ b/app/assets/javascripts/discourse/components/images-uploader.js.es6
@@ -1,12 +1,12 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import UploadMixin from "discourse/mixins/upload";
export default Component.extend(UploadMixin, {
type: "avatar",
tagName: "span",
- @computed("uploading")
+ @discourseComputed("uploading")
uploadButtonText(uploading) {
return uploading ? I18n.t("uploading") : I18n.t("upload");
},
diff --git a/app/assets/javascripts/discourse/components/invite-panel.js.es6 b/app/assets/javascripts/discourse/components/invite-panel.js.es6
index b1743d4f99..8056a92dcd 100644
--- a/app/assets/javascripts/discourse/components/invite-panel.js.es6
+++ b/app/assets/javascripts/discourse/components/invite-panel.js.es6
@@ -1,9 +1,9 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { isEmpty } from "@ember/utils";
import { alias, and, equal } from "@ember/object/computed";
import EmberObject from "@ember/object";
import Component from "@ember/component";
import { emailValid } from "discourse/lib/utilities";
-import computed from "ember-addons/ember-computed-decorators";
import Group from "discourse/models/group";
import Invite from "discourse/models/invite";
import { i18n } from "discourse/lib/computed";
@@ -30,7 +30,7 @@ export default Component.extend({
this.reset();
},
- @computed(
+ @discourseComputed(
"isAdmin",
"emailOrUsername",
"invitingToTopic",
@@ -73,7 +73,7 @@ export default Component.extend({
return false;
},
- @computed(
+ @discourseComputed(
"isAdmin",
"emailOrUsername",
"inviteModel.saving",
@@ -113,24 +113,24 @@ export default Component.extend({
return false;
},
- @computed("inviteModel.saving")
+ @discourseComputed("inviteModel.saving")
buttonTitle(saving) {
return saving ? "topic.inviting" : "topic.invite_reply.action";
},
// We are inviting to a topic if the topic isn't the current user.
// The current user would mean we are inviting to the forum in general.
- @computed("inviteModel")
+ @discourseComputed("inviteModel")
invitingToTopic(inviteModel) {
return inviteModel !== this.currentUser;
},
- @computed("inviteModel", "inviteModel.details.can_invite_via_email")
+ @discourseComputed("inviteModel", "inviteModel.details.can_invite_via_email")
canInviteViaEmail(inviteModel, canInviteViaEmail) {
return this.inviteModel === this.currentUser ? true : canInviteViaEmail;
},
- @computed("isPM", "canInviteViaEmail")
+ @discourseComputed("isPM", "canInviteViaEmail")
showCopyInviteButton(isPM, canInviteViaEmail) {
return canInviteViaEmail && !isPM;
},
@@ -148,7 +148,7 @@ export default Component.extend({
// scope to allowed usernames
allowExistingMembers: alias("invitingToTopic"),
- @computed("isAdmin", "inviteModel.group_users")
+ @discourseComputed("isAdmin", "inviteModel.group_users")
isGroupOwnerOrAdmin(isAdmin, groupUsers) {
return (
isAdmin || (groupUsers && groupUsers.some(groupUser => groupUser.owner))
@@ -156,7 +156,7 @@ export default Component.extend({
},
// Show Groups? (add invited user to private group)
- @computed(
+ @discourseComputed(
"isGroupOwnerOrAdmin",
"emailOrUsername",
"isPrivateTopic",
@@ -180,13 +180,13 @@ export default Component.extend({
);
},
- @computed("emailOrUsername")
+ @discourseComputed("emailOrUsername")
showCustomMessage(emailOrUsername) {
return this.inviteModel === this.currentUser || emailValid(emailOrUsername);
},
// Instructional text for the modal.
- @computed(
+ @discourseComputed(
"isPM",
"invitingToTopic",
"emailOrUsername",
@@ -231,7 +231,7 @@ export default Component.extend({
}
},
- @computed("isPrivateTopic")
+ @discourseComputed("isPrivateTopic")
showGroupsClass(isPrivateTopic) {
return isPrivateTopic ? "required" : "optional";
},
@@ -240,7 +240,7 @@ export default Component.extend({
return Group.findAll({ term, ignore_automatic: true });
},
- @computed("isPM", "emailOrUsername", "invitingExistingUserToTopic")
+ @discourseComputed("isPM", "emailOrUsername", "invitingExistingUserToTopic")
successMessage(isPM, emailOrUsername, invitingExistingUserToTopic) {
if (this.hasGroups) {
return I18n.t("topic.invite_private.success_group");
@@ -257,14 +257,14 @@ export default Component.extend({
}
},
- @computed("isPM")
+ @discourseComputed("isPM")
errorMessage(isPM) {
return isPM
? I18n.t("topic.invite_private.error")
: I18n.t("topic.invite_reply.error");
},
- @computed("canInviteViaEmail")
+ @discourseComputed("canInviteViaEmail")
placeholderKey(canInviteViaEmail) {
return canInviteViaEmail
? "topic.invite_private.email_or_username_placeholder"
diff --git a/app/assets/javascripts/discourse/components/login-buttons.js.es6 b/app/assets/javascripts/discourse/components/login-buttons.js.es6
index a5a0967411..1073dd3ec0 100644
--- a/app/assets/javascripts/discourse/components/login-buttons.js.es6
+++ b/app/assets/javascripts/discourse/components/login-buttons.js.es6
@@ -1,17 +1,17 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
import { findAll } from "discourse/models/login-method";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
elementId: "login-buttons",
classNameBindings: ["hidden"],
- @computed("buttons.length", "showLoginWithEmailLink")
+ @discourseComputed("buttons.length", "showLoginWithEmailLink")
hidden(buttonsCount, showLoginWithEmailLink) {
return buttonsCount === 0 && !showLoginWithEmailLink;
},
- @computed
+ @discourseComputed
buttons() {
return findAll();
},
diff --git a/app/assets/javascripts/discourse/components/mobile-nav.js.es6 b/app/assets/javascripts/discourse/components/mobile-nav.js.es6
index a47c09c5c4..02d35f53d3 100644
--- a/app/assets/javascripts/discourse/components/mobile-nav.js.es6
+++ b/app/assets/javascripts/discourse/components/mobile-nav.js.es6
@@ -1,6 +1,6 @@
import { next } from "@ember/runloop";
import Component from "@ember/component";
-import { on, observes } from "ember-addons/ember-computed-decorators";
+import { on, observes } from "discourse-common/utils/decorators";
export default Component.extend({
@on("init")
diff --git a/app/assets/javascripts/discourse/components/nav-item.js.es6 b/app/assets/javascripts/discourse/components/nav-item.js.es6
index d648e892d3..7358e2ded6 100644
--- a/app/assets/javascripts/discourse/components/nav-item.js.es6
+++ b/app/assets/javascripts/discourse/components/nav-item.js.es6
@@ -1,15 +1,15 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { inject as service } from "@ember/service";
import Component from "@ember/component";
/* You might be looking for navigation-item. */
import { iconHTML } from "discourse-common/lib/icon-library";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
tagName: "li",
classNameBindings: ["active"],
router: service(),
- @computed("label", "i18nLabel", "icon")
+ @discourseComputed("label", "i18nLabel", "icon")
contents(label, i18nLabel, icon) {
let text = i18nLabel || I18n.t(label);
if (icon) {
@@ -18,7 +18,7 @@ export default Component.extend({
return text;
},
- @computed("route", "router.currentRoute")
+ @discourseComputed("route", "router.currentRoute")
active(route, currentRoute) {
if (!route) {
return;
diff --git a/app/assets/javascripts/discourse/components/navigation-bar.js.es6 b/app/assets/javascripts/discourse/components/navigation-bar.js.es6
index eb8cb454b3..6f262ce05c 100644
--- a/app/assets/javascripts/discourse/components/navigation-bar.js.es6
+++ b/app/assets/javascripts/discourse/components/navigation-bar.js.es6
@@ -1,9 +1,9 @@
import { next } from "@ember/runloop";
import Component from "@ember/component";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import DiscourseURL from "discourse/lib/url";
import { renderedConnectorsFor } from "discourse/lib/plugin-connectors";
@@ -17,7 +17,7 @@ export default Component.extend({
this.set("connectors", renderedConnectorsFor("extra-nav-item", null, this));
},
- @computed("filterMode", "navItems")
+ @discourseComputed("filterMode", "navItems")
selectedNavItem(filterMode, navItems) {
if (filterMode.indexOf("top/") === 0) {
filterMode = "top";
diff --git a/app/assets/javascripts/discourse/components/navigation-item.js.es6 b/app/assets/javascripts/discourse/components/navigation-item.js.es6
index 6d55112a94..98742db3d4 100644
--- a/app/assets/javascripts/discourse/components/navigation-item.js.es6
+++ b/app/assets/javascripts/discourse/components/navigation-item.js.es6
@@ -1,5 +1,5 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import { bufferedRender } from "discourse-common/lib/buffered-render";
export default Component.extend(
@@ -15,7 +15,7 @@ export default Component.extend(
hidden: false,
rerenderTriggers: ["content.count"],
- @computed("content.filterMode", "filterMode", "content.active")
+ @discourseComputed("content.filterMode", "filterMode", "content.active")
active(contentFilterMode, filterMode, active) {
if (active !== undefined) {
return active;
diff --git a/app/assets/javascripts/discourse/components/notification-consent-banner.js.es6 b/app/assets/javascripts/discourse/components/notification-consent-banner.js.es6
index 8d20705f04..1ffb99c0c2 100644
--- a/app/assets/javascripts/discourse/components/notification-consent-banner.js.es6
+++ b/app/assets/javascripts/discourse/components/notification-consent-banner.js.es6
@@ -1,13 +1,11 @@
-import { default as computed } from "ember-addons/ember-computed-decorators";
-
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import { keyValueStore as pushNotificationKeyValueStore } from "discourse/lib/push-notifications";
-
import { default as DesktopNotificationConfig } from "discourse/components/desktop-notification-config";
const userDismissedPromptKey = "dismissed-prompt";
export default DesktopNotificationConfig.extend({
- @computed
+ @discourseComputed
bannerDismissed: {
set(value) {
pushNotificationKeyValueStore.setItem(userDismissedPromptKey, value);
@@ -18,7 +16,7 @@ export default DesktopNotificationConfig.extend({
}
},
- @computed(
+ @discourseComputed(
"isNotSupported",
"isEnabled",
"bannerDismissed",
diff --git a/app/assets/javascripts/discourse/components/number-field.js.es6 b/app/assets/javascripts/discourse/components/number-field.js.es6
index 1399de713e..9de92f0afe 100644
--- a/app/assets/javascripts/discourse/components/number-field.js.es6
+++ b/app/assets/javascripts/discourse/components/number-field.js.es6
@@ -1,9 +1,9 @@
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
export default Ember.TextField.extend({
classNameBindings: ["invalid"],
- @computed("number")
+ @discourseComputed("number")
value: {
get(number) {
return parseInt(number);
@@ -21,7 +21,7 @@ export default Ember.TextField.extend({
}
},
- @computed("placeholderKey")
+ @discourseComputed("placeholderKey")
placeholder(key) {
return key ? I18n.t(key) : "";
}
diff --git a/app/assets/javascripts/discourse/components/plugin-connector.js.es6 b/app/assets/javascripts/discourse/components/plugin-connector.js.es6
index 715cb62965..a844ebbf9d 100644
--- a/app/assets/javascripts/discourse/components/plugin-connector.js.es6
+++ b/app/assets/javascripts/discourse/components/plugin-connector.js.es6
@@ -1,5 +1,5 @@
import Component from "@ember/component";
-import { observes } from "ember-addons/ember-computed-decorators";
+import { observes } from "discourse-common/utils/decorators";
export default Component.extend({
init() {
diff --git a/app/assets/javascripts/discourse/components/popup-input-tip.js.es6 b/app/assets/javascripts/discourse/components/popup-input-tip.js.es6
index 38930d57e4..3f3c3d514b 100644
--- a/app/assets/javascripts/discourse/components/popup-input-tip.js.es6
+++ b/app/assets/javascripts/discourse/components/popup-input-tip.js.es6
@@ -2,9 +2,9 @@ import { alias, not } from "@ember/object/computed";
import Component from "@ember/component";
import { iconHTML } from "discourse-common/lib/icon-library";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import { bufferedRender } from "discourse-common/lib/buffered-render";
export default Component.extend(
@@ -23,7 +23,7 @@ export default Component.extend(
bad: alias("validation.failed"),
good: not("bad"),
- @computed("shownAt", "validation.lastShownAt")
+ @discourseComputed("shownAt", "validation.lastShownAt")
lastShownAt(shownAt, lastShownAt) {
return shownAt || lastShownAt;
},
diff --git a/app/assets/javascripts/discourse/components/preference-checkbox.js.es6 b/app/assets/javascripts/discourse/components/preference-checkbox.js.es6
index 7ae299f5de..83ad27853f 100644
--- a/app/assets/javascripts/discourse/components/preference-checkbox.js.es6
+++ b/app/assets/javascripts/discourse/components/preference-checkbox.js.es6
@@ -1,10 +1,10 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
classNames: ["controls"],
- @computed("labelKey")
+ @discourseComputed("labelKey")
label(labelKey) {
return I18n.t(labelKey);
},
diff --git a/app/assets/javascripts/discourse/components/pwa-install-banner.js.es6 b/app/assets/javascripts/discourse/components/pwa-install-banner.js.es6
index e2e60f3d88..cb11ef38b7 100644
--- a/app/assets/javascripts/discourse/components/pwa-install-banner.js.es6
+++ b/app/assets/javascripts/discourse/components/pwa-install-banner.js.es6
@@ -1,9 +1,9 @@
import { bind } from "@ember/runloop";
import Component from "@ember/component";
import {
- default as computed,
+ default as discourseComputed,
on
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
const USER_DISMISSED_PROMPT_KEY = "dismissed-pwa-install-banner";
@@ -28,7 +28,7 @@ export default Component.extend({
window.removeEventListener("beforeinstallprompt", this._promptEventHandler);
},
- @computed
+ @discourseComputed
bannerDismissed: {
set(value) {
this.keyValueStore.set({ key: USER_DISMISSED_PROMPT_KEY, value });
@@ -39,7 +39,7 @@ export default Component.extend({
}
},
- @computed("deferredInstallPromptEvent", "bannerDismissed")
+ @discourseComputed("deferredInstallPromptEvent", "bannerDismissed")
showPWAInstallBanner() {
const launchedFromDiscourseHub =
window.location.search.indexOf("discourse_app=1") !== -1;
diff --git a/app/assets/javascripts/discourse/components/radio-button.js.es6 b/app/assets/javascripts/discourse/components/radio-button.js.es6
index b6d44b4a99..1094aca2c7 100644
--- a/app/assets/javascripts/discourse/components/radio-button.js.es6
+++ b/app/assets/javascripts/discourse/components/radio-button.js.es6
@@ -1,5 +1,5 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
tagName: "input",
@@ -25,7 +25,7 @@ export default Component.extend({
}
},
- @computed("value", "selection")
+ @discourseComputed("value", "selection")
checked(value, selection) {
return value === selection;
}
diff --git a/app/assets/javascripts/discourse/components/related-messages.js.es6 b/app/assets/javascripts/discourse/components/related-messages.js.es6
index bf95279941..5fec6f28ba 100644
--- a/app/assets/javascripts/discourse/components/related-messages.js.es6
+++ b/app/assets/javascripts/discourse/components/related-messages.js.es6
@@ -1,12 +1,12 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import { iconHTML } from "discourse-common/lib/icon-library";
export default Component.extend({
elementId: "related-messages",
classNames: ["suggested-topics"],
- @computed("topic")
+ @discourseComputed("topic")
targetUser(topic) {
if (!topic || !topic.isPrivateMessage) {
return;
@@ -23,14 +23,14 @@ export default Component.extend({
}
},
- @computed
+ @discourseComputed
searchLink() {
return Discourse.getURL(
`/search?expanded=true&q=%40${this.targetUser.username}%20in%3Apersonal-direct`
);
},
- @computed("topic")
+ @discourseComputed("topic")
relatedTitle(topic) {
const href = this.currentUser && this.currentUser.pmPath(topic);
return href
diff --git a/app/assets/javascripts/discourse/components/reviewable-claimed-topic.js.es6 b/app/assets/javascripts/discourse/components/reviewable-claimed-topic.js.es6
index 0583a4605f..273b51afa7 100644
--- a/app/assets/javascripts/discourse/components/reviewable-claimed-topic.js.es6
+++ b/app/assets/javascripts/discourse/components/reviewable-claimed-topic.js.es6
@@ -1,12 +1,12 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import { popupAjaxError } from "discourse/lib/ajax-error";
import { ajax } from "discourse/lib/ajax";
export default Component.extend({
tagName: "",
- @computed
+ @discourseComputed
enabled() {
return this.siteSettings.reviewable_claiming !== "disabled";
},
diff --git a/app/assets/javascripts/discourse/components/reviewable-flagged-post.js.es6 b/app/assets/javascripts/discourse/components/reviewable-flagged-post.js.es6
index 58c48d1bbf..d432beece9 100644
--- a/app/assets/javascripts/discourse/components/reviewable-flagged-post.js.es6
+++ b/app/assets/javascripts/discourse/components/reviewable-flagged-post.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { gt } from "@ember/object/computed";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import { longDate } from "discourse/lib/formatter";
import { historyHeat } from "discourse/widgets/post-edits-indicator";
import showModal from "discourse/lib/show-modal";
@@ -8,12 +8,12 @@ import showModal from "discourse/lib/show-modal";
export default Component.extend({
hasEdits: gt("reviewable.post_version", 1),
- @computed("reviewable.post_updated_at")
+ @discourseComputed("reviewable.post_updated_at")
historyClass(updatedAt) {
return historyHeat(this.siteSettings, new Date(updatedAt));
},
- @computed("reviewable.post_updated_at")
+ @discourseComputed("reviewable.post_updated_at")
editedDate(updatedAt) {
return longDate(updatedAt);
},
diff --git a/app/assets/javascripts/discourse/components/reviewable-item.js.es6 b/app/assets/javascripts/discourse/components/reviewable-item.js.es6
index c5aaba8b7b..ef6626ebec 100644
--- a/app/assets/javascripts/discourse/components/reviewable-item.js.es6
+++ b/app/assets/javascripts/discourse/components/reviewable-item.js.es6
@@ -1,7 +1,7 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
import { ajax } from "discourse/lib/ajax";
import { popupAjaxError } from "discourse/lib/ajax-error";
-import computed from "ember-addons/ember-computed-decorators";
import Category from "discourse/models/category";
import optionalService from "discourse/lib/optional-service";
import showModal from "discourse/lib/show-modal";
@@ -17,17 +17,17 @@ export default Component.extend({
editing: false,
_updates: null,
- @computed("reviewable.type")
+ @discourseComputed("reviewable.type")
customClass(type) {
return type.dasherize();
},
- @computed("siteSettings.reviewable_claiming", "reviewable.topic")
+ @discourseComputed("siteSettings.reviewable_claiming", "reviewable.topic")
claimEnabled(claimMode, topic) {
return claimMode !== "disabled" && !!topic;
},
- @computed(
+ @discourseComputed(
"claimEnabled",
"siteSettings.reviewable_claiming",
"reviewable.claimed_by"
@@ -44,7 +44,10 @@ export default Component.extend({
return claimMode !== "required";
},
- @computed("siteSettings.reviewable_claiming", "reviewable.claimed_by")
+ @discourseComputed(
+ "siteSettings.reviewable_claiming",
+ "reviewable.claimed_by"
+ )
claimHelp(claimMode, claimedBy) {
if (claimedBy) {
return claimedBy.id === this.currentUser.id
@@ -61,7 +64,7 @@ export default Component.extend({
// Find a component to render, if one exists. For example:
// `ReviewableUser` will return `reviewable-user`
- @computed("reviewable.type")
+ @discourseComputed("reviewable.type")
reviewableComponent(type) {
if (_components[type] !== undefined) {
return _components[type];
diff --git a/app/assets/javascripts/discourse/components/reviewable-user.js.es6 b/app/assets/javascripts/discourse/components/reviewable-user.js.es6
index ec065a0bde..3dd3043371 100644
--- a/app/assets/javascripts/discourse/components/reviewable-user.js.es6
+++ b/app/assets/javascripts/discourse/components/reviewable-user.js.es6
@@ -1,8 +1,8 @@
import Component from "@ember/component";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
export default Component.extend({
- @computed("reviewable.user_fields")
+ @discourseComputed("reviewable.user_fields")
userFields(fields) {
return this.site.collectUserFields(fields);
}
diff --git a/app/assets/javascripts/discourse/components/search-advanced-options.js.es6 b/app/assets/javascripts/discourse/components/search-advanced-options.js.es6
index 8f1779487d..42e85897ea 100644
--- a/app/assets/javascripts/discourse/components/search-advanced-options.js.es6
+++ b/app/assets/javascripts/discourse/components/search-advanced-options.js.es6
@@ -1,7 +1,7 @@
import { debounce } from "@ember/runloop";
import { scheduleOnce } from "@ember/runloop";
import Component from "@ember/component";
-import { observes } from "ember-addons/ember-computed-decorators";
+import { observes } from "discourse-common/utils/decorators";
import { escapeExpression } from "discourse/lib/utilities";
import Group from "discourse/models/group";
import Badge from "discourse/models/badge";
diff --git a/app/assets/javascripts/discourse/components/search-text-field.js.es6 b/app/assets/javascripts/discourse/components/search-text-field.js.es6
index 349918e22e..fc6ca86c08 100644
--- a/app/assets/javascripts/discourse/components/search-text-field.js.es6
+++ b/app/assets/javascripts/discourse/components/search-text-field.js.es6
@@ -1,12 +1,12 @@
-import computed from "ember-addons/ember-computed-decorators";
-import { on } from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
+import { on } from "discourse-common/utils/decorators";
import TextField from "discourse/components/text-field";
import { applySearchAutocomplete } from "discourse/lib/search";
export default TextField.extend({
autocomplete: "discourse",
- @computed("searchService.searchContextEnabled")
+ @discourseComputed("searchService.searchContextEnabled")
placeholder(searchContextEnabled) {
return searchContextEnabled ? "" : I18n.t("search.full_page_title");
},
diff --git a/app/assets/javascripts/discourse/components/second-factor-form.js.es6 b/app/assets/javascripts/discourse/components/second-factor-form.js.es6
index ce332c23b1..47bd68a487 100644
--- a/app/assets/javascripts/discourse/components/second-factor-form.js.es6
+++ b/app/assets/javascripts/discourse/components/second-factor-form.js.es6
@@ -1,9 +1,9 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import { SECOND_FACTOR_METHODS } from "discourse/models/user";
export default Component.extend({
- @computed("secondFactorMethod")
+ @discourseComputed("secondFactorMethod")
secondFactorTitle(secondFactorMethod) {
switch (secondFactorMethod) {
case SECOND_FACTOR_METHODS.TOTP:
@@ -15,7 +15,7 @@ export default Component.extend({
}
},
- @computed("secondFactorMethod")
+ @discourseComputed("secondFactorMethod")
secondFactorDescription(secondFactorMethod) {
switch (secondFactorMethod) {
case SECOND_FACTOR_METHODS.TOTP:
@@ -27,7 +27,7 @@ export default Component.extend({
}
},
- @computed("secondFactorMethod", "isLogin")
+ @discourseComputed("secondFactorMethod", "isLogin")
linkText(secondFactorMethod, isLogin) {
if (isLogin) {
return secondFactorMethod === SECOND_FACTOR_METHODS.TOTP
@@ -40,7 +40,7 @@ export default Component.extend({
}
},
- @computed("backupEnabled", "secondFactorMethod")
+ @discourseComputed("backupEnabled", "secondFactorMethod")
showToggleMethodLink(backupEnabled, secondFactorMethod) {
return (
backupEnabled && secondFactorMethod !== SECOND_FACTOR_METHODS.SECURITY_KEY
diff --git a/app/assets/javascripts/discourse/components/second-factor-input.js.es6 b/app/assets/javascripts/discourse/components/second-factor-input.js.es6
index 97ce1a4fa7..45ed1f4b9e 100644
--- a/app/assets/javascripts/discourse/components/second-factor-input.js.es6
+++ b/app/assets/javascripts/discourse/components/second-factor-input.js.es6
@@ -1,22 +1,22 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import { SECOND_FACTOR_METHODS } from "discourse/models/user";
export default Component.extend({
- @computed("secondFactorMethod")
+ @discourseComputed("secondFactorMethod")
type(secondFactorMethod) {
if (secondFactorMethod === SECOND_FACTOR_METHODS.TOTP) return "tel";
if (secondFactorMethod === SECOND_FACTOR_METHODS.BACKUP_CODE) return "text";
},
- @computed("secondFactorMethod")
+ @discourseComputed("secondFactorMethod")
pattern(secondFactorMethod) {
if (secondFactorMethod === SECOND_FACTOR_METHODS.TOTP) return "[0-9]{6}";
if (secondFactorMethod === SECOND_FACTOR_METHODS.BACKUP_CODE)
return "[a-z0-9]{16}";
},
- @computed("secondFactorMethod")
+ @discourseComputed("secondFactorMethod")
maxlength(secondFactorMethod) {
if (secondFactorMethod === SECOND_FACTOR_METHODS.TOTP) return "6";
if (secondFactorMethod === SECOND_FACTOR_METHODS.BACKUP_CODE) return "16";
diff --git a/app/assets/javascripts/discourse/components/share-panel.js.es6 b/app/assets/javascripts/discourse/components/share-panel.js.es6
index 3a7b94b645..97e09c225e 100644
--- a/app/assets/javascripts/discourse/components/share-panel.js.es6
+++ b/app/assets/javascripts/discourse/components/share-panel.js.es6
@@ -3,7 +3,7 @@ import { alias } from "@ember/object/computed";
import { schedule } from "@ember/runloop";
import Component from "@ember/component";
import { escapeExpression } from "discourse/lib/utilities";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import Sharing from "discourse/lib/sharing";
export default Component.extend({
@@ -13,18 +13,18 @@ export default Component.extend({
topic: alias("panel.model.topic"),
- @computed
+ @discourseComputed
sources() {
return Sharing.activeSources(this.siteSettings.share_links);
},
- @computed("type", "topic.title")
+ @discourseComputed("type", "topic.title")
shareTitle(type, topicTitle) {
topicTitle = escapeExpression(topicTitle);
return I18n.t("share.topic_html", { topicTitle });
},
- @computed("panel.model.shareUrl", "topic.shareUrl")
+ @discourseComputed("panel.model.shareUrl", "topic.shareUrl")
shareUrl(forcedShareUrl, shareUrl) {
shareUrl = forcedShareUrl || shareUrl;
diff --git a/app/assets/javascripts/discourse/components/share-popup.js.es6 b/app/assets/javascripts/discourse/components/share-popup.js.es6
index 4f9d0b9792..c2174068bd 100644
--- a/app/assets/javascripts/discourse/components/share-popup.js.es6
+++ b/app/assets/javascripts/discourse/components/share-popup.js.es6
@@ -5,9 +5,9 @@ import Component from "@ember/component";
import { wantsNewWindow } from "discourse/lib/intercept-click";
import { longDateNoYear } from "discourse/lib/formatter";
import {
- default as computed,
+ default as discourseComputed,
on
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import Sharing from "discourse/lib/sharing";
import { nativeShare } from "discourse/lib/pwa-utils";
@@ -17,12 +17,12 @@ export default Component.extend({
link: null,
visible: null,
- @computed
+ @discourseComputed
sources() {
return Sharing.activeSources(this.siteSettings.share_links);
},
- @computed("type", "postNumber")
+ @discourseComputed("type", "postNumber")
shareTitle(type, postNumber) {
if (type === "topic") {
return I18n.t("share.topic");
@@ -33,7 +33,7 @@ export default Component.extend({
return I18n.t("share.topic");
},
- @computed("date")
+ @discourseComputed("date")
displayDate(date) {
return longDateNoYear(new Date(date));
},
diff --git a/app/assets/javascripts/discourse/components/shared-draft-controls.js.es6 b/app/assets/javascripts/discourse/components/shared-draft-controls.js.es6
index b408ee87a1..0b988e75cf 100644
--- a/app/assets/javascripts/discourse/components/shared-draft-controls.js.es6
+++ b/app/assets/javascripts/discourse/components/shared-draft-controls.js.es6
@@ -1,11 +1,11 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
tagName: "",
publishing: false,
- @computed("topic.destination_category_id")
+ @discourseComputed("topic.destination_category_id")
validCategory(destCatId) {
return destCatId && destCatId !== this.site.shared_drafts_category_id;
},
diff --git a/app/assets/javascripts/discourse/components/site-header.js.es6 b/app/assets/javascripts/discourse/components/site-header.js.es6
index b7b82071c1..9bdd8f0d8b 100644
--- a/app/assets/javascripts/discourse/components/site-header.js.es6
+++ b/app/assets/javascripts/discourse/components/site-header.js.es6
@@ -2,7 +2,7 @@ import { cancel } from "@ember/runloop";
import { schedule } from "@ember/runloop";
import { later } from "@ember/runloop";
import MountWidget from "discourse/components/mount-widget";
-import { observes } from "ember-addons/ember-computed-decorators";
+import { observes } from "discourse-common/utils/decorators";
import Docking from "discourse/mixins/docking";
import PanEvents, {
SWIPE_VELOCITY,
diff --git a/app/assets/javascripts/discourse/components/suggested-topics.js.es6 b/app/assets/javascripts/discourse/components/suggested-topics.js.es6
index 11b6cbf20d..8351aa984b 100644
--- a/app/assets/javascripts/discourse/components/suggested-topics.js.es6
+++ b/app/assets/javascripts/discourse/components/suggested-topics.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { get } from "@ember/object";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import { categoryBadgeHTML } from "discourse/helpers/category-link";
import { iconHTML } from "discourse-common/lib/icon-library";
@@ -8,7 +8,7 @@ export default Component.extend({
elementId: "suggested-topics",
classNames: ["suggested-topics"],
- @computed("topic")
+ @discourseComputed("topic")
suggestedTitle(topic) {
const href = this.currentUser && this.currentUser.pmPath(topic);
return topic.get("isPrivateMessage") && href
@@ -20,7 +20,7 @@ export default Component.extend({
: I18n.t("suggested_topics.title");
},
- @computed("topic", "topicTrackingState.messageCount")
+ @discourseComputed("topic", "topicTrackingState.messageCount")
browseMoreMessage(topic) {
// TODO decide what to show for pms
if (topic.get("isPrivateMessage")) {
diff --git a/app/assets/javascripts/discourse/components/tag-drop-link.js.es6 b/app/assets/javascripts/discourse/components/tag-drop-link.js.es6
index 73d20d7922..e8cfada41a 100644
--- a/app/assets/javascripts/discourse/components/tag-drop-link.js.es6
+++ b/app/assets/javascripts/discourse/components/tag-drop-link.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
import DiscourseURL from "discourse/lib/url";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
tagName: "a",
@@ -12,7 +12,7 @@ export default Component.extend({
],
attributeBindings: ["href"],
- @computed("tagId", "category")
+ @discourseComputed("tagId", "category")
href(tagId, category) {
var url = "/tags";
if (category) {
@@ -21,7 +21,7 @@ export default Component.extend({
return url + "/" + tagId;
},
- @computed("tagId")
+ @discourseComputed("tagId")
tagClass(tagId) {
return "tag-" + tagId;
},
diff --git a/app/assets/javascripts/discourse/components/tag-groups-form.js.es6 b/app/assets/javascripts/discourse/components/tag-groups-form.js.es6
index 2dddb086e8..b77220cd08 100644
--- a/app/assets/javascripts/discourse/components/tag-groups-form.js.es6
+++ b/app/assets/javascripts/discourse/components/tag-groups-form.js.es6
@@ -1,13 +1,13 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { isEmpty } from "@ember/utils";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import { bufferedProperty } from "discourse/mixins/buffered-content";
import PermissionType from "discourse/models/permission-type";
export default Component.extend(bufferedProperty("model"), {
tagName: "",
- @computed("buffered.isSaving", "buffered.name", "buffered.tag_names")
+ @discourseComputed("buffered.isSaving", "buffered.name", "buffered.tag_names")
savingDisabled(isSaving, name, tagNames) {
return isSaving || isEmpty(name) || isEmpty(tagNames);
},
diff --git a/app/assets/javascripts/discourse/components/tag-list.js.es6 b/app/assets/javascripts/discourse/components/tag-list.js.es6
index 551b70c93d..ee6de7fa3a 100644
--- a/app/assets/javascripts/discourse/components/tag-list.js.es6
+++ b/app/assets/javascripts/discourse/components/tag-list.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { sort } from "@ember/object/computed";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
classNameBindings: [":tag-list", "categoryClass", "tagGroupNameClass"],
@@ -8,22 +8,22 @@ export default Component.extend({
isPrivateMessage: false,
sortedTags: sort("tags", "sortProperties"),
- @computed("titleKey")
+ @discourseComputed("titleKey")
title(titleKey) {
return titleKey && I18n.t(titleKey);
},
- @computed("categoryId")
+ @discourseComputed("categoryId")
category(categoryId) {
return categoryId && Discourse.Category.findById(categoryId);
},
- @computed("category.fullSlug")
+ @discourseComputed("category.fullSlug")
categoryClass(slug) {
return slug && `tag-list-${slug}`;
},
- @computed("tagGroupName")
+ @discourseComputed("tagGroupName")
tagGroupNameClass(groupName) {
if (groupName) {
groupName = groupName
diff --git a/app/assets/javascripts/discourse/components/text-field.js.es6 b/app/assets/javascripts/discourse/components/text-field.js.es6
index eca66af1d3..1978cd0ab2 100644
--- a/app/assets/javascripts/discourse/components/text-field.js.es6
+++ b/app/assets/javascripts/discourse/components/text-field.js.es6
@@ -1,4 +1,4 @@
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
import { siteDir, isRTL, isLTR } from "discourse/lib/text-direction";
export default Ember.TextField.extend({
@@ -10,7 +10,7 @@ export default Ember.TextField.extend({
"dir"
],
- @computed
+ @discourseComputed
dir() {
if (this.siteSettings.support_mixed_text_direction) {
let val = this.value;
@@ -37,7 +37,7 @@ export default Ember.TextField.extend({
}
},
- @computed("placeholderKey")
+ @discourseComputed("placeholderKey")
placeholder: {
get() {
if (this._placeholder) return this._placeholder;
diff --git a/app/assets/javascripts/discourse/components/top-period-buttons.js.es6 b/app/assets/javascripts/discourse/components/top-period-buttons.js.es6
index 9c01cf1a1d..0eaf69a992 100644
--- a/app/assets/javascripts/discourse/components/top-period-buttons.js.es6
+++ b/app/assets/javascripts/discourse/components/top-period-buttons.js.es6
@@ -1,10 +1,10 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
classNames: ["top-title-buttons"],
- @computed("period")
+ @discourseComputed("period")
periods(period) {
return this.site.get("periods").filter(p => p !== period);
},
diff --git a/app/assets/javascripts/discourse/components/topic-entrance.js.es6 b/app/assets/javascripts/discourse/components/topic-entrance.js.es6
index ead6913e82..3cfa8feb6a 100644
--- a/app/assets/javascripts/discourse/components/topic-entrance.js.es6
+++ b/app/assets/javascripts/discourse/components/topic-entrance.js.es6
@@ -1,8 +1,8 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { scheduleOnce } from "@ember/runloop";
import Component from "@ember/component";
import DiscourseURL from "discourse/lib/url";
import CleansUp from "discourse/mixins/cleans-up";
-import computed from "ember-addons/ember-computed-decorators";
function entranceDate(dt, showTime) {
const today = new Date();
@@ -34,23 +34,23 @@ export default Component.extend(CleansUp, {
topic: null,
visible: null,
- @computed("topic.created_at")
+ @discourseComputed("topic.created_at")
createdDate: createdAt => new Date(createdAt),
- @computed("topic.bumped_at")
+ @discourseComputed("topic.bumped_at")
bumpedDate: bumpedAt => new Date(bumpedAt),
- @computed("createdDate", "bumpedDate")
+ @discourseComputed("createdDate", "bumpedDate")
showTime(createdDate, bumpedDate) {
return (
bumpedDate.getTime() - createdDate.getTime() < 1000 * 60 * 60 * 24 * 2
);
},
- @computed("createdDate", "showTime")
+ @discourseComputed("createdDate", "showTime")
topDate: (createdDate, showTime) => entranceDate(createdDate, showTime),
- @computed("bumpedDate", "showTime")
+ @discourseComputed("bumpedDate", "showTime")
bottomDate: (bumpedDate, showTime) => entranceDate(bumpedDate, showTime),
didInsertElement() {
diff --git a/app/assets/javascripts/discourse/components/topic-footer-buttons.js.es6 b/app/assets/javascripts/discourse/components/topic-footer-buttons.js.es6
index 7c13728bff..5f4592aeed 100644
--- a/app/assets/javascripts/discourse/components/topic-footer-buttons.js.es6
+++ b/app/assets/javascripts/discourse/components/topic-footer-buttons.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { alias, or, and } from "@ember/object/computed";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import { getTopicFooterButtons } from "discourse/lib/register-topic-footer-button";
export default Component.extend({
@@ -9,25 +9,25 @@ export default Component.extend({
// Allow us to extend it
layoutName: "components/topic-footer-buttons",
- @computed("topic.isPrivateMessage")
+ @discourseComputed("topic.isPrivateMessage")
canArchive(isPM) {
return this.siteSettings.enable_personal_messages && isPM;
},
buttons: getTopicFooterButtons(),
- @computed("buttons.[]")
+ @discourseComputed("buttons.[]")
inlineButtons(buttons) {
return buttons.filter(button => !button.dropdown);
},
// topic.assigned_to_user is for backward plugin support
- @computed("buttons.[]", "topic.assigned_to_user")
+ @discourseComputed("buttons.[]", "topic.assigned_to_user")
dropdownButtons(buttons) {
return buttons.filter(button => button.dropdown);
},
- @computed("topic.isPrivateMessage")
+ @discourseComputed("topic.isPrivateMessage")
showNotificationsButton(isPM) {
return !isPM || this.siteSettings.enable_personal_messages;
},
@@ -38,7 +38,7 @@ export default Component.extend({
inviteDisabled: or("topic.archived", "topic.closed", "topic.deleted"),
- @computed
+ @discourseComputed
showAdminButton() {
return (
!this.site.mobileView &&
@@ -49,14 +49,14 @@ export default Component.extend({
showEditOnFooter: and("topic.isPrivateMessage", "site.can_tag_pms"),
- @computed("topic.message_archived")
+ @discourseComputed("topic.message_archived")
archiveIcon: archived => (archived ? "envelope" : "folder"),
- @computed("topic.message_archived")
+ @discourseComputed("topic.message_archived")
archiveTitle: archived =>
archived ? "topic.move_to_inbox.help" : "topic.archive_message.help",
- @computed("topic.message_archived")
+ @discourseComputed("topic.message_archived")
archiveLabel: archived =>
archived ? "topic.move_to_inbox.title" : "topic.archive_message.title"
});
diff --git a/app/assets/javascripts/discourse/components/topic-join-group-notice.js.es6 b/app/assets/javascripts/discourse/components/topic-join-group-notice.js.es6
index 114e02aa04..4a55fb8886 100644
--- a/app/assets/javascripts/discourse/components/topic-join-group-notice.js.es6
+++ b/app/assets/javascripts/discourse/components/topic-join-group-notice.js.es6
@@ -1,17 +1,17 @@
import Component from "@ember/component";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
export default Component.extend({
classNames: ["topic-notice"],
- @computed("model.group.{full_name,name,allow_membership_requests}")
+ @discourseComputed("model.group.{full_name,name,allow_membership_requests}")
accessViaGroupText(group) {
const name = group.full_name || group.name;
const suffix = group.allow_membership_requests ? "request" : "join";
return I18n.t(`topic.group_${suffix}`, { name });
},
- @computed("model.group.allow_membership_requests")
+ @discourseComputed("model.group.allow_membership_requests")
accessViaGroupButtonText(allowRequest) {
return `groups.${allowRequest ? "request" : "join"}`;
}
diff --git a/app/assets/javascripts/discourse/components/topic-list-item.js.es6 b/app/assets/javascripts/discourse/components/topic-list-item.js.es6
index 10161d7b51..670d45b64c 100644
--- a/app/assets/javascripts/discourse/components/topic-list-item.js.es6
+++ b/app/assets/javascripts/discourse/components/topic-list-item.js.es6
@@ -1,7 +1,7 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { alias } from "@ember/object/computed";
import Component from "@ember/component";
import DiscourseURL from "discourse/lib/url";
-import computed from "ember-addons/ember-computed-decorators";
import { bufferedRender } from "discourse-common/lib/buffered-render";
import { findRawTemplate } from "discourse/lib/raw-templates";
import { wantsNewWindow } from "discourse/lib/intercept-click";
@@ -64,29 +64,29 @@ export const ListItemDefaults = {
}
},
- @computed("topic.id")
+ @discourseComputed("topic.id")
unreadIndicatorChannel(topicId) {
return `/private-messages/unread-indicator/${topicId}`;
},
- @computed("topic.unread_by_group_member")
+ @discourseComputed("topic.unread_by_group_member")
unreadClass(unreadByGroupMember) {
return unreadByGroupMember ? "" : "read";
},
- @computed("topic.unread_by_group_member")
+ @discourseComputed("topic.unread_by_group_member")
includeUnreadIndicator(unreadByGroupMember) {
return typeof unreadByGroupMember !== "undefined";
},
- @computed
+ @discourseComputed
newDotText() {
return this.currentUser && this.currentUser.trust_level > 0
? ""
: I18n.t("filters.new.lower_title");
},
- @computed("topic", "lastVisitedTopic")
+ @discourseComputed("topic", "lastVisitedTopic")
unboundClassNames(topic, lastVisitedTopic) {
let classes = [];
@@ -131,7 +131,7 @@ export const ListItemDefaults = {
return this.get("topic.op_like_count") > 0;
},
- @computed
+ @discourseComputed
expandPinned: function() {
const pinned = this.get("topic.pinned");
if (!pinned) {
diff --git a/app/assets/javascripts/discourse/components/topic-list.js.es6 b/app/assets/javascripts/discourse/components/topic-list.js.es6
index 6d3ea337e2..d744b28a70 100644
--- a/app/assets/javascripts/discourse/components/topic-list.js.es6
+++ b/app/assets/javascripts/discourse/components/topic-list.js.es6
@@ -2,9 +2,9 @@ import { alias, reads } from "@ember/object/computed";
import { schedule } from "@ember/runloop";
import Component from "@ember/component";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import LoadMore from "discourse/mixins/load-more";
import { on } from "@ember/object/evented";
@@ -24,24 +24,24 @@ export default Component.extend(LoadMore, {
this.refreshLastVisited();
}),
- @computed("bulkSelectEnabled")
+ @discourseComputed("bulkSelectEnabled")
toggleInTitle(bulkSelectEnabled) {
return !bulkSelectEnabled && this.canBulkSelect;
},
- @computed
+ @discourseComputed
sortable() {
return !!this.changeSort;
},
skipHeader: reads("site.mobileView"),
- @computed("order")
+ @discourseComputed("order")
showLikes(order) {
return order === "likes";
},
- @computed("order")
+ @discourseComputed("order")
showOpLikes(order) {
return order === "op_likes";
},
diff --git a/app/assets/javascripts/discourse/components/topic-navigation.js.es6 b/app/assets/javascripts/discourse/components/topic-navigation.js.es6
index b2115e755d..3324814bf6 100644
--- a/app/assets/javascripts/discourse/components/topic-navigation.js.es6
+++ b/app/assets/javascripts/discourse/components/topic-navigation.js.es6
@@ -2,7 +2,7 @@ import EmberObject from "@ember/object";
import { scheduleOnce } from "@ember/runloop";
import { later } from "@ember/runloop";
import Component from "@ember/component";
-import { observes } from "ember-addons/ember-computed-decorators";
+import { observes } from "discourse-common/utils/decorators";
import showModal from "discourse/lib/show-modal";
import PanEvents, {
SWIPE_VELOCITY,
diff --git a/app/assets/javascripts/discourse/components/topic-progress.js.es6 b/app/assets/javascripts/discourse/components/topic-progress.js.es6
index 9d5cb2103f..3e055c96ed 100644
--- a/app/assets/javascripts/discourse/components/topic-progress.js.es6
+++ b/app/assets/javascripts/discourse/components/topic-progress.js.es6
@@ -2,9 +2,9 @@ import { alias } from "@ember/object/computed";
import { scheduleOnce } from "@ember/runloop";
import Component from "@ember/component";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
export default Component.extend({
elementId: "topic-progress-wrapper",
@@ -14,12 +14,12 @@ export default Component.extend({
postStream: alias("topic.postStream"),
_streamPercentage: null,
- @computed("progressPosition")
+ @discourseComputed("progressPosition")
jumpTopDisabled(progressPosition) {
return progressPosition <= 3;
},
- @computed(
+ @discourseComputed(
"postStream.filteredPostsCount",
"topic.highest_post_number",
"progressPosition"
@@ -31,7 +31,7 @@ export default Component.extend({
);
},
- @computed(
+ @discourseComputed(
"postStream.loaded",
"topic.currentPost",
"postStream.filteredPostsCount"
@@ -44,14 +44,14 @@ export default Component.extend({
);
},
- @computed("postStream.filteredPostsCount")
+ @discourseComputed("postStream.filteredPostsCount")
hugeNumberOfPosts(filteredPostsCount) {
return (
filteredPostsCount >= this.siteSettings.short_progress_text_threshold
);
},
- @computed("hugeNumberOfPosts", "topic.highest_post_number")
+ @discourseComputed("hugeNumberOfPosts", "topic.highest_post_number")
jumpToBottomTitle(hugeNumberOfPosts, highestPostNumber) {
if (hugeNumberOfPosts) {
return I18n.t("topic.progress.jump_bottom_with_number", {
@@ -62,7 +62,7 @@ export default Component.extend({
}
},
- @computed("progressPosition", "topic.last_read_post_id")
+ @discourseComputed("progressPosition", "topic.last_read_post_id")
showBackButton(position, lastReadId) {
if (!lastReadId) {
return;
diff --git a/app/assets/javascripts/discourse/components/topic-status.js.es6 b/app/assets/javascripts/discourse/components/topic-status.js.es6
index dc3e0d14f6..dd1f6c5066 100644
--- a/app/assets/javascripts/discourse/components/topic-status.js.es6
+++ b/app/assets/javascripts/discourse/components/topic-status.js.es6
@@ -1,9 +1,9 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
import { iconHTML } from "discourse-common/lib/icon-library";
import { bufferedRender } from "discourse-common/lib/buffered-render";
import { escapeExpression } from "discourse/lib/utilities";
import TopicStatusIcons from "discourse/helpers/topic-status-icons";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend(
bufferedRender({
@@ -28,7 +28,7 @@ export default Component.extend(
return false;
},
- @computed("disableActions")
+ @discourseComputed("disableActions")
canAct(disableActions) {
return this.currentUser && !disableActions;
},
diff --git a/app/assets/javascripts/discourse/components/topic-timeline.js.es6 b/app/assets/javascripts/discourse/components/topic-timeline.js.es6
index 9aa6541065..b802d47586 100644
--- a/app/assets/javascripts/discourse/components/topic-timeline.js.es6
+++ b/app/assets/javascripts/discourse/components/topic-timeline.js.es6
@@ -1,7 +1,7 @@
import { next } from "@ember/runloop";
import MountWidget from "discourse/components/mount-widget";
import Docking from "discourse/mixins/docking";
-import { observes } from "ember-addons/ember-computed-decorators";
+import { observes } from "discourse-common/utils/decorators";
import optionalService from "discourse/lib/optional-service";
const headerPadding = () => {
diff --git a/app/assets/javascripts/discourse/components/topic-timer-info.js.es6 b/app/assets/javascripts/discourse/components/topic-timer-info.js.es6
index 3f219f3143..487307f624 100644
--- a/app/assets/javascripts/discourse/components/topic-timer-info.js.es6
+++ b/app/assets/javascripts/discourse/components/topic-timer-info.js.es6
@@ -1,10 +1,10 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { cancel } from "@ember/runloop";
import { later } from "@ember/runloop";
import Component from "@ember/component";
import { iconHTML } from "discourse-common/lib/icon-library";
import { bufferedRender } from "discourse-common/lib/buffered-render";
import Category from "discourse/models/category";
-import computed from "ember-addons/ember-computed-decorators";
import { REMINDER_TYPE } from "discourse/controllers/edit-topic-timer";
import ENV from "discourse-common/config/environment";
@@ -22,7 +22,7 @@ export default Component.extend(
"categoryId"
],
- @computed("statusType")
+ @discourseComputed("statusType")
canRemoveTimer(type) {
if (type === REMINDER_TYPE) return true;
return this.currentUser && this.currentUser.get("canManageTopic");
diff --git a/app/assets/javascripts/discourse/components/user-badge.js.es6 b/app/assets/javascripts/discourse/components/user-badge.js.es6
index 85de291634..6f9c4850b5 100644
--- a/app/assets/javascripts/discourse/components/user-badge.js.es6
+++ b/app/assets/javascripts/discourse/components/user-badge.js.es6
@@ -1,15 +1,15 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
tagName: "span",
- @computed("count")
+ @discourseComputed("count")
showGrantCount(count) {
return count && count > 1;
},
- @computed("badge", "user")
+ @discourseComputed("badge", "user")
badgeUrl() {
// NOTE: I tried using a link-to helper here but the queryParams mean it fails
var username = this.get("user.username_lower") || "";
diff --git a/app/assets/javascripts/discourse/components/user-card-contents.js.es6 b/app/assets/javascripts/discourse/components/user-card-contents.js.es6
index 9163d36d53..255e494f21 100644
--- a/app/assets/javascripts/discourse/components/user-card-contents.js.es6
+++ b/app/assets/javascripts/discourse/components/user-card-contents.js.es6
@@ -3,9 +3,9 @@ import { alias, gte, and, gt, not, or } from "@ember/object/computed";
import EmberObject from "@ember/object";
import Component from "@ember/component";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import User from "discourse/models/user";
import { propertyNotEqual, setting } from "discourse/lib/computed";
import { durationTiny } from "discourse/lib/formatter";
@@ -50,26 +50,26 @@ export default Component.extend(CardContentsBase, CanCheckEmails, CleansUp, {
// If inside a topic
topicPostCount: null,
- @computed("user.staff")
+ @discourseComputed("user.staff")
staff: isStaff => (isStaff ? "staff" : ""),
- @computed("user.trust_level")
+ @discourseComputed("user.trust_level")
newUser: trustLevel => (trustLevel === 0 ? "new-user" : ""),
- @computed("user.name")
+ @discourseComputed("user.name")
nameFirst(name) {
return prioritizeNameInUx(name, this.siteSettings);
},
- @computed("username")
+ @discourseComputed("username")
usernameClass: username => (username ? `user-card-${username}` : ""),
- @computed("username", "topicPostCount")
+ @discourseComputed("username", "topicPostCount")
togglePostsLabel(username, count) {
return I18n.t("topic.filter_to", { username, count });
},
- @computed("user.user_fields.@each.value")
+ @discourseComputed("user.user_fields.@each.value")
publicUserFields() {
const siteUserFields = this.site.get("user_fields");
if (!isEmpty(siteUserFields)) {
@@ -86,25 +86,25 @@ export default Component.extend(CardContentsBase, CanCheckEmails, CleansUp, {
}
},
- @computed("user.trust_level")
+ @discourseComputed("user.trust_level")
removeNoFollow(trustLevel) {
return trustLevel > 2 && !this.siteSettings.tl3_links_no_follow;
},
- @computed("user.badge_count", "user.featured_user_badges.length")
+ @discourseComputed("user.badge_count", "user.featured_user_badges.length")
moreBadgesCount: (badgeCount, badgeLength) => badgeCount - badgeLength,
- @computed("user.time_read", "user.recent_time_read")
+ @discourseComputed("user.time_read", "user.recent_time_read")
showRecentTimeRead(timeRead, recentTimeRead) {
return timeRead !== recentTimeRead && recentTimeRead !== 0;
},
- @computed("user.recent_time_read")
+ @discourseComputed("user.recent_time_read")
recentTimeRead(recentTimeReadSeconds) {
return durationTiny(recentTimeReadSeconds);
},
- @computed("showRecentTimeRead", "user.time_read", "recentTimeRead")
+ @discourseComputed("showRecentTimeRead", "user.time_read", "recentTimeRead")
timeReadTooltip(showRecent, timeRead, recentTimeRead) {
if (showRecent) {
return I18n.t("time_read_recently_tooltip", {
diff --git a/app/assets/javascripts/discourse/components/user-field.js.es6 b/app/assets/javascripts/discourse/components/user-field.js.es6
index b54cbafd0a..f8e2554ab0 100644
--- a/app/assets/javascripts/discourse/components/user-field.js.es6
+++ b/app/assets/javascripts/discourse/components/user-field.js.es6
@@ -1,17 +1,17 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
import { fmt } from "discourse/lib/computed";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
classNameBindings: [":user-field", "field.field_type", "customFieldClass"],
layoutName: fmt("field.field_type", "components/user-fields/%@"),
- @computed
+ @discourseComputed
noneLabel() {
return "user_fields.none";
},
- @computed("field.name")
+ @discourseComputed("field.name")
customFieldClass(fieldName) {
if (fieldName) {
fieldName = fieldName
diff --git a/app/assets/javascripts/discourse/components/user-flag-percentage.js.es6 b/app/assets/javascripts/discourse/components/user-flag-percentage.js.es6
index 5c24fb70af..60e3c4ccef 100644
--- a/app/assets/javascripts/discourse/components/user-flag-percentage.js.es6
+++ b/app/assets/javascripts/discourse/components/user-flag-percentage.js.es6
@@ -1,16 +1,16 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
tagName: "",
- @computed("percentage")
+ @discourseComputed("percentage")
showPercentage(percentage) {
return percentage.total >= 3;
},
// We do a little logic to choose which icon to display and which text
- @computed("agreed", "disagreed", "ignored")
+ @discourseComputed("agreed", "disagreed", "ignored")
percentage(agreed, disagreed, ignored) {
let total = agreed + disagreed + ignored;
let result = { total };
diff --git a/app/assets/javascripts/discourse/components/user-info.js.es6 b/app/assets/javascripts/discourse/components/user-info.js.es6
index 5873829a25..2de553d13d 100644
--- a/app/assets/javascripts/discourse/components/user-info.js.es6
+++ b/app/assets/javascripts/discourse/components/user-info.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { alias } from "@ember/object/computed";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
import { userPath } from "discourse/lib/url";
export function normalize(name) {
@@ -12,7 +12,7 @@ export default Component.extend({
attributeBindings: ["data-username"],
size: "small",
- @computed("user.username")
+ @discourseComputed("user.username")
userPath(username) {
return userPath(username);
},
@@ -22,7 +22,7 @@ export default Component.extend({
// TODO: In later ember releases `hasBlock` works without this
hasBlock: alias("template"),
- @computed("user.name", "user.username")
+ @discourseComputed("user.name", "user.username")
name(name, username) {
if (name && normalize(username) !== normalize(name)) {
return name;
diff --git a/app/assets/javascripts/discourse/components/user-notifications-large.js.es6 b/app/assets/javascripts/discourse/components/user-notifications-large.js.es6
index de804fb75e..3d2a2112b5 100644
--- a/app/assets/javascripts/discourse/components/user-notifications-large.js.es6
+++ b/app/assets/javascripts/discourse/components/user-notifications-large.js.es6
@@ -1,5 +1,5 @@
import MountWidget from "discourse/components/mount-widget";
-import { observes } from "ember-addons/ember-computed-decorators";
+import { observes } from "discourse-common/utils/decorators";
export default MountWidget.extend({
widget: "user-notifications-large",
diff --git a/app/assets/javascripts/discourse/components/user-selector.js.es6 b/app/assets/javascripts/discourse/components/user-selector.js.es6
index 772777543c..e6170b81ed 100644
--- a/app/assets/javascripts/discourse/components/user-selector.js.es6
+++ b/app/assets/javascripts/discourse/components/user-selector.js.es6
@@ -1,5 +1,5 @@
import { isEmpty } from "@ember/utils";
-import { on, observes } from "ember-addons/ember-computed-decorators";
+import { on, observes } from "discourse-common/utils/decorators";
import TextField from "discourse/components/text-field";
import userSearch from "discourse/lib/user-search";
import { findRawTemplate } from "discourse/lib/raw-templates";
diff --git a/app/assets/javascripts/discourse/components/user-summary-category-search.js.es6 b/app/assets/javascripts/discourse/components/user-summary-category-search.js.es6
index 5206a83988..202ee1eb58 100644
--- a/app/assets/javascripts/discourse/components/user-summary-category-search.js.es6
+++ b/app/assets/javascripts/discourse/components/user-summary-category-search.js.es6
@@ -1,10 +1,10 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
tagName: "",
- @computed("user", "category")
+ @discourseComputed("user", "category")
searchParams() {
return `@${this.get("user.username")} #${this.get("category.slug")}`;
}
diff --git a/app/assets/javascripts/discourse/components/user-summary-topics-list.js.es6 b/app/assets/javascripts/discourse/components/user-summary-topics-list.js.es6
index 39970994da..5cee1e00e9 100644
--- a/app/assets/javascripts/discourse/components/user-summary-topics-list.js.es6
+++ b/app/assets/javascripts/discourse/components/user-summary-topics-list.js.es6
@@ -1,5 +1,5 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
// should be kept in sync with 'UserSummary::MAX_SUMMARY_RESULTS'
const MAX_SUMMARY_RESULTS = 6;
@@ -7,7 +7,7 @@ const MAX_SUMMARY_RESULTS = 6;
export default Component.extend({
tagName: "",
- @computed("items.length")
+ @discourseComputed("items.length")
hasMore(length) {
return length >= MAX_SUMMARY_RESULTS;
}
diff --git a/app/assets/javascripts/discourse/controllers/about.js.es6 b/app/assets/javascripts/discourse/controllers/about.js.es6
index 85f26757ae..9225421995 100644
--- a/app/assets/javascripts/discourse/controllers/about.js.es6
+++ b/app/assets/javascripts/discourse/controllers/about.js.es6
@@ -1,11 +1,11 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { gt } from "@ember/object/computed";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
export default Controller.extend({
faqOverriden: gt("siteSettings.faq_url.length", 0),
- @computed
+ @discourseComputed
contactInfo() {
if (this.siteSettings.contact_url) {
return I18n.t("about.contact_info", {
diff --git a/app/assets/javascripts/discourse/controllers/account-created-edit-email.js.es6 b/app/assets/javascripts/discourse/controllers/account-created-edit-email.js.es6
index 1002a90752..dd3314110b 100644
--- a/app/assets/javascripts/discourse/controllers/account-created-edit-email.js.es6
+++ b/app/assets/javascripts/discourse/controllers/account-created-edit-email.js.es6
@@ -1,13 +1,13 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Controller from "@ember/controller";
import { changeEmail } from "discourse/lib/user-activation";
-import computed from "ember-addons/ember-computed-decorators";
import { popupAjaxError } from "discourse/lib/ajax-error";
export default Controller.extend({
accountCreated: null,
newEmail: null,
- @computed("newEmail", "accountCreated.email")
+ @discourseComputed("newEmail", "accountCreated.email")
submitDisabled(newEmail, currentEmail) {
return newEmail === currentEmail;
},
diff --git a/app/assets/javascripts/discourse/controllers/activation-edit.js.es6 b/app/assets/javascripts/discourse/controllers/activation-edit.js.es6
index 8fc90f6cf0..010878f720 100644
--- a/app/assets/javascripts/discourse/controllers/activation-edit.js.es6
+++ b/app/assets/javascripts/discourse/controllers/activation-edit.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
import ModalFunctionality from "discourse/mixins/modal-functionality";
import { extractError } from "discourse/lib/ajax-error";
import { changeEmail } from "discourse/lib/user-activation";
@@ -12,7 +12,7 @@ export default Controller.extend(ModalFunctionality, {
newEmail: null,
password: null,
- @computed("newEmail", "currentEmail")
+ @discourseComputed("newEmail", "currentEmail")
submitDisabled(newEmail, currentEmail) {
return newEmail === currentEmail;
},
diff --git a/app/assets/javascripts/discourse/controllers/add-post-notice.js.es6 b/app/assets/javascripts/discourse/controllers/add-post-notice.js.es6
index 83883ca5aa..b0c92b3a81 100644
--- a/app/assets/javascripts/discourse/controllers/add-post-notice.js.es6
+++ b/app/assets/javascripts/discourse/controllers/add-post-notice.js.es6
@@ -1,7 +1,7 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { isEmpty } from "@ember/utils";
import Controller from "@ember/controller";
import ModalFunctionality from "discourse/mixins/modal-functionality";
-import computed from "ember-addons/ember-computed-decorators";
import { cookAsync } from "discourse/lib/text";
export default Controller.extend(ModalFunctionality, {
@@ -12,7 +12,7 @@ export default Controller.extend(ModalFunctionality, {
notice: null,
saving: false,
- @computed("saving", "notice")
+ @discourseComputed("saving", "notice")
disabled(saving, notice) {
return saving || isEmpty(notice);
},
diff --git a/app/assets/javascripts/discourse/controllers/application.js.es6 b/app/assets/javascripts/discourse/controllers/application.js.es6
index 610e745e64..c96c10c6e0 100644
--- a/app/assets/javascripts/discourse/controllers/application.js.es6
+++ b/app/assets/javascripts/discourse/controllers/application.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { inject as service } from "@ember/service";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
import { isAppWebview, isiOSPWA } from "discourse/lib/utilities";
export default Controller.extend({
@@ -8,7 +8,7 @@ export default Controller.extend({
showFooter: false,
router: service(),
- @computed
+ @discourseComputed
canSignUp() {
return (
!Discourse.SiteSettings.invite_only &&
@@ -17,12 +17,12 @@ export default Controller.extend({
);
},
- @computed
+ @discourseComputed
loginRequired() {
return Discourse.SiteSettings.login_required && !this.currentUser;
},
- @computed
+ @discourseComputed
showFooterNav() {
return isAppWebview() || isiOSPWA();
}
diff --git a/app/assets/javascripts/discourse/controllers/avatar-selector.js.es6 b/app/assets/javascripts/discourse/controllers/avatar-selector.js.es6
index 1a23033580..59c28e6932 100644
--- a/app/assets/javascripts/discourse/controllers/avatar-selector.js.es6
+++ b/app/assets/javascripts/discourse/controllers/avatar-selector.js.es6
@@ -1,12 +1,12 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
import ModalFunctionality from "discourse/mixins/modal-functionality";
import { ajax } from "discourse/lib/ajax";
import { allowsImages } from "discourse/lib/utilities";
import { popupAjaxError } from "discourse/lib/ajax-error";
export default Controller.extend(ModalFunctionality, {
- @computed(
+ @discourseComputed(
"selected",
"user.system_avatar_upload_id",
"user.gravatar_avatar_upload_id",
@@ -23,7 +23,7 @@ export default Controller.extend(ModalFunctionality, {
}
},
- @computed(
+ @discourseComputed(
"selected",
"user.system_avatar_template",
"user.gravatar_avatar_template",
@@ -40,7 +40,7 @@ export default Controller.extend(ModalFunctionality, {
}
},
- @computed()
+ @discourseComputed()
allowAvatarUpload() {
return this.siteSettings.allow_uploaded_avatars && allowsImages();
},
diff --git a/app/assets/javascripts/discourse/controllers/badges/index.js.es6 b/app/assets/javascripts/discourse/controllers/badges/index.js.es6
index c1c4d8db27..e056401703 100644
--- a/app/assets/javascripts/discourse/controllers/badges/index.js.es6
+++ b/app/assets/javascripts/discourse/controllers/badges/index.js.es6
@@ -1,8 +1,8 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
export default Controller.extend({
- @computed("model")
+ @discourseComputed("model")
badgeGroups(model) {
var sorted = _.sortBy(model, function(badge) {
var pos = badge.get("badge_grouping.position");
diff --git a/app/assets/javascripts/discourse/controllers/badges/show.js.es6 b/app/assets/javascripts/discourse/controllers/badges/show.js.es6
index d1093c13bc..807ea2b596 100644
--- a/app/assets/javascripts/discourse/controllers/badges/show.js.es6
+++ b/app/assets/javascripts/discourse/controllers/badges/show.js.es6
@@ -4,9 +4,9 @@ import Controller from "@ember/controller";
import Badge from "discourse/models/badge";
import UserBadge from "discourse/models/user-badge";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
export default Controller.extend({
queryParams: ["username"],
@@ -15,12 +15,12 @@ export default Controller.extend({
application: inject(),
hiddenSetTitle: true,
- @computed("userBadgesAll")
+ @discourseComputed("userBadgesAll")
filteredList(userBadgesAll) {
return userBadgesAll.filterBy("badge.allow_title", true);
},
- @computed("filteredList")
+ @discourseComputed("filteredList")
selectableUserBadges(filteredList) {
return [
EmberObject.create({
@@ -30,24 +30,24 @@ export default Controller.extend({
];
},
- @computed("username")
+ @discourseComputed("username")
user(username) {
if (username) {
return this.userBadges[0].get("user");
}
},
- @computed("username", "model.grant_count", "userBadges.grant_count")
+ @discourseComputed("username", "model.grant_count", "userBadges.grant_count")
grantCount(username, modelCount, userCount) {
return username ? userCount : modelCount;
},
- @computed("model.grant_count", "userBadges.grant_count")
+ @discourseComputed("model.grant_count", "userBadges.grant_count")
othersCount(modelCount, userCount) {
return modelCount - userCount;
},
- @computed("model.allow_title", "model.has_badge", "model")
+ @discourseComputed("model.allow_title", "model.has_badge", "model")
canSelectTitle(hasTitleBadges, hasBadge) {
return this.siteSettings.enable_badges && hasTitleBadges && hasBadge;
},
@@ -81,7 +81,7 @@ export default Controller.extend({
}
},
- @computed("noMoreBadges", "grantCount", "userBadges.length")
+ @discourseComputed("noMoreBadges", "grantCount", "userBadges.length")
canLoadMore(noMoreBadges, grantCount, userBadgeLength) {
if (noMoreBadges) {
return false;
@@ -89,7 +89,7 @@ export default Controller.extend({
return grantCount > (userBadgeLength || 0);
},
- @computed("user", "model.grant_count")
+ @discourseComputed("user", "model.grant_count")
canShowOthers(user, grantCount) {
return !!user && grantCount > 1;
},
diff --git a/app/assets/javascripts/discourse/controllers/bulk-notification-level.js.es6 b/app/assets/javascripts/discourse/controllers/bulk-notification-level.js.es6
index 0d8ac58ca2..d9627ee47f 100644
--- a/app/assets/javascripts/discourse/controllers/bulk-notification-level.js.es6
+++ b/app/assets/javascripts/discourse/controllers/bulk-notification-level.js.es6
@@ -1,7 +1,7 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { empty } from "@ember/object/computed";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
import { topicLevels } from "discourse/lib/notification-levels";
// Support for changing the notification level of various topics
@@ -9,7 +9,7 @@ export default Controller.extend({
topicBulkActions: inject(),
notificationLevelId: null,
- @computed
+ @discourseComputed
notificationLevels() {
return topicLevels.map(level => {
return {
diff --git a/app/assets/javascripts/discourse/controllers/change-owner.js.es6 b/app/assets/javascripts/discourse/controllers/change-owner.js.es6
index 9a738881d5..0380faf86c 100644
--- a/app/assets/javascripts/discourse/controllers/change-owner.js.es6
+++ b/app/assets/javascripts/discourse/controllers/change-owner.js.es6
@@ -1,3 +1,4 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { isEmpty } from "@ember/utils";
import { alias } from "@ember/object/computed";
import { next } from "@ember/runloop";
@@ -6,7 +7,6 @@ import Controller from "@ember/controller";
import ModalFunctionality from "discourse/mixins/modal-functionality";
import DiscourseURL from "discourse/lib/url";
import Topic from "discourse/models/topic";
-import computed from "ember-addons/ember-computed-decorators";
export default Controller.extend(ModalFunctionality, {
topicController: inject("topic"),
@@ -17,7 +17,7 @@ export default Controller.extend(ModalFunctionality, {
selectedPostsCount: alias("topicController.selectedPostsCount"),
selectedPostsUsername: alias("topicController.selectedPostsUsername"),
- @computed("saving", "new_user")
+ @discourseComputed("saving", "new_user")
buttonDisabled(saving, newUser) {
return saving || isEmpty(newUser);
},
diff --git a/app/assets/javascripts/discourse/controllers/change-timestamp.js.es6 b/app/assets/javascripts/discourse/controllers/change-timestamp.js.es6
index 9a29c747d7..5cb6bdba53 100644
--- a/app/assets/javascripts/discourse/controllers/change-timestamp.js.es6
+++ b/app/assets/javascripts/discourse/controllers/change-timestamp.js.es6
@@ -1,9 +1,9 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { isEmpty } from "@ember/utils";
import { next } from "@ember/runloop";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
import ModalFunctionality from "discourse/mixins/modal-functionality";
-import computed from "ember-addons/ember-computed-decorators";
import DiscourseURL from "discourse/lib/url";
import Topic from "discourse/models/topic";
@@ -14,22 +14,22 @@ export default Controller.extend(ModalFunctionality, {
date: "",
time: "",
- @computed("saving")
+ @discourseComputed("saving")
buttonTitle(saving) {
return saving ? I18n.t("saving") : I18n.t("topic.change_timestamp.action");
},
- @computed("date", "time")
+ @discourseComputed("date", "time")
createdAt(date, time) {
return moment(`${date} ${time}`, "YYYY-MM-DD HH:mm:ss");
},
- @computed("createdAt")
+ @discourseComputed("createdAt")
validTimestamp(createdAt) {
return moment().diff(createdAt, "minutes") < 0;
},
- @computed("saving", "date", "validTimestamp")
+ @discourseComputed("saving", "date", "validTimestamp")
buttonDisabled(saving, date, validTimestamp) {
if (saving || validTimestamp) return true;
return isEmpty(date);
diff --git a/app/assets/javascripts/discourse/controllers/composer.js.es6 b/app/assets/javascripts/discourse/controllers/composer.js.es6
index ce4b607add..818f70c089 100644
--- a/app/assets/javascripts/discourse/controllers/composer.js.es6
+++ b/app/assets/javascripts/discourse/controllers/composer.js.es6
@@ -9,10 +9,10 @@ import Quote from "discourse/lib/quote";
import Draft from "discourse/models/draft";
import Composer from "discourse/models/composer";
import {
- default as computed,
+ default as discourseComputed,
observes,
on
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import InputValidation from "discourse/models/input-validation";
import { getOwner } from "discourse-common/lib/get-owner";
import {
@@ -110,7 +110,7 @@ export default Controller.extend({
this.set("showPreview", val === "true");
},
- @computed("showPreview")
+ @discourseComputed("showPreview")
toggleText(showPreview) {
return showPreview
? I18n.t("composer.hide_preview")
@@ -127,7 +127,7 @@ export default Controller.extend({
}
},
- @computed(
+ @discourseComputed(
"model.replyingToTopic",
"model.creatingPrivateMessage",
"model.targetUsernames",
@@ -184,7 +184,7 @@ export default Controller.extend({
topicModel: alias("topicController.model"),
- @computed("model.canEditTitle", "model.creatingPrivateMessage")
+ @discourseComputed("model.canEditTitle", "model.creatingPrivateMessage")
canEditTags(canEditTitle, creatingPrivateMessage) {
return (
this.site.can_tag_topics &&
@@ -194,12 +194,12 @@ export default Controller.extend({
);
},
- @computed("model.editingPost", "model.topic.details.can_edit")
+ @discourseComputed("model.editingPost", "model.topic.details.can_edit")
disableCategoryChooser(editingPost, canEditTopic) {
return editingPost && !canEditTopic;
},
- @computed("model.editingPost", "model.topic.canEditTags")
+ @discourseComputed("model.editingPost", "model.topic.canEditTags")
disableTagsChooser(editingPost, canEditTags) {
return editingPost && !canEditTags;
},
@@ -208,12 +208,12 @@ export default Controller.extend({
canUnlistTopic: and("model.creatingTopic", "isStaffUser"),
- @computed("canWhisper", "replyingToWhisper")
+ @discourseComputed("canWhisper", "replyingToWhisper")
showWhisperToggle(canWhisper, replyingToWhisper) {
return canWhisper && !replyingToWhisper;
},
- @computed("model.post")
+ @discourseComputed("model.post")
replyingToWhisper(repliedToPost) {
return (
repliedToPost && repliedToPost.post_type === this.site.post_types.whisper
@@ -222,14 +222,14 @@ export default Controller.extend({
isWhispering: or("replyingToWhisper", "model.whisper"),
- @computed("model.action", "isWhispering")
+ @discourseComputed("model.action", "isWhispering")
saveIcon(action, isWhispering) {
if (isWhispering) return "far-eye-slash";
return SAVE_ICONS[action];
},
- @computed("model.action", "isWhispering", "model.editConflict")
+ @discourseComputed("model.action", "isWhispering", "model.editConflict")
saveLabel(action, isWhispering, editConflict) {
if (editConflict) return "composer.overwrite_edit";
else if (isWhispering) return "composer.create_whisper";
@@ -237,7 +237,7 @@ export default Controller.extend({
return SAVE_LABELS[action];
},
- @computed("isStaffUser", "model.action")
+ @discourseComputed("isStaffUser", "model.action")
canWhisper(isStaffUser, action) {
return (
this.siteSettings.enable_whispers &&
@@ -260,7 +260,7 @@ export default Controller.extend({
return option;
},
- @computed("model.composeState", "model.creatingTopic", "model.post")
+ @discourseComputed("model.composeState", "model.creatingTopic", "model.post")
popupMenuOptions(composeState) {
if (composeState === "open" || composeState === "fullscreen") {
const options = [];
@@ -295,7 +295,7 @@ export default Controller.extend({
}
},
- @computed("model.creatingPrivateMessage", "model.targetUsernames")
+ @discourseComputed("model.creatingPrivateMessage", "model.targetUsernames")
showWarning(creatingPrivateMessage, usernames) {
if (!this.get("currentUser.staff")) {
return false;
@@ -315,17 +315,17 @@ export default Controller.extend({
return creatingPrivateMessage;
},
- @computed("model.topic.title")
+ @discourseComputed("model.topic.title")
draftTitle(topicTitle) {
return emojiUnescape(escapeExpression(topicTitle));
},
- @computed
+ @discourseComputed
allowUpload() {
return authorizesOneOrMoreExtensions();
},
- @computed()
+ @discourseComputed()
uploadIcon: () => uploadIcon(),
actions: {
@@ -1054,7 +1054,7 @@ export default Controller.extend({
debounce(this, this._saveDraft, 2000);
},
- @computed("model.categoryId", "lastValidatedAt")
+ @discourseComputed("model.categoryId", "lastValidatedAt")
categoryValidation(categoryId, lastValidatedAt) {
if (!this.siteSettings.allow_uncategorized_topics && !categoryId) {
return InputValidation.create({
@@ -1065,7 +1065,7 @@ export default Controller.extend({
}
},
- @computed("model.category", "model.tags", "lastValidatedAt")
+ @discourseComputed("model.category", "model.tags", "lastValidatedAt")
tagValidation(category, tags, lastValidatedAt) {
const tagsArray = tags || [];
if (
@@ -1112,12 +1112,12 @@ export default Controller.extend({
$(".d-editor-input").autocomplete({ cancel: true });
},
- @computed("model.action")
+ @discourseComputed("model.action")
canEdit(action) {
return action === "edit" && this.currentUser.can_edit;
},
- @computed("model.composeState")
+ @discourseComputed("model.composeState")
visible(state) {
return state && state !== "closed";
}
diff --git a/app/assets/javascripts/discourse/controllers/create-account.js.es6 b/app/assets/javascripts/discourse/controllers/create-account.js.es6
index beb87d2d3a..96abb66d22 100644
--- a/app/assets/javascripts/discourse/controllers/create-account.js.es6
+++ b/app/assets/javascripts/discourse/controllers/create-account.js.es6
@@ -6,9 +6,9 @@ import { ajax } from "discourse/lib/ajax";
import ModalFunctionality from "discourse/mixins/modal-functionality";
import { setting } from "discourse/lib/computed";
import {
- default as computed,
+ default as discourseComputed,
on
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import { emailValid } from "discourse/lib/utilities";
import InputValidation from "discourse/models/input-validation";
import PasswordValidation from "discourse/mixins/password-validation";
@@ -58,7 +58,7 @@ export default Controller.extend(
this._createUserFields();
},
- @computed(
+ @discourseComputed(
"passwordRequired",
"nameValidation.failed",
"emailValidation.failed",
@@ -82,7 +82,7 @@ export default Controller.extend(
usernameRequired: not("authOptions.omit_username"),
- @computed
+ @discourseComputed
fullnameRequired() {
return (
this.get("siteSettings.full_name_required") ||
@@ -90,12 +90,12 @@ export default Controller.extend(
);
},
- @computed("authOptions.auth_provider")
+ @discourseComputed("authOptions.auth_provider")
passwordRequired(authProvider) {
return isEmpty(authProvider);
},
- @computed
+ @discourseComputed
disclaimerHtml() {
return I18n.t("create_account.disclaimer", {
tos_link: this.get("siteSettings.tos_url") || Discourse.getURL("/tos"),
@@ -106,7 +106,7 @@ export default Controller.extend(
},
// Check the email address
- @computed("accountEmail", "rejectedEmails.[]")
+ @discourseComputed("accountEmail", "rejectedEmails.[]")
emailValidation(email, rejectedEmails) {
// If blank, fail without a reason
if (isEmpty(email)) {
@@ -149,7 +149,11 @@ export default Controller.extend(
});
},
- @computed("accountEmail", "authOptions.email", "authOptions.email_valid")
+ @discourseComputed(
+ "accountEmail",
+ "authOptions.email",
+ "authOptions.email_valid"
+ )
emailValidated() {
return (
this.get("authOptions.email") === this.accountEmail &&
@@ -187,7 +191,7 @@ export default Controller.extend(
}.observes("emailValidation", "accountEmail"),
// Determines whether at least one login button is enabled
- @computed
+ @discourseComputed
hasAtLeastOneLoginButton() {
return findAll().length > 0;
},
diff --git a/app/assets/javascripts/discourse/controllers/discovery/categories.js.es6 b/app/assets/javascripts/discourse/controllers/discovery/categories.js.es6
index 81542214ef..69e59db2a9 100644
--- a/app/assets/javascripts/discourse/controllers/discovery/categories.js.es6
+++ b/app/assets/javascripts/discourse/controllers/discovery/categories.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { reads } from "@ember/object/computed";
import { inject } from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
import DiscoveryController from "discourse/controllers/discovery";
import { dasherize } from "@ember/string";
@@ -19,7 +19,7 @@ export default DiscoveryController.extend({
canEdit: reads("currentUser.staff"),
- @computed("model.categories.[].featuredTopics.length")
+ @discourseComputed("model.categories.[].featuredTopics.length")
latestTopicOnly() {
return (
this.get("model.categories").find(
@@ -28,7 +28,7 @@ export default DiscoveryController.extend({
);
},
- @computed("model.parentCategory")
+ @discourseComputed("model.parentCategory")
categoryPageStyle(parentCategory) {
let style = this.site.mobileView
? "categories_with_featured_topics"
diff --git a/app/assets/javascripts/discourse/controllers/discovery/topics.js.es6 b/app/assets/javascripts/discourse/controllers/discovery/topics.js.es6
index 3d1d4b9348..9e4d81cedd 100644
--- a/app/assets/javascripts/discourse/controllers/discovery/topics.js.es6
+++ b/app/assets/javascripts/discourse/controllers/discovery/topics.js.es6
@@ -1,3 +1,4 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { alias, not, gt, empty, notEmpty, equal } from "@ember/object/computed";
import { inject } from "@ember/controller";
import DiscoveryController from "discourse/controllers/discovery";
@@ -7,7 +8,6 @@ import { endWith } from "discourse/lib/computed";
import showModal from "discourse/lib/show-modal";
import { userPath } from "discourse/lib/url";
import TopicList from "discourse/models/topic-list";
-import computed from "ember-addons/ember-computed-decorators";
import Topic from "discourse/models/topic";
const controllerOpts = {
@@ -99,17 +99,17 @@ const controllerOpts = {
return filter.match(new RegExp(filterType + "$", "gi")) ? true : false;
},
- @computed("model.filter", "model.topics.length")
+ @discourseComputed("model.filter", "model.topics.length")
showDismissRead(filter, topicsLength) {
return this.isFilterPage(filter, "unread") && topicsLength > 0;
},
- @computed("model.filter", "model.topics.length")
+ @discourseComputed("model.filter", "model.topics.length")
showResetNew(filter, topicsLength) {
return filter === "new" && topicsLength > 0;
},
- @computed("model.filter", "model.topics.length")
+ @discourseComputed("model.filter", "model.topics.length")
showDismissAtTop(filter, topicsLength) {
return (
(this.isFilterPage(filter, "new") ||
@@ -129,7 +129,7 @@ const controllerOpts = {
weekly: equal("period", "weekly"),
daily: equal("period", "daily"),
- @computed("allLoaded", "model.topics.length")
+ @discourseComputed("allLoaded", "model.topics.length")
footerMessage(allLoaded, topicsLength) {
if (!allLoaded) return;
@@ -152,7 +152,7 @@ const controllerOpts = {
}
},
- @computed("allLoaded", "model.topics.length")
+ @discourseComputed("allLoaded", "model.topics.length")
footerEducation(allLoaded, topicsLength) {
if (!allLoaded || topicsLength > 0 || !this.currentUser) {
return;
diff --git a/app/assets/javascripts/discourse/controllers/edit-category.js.es6 b/app/assets/javascripts/discourse/controllers/edit-category.js.es6
index 87c1378ffe..21b1e5c5ac 100644
--- a/app/assets/javascripts/discourse/controllers/edit-category.js.es6
+++ b/app/assets/javascripts/discourse/controllers/edit-category.js.es6
@@ -4,10 +4,10 @@ import ModalFunctionality from "discourse/mixins/modal-functionality";
import DiscourseURL from "discourse/lib/url";
import { extractError } from "discourse/lib/ajax-error";
import {
- default as computed,
+ default as discourseComputed,
on,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
export default Controller.extend(ModalFunctionality, {
selectedTab: null,
@@ -39,7 +39,7 @@ export default Controller.extend(ModalFunctionality, {
}
},
- @computed("model.{id,name}")
+ @discourseComputed("model.{id,name}")
title(model) {
if (model.id) {
return I18n.t("category.edit_dialog_title", {
@@ -54,7 +54,7 @@ export default Controller.extend(ModalFunctionality, {
this.set("modal.title", this.title);
},
- @computed("saving", "model.name", "model.color", "deleting")
+ @discourseComputed("saving", "model.name", "model.color", "deleting")
disabled(saving, name, color, deleting) {
if (saving || deleting) return true;
if (!name) return true;
@@ -62,18 +62,18 @@ export default Controller.extend(ModalFunctionality, {
return false;
},
- @computed("saving", "deleting")
+ @discourseComputed("saving", "deleting")
deleteDisabled(saving, deleting) {
return deleting || saving || false;
},
- @computed("name")
+ @discourseComputed("name")
categoryName(name) {
name = name || "";
return name.trim().length > 0 ? name : I18n.t("preview");
},
- @computed("saving", "model.id")
+ @discourseComputed("saving", "model.id")
saveLabel(saving, id) {
if (saving) return "saving";
return id ? "category.save" : "category.create";
diff --git a/app/assets/javascripts/discourse/controllers/edit-topic-timer.js.es6 b/app/assets/javascripts/discourse/controllers/edit-topic-timer.js.es6
index 7dc26c632c..c1473509f2 100644
--- a/app/assets/javascripts/discourse/controllers/edit-topic-timer.js.es6
+++ b/app/assets/javascripts/discourse/controllers/edit-topic-timer.js.es6
@@ -1,6 +1,6 @@
import EmberObject from "@ember/object";
import Controller from "@ember/controller";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import ModalFunctionality from "discourse/mixins/modal-functionality";
import TopicTimer from "discourse/models/topic-timer";
import { popupAjaxError } from "discourse/lib/ajax-error";
@@ -17,7 +17,7 @@ export default Controller.extend(ModalFunctionality, {
loading: false,
isPublic: "true",
- @computed("model.closed")
+ @discourseComputed("model.closed")
publicTimerTypes(closed) {
let types = [
{
@@ -50,17 +50,21 @@ export default Controller.extend(ModalFunctionality, {
return types;
},
- @computed()
+ @discourseComputed()
privateTimerTypes() {
return [{ id: REMINDER_TYPE, name: I18n.t("topic.reminder.title") }];
},
- @computed("isPublic", "publicTimerTypes", "privateTimerTypes")
+ @discourseComputed("isPublic", "publicTimerTypes", "privateTimerTypes")
selections(isPublic, publicTimerTypes, privateTimerTypes) {
return "true" === isPublic ? publicTimerTypes : privateTimerTypes;
},
- @computed("isPublic", "model.topic_timer", "model.private_topic_timer")
+ @discourseComputed(
+ "isPublic",
+ "model.topic_timer",
+ "model.private_topic_timer"
+ )
topicTimer(isPublic, publicTopicTimer, privateTopicTimer) {
return "true" === isPublic ? publicTopicTimer : privateTopicTimer;
},
diff --git a/app/assets/javascripts/discourse/controllers/email-login.js.es6 b/app/assets/javascripts/discourse/controllers/email-login.js.es6
index 78ab74f239..01612c766f 100644
--- a/app/assets/javascripts/discourse/controllers/email-login.js.es6
+++ b/app/assets/javascripts/discourse/controllers/email-login.js.es6
@@ -1,5 +1,5 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
import { SECOND_FACTOR_METHODS } from "discourse/models/user";
import { ajax } from "discourse/lib/ajax";
import DiscourseURL from "discourse/lib/url";
@@ -9,12 +9,12 @@ import { getWebauthnCredential } from "discourse/lib/webauthn";
export default Controller.extend({
lockImageUrl: Discourse.getURL("/images/lock.svg"),
- @computed("model")
+ @discourseComputed("model")
secondFactorRequired(model) {
return model.security_key_required || model.second_factor_required;
},
- @computed("model")
+ @discourseComputed("model")
secondFactorMethod(model) {
return model.security_key_required
? SECOND_FACTOR_METHODS.SECURITY_KEY
diff --git a/app/assets/javascripts/discourse/controllers/exception.js.es6 b/app/assets/javascripts/discourse/controllers/exception.js.es6
index 7967f2d24a..f53eff91fd 100644
--- a/app/assets/javascripts/discourse/controllers/exception.js.es6
+++ b/app/assets/javascripts/discourse/controllers/exception.js.es6
@@ -3,8 +3,8 @@ import { schedule } from "@ember/runloop";
import Controller from "@ember/controller";
import {
on,
- default as computed
-} from "ember-addons/ember-computed-decorators";
+ default as discourseComputed
+} from "discourse-common/utils/decorators";
const ButtonBackBright = {
classes: "btn-primary",
@@ -33,7 +33,7 @@ export default Controller.extend({
thrown: null,
lastTransition: null,
- @computed
+ @discourseComputed
isNetwork() {
// never made it on the wire
if (this.get("thrown.readyState") === 0) return true;
@@ -60,7 +60,7 @@ export default Controller.extend({
this.set("loading", false);
},
- @computed("isNetwork", "isServer", "isUnknown")
+ @discourseComputed("isNetwork", "isServer", "isUnknown")
reason() {
if (this.isNetwork) {
return I18n.t("errors.reasons.network");
@@ -78,7 +78,7 @@ export default Controller.extend({
requestUrl: alias("thrown.requestedUrl"),
- @computed("networkFixed", "isNetwork", "isServer", "isUnknown")
+ @discourseComputed("networkFixed", "isNetwork", "isServer", "isUnknown")
desc() {
if (this.networkFixed) {
return I18n.t("errors.desc.network_fixed");
@@ -96,7 +96,7 @@ export default Controller.extend({
}
},
- @computed("networkFixed", "isNetwork", "isServer", "isUnknown")
+ @discourseComputed("networkFixed", "isNetwork", "isServer", "isUnknown")
enabledButtons() {
if (this.networkFixed) {
return [ButtonLoadPage];
diff --git a/app/assets/javascripts/discourse/controllers/feature-topic.js.es6 b/app/assets/javascripts/discourse/controllers/feature-topic.js.es6
index 48ca403722..3535e355ce 100644
--- a/app/assets/javascripts/discourse/controllers/feature-topic.js.es6
+++ b/app/assets/javascripts/discourse/controllers/feature-topic.js.es6
@@ -1,9 +1,9 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
import { ajax } from "discourse/lib/ajax";
import ModalFunctionality from "discourse/mixins/modal-functionality";
import { categoryLinkHTML } from "discourse/helpers/category-link";
-import computed from "ember-addons/ember-computed-decorators";
import InputValidation from "discourse/models/input-validation";
export default Controller.extend(ModalFunctionality, {
@@ -23,12 +23,16 @@ export default Controller.extend(ModalFunctionality, {
});
},
- @computed("model.category")
+ @discourseComputed("model.category")
categoryLink(category) {
return categoryLinkHTML(category, { allowUncategorized: true });
},
- @computed("categoryLink", "model.pinned_globally", "model.pinned_until")
+ @discourseComputed(
+ "categoryLink",
+ "model.pinned_globally",
+ "model.pinned_until"
+ )
unPinMessage(categoryLink, pinnedGlobally, pinnedUntil) {
let name = "topic.feature_topic.unpin";
if (pinnedGlobally) name += "_globally";
@@ -38,12 +42,12 @@ export default Controller.extend(ModalFunctionality, {
return I18n.t(name, { categoryLink, until });
},
- @computed("categoryLink")
+ @discourseComputed("categoryLink")
pinMessage(categoryLink) {
return I18n.t("topic.feature_topic.pin", { categoryLink });
},
- @computed("categoryLink", "pinnedInCategoryCount")
+ @discourseComputed("categoryLink", "pinnedInCategoryCount")
alreadyPinnedMessage(categoryLink, count) {
const key =
count === 0
@@ -52,27 +56,27 @@ export default Controller.extend(ModalFunctionality, {
return I18n.t(key, { categoryLink, count });
},
- @computed("parsedPinnedInCategoryUntil")
+ @discourseComputed("parsedPinnedInCategoryUntil")
pinDisabled(parsedPinnedInCategoryUntil) {
return !this._isDateValid(parsedPinnedInCategoryUntil);
},
- @computed("parsedPinnedGloballyUntil")
+ @discourseComputed("parsedPinnedGloballyUntil")
pinGloballyDisabled(parsedPinnedGloballyUntil) {
return !this._isDateValid(parsedPinnedGloballyUntil);
},
- @computed("model.pinnedInCategoryUntil")
+ @discourseComputed("model.pinnedInCategoryUntil")
parsedPinnedInCategoryUntil(pinnedInCategoryUntil) {
return this._parseDate(pinnedInCategoryUntil);
},
- @computed("model.pinnedGloballyUntil")
+ @discourseComputed("model.pinnedGloballyUntil")
parsedPinnedGloballyUntil(pinnedGloballyUntil) {
return this._parseDate(pinnedGloballyUntil);
},
- @computed("pinDisabled")
+ @discourseComputed("pinDisabled")
pinInCategoryValidation(pinDisabled) {
if (pinDisabled) {
return InputValidation.create({
@@ -82,7 +86,7 @@ export default Controller.extend(ModalFunctionality, {
}
},
- @computed("pinGloballyDisabled")
+ @discourseComputed("pinGloballyDisabled")
pinGloballyValidation(pinGloballyDisabled) {
if (pinGloballyDisabled) {
return InputValidation.create({
diff --git a/app/assets/javascripts/discourse/controllers/flag.js.es6 b/app/assets/javascripts/discourse/controllers/flag.js.es6
index 8f3c49ebc5..9eb3ae711d 100644
--- a/app/assets/javascripts/discourse/controllers/flag.js.es6
+++ b/app/assets/javascripts/discourse/controllers/flag.js.es6
@@ -1,10 +1,10 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { not } from "@ember/object/computed";
import EmberObject from "@ember/object";
import Controller from "@ember/controller";
import ModalFunctionality from "discourse/mixins/modal-functionality";
import ActionSummary from "discourse/models/action-summary";
import { MAX_MESSAGE_LENGTH } from "discourse/models/post-action-type";
-import computed from "ember-addons/ember-computed-decorators";
import optionalService from "discourse/lib/optional-service";
import { popupAjaxError } from "discourse/lib/ajax-error";
@@ -32,17 +32,17 @@ export default Controller.extend(ModalFunctionality, {
}
},
- @computed("spammerDetails.canDelete", "selected.name_key")
+ @discourseComputed("spammerDetails.canDelete", "selected.name_key")
showDeleteSpammer(canDeleteSpammer, nameKey) {
return canDeleteSpammer && nameKey === "spam";
},
- @computed("flagTopic")
+ @discourseComputed("flagTopic")
title(flagTopic) {
return flagTopic ? "flagging_topic.title" : "flagging.title";
},
- @computed("post", "flagTopic", "model.actions_summary.@each.can_act")
+ @discourseComputed("post", "flagTopic", "model.actions_summary.@each.can_act")
flagsAvailable() {
if (!this.flagTopic) {
// flagging post
@@ -77,7 +77,7 @@ export default Controller.extend(ModalFunctionality, {
}
},
- @computed("post", "flagTopic", "model.actions_summary.@each.can_act")
+ @discourseComputed("post", "flagTopic", "model.actions_summary.@each.can_act")
staffFlagsAvailable() {
return (
this.get("model.flagsAvailable") &&
@@ -85,7 +85,7 @@ export default Controller.extend(ModalFunctionality, {
);
},
- @computed("selected.is_custom_flag", "message.length")
+ @discourseComputed("selected.is_custom_flag", "message.length")
submitEnabled() {
const selected = this.selected;
if (!selected) return false;
@@ -103,17 +103,17 @@ export default Controller.extend(ModalFunctionality, {
submitDisabled: not("submitEnabled"),
// Staff accounts can "take action"
- @computed("flagTopic", "selected.is_custom_flag")
+ @discourseComputed("flagTopic", "selected.is_custom_flag")
canTakeAction(flagTopic, isCustomFlag) {
return !flagTopic && !isCustomFlag && this.currentUser.get("staff");
},
- @computed("selected.is_custom_flag")
+ @discourseComputed("selected.is_custom_flag")
submitIcon(isCustomFlag) {
return isCustomFlag ? "envelope" : "flag";
},
- @computed("selected.is_custom_flag", "flagTopic")
+ @discourseComputed("selected.is_custom_flag", "flagTopic")
submitLabel(isCustomFlag, flagTopic) {
if (isCustomFlag) {
return flagTopic
@@ -193,7 +193,7 @@ export default Controller.extend(ModalFunctionality, {
}
},
- @computed("flagTopic", "selected.name_key")
+ @discourseComputed("flagTopic", "selected.name_key")
canSendWarning(flagTopic, nameKey) {
return (
!flagTopic && this.currentUser.get("staff") && nameKey === "notify_user"
diff --git a/app/assets/javascripts/discourse/controllers/forgot-password.js.es6 b/app/assets/javascripts/discourse/controllers/forgot-password.js.es6
index ae5d53679d..0f667683ad 100644
--- a/app/assets/javascripts/discourse/controllers/forgot-password.js.es6
+++ b/app/assets/javascripts/discourse/controllers/forgot-password.js.es6
@@ -1,16 +1,16 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { isEmpty } from "@ember/utils";
import Controller from "@ember/controller";
import { ajax } from "discourse/lib/ajax";
import ModalFunctionality from "discourse/mixins/modal-functionality";
import { escapeExpression } from "discourse/lib/utilities";
import { extractError } from "discourse/lib/ajax-error";
-import computed from "ember-addons/ember-computed-decorators";
export default Controller.extend(ModalFunctionality, {
offerHelp: null,
helpSeen: false,
- @computed("accountEmailOrUsername", "disabled")
+ @discourseComputed("accountEmailOrUsername", "disabled")
submitDisabled(accountEmailOrUsername, disabled) {
return isEmpty((accountEmailOrUsername || "").trim()) || disabled;
},
diff --git a/app/assets/javascripts/discourse/controllers/full-page-search.js.es6 b/app/assets/javascripts/discourse/controllers/full-page-search.js.es6
index 0b37bead27..d62a2a8177 100644
--- a/app/assets/javascripts/discourse/controllers/full-page-search.js.es6
+++ b/app/assets/javascripts/discourse/controllers/full-page-search.js.es6
@@ -10,9 +10,9 @@ import {
isValidSearchTerm
} from "discourse/lib/search";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import Category from "discourse/models/category";
import { escapeExpression } from "discourse/lib/utilities";
import { setTransient } from "discourse/lib/page-tracker";
@@ -47,17 +47,17 @@ export default Controller.extend({
page: 1,
resultCount: null,
- @computed("resultCount")
+ @discourseComputed("resultCount")
hasResults(resultCount) {
return (resultCount || 0) > 0;
},
- @computed("q")
+ @discourseComputed("q")
hasAutofocus(q) {
return isEmpty(q);
},
- @computed("q")
+ @discourseComputed("q")
highlightQuery(q) {
if (!q) {
return;
@@ -66,7 +66,7 @@ export default Controller.extend({
return _.reject(q.split(/\s+/), t => t === "l").join(" ");
},
- @computed("skip_context", "context")
+ @discourseComputed("skip_context", "context")
searchContextEnabled: {
get(skip, context) {
return (!skip && context) || skip === "false";
@@ -76,7 +76,7 @@ export default Controller.extend({
}
},
- @computed("context", "context_id")
+ @discourseComputed("context", "context_id")
searchContextDescription(context, id) {
var name = id;
if (context === "category") {
@@ -90,18 +90,18 @@ export default Controller.extend({
return searchContextDescription(context, name);
},
- @computed("q")
+ @discourseComputed("q")
searchActive(q) {
return isValidSearchTerm(q);
},
- @computed("q")
+ @discourseComputed("q")
noSortQ(q) {
q = this.cleanTerm(q);
return escapeExpression(q);
},
- @computed("canCreateTopic", "siteSettings.login_required")
+ @discourseComputed("canCreateTopic", "siteSettings.login_required")
showSuggestion(canCreateTopic, loginRequired) {
return canCreateTopic || !loginRequired;
},
@@ -146,7 +146,7 @@ export default Controller.extend({
}
},
- @computed("q")
+ @discourseComputed("q")
showLikeCount(q) {
return q && q.indexOf("order:likes") > -1;
},
@@ -160,7 +160,7 @@ export default Controller.extend({
}
},
- @computed("q")
+ @discourseComputed("q")
isPrivateMessage(q) {
return (
q &&
@@ -177,7 +177,7 @@ export default Controller.extend({
this.set("application.showFooter", !this.loading);
},
- @computed("resultCount", "noSortQ")
+ @discourseComputed("resultCount", "noSortQ")
resultCountLabel(count, term) {
const plus = count % 50 === 0 ? "+" : "";
return I18n.t("search.result_count", { count, plus, term });
@@ -188,17 +188,17 @@ export default Controller.extend({
this.set("resultCount", this.get("model.posts.length"));
},
- @computed("hasResults")
+ @discourseComputed("hasResults")
canBulkSelect(hasResults) {
return this.currentUser && this.currentUser.staff && hasResults;
},
- @computed("model.grouped_search_result.can_create_topic")
+ @discourseComputed("model.grouped_search_result.can_create_topic")
canCreateTopic(userCanCreateTopic) {
return this.currentUser && userCanCreateTopic;
},
- @computed("page")
+ @discourseComputed("page")
isLastPage(page) {
return page === PAGE_LIMIT;
},
diff --git a/app/assets/javascripts/discourse/controllers/grant-badge.js.es6 b/app/assets/javascripts/discourse/controllers/grant-badge.js.es6
index 287b6a6994..a3cd4e11e8 100644
--- a/app/assets/javascripts/discourse/controllers/grant-badge.js.es6
+++ b/app/assets/javascripts/discourse/controllers/grant-badge.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
import { extractError } from "discourse/lib/ajax-error";
import ModalFunctionality from "discourse/mixins/modal-functionality";
import GrantBadgeController from "discourse/mixins/grant-badge-controller";
@@ -21,12 +21,12 @@ export default Controller.extend(ModalFunctionality, GrantBadgeController, {
this.userBadges = [];
},
- @computed("topicController.selectedPosts")
+ @discourseComputed("topicController.selectedPosts")
post() {
return this.get("topicController.selectedPosts")[0];
},
- @computed("post")
+ @discourseComputed("post")
badgeReason(post) {
const url = post.get("url");
const protocolAndHost =
@@ -35,7 +35,7 @@ export default Controller.extend(ModalFunctionality, GrantBadgeController, {
return url.indexOf("/") === 0 ? protocolAndHost + url : url;
},
- @computed("saving", "selectedBadgeGrantable")
+ @discourseComputed("saving", "selectedBadgeGrantable")
buttonDisabled(saving, selectedBadgeGrantable) {
return saving || !selectedBadgeGrantable;
},
diff --git a/app/assets/javascripts/discourse/controllers/group-activity-posts.js.es6 b/app/assets/javascripts/discourse/controllers/group-activity-posts.js.es6
index ed648a3dec..d73bf08d2f 100644
--- a/app/assets/javascripts/discourse/controllers/group-activity-posts.js.es6
+++ b/app/assets/javascripts/discourse/controllers/group-activity-posts.js.es6
@@ -1,6 +1,6 @@
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
-import { observes } from "ember-addons/ember-computed-decorators";
+import { observes } from "discourse-common/utils/decorators";
import { fmt } from "discourse/lib/computed";
export default Controller.extend({
diff --git a/app/assets/javascripts/discourse/controllers/group-add-members.js.es6 b/app/assets/javascripts/discourse/controllers/group-add-members.js.es6
index 53c1327c42..9b1f888113 100644
--- a/app/assets/javascripts/discourse/controllers/group-add-members.js.es6
+++ b/app/assets/javascripts/discourse/controllers/group-add-members.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { isEmpty } from "@ember/utils";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
import { extractError } from "discourse/lib/ajax-error";
import ModalFunctionality from "discourse/mixins/modal-functionality";
@@ -8,7 +8,7 @@ export default Controller.extend(ModalFunctionality, {
loading: false,
setAsOwner: false,
- @computed("model.usernames", "loading")
+ @discourseComputed("model.usernames", "loading")
disableAddButton(usernames, loading) {
return loading || !usernames || !(usernames.length > 0);
},
diff --git a/app/assets/javascripts/discourse/controllers/group-bulk-add.js.es6 b/app/assets/javascripts/discourse/controllers/group-bulk-add.js.es6
index bef9d535f4..0310d4e309 100644
--- a/app/assets/javascripts/discourse/controllers/group-bulk-add.js.es6
+++ b/app/assets/javascripts/discourse/controllers/group-bulk-add.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { isEmpty } from "@ember/utils";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
import { extractError } from "discourse/lib/ajax-error";
import ModalFunctionality from "discourse/mixins/modal-functionality";
import { ajax } from "discourse/lib/ajax";
@@ -8,7 +8,7 @@ import { ajax } from "discourse/lib/ajax";
export default Controller.extend(ModalFunctionality, {
loading: false,
- @computed("input", "loading", "result")
+ @discourseComputed("input", "loading", "result")
disableAddButton(input, loading, result) {
return loading || isEmpty(input) || input.length <= 0 || result;
},
diff --git a/app/assets/javascripts/discourse/controllers/group-index.js.es6 b/app/assets/javascripts/discourse/controllers/group-index.js.es6
index 2cc94f9f4e..05df6fa12e 100644
--- a/app/assets/javascripts/discourse/controllers/group-index.js.es6
+++ b/app/assets/javascripts/discourse/controllers/group-index.js.es6
@@ -4,9 +4,9 @@ import Controller from "@ember/controller";
import { popupAjaxError } from "discourse/lib/ajax-error";
import Group from "discourse/models/group";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import debounce from "discourse/lib/debounce";
export default Controller.extend({
@@ -43,22 +43,22 @@ export default Controller.extend({
}
},
- @computed("order", "desc", "filter")
+ @discourseComputed("order", "desc", "filter")
memberParams(order, desc, filter) {
return { order, desc, filter };
},
- @computed("model.members")
+ @discourseComputed("model.members")
hasMembers(members) {
return members && members.length > 0;
},
- @computed("model")
+ @discourseComputed("model")
canManageGroup(model) {
return this.currentUser && this.currentUser.canManageGroup(model);
},
- @computed
+ @discourseComputed
filterPlaceholder() {
if (this.currentUser && this.currentUser.admin) {
return "groups.members.filter_placeholder_admin";
diff --git a/app/assets/javascripts/discourse/controllers/group-manage-logs.js.es6 b/app/assets/javascripts/discourse/controllers/group-manage-logs.js.es6
index f5c3ba48f3..3aaf3fdb87 100644
--- a/app/assets/javascripts/discourse/controllers/group-manage-logs.js.es6
+++ b/app/assets/javascripts/discourse/controllers/group-manage-logs.js.es6
@@ -2,9 +2,9 @@ import { inject } from "@ember/controller";
import EmberObject from "@ember/object";
import Controller from "@ember/controller";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
export default Controller.extend({
group: inject(),
@@ -17,7 +17,7 @@ export default Controller.extend({
this.set("filters", EmberObject.create());
},
- @computed(
+ @discourseComputed(
"filters.action",
"filters.acting_user",
"filters.target_user",
diff --git a/app/assets/javascripts/discourse/controllers/group-manage.js.es6 b/app/assets/javascripts/discourse/controllers/group-manage.js.es6
index dab05b6dbc..b99f8a70f9 100644
--- a/app/assets/javascripts/discourse/controllers/group-manage.js.es6
+++ b/app/assets/javascripts/discourse/controllers/group-manage.js.es6
@@ -1,11 +1,11 @@
import { inject as service } from "@ember/service";
import Controller from "@ember/controller";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
export default Controller.extend({
router: service(),
- @computed("model.automatic")
+ @discourseComputed("model.automatic")
tabs(automatic) {
const defaultTabs = [
{ route: "group.manage.profile", title: "groups.manage.profile.title" },
diff --git a/app/assets/javascripts/discourse/controllers/group-requests.js.es6 b/app/assets/javascripts/discourse/controllers/group-requests.js.es6
index 246fd0cf9a..5be58b2d60 100644
--- a/app/assets/javascripts/discourse/controllers/group-requests.js.es6
+++ b/app/assets/javascripts/discourse/controllers/group-requests.js.es6
@@ -4,9 +4,9 @@ import { ajax } from "discourse/lib/ajax";
import { popupAjaxError } from "discourse/lib/ajax-error";
import Group from "discourse/models/group";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import debounce from "discourse/lib/debounce";
export default Controller.extend({
@@ -70,12 +70,12 @@ export default Controller.extend({
});
},
- @computed("model.requesters")
+ @discourseComputed("model.requesters")
hasRequesters(requesters) {
return requesters && requesters.length > 0;
},
- @computed
+ @discourseComputed
filterPlaceholder() {
if (this.currentUser && this.currentUser.admin) {
return "groups.members.filter_placeholder_admin";
diff --git a/app/assets/javascripts/discourse/controllers/group.js.es6 b/app/assets/javascripts/discourse/controllers/group.js.es6
index 322e7ab12c..bd79392b85 100644
--- a/app/assets/javascripts/discourse/controllers/group.js.es6
+++ b/app/assets/javascripts/discourse/controllers/group.js.es6
@@ -1,7 +1,7 @@
import EmberObject from "@ember/object";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
const Tab = EmberObject.extend({
init() {
@@ -18,7 +18,7 @@ export default Controller.extend({
showing: "members",
destroying: null,
- @computed(
+ @discourseComputed(
"showMessages",
"model.user_count",
"canManageGroup",
@@ -68,7 +68,7 @@ export default Controller.extend({
return defaultTabs;
},
- @computed("model.is_group_user")
+ @discourseComputed("model.is_group_user")
showMessages(isGroupUser) {
if (!this.siteSettings.enable_personal_messages) {
return false;
@@ -77,17 +77,17 @@ export default Controller.extend({
return isGroupUser || (this.currentUser && this.currentUser.admin);
},
- @computed("model.is_group_owner", "model.automatic")
+ @discourseComputed("model.is_group_owner", "model.automatic")
canEditGroup(isGroupOwner, automatic) {
return !automatic && isGroupOwner;
},
- @computed("model.displayName", "model.full_name")
+ @discourseComputed("model.displayName", "model.full_name")
groupName(displayName, fullName) {
return (fullName || displayName).capitalize();
},
- @computed(
+ @discourseComputed(
"model.name",
"model.flair_url",
"model.flair_bg_color",
@@ -102,12 +102,12 @@ export default Controller.extend({
};
},
- @computed("model.messageable")
+ @discourseComputed("model.messageable")
displayGroupMessageButton(messageable) {
return this.currentUser && messageable;
},
- @computed("model", "model.automatic")
+ @discourseComputed("model", "model.automatic")
canManageGroup(model, automatic) {
return (
this.currentUser &&
diff --git a/app/assets/javascripts/discourse/controllers/groups-index.js.es6 b/app/assets/javascripts/discourse/controllers/groups-index.js.es6
index a466572b26..9758b30ad5 100644
--- a/app/assets/javascripts/discourse/controllers/groups-index.js.es6
+++ b/app/assets/javascripts/discourse/controllers/groups-index.js.es6
@@ -2,9 +2,9 @@ import { inject } from "@ember/controller";
import Controller from "@ember/controller";
import debounce from "discourse/lib/debounce";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
export default Controller.extend({
application: inject(),
@@ -14,7 +14,7 @@ export default Controller.extend({
filter: "",
type: null,
- @computed("model.extras.type_filters")
+ @discourseComputed("model.extras.type_filters")
types(typeFilters) {
const types = [];
diff --git a/app/assets/javascripts/discourse/controllers/history.js.es6 b/app/assets/javascripts/discourse/controllers/history.js.es6
index 69ea502d41..79203ed563 100644
--- a/app/assets/javascripts/discourse/controllers/history.js.es6
+++ b/app/assets/javascripts/discourse/controllers/history.js.es6
@@ -1,10 +1,10 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { alias, gt, not, or, equal } from "@ember/object/computed";
import Controller from "@ember/controller";
import ModalFunctionality from "discourse/mixins/modal-functionality";
import { categoryBadgeHTML } from "discourse/helpers/category-link";
-import computed from "ember-addons/ember-computed-decorators";
import { propertyGreaterThan, propertyLessThan } from "discourse/lib/computed";
-import { on, observes } from "ember-addons/ember-computed-decorators";
+import { on, observes } from "discourse-common/utils/decorators";
import { sanitizeAsync } from "discourse/lib/text";
import { iconHTML } from "discourse-common/lib/icon-library";
@@ -39,7 +39,11 @@ export default Controller.extend(ModalFunctionality, {
previousTagChanges: customTagArray("model.tags_changes.previous"),
currentTagChanges: customTagArray("model.tags_changes.current"),
- @computed("previousVersion", "model.current_version", "model.version_count")
+ @discourseComputed(
+ "previousVersion",
+ "model.current_version",
+ "model.version_count"
+ )
revisionsText(previous, current, total) {
return I18n.t(
"post.revisions.controls.comparing_previous_to_current_out_of_total",
@@ -101,17 +105,17 @@ export default Controller.extend(ModalFunctionality, {
});
},
- @computed("model.created_at")
+ @discourseComputed("model.created_at")
createdAtDate(createdAt) {
return moment(createdAt).format("LLLL");
},
- @computed("model.current_version")
+ @discourseComputed("model.current_version")
previousVersion(current) {
return current - 1;
},
- @computed("model.current_revision", "model.previous_revision")
+ @discourseComputed("model.current_revision", "model.previous_revision")
displayGoToPrevious(current, prev) {
return prev && current > prev;
},
@@ -140,17 +144,17 @@ export default Controller.extend(ModalFunctionality, {
loadNextDisabled: or("loading", "hideGoToNext"),
loadLastDisabled: or("loading", "hideGoToLast"),
- @computed("model.previous_hidden")
+ @discourseComputed("model.previous_hidden")
displayShow(prevHidden) {
return prevHidden && this.currentUser && this.currentUser.get("staff");
},
- @computed("model.previous_hidden")
+ @discourseComputed("model.previous_hidden")
displayHide(prevHidden) {
return !prevHidden && this.currentUser && this.currentUser.get("staff");
},
- @computed(
+ @discourseComputed(
"model.last_revision",
"model.current_revision",
"model.can_edit",
@@ -160,19 +164,23 @@ export default Controller.extend(ModalFunctionality, {
return !!(canEdit && topicController && lastRevision === currentRevision);
},
- @computed("model.wiki")
+ @discourseComputed("model.wiki")
editButtonLabel(wiki) {
return `post.revisions.controls.${wiki ? "edit_wiki" : "edit_post"}`;
},
- @computed()
+ @discourseComputed()
displayRevert() {
return this.currentUser && this.currentUser.get("staff");
},
isEitherRevisionHidden: or("model.previous_hidden", "model.current_hidden"),
- @computed("model.previous_hidden", "model.current_hidden", "displayingInline")
+ @discourseComputed(
+ "model.previous_hidden",
+ "model.current_hidden",
+ "displayingInline"
+ )
hiddenClasses(prevHidden, currentHidden, displayingInline) {
if (displayingInline) {
return this.isEitherRevisionHidden ? "hidden-revision-either" : null;
@@ -192,22 +200,22 @@ export default Controller.extend(ModalFunctionality, {
displayingSideBySide: equal("viewMode", "side_by_side"),
displayingSideBySideMarkdown: equal("viewMode", "side_by_side_markdown"),
- @computed("displayingInline")
+ @discourseComputed("displayingInline")
inlineClass(displayingInline) {
return displayingInline ? "btn-danger" : "btn-flat";
},
- @computed("displayingSideBySide")
+ @discourseComputed("displayingSideBySide")
sideBySideClass(displayingSideBySide) {
return displayingSideBySide ? "btn-danger" : "btn-flat";
},
- @computed("displayingSideBySideMarkdown")
+ @discourseComputed("displayingSideBySideMarkdown")
sideBySideMarkdownClass(displayingSideBySideMarkdown) {
return displayingSideBySideMarkdown ? "btn-danger" : "btn-flat";
},
- @computed("model.category_id_changes")
+ @discourseComputed("model.category_id_changes")
previousCategory(changes) {
if (changes) {
var category = Discourse.Category.findById(changes["previous"]);
@@ -215,7 +223,7 @@ export default Controller.extend(ModalFunctionality, {
}
},
- @computed("model.category_id_changes")
+ @discourseComputed("model.category_id_changes")
currentCategory(changes) {
if (changes) {
var category = Discourse.Category.findById(changes["current"]);
@@ -223,12 +231,12 @@ export default Controller.extend(ModalFunctionality, {
}
},
- @computed("model.wiki_changes")
+ @discourseComputed("model.wiki_changes")
wikiDisabled(changes) {
return changes && !changes["current"];
},
- @computed("model.post_type_changes")
+ @discourseComputed("model.post_type_changes")
postTypeDisabled(changes) {
return (
changes &&
@@ -236,7 +244,7 @@ export default Controller.extend(ModalFunctionality, {
);
},
- @computed("viewMode", "model.title_changes")
+ @discourseComputed("viewMode", "model.title_changes")
titleDiff(viewMode) {
if (viewMode === "side_by_side_markdown") {
viewMode = "side_by_side";
diff --git a/app/assets/javascripts/discourse/controllers/invites-show.js.es6 b/app/assets/javascripts/discourse/controllers/invites-show.js.es6
index 1b1c99de7d..f6e0ced4fd 100644
--- a/app/assets/javascripts/discourse/controllers/invites-show.js.es6
+++ b/app/assets/javascripts/discourse/controllers/invites-show.js.es6
@@ -1,7 +1,7 @@
import { isEmpty } from "@ember/utils";
import { alias, notEmpty } from "@ember/object/computed";
import Controller from "@ember/controller";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import getUrl from "discourse-common/lib/get-url";
import DiscourseURL from "discourse/lib/url";
import { ajax } from "discourse/lib/ajax";
@@ -26,24 +26,24 @@ export default Controller.extend(
userFields: null,
inviteImageUrl: getUrl("/images/envelope.svg"),
- @computed
+ @discourseComputed
welcomeTitle() {
return I18n.t("invites.welcome_to", {
site_name: this.siteSettings.title
});
},
- @computed("email")
+ @discourseComputed("email")
yourEmailMessage(email) {
return I18n.t("invites.your_email", { email: email });
},
- @computed
+ @discourseComputed
externalAuthsEnabled() {
return findLoginMethods().length > 0;
},
- @computed(
+ @discourseComputed(
"usernameValidation.failed",
"passwordValidation.failed",
"nameValidation.failed",
@@ -58,7 +58,7 @@ export default Controller.extend(
return usernameFailed || passwordFailed || nameFailed || userFieldsFailed;
},
- @computed
+ @discourseComputed
fullnameRequired() {
return (
this.siteSettings.full_name_required || this.siteSettings.enable_names
diff --git a/app/assets/javascripts/discourse/controllers/login.js.es6 b/app/assets/javascripts/discourse/controllers/login.js.es6
index 19fbc21fb7..701d410256 100644
--- a/app/assets/javascripts/discourse/controllers/login.js.es6
+++ b/app/assets/javascripts/discourse/controllers/login.js.es6
@@ -1,3 +1,4 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { isEmpty } from "@ember/utils";
import { alias, or, readOnly } from "@ember/object/computed";
import EmberObject from "@ember/object";
@@ -13,7 +14,6 @@ import { findAll } from "discourse/models/login-method";
import { escape } from "pretty-text/sanitizer";
import { escapeExpression, areCookiesEnabled } from "discourse/lib/utilities";
import { extractError } from "discourse/lib/ajax-error";
-import computed from "ember-addons/ember-computed-decorators";
import { SECOND_FACTOR_METHODS } from "discourse/models/user";
import { getWebauthnCredential } from "discourse/lib/webauthn";
@@ -55,17 +55,17 @@ export default Controller.extend(ModalFunctionality, {
});
},
- @computed("showSecondFactor", "showSecurityKey")
+ @discourseComputed("showSecondFactor", "showSecurityKey")
credentialsClass(showSecondFactor, showSecurityKey) {
return showSecondFactor || showSecurityKey ? "hidden" : "";
},
- @computed("showSecondFactor", "showSecurityKey")
+ @discourseComputed("showSecondFactor", "showSecurityKey")
secondFactorClass(showSecondFactor, showSecurityKey) {
return showSecondFactor || showSecurityKey ? "" : "hidden";
},
- @computed("awaitingApproval", "hasAtLeastOneLoginButton")
+ @discourseComputed("awaitingApproval", "hasAtLeastOneLoginButton")
modalBodyClasses(awaitingApproval, hasAtLeastOneLoginButton) {
const classes = ["login-modal"];
if (awaitingApproval) classes.push("awaiting-approval");
@@ -73,31 +73,31 @@ export default Controller.extend(ModalFunctionality, {
return classes.join(" ");
},
- @computed("showSecondFactor", "showSecurityKey")
+ @discourseComputed("showSecondFactor", "showSecurityKey")
disableLoginFields(showSecondFactor, showSecurityKey) {
return showSecondFactor || showSecurityKey;
},
- @computed("canLoginLocalWithEmail")
+ @discourseComputed("canLoginLocalWithEmail")
hasAtLeastOneLoginButton(canLoginLocalWithEmail) {
return findAll().length > 0 || canLoginLocalWithEmail;
},
- @computed("loggingIn")
+ @discourseComputed("loggingIn")
loginButtonLabel(loggingIn) {
return loggingIn ? "login.logging_in" : "login.title";
},
loginDisabled: or("loggingIn", "loggedIn"),
- @computed("loggingIn", "application.canSignUp")
+ @discourseComputed("loggingIn", "application.canSignUp")
showSignupLink(loggingIn, canSignUp) {
return canSignUp && !loggingIn;
},
showSpinner: readOnly("loggingIn"),
- @computed("canLoginLocalWithEmail", "processingEmailLink")
+ @discourseComputed("canLoginLocalWithEmail", "processingEmailLink")
showLoginWithEmailLink(canLoginLocalWithEmail, processingEmailLink) {
return canLoginLocalWithEmail && !processingEmailLink;
},
diff --git a/app/assets/javascripts/discourse/controllers/move-to-topic.js.es6 b/app/assets/javascripts/discourse/controllers/move-to-topic.js.es6
index c8934801cb..609ae2cf2d 100644
--- a/app/assets/javascripts/discourse/controllers/move-to-topic.js.es6
+++ b/app/assets/javascripts/discourse/controllers/move-to-topic.js.es6
@@ -6,7 +6,7 @@ import Controller from "@ember/controller";
import ModalFunctionality from "discourse/mixins/modal-functionality";
import { movePosts, mergeTopic } from "discourse/models/topic";
import DiscourseURL from "discourse/lib/url";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import { extractError } from "discourse/lib/ajax-error";
export default Controller.extend(ModalFunctionality, {
@@ -46,12 +46,12 @@ export default Controller.extend(ModalFunctionality, {
selectedAllPosts: alias("topicController.selectedAllPosts"),
selectedPosts: alias("topicController.selectedPosts"),
- @computed("saving", "selectedTopicId", "topicName")
+ @discourseComputed("saving", "selectedTopicId", "topicName")
buttonDisabled(saving, selectedTopicId, topicName) {
return saving || (isEmpty(selectedTopicId) && isEmpty(topicName));
},
- @computed(
+ @discourseComputed(
"saving",
"newTopic",
"existingTopic",
@@ -95,7 +95,7 @@ export default Controller.extend(ModalFunctionality, {
}
},
- @computed("selectedAllPosts", "selectedPosts", "selectedPosts.[]")
+ @discourseComputed("selectedAllPosts", "selectedPosts", "selectedPosts.[]")
canSplitTopic(selectedAllPosts, selectedPosts) {
return (
!selectedAllPosts &&
@@ -105,7 +105,7 @@ export default Controller.extend(ModalFunctionality, {
);
},
- @computed("canSplitTopic")
+ @discourseComputed("canSplitTopic")
canSplitToPM(canSplitTopic) {
return canSplitTopic && (this.currentUser && this.currentUser.admin);
},
diff --git a/app/assets/javascripts/discourse/controllers/navigation/categories.js.es6 b/app/assets/javascripts/discourse/controllers/navigation/categories.js.es6
index 216ca0448f..db7ac2bae9 100644
--- a/app/assets/javascripts/discourse/controllers/navigation/categories.js.es6
+++ b/app/assets/javascripts/discourse/controllers/navigation/categories.js.es6
@@ -1,11 +1,14 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { inject } from "@ember/controller";
import NavigationDefaultController from "discourse/controllers/navigation/default";
-import computed from "ember-addons/ember-computed-decorators";
export default NavigationDefaultController.extend({
discoveryCategories: inject("discovery/categories"),
- @computed("discoveryCategories.model", "discoveryCategories.model.draft")
+ @discourseComputed(
+ "discoveryCategories.model",
+ "discoveryCategories.model.draft"
+ )
draft() {
return this.get("discoveryCategories.model.draft");
}
diff --git a/app/assets/javascripts/discourse/controllers/navigation/default.js.es6 b/app/assets/javascripts/discourse/controllers/navigation/default.js.es6
index 9d4d051974..23220761c1 100644
--- a/app/assets/javascripts/discourse/controllers/navigation/default.js.es6
+++ b/app/assets/javascripts/discourse/controllers/navigation/default.js.es6
@@ -1,12 +1,12 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
export default Controller.extend({
discovery: inject(),
discoveryTopics: inject("discovery/topics"),
- @computed("discoveryTopics.model", "discoveryTopics.model.draft")
+ @discourseComputed("discoveryTopics.model", "discoveryTopics.model.draft")
draft: function() {
return this.get("discoveryTopics.model.draft");
}
diff --git a/app/assets/javascripts/discourse/controllers/password-reset.js.es6 b/app/assets/javascripts/discourse/controllers/password-reset.js.es6
index b7a4545aed..7f3718482e 100644
--- a/app/assets/javascripts/discourse/controllers/password-reset.js.es6
+++ b/app/assets/javascripts/discourse/controllers/password-reset.js.es6
@@ -1,6 +1,6 @@
import { alias, or } from "@ember/object/computed";
import Controller from "@ember/controller";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import DiscourseURL from "discourse/lib/url";
import { ajax } from "discourse/lib/ajax";
import PasswordValidation from "discourse/mixins/password-validation";
@@ -18,7 +18,7 @@ export default Controller.extend(PasswordValidation, {
"model.second_factor_required",
"model.security_key_required"
),
- @computed("model.security_key_required")
+ @discourseComputed("model.security_key_required")
secondFactorMethod(security_key_required) {
return security_key_required
? SECOND_FACTOR_METHODS.SECURITY_KEY
@@ -30,14 +30,14 @@ export default Controller.extend(PasswordValidation, {
requiresApproval: false,
redirected: false,
- @computed()
+ @discourseComputed()
continueButtonText() {
return I18n.t("password_reset.continue", {
site_name: this.siteSettings.title
});
},
- @computed("redirectTo")
+ @discourseComputed("redirectTo")
redirectHref(redirectTo) {
return Discourse.getURL(redirectTo || "/");
},
diff --git a/app/assets/javascripts/discourse/controllers/preferences/account.js.es6 b/app/assets/javascripts/discourse/controllers/preferences/account.js.es6
index e30386afdf..337cac9db1 100644
--- a/app/assets/javascripts/discourse/controllers/preferences/account.js.es6
+++ b/app/assets/javascripts/discourse/controllers/preferences/account.js.es6
@@ -3,7 +3,7 @@ import { not, or, gt } from "@ember/object/computed";
import Controller from "@ember/controller";
import { iconHTML } from "discourse-common/lib/icon-library";
import CanCheckEmails from "discourse/mixins/can-check-emails";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import PreferencesTabController from "discourse/mixins/preferences-tab-controller";
import { propertyNotEqual, setting } from "discourse/lib/computed";
import { popupAjaxError } from "discourse/lib/ajax-error";
@@ -43,7 +43,7 @@ export default Controller.extend(CanCheckEmails, PreferencesTabController, {
this.set("passwordProgress", null);
},
- @computed()
+ @discourseComputed()
nameInstructions() {
return I18n.t(
this.siteSettings.full_name_required
@@ -54,7 +54,7 @@ export default Controller.extend(CanCheckEmails, PreferencesTabController, {
canSelectTitle: gt("model.availableTitles.length", 0),
- @computed("model.filteredGroups")
+ @discourseComputed("model.filteredGroups")
canSelectPrimaryGroup(primaryGroupOptions) {
return (
primaryGroupOptions.length > 0 &&
@@ -62,7 +62,7 @@ export default Controller.extend(CanCheckEmails, PreferencesTabController, {
);
},
- @computed("model.is_anonymous")
+ @discourseComputed("model.is_anonymous")
canChangePassword(isAnonymous) {
if (isAnonymous) {
return false;
@@ -73,12 +73,12 @@ export default Controller.extend(CanCheckEmails, PreferencesTabController, {
}
},
- @computed("model.associated_accounts")
+ @discourseComputed("model.associated_accounts")
associatedAccountsLoaded(associatedAccounts) {
return typeof associatedAccounts !== "undefined";
},
- @computed("model.associated_accounts.[]")
+ @discourseComputed("model.associated_accounts.[]")
authProviders(accounts) {
const allMethods = findAll();
@@ -94,7 +94,7 @@ export default Controller.extend(CanCheckEmails, PreferencesTabController, {
disableConnectButtons: propertyNotEqual("model.id", "currentUser.id"),
- @computed(
+ @discourseComputed(
"model.second_factor_enabled",
"canCheckEmails",
"model.is_anonymous"
@@ -110,7 +110,7 @@ export default Controller.extend(CanCheckEmails, PreferencesTabController, {
return findAll().length > 0;
},
- @computed("showAllAuthTokens", "model.user_auth_tokens")
+ @discourseComputed("showAllAuthTokens", "model.user_auth_tokens")
authTokens(showAllAuthTokens, tokens) {
tokens.sort((a, b) => {
if (a.is_active) {
diff --git a/app/assets/javascripts/discourse/controllers/preferences/categories.js.es6 b/app/assets/javascripts/discourse/controllers/preferences/categories.js.es6
index 8f86974e38..4628234524 100644
--- a/app/assets/javascripts/discourse/controllers/preferences/categories.js.es6
+++ b/app/assets/javascripts/discourse/controllers/preferences/categories.js.es6
@@ -1,8 +1,8 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { or } from "@ember/object/computed";
import Controller from "@ember/controller";
import PreferencesTabController from "discourse/mixins/preferences-tab-controller";
import { popupAjaxError } from "discourse/lib/ajax-error";
-import computed from "ember-addons/ember-computed-decorators";
export default Controller.extend(PreferencesTabController, {
init() {
@@ -16,7 +16,7 @@ export default Controller.extend(PreferencesTabController, {
];
},
- @computed(
+ @discourseComputed(
"model.watchedCategories",
"model.watchedFirstPostCategories",
"model.trackedCategories",
@@ -26,12 +26,12 @@ export default Controller.extend(PreferencesTabController, {
return [].concat(watched, watchedFirst, tracked, muted).filter(t => t);
},
- @computed
+ @discourseComputed
canSee() {
return this.get("currentUser.id") === this.get("model.id");
},
- @computed("siteSettings.remove_muted_tags_from_latest")
+ @discourseComputed("siteSettings.remove_muted_tags_from_latest")
hideMutedTags() {
return this.siteSettings.remove_muted_tags_from_latest !== "never";
},
diff --git a/app/assets/javascripts/discourse/controllers/preferences/email.js.es6 b/app/assets/javascripts/discourse/controllers/preferences/email.js.es6
index c25db36a43..94a13ae596 100644
--- a/app/assets/javascripts/discourse/controllers/preferences/email.js.es6
+++ b/app/assets/javascripts/discourse/controllers/preferences/email.js.es6
@@ -1,9 +1,9 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { empty, or } from "@ember/object/computed";
import Controller from "@ember/controller";
import { propertyEqual } from "discourse/lib/computed";
import InputValidation from "discourse/models/input-validation";
import { emailValid } from "discourse/lib/utilities";
-import computed from "ember-addons/ember-computed-decorators";
export default Controller.extend({
taken: false,
@@ -24,23 +24,23 @@ export default Controller.extend({
unchanged: propertyEqual("newEmailLower", "currentUser.email"),
- @computed("newEmail")
+ @discourseComputed("newEmail")
newEmailLower(newEmail) {
return newEmail.toLowerCase().trim();
},
- @computed("saving")
+ @discourseComputed("saving")
saveButtonText(saving) {
if (saving) return I18n.t("saving");
return I18n.t("user.change");
},
- @computed("newEmail")
+ @discourseComputed("newEmail")
invalidEmail(newEmail) {
return !emailValid(newEmail);
},
- @computed("invalidEmail")
+ @discourseComputed("invalidEmail")
emailValidation(invalidEmail) {
if (invalidEmail) {
return InputValidation.create({
diff --git a/app/assets/javascripts/discourse/controllers/preferences/emails.js.es6 b/app/assets/javascripts/discourse/controllers/preferences/emails.js.es6
index a2001457e5..008ed9c8cd 100644
--- a/app/assets/javascripts/discourse/controllers/preferences/emails.js.es6
+++ b/app/assets/javascripts/discourse/controllers/preferences/emails.js.es6
@@ -1,7 +1,7 @@
import { equal } from "@ember/object/computed";
import Controller from "@ember/controller";
import PreferencesTabController from "discourse/mixins/preferences-tab-controller";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import { popupAjaxError } from "discourse/lib/ajax-error";
const EMAIL_LEVELS = {
@@ -60,7 +60,7 @@ export default Controller.extend(PreferencesTabController, {
];
},
- @computed()
+ @discourseComputed()
frequencyEstimate() {
var estimate = this.get("model.mailing_list_posts_per_day");
if (!estimate || estimate < 2) {
@@ -72,7 +72,7 @@ export default Controller.extend(PreferencesTabController, {
}
},
- @computed()
+ @discourseComputed()
mailingListModeOptions() {
return [
{ name: this.frequencyEstimate, value: 1 },
@@ -80,7 +80,7 @@ export default Controller.extend(PreferencesTabController, {
];
},
- @computed()
+ @discourseComputed()
emailFrequencyInstructions() {
if (this.siteSettings.email_time_window_mins) {
return I18n.t("user.email.frequency", {
diff --git a/app/assets/javascripts/discourse/controllers/preferences/interface.js.es6 b/app/assets/javascripts/discourse/controllers/preferences/interface.js.es6
index 9ef7280fc2..370d5b9a4d 100644
--- a/app/assets/javascripts/discourse/controllers/preferences/interface.js.es6
+++ b/app/assets/javascripts/discourse/controllers/preferences/interface.js.es6
@@ -3,9 +3,9 @@ import Controller from "@ember/controller";
import PreferencesTabController from "discourse/mixins/preferences-tab-controller";
import { setDefaultHomepage } from "discourse/lib/utilities";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import {
listThemes,
previewTheme,
@@ -30,7 +30,7 @@ const TEXT_SIZES = ["smaller", "normal", "larger", "largest"];
const TITLE_COUNT_MODES = ["notifications", "contextual"];
export default Controller.extend(PreferencesTabController, {
- @computed("makeThemeDefault")
+ @discourseComputed("makeThemeDefault")
saveAttrNames(makeDefault) {
let attrs = [
"locale",
@@ -55,43 +55,43 @@ export default Controller.extend(PreferencesTabController, {
preferencesController: inject("preferences"),
- @computed()
+ @discourseComputed()
isiPad() {
// TODO: remove this preference checkbox when iOS adoption > 90%
// (currently only applies to iOS 12 and below)
return isiPad() && !iOSWithVisualViewport();
},
- @computed()
+ @discourseComputed()
disableSafariHacks() {
return safariHacksDisabled();
},
- @computed()
+ @discourseComputed()
availableLocales() {
return JSON.parse(this.siteSettings.available_locales);
},
- @computed
+ @discourseComputed
textSizes() {
return TEXT_SIZES.map(value => {
return { name: I18n.t(`user.text_size.${value}`), value };
});
},
- @computed
+ @discourseComputed
titleCountModes() {
return TITLE_COUNT_MODES.map(value => {
return { name: I18n.t(`user.title_count_mode.${value}`), value };
});
},
- @computed
+ @discourseComputed
userSelectableThemes() {
return listThemes(this.site);
},
- @computed("userSelectableThemes")
+ @discourseComputed("userSelectableThemes")
showThemeSelector(themes) {
return themes && themes.length > 1;
},
@@ -102,12 +102,12 @@ export default Controller.extend(PreferencesTabController, {
previewTheme([id]);
},
- @computed("model.user_option.theme_ids", "themeId")
+ @discourseComputed("model.user_option.theme_ids", "themeId")
showThemeSetDefault(userOptionThemes, selectedTheme) {
return !userOptionThemes || userOptionThemes[0] !== selectedTheme;
},
- @computed("model.user_option.text_size", "textSize")
+ @discourseComputed("model.user_option.text_size", "textSize")
showTextSetDefault(userOptionTextSize, selectedTextSize) {
return userOptionTextSize !== selectedTextSize;
},
@@ -119,7 +119,7 @@ export default Controller.extend(PreferencesTabController, {
setDefaultHomepage(userHome || siteHome);
},
- @computed()
+ @discourseComputed()
userSelectableHome() {
let homeValues = {};
Object.keys(USER_HOMES).forEach(newValue => {
diff --git a/app/assets/javascripts/discourse/controllers/preferences/profile.js.es6 b/app/assets/javascripts/discourse/controllers/preferences/profile.js.es6
index b4e9a46fac..f726f87e17 100644
--- a/app/assets/javascripts/discourse/controllers/preferences/profile.js.es6
+++ b/app/assets/javascripts/discourse/controllers/preferences/profile.js.es6
@@ -1,7 +1,7 @@
import { isEmpty } from "@ember/utils";
import EmberObject from "@ember/object";
import Controller from "@ember/controller";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import PreferencesTabController from "discourse/mixins/preferences-tab-controller";
import { popupAjaxError } from "discourse/lib/ajax-error";
import { cookAsync } from "discourse/lib/text";
@@ -22,7 +22,7 @@ export default Controller.extend(PreferencesTabController, {
];
},
- @computed("model.user_fields.@each.value")
+ @discourseComputed("model.user_fields.@each.value")
userFields() {
let siteUserFields = this.site.get("user_fields");
if (!isEmpty(siteUserFields)) {
@@ -41,7 +41,7 @@ export default Controller.extend(PreferencesTabController, {
}
},
- @computed("model.can_change_bio")
+ @discourseComputed("model.can_change_bio")
canChangeBio(canChangeBio) {
return canChangeBio;
},
diff --git a/app/assets/javascripts/discourse/controllers/preferences/second-factor.js.es6 b/app/assets/javascripts/discourse/controllers/preferences/second-factor.js.es6
index 233ed03390..21e9a55f38 100644
--- a/app/assets/javascripts/discourse/controllers/preferences/second-factor.js.es6
+++ b/app/assets/javascripts/discourse/controllers/preferences/second-factor.js.es6
@@ -1,6 +1,6 @@
import { alias, and } from "@ember/object/computed";
import Controller from "@ember/controller";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import CanCheckEmails from "discourse/mixins/can-check-emails";
import { default as DiscourseURL, userPath } from "discourse/lib/url";
import { popupAjaxError } from "discourse/lib/ajax-error";
@@ -27,12 +27,12 @@ export default Controller.extend(CanCheckEmails, {
this.set("totps", []);
},
- @computed
+ @discourseComputed
displayOAuthWarning() {
return findAll().length > 0;
},
- @computed("currentUser")
+ @discourseComputed("currentUser")
showEnforcedNotice(user) {
return user && user.enforcedSecondFactor;
},
diff --git a/app/assets/javascripts/discourse/controllers/preferences/tags.js.es6 b/app/assets/javascripts/discourse/controllers/preferences/tags.js.es6
index 85d1241ad3..1aede6792d 100644
--- a/app/assets/javascripts/discourse/controllers/preferences/tags.js.es6
+++ b/app/assets/javascripts/discourse/controllers/preferences/tags.js.es6
@@ -1,7 +1,7 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Controller from "@ember/controller";
import PreferencesTabController from "discourse/mixins/preferences-tab-controller";
import { popupAjaxError } from "discourse/lib/ajax-error";
-import computed from "ember-addons/ember-computed-decorators";
export default Controller.extend(PreferencesTabController, {
init() {
@@ -15,7 +15,7 @@ export default Controller.extend(PreferencesTabController, {
];
},
- @computed(
+ @discourseComputed(
"model.watched_tags.[]",
"model.watching_first_post_tags.[]",
"model.tracked_tags.[]",
diff --git a/app/assets/javascripts/discourse/controllers/preferences/username.js.es6 b/app/assets/javascripts/discourse/controllers/preferences/username.js.es6
index 954e8c739e..6d3f8ea6cc 100644
--- a/app/assets/javascripts/discourse/controllers/preferences/username.js.es6
+++ b/app/assets/javascripts/discourse/controllers/preferences/username.js.es6
@@ -2,9 +2,9 @@ import { isEmpty } from "@ember/utils";
import { empty, or } from "@ember/object/computed";
import Controller from "@ember/controller";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import { setting, propertyEqual } from "discourse/lib/computed";
import DiscourseURL from "discourse/lib/url";
import { userPath } from "discourse/lib/url";
@@ -55,7 +55,7 @@ export default Controller.extend({
}
},
- @computed("saving")
+ @discourseComputed("saving")
saveButtonText(saving) {
if (saving) return I18n.t("saving");
return I18n.t("user.change");
diff --git a/app/assets/javascripts/discourse/controllers/rename-tag.js.es6 b/app/assets/javascripts/discourse/controllers/rename-tag.js.es6
index b08bc2d646..4bb35a34ca 100644
--- a/app/assets/javascripts/discourse/controllers/rename-tag.js.es6
+++ b/app/assets/javascripts/discourse/controllers/rename-tag.js.es6
@@ -1,11 +1,11 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Controller from "@ember/controller";
import ModalFunctionality from "discourse/mixins/modal-functionality";
-import computed from "ember-addons/ember-computed-decorators";
import BufferedContent from "discourse/mixins/buffered-content";
import { extractError } from "discourse/lib/ajax-error";
export default Controller.extend(ModalFunctionality, BufferedContent, {
- @computed("buffered.id", "id")
+ @discourseComputed("buffered.id", "id")
renameDisabled(inputTagName, currentTagName) {
const filterRegexp = new RegExp(this.site.tags_filter_regexp, "g");
const newTagName = inputTagName
diff --git a/app/assets/javascripts/discourse/controllers/reorder-categories.js.es6 b/app/assets/javascripts/discourse/controllers/reorder-categories.js.es6
index 06d5f30cca..cf7c2ca7cb 100644
--- a/app/assets/javascripts/discourse/controllers/reorder-categories.js.es6
+++ b/app/assets/javascripts/discourse/controllers/reorder-categories.js.es6
@@ -7,8 +7,8 @@ const BufferedProxy = window.BufferedProxy; // import BufferedProxy from 'ember-
import { popupAjaxError } from "discourse/lib/ajax-error";
import {
on,
- default as computed
-} from "ember-addons/ember-computed-decorators";
+ default as discourseComputed
+} from "discourse-common/utils/decorators";
import Ember from "ember";
export default Controller.extend(ModalFunctionality, Ember.Evented, {
@@ -23,7 +23,7 @@ export default Controller.extend(ModalFunctionality, Ember.Evented, {
this.fixIndices();
},
- @computed("site.categories")
+ @discourseComputed("site.categories")
categoriesBuffered(categories) {
const bufProxy = EmberObjectProxy.extend(BufferedProxy);
return categories.map(c => bufProxy.create({ content: c }));
@@ -31,7 +31,7 @@ export default Controller.extend(ModalFunctionality, Ember.Evented, {
categoriesOrdered: sort("categoriesBuffered", "categoriesSorting"),
- @computed("categoriesBuffered.@each.hasBufferedChanges")
+ @discourseComputed("categoriesBuffered.@each.hasBufferedChanges")
showApplyAll() {
let anyChanged = false;
this.categoriesBuffered.forEach(bc => {
diff --git a/app/assets/javascripts/discourse/controllers/request-group-membership-form.js.es6 b/app/assets/javascripts/discourse/controllers/request-group-membership-form.js.es6
index 0f316873ce..bbb54d03dd 100644
--- a/app/assets/javascripts/discourse/controllers/request-group-membership-form.js.es6
+++ b/app/assets/javascripts/discourse/controllers/request-group-membership-form.js.es6
@@ -1,7 +1,7 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { isEmpty } from "@ember/utils";
import { alias } from "@ember/object/computed";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
import { popupAjaxError } from "discourse/lib/ajax-error";
import DiscourseURL from "discourse/lib/url";
import ModalFunctionality from "discourse/mixins/modal-functionality";
@@ -10,12 +10,12 @@ export default Controller.extend(ModalFunctionality, {
loading: false,
reason: alias("model.membership_request_template"),
- @computed("model.name")
+ @discourseComputed("model.name")
title(groupName) {
return I18n.t("groups.membership_request.title", { group_name: groupName });
},
- @computed("loading", "reason")
+ @discourseComputed("loading", "reason")
disableSubmit(loading, reason) {
return loading || isEmpty(reason);
},
diff --git a/app/assets/javascripts/discourse/controllers/review-index.js.es6 b/app/assets/javascripts/discourse/controllers/review-index.js.es6
index 75ab25b4f1..df95f33cfb 100644
--- a/app/assets/javascripts/discourse/controllers/review-index.js.es6
+++ b/app/assets/javascripts/discourse/controllers/review-index.js.es6
@@ -1,5 +1,5 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
export default Controller.extend({
queryParams: [
@@ -27,7 +27,7 @@ export default Controller.extend({
this.set("filtersExpanded", !this.site.mobileView);
},
- @computed("reviewableTypes")
+ @discourseComputed("reviewableTypes")
allTypes() {
return (this.reviewableTypes || []).map(type => {
return {
@@ -37,7 +37,7 @@ export default Controller.extend({
});
},
- @computed
+ @discourseComputed
priorities() {
return ["low", "medium", "high"].map(priority => {
return {
@@ -47,7 +47,7 @@ export default Controller.extend({
});
},
- @computed
+ @discourseComputed
sortOrders() {
return ["priority", "priority_asc", "created_at", "created_at_asc"].map(
order => {
@@ -59,7 +59,7 @@ export default Controller.extend({
);
},
- @computed
+ @discourseComputed
statuses() {
return [
"pending",
@@ -74,7 +74,7 @@ export default Controller.extend({
});
},
- @computed("filtersExpanded")
+ @discourseComputed("filtersExpanded")
toggleFiltersIcon(filtersExpanded) {
return filtersExpanded ? "chevron-up" : "chevron-down";
},
diff --git a/app/assets/javascripts/discourse/controllers/search-help.js.es6 b/app/assets/javascripts/discourse/controllers/search-help.js.es6
index 654722d2c7..1475373480 100644
--- a/app/assets/javascripts/discourse/controllers/search-help.js.es6
+++ b/app/assets/javascripts/discourse/controllers/search-help.js.es6
@@ -1,9 +1,9 @@
+import discourseComputed from "discourse-common/utils/decorators";
import Controller from "@ember/controller";
import ModalFunctionality from "discourse/mixins/modal-functionality";
-import computed from "ember-addons/ember-computed-decorators";
export default Controller.extend(ModalFunctionality, {
- @computed
+ @discourseComputed
showGoogleSearch() {
return !Discourse.SiteSettings.login_required;
}
diff --git a/app/assets/javascripts/discourse/controllers/second-factor-backup-edit.js.es6 b/app/assets/javascripts/discourse/controllers/second-factor-backup-edit.js.es6
index 2801056c71..35b24b07df 100644
--- a/app/assets/javascripts/discourse/controllers/second-factor-backup-edit.js.es6
+++ b/app/assets/javascripts/discourse/controllers/second-factor-backup-edit.js.es6
@@ -1,7 +1,7 @@
import { alias } from "@ember/object/computed";
import { later } from "@ember/runloop";
import Controller from "@ember/controller";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import { SECOND_FACTOR_METHODS } from "discourse/models/user";
import ModalFunctionality from "discourse/mixins/modal-functionality";
@@ -14,7 +14,7 @@ export default Controller.extend(ModalFunctionality, {
backupCodes: null,
secondFactorMethod: SECOND_FACTOR_METHODS.TOTP,
- @computed("backupEnabled")
+ @discourseComputed("backupEnabled")
generateBackupCodeBtnLabel(backupEnabled) {
return backupEnabled
? "user.second_factor_backup.regenerate"
diff --git a/app/assets/javascripts/discourse/controllers/static.js.es6 b/app/assets/javascripts/discourse/controllers/static.js.es6
index 587e14da81..ad4f953105 100644
--- a/app/assets/javascripts/discourse/controllers/static.js.es6
+++ b/app/assets/javascripts/discourse/controllers/static.js.es6
@@ -1,8 +1,8 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { equal } from "@ember/object/computed";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
import { ajax } from "discourse/lib/ajax";
-import computed from "ember-addons/ember-computed-decorators";
import { userPath } from "discourse/lib/url";
export default Controller.extend({
@@ -10,10 +10,10 @@ export default Controller.extend({
showLoginButton: equal("model.path", "login"),
- @computed("model.path")
+ @discourseComputed("model.path")
bodyClass: path => `static-${path}`,
- @computed("model.path")
+ @discourseComputed("model.path")
showSignupButton() {
return (
this.get("model.path") === "login" && this.get("application.canSignUp")
diff --git a/app/assets/javascripts/discourse/controllers/tags-index.js.es6 b/app/assets/javascripts/discourse/controllers/tags-index.js.es6
index c2ec12fda6..14473df9a5 100644
--- a/app/assets/javascripts/discourse/controllers/tags-index.js.es6
+++ b/app/assets/javascripts/discourse/controllers/tags-index.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { alias, notEmpty } from "@ember/object/computed";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
import showModal from "discourse/lib/show-modal";
import { ajax } from "discourse/lib/ajax";
import { popupAjaxError } from "discourse/lib/ajax-error";
@@ -19,7 +19,7 @@ export default Controller.extend({
this.sortProperties = ["totalCount:desc", "id"];
},
- @computed("groupedByCategory", "groupedByTagGroup")
+ @discourseComputed("groupedByCategory", "groupedByTagGroup")
otherTagsTitleKey(groupedByCategory, groupedByTagGroup) {
if (!groupedByCategory && !groupedByTagGroup) {
return "tagging.all_tags";
@@ -28,7 +28,7 @@ export default Controller.extend({
}
},
- @computed
+ @discourseComputed
actionsMapping() {
return {
manageGroups: () => this.send("showTagGroups"),
diff --git a/app/assets/javascripts/discourse/controllers/tags-show.js.es6 b/app/assets/javascripts/discourse/controllers/tags-show.js.es6
index 9d787fe8a4..631f85d7df 100644
--- a/app/assets/javascripts/discourse/controllers/tags-show.js.es6
+++ b/app/assets/javascripts/discourse/controllers/tags-show.js.es6
@@ -2,9 +2,9 @@ import { alias } from "@ember/object/computed";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import BulkTopicSelection from "discourse/mixins/bulk-topic-selection";
import {
default as NavItem,
@@ -72,12 +72,12 @@ export default Controller.extend(BulkTopicSelection, {
categories: alias("site.categoriesList"),
- @computed("list", "list.draft")
+ @discourseComputed("list", "list.draft")
createTopicLabel(list, listDraft) {
return listDraft ? "topic.open_draft" : "topic.create";
},
- @computed(
+ @discourseComputed(
"canCreateTopic",
"category",
"canCreateTopicOnCategory",
@@ -108,7 +108,7 @@ export default Controller.extend(BulkTopicSelection, {
"q"
],
- @computed("category", "tag.id", "filterMode")
+ @discourseComputed("category", "tag.id", "filterMode")
navItems(category, tagId, filterMode) {
return NavItem.buildList(category, {
tagId,
@@ -116,12 +116,12 @@ export default Controller.extend(BulkTopicSelection, {
});
},
- @computed("category")
+ @discourseComputed("category")
showTagFilter() {
return Discourse.SiteSettings.show_filter_by_tag;
},
- @computed("additionalTags", "canAdminTag", "category")
+ @discourseComputed("additionalTags", "canAdminTag", "category")
showAdminControls(additionalTags, canAdminTag, category) {
return !additionalTags && canAdminTag && !category;
},
@@ -135,7 +135,7 @@ export default Controller.extend(BulkTopicSelection, {
this.set("application.showFooter", !this.get("list.canLoadMore"));
},
- @computed("navMode", "list.topics.length", "loading")
+ @discourseComputed("navMode", "list.topics.length", "loading")
footerMessage(navMode, listTopicsLength, loading) {
if (loading || listTopicsLength !== 0) {
return;
diff --git a/app/assets/javascripts/discourse/controllers/topic.js.es6 b/app/assets/javascripts/discourse/controllers/topic.js.es6
index 730bd8fefe..7f2708a789 100644
--- a/app/assets/javascripts/discourse/controllers/topic.js.es6
+++ b/app/assets/javascripts/discourse/controllers/topic.js.es6
@@ -16,9 +16,9 @@ import debounce from "discourse/lib/debounce";
import isElementInViewport from "discourse/lib/is-element-in-viewport";
import { ajax } from "discourse/lib/ajax";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import { extractLinkMeta } from "discourse/lib/render-topic-featured-link";
import { popupAjaxError } from "discourse/lib/ajax-error";
import { spinnerHTML } from "discourse/helpers/loading-spinner";
@@ -80,7 +80,7 @@ export default Controller.extend(bufferedProperty("model"), {
}
},
- @computed("model.details.can_create_post")
+ @discourseComputed("model.details.can_create_post")
embedQuoteButton(canCreatePost) {
return (
canCreatePost &&
@@ -89,28 +89,31 @@ export default Controller.extend(bufferedProperty("model"), {
);
},
- @computed("model.postStream.loaded", "model.category_id")
+ @discourseComputed("model.postStream.loaded", "model.category_id")
showSharedDraftControls(loaded, categoryId) {
let draftCat = this.site.shared_drafts_category_id;
return loaded && draftCat && categoryId && draftCat === categoryId;
},
- @computed("site.mobileView", "model.posts_count")
+ @discourseComputed("site.mobileView", "model.posts_count")
showSelectedPostsAtBottom(mobileView, postsCount) {
return mobileView && postsCount > 3;
},
- @computed("model.postStream.posts", "model.postStream.postsWithPlaceholders")
+ @discourseComputed(
+ "model.postStream.posts",
+ "model.postStream.postsWithPlaceholders"
+ )
postsToRender(posts, postsWithPlaceholders) {
return this.capabilities.isAndroid ? posts : postsWithPlaceholders;
},
- @computed("model.postStream.loadingFilter")
+ @discourseComputed("model.postStream.loadingFilter")
androidLoading(loading) {
return this.capabilities.isAndroid && loading;
},
- @computed("model")
+ @discourseComputed("model")
pmPath(topic) {
return this.currentUser && this.currentUser.pmPath(topic);
},
@@ -153,12 +156,12 @@ export default Controller.extend(bufferedProperty("model"), {
DiscourseURL.routeTo(url);
},
- @computed
+ @discourseComputed
selectedQuery() {
return post => this.postSelected(post);
},
- @computed("model.isPrivateMessage", "model.category.id")
+ @discourseComputed("model.isPrivateMessage", "model.category.id")
canEditTopicFeaturedLink(isPrivateMessage, categoryId) {
if (!this.siteSettings.topic_featured_link_enabled || isPrivateMessage) {
return false;
@@ -174,12 +177,12 @@ export default Controller.extend(bufferedProperty("model"), {
);
},
- @computed("model")
+ @discourseComputed("model")
featuredLinkDomain(topic) {
return extractLinkMeta(topic).domain;
},
- @computed("model.isPrivateMessage")
+ @discourseComputed("model.isPrivateMessage")
canEditTags(isPrivateMessage) {
return (
this.site.get("can_tag_topics") &&
@@ -1157,7 +1160,7 @@ export default Controller.extend(bufferedProperty("model"), {
selectedPostsCount: alias("selectedPostIds.length"),
- @computed(
+ @discourseComputed(
"selectedPostIds",
"model.postStream.posts",
"selectedPostIds.[]",
@@ -1169,7 +1172,7 @@ export default Controller.extend(bufferedProperty("model"), {
.filter(post => post !== undefined);
},
- @computed("selectedPostsCount", "selectedPosts", "selectedPosts.[]")
+ @discourseComputed("selectedPostsCount", "selectedPosts", "selectedPosts.[]")
selectedPostsUsername(selectedPostsCount, selectedPosts) {
if (selectedPosts.length < 1 || selectedPostsCount > selectedPosts.length) {
return undefined;
@@ -1180,7 +1183,7 @@ export default Controller.extend(bufferedProperty("model"), {
: undefined;
},
- @computed(
+ @discourseComputed(
"selectedPostsCount",
"model.postStream.isMegaTopic",
"model.postStream.stream.length",
@@ -1199,14 +1202,14 @@ export default Controller.extend(bufferedProperty("model"), {
}
},
- @computed("selectedAllPosts", "model.postStream.isMegaTopic")
+ @discourseComputed("selectedAllPosts", "model.postStream.isMegaTopic")
canSelectAll(selectedAllPosts, isMegaTopic) {
return isMegaTopic ? false : !selectedAllPosts;
},
canDeselectAll: alias("selectedAllPosts"),
- @computed(
+ @discourseComputed(
"currentUser.staff",
"selectedPostsCount",
"selectedAllPosts",
@@ -1225,19 +1228,23 @@ export default Controller.extend(bufferedProperty("model"), {
);
},
- @computed("model.details.can_move_posts", "selectedPostsCount")
+ @discourseComputed("model.details.can_move_posts", "selectedPostsCount")
canMergeTopic(canMovePosts, selectedPostsCount) {
return canMovePosts && selectedPostsCount > 0;
},
- @computed("currentUser.admin", "selectedPostsCount", "selectedPostsUsername")
+ @discourseComputed(
+ "currentUser.admin",
+ "selectedPostsCount",
+ "selectedPostsUsername"
+ )
canChangeOwner(isAdmin, selectedPostsCount, selectedPostsUsername) {
return (
isAdmin && selectedPostsCount > 0 && selectedPostsUsername !== undefined
);
},
- @computed(
+ @discourseComputed(
"selectedPostsCount",
"selectedPostsUsername",
"selectedPosts",
@@ -1260,7 +1267,7 @@ export default Controller.extend(bufferedProperty("model"), {
return this.selectedAllPost || this.selectedPostIds.includes(post.id);
},
- @computed
+ @discourseComputed
loadingHTML() {
return spinnerHTML;
},
diff --git a/app/assets/javascripts/discourse/controllers/upload-selector.js.es6 b/app/assets/javascripts/discourse/controllers/upload-selector.js.es6
index 87c73494a0..554fe6db2f 100644
--- a/app/assets/javascripts/discourse/controllers/upload-selector.js.es6
+++ b/app/assets/javascripts/discourse/controllers/upload-selector.js.es6
@@ -2,9 +2,9 @@ import { equal } from "@ember/object/computed";
import Controller from "@ember/controller";
import ModalFunctionality from "discourse/mixins/modal-functionality";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import {
allowsAttachments,
authorizesAllExtensions,
@@ -27,13 +27,13 @@ export default Controller.extend(ModalFunctionality, {
remote: equal("selection", "remote"),
selection: "local",
- @computed()
+ @discourseComputed()
uploadIcon: () => uploadIcon(),
- @computed()
+ @discourseComputed()
title: () => uploadTranslate("title"),
- @computed("selection")
+ @discourseComputed("selection")
tip(selection) {
const authorized_extensions = authorizesAllExtensions()
? ""
diff --git a/app/assets/javascripts/discourse/controllers/user-invited-show.js.es6 b/app/assets/javascripts/discourse/controllers/user-invited-show.js.es6
index 8a8c102b0e..59d197a875 100644
--- a/app/assets/javascripts/discourse/controllers/user-invited-show.js.es6
+++ b/app/assets/javascripts/discourse/controllers/user-invited-show.js.es6
@@ -4,9 +4,9 @@ import Invite from "discourse/models/invite";
import debounce from "discourse/lib/debounce";
import { popupAjaxError } from "discourse/lib/ajax-error";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
export default Controller.extend({
user: null,
@@ -35,7 +35,7 @@ export default Controller.extend({
inviteRedeemed: equal("filter", "redeemed"),
- @computed("filter")
+ @discourseComputed("filter")
showBulkActionButtons(filter) {
return (
filter === "pending" &&
@@ -50,7 +50,7 @@ export default Controller.extend({
showSearch: gte("totalInvites", 10),
- @computed("invitesCount.total", "invitesCount.pending")
+ @discourseComputed("invitesCount.total", "invitesCount.pending")
pendingLabel(invitesCountTotal, invitesCountPending) {
if (invitesCountTotal > 50) {
return I18n.t("user.invited.pending_tab_with_count", {
@@ -61,7 +61,7 @@ export default Controller.extend({
}
},
- @computed("invitesCount.total", "invitesCount.redeemed")
+ @discourseComputed("invitesCount.total", "invitesCount.redeemed")
redeemedLabel(invitesCountTotal, invitesCountRedeemed) {
if (invitesCountTotal > 50) {
return I18n.t("user.invited.redeemed_tab_with_count", {
diff --git a/app/assets/javascripts/discourse/controllers/user-notifications.js.es6 b/app/assets/javascripts/discourse/controllers/user-notifications.js.es6
index ea5507cc5c..24e61aa73a 100644
--- a/app/assets/javascripts/discourse/controllers/user-notifications.js.es6
+++ b/app/assets/javascripts/discourse/controllers/user-notifications.js.es6
@@ -2,9 +2,9 @@ import { inject } from "@ember/controller";
import Controller from "@ember/controller";
import { ajax } from "discourse/lib/ajax";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
export default Controller.extend({
application: inject(),
@@ -14,12 +14,12 @@ export default Controller.extend({
this.set("application.showFooter", !this.get("model.canLoadMore"));
},
- @computed("model.content.length")
+ @discourseComputed("model.content.length")
hasNotifications(length) {
return length > 0;
},
- @computed("model.content.@each.read")
+ @discourseComputed("model.content.@each.read")
allNotificationsRead() {
return !this.get("model.content").some(
notification => !notification.get("read")
diff --git a/app/assets/javascripts/discourse/controllers/user-private-messages.js.es6 b/app/assets/javascripts/discourse/controllers/user-private-messages.js.es6
index c6252978c9..724d8b9909 100644
--- a/app/assets/javascripts/discourse/controllers/user-private-messages.js.es6
+++ b/app/assets/javascripts/discourse/controllers/user-private-messages.js.es6
@@ -1,8 +1,8 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { alias, equal, and } from "@ember/object/computed";
import { inject as service } from "@ember/service";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
import Topic from "discourse/models/topic";
export default Controller.extend({
@@ -22,17 +22,17 @@ export default Controller.extend({
showNewPM: and("user.viewingSelf", "currentUser.can_send_private_messages"),
- @computed("selected.[]", "bulkSelectEnabled")
+ @discourseComputed("selected.[]", "bulkSelectEnabled")
hasSelection(selected, bulkSelectEnabled) {
return bulkSelectEnabled && selected && selected.length > 0;
},
- @computed("hasSelection", "pmView", "archive")
+ @discourseComputed("hasSelection", "pmView", "archive")
canMoveToInbox(hasSelection, pmView, archive) {
return hasSelection && (pmView === "archive" || archive);
},
- @computed("hasSelection", "pmView", "archive")
+ @discourseComputed("hasSelection", "pmView", "archive")
canArchive(hasSelection, pmView, archive) {
return hasSelection && pmView !== "archive" && !archive;
},
diff --git a/app/assets/javascripts/discourse/controllers/user-summary.js.es6 b/app/assets/javascripts/discourse/controllers/user-summary.js.es6
index 7383cfa336..0a1a37572e 100644
--- a/app/assets/javascripts/discourse/controllers/user-summary.js.es6
+++ b/app/assets/javascripts/discourse/controllers/user-summary.js.es6
@@ -1,7 +1,7 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { alias } from "@ember/object/computed";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
import { durationTiny } from "discourse/lib/formatter";
// should be kept in sync with 'UserSummary::MAX_BADGES'
@@ -11,22 +11,22 @@ export default Controller.extend({
userController: inject("user"),
user: alias("userController.model"),
- @computed("model.badges.length")
+ @discourseComputed("model.badges.length")
moreBadges(badgesLength) {
return badgesLength >= MAX_BADGES;
},
- @computed("model.time_read")
+ @discourseComputed("model.time_read")
timeRead(timeReadSeconds) {
return durationTiny(timeReadSeconds);
},
- @computed("model.time_read", "model.recent_time_read")
+ @discourseComputed("model.time_read", "model.recent_time_read")
showRecentTimeRead(timeRead, recentTimeRead) {
return timeRead !== recentTimeRead && recentTimeRead !== 0;
},
- @computed("model.recent_time_read")
+ @discourseComputed("model.recent_time_read")
recentTimeRead(recentTimeReadSeconds) {
return recentTimeReadSeconds > 0
? durationTiny(recentTimeReadSeconds)
diff --git a/app/assets/javascripts/discourse/controllers/user-topics-list.js.es6 b/app/assets/javascripts/discourse/controllers/user-topics-list.js.es6
index 5539500165..6c09d2e36b 100644
--- a/app/assets/javascripts/discourse/controllers/user-topics-list.js.es6
+++ b/app/assets/javascripts/discourse/controllers/user-topics-list.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
// Lists of topics on a user's page.
export default Controller.extend({
@@ -26,7 +26,7 @@ export default Controller.extend({
this.set("application.showFooter", !this.get("model.canLoadMore"));
}.observes("model.canLoadMore"),
- @computed("incomingCount")
+ @discourseComputed("incomingCount")
hasIncoming(incomingCount) {
return incomingCount > 0;
},
diff --git a/app/assets/javascripts/discourse/controllers/user.js.es6 b/app/assets/javascripts/discourse/controllers/user.js.es6
index e24bf67a68..507ca24690 100644
--- a/app/assets/javascripts/discourse/controllers/user.js.es6
+++ b/app/assets/javascripts/discourse/controllers/user.js.es6
@@ -1,3 +1,4 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { isEmpty } from "@ember/utils";
import { alias, or, gt, not, and } from "@ember/object/computed";
import EmberObject from "@ember/object";
@@ -5,7 +6,6 @@ import { inject as service } from "@ember/service";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
import CanCheckEmails from "discourse/mixins/can-check-emails";
-import computed from "ember-addons/ember-computed-decorators";
import User from "discourse/models/user";
import optionalService from "discourse/lib/optional-service";
import { prioritizeNameInUx } from "discourse/lib/settings";
@@ -18,23 +18,28 @@ export default Controller.extend(CanCheckEmails, {
currentPath: alias("router._router.currentPath"),
adminTools: optionalService(),
- @computed("model.username")
+ @discourseComputed("model.username")
viewingSelf(username) {
let currentUser = this.currentUser;
return currentUser && username === currentUser.get("username");
},
- @computed("viewingSelf", "model.profile_hidden")
+ @discourseComputed("viewingSelf", "model.profile_hidden")
canExpandProfile(viewingSelf, profileHidden) {
return !profileHidden && viewingSelf;
},
- @computed("model.profileBackgroundUrl")
+ @discourseComputed("model.profileBackgroundUrl")
hasProfileBackgroundUrl(background) {
return !isEmpty(background.toString());
},
- @computed("model.profile_hidden", "indexStream", "viewingSelf", "forceExpand")
+ @discourseComputed(
+ "model.profile_hidden",
+ "indexStream",
+ "viewingSelf",
+ "forceExpand"
+ )
collapsedInfo(profileHidden, indexStream, viewingSelf, forceExpand) {
if (profileHidden) {
return true;
@@ -56,58 +61,58 @@ export default Controller.extend(CanCheckEmails, {
"hasReceivedWarnings"
),
- @computed("model.suspended", "currentUser.staff")
+ @discourseComputed("model.suspended", "currentUser.staff")
isNotSuspendedOrIsStaff(suspended, isStaff) {
return !suspended || isStaff;
},
linkWebsite: not("model.isBasic"),
- @computed("model.trust_level")
+ @discourseComputed("model.trust_level")
removeNoFollow(trustLevel) {
return trustLevel > 2 && !this.siteSettings.tl3_links_no_follow;
},
- @computed("viewingSelf", "currentUser.admin")
+ @discourseComputed("viewingSelf", "currentUser.admin")
showBookmarks(viewingSelf, isAdmin) {
return viewingSelf || isAdmin;
},
- @computed("viewingSelf")
+ @discourseComputed("viewingSelf")
showDrafts(viewingSelf) {
return viewingSelf;
},
- @computed("viewingSelf", "currentUser.admin")
+ @discourseComputed("viewingSelf", "currentUser.admin")
showPrivateMessages(viewingSelf, isAdmin) {
return (
this.siteSettings.enable_personal_messages && (viewingSelf || isAdmin)
);
},
- @computed("viewingSelf", "currentUser.staff")
+ @discourseComputed("viewingSelf", "currentUser.staff")
showNotificationsTab(viewingSelf, staff) {
return viewingSelf || staff;
},
- @computed("model.name")
+ @discourseComputed("model.name")
nameFirst(name) {
return prioritizeNameInUx(name, this.siteSettings);
},
- @computed("model.badge_count")
+ @discourseComputed("model.badge_count")
showBadges(badgeCount) {
return Discourse.SiteSettings.enable_badges && badgeCount > 0;
},
- @computed()
+ @discourseComputed()
canInviteToForum() {
return User.currentProp("can_invite_to_forum");
},
canDeleteUser: and("model.can_be_deleted", "model.can_delete_all_posts"),
- @computed("model.user_fields.@each.value")
+ @discourseComputed("model.user_fields.@each.value")
publicUserFields() {
const siteUserFields = this.site.get("user_fields");
if (!isEmpty(siteUserFields)) {
diff --git a/app/assets/javascripts/discourse/helpers/reviewable-status.js.es6 b/app/assets/javascripts/discourse/helpers/reviewable-status.js.es6
index 5807cb0e64..b024500a0c 100644
--- a/app/assets/javascripts/discourse/helpers/reviewable-status.js.es6
+++ b/app/assets/javascripts/discourse/helpers/reviewable-status.js.es6
@@ -1,6 +1,5 @@
import { htmlHelper } from "discourse-common/lib/helpers";
import { iconHTML } from "discourse-common/lib/icon-library";
-
import {
PENDING,
APPROVED,
diff --git a/app/assets/javascripts/discourse/lib/computed.js.es6 b/app/assets/javascripts/discourse/lib/computed.js.es6
index e6a440eb83..992029d293 100644
--- a/app/assets/javascripts/discourse/lib/computed.js.es6
+++ b/app/assets/javascripts/discourse/lib/computed.js.es6
@@ -6,7 +6,7 @@ import addonFmt from "ember-addons/fmt";
@method propertyEqual
@params {String} p1 the first property
@params {String} p2 the second property
- @return {Function} computedProperty function
+ @return {Function} discourseComputedProperty function
**/
export function propertyEqual(p1, p2) {
@@ -21,7 +21,7 @@ export function propertyEqual(p1, p2) {
@method propertyNotEqual
@params {String} p1 the first property
@params {String} p2 the second property
- @return {Function} computedProperty function
+ @return {Function} discourseComputedProperty function
**/
export function propertyNotEqual(p1, p2) {
return Ember.computed(p1, p2, function() {
@@ -47,7 +47,7 @@ export function propertyLessThan(p1, p2) {
@method i18n
@params {String} properties* to format
@params {String} format the i18n format string
- @return {Function} computedProperty function
+ @return {Function} discourseComputedProperty function
**/
export function i18n(...args) {
const format = args.pop();
@@ -63,7 +63,7 @@ export function i18n(...args) {
@method fmt
@params {String} properties* to format
@params {String} format the format string
- @return {Function} computedProperty function
+ @return {Function} discourseComputedProperty function
**/
export function fmt(...args) {
const format = args.pop();
@@ -79,7 +79,7 @@ export function fmt(...args) {
@method url
@params {String} properties* to format
@params {String} format the format string for the URL
- @return {Function} computedProperty function returning a URL
+ @return {Function} discourseComputedProperty function returning a URL
**/
export function url(...args) {
const format = args.pop();
@@ -94,7 +94,7 @@ export function url(...args) {
@method endWith
@params {String} properties* to check
@params {String} substring the substring
- @return {Function} computedProperty function
+ @return {Function} discourseComputedProperty function
**/
export function endWith() {
const args = Array.prototype.slice.call(arguments, 0);
diff --git a/app/assets/javascripts/discourse/lib/posts-with-placeholders.js.es6 b/app/assets/javascripts/discourse/lib/posts-with-placeholders.js.es6
index d1b2092445..3bf8c2457c 100644
--- a/app/assets/javascripts/discourse/lib/posts-with-placeholders.js.es6
+++ b/app/assets/javascripts/discourse/lib/posts-with-placeholders.js.es6
@@ -1,5 +1,5 @@
import EmberObject from "@ember/object";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
export function Placeholder(viewName) {
this.viewName = viewName;
@@ -13,7 +13,7 @@ export default EmberObject.extend(Ember.Array, {
this._appendingIds = {};
},
- @computed
+ @discourseComputed
length() {
return (
this.get("posts.length") + Object.keys(this._appendingIds || {}).length
diff --git a/app/assets/javascripts/discourse/lib/register-topic-footer-button.js.es6 b/app/assets/javascripts/discourse/lib/register-topic-footer-button.js.es6
index 65b687ac7c..6b7bdf63b0 100644
--- a/app/assets/javascripts/discourse/lib/register-topic-footer-button.js.es6
+++ b/app/assets/javascripts/discourse/lib/register-topic-footer-button.js.es6
@@ -33,7 +33,7 @@ export function registerTopicFooterButton(button) {
// css class appended to the button
classNames: [],
- // computed properties which should force a button state refresh
+ // discourseComputed properties which should force a button state refresh
// eg: ["topic.bookmarked", "topic.category_id"]
dependentKeys: [],
@@ -88,37 +88,37 @@ export function getTopicFooterButtons() {
return Object.values(_topicFooterButtons)
.filter(button => _compute(button, "displayed"))
.map(button => {
- const computedButon = {};
+ const discourseComputedButon = {};
- computedButon.id = button.id;
+ discourseComputedButon.id = button.id;
const label = _compute(button, "label");
- computedButon.label = label
+ discourseComputedButon.label = label
? I18n.t(label)
: _compute(button, "translatedLabel");
const title = _compute(button, "title");
- computedButon.title = title
+ discourseComputedButon.title = title
? I18n.t(title)
: _compute(button, "translatedTitle");
- computedButon.classNames = (
+ discourseComputedButon.classNames = (
_compute(button, "classNames") || []
).join(" ");
- computedButon.icon = _compute(button, "icon");
- computedButon.disabled = _compute(button, "disabled");
- computedButon.dropdown = _compute(button, "dropdown");
- computedButon.priority = _compute(button, "priority");
+ discourseComputedButon.icon = _compute(button, "icon");
+ discourseComputedButon.disabled = _compute(button, "disabled");
+ discourseComputedButon.dropdown = _compute(button, "dropdown");
+ discourseComputedButon.priority = _compute(button, "priority");
if (_isFunction(button.action)) {
- computedButon.action = () => button.action.apply(this);
+ discourseComputedButon.action = () => button.action.apply(this);
} else {
const actionName = button.action;
- computedButon.action = () => this[actionName]();
+ discourseComputedButon.action = () => this[actionName]();
}
- return computedButon;
+ return discourseComputedButon;
})
.sortBy("priority")
.reverse();
diff --git a/app/assets/javascripts/discourse/mixins/add-archetype-class.js.es6 b/app/assets/javascripts/discourse/mixins/add-archetype-class.js.es6
index a8a2c3c528..1436f0def6 100644
--- a/app/assets/javascripts/discourse/mixins/add-archetype-class.js.es6
+++ b/app/assets/javascripts/discourse/mixins/add-archetype-class.js.es6
@@ -1,4 +1,4 @@
-import { on, observes } from "ember-addons/ember-computed-decorators";
+import { on, observes } from "discourse-common/utils/decorators";
// Mix this in to a view that has a `archetype` property to automatically
// add it to the body as the view is entered / left / model is changed.
diff --git a/app/assets/javascripts/discourse/mixins/bulk-topic-selection.js.es6 b/app/assets/javascripts/discourse/mixins/bulk-topic-selection.js.es6
index a4772fb594..cc2dfc1d55 100644
--- a/app/assets/javascripts/discourse/mixins/bulk-topic-selection.js.es6
+++ b/app/assets/javascripts/discourse/mixins/bulk-topic-selection.js.es6
@@ -1,6 +1,6 @@
import { alias } from "@ember/object/computed";
import { NotificationLevels } from "discourse/lib/notification-levels";
-import { on } from "ember-addons/ember-computed-decorators";
+import { on } from "discourse-common/utils/decorators";
import Mixin from "@ember/object/mixin";
import Topic from "discourse/models/topic";
diff --git a/app/assets/javascripts/discourse/mixins/grant-badge-controller.js.es6 b/app/assets/javascripts/discourse/mixins/grant-badge-controller.js.es6
index 37502e3749..153ba29c01 100644
--- a/app/assets/javascripts/discourse/mixins/grant-badge-controller.js.es6
+++ b/app/assets/javascripts/discourse/mixins/grant-badge-controller.js.es6
@@ -1,11 +1,11 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { empty } from "@ember/object/computed";
-import computed from "ember-addons/ember-computed-decorators";
import UserBadge from "discourse/models/user-badge";
import { convertIconClass } from "discourse-common/lib/icon-library";
import Mixin from "@ember/object/mixin";
export default Mixin.create({
- @computed("allBadges.[]", "userBadges.[]")
+ @discourseComputed("allBadges.[]", "userBadges.[]")
grantableBadges(allBadges, userBadges) {
const granted = userBadges.reduce((map, badge) => {
map[badge.get("badge_id")] = true;
@@ -31,7 +31,7 @@ export default Mixin.create({
noGrantableBadges: empty("grantableBadges"),
- @computed("selectedBadgeId", "grantableBadges")
+ @discourseComputed("selectedBadgeId", "grantableBadges")
selectedBadgeGrantable(selectedBadgeId, grantableBadges) {
return (
grantableBadges &&
diff --git a/app/assets/javascripts/discourse/mixins/load-more.js.es6 b/app/assets/javascripts/discourse/mixins/load-more.js.es6
index a7761e1399..f54b563034 100644
--- a/app/assets/javascripts/discourse/mixins/load-more.js.es6
+++ b/app/assets/javascripts/discourse/mixins/load-more.js.es6
@@ -1,6 +1,6 @@
import Eyeline from "discourse/lib/eyeline";
import Scrolling from "discourse/mixins/scrolling";
-import { on } from "ember-addons/ember-computed-decorators";
+import { on } from "discourse-common/utils/decorators";
import Mixin from "@ember/object/mixin";
// Provides the ability to load more items for a view which is scrolled to the bottom.
diff --git a/app/assets/javascripts/discourse/mixins/name-validation.js.es6 b/app/assets/javascripts/discourse/mixins/name-validation.js.es6
index 46f1b4dfae..e447f9fcb6 100644
--- a/app/assets/javascripts/discourse/mixins/name-validation.js.es6
+++ b/app/assets/javascripts/discourse/mixins/name-validation.js.es6
@@ -1,10 +1,10 @@
import { isEmpty } from "@ember/utils";
import InputValidation from "discourse/models/input-validation";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import Mixin from "@ember/object/mixin";
export default Mixin.create({
- @computed()
+ @discourseComputed()
nameInstructions() {
return I18n.t(
this.siteSettings.full_name_required
@@ -14,7 +14,7 @@ export default Mixin.create({
},
// Validate the name.
- @computed("accountName")
+ @discourseComputed("accountName")
nameValidation() {
if (this.siteSettings.full_name_required && isEmpty(this.accountName)) {
return InputValidation.create({ failed: true });
diff --git a/app/assets/javascripts/discourse/mixins/password-validation.js.es6 b/app/assets/javascripts/discourse/mixins/password-validation.js.es6
index 3ddf9131f0..ec665cdbe6 100644
--- a/app/assets/javascripts/discourse/mixins/password-validation.js.es6
+++ b/app/assets/javascripts/discourse/mixins/password-validation.js.es6
@@ -1,6 +1,6 @@
import { isEmpty } from "@ember/utils";
import InputValidation from "discourse/models/input-validation";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import Mixin from "@ember/object/mixin";
export default Mixin.create({
@@ -12,21 +12,21 @@ export default Mixin.create({
this.set("rejectedPasswordsMessages", new Map());
},
- @computed("passwordMinLength")
+ @discourseComputed("passwordMinLength")
passwordInstructions() {
return I18n.t("user.password.instructions", {
count: this.passwordMinLength
});
},
- @computed("isDeveloper", "admin")
+ @discourseComputed("isDeveloper", "admin")
passwordMinLength(isDeveloper, admin) {
return isDeveloper || admin
? this.siteSettings.min_admin_password_length
: this.siteSettings.min_password_length;
},
- @computed(
+ @discourseComputed(
"accountPassword",
"passwordRequired",
"rejectedPasswords.[]",
diff --git a/app/assets/javascripts/discourse/mixins/preferences-tab-controller.js.es6 b/app/assets/javascripts/discourse/mixins/preferences-tab-controller.js.es6
index 7e49326f41..2e8763097c 100644
--- a/app/assets/javascripts/discourse/mixins/preferences-tab-controller.js.es6
+++ b/app/assets/javascripts/discourse/mixins/preferences-tab-controller.js.es6
@@ -1,10 +1,10 @@
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import Mixin from "@ember/object/mixin";
export default Mixin.create({
saved: false,
- @computed("model.isSaving")
+ @discourseComputed("model.isSaving")
saveButtonText(isSaving) {
return isSaving ? I18n.t("saving") : I18n.t("save");
}
diff --git a/app/assets/javascripts/discourse/mixins/upload.js.es6 b/app/assets/javascripts/discourse/mixins/upload.js.es6
index a3b0d8626a..071f749b75 100644
--- a/app/assets/javascripts/discourse/mixins/upload.js.es6
+++ b/app/assets/javascripts/discourse/mixins/upload.js.es6
@@ -2,7 +2,6 @@ import {
displayErrorForUpload,
validateUploadedFiles
} from "discourse/lib/utilities";
-
import getUrl from "discourse-common/lib/get-url";
import { on } from "@ember/object/evented";
import Mixin from "@ember/object/mixin";
diff --git a/app/assets/javascripts/discourse/mixins/user-fields-validation.js.es6 b/app/assets/javascripts/discourse/mixins/user-fields-validation.js.es6
index ec007c993d..e535043a2d 100644
--- a/app/assets/javascripts/discourse/mixins/user-fields-validation.js.es6
+++ b/app/assets/javascripts/discourse/mixins/user-fields-validation.js.es6
@@ -3,8 +3,8 @@ import EmberObject from "@ember/object";
import InputValidation from "discourse/models/input-validation";
import {
on,
- default as computed
-} from "ember-addons/ember-computed-decorators";
+ default as discourseComputed
+} from "discourse-common/utils/decorators";
import Mixin from "@ember/object/mixin";
export default Mixin.create({
@@ -24,7 +24,7 @@ export default Mixin.create({
},
// Validate required fields
- @computed("userFields.@each.value")
+ @discourseComputed("userFields.@each.value")
userFieldsValidation() {
let userFields = this.userFields;
if (userFields) {
diff --git a/app/assets/javascripts/discourse/mixins/username-validation.js.es6 b/app/assets/javascripts/discourse/mixins/username-validation.js.es6
index 66e86221a9..35ccf6c8cc 100644
--- a/app/assets/javascripts/discourse/mixins/username-validation.js.es6
+++ b/app/assets/javascripts/discourse/mixins/username-validation.js.es6
@@ -2,7 +2,7 @@ import { isEmpty } from "@ember/utils";
import InputValidation from "discourse/models/input-validation";
import debounce from "discourse/lib/debounce";
import { setting } from "discourse/lib/computed";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import Mixin from "@ember/object/mixin";
export default Mixin.create({
@@ -27,7 +27,7 @@ export default Mixin.create({
});
}, 500),
- @computed("accountUsername")
+ @discourseComputed("accountUsername")
basicUsernameValidation(accountUsername) {
this.set("uniqueUsernameValidation", null);
@@ -118,7 +118,7 @@ export default Mixin.create({
}, 500),
// Actually wait for the async name check before we're 100% sure we're good to go
- @computed("uniqueUsernameValidation", "basicUsernameValidation")
+ @discourseComputed("uniqueUsernameValidation", "basicUsernameValidation")
usernameValidation() {
const basicValidation = this.basicUsernameValidation;
const uniqueUsername = this.uniqueUsernameValidation;
diff --git a/app/assets/javascripts/discourse/models/badge-grouping.js.es6 b/app/assets/javascripts/discourse/models/badge-grouping.js.es6
index 573dff223d..6dbaa5c7c6 100644
--- a/app/assets/javascripts/discourse/models/badge-grouping.js.es6
+++ b/app/assets/javascripts/discourse/models/badge-grouping.js.es6
@@ -1,13 +1,13 @@
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
import RestModel from "discourse/models/rest";
export default RestModel.extend({
- @computed("name")
+ @discourseComputed("name")
i18nNameKey() {
return this.name.toLowerCase().replace(/\s/g, "_");
},
- @computed("name")
+ @discourseComputed("name")
displayName() {
const i18nKey = `badges.badge_grouping.${this.i18nNameKey}.name`;
return I18n.t(i18nKey, { defaultValue: this.name });
diff --git a/app/assets/javascripts/discourse/models/badge.js.es6 b/app/assets/javascripts/discourse/models/badge.js.es6
index 88203b5084..5b9e46cef9 100644
--- a/app/assets/javascripts/discourse/models/badge.js.es6
+++ b/app/assets/javascripts/discourse/models/badge.js.es6
@@ -1,15 +1,15 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { none } from "@ember/object/computed";
import EmberObject from "@ember/object";
import { ajax } from "discourse/lib/ajax";
import BadgeGrouping from "discourse/models/badge-grouping";
import RestModel from "discourse/models/rest";
-import computed from "ember-addons/ember-computed-decorators";
import { Promise } from "rsvp";
const Badge = RestModel.extend({
newBadge: none("id"),
- @computed
+ @discourseComputed
url() {
return Discourse.getURL(`/badges/${this.id}/${this.slug}`);
},
@@ -27,7 +27,7 @@ const Badge = RestModel.extend({
}
},
- @computed("badge_type.name")
+ @discourseComputed("badge_type.name")
badgeTypeClassName(type) {
type = type || "";
return `badge-type-${type.toLowerCase()}`;
diff --git a/app/assets/javascripts/discourse/models/category.js.es6 b/app/assets/javascripts/discourse/models/category.js.es6
index 4248f6a8f8..98336dac42 100644
--- a/app/assets/javascripts/discourse/models/category.js.es6
+++ b/app/assets/javascripts/discourse/models/category.js.es6
@@ -1,8 +1,8 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { get } from "@ember/object";
import { ajax } from "discourse/lib/ajax";
import RestModel from "discourse/models/rest";
-import computed from "ember-addons/ember-computed-decorators";
-import { on } from "ember-addons/ember-computed-decorators";
+import { on } from "discourse-common/utils/decorators";
import PermissionType from "discourse/models/permission-type";
import { NotificationLevels } from "discourse/lib/notification-levels";
@@ -39,7 +39,7 @@ const Category = RestModel.extend({
}
},
- @computed
+ @discourseComputed
availablePermissions() {
return [
PermissionType.create({ id: PermissionType.FULL }),
@@ -48,52 +48,52 @@ const Category = RestModel.extend({
];
},
- @computed("id")
+ @discourseComputed("id")
searchContext(id) {
return { type: "category", id, category: this };
},
- @computed("notification_level")
+ @discourseComputed("notification_level")
isMuted(notificationLevel) {
return notificationLevel === NotificationLevels.MUTED;
},
- @computed("name")
+ @discourseComputed("name")
url() {
return Discourse.getURL("/c/") + Category.slugFor(this);
},
- @computed
+ @discourseComputed
fullSlug() {
return Category.slugFor(this).replace(/\//g, "-");
},
- @computed("name")
+ @discourseComputed("name")
nameLower(name) {
return name.toLowerCase();
},
- @computed("url")
+ @discourseComputed("url")
unreadUrl(url) {
return `${url}/l/unread`;
},
- @computed("url")
+ @discourseComputed("url")
newUrl(url) {
return `${url}/l/new`;
},
- @computed("color", "text_color")
+ @discourseComputed("color", "text_color")
style(color, textColor) {
return `background-color: #${color}; color: #${textColor}`;
},
- @computed("topic_count")
+ @discourseComputed("topic_count")
moreTopics(topicCount) {
return topicCount > (this.num_featured_topics || 2);
},
- @computed("topic_count", "subcategories")
+ @discourseComputed("topic_count", "subcategories")
totalTopicCount(topicCount, subcats) {
let count = topicCount;
if (subcats) {
@@ -181,26 +181,26 @@ const Category = RestModel.extend({
this.availableGroups.addObject(permission.group_name);
},
- @computed("topics")
+ @discourseComputed("topics")
latestTopic(topics) {
if (topics && topics.length) {
return topics[0];
}
},
- @computed("topics")
+ @discourseComputed("topics")
featuredTopics(topics) {
if (topics && topics.length) {
return topics.slice(0, this.num_featured_topics || 2);
}
},
- @computed("id", "topicTrackingState.messageCount")
+ @discourseComputed("id", "topicTrackingState.messageCount")
unreadTopics(id) {
return this.topicTrackingState.countUnread(id);
},
- @computed("id", "topicTrackingState.messageCount")
+ @discourseComputed("id", "topicTrackingState.messageCount")
newTopics(id) {
return this.topicTrackingState.countNew(id);
},
@@ -211,7 +211,7 @@ const Category = RestModel.extend({
return ajax(url, { data: { notification_level }, type: "POST" });
},
- @computed("id")
+ @discourseComputed("id")
isUncategorizedCategory(id) {
return id === Discourse.Site.currentProp("uncategorized_category_id");
}
diff --git a/app/assets/javascripts/discourse/models/composer.js.es6 b/app/assets/javascripts/discourse/models/composer.js.es6
index 8e3a1af259..60fb8272a6 100644
--- a/app/assets/javascripts/discourse/models/composer.js.es6
+++ b/app/assets/javascripts/discourse/models/composer.js.es6
@@ -10,10 +10,10 @@ import { throwAjaxError } from "discourse/lib/ajax-error";
import Quote from "discourse/lib/quote";
import Draft from "discourse/models/draft";
import {
- default as computed,
+ default as discourseComputed,
observes,
on
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import { escapeExpression, tinyAvatar } from "discourse/lib/utilities";
import { propertyNotEqual } from "discourse/lib/computed";
import throttle from "discourse/lib/throttle";
@@ -108,7 +108,7 @@ const Composer = RestModel.extend({
sharedDraft: equal("action", CREATE_SHARED_DRAFT),
- @computed
+ @discourseComputed
categoryId: {
get() {
return this._categoryId;
@@ -132,12 +132,12 @@ const Composer = RestModel.extend({
}
},
- @computed("categoryId")
+ @discourseComputed("categoryId")
category(categoryId) {
return categoryId ? this.site.categories.findBy("id", categoryId) : null;
},
- @computed("category")
+ @discourseComputed("category")
minimumRequiredTags(category) {
return category && category.minimum_required_tags > 0
? category.minimum_required_tags
@@ -150,18 +150,18 @@ const Composer = RestModel.extend({
notCreatingPrivateMessage: not("creatingPrivateMessage"),
notPrivateMessage: not("privateMessage"),
- @computed("editingPost", "topic.details.can_edit")
+ @discourseComputed("editingPost", "topic.details.can_edit")
disableTitleInput(editingPost, canEditTopic) {
return editingPost && !canEditTopic;
},
- @computed("privateMessage", "archetype.hasOptions")
+ @discourseComputed("privateMessage", "archetype.hasOptions")
showCategoryChooser(isPrivateMessage, hasOptions) {
const manyCategories = this.site.categories.length > 1;
return !isPrivateMessage && (hasOptions || manyCategories);
},
- @computed("creatingPrivateMessage", "topic")
+ @discourseComputed("creatingPrivateMessage", "topic")
privateMessage(creatingPrivateMessage, topic) {
return (
creatingPrivateMessage || (topic && topic.archetype === "private_message")
@@ -170,7 +170,7 @@ const Composer = RestModel.extend({
topicFirstPost: or("creatingTopic", "editingFirstPost"),
- @computed("action")
+ @discourseComputed("action")
editingPost: isEdit,
replyingToTopic: equal("action", REPLY),
@@ -202,7 +202,7 @@ const Composer = RestModel.extend({
}
},
- @computed
+ @discourseComputed
composerTime: {
get() {
let total = this.composerTotalOpened || 0;
@@ -216,7 +216,7 @@ const Composer = RestModel.extend({
}
},
- @computed("archetypeId")
+ @discourseComputed("archetypeId")
archetype(archetypeId) {
return this.archetypes.findBy("id", archetypeId);
},
@@ -251,7 +251,7 @@ const Composer = RestModel.extend({
"notPrivateMessage"
),
- @computed("canEditTitle", "creatingPrivateMessage", "categoryId")
+ @discourseComputed("canEditTitle", "creatingPrivateMessage", "categoryId")
canEditTopicFeaturedLink(canEditTitle, creatingPrivateMessage, categoryId) {
if (
!this.siteSettings.topic_featured_link_enabled ||
@@ -277,14 +277,14 @@ const Composer = RestModel.extend({
);
},
- @computed("canEditTopicFeaturedLink")
+ @discourseComputed("canEditTopicFeaturedLink")
titlePlaceholder(canEditTopicFeaturedLink) {
return canEditTopicFeaturedLink
? "composer.title_or_link_placeholder"
: "composer.title_placeholder";
},
- @computed("action", "post", "topic", "topic.title")
+ @discourseComputed("action", "post", "topic", "topic.title")
replyOptions(action, post, topic, topicTitle) {
const options = {
userLink: null,
@@ -334,7 +334,7 @@ const Composer = RestModel.extend({
return options;
},
- @computed(
+ @discourseComputed(
"loading",
"canEditTitle",
"titleLength",
@@ -405,7 +405,7 @@ const Composer = RestModel.extend({
}
},
- @computed("canCategorize", "categoryId")
+ @discourseComputed("canCategorize", "categoryId")
requiredCategoryMissing(canCategorize, categoryId) {
return (
canCategorize &&
@@ -414,14 +414,14 @@ const Composer = RestModel.extend({
);
},
- @computed("minimumTitleLength", "titleLength", "post.static_doc")
+ @discourseComputed("minimumTitleLength", "titleLength", "post.static_doc")
titleLengthValid(minTitleLength, titleLength, staticDoc) {
if (this.user.admin && staticDoc && titleLength > 0) return true;
if (titleLength < minTitleLength) return false;
return titleLength <= this.siteSettings.max_topic_title_length;
},
- @computed("metaData")
+ @discourseComputed("metaData")
hasMetaData(metaData) {
return metaData ? isEmpty(Ember.keys(metaData)) : false;
},
@@ -430,12 +430,12 @@ const Composer = RestModel.extend({
titleDirty: propertyNotEqual("title", "originalTitle"),
- @computed("minimumTitleLength", "titleLength")
+ @discourseComputed("minimumTitleLength", "titleLength")
missingTitleCharacters(minimumTitleLength, titleLength) {
return minimumTitleLength - titleLength;
},
- @computed("privateMessage")
+ @discourseComputed("privateMessage")
minimumTitleLength(privateMessage) {
if (privateMessage) {
return this.siteSettings.min_personal_message_title_length;
@@ -444,7 +444,11 @@ const Composer = RestModel.extend({
}
},
- @computed("minimumPostLength", "replyLength", "canEditTopicFeaturedLink")
+ @discourseComputed(
+ "minimumPostLength",
+ "replyLength",
+ "canEditTopicFeaturedLink"
+ )
missingReplyCharacters(
minimumPostLength,
replyLength,
@@ -459,7 +463,11 @@ const Composer = RestModel.extend({
return minimumPostLength - replyLength;
},
- @computed("privateMessage", "topicFirstPost", "topic.pm_with_non_human_user")
+ @discourseComputed(
+ "privateMessage",
+ "topicFirstPost",
+ "topic.pm_with_non_human_user"
+ )
minimumPostLength(privateMessage, topicFirstPost, pmWithNonHumanUser) {
if (pmWithNonHumanUser) {
return 1;
@@ -473,13 +481,13 @@ const Composer = RestModel.extend({
}
},
- @computed("title")
+ @discourseComputed("title")
titleLength(title) {
title = title || "";
return title.replace(/\s+/gim, " ").trim().length;
},
- @computed("reply")
+ @discourseComputed("reply")
replyLength(reply) {
reply = reply || "";
diff --git a/app/assets/javascripts/discourse/models/group-history.js.es6 b/app/assets/javascripts/discourse/models/group-history.js.es6
index 946741ae5d..8c22e9af5f 100644
--- a/app/assets/javascripts/discourse/models/group-history.js.es6
+++ b/app/assets/javascripts/discourse/models/group-history.js.es6
@@ -1,8 +1,8 @@
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
import RestModel from "discourse/models/rest";
export default RestModel.extend({
- @computed("action")
+ @discourseComputed("action")
actionTitle(action) {
return I18n.t(`group_histories.actions.${action}`);
}
diff --git a/app/assets/javascripts/discourse/models/group.js.es6 b/app/assets/javascripts/discourse/models/group.js.es6
index b25746471e..f8bed56d59 100644
--- a/app/assets/javascripts/discourse/models/group.js.es6
+++ b/app/assets/javascripts/discourse/models/group.js.es6
@@ -2,9 +2,9 @@ import { isEmpty } from "@ember/utils";
import { notEmpty, equal } from "@ember/object/computed";
import { ajax } from "discourse/lib/ajax";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import GroupHistory from "discourse/models/group-history";
import RestModel from "discourse/models/rest";
import Category from "discourse/models/category";
@@ -26,17 +26,17 @@ const Group = RestModel.extend({
hasOwners: notEmpty("owners"),
- @computed("automatic_membership_email_domains")
+ @discourseComputed("automatic_membership_email_domains")
emailDomains(value) {
return isEmpty(value) ? "" : value;
},
- @computed("automatic")
+ @discourseComputed("automatic")
type(automatic) {
return automatic ? "automatic" : "custom";
},
- @computed("user_count")
+ @discourseComputed("user_count")
userCountDisplay(userCount) {
// don't display zero its ugly
if (userCount > 0) {
@@ -119,19 +119,19 @@ const Group = RestModel.extend({
return this.findMembers({ filter: response.usernames.join(",") });
},
- @computed("display_name", "name")
+ @discourseComputed("display_name", "name")
displayName(groupDisplayName, name) {
return groupDisplayName || name;
},
- @computed("flair_bg_color")
+ @discourseComputed("flair_bg_color")
flairBackgroundHexColor(flairBgColor) {
return flairBgColor
? flairBgColor.replace(new RegExp("[^0-9a-fA-F]", "g"), "")
: null;
},
- @computed("flair_color")
+ @discourseComputed("flair_color")
flairHexColor(flairColor) {
return flairColor
? flairColor.replace(new RegExp("[^0-9a-fA-F]", "g"), "")
@@ -140,7 +140,7 @@ const Group = RestModel.extend({
canEveryoneMention: equal("mentionable_level", 99),
- @computed("visibility_level")
+ @discourseComputed("visibility_level")
isPrivate(visibilityLevel) {
return visibilityLevel > 1;
},
diff --git a/app/assets/javascripts/discourse/models/login-method.js.es6 b/app/assets/javascripts/discourse/models/login-method.js.es6
index 0bfddf3951..12a4969768 100644
--- a/app/assets/javascripts/discourse/models/login-method.js.es6
+++ b/app/assets/javascripts/discourse/models/login-method.js.es6
@@ -1,20 +1,20 @@
+import discourseComputed from "discourse-common/utils/decorators";
import EmberObject from "@ember/object";
-import computed from "ember-addons/ember-computed-decorators";
import { updateCsrfToken } from "discourse/lib/ajax";
import { Promise } from "rsvp";
const LoginMethod = EmberObject.extend({
- @computed
+ @discourseComputed
title() {
return this.title_override || I18n.t(`login.${this.name}.title`);
},
- @computed
+ @discourseComputed
prettyName() {
return this.pretty_name_override || I18n.t(`login.${this.name}.name`);
},
- @computed
+ @discourseComputed
message() {
return this.message_override || I18n.t(`login.${this.name}.message`);
},
diff --git a/app/assets/javascripts/discourse/models/nav-item.js.es6 b/app/assets/javascripts/discourse/models/nav-item.js.es6
index 5b36d3b4e4..0eff005189 100644
--- a/app/assets/javascripts/discourse/models/nav-item.js.es6
+++ b/app/assets/javascripts/discourse/models/nav-item.js.es6
@@ -1,9 +1,9 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { toTitleCase } from "discourse/lib/formatter";
import { emojiUnescape } from "discourse/lib/text";
-import computed from "ember-addons/ember-computed-decorators";
const NavItem = Discourse.Model.extend({
- @computed("categoryName", "name")
+ @discourseComputed("categoryName", "name")
title(categoryName, name) {
const extra = {};
@@ -15,7 +15,7 @@ const NavItem = Discourse.Model.extend({
return I18n.t("filters." + name.replace("/", ".") + ".help", extra);
},
- @computed("categoryName", "name", "count")
+ @discourseComputed("categoryName", "name", "count")
displayName(categoryName, name, count) {
count = count || 0;
@@ -39,13 +39,13 @@ const NavItem = Discourse.Model.extend({
);
},
- @computed("name")
+ @discourseComputed("name")
categoryName(name) {
const split = name.split("/");
return split[0] === "category" ? split[1] : null;
},
- @computed("name")
+ @discourseComputed("name")
categorySlug(name) {
const split = name.split("/");
if (split[0] === "category" && split[1]) {
@@ -58,7 +58,7 @@ const NavItem = Discourse.Model.extend({
return null;
},
- @computed("filterMode")
+ @discourseComputed("filterMode")
href(filterMode) {
let customHref = null;
@@ -76,7 +76,7 @@ const NavItem = Discourse.Model.extend({
return Discourse.getURL("/") + filterMode;
},
- @computed("name", "category", "categorySlug", "noSubcategories")
+ @discourseComputed("name", "category", "categorySlug", "noSubcategories")
filterMode(name, category, categorySlug, noSubcategories) {
if (name.split("/")[0] === "category") {
return "c/" + categorySlug;
@@ -94,7 +94,7 @@ const NavItem = Discourse.Model.extend({
}
},
- @computed("name", "category", "topicTrackingState.messageCount")
+ @discourseComputed("name", "category", "topicTrackingState.messageCount")
count(name, category) {
const state = this.topicTrackingState;
if (state) {
@@ -104,7 +104,7 @@ const NavItem = Discourse.Model.extend({
});
const ExtraNavItem = NavItem.extend({
- href: computed("href", {
+ href: discourseComputed("href", {
get() {
if (this._href) {
return this._href;
diff --git a/app/assets/javascripts/discourse/models/permission-type.js.es6 b/app/assets/javascripts/discourse/models/permission-type.js.es6
index 858be5722f..94a9af0401 100644
--- a/app/assets/javascripts/discourse/models/permission-type.js.es6
+++ b/app/assets/javascripts/discourse/models/permission-type.js.es6
@@ -1,7 +1,7 @@
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
const PermissionType = Discourse.Model.extend({
- @computed("id")
+ @discourseComputed("id")
description(id) {
var key = "";
diff --git a/app/assets/javascripts/discourse/models/post-stream.js.es6 b/app/assets/javascripts/discourse/models/post-stream.js.es6
index 6baafb909b..1abd6aaa65 100644
--- a/app/assets/javascripts/discourse/models/post-stream.js.es6
+++ b/app/assets/javascripts/discourse/models/post-stream.js.es6
@@ -5,7 +5,7 @@ import { ajax } from "discourse/lib/ajax";
import DiscourseURL from "discourse/lib/url";
import RestModel from "discourse/models/rest";
import PostsWithPlaceholders from "discourse/lib/posts-with-placeholders";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import { loadTopicView } from "discourse/models/topic";
import { Promise } from "rsvp";
@@ -50,17 +50,21 @@ export default RestModel.extend({
loading: or("loadingAbove", "loadingBelow", "loadingFilter", "stagingPost"),
notLoading: not("loading"),
- @computed("isMegaTopic", "stream.length", "topic.highest_post_number")
+ @discourseComputed(
+ "isMegaTopic",
+ "stream.length",
+ "topic.highest_post_number"
+ )
filteredPostsCount(isMegaTopic, streamLength, topicHighestPostNumber) {
return isMegaTopic ? topicHighestPostNumber : streamLength;
},
- @computed("posts.[]")
+ @discourseComputed("posts.[]")
hasPosts() {
return this.get("posts.length") > 0;
},
- @computed("hasPosts", "filteredPostsCount")
+ @discourseComputed("hasPosts", "filteredPostsCount")
hasLoadedData(hasPosts, filteredPostsCount) {
return hasPosts && filteredPostsCount > 0;
},
@@ -68,7 +72,7 @@ export default RestModel.extend({
canAppendMore: and("notLoading", "hasPosts", "lastPostNotLoaded"),
canPrependMore: and("notLoading", "hasPosts", "firstPostNotLoaded"),
- @computed("hasLoadedData", "firstPostId", "posts.[]")
+ @discourseComputed("hasLoadedData", "firstPostId", "posts.[]")
firstPostPresent(hasLoadedData, firstPostId) {
if (!hasLoadedData) {
return false;
@@ -81,17 +85,17 @@ export default RestModel.extend({
firstId: null,
lastId: null,
- @computed("isMegaTopic", "stream.firstObject", "firstId")
+ @discourseComputed("isMegaTopic", "stream.firstObject", "firstId")
firstPostId(isMegaTopic, streamFirstId, firstId) {
return isMegaTopic ? firstId : streamFirstId;
},
- @computed("isMegaTopic", "stream.lastObject", "lastId")
+ @discourseComputed("isMegaTopic", "stream.lastObject", "lastId")
lastPostId(isMegaTopic, streamLastId, lastId) {
return isMegaTopic ? lastId : streamLastId;
},
- @computed("hasLoadedData", "lastPostId", "posts.@each.id")
+ @discourseComputed("hasLoadedData", "lastPostId", "posts.@each.id")
loadedAllPosts(hasLoadedData, lastPostId) {
if (!hasLoadedData) {
return false;
@@ -109,7 +113,7 @@ export default RestModel.extend({
Returns a JS Object of current stream filter options. It should match the query
params for the stream.
**/
- @computed("summary", "userFilters.[]")
+ @discourseComputed("summary", "userFilters.[]")
streamFilters(summary) {
const result = {};
if (summary) {
@@ -124,7 +128,7 @@ export default RestModel.extend({
return result;
},
- @computed("streamFilters.[]", "topic.posts_count", "posts.length")
+ @discourseComputed("streamFilters.[]", "topic.posts_count", "posts.length")
hasNoFilters() {
const streamFilters = this.streamFilters;
return !(
@@ -137,7 +141,7 @@ export default RestModel.extend({
Returns the window of posts above the current set in the stream, bound to the top of the stream.
This is the collection we'll ask for when scrolling upwards.
**/
- @computed("posts.[]", "stream.[]")
+ @discourseComputed("posts.[]", "stream.[]")
previousWindow() {
// If we can't find the last post loaded, bail
const firstPost = _.first(this.posts);
@@ -163,7 +167,7 @@ export default RestModel.extend({
Returns the window of posts below the current set in the stream, bound by the bottom of the
stream. This is the collection we use when scrolling downwards.
**/
- @computed("posts.lastObject", "stream.[]")
+ @discourseComputed("posts.lastObject", "stream.[]")
nextWindow(lastLoadedPost) {
// If we can't find the last post loaded, bail
if (!lastLoadedPost) {
diff --git a/app/assets/javascripts/discourse/models/post.js.es6 b/app/assets/javascripts/discourse/models/post.js.es6
index 4fbfcdeea0..83a18d9a12 100644
--- a/app/assets/javascripts/discourse/models/post.js.es6
+++ b/app/assets/javascripts/discourse/models/post.js.es6
@@ -1,3 +1,4 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { get } from "@ember/object";
import { isEmpty } from "@ember/utils";
import { equal, and, or, not } from "@ember/object/computed";
@@ -8,7 +9,6 @@ import { popupAjaxError } from "discourse/lib/ajax-error";
import ActionSummary from "discourse/models/action-summary";
import { propertyEqual } from "discourse/lib/computed";
import Quote from "discourse/lib/quote";
-import computed from "ember-addons/ember-computed-decorators";
import { postUrl } from "discourse/lib/utilities";
import { cookAsync } from "discourse/lib/text";
import { userPath } from "discourse/lib/url";
@@ -28,7 +28,7 @@ const Post = RestModel.extend({
}
}),
- @computed("url")
+ @discourseComputed("url")
shareUrl(url) {
const user = Discourse.User.current();
const userSuffix = user ? `?u=${user.username_lower}` : "";
@@ -48,24 +48,24 @@ const Post = RestModel.extend({
deleted: or("deleted_at", "deletedViaTopic"),
notDeleted: not("deleted"),
- @computed("name", "username")
+ @discourseComputed("name", "username")
showName(name, username) {
return (
name && name !== username && Discourse.SiteSettings.display_name_on_posts
);
},
- @computed("firstPost", "deleted_by", "topic.deleted_by")
+ @discourseComputed("firstPost", "deleted_by", "topic.deleted_by")
postDeletedBy(firstPost, deletedBy, topicDeletedBy) {
return firstPost ? topicDeletedBy : deletedBy;
},
- @computed("firstPost", "deleted_at", "topic.deleted_at")
+ @discourseComputed("firstPost", "deleted_at", "topic.deleted_at")
postDeletedAt(firstPost, deletedAt, topicDeletedAt) {
return firstPost ? topicDeletedAt : deletedAt;
},
- @computed("post_number", "topic_id", "topic.slug")
+ @discourseComputed("post_number", "topic_id", "topic.slug")
url(post_number, topic_id, topicSlug) {
return postUrl(
topicSlug || this.topic_slug,
@@ -75,12 +75,12 @@ const Post = RestModel.extend({
},
// Don't drop the /1
- @computed("post_number", "url")
+ @discourseComputed("post_number", "url")
urlWithNumber(postNumber, baseUrl) {
return postNumber === 1 ? `${baseUrl}/1` : baseUrl;
},
- @computed("username")
+ @discourseComputed("username")
usernameUrl: userPath,
topicOwner: propertyEqual("topic.details.created_by.id", "user_id"),
@@ -94,14 +94,14 @@ const Post = RestModel.extend({
.catch(popupAjaxError);
},
- @computed("link_counts.@each.internal")
+ @discourseComputed("link_counts.@each.internal")
internalLinks() {
if (isEmpty(this.link_counts)) return null;
return this.link_counts.filterBy("internal").filterBy("title");
},
- @computed("actions_summary.@each.can_act")
+ @discourseComputed("actions_summary.@each.can_act")
flagsAvailable() {
// TODO: Investigate why `this.site` is sometimes null when running
// Search - Search with context
diff --git a/app/assets/javascripts/discourse/models/result-set.js.es6 b/app/assets/javascripts/discourse/models/result-set.js.es6
index 436abfd2de..56e2c164b5 100644
--- a/app/assets/javascripts/discourse/models/result-set.js.es6
+++ b/app/assets/javascripts/discourse/models/result-set.js.es6
@@ -1,4 +1,4 @@
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
import { Promise } from "rsvp";
export default Ember.ArrayProxy.extend({
@@ -15,7 +15,7 @@ export default Ember.ArrayProxy.extend({
__type: null,
resultSetMeta: null,
- @computed("totalRows", "length")
+ @discourseComputed("totalRows", "length")
canLoadMore(totalRows, length) {
return length < totalRows;
},
diff --git a/app/assets/javascripts/discourse/models/reviewable.js.es6 b/app/assets/javascripts/discourse/models/reviewable.js.es6
index 892822c59e..fd6ad39603 100644
--- a/app/assets/javascripts/discourse/models/reviewable.js.es6
+++ b/app/assets/javascripts/discourse/models/reviewable.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { ajax } from "discourse/lib/ajax";
import RestModel from "discourse/models/rest";
-import computed from "ember-addons/ember-computed-decorators";
import Category from "discourse/models/category";
import { Promise } from "rsvp";
@@ -11,7 +11,7 @@ export const IGNORED = 3;
export const DELETED = 4;
export default RestModel.extend({
- @computed("type", "topic")
+ @discourseComputed("type", "topic")
humanType(type, topic) {
// Display "Queued Topic" if the post will create a topic
if (type === "ReviewableQueuedPost" && !topic) {
diff --git a/app/assets/javascripts/discourse/models/site.js.es6 b/app/assets/javascripts/discourse/models/site.js.es6
index bb76b07a0e..81d4acca56 100644
--- a/app/assets/javascripts/discourse/models/site.js.es6
+++ b/app/assets/javascripts/discourse/models/site.js.es6
@@ -1,8 +1,8 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { get } from "@ember/object";
import { isEmpty } from "@ember/utils";
import { alias, sort } from "@ember/object/computed";
import EmberObject from "@ember/object";
-import computed from "ember-addons/ember-computed-decorators";
import Archetype from "discourse/models/archetype";
import PostActionType from "discourse/models/post-action-type";
import Singleton from "discourse/mixins/singleton";
@@ -19,7 +19,7 @@ const Site = RestModel.extend({
this.topicCountDesc = ["topic_count:desc"];
},
- @computed("notification_types")
+ @discourseComputed("notification_types")
notificationLookup(notificationTypes) {
const result = [];
Object.keys(notificationTypes).forEach(
@@ -28,7 +28,7 @@ const Site = RestModel.extend({
return result;
},
- @computed("post_action_types.[]")
+ @discourseComputed("post_action_types.[]")
flagTypes() {
const postActionTypes = this.post_action_types;
if (!postActionTypes) return [];
@@ -53,7 +53,7 @@ const Site = RestModel.extend({
},
// Sort subcategories under parents
- @computed("categoriesByCount", "categories.[]")
+ @discourseComputed("categoriesByCount", "categories.[]")
sortedCategories(cats) {
const result = [],
remaining = {};
@@ -80,13 +80,13 @@ const Site = RestModel.extend({
return result;
},
- @computed
+ @discourseComputed
baseUri() {
return Discourse.baseUri;
},
// Returns it in the correct order, by setting
- @computed
+ @discourseComputed
categoriesList() {
return this.siteSettings.fixed_category_positions
? this.categories
diff --git a/app/assets/javascripts/discourse/models/tag-group.js.es6 b/app/assets/javascripts/discourse/models/tag-group.js.es6
index e42ccee9dd..18afc52fe7 100644
--- a/app/assets/javascripts/discourse/models/tag-group.js.es6
+++ b/app/assets/javascripts/discourse/models/tag-group.js.es6
@@ -1,9 +1,9 @@
+import discourseComputed from "discourse-common/utils/decorators";
import RestModel from "discourse/models/rest";
-import computed from "ember-addons/ember-computed-decorators";
import PermissionType from "discourse/models/permission-type";
export default RestModel.extend({
- @computed("permissions")
+ @discourseComputed("permissions")
permissionName(permissions) {
if (!permissions) return "public";
diff --git a/app/assets/javascripts/discourse/models/tag.js.es6 b/app/assets/javascripts/discourse/models/tag.js.es6
index c9665111ac..ebfa93d93d 100644
--- a/app/assets/javascripts/discourse/models/tag.js.es6
+++ b/app/assets/javascripts/discourse/models/tag.js.es6
@@ -1,13 +1,13 @@
+import discourseComputed from "discourse-common/utils/decorators";
import RestModel from "discourse/models/rest";
-import computed from "ember-addons/ember-computed-decorators";
export default RestModel.extend({
- @computed("count", "pm_count")
+ @discourseComputed("count", "pm_count")
totalCount(count, pmCount) {
return count + pmCount;
},
- @computed("count", "pm_count")
+ @discourseComputed("count", "pm_count")
pmOnly(count, pmCount) {
return count === 0 && pmCount > 0;
}
diff --git a/app/assets/javascripts/discourse/models/topic-details.js.es6 b/app/assets/javascripts/discourse/models/topic-details.js.es6
index 0622cacb69..0e0ad21b34 100644
--- a/app/assets/javascripts/discourse/models/topic-details.js.es6
+++ b/app/assets/javascripts/discourse/models/topic-details.js.es6
@@ -1,6 +1,6 @@
+import discourseComputed from "discourse-common/utils/decorators";
import EmberObject from "@ember/object";
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.
@@ -32,7 +32,7 @@ const TopicDetails = RestModel.extend({
this.set("loaded", true);
},
- @computed("notification_level", "notifications_reason_id")
+ @discourseComputed("notification_level", "notifications_reason_id")
notificationReasonText(level, reason) {
if (typeof level !== "number") {
level = 1;
diff --git a/app/assets/javascripts/discourse/models/topic-tracking-state.js.es6 b/app/assets/javascripts/discourse/models/topic-tracking-state.js.es6
index 89eab6119a..de53d7c35a 100644
--- a/app/assets/javascripts/discourse/models/topic-tracking-state.js.es6
+++ b/app/assets/javascripts/discourse/models/topic-tracking-state.js.es6
@@ -2,9 +2,9 @@ import { get } from "@ember/object";
import { isEmpty } from "@ember/utils";
import { NotificationLevels } from "discourse/lib/notification-levels";
import {
- default as computed,
+ default as discourseComputed,
on
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import { defaultHomepage } from "discourse/lib/utilities";
import PreloadStore from "preload-store";
@@ -206,7 +206,7 @@ const TopicTrackingState = Discourse.Model.extend({
this.set("incomingCount", 0);
},
- @computed("incomingCount")
+ @discourseComputed("incomingCount")
hasIncoming(incomingCount) {
return incomingCount && incomingCount > 0;
},
diff --git a/app/assets/javascripts/discourse/models/topic.js.es6 b/app/assets/javascripts/discourse/models/topic.js.es6
index f4bf6c6533..9590ffcda8 100644
--- a/app/assets/javascripts/discourse/models/topic.js.es6
+++ b/app/assets/javascripts/discourse/models/topic.js.es6
@@ -14,10 +14,10 @@ import { emojiUnescape } from "discourse/lib/text";
import PreloadStore from "preload-store";
import { userPath } from "discourse/lib/url";
import {
- default as computed,
+ default as discourseComputed,
observes,
on
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
export function loadTopicView(topic, args) {
const data = _.merge({}, args);
@@ -42,18 +42,18 @@ const Topic = RestModel.extend({
message: null,
errorLoading: false,
- @computed("last_read_post_number", "highest_post_number")
+ @discourseComputed("last_read_post_number", "highest_post_number")
visited(lastReadPostNumber, highestPostNumber) {
// >= to handle case where there are deleted posts at the end of the topic
return lastReadPostNumber >= highestPostNumber;
},
- @computed("posters.firstObject")
+ @discourseComputed("posters.firstObject")
creator(poster) {
return poster && poster.user;
},
- @computed("posters.[]")
+ @discourseComputed("posters.[]")
lastPoster(posters) {
let user;
if (posters && posters.length > 0) {
@@ -65,7 +65,7 @@ const Topic = RestModel.extend({
return user || this.creator;
},
- @computed("posters.[]", "participants.[]")
+ @discourseComputed("posters.[]", "participants.[]")
featuredUsers(posters, participants) {
let users = posters;
const maxUserCount = 5;
@@ -95,7 +95,7 @@ const Topic = RestModel.extend({
return users;
},
- @computed("fancy_title")
+ @discourseComputed("fancy_title")
fancyTitle(title) {
let fancyTitle = censor(
emojiUnescape(title || ""),
@@ -110,7 +110,7 @@ const Topic = RestModel.extend({
},
// returns createdAt if there's no bumped date
- @computed("bumped_at", "createdAt")
+ @discourseComputed("bumped_at", "createdAt")
bumpedAt(bumped_at, createdAt) {
if (bumped_at) {
return new Date(bumped_at);
@@ -119,7 +119,7 @@ const Topic = RestModel.extend({
}
},
- @computed("bumpedAt", "createdAt")
+ @discourseComputed("bumpedAt", "createdAt")
bumpedAtTitle(bumpedAt, createdAt) {
const firstPost = I18n.t("first_post");
const lastPost = I18n.t("last_post");
@@ -129,12 +129,12 @@ const Topic = RestModel.extend({
return `${firstPost}: ${createdAtDate}\n${lastPost}: ${bumpedAtDate}`;
},
- @computed("created_at")
+ @discourseComputed("created_at")
createdAt(created_at) {
return new Date(created_at);
},
- @computed
+ @discourseComputed
postStream() {
return this.store.createRecord("postStream", {
id: this.id,
@@ -142,7 +142,7 @@ const Topic = RestModel.extend({
});
},
- @computed("tags")
+ @discourseComputed("tags")
visibleListTags(tags) {
if (!tags || !Discourse.SiteSettings.suppress_overlapping_tags_in_list) {
return tags;
@@ -160,7 +160,7 @@ const Topic = RestModel.extend({
return newTags;
},
- @computed("related_messages")
+ @discourseComputed("related_messages")
relatedMessages(relatedMessages) {
if (relatedMessages) {
const store = this.store;
@@ -172,7 +172,7 @@ const Topic = RestModel.extend({
}
},
- @computed("suggested_topics")
+ @discourseComputed("suggested_topics")
suggestedTopics(suggestedTopics) {
if (suggestedTopics) {
const store = this.store;
@@ -184,12 +184,12 @@ const Topic = RestModel.extend({
}
},
- @computed("posts_count")
+ @discourseComputed("posts_count")
replyCount(postsCount) {
return postsCount - 1;
},
- @computed
+ @discourseComputed
details() {
return this.store.createRecord("topicDetails", {
id: this.id,
@@ -200,7 +200,7 @@ const Topic = RestModel.extend({
invisible: not("visible"),
deleted: notEmpty("deleted_at"),
- @computed("id")
+ @discourseComputed("id")
searchContext(id) {
return { type: "topic", id };
},
@@ -223,12 +223,12 @@ const Topic = RestModel.extend({
categoryClass: fmt("category.fullSlug", "category-%@"),
- @computed("tags")
+ @discourseComputed("tags")
tagClasses(tags) {
return tags && tags.map(t => `tag-${t}`).join(" ");
},
- @computed("url")
+ @discourseComputed("url")
shareUrl(url) {
const user = Discourse.User.current();
const userQueryString = user ? `?u=${user.get("username_lower")}` : "";
@@ -237,7 +237,7 @@ const Topic = RestModel.extend({
printUrl: fmt("url", "%@/print"),
- @computed("id", "slug")
+ @discourseComputed("id", "slug")
url(id, slug) {
slug = slug || "";
if (slug.trim().length === 0) {
@@ -255,18 +255,18 @@ const Topic = RestModel.extend({
return url;
},
- @computed("new_posts", "unread")
+ @discourseComputed("new_posts", "unread")
totalUnread(newPosts, unread) {
const count = (unread || 0) + (newPosts || 0);
return count > 0 ? count : null;
},
- @computed("last_read_post_number", "url")
+ @discourseComputed("last_read_post_number", "url")
lastReadUrl(lastReadPostNumber) {
return this.urlForPostNumber(lastReadPostNumber);
},
- @computed("last_read_post_number", "highest_post_number", "url")
+ @discourseComputed("last_read_post_number", "highest_post_number", "url")
lastUnreadUrl(lastReadPostNumber, highestPostNumber) {
if (highestPostNumber <= lastReadPostNumber) {
if (this.get("category.navigate_to_first_post_after_read")) {
@@ -279,23 +279,23 @@ const Topic = RestModel.extend({
}
},
- @computed("highest_post_number", "url")
+ @discourseComputed("highest_post_number", "url")
lastPostUrl(highestPostNumber) {
return this.urlForPostNumber(highestPostNumber);
},
- @computed("url")
+ @discourseComputed("url")
firstPostUrl() {
return this.urlForPostNumber(1);
},
- @computed("url")
+ @discourseComputed("url")
summaryUrl() {
const summaryQueryString = this.has_summary ? "?filter=summary" : "";
return `${this.urlForPostNumber(1)}${summaryQueryString}`;
},
- @computed("last_poster.username")
+ @discourseComputed("last_poster.username")
lastPosterUrl(username) {
return userPath(username);
},
@@ -303,7 +303,7 @@ const Topic = RestModel.extend({
// The amount of new posts to display. It might be different than what the server
// tells us if we are still asynchronously flushing our "recently read" data.
// So take what the browser has seen into consideration.
- @computed("new_posts", "id")
+ @discourseComputed("new_posts", "id")
displayNewPosts(newPosts, id) {
const highestSeen = Discourse.Session.currentProp("highestSeenByTopic")[id];
if (highestSeen) {
@@ -319,7 +319,7 @@ const Topic = RestModel.extend({
return newPosts;
},
- @computed("views")
+ @discourseComputed("views")
viewsHeat(v) {
if (v >= Discourse.SiteSettings.topic_views_heat_high) {
return "heatmap-high";
@@ -333,7 +333,7 @@ const Topic = RestModel.extend({
return null;
},
- @computed("archetype")
+ @discourseComputed("archetype")
archetypeObject(archetype) {
return Discourse.Site.currentProp("archetypes").findBy("id", archetype);
},
@@ -532,14 +532,14 @@ const Topic = RestModel.extend({
});
},
- @computed("excerpt")
+ @discourseComputed("excerpt")
escapedExcerpt(excerpt) {
return emojiUnescape(excerpt);
},
hasExcerpt: notEmpty("excerpt"),
- @computed("excerpt")
+ @discourseComputed("excerpt")
excerptTruncated(excerpt) {
return excerpt && excerpt.substr(excerpt.length - 8, 8) === "…";
},
diff --git a/app/assets/javascripts/discourse/models/user-action-stat.js.es6 b/app/assets/javascripts/discourse/models/user-action-stat.js.es6
index fd531cde9a..0791edd34d 100644
--- a/app/assets/javascripts/discourse/models/user-action-stat.js.es6
+++ b/app/assets/javascripts/discourse/models/user-action-stat.js.es6
@@ -1,10 +1,10 @@
+import discourseComputed from "discourse-common/utils/decorators";
import RestModel from "discourse/models/rest";
import UserAction from "discourse/models/user-action";
import { i18n } from "discourse/lib/computed";
-import computed from "ember-addons/ember-computed-decorators";
export default RestModel.extend({
- @computed("action_type")
+ @discourseComputed("action_type")
isPM(actionType) {
return (
actionType === UserAction.TYPES.messages_sent ||
@@ -14,7 +14,7 @@ export default RestModel.extend({
description: i18n("action_type", "user_action_groups.%@"),
- @computed("action_type")
+ @discourseComputed("action_type")
isResponse(actionType) {
return (
actionType === UserAction.TYPES.replies ||
diff --git a/app/assets/javascripts/discourse/models/user-action.js.es6 b/app/assets/javascripts/discourse/models/user-action.js.es6
index 5ca07e7025..183c47e44b 100644
--- a/app/assets/javascripts/discourse/models/user-action.js.es6
+++ b/app/assets/javascripts/discourse/models/user-action.js.es6
@@ -1,7 +1,7 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { or, equal, and } from "@ember/object/computed";
import RestModel from "discourse/models/rest";
-import { on } from "ember-addons/ember-computed-decorators";
-import computed from "ember-addons/ember-computed-decorators";
+import { on } from "discourse-common/utils/decorators";
import UserActionGroup from "discourse/models/user-action-group";
import { postUrl } from "discourse/lib/utilities";
import { userPath } from "discourse/lib/url";
@@ -35,7 +35,7 @@ const UserAction = RestModel.extend({
}
},
- @computed("action_type")
+ @discourseComputed("action_type")
descriptionKey(action) {
if (action === null || UserAction.TO_SHOW.indexOf(action) >= 0) {
if (this.isPM) {
@@ -66,12 +66,12 @@ const UserAction = RestModel.extend({
}
},
- @computed("username")
+ @discourseComputed("username")
sameUser(username) {
return username === Discourse.User.currentProp("username");
},
- @computed("target_username")
+ @discourseComputed("target_username")
targetUser(targetUsername) {
return targetUsername === Discourse.User.currentProp("username");
},
@@ -80,27 +80,27 @@ const UserAction = RestModel.extend({
targetDisplayName: or("target_name", "target_username"),
actingDisplayName: or("acting_name", "acting_username"),
- @computed("target_username")
+ @discourseComputed("target_username")
targetUserUrl(username) {
return userPath(username);
},
- @computed("username")
+ @discourseComputed("username")
usernameLower(username) {
return username.toLowerCase();
},
- @computed("usernameLower")
+ @discourseComputed("usernameLower")
userUrl(usernameLower) {
return userPath(usernameLower);
},
- @computed()
+ @discourseComputed()
postUrl() {
return postUrl(this.slug, this.topic_id, this.post_number);
},
- @computed()
+ @discourseComputed()
replyUrl() {
return postUrl(this.slug, this.topic_id, this.reply_to_post_number);
},
@@ -145,7 +145,7 @@ const UserAction = RestModel.extend({
}
},
- @computed(
+ @discourseComputed(
"childGroups",
"childGroups.likes.items",
"childGroups.likes.items.[]",
diff --git a/app/assets/javascripts/discourse/models/user-badge.js.es6 b/app/assets/javascripts/discourse/models/user-badge.js.es6
index 511ed71de2..3e00072f6e 100644
--- a/app/assets/javascripts/discourse/models/user-badge.js.es6
+++ b/app/assets/javascripts/discourse/models/user-badge.js.es6
@@ -1,11 +1,11 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { ajax } from "discourse/lib/ajax";
import Badge from "discourse/models/badge";
-import computed from "ember-addons/ember-computed-decorators";
import { Promise } from "rsvp";
import Topic from "discourse/models/topic";
const UserBadge = Discourse.Model.extend({
- @computed
+ @discourseComputed
postUrl: function() {
if (this.topic_title) {
return "/t/-/" + this.topic_id + "/" + this.post_number;
diff --git a/app/assets/javascripts/discourse/models/user-draft.js.es6 b/app/assets/javascripts/discourse/models/user-draft.js.es6
index 2ab353e92c..6e31ae3b2f 100644
--- a/app/assets/javascripts/discourse/models/user-draft.js.es6
+++ b/app/assets/javascripts/discourse/models/user-draft.js.es6
@@ -1,33 +1,32 @@
+import discourseComputed from "discourse-common/utils/decorators";
import RestModel from "discourse/models/rest";
-import computed from "ember-addons/ember-computed-decorators";
import { postUrl } from "discourse/lib/utilities";
import { userPath } from "discourse/lib/url";
import User from "discourse/models/user";
-
import {
NEW_TOPIC_KEY,
NEW_PRIVATE_MESSAGE_KEY
} from "discourse/models/composer";
export default RestModel.extend({
- @computed("draft_username")
+ @discourseComputed("draft_username")
editableDraft(draftUsername) {
return draftUsername === User.currentProp("username");
},
- @computed("username_lower")
+ @discourseComputed("username_lower")
userUrl(usernameLower) {
return userPath(usernameLower);
},
- @computed("topic_id")
+ @discourseComputed("topic_id")
postUrl(topicId) {
if (!topicId) return;
return postUrl(this.slug, this.topic_id, this.post_number);
},
- @computed("draft_key")
+ @discourseComputed("draft_key")
draftType(draftKey) {
switch (draftKey) {
case NEW_TOPIC_KEY:
diff --git a/app/assets/javascripts/discourse/models/user-drafts-stream.js.es6 b/app/assets/javascripts/discourse/models/user-drafts-stream.js.es6
index ee1d3cccad..7472cc8e67 100644
--- a/app/assets/javascripts/discourse/models/user-drafts-stream.js.es6
+++ b/app/assets/javascripts/discourse/models/user-drafts-stream.js.es6
@@ -1,9 +1,9 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { ajax } from "discourse/lib/ajax";
import { url } from "discourse/lib/computed";
import RestModel from "discourse/models/rest";
import UserDraft from "discourse/models/user-draft";
import { emojiUnescape } from "discourse/lib/text";
-import computed from "ember-addons/ember-computed-decorators";
import { Promise } from "rsvp";
import {
NEW_TOPIC_KEY,
@@ -38,7 +38,7 @@ export default RestModel.extend({
return this.findItems();
},
- @computed("content.length", "loaded")
+ @discourseComputed("content.length", "loaded")
noContent(contentLength, loaded) {
return loaded && contentLength === 0;
},
diff --git a/app/assets/javascripts/discourse/models/user-posts-stream.js.es6 b/app/assets/javascripts/discourse/models/user-posts-stream.js.es6
index 74cadcb455..6213d98d14 100644
--- a/app/assets/javascripts/discourse/models/user-posts-stream.js.es6
+++ b/app/assets/javascripts/discourse/models/user-posts-stream.js.es6
@@ -1,4 +1,4 @@
-import { on } from "ember-addons/ember-computed-decorators";
+import { on } from "discourse-common/utils/decorators";
import { ajax } from "discourse/lib/ajax";
import { url } from "discourse/lib/computed";
import UserAction from "discourse/models/user-action";
diff --git a/app/assets/javascripts/discourse/models/user-stream.js.es6 b/app/assets/javascripts/discourse/models/user-stream.js.es6
index 1a90ebd940..d411b58cee 100644
--- a/app/assets/javascripts/discourse/models/user-stream.js.es6
+++ b/app/assets/javascripts/discourse/models/user-stream.js.es6
@@ -5,9 +5,9 @@ import UserAction from "discourse/models/user-action";
import { emojiUnescape } from "discourse/lib/text";
import { Promise } from "rsvp";
import {
- default as computed,
+ default as discourseComputed,
on
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
export default RestModel.extend({
loaded: false,
@@ -17,7 +17,7 @@ export default RestModel.extend({
this.setProperties({ itemsLoaded: 0, content: [] });
},
- @computed("filter")
+ @discourseComputed("filter")
filterParam(filter) {
if (filter === Discourse.UserAction.TYPES.replies) {
return [UserAction.TYPES.replies, UserAction.TYPES.quotes].join(",");
@@ -51,7 +51,7 @@ export default RestModel.extend({
return this.findItems();
},
- @computed("loaded", "content.[]")
+ @discourseComputed("loaded", "content.[]")
noContent(loaded, content) {
return loaded && content.length === 0;
},
diff --git a/app/assets/javascripts/discourse/models/user.js.es6 b/app/assets/javascripts/discourse/models/user.js.es6
index af2a0dd2fc..8b7289d5ce 100644
--- a/app/assets/javascripts/discourse/models/user.js.es6
+++ b/app/assets/javascripts/discourse/models/user.js.es6
@@ -9,9 +9,9 @@ import UserPostsStream from "discourse/models/user-posts-stream";
import Singleton from "discourse/mixins/singleton";
import { longDate } from "discourse/lib/formatter";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import Badge from "discourse/models/badge";
import UserBadge from "discourse/models/user-badge";
import UserActionStat from "discourse/models/user-action-stat";
@@ -43,22 +43,22 @@ const User = RestModel.extend({
reason: null
},
- @computed("can_be_deleted", "post_count")
+ @discourseComputed("can_be_deleted", "post_count")
canBeDeleted(canBeDeleted, postCount) {
return canBeDeleted && postCount <= 5;
},
- @computed()
+ @discourseComputed()
stream() {
return UserStream.create({ user: this });
},
- @computed()
+ @discourseComputed()
postsStream() {
return UserPostsStream.create({ user: this });
},
- @computed()
+ @discourseComputed()
userDraftsStream() {
return UserDraftsStream.create({ user: this });
},
@@ -78,7 +78,7 @@ const User = RestModel.extend({
return ajax(`/session/${this.username}`, { type: "DELETE" });
},
- @computed("username_lower")
+ @discourseComputed("username_lower")
searchContext(username) {
return {
type: "user",
@@ -87,7 +87,7 @@ const User = RestModel.extend({
};
},
- @computed("username", "name")
+ @discourseComputed("username", "name")
displayName(username, name) {
if (Discourse.SiteSettings.enable_names && !isEmpty(name)) {
return name;
@@ -95,7 +95,7 @@ const User = RestModel.extend({
return username;
},
- @computed("profile_background_upload_url")
+ @discourseComputed("profile_background_upload_url")
profileBackgroundUrl(bgUrl) {
if (isEmpty(bgUrl) || !Discourse.SiteSettings.allow_profile_backgrounds) {
return "".htmlSafe();
@@ -107,13 +107,13 @@ const User = RestModel.extend({
).htmlSafe();
},
- @computed()
+ @discourseComputed()
path() {
// no need to observe, requires a hard refresh to update
return userPath(this.username_lower);
},
- @computed()
+ @discourseComputed()
userApiKeys() {
const keys = this.user_api_keys;
if (keys) {
@@ -171,33 +171,33 @@ const User = RestModel.extend({
adminPath: url("id", "username_lower", "/admin/users/%@1/%@2"),
- @computed()
+ @discourseComputed()
mutedTopicsPath() {
return defaultHomepage() === "latest"
? Discourse.getURL("/?state=muted")
: Discourse.getURL("/latest?state=muted");
},
- @computed()
+ @discourseComputed()
watchingTopicsPath() {
return defaultHomepage() === "latest"
? Discourse.getURL("/?state=watching")
: Discourse.getURL("/latest?state=watching");
},
- @computed()
+ @discourseComputed()
trackingTopicsPath() {
return defaultHomepage() === "latest"
? Discourse.getURL("/?state=tracking")
: Discourse.getURL("/latest?state=tracking");
},
- @computed("username")
+ @discourseComputed("username")
username_lower(username) {
return username.toLowerCase();
},
- @computed("trust_level")
+ @discourseComputed("trust_level")
trustLevel(trustLevel) {
return Discourse.Site.currentProp("trustLevels").findBy(
"id",
@@ -210,26 +210,26 @@ const User = RestModel.extend({
isElder: equal("trust_level", 4),
canManageTopic: or("staff", "isElder"),
- @computed("previous_visit_at")
+ @discourseComputed("previous_visit_at")
previousVisitAt(previous_visit_at) {
return new Date(previous_visit_at);
},
- @computed("suspended_till")
+ @discourseComputed("suspended_till")
suspended(suspendedTill) {
return suspendedTill && moment(suspendedTill).isAfter();
},
- @computed("suspended_till")
+ @discourseComputed("suspended_till")
suspendedForever: isForever,
- @computed("silenced_till")
+ @discourseComputed("silenced_till")
silencedForever: isForever,
- @computed("suspended_till")
+ @discourseComputed("suspended_till")
suspendedTillDate: longDate,
- @computed("silenced_till")
+ @discourseComputed("silenced_till")
silencedTillDate: longDate,
changeUsername(new_username) {
@@ -492,7 +492,7 @@ const User = RestModel.extend({
numGroupsToDisplay: 2,
- @computed("groups.[]")
+ @discourseComputed("groups.[]")
filteredGroups() {
const groups = this.groups || [];
@@ -501,19 +501,19 @@ const User = RestModel.extend({
});
},
- @computed("filteredGroups", "numGroupsToDisplay")
+ @discourseComputed("filteredGroups", "numGroupsToDisplay")
displayGroups(filteredGroups, numGroupsToDisplay) {
const groups = filteredGroups.slice(0, numGroupsToDisplay);
return groups.length === 0 ? null : groups;
},
- @computed("filteredGroups", "numGroupsToDisplay")
+ @discourseComputed("filteredGroups", "numGroupsToDisplay")
showMoreGroupsLink(filteredGroups, numGroupsToDisplay) {
return filteredGroups.length > numGroupsToDisplay;
},
// The user's stat count, excluding PMs.
- @computed("statsExcludingPms.@each.count")
+ @discourseComputed("statsExcludingPms.@each.count")
statsCountNonPM() {
if (isEmpty(this.statsExcludingPms)) return 0;
let count = 0;
@@ -526,7 +526,7 @@ const User = RestModel.extend({
},
// The user's stats, excluding PMs.
- @computed("stats.@each.isPM")
+ @discourseComputed("stats.@each.isPM")
statsExcludingPms() {
if (isEmpty(this.stats)) return [];
return this.stats.rejectBy("isPM");
@@ -661,7 +661,7 @@ const User = RestModel.extend({
);
},
- @computed("can_delete_account")
+ @discourseComputed("can_delete_account")
canDeleteAccount(canDeleteAccount) {
return !Discourse.SiteSettings.enable_sso && canDeleteAccount;
},
@@ -768,7 +768,7 @@ const User = RestModel.extend({
: this.admin || group.get("is_group_owner");
},
- @computed("groups.@each.title", "badges.[]")
+ @discourseComputed("groups.@each.title", "badges.[]")
availableTitles() {
let titles = [];
@@ -794,7 +794,7 @@ const User = RestModel.extend({
});
},
- @computed("user_option.text_size_seq", "user_option.text_size")
+ @discourseComputed("user_option.text_size_seq", "user_option.text_size")
currentTextSize(serverSeq, serverSize) {
if ($.cookie("text_size")) {
const [cookieSize, cookieSeq] = $.cookie("text_size").split("|");
@@ -817,7 +817,7 @@ const User = RestModel.extend({
}
},
- @computed("second_factor_enabled", "staff")
+ @discourseComputed("second_factor_enabled", "staff")
enforcedSecondFactor(secondFactorEnabled, staff) {
const enforce = Discourse.SiteSettings.enforce_second_factor;
return (
diff --git a/app/assets/javascripts/discourse/raw-views/list/post-count-or-badges.js.es6 b/app/assets/javascripts/discourse/raw-views/list/post-count-or-badges.js.es6
index d7c5f0aa06..20b15a3ebd 100644
--- a/app/assets/javascripts/discourse/raw-views/list/post-count-or-badges.js.es6
+++ b/app/assets/javascripts/discourse/raw-views/list/post-count-or-badges.js.es6
@@ -1,12 +1,12 @@
import { or, and } from "@ember/object/computed";
import EmberObject from "@ember/object";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
export default EmberObject.extend({
postCountsPresent: or("topic.unread", "topic.displayNewPosts"),
showBadges: and("postBadgesEnabled", "postCountsPresent"),
- @computed
+ @discourseComputed
newDotText() {
return this.currentUser && this.currentUser.trust_level > 0
? ""
diff --git a/app/assets/javascripts/discourse/raw-views/list/posts-count-column.js.es6 b/app/assets/javascripts/discourse/raw-views/list/posts-count-column.js.es6
index 2c7ca4c9b9..12a27f3a22 100644
--- a/app/assets/javascripts/discourse/raw-views/list/posts-count-column.js.es6
+++ b/app/assets/javascripts/discourse/raw-views/list/posts-count-column.js.es6
@@ -1,11 +1,11 @@
+import discourseComputed from "discourse-common/utils/decorators";
import EmberObject from "@ember/object";
-import computed from "ember-addons/ember-computed-decorators";
import { fmt } from "discourse/lib/computed";
export default EmberObject.extend({
tagName: "td",
- @computed("topic.like_count", "topic.posts_count")
+ @discourseComputed("topic.like_count", "topic.posts_count")
ratio(likeCount, postCount) {
const likes = parseFloat(likeCount);
const posts = parseFloat(postCount);
@@ -17,12 +17,12 @@ export default EmberObject.extend({
return (likes || 0) / posts;
},
- @computed("topic.replyCount", "ratioText")
+ @discourseComputed("topic.replyCount", "ratioText")
title(count, ratio) {
return I18n.messageFormat("posts_likes_MF", { count, ratio }).trim();
},
- @computed("ratio")
+ @discourseComputed("ratio")
ratioText(ratio) {
const settings = this.siteSettings;
if (ratio > settings.topic_post_like_heat_high) {
diff --git a/app/assets/javascripts/discourse/raw-views/list/visited-line.js.es6 b/app/assets/javascripts/discourse/raw-views/list/visited-line.js.es6
index b2aac57550..2428c81012 100644
--- a/app/assets/javascripts/discourse/raw-views/list/visited-line.js.es6
+++ b/app/assets/javascripts/discourse/raw-views/list/visited-line.js.es6
@@ -1,8 +1,8 @@
+import discourseComputed from "discourse-common/utils/decorators";
import EmberObject from "@ember/object";
-import computed from "ember-addons/ember-computed-decorators";
export default EmberObject.extend({
- @computed
+ @discourseComputed
isLastVisited: function() {
return this.lastVisitedTopic === this.topic;
}
diff --git a/app/assets/javascripts/discourse/raw-views/topic-list-header-column.js.es6 b/app/assets/javascripts/discourse/raw-views/topic-list-header-column.js.es6
index 0ac85216b7..e5b44af68e 100644
--- a/app/assets/javascripts/discourse/raw-views/topic-list-header-column.js.es6
+++ b/app/assets/javascripts/discourse/raw-views/topic-list-header-column.js.es6
@@ -1,8 +1,8 @@
import EmberObject from "@ember/object";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
export default EmberObject.extend({
- @computed
+ @discourseComputed
localizedName() {
if (this.forceName) {
return this.forceName;
@@ -11,18 +11,18 @@ export default EmberObject.extend({
return this.name ? I18n.t(this.name) : "";
},
- @computed
+ @discourseComputed
sortIcon() {
const asc = this.parent.ascending ? "up" : "down";
return `chevron-${asc}`;
},
- @computed
+ @discourseComputed
isSorting() {
return this.sortable && this.parent.order === this.order;
},
- @computed
+ @discourseComputed
className() {
const name = [];
diff --git a/app/assets/javascripts/discourse/raw-views/topic-status.js.es6 b/app/assets/javascripts/discourse/raw-views/topic-status.js.es6
index 8e7269bbca..d6b2c74999 100644
--- a/app/assets/javascripts/discourse/raw-views/topic-status.js.es6
+++ b/app/assets/javascripts/discourse/raw-views/topic-status.js.es6
@@ -1,15 +1,15 @@
+import discourseComputed from "discourse-common/utils/decorators";
import EmberObject from "@ember/object";
-import computed from "ember-addons/ember-computed-decorators";
export default EmberObject.extend({
showDefault: null,
- @computed("defaultIcon")
+ @discourseComputed("defaultIcon")
renderDiv(defaultIcon) {
return (defaultIcon || this.statuses.length > 0) && !this.noDiv;
},
- @computed
+ @discourseComputed
statuses() {
const topic = this.topic;
const results = [];
diff --git a/app/assets/javascripts/discourse/services/logs-notice.js.es6 b/app/assets/javascripts/discourse/services/logs-notice.js.es6
index 73961054a1..9d124edf0b 100644
--- a/app/assets/javascripts/discourse/services/logs-notice.js.es6
+++ b/app/assets/javascripts/discourse/services/logs-notice.js.es6
@@ -1,10 +1,10 @@
import { isEmpty } from "@ember/utils";
import EmberObject from "@ember/object";
import {
- default as computed,
+ default as discourseComputed,
on,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import { autoUpdatingRelativeAge } from "discourse/lib/formatter";
const LOGS_NOTICE_KEY = "logs-notice-text";
@@ -47,22 +47,22 @@ const LogsNotice = EmberObject.extend({
});
},
- @computed("text")
+ @discourseComputed("text")
isEmpty(text) {
return isEmpty(text);
},
- @computed("text")
+ @discourseComputed("text")
message(text) {
return new Handlebars.SafeString(text);
},
- @computed("currentUser")
+ @discourseComputed("currentUser")
isAdmin(currentUser) {
return currentUser && currentUser.admin;
},
- @computed("isEmpty", "isAdmin")
+ @discourseComputed("isEmpty", "isAdmin")
hidden(thisIsEmpty, isAdmin) {
return !isAdmin || thisIsEmpty;
},
@@ -72,7 +72,7 @@ const LogsNotice = EmberObject.extend({
this.keyValueStore.setItem(LOGS_NOTICE_KEY, this.text);
},
- @computed(
+ @discourseComputed(
"siteSettings.alert_admins_if_errors_per_hour",
"siteSettings.alert_admins_if_errors_per_minute"
)
diff --git a/app/assets/javascripts/discourse/services/search.js.es6 b/app/assets/javascripts/discourse/services/search.js.es6
index 641e35e482..c9e51f43c8 100644
--- a/app/assets/javascripts/discourse/services/search.js.es6
+++ b/app/assets/javascripts/discourse/services/search.js.es6
@@ -1,9 +1,9 @@
import { get } from "@ember/object";
import EmberObject from "@ember/object";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
export default EmberObject.extend({
searchContextEnabled: false, // checkbox to scope search
@@ -16,7 +16,7 @@ export default EmberObject.extend({
this.set("highlightTerm", this.term);
},
- @computed("searchContext")
+ @discourseComputed("searchContext")
contextType: {
get(searchContext) {
if (searchContext) {
diff --git a/app/assets/javascripts/discourse/templates/components/reviewable-score.js.es6 b/app/assets/javascripts/discourse/templates/components/reviewable-score.js.es6
index 291db6c238..ee36959c61 100644
--- a/app/assets/javascripts/discourse/templates/components/reviewable-score.js.es6
+++ b/app/assets/javascripts/discourse/templates/components/reviewable-score.js.es6
@@ -1,13 +1,13 @@
+import discourseComputed from "discourse-common/utils/decorators";
import { gt } from "@ember/object/computed";
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
export default Component.extend({
tagName: "",
showStatus: gt("rs.status", 0),
- @computed("rs.score_type.title", "reviewable.target_created_by")
+ @discourseComputed("rs.score_type.title", "reviewable.target_created_by")
title(title, targetCreatedBy) {
if (title && targetCreatedBy) {
return title.replace("{{username}}", targetCreatedBy.username);
diff --git a/app/assets/javascripts/ember-addons/decorator-alias.js.es6 b/app/assets/javascripts/ember-addons/decorator-alias.js.es6
index 44d911a1dd..327dc7a2cb 100644
--- a/app/assets/javascripts/ember-addons/decorator-alias.js.es6
+++ b/app/assets/javascripts/ember-addons/decorator-alias.js.es6
@@ -2,7 +2,7 @@ import extractValue from "./utils/extract-value";
export default function decoratorAlias(fn, errorMessage) {
return function(...params) {
- // determine if user called as @computed('blah', 'blah') or @computed
+ // determine if user called as @discourseComputed('blah', 'blah') or @discourseComputed
if (params.length === 0) {
throw new Error(errorMessage);
} else {
diff --git a/app/assets/javascripts/pretty-text/engines/discourse-markdown/onebox.js.es6 b/app/assets/javascripts/pretty-text/engines/discourse-markdown/onebox.js.es6
index 3203110c94..7358bdaa06 100644
--- a/app/assets/javascripts/pretty-text/engines/discourse-markdown/onebox.js.es6
+++ b/app/assets/javascripts/pretty-text/engines/discourse-markdown/onebox.js.es6
@@ -1,6 +1,5 @@
import { lookupCache } from "pretty-text/oneboxer-cache";
import { cachedInlineOnebox } from "pretty-text/inline-oneboxer";
-
import {
INLINE_ONEBOX_LOADING_CSS_CLASS,
INLINE_ONEBOX_CSS_CLASS
diff --git a/app/assets/javascripts/select-kit/components/admin-group-selector.js.es6 b/app/assets/javascripts/select-kit/components/admin-group-selector.js.es6
index ddc883ee07..2d99404c0a 100644
--- a/app/assets/javascripts/select-kit/components/admin-group-selector.js.es6
+++ b/app/assets/javascripts/select-kit/components/admin-group-selector.js.es6
@@ -1,5 +1,6 @@
import MultiSelectComponent from "select-kit/components/multi-select";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
+
const { makeArray } = Ember;
export default MultiSelectComponent.extend({
@@ -10,7 +11,7 @@ export default MultiSelectComponent.extend({
allowAny: false,
buffer: null,
- @computed("buffer")
+ @discourseComputed("buffer")
values(buffer) {
return buffer === null
? makeArray(this.selected).map(s => this.valueForContentItem(s))
diff --git a/app/assets/javascripts/select-kit/components/category-chooser.js.es6 b/app/assets/javascripts/select-kit/components/category-chooser.js.es6
index a1d453aa2a..8a91e9868e 100644
--- a/app/assets/javascripts/select-kit/components/category-chooser.js.es6
+++ b/app/assets/javascripts/select-kit/components/category-chooser.js.es6
@@ -1,5 +1,5 @@
import ComboBoxComponent from "select-kit/components/combo-box";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
import PermissionType from "discourse/models/permission-type";
import Category from "discourse/models/category";
import { categoryBadgeHTML } from "discourse/helpers/category-link";
@@ -53,7 +53,7 @@ export default ComboBoxComponent.extend({
});
},
- @computed("rootNone", "rootNoneLabel")
+ @discourseComputed("rootNone", "rootNoneLabel")
none(rootNone, rootNoneLabel) {
if (
this.siteSettings.allow_uncategorized_topics ||
diff --git a/app/assets/javascripts/select-kit/components/category-drop.js.es6 b/app/assets/javascripts/select-kit/components/category-drop.js.es6
index 425c2bb038..25f72b2655 100644
--- a/app/assets/javascripts/select-kit/components/category-drop.js.es6
+++ b/app/assets/javascripts/select-kit/components/category-drop.js.es6
@@ -1,6 +1,6 @@
import ComboBoxComponent from "select-kit/components/combo-box";
import DiscourseURL from "discourse/lib/url";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import Category from "discourse/models/category";
import { categoryBadgeHTML } from "discourse/helpers/category-link";
const { isEmpty } = Ember;
@@ -23,7 +23,12 @@ export default ComboBoxComponent.extend({
subCategory: false,
isAsync: Ember.computed.not("subCategory"),
- @computed("categories", "hasSelection", "subCategory", "noSubcategories")
+ @discourseComputed(
+ "categories",
+ "hasSelection",
+ "subCategory",
+ "noSubcategories"
+ )
categoriesWithShortcuts(
categories,
hasSelection,
@@ -70,7 +75,7 @@ export default ComboBoxComponent.extend({
this.forceValue(this.get("category.id"));
},
- @computed("content")
+ @discourseComputed("content")
filterable(content) {
const contentLength = (content && content.length) || 0;
return (
@@ -107,7 +112,7 @@ export default ComboBoxComponent.extend({
return content;
},
- @computed("parentCategory.name", "subCategory")
+ @discourseComputed("parentCategory.name", "subCategory")
allCategoriesLabel(categoryName, subCategory) {
if (subCategory) {
return I18n.t("categories.all_subcategories", { categoryName });
@@ -115,12 +120,12 @@ export default ComboBoxComponent.extend({
return I18n.t("categories.all");
},
- @computed("parentCategory.url", "subCategory")
+ @discourseComputed("parentCategory.url", "subCategory")
allCategoriesUrl(parentCategoryUrl, subCategory) {
return Discourse.getURL(subCategory ? parentCategoryUrl || "/" : "/");
},
- @computed("parentCategory.url")
+ @discourseComputed("parentCategory.url")
noCategoriesUrl(parentCategoryUrl) {
return Discourse.getURL(`${parentCategoryUrl}/none`);
},
diff --git a/app/assets/javascripts/select-kit/components/category-drop/category-drop-header.js.es6 b/app/assets/javascripts/select-kit/components/category-drop/category-drop-header.js.es6
index c04fc30840..ad86019a19 100644
--- a/app/assets/javascripts/select-kit/components/category-drop/category-drop-header.js.es6
+++ b/app/assets/javascripts/select-kit/components/category-drop/category-drop-header.js.es6
@@ -1,6 +1,6 @@
import { isEmpty } from "@ember/utils";
import ComboBoxSelectBoxHeaderComponent from "select-kit/components/combo-box/combo-box-header";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
import Category from "discourse/models/category";
export default ComboBoxSelectBoxHeaderComponent.extend({
@@ -11,7 +11,7 @@ export default ComboBoxSelectBoxHeaderComponent.extend({
classNameBindings: ["categoryStyleClass"],
categoryStyleClass: Ember.computed.alias("site.category_style"),
- @computed("computedContent.value", "computedContent.name")
+ @discourseComputed("computedContent.value", "computedContent.name")
category(value, name) {
if (isEmpty(value)) {
const uncat = Category.findUncategorized();
@@ -23,17 +23,17 @@ export default ComboBoxSelectBoxHeaderComponent.extend({
}
},
- @computed("category.color")
+ @discourseComputed("category.color")
categoryBackgroundColor(categoryColor) {
return categoryColor || "#e9e9e9";
},
- @computed("category.text_color")
+ @discourseComputed("category.text_color")
categoryTextColor(categoryTextColor) {
return categoryTextColor || "#333";
},
- @computed("category", "categoryBackgroundColor", "categoryTextColor")
+ @discourseComputed("category", "categoryBackgroundColor", "categoryTextColor")
categoryStyle(category, categoryBackgroundColor, categoryTextColor) {
const categoryStyle = this.siteSettings.category_style;
diff --git a/app/assets/javascripts/select-kit/components/category-row.js.es6 b/app/assets/javascripts/select-kit/components/category-row.js.es6
index 8523bfb07e..d2a548164e 100644
--- a/app/assets/javascripts/select-kit/components/category-row.js.es6
+++ b/app/assets/javascripts/select-kit/components/category-row.js.es6
@@ -1,6 +1,6 @@
import { isEmpty } from "@ember/utils";
import SelectKitRowComponent from "select-kit/components/select-kit/select-kit-row";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
import Category from "discourse/models/category";
import { categoryBadgeHTML } from "discourse/helpers/category-link";
@@ -12,7 +12,7 @@ export default SelectKitRowComponent.extend({
allowUncategorized: Ember.computed.bool("options.allowUncategorized"),
categoryLink: Ember.computed.bool("options.categoryLink"),
- @computed("options.displayCategoryDescription")
+ @discourseComputed("options.displayCategoryDescription")
displayCategoryDescription(displayCategoryDescription) {
if (Ember.isNone(displayCategoryDescription)) {
return true;
@@ -21,12 +21,12 @@ export default SelectKitRowComponent.extend({
return displayCategoryDescription;
},
- @computed("descriptionText", "description", "category.name")
+ @discourseComputed("descriptionText", "description", "category.name")
title(descriptionText, description, name) {
return descriptionText || description || name;
},
- @computed("computedContent.value", "computedContent.name")
+ @discourseComputed("computedContent.value", "computedContent.name")
category(value, name) {
if (isEmpty(value)) {
const uncat = Category.findUncategorized();
@@ -38,7 +38,7 @@ export default SelectKitRowComponent.extend({
}
},
- @computed("category", "parentCategory")
+ @discourseComputed("category", "parentCategory")
badgeForCategory(category, parentCategory) {
return categoryBadgeHTML(category, {
link: this.categoryLink,
@@ -47,7 +47,7 @@ export default SelectKitRowComponent.extend({
}).htmlSafe();
},
- @computed("parentCategory")
+ @discourseComputed("parentCategory")
badgeForParentCategory(parentCategory) {
return categoryBadgeHTML(parentCategory, {
link: this.categoryLink,
@@ -55,22 +55,22 @@ export default SelectKitRowComponent.extend({
}).htmlSafe();
},
- @computed("parentCategoryid")
+ @discourseComputed("parentCategoryid")
parentCategory(parentCategoryId) {
return Category.findById(parentCategoryId);
},
- @computed("parentCategoryid")
+ @discourseComputed("parentCategoryid")
hasParentCategory(parentCategoryid) {
return !Ember.isNone(parentCategoryid);
},
- @computed("category")
+ @discourseComputed("category")
parentCategoryid(category) {
return category.get("parent_category_id");
},
- @computed(
+ @discourseComputed(
"category.totalTopicCount",
"category.topic_count",
"options.countSubcategories"
@@ -79,19 +79,19 @@ export default SelectKitRowComponent.extend({
return countSubcats ? totalCount : topicCount;
},
- @computed("displayCategoryDescription", "category.description")
+ @discourseComputed("displayCategoryDescription", "category.description")
shouldDisplayDescription(displayCategoryDescription, description) {
return displayCategoryDescription && description && description !== "null";
},
- @computed("category.description_text")
+ @discourseComputed("category.description_text")
descriptionText(descriptionText) {
if (descriptionText) {
return this._formatCategoryDescription(descriptionText);
}
},
- @computed("category.description")
+ @discourseComputed("category.description")
description(description) {
if (description) {
return this._formatCategoryDescription(description);
diff --git a/app/assets/javascripts/select-kit/components/color-palettes/color-palettes-row.js.es6 b/app/assets/javascripts/select-kit/components/color-palettes/color-palettes-row.js.es6
index e0ae6b7039..7aa53eb596 100644
--- a/app/assets/javascripts/select-kit/components/color-palettes/color-palettes-row.js.es6
+++ b/app/assets/javascripts/select-kit/components/color-palettes/color-palettes-row.js.es6
@@ -1,13 +1,13 @@
import { escapeExpression } from "discourse/lib/utilities";
import SelectKitRowComponent from "select-kit/components/select-kit/select-kit-row";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
export default SelectKitRowComponent.extend({
layoutName:
"select-kit/templates/components/color-palettes/color-palettes-row",
classNames: "color-palettes-row",
- @computed("computedContent.originalContent.colors")
+ @discourseComputed("computedContent.originalContent.colors")
colors(colors) {
return (colors || []).map(color => `#${escapeExpression(color.hex)}`);
}
diff --git a/app/assets/javascripts/select-kit/components/combo-box.js.es6 b/app/assets/javascripts/select-kit/components/combo-box.js.es6
index 09e8a7c7bd..71928d314f 100644
--- a/app/assets/javascripts/select-kit/components/combo-box.js.es6
+++ b/app/assets/javascripts/select-kit/components/combo-box.js.es6
@@ -1,8 +1,8 @@
import SingleSelectComponent from "select-kit/components/single-select";
import {
on,
- default as computed
-} from "ember-addons/ember-computed-decorators";
+ default as discourseComputed
+} from "discourse-common/utils/decorators";
export default SingleSelectComponent.extend({
pluginApiIdentifiers: ["combo-box"],
@@ -20,7 +20,7 @@ export default SingleSelectComponent.extend({
return content;
},
- @computed("isExpanded", "caretUpIcon", "caretDownIcon")
+ @discourseComputed("isExpanded", "caretUpIcon", "caretDownIcon")
caretIcon(isExpanded, caretUpIcon, caretDownIcon) {
return isExpanded ? caretUpIcon : caretDownIcon;
},
diff --git a/app/assets/javascripts/select-kit/components/composer-actions.js.es6 b/app/assets/javascripts/select-kit/components/composer-actions.js.es6
index 98b1d06410..e36b27f15e 100644
--- a/app/assets/javascripts/select-kit/components/composer-actions.js.es6
+++ b/app/assets/javascripts/select-kit/components/composer-actions.js.es6
@@ -1,5 +1,5 @@
import DropdownSelectBoxComponent from "select-kit/components/dropdown-select-box";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
import {
PRIVATE_MESSAGE,
CREATE_TOPIC,
@@ -76,7 +76,7 @@ export default DropdownSelectBoxComponent.extend({
return content;
},
- @computed("options", "canWhisper", "action")
+ @discourseComputed("options", "canWhisper", "action")
content(options, canWhisper, action) {
let items = [];
diff --git a/app/assets/javascripts/select-kit/components/dropdown-select-box.js.es6 b/app/assets/javascripts/select-kit/components/dropdown-select-box.js.es6
index 1bbf6d510e..77c1927e96 100644
--- a/app/assets/javascripts/select-kit/components/dropdown-select-box.js.es6
+++ b/app/assets/javascripts/select-kit/components/dropdown-select-box.js.es6
@@ -1,5 +1,5 @@
import SingleSelectComponent from "select-kit/components/single-select";
-import { on } from "ember-addons/ember-computed-decorators";
+import { on } from "discourse-common/utils/decorators";
export default SingleSelectComponent.extend({
pluginApiIdentifiers: ["dropdown-select-box"],
diff --git a/app/assets/javascripts/select-kit/components/dropdown-select-box/dropdown-select-box-header.js.es6 b/app/assets/javascripts/select-kit/components/dropdown-select-box/dropdown-select-box-header.js.es6
index 1acccd3067..d83156c018 100644
--- a/app/assets/javascripts/select-kit/components/dropdown-select-box/dropdown-select-box-header.js.es6
+++ b/app/assets/javascripts/select-kit/components/dropdown-select-box/dropdown-select-box-header.js.es6
@@ -1,5 +1,5 @@
import SelectKitHeaderComponent from "select-kit/components/select-kit/select-kit-header";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
export default SelectKitHeaderComponent.extend({
layoutName:
@@ -9,7 +9,7 @@ export default SelectKitHeaderComponent.extend({
classNameBindings: ["btnClassName"],
- @computed("options.showFullTitle")
+ @discourseComputed("options.showFullTitle")
btnClassName(showFullTitle) {
return `btn ${showFullTitle ? "btn-icon-text" : "no-text btn-icon"}`;
}
diff --git a/app/assets/javascripts/select-kit/components/group-dropdown.js.es6 b/app/assets/javascripts/select-kit/components/group-dropdown.js.es6
index 882bf46cb9..a53988a953 100644
--- a/app/assets/javascripts/select-kit/components/group-dropdown.js.es6
+++ b/app/assets/javascripts/select-kit/components/group-dropdown.js.es6
@@ -1,6 +1,6 @@
import ComboBoxComponent from "select-kit/components/combo-box";
import DiscourseURL from "discourse/lib/url";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
export default ComboBoxComponent.extend({
pluginApiIdentifiers: ["group-dropdown"],
@@ -12,7 +12,7 @@ export default ComboBoxComponent.extend({
allowAutoSelectFirst: false,
valueAttribute: "name",
- @computed("content")
+ @discourseComputed("content")
filterable(content) {
return content && content.length >= 10;
},
@@ -27,7 +27,7 @@ export default ComboBoxComponent.extend({
return content;
},
- @computed
+ @discourseComputed
collectionHeader() {
if (
this.siteSettings.enable_group_directory ||
diff --git a/app/assets/javascripts/select-kit/components/mini-tag-chooser.js.es6 b/app/assets/javascripts/select-kit/components/mini-tag-chooser.js.es6
index c32e15e19a..5a2fe7a73e 100644
--- a/app/assets/javascripts/select-kit/components/mini-tag-chooser.js.es6
+++ b/app/assets/javascripts/select-kit/components/mini-tag-chooser.js.es6
@@ -1,7 +1,7 @@
import Category from "discourse/models/category";
import ComboBox from "select-kit/components/combo-box";
import TagsMixin from "select-kit/mixins/tags";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
import renderTag from "discourse/lib/render-tag";
import { escapeExpression } from "discourse/lib/utilities";
import { makeArray } from "discourse-common/lib/helpers";
@@ -55,7 +55,7 @@ export default ComboBox.extend(TagsMixin, {
);
},
- @computed(
+ @discourseComputed(
"computedValue",
"filter",
"collectionComputedContent.[]",
@@ -98,12 +98,12 @@ export default ComboBox.extend(TagsMixin, {
);
},
- @computed("hasReachedMaximum")
+ @discourseComputed("hasReachedMaximum")
caretIcon(hasReachedMaximum) {
return hasReachedMaximum ? null : "plus";
},
- @computed("tags")
+ @discourseComputed("tags")
selection(tags) {
return makeArray(tags).map(c => this.computeContentItem(c));
},
@@ -139,7 +139,7 @@ export default ComboBox.extend(TagsMixin, {
return true;
},
- @computed("tags.[]", "filter", "highlightedSelection.[]")
+ @discourseComputed("tags.[]", "filter", "highlightedSelection.[]")
collectionHeader(tags, filter, highlightedSelection) {
if (!isEmpty(tags)) {
let output = "";
diff --git a/app/assets/javascripts/select-kit/components/multi-select.js.es6 b/app/assets/javascripts/select-kit/components/multi-select.js.es6
index 2bb2bbb610..40a5dc7f0b 100644
--- a/app/assets/javascripts/select-kit/components/multi-select.js.es6
+++ b/app/assets/javascripts/select-kit/components/multi-select.js.es6
@@ -1,6 +1,8 @@
import SelectKitComponent from "select-kit/components/select-kit";
-import computed from "ember-addons/ember-computed-decorators";
-import { on } from "ember-addons/ember-computed-decorators";
+import {
+ default as discourseComputed,
+ on
+} from "discourse-common/utils/decorators";
const { get, isNone, isEmpty, makeArray, run } = Ember;
import {
applyOnSelectPluginApiCallbacks,
@@ -67,7 +69,7 @@ export default SelectKitComponent.extend({
});
},
- @computed("filter", "shouldDisplayCreateRow")
+ @discourseComputed("filter", "shouldDisplayCreateRow")
createRowComputedContent(filter, shouldDisplayCreateRow) {
if (shouldDisplayCreateRow) {
let content = this.createContentFromInput(filter);
@@ -75,12 +77,12 @@ export default SelectKitComponent.extend({
}
},
- @computed("filter", "computedValues")
+ @discourseComputed("filter", "computedValues")
shouldDisplayCreateRow(filter, computedValues) {
return this._super() && !computedValues.includes(filter);
},
- @computed
+ @discourseComputed
shouldDisplayFilter() {
return true;
},
@@ -126,7 +128,7 @@ export default SelectKitComponent.extend({
});
},
- @computed("computedAsyncContent.[]", "computedValues.[]")
+ @discourseComputed("computedAsyncContent.[]", "computedValues.[]")
filteredAsyncComputedContent(computedAsyncContent, computedValues) {
computedAsyncContent = computedAsyncContent.filter(c => {
return !computedValues.includes(get(c, "value"));
@@ -139,7 +141,7 @@ export default SelectKitComponent.extend({
return computedAsyncContent;
},
- @computed("computedContent.[]", "computedValues.[]", "filter")
+ @discourseComputed("computedContent.[]", "computedValues.[]", "filter")
filteredComputedContent(computedContent, computedValues, filter) {
computedContent = computedContent.filter(c => {
return !computedValues.includes(get(c, "value"));
@@ -182,7 +184,7 @@ export default SelectKitComponent.extend({
return content;
},
- @computed("filter")
+ @discourseComputed("filter")
templateForCreateRow() {
return rowComponent => {
return I18n.t("select_kit.create", {
@@ -195,7 +197,7 @@ export default SelectKitComponent.extend({
return this._super() && !this.hasReachedMaximum;
},
- @computed("computedValues.[]", "computedContent.[]")
+ @discourseComputed("computedValues.[]", "computedContent.[]")
selection(computedValues, computedContent) {
const selected = [];
@@ -207,7 +209,7 @@ export default SelectKitComponent.extend({
return selected;
},
- @computed("selection.[]")
+ @discourseComputed("selection.[]")
hasSelection(selection) {
return !isEmpty(selection);
},
diff --git a/app/assets/javascripts/select-kit/components/multi-select/multi-select-filter.js.es6 b/app/assets/javascripts/select-kit/components/multi-select/multi-select-filter.js.es6
index e9b9233448..3732ccd914 100644
--- a/app/assets/javascripts/select-kit/components/multi-select/multi-select-filter.js.es6
+++ b/app/assets/javascripts/select-kit/components/multi-select/multi-select-filter.js.es6
@@ -1,4 +1,4 @@
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
const { isEmpty } = Ember;
import SelectKitFilterComponent from "select-kit/components/select-kit/select-kit-filter";
@@ -6,8 +6,8 @@ export default SelectKitFilterComponent.extend({
layoutName: "select-kit/templates/components/select-kit/select-kit-filter",
classNames: ["multi-select-filter"],
- @computed("placeholder", "hasSelection")
- computedPlaceholder(placeholder, hasSelection) {
+ @discourseComputed("placeholder", "hasSelection")
+ discourseComputedPlaceholder(placeholder, hasSelection) {
if (hasSelection) return "";
return isEmpty(placeholder) ? "" : I18n.t(placeholder);
}
diff --git a/app/assets/javascripts/select-kit/components/multi-select/multi-select-header.js.es6 b/app/assets/javascripts/select-kit/components/multi-select/multi-select-header.js.es6
index b16ed0c290..67c3ac3f9e 100644
--- a/app/assets/javascripts/select-kit/components/multi-select/multi-select-header.js.es6
+++ b/app/assets/javascripts/select-kit/components/multi-select/multi-select-header.js.es6
@@ -1,6 +1,6 @@
import { makeArray } from "discourse-common/lib/helpers";
-import { on } from "ember-addons/ember-computed-decorators";
-import computed from "ember-addons/ember-computed-decorators";
+import { on } from "discourse-common/utils/decorators";
+import discourseComputed from "discourse-common/utils/decorators";
import SelectKitHeaderComponent from "select-kit/components/select-kit/select-kit-header";
export default SelectKitHeaderComponent.extend({
@@ -38,14 +38,14 @@ export default SelectKitHeaderComponent.extend({
$filter.width(availableSpace - parentRightPadding * 4);
},
- @computed("computedContent.selection.[]")
+ @discourseComputed("computedContent.selection.[]")
names(selection) {
return makeArray(selection)
.map(s => s.name)
.join(",");
},
- @computed("computedContent.selection.[]")
+ @discourseComputed("computedContent.selection.[]")
values(selection) {
return makeArray(selection)
.map(s => s.value)
diff --git a/app/assets/javascripts/select-kit/components/multi-select/selected-category.js.es6 b/app/assets/javascripts/select-kit/components/multi-select/selected-category.js.es6
index a24ed6eae3..155506095b 100644
--- a/app/assets/javascripts/select-kit/components/multi-select/selected-category.js.es6
+++ b/app/assets/javascripts/select-kit/components/multi-select/selected-category.js.es6
@@ -1,12 +1,12 @@
import SelectedNameComponent from "select-kit/components/multi-select/selected-name";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
import { categoryBadgeHTML } from "discourse/helpers/category-link";
export default SelectedNameComponent.extend({
classNames: "selected-category",
layoutName: "select-kit/templates/components/multi-select/selected-category",
- @computed("computedContent.originalContent")
+ @discourseComputed("computedContent.originalContent")
badge(category) {
return categoryBadgeHTML(category, {
allowUncategorized: true,
diff --git a/app/assets/javascripts/select-kit/components/multi-select/selected-color.js.es6 b/app/assets/javascripts/select-kit/components/multi-select/selected-color.js.es6
index f75e7a708f..3574550c20 100644
--- a/app/assets/javascripts/select-kit/components/multi-select/selected-color.js.es6
+++ b/app/assets/javascripts/select-kit/components/multi-select/selected-color.js.es6
@@ -1,10 +1,10 @@
import SelectedNameComponent from "select-kit/components/multi-select/selected-name";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
export default SelectedNameComponent.extend({
classNames: "selected-color",
- @computed("name")
+ @discourseComputed("name")
footerContent(name) {
return ``.htmlSafe();
}
diff --git a/app/assets/javascripts/select-kit/components/multi-select/selected-name.js.es6 b/app/assets/javascripts/select-kit/components/multi-select/selected-name.js.es6
index 0c542410fb..6de8c9d0a8 100644
--- a/app/assets/javascripts/select-kit/components/multi-select/selected-name.js.es6
+++ b/app/assets/javascripts/select-kit/components/multi-select/selected-name.js.es6
@@ -1,5 +1,5 @@
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
export default Component.extend({
attributeBindings: [
@@ -16,14 +16,14 @@ export default Component.extend({
tagName: "span",
tabindex: -1,
- @computed("computedContent")
+ @discourseComputed("computedContent")
guid(computedContent) {
return Ember.guidFor(computedContent);
},
ariaLabel: Ember.computed.or("computedContent.ariaLabel", "title"),
- @computed("computedContent.title", "name")
+ @discourseComputed("computedContent.title", "name")
title(computedContentTitle, name) {
if (computedContentTitle) return computedContentTitle;
if (name) return name;
@@ -41,7 +41,7 @@ export default Component.extend({
return this.getWithDefault("computedContent.locked", false);
}),
- @computed("computedContent", "highlightedSelection.[]")
+ @discourseComputed("computedContent", "highlightedSelection.[]")
isHighlighted(computedContent, highlightedSelection) {
return highlightedSelection.includes(this.computedContent);
},
diff --git a/app/assets/javascripts/select-kit/components/none-category-row.js.es6 b/app/assets/javascripts/select-kit/components/none-category-row.js.es6
index 8488a93a4a..7d2aa1ef26 100644
--- a/app/assets/javascripts/select-kit/components/none-category-row.js.es6
+++ b/app/assets/javascripts/select-kit/components/none-category-row.js.es6
@@ -1,12 +1,12 @@
import CategoryRowComponent from "select-kit/components/category-row";
import { categoryBadgeHTML } from "discourse/helpers/category-link";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
export default CategoryRowComponent.extend({
layoutName: "select-kit/templates/components/category-row",
classNames: "none category-row",
- @computed("category")
+ @discourseComputed("category")
badgeForCategory(category) {
return categoryBadgeHTML(category, {
link: this.categoryLink,
diff --git a/app/assets/javascripts/select-kit/components/notifications-button.js.es6 b/app/assets/javascripts/select-kit/components/notifications-button.js.es6
index fcfe0c5c8c..5c5bec067b 100644
--- a/app/assets/javascripts/select-kit/components/notifications-button.js.es6
+++ b/app/assets/javascripts/select-kit/components/notifications-button.js.es6
@@ -1,9 +1,9 @@
import DropdownSelectBoxComponent from "select-kit/components/dropdown-select-box";
import {
- default as computed,
+ default as discourseComputed,
observes,
on
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import { buttonDetails } from "discourse/lib/notification-levels";
import { allLevels } from "discourse/lib/notification-levels";
@@ -20,7 +20,7 @@ export default DropdownSelectBoxComponent.extend({
i18nPrefix: "",
i18nPostfix: "",
- @computed("iconForSelectedDetails")
+ @discourseComputed("iconForSelectedDetails")
headerIcon(iconForSelectedDetails) {
return iconForSelectedDetails;
},
@@ -47,7 +47,7 @@ export default DropdownSelectBoxComponent.extend({
return content;
},
- @computed("computedValue")
+ @discourseComputed("computedValue")
selectedDetails(computedValue) {
return buttonDetails(computedValue);
}
diff --git a/app/assets/javascripts/select-kit/components/notifications-button/notifications-button-row.js.es6 b/app/assets/javascripts/select-kit/components/notifications-button/notifications-button-row.js.es6
index d41133b9b6..e4a3b45bd5 100644
--- a/app/assets/javascripts/select-kit/components/notifications-button/notifications-button-row.js.es6
+++ b/app/assets/javascripts/select-kit/components/notifications-button/notifications-button-row.js.es6
@@ -1,6 +1,6 @@
import DropdownSelectBoxRoxComponent from "select-kit/components/dropdown-select-box/dropdown-select-box-row";
import { buttonDetails } from "discourse/lib/notification-levels";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
import { iconHTML } from "discourse-common/lib/icon-library";
export default DropdownSelectBoxRoxComponent.extend({
@@ -9,18 +9,21 @@ export default DropdownSelectBoxRoxComponent.extend({
i18nPrefix: Ember.computed.alias("options.i18nPrefix"),
i18nPostfix: Ember.computed.alias("options.i18nPostfix"),
- @computed("computedContent.value", "i18nPrefix", "i18nPostfix")
+ @discourseComputed("computedContent.value", "i18nPrefix", "i18nPostfix")
title(value, prefix, postfix) {
const key = buttonDetails(value).key;
return I18n.t(`${prefix}.${key}${postfix}.title`);
},
- @computed("computedContent.name", "computedContent.originalContent.icon")
+ @discourseComputed(
+ "computedContent.name",
+ "computedContent.originalContent.icon"
+ )
icon(contentName, icon) {
return iconHTML(icon, { class: contentName.dasherize() });
},
- @computed("_start")
+ @discourseComputed("_start")
description(_start) {
if (this.site && this.site.mobileView) {
return null;
@@ -29,12 +32,12 @@ export default DropdownSelectBoxRoxComponent.extend({
return Handlebars.escapeExpression(I18n.t(`${_start}.description`));
},
- @computed("_start")
+ @discourseComputed("_start")
name(_start) {
return Handlebars.escapeExpression(I18n.t(`${_start}.title`));
},
- @computed("i18nPrefix", "i18nPostfix", "computedContent.name")
+ @discourseComputed("i18nPrefix", "i18nPostfix", "computedContent.name")
_start(prefix, postfix, contentName) {
return `${prefix}.${contentName}${postfix}`;
}
diff --git a/app/assets/javascripts/select-kit/components/period-chooser.js.es6 b/app/assets/javascripts/select-kit/components/period-chooser.js.es6
index 56a2079988..bc9befb89a 100644
--- a/app/assets/javascripts/select-kit/components/period-chooser.js.es6
+++ b/app/assets/javascripts/select-kit/components/period-chooser.js.es6
@@ -1,5 +1,5 @@
import DropdownSelectBoxComponent from "select-kit/components/dropdown-select-box";
-import computed, { on } from "ember-addons/ember-computed-decorators";
+import discourseComputed, { on } from "discourse-common/utils/decorators";
export default DropdownSelectBoxComponent.extend({
classNames: ["period-chooser"],
@@ -9,7 +9,7 @@ export default DropdownSelectBoxComponent.extend({
value: Ember.computed.alias("period"),
isHidden: Ember.computed.alias("showPeriods"),
- @computed("isExpanded")
+ @discourseComputed("isExpanded")
caretIcon(isExpanded) {
return isExpanded ? "caret-up" : "caret-down";
},
diff --git a/app/assets/javascripts/select-kit/components/period-chooser/period-chooser-row.js.es6 b/app/assets/javascripts/select-kit/components/period-chooser/period-chooser-row.js.es6
index 18a0b529fa..4cb25af58e 100644
--- a/app/assets/javascripts/select-kit/components/period-chooser/period-chooser-row.js.es6
+++ b/app/assets/javascripts/select-kit/components/period-chooser/period-chooser-row.js.es6
@@ -1,12 +1,12 @@
import DropdownSelectBoxRowComponent from "select-kit/components/dropdown-select-box/dropdown-select-box-row";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
export default DropdownSelectBoxRowComponent.extend({
layoutName:
"select-kit/templates/components/period-chooser/period-chooser-row",
classNames: "period-chooser-row",
- @computed("computedContent")
+ @discourseComputed("computedContent")
title(computedContent) {
return I18n.t(`filters.top.${computedContent.name || "this_week"}`).title;
}
diff --git a/app/assets/javascripts/select-kit/components/pinned-button.js.es6 b/app/assets/javascripts/select-kit/components/pinned-button.js.es6
index 9002d913b3..8332f0f41a 100644
--- a/app/assets/javascripts/select-kit/components/pinned-button.js.es6
+++ b/app/assets/javascripts/select-kit/components/pinned-button.js.es6
@@ -1,5 +1,5 @@
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
export default Component.extend({
pluginApiIdentifiers: ["pinned-button"],
@@ -8,7 +8,7 @@ export default Component.extend({
classNameBindings: ["isHidden"],
layoutName: "select-kit/templates/components/pinned-button",
- @computed("topic.pinned_globally", "pinned")
+ @discourseComputed("topic.pinned_globally", "pinned")
reasonText(pinnedGlobally, pinned) {
const globally = pinnedGlobally ? "_globally" : "";
const pinnedKey = pinned ? `pinned${globally}` : "unpinned";
@@ -16,7 +16,7 @@ export default Component.extend({
return I18n.t(key);
},
- @computed("pinned", "topic.deleted", "topic.unpinned")
+ @discourseComputed("pinned", "topic.deleted", "topic.unpinned")
isHidden(pinned, deleted, unpinned) {
return deleted || (!pinned && !unpinned);
}
diff --git a/app/assets/javascripts/select-kit/components/pinned-options.js.es6 b/app/assets/javascripts/select-kit/components/pinned-options.js.es6
index a560bff74d..c96856a804 100644
--- a/app/assets/javascripts/select-kit/components/pinned-options.js.es6
+++ b/app/assets/javascripts/select-kit/components/pinned-options.js.es6
@@ -1,5 +1,5 @@
import DropdownSelectBoxComponent from "select-kit/components/dropdown-select-box";
-import { on } from "ember-addons/ember-computed-decorators";
+import { on } from "discourse-common/utils/decorators";
import { iconHTML } from "discourse-common/lib/icon-library";
export default DropdownSelectBoxComponent.extend({
diff --git a/app/assets/javascripts/select-kit/components/select-kit.js.es6 b/app/assets/javascripts/select-kit/components/select-kit.js.es6
index 9179e66680..6c2199a5b7 100644
--- a/app/assets/javascripts/select-kit/components/select-kit.js.es6
+++ b/app/assets/javascripts/select-kit/components/select-kit.js.es6
@@ -1,7 +1,8 @@
+import discourseComputed from "discourse-common/utils/decorators";
import EmberObject from "@ember/object";
import Component from "@ember/component";
const { get, isNone, run, isEmpty, makeArray } = Ember;
-import computed from "ember-addons/ember-computed-decorators";
+
import UtilsMixin from "select-kit/mixins/utils";
import DomHelpersMixin from "select-kit/mixins/dom-helpers";
import EventsMixin from "select-kit/mixins/events";
@@ -223,7 +224,7 @@ export default Component.extend(
return this.computeContentItem(contentItem, options);
},
- @computed(
+ @discourseComputed(
"isAsync",
"isLoading",
"filteredAsyncComputedContent.[]",
@@ -250,28 +251,28 @@ export default Component.extend(
return !this.hasReachedMaximum;
},
- @computed("maximum", "selection.[]")
+ @discourseComputed("maximum", "selection.[]")
hasReachedMaximum(maximum, selection) {
if (!maximum) return false;
selection = makeArray(selection);
return selection.length >= maximum;
},
- @computed("minimum", "selection.[]")
+ @discourseComputed("minimum", "selection.[]")
hasReachedMinimum(minimum, selection) {
if (!minimum) return true;
selection = makeArray(selection);
return selection.length >= minimum;
},
- @computed("shouldFilter", "allowAny")
+ @discourseComputed("shouldFilter", "allowAny")
shouldDisplayFilter(shouldFilter, allowAny) {
if (shouldFilter) return true;
if (allowAny) return true;
return false;
},
- @computed("filter", "collectionComputedContent.[]", "isLoading")
+ @discourseComputed("filter", "collectionComputedContent.[]", "isLoading")
noContentRow(filter, collectionComputedContent, isLoading) {
if (
filter.length > 0 &&
@@ -282,7 +283,7 @@ export default Component.extend(
}
},
- @computed("hasReachedMaximum", "hasReachedMinimum", "isExpanded")
+ @discourseComputed("hasReachedMaximum", "hasReachedMinimum", "isExpanded")
validationMessage(hasReachedMaximum, hasReachedMinimum) {
if (hasReachedMaximum && this.maximum) {
const key = this.maximumLabel || "select_kit.max_content_reached";
@@ -295,14 +296,19 @@ export default Component.extend(
}
},
- @computed("allowAny")
+ @discourseComputed("allowAny")
filterPlaceholder(allowAny) {
return allowAny
? "select_kit.filter_placeholder_with_any"
: "select_kit.filter_placeholder";
},
- @computed("filter", "filterable", "autoFilterable", "renderedFilterOnce")
+ @discourseComputed(
+ "filter",
+ "filterable",
+ "autoFilterable",
+ "renderedFilterOnce"
+ )
shouldFilter(filter, filterable, autoFilterable, renderedFilterOnce) {
if (renderedFilterOnce && filterable) return true;
if (filterable) return true;
@@ -310,7 +316,7 @@ export default Component.extend(
return false;
},
- @computed(
+ @discourseComputed(
"computedValue",
"filter",
"collectionComputedContent.[]",
@@ -331,7 +337,7 @@ export default Component.extend(
return false;
},
- @computed("filter", "shouldDisplayCreateRow")
+ @discourseComputed("filter", "shouldDisplayCreateRow")
createRowComputedContent(filter, shouldDisplayCreateRow) {
if (shouldDisplayCreateRow) {
let content = this.createContentFromInput(filter);
@@ -343,17 +349,17 @@ export default Component.extend(
}
},
- @computed
+ @discourseComputed
templateForRow() {
return () => null;
},
- @computed
+ @discourseComputed
templateForNoneRow() {
return () => null;
},
- @computed("filter")
+ @discourseComputed("filter")
templateForCreateRow() {
return rowComponent => {
return I18n.t("select_kit.create", {
@@ -362,7 +368,7 @@ export default Component.extend(
};
},
- @computed("none")
+ @discourseComputed("none")
noneRowComputedContent(none) {
if (isNone(none)) return null;
@@ -427,7 +433,12 @@ export default Component.extend(
this._boundaryActionHandler("onStopLoading");
},
- @computed("selection.[]", "isExpanded", "filter", "highlightedSelection.[]")
+ @discourseComputed(
+ "selection.[]",
+ "isExpanded",
+ "filter",
+ "highlightedSelection.[]"
+ )
collectionHeaderComputedContent() {
return applyCollectionHeaderCallbacks(
this.pluginApiIdentifiers,
@@ -436,7 +447,7 @@ export default Component.extend(
);
},
- @computed("selection.[]", "isExpanded", "headerIcon")
+ @discourseComputed("selection.[]", "isExpanded", "headerIcon")
headerComputedContent() {
return applyHeaderContentPluginApiCallbacks(
this.pluginApiIdentifiers,
diff --git a/app/assets/javascripts/select-kit/components/select-kit/select-kit-filter.js.es6 b/app/assets/javascripts/select-kit/components/select-kit/select-kit-filter.js.es6
index 9576816708..a239c780cd 100644
--- a/app/assets/javascripts/select-kit/components/select-kit/select-kit-filter.js.es6
+++ b/app/assets/javascripts/select-kit/components/select-kit/select-kit-filter.js.es6
@@ -1,5 +1,6 @@
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
+
const { isEmpty } = Ember;
export default Component.extend({
@@ -8,8 +9,8 @@ export default Component.extend({
classNameBindings: ["isFocused", "isHidden"],
isHidden: Ember.computed.not("shouldDisplayFilter"),
- @computed("placeholder")
- computedPlaceholder(placeholder) {
+ @discourseComputed("placeholder")
+ discourseComputedPlaceholder(placeholder) {
return isEmpty(placeholder) ? "" : I18n.t(placeholder);
}
});
diff --git a/app/assets/javascripts/select-kit/components/select-kit/select-kit-header.js.es6 b/app/assets/javascripts/select-kit/components/select-kit/select-kit-header.js.es6
index 807326c990..fd145162d0 100644
--- a/app/assets/javascripts/select-kit/components/select-kit/select-kit-header.js.es6
+++ b/app/assets/javascripts/select-kit/components/select-kit/select-kit-header.js.es6
@@ -1,5 +1,6 @@
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
+
const { isEmpty, makeArray } = Ember;
export default Component.extend({
@@ -23,7 +24,7 @@ export default Component.extend({
ariaLabel: Ember.computed.or("computedContent.ariaLabel", "sanitizedTitle"),
- @computed("computedContent.title", "name")
+ @discourseComputed("computedContent.title", "name")
title(computedContentTitle, name) {
if (computedContentTitle) return computedContentTitle;
if (name) return name;
@@ -33,7 +34,7 @@ export default Component.extend({
// this might need a more advanced solution
// but atm it's the only case we have to handle
- @computed("title")
+ @discourseComputed("title")
sanitizedTitle(title) {
return String(title).replace("…", "");
},
@@ -44,7 +45,7 @@ export default Component.extend({
value: Ember.computed.alias("computedContent.value"),
- @computed("computedContent.icon", "computedContent.icons")
+ @discourseComputed("computedContent.icon", "computedContent.icons")
icons(icon, icons) {
return makeArray(icon)
.concat(icons)
diff --git a/app/assets/javascripts/select-kit/components/select-kit/select-kit-row.js.es6 b/app/assets/javascripts/select-kit/components/select-kit/select-kit-row.js.es6
index 5b016fe905..01828a5e94 100644
--- a/app/assets/javascripts/select-kit/components/select-kit/select-kit-row.js.es6
+++ b/app/assets/javascripts/select-kit/components/select-kit/select-kit-row.js.es6
@@ -1,6 +1,9 @@
import Component from "@ember/component";
-import { on } from "ember-addons/ember-computed-decorators";
-import computed from "ember-addons/ember-computed-decorators";
+import {
+ default as discourseComputed,
+ on
+} from "discourse-common/utils/decorators";
+
const { run, isPresent, makeArray, isEmpty } = Ember;
import UtilsMixin from "select-kit/mixins/utils";
@@ -27,7 +30,7 @@ export default Component.extend(UtilsMixin, {
ariaLabel: Ember.computed.or("computedContent.ariaLabel", "title"),
- @computed("computedContent.title", "name")
+ @discourseComputed("computedContent.title", "name")
title(computedContentTitle, name) {
if (computedContentTitle) return computedContentTitle;
if (name) return name;
@@ -35,7 +38,7 @@ export default Component.extend(UtilsMixin, {
return null;
},
- @computed("computedContent")
+ @discourseComputed("computedContent")
guid(computedContent) {
return Ember.guidFor(computedContent);
},
@@ -46,7 +49,7 @@ export default Component.extend(UtilsMixin, {
value: Ember.computed.alias("computedContent.value"),
- @computed("templateForRow")
+ @discourseComputed("templateForRow")
template(templateForRow) {
return templateForRow(this);
},
@@ -67,7 +70,7 @@ export default Component.extend(UtilsMixin, {
}
},
- @computed(
+ @discourseComputed(
"computedContent.icon",
"computedContent.icons",
"computedContent.originalContent.icon"
diff --git a/app/assets/javascripts/select-kit/components/single-select.js.es6 b/app/assets/javascripts/select-kit/components/single-select.js.es6
index 5b4f6cd877..92c86cc4c5 100644
--- a/app/assets/javascripts/select-kit/components/single-select.js.es6
+++ b/app/assets/javascripts/select-kit/components/single-select.js.es6
@@ -1,8 +1,8 @@
import SelectKitComponent from "select-kit/components/select-kit";
import {
- default as computed,
+ default as discourseComputed,
on
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
const { get, isNone, isEmpty, isPresent, run, makeArray } = Ember;
import {
@@ -115,7 +115,7 @@ export default SelectKitComponent.extend({
return content;
},
- @computed("computedAsyncContent.[]", "computedValue")
+ @discourseComputed("computedAsyncContent.[]", "computedValue")
filteredAsyncComputedContent(computedAsyncContent, computedValue) {
computedAsyncContent = (computedAsyncContent || []).filter(c => {
return computedValue !== get(c, "value");
@@ -128,7 +128,12 @@ export default SelectKitComponent.extend({
return computedAsyncContent;
},
- @computed("computedContent.[]", "computedValue", "filter", "shouldFilter")
+ @discourseComputed(
+ "computedContent.[]",
+ "computedValue",
+ "filter",
+ "shouldFilter"
+ )
filteredComputedContent(
computedContent,
computedValue,
@@ -150,17 +155,17 @@ export default SelectKitComponent.extend({
return computedContent;
},
- @computed("computedValue", "computedContent.[]")
+ @discourseComputed("computedValue", "computedContent.[]")
selection(computedValue, computedContent) {
return computedContent.findBy("value", computedValue);
},
- @computed("selection")
+ @discourseComputed("selection")
hasSelection(selection) {
return selection !== this.noneRowComputedContent && !isNone(selection);
},
- @computed(
+ @discourseComputed(
"computedValue",
"filter",
"collectionComputedContent.[]",
diff --git a/app/assets/javascripts/select-kit/components/tag-chooser.js.es6 b/app/assets/javascripts/select-kit/components/tag-chooser.js.es6
index 3e92b80a88..1ad21b0642 100644
--- a/app/assets/javascripts/select-kit/components/tag-chooser.js.es6
+++ b/app/assets/javascripts/select-kit/components/tag-chooser.js.es6
@@ -1,7 +1,7 @@
import MultiSelectComponent from "select-kit/components/multi-select";
import TagsMixin from "select-kit/mixins/tags";
import renderTag from "discourse/lib/render-tag";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
import { makeArray } from "discourse-common/lib/helpers";
const { get, run } = Ember;
@@ -55,12 +55,12 @@ export default MultiSelectComponent.extend(TagsMixin, {
this.set("tags", values.filter(v => v));
},
- @computed("tags")
+ @discourseComputed("tags")
values(tags) {
return makeArray(tags);
},
- @computed("tags")
+ @discourseComputed("tags")
content(tags) {
return makeArray(tags);
},
diff --git a/app/assets/javascripts/select-kit/components/tag-drop.js.es6 b/app/assets/javascripts/select-kit/components/tag-drop.js.es6
index 66958c3452..9fbce57f85 100644
--- a/app/assets/javascripts/select-kit/components/tag-drop.js.es6
+++ b/app/assets/javascripts/select-kit/components/tag-drop.js.es6
@@ -2,7 +2,7 @@ import { makeArray } from "discourse-common/lib/helpers";
import ComboBoxComponent from "select-kit/components/combo-box";
import DiscourseURL from "discourse/lib/url";
import TagsMixin from "select-kit/mixins/tags";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
const { isEmpty, run } = Ember;
export default ComboBoxComponent.extend(TagsMixin, {
@@ -25,18 +25,18 @@ export default ComboBoxComponent.extend(TagsMixin, {
allowContentReplacement: true,
isAsync: true,
- @computed("tagId")
+ @discourseComputed("tagId")
noTagsSelected() {
return this.tagId === "none";
},
- @computed("showFilterByTag", "content")
+ @discourseComputed("showFilterByTag", "content")
isHidden(showFilterByTag, content) {
if (showFilterByTag && !isEmpty(content)) return false;
return true;
},
- @computed("content")
+ @discourseComputed("content")
filterable(content) {
return content && content.length >= 15;
},
@@ -63,12 +63,12 @@ export default ComboBoxComponent.extend(TagsMixin, {
return content;
},
- @computed("tagId")
+ @discourseComputed("tagId")
tagClass(tagId) {
return tagId ? `tag-${tagId}` : "tag_all";
},
- @computed("firstCategory", "secondCategory")
+ @discourseComputed("firstCategory", "secondCategory")
allTagsUrl() {
if (this.currentCategory) {
return Discourse.getURL(this.get("currentCategory.url") + "?allTags=1");
@@ -77,7 +77,7 @@ export default ComboBoxComponent.extend(TagsMixin, {
}
},
- @computed("firstCategory", "secondCategory")
+ @discourseComputed("firstCategory", "secondCategory")
noTagsUrl() {
var url = "/tags";
if (this.currentCategory) {
@@ -86,17 +86,17 @@ export default ComboBoxComponent.extend(TagsMixin, {
return Discourse.getURL(`${url}/none`);
},
- @computed("tag")
+ @discourseComputed("tag")
allTagsLabel() {
return I18n.t("tagging.selector_all_tags");
},
- @computed("tag")
+ @discourseComputed("tag")
noTagsLabel() {
return I18n.t("tagging.selector_no_tags");
},
- @computed("tagId", "allTagsLabel", "noTagsLabel")
+ @discourseComputed("tagId", "allTagsLabel", "noTagsLabel")
shortcuts(tagId, allTagsLabel, noTagsLabel) {
const shortcuts = [];
@@ -119,7 +119,7 @@ export default ComboBoxComponent.extend(TagsMixin, {
return shortcuts;
},
- @computed("site.top_tags", "shortcuts")
+ @discourseComputed("site.top_tags", "shortcuts")
content(topTags, shortcuts) {
if (this.siteSettings.tags_sort_alphabetically && topTags) {
return shortcuts.concat(topTags.sort());
diff --git a/app/assets/javascripts/select-kit/components/tag-group-chooser.js.es6 b/app/assets/javascripts/select-kit/components/tag-group-chooser.js.es6
index c3cb9d0ef3..71d2343b34 100644
--- a/app/assets/javascripts/select-kit/components/tag-group-chooser.js.es6
+++ b/app/assets/javascripts/select-kit/components/tag-group-chooser.js.es6
@@ -1,7 +1,8 @@
import MultiSelectComponent from "select-kit/components/multi-select";
import TagsMixin from "select-kit/mixins/tags";
import renderTag from "discourse/lib/render-tag";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
+
const { get, isEmpty, run, makeArray } = Ember;
export default MultiSelectComponent.extend(TagsMixin, {
@@ -29,12 +30,12 @@ export default MultiSelectComponent.extend(TagsMixin, {
this.set("tagGroups", values.filter(v => v));
},
- @computed("tagGroups")
+ @discourseComputed("tagGroups")
values(tagGroups) {
return makeArray(tagGroups);
},
- @computed("tagGroups")
+ @discourseComputed("tagGroups")
content(tagGroups) {
return makeArray(tagGroups);
},
diff --git a/app/assets/javascripts/select-kit/components/tag-notifications-button.js.es6 b/app/assets/javascripts/select-kit/components/tag-notifications-button.js.es6
index 12aef37fac..c163c3d5d9 100644
--- a/app/assets/javascripts/select-kit/components/tag-notifications-button.js.es6
+++ b/app/assets/javascripts/select-kit/components/tag-notifications-button.js.es6
@@ -1,5 +1,5 @@
import NotificationOptionsComponent from "select-kit/components/notifications-button";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
export default NotificationOptionsComponent.extend({
pluginApiIdentifiers: ["tag-notifications-button"],
@@ -16,7 +16,7 @@ export default NotificationOptionsComponent.extend({
return this.notificationLevel;
},
- @computed("iconForSelectedDetails")
+ @discourseComputed("iconForSelectedDetails")
headerIcon(iconForSelectedDetails) {
return iconForSelectedDetails;
}
diff --git a/app/assets/javascripts/select-kit/components/timezone-input.js.es6 b/app/assets/javascripts/select-kit/components/timezone-input.js.es6
index e141839a1d..cc837e1d66 100644
--- a/app/assets/javascripts/select-kit/components/timezone-input.js.es6
+++ b/app/assets/javascripts/select-kit/components/timezone-input.js.es6
@@ -1,5 +1,5 @@
import ComboBoxComponent from "select-kit/components/combo-box";
-import { default as computed } from "ember-addons/ember-computed-decorators";
+import { default as discourseComputed } from "discourse-common/utils/decorators";
export default ComboBoxComponent.extend({
pluginApiIdentifiers: ["timezone-input"],
@@ -9,7 +9,7 @@ export default ComboBoxComponent.extend({
filterable: true,
allowAny: false,
- @computed
+ @discourseComputed
content() {
let timezones;
diff --git a/app/assets/javascripts/select-kit/components/toolbar-popup-menu-options.js.es6 b/app/assets/javascripts/select-kit/components/toolbar-popup-menu-options.js.es6
index 39d8348119..0c0ab1f730 100644
--- a/app/assets/javascripts/select-kit/components/toolbar-popup-menu-options.js.es6
+++ b/app/assets/javascripts/select-kit/components/toolbar-popup-menu-options.js.es6
@@ -1,5 +1,5 @@
import DropdownSelectBoxComponent from "select-kit/components/dropdown-select-box";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
export default DropdownSelectBoxComponent.extend({
pluginApiIdentifiers: ["toolbar-popup-menu-options"],
@@ -7,7 +7,7 @@ export default DropdownSelectBoxComponent.extend({
isHidden: Ember.computed.empty("computedContent"),
showFullTitle: false,
- @computed("title")
+ @discourseComputed("title")
collectionHeader(title) {
return `${title}
`;
},
diff --git a/app/assets/javascripts/select-kit/components/topic-notifications-options.js.es6 b/app/assets/javascripts/select-kit/components/topic-notifications-options.js.es6
index e59e5d5d34..1001c7884d 100644
--- a/app/assets/javascripts/select-kit/components/topic-notifications-options.js.es6
+++ b/app/assets/javascripts/select-kit/components/topic-notifications-options.js.es6
@@ -1,8 +1,8 @@
import NotificationOptionsComponent from "select-kit/components/notifications-button";
import {
- default as computed,
+ default as discourseComputed,
on
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import { topicLevels } from "discourse/lib/notification-levels";
export default NotificationOptionsComponent.extend({
@@ -12,7 +12,7 @@ export default NotificationOptionsComponent.extend({
i18nPrefix: "topic.notifications",
allowInitialValueMutation: false,
- @computed("topic.archetype")
+ @discourseComputed("topic.archetype")
i18nPostfix(archetype) {
return archetype === "private_message" ? "_pm" : "";
},
diff --git a/app/assets/javascripts/select-kit/components/user-notifications-dropdown.js.es6 b/app/assets/javascripts/select-kit/components/user-notifications-dropdown.js.es6
index 2289b2f667..2551e20b61 100644
--- a/app/assets/javascripts/select-kit/components/user-notifications-dropdown.js.es6
+++ b/app/assets/javascripts/select-kit/components/user-notifications-dropdown.js.es6
@@ -1,7 +1,7 @@
import DropdownSelectBox from "select-kit/components/dropdown-select-box";
import { popupAjaxError } from "discourse/lib/ajax-error";
import showModal from "discourse/lib/show-modal";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
export default DropdownSelectBox.extend({
classNames: ["user-notifications", "user-notifications-dropdown"],
@@ -36,7 +36,7 @@ export default DropdownSelectBox.extend({
return content;
},
- @computed("value")
+ @discourseComputed("value")
headerIcon(value) {
return this.computeContent().find(row => row.id === value).icon;
},
@@ -53,7 +53,7 @@ export default DropdownSelectBox.extend({
});
},
- @computed("user.ignored", "user.muted")
+ @discourseComputed("user.ignored", "user.muted")
value() {
if (this.get("user.ignored")) {
return "changeToIgnored";
diff --git a/app/assets/javascripts/select-kit/mixins/dom-helpers.js.es6 b/app/assets/javascripts/select-kit/mixins/dom-helpers.js.es6
index 98e79eba58..8de81dc595 100644
--- a/app/assets/javascripts/select-kit/mixins/dom-helpers.js.es6
+++ b/app/assets/javascripts/select-kit/mixins/dom-helpers.js.es6
@@ -1,6 +1,6 @@
import { next } from "@ember/runloop";
import { schedule } from "@ember/runloop";
-import { on } from "ember-addons/ember-computed-decorators";
+import { on } from "discourse-common/utils/decorators";
import Mixin from "@ember/object/mixin";
export default Mixin.create({
diff --git a/app/assets/javascripts/select-kit/mixins/events.js.es6 b/app/assets/javascripts/select-kit/mixins/events.js.es6
index 739d0925e3..4c54979d1f 100644
--- a/app/assets/javascripts/select-kit/mixins/events.js.es6
+++ b/app/assets/javascripts/select-kit/mixins/events.js.es6
@@ -3,7 +3,7 @@ import { makeArray } from "discourse-common/lib/helpers";
import { isEmpty } from "@ember/utils";
import { throttle } from "@ember/runloop";
import { schedule } from "@ember/runloop";
-import { on } from "ember-addons/ember-computed-decorators";
+import { on } from "discourse-common/utils/decorators";
import Mixin from "@ember/object/mixin";
const { bind } = Ember.run;
diff --git a/app/assets/javascripts/wizard-application.js b/app/assets/javascripts/wizard-application.js
index d5460545ae..3a409952c1 100644
--- a/app/assets/javascripts/wizard-application.js
+++ b/app/assets/javascripts/wizard-application.js
@@ -1,7 +1,7 @@
//= require_tree ./ember-addons/utils
//= require ./ember-addons/decorator-alias
//= require ./ember-addons/macro-alias
-//= require ./ember-addons/ember-computed-decorators
+//= require ./discourse-common/utils/decorators
//= require_tree ./discourse-common
//= require i18n-patches
//= require_tree ./select-kit
diff --git a/app/assets/javascripts/wizard/components/homepage-preview.js.es6 b/app/assets/javascripts/wizard/components/homepage-preview.js.es6
index f92f7b04f3..c0de35c55a 100644
--- a/app/assets/javascripts/wizard/components/homepage-preview.js.es6
+++ b/app/assets/javascripts/wizard/components/homepage-preview.js.es6
@@ -1,4 +1,4 @@
-import { observes } from "ember-addons/ember-computed-decorators";
+import { observes } from "discourse-common/utils/decorators";
import {
createPreviewComponent,
LOREM,
diff --git a/app/assets/javascripts/wizard/components/image-preview-favicon.js.es6 b/app/assets/javascripts/wizard/components/image-preview-favicon.js.es6
index 91a72ecda7..31df907e58 100644
--- a/app/assets/javascripts/wizard/components/image-preview-favicon.js.es6
+++ b/app/assets/javascripts/wizard/components/image-preview-favicon.js.es6
@@ -1,5 +1,4 @@
-import { observes } from "ember-addons/ember-computed-decorators";
-
+import { observes } from "discourse-common/utils/decorators";
import { createPreviewComponent } from "wizard/lib/preview";
export default createPreviewComponent(371, 124, {
diff --git a/app/assets/javascripts/wizard/components/image-preview-large-icon.js.es6 b/app/assets/javascripts/wizard/components/image-preview-large-icon.js.es6
index 17a605c23a..30ad47db87 100644
--- a/app/assets/javascripts/wizard/components/image-preview-large-icon.js.es6
+++ b/app/assets/javascripts/wizard/components/image-preview-large-icon.js.es6
@@ -1,4 +1,4 @@
-import { observes } from "ember-addons/ember-computed-decorators";
+import { observes } from "discourse-common/utils/decorators";
import { createPreviewComponent } from "wizard/lib/preview";
export default createPreviewComponent(325, 125, {
diff --git a/app/assets/javascripts/wizard/components/image-preview-logo-small.js.es6 b/app/assets/javascripts/wizard/components/image-preview-logo-small.js.es6
index db498c91ee..64ad289234 100644
--- a/app/assets/javascripts/wizard/components/image-preview-logo-small.js.es6
+++ b/app/assets/javascripts/wizard/components/image-preview-logo-small.js.es6
@@ -1,5 +1,4 @@
-import { observes } from "ember-addons/ember-computed-decorators";
-
+import { observes } from "discourse-common/utils/decorators";
import { createPreviewComponent, drawHeader, LOREM } from "wizard/lib/preview";
export default createPreviewComponent(375, 100, {
diff --git a/app/assets/javascripts/wizard/components/image-preview-logo.js.es6 b/app/assets/javascripts/wizard/components/image-preview-logo.js.es6
index f8b5d3f39c..3c37019b50 100644
--- a/app/assets/javascripts/wizard/components/image-preview-logo.js.es6
+++ b/app/assets/javascripts/wizard/components/image-preview-logo.js.es6
@@ -1,5 +1,4 @@
-import { observes } from "ember-addons/ember-computed-decorators";
-
+import { observes } from "discourse-common/utils/decorators";
import { createPreviewComponent, drawHeader } from "wizard/lib/preview";
export default createPreviewComponent(400, 100, {
diff --git a/app/assets/javascripts/wizard/components/invite-list-user.js.es6 b/app/assets/javascripts/wizard/components/invite-list-user.js.es6
index cc07ab1a2d..8cc39470a3 100644
--- a/app/assets/javascripts/wizard/components/invite-list-user.js.es6
+++ b/app/assets/javascripts/wizard/components/invite-list-user.js.es6
@@ -1,10 +1,10 @@
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
export default Component.extend({
classNames: ["invite-list-user"],
- @computed("user.role")
+ @discourseComputed("user.role")
roleName(role) {
return this.roles.findBy("id", role).label;
}
diff --git a/app/assets/javascripts/wizard/components/radio-button.js.es6 b/app/assets/javascripts/wizard/components/radio-button.js.es6
index e7ceaa898f..6184362bb5 100644
--- a/app/assets/javascripts/wizard/components/radio-button.js.es6
+++ b/app/assets/javascripts/wizard/components/radio-button.js.es6
@@ -1,6 +1,6 @@
import { next } from "@ember/runloop";
import Component from "@ember/component";
-import { observes, on } from "ember-addons/ember-computed-decorators";
+import { observes, on } from "discourse-common/utils/decorators";
export default Component.extend({
tagName: "label",
diff --git a/app/assets/javascripts/wizard/components/staff-count.js.es6 b/app/assets/javascripts/wizard/components/staff-count.js.es6
index 2e7db93b3c..d37b291037 100644
--- a/app/assets/javascripts/wizard/components/staff-count.js.es6
+++ b/app/assets/javascripts/wizard/components/staff-count.js.es6
@@ -1,7 +1,7 @@
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
export default Component.extend({
- @computed("field.value")
+ @discourseComputed("field.value")
showStaffCount: staffCount => staffCount > 1
});
diff --git a/app/assets/javascripts/wizard/components/theme-preview.js.es6 b/app/assets/javascripts/wizard/components/theme-preview.js.es6
index 2a098fb879..768e2e5522 100644
--- a/app/assets/javascripts/wizard/components/theme-preview.js.es6
+++ b/app/assets/javascripts/wizard/components/theme-preview.js.es6
@@ -1,6 +1,5 @@
-import computed from "ember-addons/ember-computed-decorators";
-import { observes } from "ember-addons/ember-computed-decorators";
-
+import discourseComputed from "discourse-common/utils/decorators";
+import { observes } from "discourse-common/utils/decorators";
import {
createPreviewComponent,
darkLightDiff,
@@ -14,7 +13,7 @@ export default createPreviewComponent(305, 165, {
classNameBindings: ["isSelected"],
- @computed("selectedId", "colorsId")
+ @discourseComputed("selectedId", "colorsId")
isSelected(selectedId, colorsId) {
return selectedId === colorsId;
},
diff --git a/app/assets/javascripts/wizard/components/wizard-field-image.js.es6 b/app/assets/javascripts/wizard/components/wizard-field-image.js.es6
index a407bd5046..e97137707d 100644
--- a/app/assets/javascripts/wizard/components/wizard-field-image.js.es6
+++ b/app/assets/javascripts/wizard/components/wizard-field-image.js.es6
@@ -1,6 +1,6 @@
import Component from "@ember/component";
import getUrl from "discourse-common/lib/get-url";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
import { getToken } from "wizard/lib/ajax";
import { getOwner } from "discourse-common/lib/get-owner";
import { dasherize } from "@ember/string";
@@ -9,7 +9,7 @@ export default Component.extend({
classNames: ["wizard-image-row"],
uploading: false,
- @computed("field.id")
+ @discourseComputed("field.id")
previewComponent(id) {
const componentName = `image-preview-${dasherize(id)}`;
const exists = getOwner(this).lookup(`component:${componentName}`);
diff --git a/app/assets/javascripts/wizard/components/wizard-field.js.es6 b/app/assets/javascripts/wizard/components/wizard-field.js.es6
index 7636eee0d0..d5491a4ef9 100644
--- a/app/assets/javascripts/wizard/components/wizard-field.js.es6
+++ b/app/assets/javascripts/wizard/components/wizard-field.js.es6
@@ -1,17 +1,17 @@
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
import { dasherize } from "@ember/string";
export default Component.extend({
classNameBindings: [":wizard-field", "typeClass", "field.invalid"],
- @computed("field.type")
+ @discourseComputed("field.type")
typeClass: type => `${dasherize(type)}-field`,
- @computed("field.id")
+ @discourseComputed("field.id")
fieldClass: id => `field-${dasherize(id)} wizard-focusable`,
- @computed("field.type", "field.id")
+ @discourseComputed("field.type", "field.id")
inputComponentName(type, id) {
return type === "component" ? dasherize(id) : `wizard-field-${type}`;
}
diff --git a/app/assets/javascripts/wizard/components/wizard-step-form.js.es6 b/app/assets/javascripts/wizard/components/wizard-step-form.js.es6
index 7bc7a8446e..461a5a0d18 100644
--- a/app/assets/javascripts/wizard/components/wizard-step-form.js.es6
+++ b/app/assets/javascripts/wizard/components/wizard-step-form.js.es6
@@ -1,9 +1,9 @@
import Component from "@ember/component";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
export default Component.extend({
classNameBindings: [":wizard-step-form", "customStepClass"],
- @computed("step.id")
+ @discourseComputed("step.id")
customStepClass: stepId => `wizard-step-${stepId}`
});
diff --git a/app/assets/javascripts/wizard/components/wizard-step.js.es6 b/app/assets/javascripts/wizard/components/wizard-step.js.es6
index a1a3372473..c5008ac2ac 100644
--- a/app/assets/javascripts/wizard/components/wizard-step.js.es6
+++ b/app/assets/javascripts/wizard/components/wizard-step.js.es6
@@ -2,9 +2,9 @@ import { scheduleOnce } from "@ember/runloop";
import Component from "@ember/component";
import getUrl from "discourse-common/lib/get-url";
import {
- default as computed,
+ default as discourseComputed,
observes
-} from "ember-addons/ember-computed-decorators";
+} from "discourse-common/utils/decorators";
import { htmlSafe } from "@ember/template";
jQuery.fn.wiggle = function(times, duration) {
@@ -34,16 +34,16 @@ export default Component.extend({
this.autoFocus();
},
- @computed("step.index")
+ @discourseComputed("step.index")
showQuitButton: index => index === 0,
- @computed("step.displayIndex", "wizard.totalSteps")
+ @discourseComputed("step.displayIndex", "wizard.totalSteps")
showNextButton: (current, total) => current < total,
- @computed("step.displayIndex", "wizard.totalSteps")
+ @discourseComputed("step.displayIndex", "wizard.totalSteps")
showDoneButton: (current, total) => current === total,
- @computed(
+ @discourseComputed(
"step.index",
"step.displayIndex",
"wizard.totalSteps",
@@ -53,10 +53,10 @@ export default Component.extend({
return index !== 0 && displayIndex !== total && completed;
},
- @computed("step.index")
+ @discourseComputed("step.index")
showBackButton: index => index > 0,
- @computed("step.banner")
+ @discourseComputed("step.banner")
bannerImage(src) {
if (!src) {
return;
@@ -80,7 +80,7 @@ export default Component.extend({
}
},
- @computed("step.index", "wizard.totalSteps")
+ @discourseComputed("step.index", "wizard.totalSteps")
barStyle(displayIndex, totalSteps) {
let ratio = parseFloat(displayIndex) / parseFloat(totalSteps - 1);
if (ratio < 0) {
diff --git a/app/assets/javascripts/wizard/controllers/application.js.es6 b/app/assets/javascripts/wizard/controllers/application.js.es6
index 58aede12a1..ca6d2d3e9e 100644
--- a/app/assets/javascripts/wizard/controllers/application.js.es6
+++ b/app/assets/javascripts/wizard/controllers/application.js.es6
@@ -1,10 +1,10 @@
import Controller from "@ember/controller";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
export default Controller.extend({
currentStepId: null,
- @computed("currentStepId")
+ @discourseComputed("currentStepId")
showCanvas(currentStepId) {
return currentStepId === "finished";
}
diff --git a/app/assets/javascripts/wizard/mixins/valid-state.js.es6 b/app/assets/javascripts/wizard/mixins/valid-state.js.es6
index b2dc3e8954..1f82cccb91 100644
--- a/app/assets/javascripts/wizard/mixins/valid-state.js.es6
+++ b/app/assets/javascripts/wizard/mixins/valid-state.js.es6
@@ -1,4 +1,4 @@
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
export const States = {
UNCHECKED: 0,
@@ -15,13 +15,13 @@ export default {
this.set("_validState", States.UNCHECKED);
},
- @computed("_validState")
+ @discourseComputed("_validState")
valid: state => state === States.VALID,
- @computed("_validState")
+ @discourseComputed("_validState")
invalid: state => state === States.INVALID,
- @computed("_validState")
+ @discourseComputed("_validState")
unchecked: state => state === States.UNCHECKED,
setValid(valid, description) {
diff --git a/app/assets/javascripts/wizard/models/step.js.es6 b/app/assets/javascripts/wizard/models/step.js.es6
index cbc7edca18..7909d39aaf 100644
--- a/app/assets/javascripts/wizard/models/step.js.es6
+++ b/app/assets/javascripts/wizard/models/step.js.es6
@@ -1,15 +1,15 @@
import EmberObject from "@ember/object";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
import ValidState from "wizard/mixins/valid-state";
import { ajax } from "wizard/lib/ajax";
export default EmberObject.extend(ValidState, {
id: null,
- @computed("index")
+ @discourseComputed("index")
displayIndex: index => index + 1,
- @computed("fields.[]")
+ @discourseComputed("fields.[]")
fieldsById(fields) {
const lookup = {};
fields.forEach(field => (lookup[field.get("id")] = field));
diff --git a/app/assets/javascripts/wizard/models/wizard.js.es6 b/app/assets/javascripts/wizard/models/wizard.js.es6
index 569a2d5bf7..e907687e11 100644
--- a/app/assets/javascripts/wizard/models/wizard.js.es6
+++ b/app/assets/javascripts/wizard/models/wizard.js.es6
@@ -1,11 +1,11 @@
import Step from "wizard/models/step";
import WizardField from "wizard/models/wizard-field";
import { ajax } from "wizard/lib/ajax";
-import computed from "ember-addons/ember-computed-decorators";
+import discourseComputed from "discourse-common/utils/decorators";
import EmberObject from "@ember/object";
const Wizard = EmberObject.extend({
- @computed("steps.length")
+ @discourseComputed("steps.length")
totalSteps: length => length,
getTitle() {
From 99b0697bd9563ec4cdab2c122c99b2e08a7de881 Mon Sep 17 00:00:00 2001
From: David Taylor
Date: Thu, 7 Nov 2019 23:41:43 +0000
Subject: [PATCH 026/408] FIX: Correct display of last used date in API key
details UI
---
app/assets/javascripts/admin/templates/api-keys-show.hbs | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/app/assets/javascripts/admin/templates/api-keys-show.hbs b/app/assets/javascripts/admin/templates/api-keys-show.hbs
index a742cf994a..217a77f778 100644
--- a/app/assets/javascripts/admin/templates/api-keys-show.hbs
+++ b/app/assets/javascripts/admin/templates/api-keys-show.hbs
@@ -45,8 +45,8 @@
{{/admin-form-row}}
{{#admin-form-row label="admin.api.last_used"}}
- {{#if k.last_used_at}}
- {{format-date k.last_used_at leaveAgo="true"}}
+ {{#if model.last_used_at}}
+ {{format-date model.last_used_at leaveAgo="true"}}
{{else}}
{{i18n "admin.api.never_used"}}
{{/if}}
From 2db20031879dbafd1a90cbb1a43bca55d51c1b08 Mon Sep 17 00:00:00 2001
From: Blake Erickson
Date: Thu, 7 Nov 2019 16:58:19 -0700
Subject: [PATCH 027/408] DEV: Add deprecation warning of non-header based API
auth
This change adds a message to the admin panel if it detects an api
requests that doesn't use the new header based authentication method.
The message is to warn people to switch to header based auth and links
to the api documention topic on meta for more info.
---
app/models/admin_dashboard_data.rb | 3 ++-
config/locales/server.en.yml | 1 +
lib/auth/default_current_user_provider.rb | 4 ++++
3 files changed, 7 insertions(+), 1 deletion(-)
diff --git a/app/models/admin_dashboard_data.rb b/app/models/admin_dashboard_data.rb
index 633b1a0019..0ef9960d1b 100644
--- a/app/models/admin_dashboard_data.rb
+++ b/app/models/admin_dashboard_data.rb
@@ -84,7 +84,8 @@ class AdminDashboardData
@problem_messages = [
'dashboard.bad_favicon_url',
'dashboard.poll_pop3_timeout',
- 'dashboard.poll_pop3_auth_error'
+ 'dashboard.poll_pop3_auth_error',
+ 'dashboard.deprecated_api_usage'
]
add_problem_check :rails_env_check, :host_names_check, :force_https_check,
diff --git a/config/locales/server.en.yml b/config/locales/server.en.yml
index 0e313715f2..ffd59c8380 100644
--- a/config/locales/server.en.yml
+++ b/config/locales/server.en.yml
@@ -1338,6 +1338,7 @@ en:
other: "Email polling has generated %{count} errors in the past 24 hours. Look at the logs for more details."
missing_mailgun_api_key: "The server is configured to send emails via Mailgun but you haven't provided an API key used to verify the webhook messages."
bad_favicon_url: "The favicon is failing to load. Check your favicon setting in Site Settings."
+ deprecated_api_usage: "We detected an API request using a deprecated authentication method. Please update it to use header based auth."
poll_pop3_timeout: "Connection to the POP3 server is timing out. Incoming email could not be retrieved. Please check your POP3 settings and service provider."
poll_pop3_auth_error: "Connection to the POP3 server is failing with an authentication error. Please check your POP3 settings."
force_https_warning: "Your website is using SSL. But `force_https` is not yet enabled in your site settings."
diff --git a/lib/auth/default_current_user_provider.rb b/lib/auth/default_current_user_provider.rb
index d7ffdbeb3e..353555880e 100644
--- a/lib/auth/default_current_user_provider.rb
+++ b/lib/auth/default_current_user_provider.rb
@@ -283,6 +283,10 @@ class Auth::DefaultCurrentUserProvider
def lookup_api_user(api_key_value, request)
if api_key = ApiKey.active.where(key: api_key_value).includes(:user).first
api_username = header_api_key? ? @env[HEADER_API_USERNAME] : request[API_USERNAME]
+ if !header_api_key?
+ # Notify admins of deprecated auth method
+ AdminDashboardData.add_problem_message('dashboard.deprecated_api_usage', 1.day)
+ end
if api_key.allowed_ips.present? && !api_key.allowed_ips.any? { |ip| ip.include?(request.ip) }
Rails.logger.warn("[Unauthorized API Access] username: #{api_username}, IP address: #{request.ip}")
From deec2cf578ce1c898bcde88117610d8bc945f174 Mon Sep 17 00:00:00 2001
From: Sam Saffron
Date: Fri, 8 Nov 2019 11:44:02 +1100
Subject: [PATCH 028/408] FIX: drafts are unique by draft_key and user_id
Previously our index was non unique, causing situations where a user could
have multiple drafts stored in the table for the same exact entity.
This does not properly reflect reality and needed to change as in certain
cases duplicate drafts could be created causing internal data inconsistency
---
app/models/draft.rb | 2 +-
...191108000414_add_unique_index_to_drafts.rb | 27 +++++++++++++++++++
2 files changed, 28 insertions(+), 1 deletion(-)
create mode 100644 db/migrate/20191108000414_add_unique_index_to_drafts.rb
diff --git a/app/models/draft.rb b/app/models/draft.rb
index 2bbc3bcaf6..4f7a03711f 100644
--- a/app/models/draft.rb
+++ b/app/models/draft.rb
@@ -282,5 +282,5 @@ end
#
# Indexes
#
-# index_drafts_on_user_id_and_draft_key (user_id,draft_key)
+# index_drafts_on_user_id_and_draft_key (user_id,draft_key) UNIQUE
#
diff --git a/db/migrate/20191108000414_add_unique_index_to_drafts.rb b/db/migrate/20191108000414_add_unique_index_to_drafts.rb
new file mode 100644
index 0000000000..f50d1b7c49
--- /dev/null
+++ b/db/migrate/20191108000414_add_unique_index_to_drafts.rb
@@ -0,0 +1,27 @@
+# frozen_string_literal: true
+
+class AddUniqueIndexToDrafts < ActiveRecord::Migration[6.0]
+ def up
+
+ execute <<~SQL
+ DELETE FROM drafts d1
+ USING (
+ SELECT MAX(id) as id, draft_key, user_id
+ FROM drafts
+ GROUP BY draft_key, user_id
+ HAVING COUNT(*) > 1
+ ) d2
+ WHERE
+ d1.draft_key = d2.draft_key AND
+ d1.user_id = d2.user_id AND
+ d1.id <> d2.id
+ SQL
+
+ remove_index :drafts, [:user_id, :draft_key]
+ add_index :drafts, [:user_id, :draft_key], unique: true
+ end
+
+ def down
+ raise ActiveRecord::IrreversibleMigration
+ end
+end
From ba5b78a34874d393440e7eee0aee07f0b213c4ae Mon Sep 17 00:00:00 2001
From: Vinoth Kannan
Date: Fri, 8 Nov 2019 08:28:11 +0530
Subject: [PATCH 029/408] FEATURE: support to mute all categories by default.
(#8295)
Instead of enabling `suppress_from_latest` setting on many categories now we can enable `mute_all_categories_by_default` site setting. Then users should opt-in to categories for them to appear in the latest and categories pages.
---
.../templates/preferences/categories.hbs | 18 +++++-----
.../discourse/widgets/hamburger-menu.js.es6 | 6 +++-
app/models/category_list.rb | 10 ++----
app/models/category_user.rb | 20 +++++++++++
app/models/site.rb | 10 ++----
config/locales/server.en.yml | 1 +
config/site_settings.yml | 3 ++
lib/topic_query.rb | 29 +++++++++++++++-
spec/components/topic_query_spec.rb | 33 +++++++++++++++++++
spec/models/category_list_spec.rb | 33 +++++++++++++++++--
spec/models/site_spec.rb | 10 ++++++
11 files changed, 147 insertions(+), 26 deletions(-)
diff --git a/app/assets/javascripts/discourse/templates/preferences/categories.hbs b/app/assets/javascripts/discourse/templates/preferences/categories.hbs
index e264ef1137..671242a16a 100644
--- a/app/assets/javascripts/discourse/templates/preferences/categories.hbs
+++ b/app/assets/javascripts/discourse/templates/preferences/categories.hbs
@@ -27,14 +27,16 @@
{{i18n 'user.watched_first_post_categories_instructions'}}
-
-
- {{#if canSee}}
-
{{i18n 'user.tracked_topics_link'}}
- {{/if}}
- {{category-selector categories=model.mutedCategories blacklist=selectedCategories}}
-
- {{i18n (if hideMutedTags 'user.muted_categories_instructions' 'user.muted_categories_instructions_dont_hide')}}
+ {{#unless siteSettings.mute_all_categories_by_default}}
+
+
+ {{#if canSee}}
+
{{i18n 'user.tracked_topics_link'}}
+ {{/if}}
+ {{category-selector categories=model.mutedCategories blacklist=selectedCategories}}
+
+ {{i18n (if hideMutedTags 'user.muted_categories_instructions' 'user.muted_categories_instructions_dont_hide')}}
+ {{/unless}}
{{plugin-outlet name="user-preferences-categories" args=(hash model=model save=(action "save"))}}
diff --git a/app/assets/javascripts/discourse/widgets/hamburger-menu.js.es6 b/app/assets/javascripts/discourse/widgets/hamburger-menu.js.es6
index b11689796a..be146f4285 100644
--- a/app/assets/javascripts/discourse/widgets/hamburger-menu.js.es6
+++ b/app/assets/javascripts/discourse/widgets/hamburger-menu.js.es6
@@ -173,7 +173,7 @@ export default createWidget("hamburger-menu", {
listCategories() {
const maxCategoriesToDisplay = this.siteSettings
.header_dropdown_category_count;
- let categories = this.site.get("categoriesByCount");
+ let categories = [];
if (this.currentUser) {
const allCategories = this.site
@@ -203,6 +203,10 @@ export default createWidget("hamburger-menu", {
.filter(c => !categories.includes(c))
.sort((a, b) => b.topic_count - a.topic_count)
);
+ } else {
+ categories = this.site
+ .get("categoriesByCount")
+ .filter(c => c.notification_level !== NotificationLevels.MUTED);
}
if (!this.siteSettings.allow_uncategorized_topics) {
diff --git a/app/models/category_list.rb b/app/models/category_list.rb
index f1f7b6a0d9..bc1d6a4980 100644
--- a/app/models/category_list.rb
+++ b/app/models/category_list.rb
@@ -92,16 +92,12 @@ class CategoryList
@categories = @categories.to_a
- category_user = {}
- default_notification_level = nil
- unless @guardian.anonymous?
- category_user = Hash[*CategoryUser.where(user: @guardian.user).pluck(:category_id, :notification_level).flatten]
- default_notification_level = CategoryUser.notification_levels[:regular]
- end
+ notification_levels = CategoryUser.notification_levels_for(@guardian)
+ default_notification_level = CategoryUser.default_notification_level
allowed_topic_create = Set.new(Category.topic_create_allowed(@guardian).pluck(:id))
@categories.each do |category|
- category.notification_level = category_user[category.id] || default_notification_level
+ category.notification_level = notification_levels[category.id] || default_notification_level
category.permission = CategoryGroup.permission_types[:full] if allowed_topic_create.include?(category.id)
category.has_children = category.subcategories.present?
end
diff --git a/app/models/category_user.rb b/app/models/category_user.rb
index e25f917d32..d2dd1a4d36 100644
--- a/app/models/category_user.rb
+++ b/app/models/category_user.rb
@@ -197,6 +197,26 @@ class CategoryUser < ActiveRecord::Base
SQL
end
+ def self.default_notification_level
+ SiteSetting.mute_all_categories_by_default ? notification_levels[:muted] : notification_levels[:regular]
+ end
+
+ def self.notification_levels_for(guardian)
+ if guardian.anonymous?
+ notification_levels = [
+ SiteSetting.default_categories_watching.split("|"),
+ SiteSetting.default_categories_tracking.split("|"),
+ SiteSetting.default_categories_watching_first_post.split("|"),
+ ].flatten.map { |id| [id.to_i, 1] }
+
+ notification_levels += SiteSetting.default_categories_muted.split("|").map { |id| [id.to_i, 0] }
+ else
+ notification_levels = CategoryUser.where(user: guardian.user).pluck(:category_id, :notification_level)
+ end
+
+ Hash[*notification_levels.flatten]
+ end
+
end
# == Schema Information
diff --git a/app/models/site.rb b/app/models/site.rb
index c7330e1e25..d8bddf0a99 100644
--- a/app/models/site.rb
+++ b/app/models/site.rb
@@ -55,15 +55,11 @@ class Site
by_id = {}
- category_user = {}
- unless @guardian.anonymous?
- category_user = Hash[*CategoryUser.where(user: @guardian.user).pluck(:category_id, :notification_level).flatten]
- end
-
- regular = CategoryUser.notification_levels[:regular]
+ notification_levels = CategoryUser.notification_levels_for(@guardian)
+ default_notification_level = CategoryUser.default_notification_level
categories.each do |category|
- category.notification_level = category_user[category.id] || regular
+ category.notification_level = notification_levels[category.id] || default_notification_level
category.permission = CategoryGroup.permission_types[:full] if allowed_topic_create&.include?(category.id) || @guardian.is_admin?
category.has_children = with_children.include?(category.id)
by_id[category.id] = category
diff --git a/config/locales/server.en.yml b/config/locales/server.en.yml
index ffd59c8380..dac88f2d93 100644
--- a/config/locales/server.en.yml
+++ b/config/locales/server.en.yml
@@ -2067,6 +2067,7 @@ en:
default_categories_tracking: "List of categories that are tracked by default."
default_categories_muted: "List of categories that are muted by default."
default_categories_watching_first_post: "List of categories in which first post in each new topic will be watched by default."
+ mute_all_categories_by_default: "Set the default notification level of all the categories to muted. Require users opt-in to categories for them to appear in 'latest' and 'categories' pages. If you wish to amend the defaults for anonymous users set 'default_categories_' settings."
default_tags_watching: "List of tags that are watched by default."
default_tags_tracking: "List of tags that are tracked by default."
diff --git a/config/site_settings.yml b/config/site_settings.yml
index 63f1aecf1c..02a4ae3386 100644
--- a/config/site_settings.yml
+++ b/config/site_settings.yml
@@ -2022,6 +2022,9 @@ user_preferences:
default_categories_watching_first_post:
type: category_list
default: ""
+ mute_all_categories_by_default:
+ default: false
+ client: true
default_tags_watching:
type: tag_list
diff --git a/lib/topic_query.rb b/lib/topic_query.rb
index 8a2c4637f3..dec1268030 100644
--- a/lib/topic_query.rb
+++ b/lib/topic_query.rb
@@ -869,7 +869,34 @@ class TopicQuery
def remove_muted_categories(list, user, opts = nil)
category_id = get_category_id(opts[:exclude]) if opts
- if user
+ if SiteSetting.mute_all_categories_by_default
+ if user
+ list = list.references("cu")
+ .where("
+ NOT EXISTS (
+ SELECT 1
+ FROM categories c
+ LEFT OUTER JOIN category_users cu
+ ON c.id = cu.category_id AND cu.user_id = :user_id
+ WHERE c.id = topics.category_id
+ AND c.id <> :category_id
+ AND (COALESCE(cu.notification_level, :muted) = :muted)
+ AND (COALESCE(tu.notification_level, :regular) <= :regular)
+ )", user_id: user.id,
+ muted: CategoryUser.notification_levels[:muted],
+ regular: TopicUser.notification_levels[:regular],
+ category_id: category_id || -1)
+ else
+ category_ids = [
+ SiteSetting.default_categories_watching.split("|"),
+ SiteSetting.default_categories_tracking.split("|"),
+ SiteSetting.default_categories_watching_first_post.split("|")
+ ].flatten.map(&:to_i)
+ category_ids << category_id if category_id.present? && category_ids.exclude?(category_id)
+
+ list = list.where("topics.category_id IN (?)", category_ids) if category_ids.present?
+ end
+ elsif user
list = list.references("cu")
.where("
NOT EXISTS (
diff --git a/spec/components/topic_query_spec.rb b/spec/components/topic_query_spec.rb
index e3e2ab2724..aac94f9b67 100644
--- a/spec/components/topic_query_spec.rb
+++ b/spec/components/topic_query_spec.rb
@@ -240,6 +240,39 @@ describe TopicQuery do
end
end
+ context 'mute_all_categories_by_default' do
+ fab!(:category) { Fabricate(:category_with_definition) }
+ fab!(:topic) { Fabricate(:topic, category: category) }
+
+ before do
+ SiteSetting.mute_all_categories_by_default = true
+ end
+
+ it 'should remove all topics from new and latest lists by default' do
+ expect(topic_query.list_new.topics.map(&:id)).not_to include(topic.id)
+ expect(topic_query.list_latest.topics.map(&:id)).not_to include(topic.id)
+ end
+
+ it 'should include tracked category topics in new and latest lists' do
+ topic = Fabricate(:topic, category: category)
+ CategoryUser.create!(user_id: user.id,
+ category_id: category.id,
+ notification_level: CategoryUser.notification_levels[:tracking])
+ expect(topic_query.list_new.topics.map(&:id)).to include(topic.id)
+ expect(topic_query.list_latest.topics.map(&:id)).to include(topic.id)
+ end
+
+ it 'should include default watched category topics in latest list for anonymous users' do
+ SiteSetting.default_categories_watching = category.id.to_s
+ expect(TopicQuery.new.list_latest.topics.map(&:id)).to include(topic.id)
+ end
+
+ it 'should include topics when filtered by category' do
+ topic_query = TopicQuery.new(user, category: topic.category_id)
+ expect(topic_query.list_latest.topics.map(&:id)).to include(topic.id)
+ end
+ end
+
context 'muted tags' do
it 'is removed from new and latest lists' do
SiteSetting.tagging_enabled = true
diff --git a/spec/models/category_list_spec.rb b/spec/models/category_list_spec.rb
index 85f4507894..bc6e03963d 100644
--- a/spec/models/category_list_spec.rb
+++ b/spec/models/category_list_spec.rb
@@ -65,6 +65,35 @@ describe CategoryList do
end
end
+ context "when mute_all_categories_by_default enabled" do
+ fab!(:category) { Fabricate(:category) }
+
+ before do
+ SiteSetting.mute_all_categories_by_default = true
+ end
+
+ it "removes the category by default" do
+ expect(category_list.categories).not_to include(category)
+ end
+
+ it "returns correct notification level for user tracking category" do
+ CategoryUser.set_notification_level_for_category(user, NotificationLevels.all[:tracking], category.id)
+ notification_level = category_list.categories.find { |c| c.id == category.id }.notification_level
+ expect(notification_level).to eq(CategoryUser.notification_levels[:tracking])
+ end
+
+ it "returns correct notification level in default categories for anonymous" do
+ SiteSetting.default_categories_watching = category.id.to_s
+ notification_level = CategoryList.new(Guardian.new).categories.find { |c| c.id == category.id }.notification_level
+ expect(notification_level).to eq(CategoryUser.notification_levels[:regular])
+ end
+
+ it "removes the default muted categories for anonymous" do
+ SiteSetting.default_categories_muted = category.id.to_s
+ expect(CategoryList.new(Guardian.new).categories).not_to include(category)
+ end
+ end
+
context "with a category" do
fab!(:topic_category) { Fabricate(:category_with_definition, num_featured_topics: 2) }
@@ -114,11 +143,11 @@ describe CategoryList do
expect(category.notification_level).to eq(NotificationLevels.all[:watching])
end
- it "returns no notication level for anonymous users" do
+ it "returns default notication level for anonymous users" do
category_list = CategoryList.new(Guardian.new(nil))
category = category_list.categories.find { |c| c.id == topic_category.id }
- expect(category.notification_level).to be_nil
+ expect(category.notification_level).to eq(NotificationLevels.all[:regular])
end
end
diff --git a/spec/models/site_spec.rb b/spec/models/site_spec.rb
index 53b5f7493e..c97aafe10b 100644
--- a/spec/models/site_spec.rb
+++ b/spec/models/site_spec.rb
@@ -41,6 +41,16 @@ describe Site do
end
+ it "returns correct notification level for categories" do
+ category = Fabricate(:category)
+ guardian = Guardian.new
+ expect(Site.new(guardian).categories.last.notification_level).to eq(1)
+ SiteSetting.mute_all_categories_by_default = true
+ expect(Site.new(guardian).categories.last.notification_level).to eq(0)
+ SiteSetting.default_categories_tracking = category.id.to_s
+ expect(Site.new(guardian).categories.last.notification_level).to eq(1)
+ end
+
it "omits categories users can not write to from the category list" do
category = Fabricate(:category)
user = Fabricate(:user)
From 64b4a7ba45fae3b688925754c632e458fcacd486 Mon Sep 17 00:00:00 2001
From: Martin Brennan
Date: Fri, 8 Nov 2019 15:11:53 +1000
Subject: [PATCH 030/408] FIX: Ensure enforce 2FA for staff satisfied by
security keys (#8316)
* If a staff user created only a security key as their single 2FA option. they continued to be prompted to create a 2FA option because we only considered this condition satisfied if a TOTP was added.
* The condition is now satisfied if TOTP OR security keys are enabled.
---
.../admin_detailed_user_serializer.rb | 2 +-
app/serializers/current_user_serializer.rb | 2 +-
app/serializers/user_serializer.rb | 2 +-
.../current_user_serializer_spec.rb | 32 +++++++++++++++++++
spec/serializers/user_serializer_spec.rb | 30 ++++++++++++++++-
5 files changed, 64 insertions(+), 4 deletions(-)
diff --git a/app/serializers/admin_detailed_user_serializer.rb b/app/serializers/admin_detailed_user_serializer.rb
index 3555522497..4a83a594b1 100644
--- a/app/serializers/admin_detailed_user_serializer.rb
+++ b/app/serializers/admin_detailed_user_serializer.rb
@@ -39,7 +39,7 @@ class AdminDetailedUserSerializer < AdminUserSerializer
has_many :groups, embed: :object, serializer: BasicGroupSerializer
def second_factor_enabled
- object.totp_enabled?
+ object.totp_enabled? || object.security_keys_enabled?
end
def can_disable_second_factor
diff --git a/app/serializers/current_user_serializer.rb b/app/serializers/current_user_serializer.rb
index 4ba1a982f8..72363fc3ac 100644
--- a/app/serializers/current_user_serializer.rb
+++ b/app/serializers/current_user_serializer.rb
@@ -210,6 +210,6 @@ class CurrentUserSerializer < BasicUserSerializer
end
def second_factor_enabled
- object.totp_enabled?
+ object.totp_enabled? || object.security_keys_enabled?
end
end
diff --git a/app/serializers/user_serializer.rb b/app/serializers/user_serializer.rb
index 52d1214cfd..79111200ef 100644
--- a/app/serializers/user_serializer.rb
+++ b/app/serializers/user_serializer.rb
@@ -164,7 +164,7 @@ class UserSerializer < BasicUserSerializer
end
def second_factor_enabled
- object.totp_enabled?
+ object.totp_enabled? || object.security_keys_enabled?
end
def include_second_factor_backup_enabled?
diff --git a/spec/serializers/current_user_serializer_spec.rb b/spec/serializers/current_user_serializer_spec.rb
index 9eb2d34c62..30c6a40497 100644
--- a/spec/serializers/current_user_serializer_spec.rb
+++ b/spec/serializers/current_user_serializer_spec.rb
@@ -68,6 +68,38 @@ RSpec.describe CurrentUserSerializer do
end
end
+ context "#second_factor_enabled" do
+ fab!(:user) { Fabricate(:user) }
+ let :serializer do
+ CurrentUserSerializer.new(user, scope: Guardian.new(user), root: false)
+ end
+ let(:json) { serializer.as_json }
+
+ it "is false by default" do
+ expect(json[:second_factor_enabled]).to eq(false)
+ end
+
+ context "when totp enabled" do
+ before do
+ User.any_instance.stubs(:totp_enabled?).returns(true)
+ end
+
+ it "is true" do
+ expect(json[:second_factor_enabled]).to eq(true)
+ end
+ end
+
+ context "when security_keys enabled" do
+ before do
+ User.any_instance.stubs(:security_keys_enabled?).returns(true)
+ end
+
+ it "is true" do
+ expect(json[:second_factor_enabled]).to eq(true)
+ end
+ end
+ end
+
context "#groups" do
fab!(:member) { Fabricate(:user) }
let :serializer do
diff --git a/spec/serializers/user_serializer_spec.rb b/spec/serializers/user_serializer_spec.rb
index 262166422a..fbe25589db 100644
--- a/spec/serializers/user_serializer_spec.rb
+++ b/spec/serializers/user_serializer_spec.rb
@@ -40,8 +40,9 @@ describe UserSerializer do
end
context "with a user" do
+ let(:scope) { Guardian.new }
fab!(:user) { Fabricate(:user) }
- let(:serializer) { UserSerializer.new(user, scope: Guardian.new, root: false) }
+ let(:serializer) { UserSerializer.new(user, scope: scope, root: false) }
let(:json) { serializer.as_json }
fab!(:upload) { Fabricate(:upload) }
fab!(:upload2) { Fabricate(:upload) }
@@ -164,6 +165,33 @@ describe UserSerializer do
expect(json[:bio_cooked]).to eq 'my cooked bio'
end
end
+
+ describe "second_factor_enabled" do
+ let(:scope) { Guardian.new(user) }
+ it "is false by default" do
+ expect(json[:second_factor_enabled]).to eq(false)
+ end
+
+ context "when totp enabled" do
+ before do
+ User.any_instance.stubs(:totp_enabled?).returns(true)
+ end
+
+ it "is true" do
+ expect(json[:second_factor_enabled]).to eq(true)
+ end
+ end
+
+ context "when security_keys enabled" do
+ before do
+ User.any_instance.stubs(:security_keys_enabled?).returns(true)
+ end
+
+ it "is true" do
+ expect(json[:second_factor_enabled]).to eq(true)
+ end
+ end
+ end
end
context "with custom_fields" do
From 56d3e29a698e704f647cf2e500d0d94d7d9e21bf Mon Sep 17 00:00:00 2001
From: Martin Brennan
Date: Fri, 8 Nov 2019 15:34:24 +1000
Subject: [PATCH 031/408] FIX: Badge and user title interaction fixes (#8282)
* Fix user title logic when badge name customized
* Fix an issue where a user's title was not considered a badge granted title when the user used a badge for their title and the badge name was customized. this affected the effectiveness of revoke_ungranted_titles! which only operates on badge_granted_titles.
* When a user's title is set now it is considered a badge_granted_title if the badge name OR the badge custom name from TranslationOverride is the same as the title
* When a user's badge is revoked we now also revoke their title if the user's title matches the badge name OR the badge custom name from TranslationOverride
* Add a user history log when the title is revoked to remove confusion about why titles are revoked
* Add granted_title_badge_id to user_profile, now when we set badge_granted_title on a user profile when updating a user's title based on a badge, we also remember which badge matched the title
* When badge name (or custom text) changes update titles of users in a background job
* When the name of a badge changes, or in the case of system badges when their custom translation text changes, then we need to update the title of all corresponding users who have a badge_granted_title and matching granted_title_badge_id. In the case of system badges we need to first get the proper badge ID based on the translation key e.g. badges.regular.name
* Add migration to backfill all granted_title_badge_ids for both normal badge name titles and titles using custom badge text.
---
app/controllers/admin/badges_controller.rb | 9 ++++
.../admin/site_texts_controller.rb | 24 +++++++--
app/controllers/users_controller.rb | 26 +++++++++-
app/jobs/regular/bulk_user_title_update.rb | 51 +++++++++++++++++++
app/models/badge.rb | 17 ++++++-
app/models/user.rb | 9 +++-
app/models/user_history.rb | 6 ++-
app/models/user_profile.rb | 4 ++
app/services/badge_granter.rb | 15 +++++-
app/services/staff_action_logger.rb | 21 ++++++++
config/locales/client.en.yml | 2 +
..._granted_title_badge_id_to_user_profile.rb | 35 +++++++++++++
.../regular/bulk_user_title_update_spec.rb | 50 ++++++++++++++++++
spec/models/badge_spec.rb | 27 ++++++++++
spec/models/user_spec.rb | 24 +++++++++
spec/requests/admin/badges_controller_spec.rb | 23 +++++++++
.../admin/site_texts_controller_spec.rb | 31 +++++++++++
spec/requests/users_controller_spec.rb | 10 +++-
spec/services/badge_granter_spec.rb | 27 ++++++++++
19 files changed, 397 insertions(+), 14 deletions(-)
create mode 100644 app/jobs/regular/bulk_user_title_update.rb
create mode 100644 db/migrate/20191031052711_add_granted_title_badge_id_to_user_profile.rb
create mode 100644 spec/jobs/regular/bulk_user_title_update_spec.rb
diff --git a/app/controllers/admin/badges_controller.rb b/app/controllers/admin/badges_controller.rb
index 0a1b741fd4..fe67475e26 100644
--- a/app/controllers/admin/badges_controller.rb
+++ b/app/controllers/admin/badges_controller.rb
@@ -125,6 +125,15 @@ class Admin::BadgesController < Admin::AdminController
badge.save!
end
+ if opts[:new].blank?
+ Jobs.enqueue(
+ :bulk_user_title_update,
+ new_title: badge.name,
+ granted_badge_id: badge.id,
+ action: Jobs::BulkUserTitleUpdate::UPDATE_ACTION
+ )
+ end
+
errors
rescue ActiveRecord::RecordInvalid
errors.push(*badge.errors.full_messages)
diff --git a/app/controllers/admin/site_texts_controller.rb b/app/controllers/admin/site_texts_controller.rb
index ef594471d9..0f9d7bad65 100644
--- a/app/controllers/admin/site_texts_controller.rb
+++ b/app/controllers/admin/site_texts_controller.rb
@@ -59,6 +59,15 @@ class Admin::SiteTextsController < Admin::AdminController
if translation_override.errors.empty?
StaffActionLogger.new(current_user).log_site_text_change(id, value, old_value)
+ system_badge_id = Badge.find_system_badge_id_from_translation_key(id)
+ if system_badge_id.present?
+ Jobs.enqueue(
+ :bulk_user_title_update,
+ new_title: value,
+ granted_badge_id: system_badge_id,
+ action: Jobs::BulkUserTitleUpdate::UPDATE_ACTION
+ )
+ end
render_serialized(site_text, SiteTextSerializer, root: 'site_text', rest_serializer: true)
else
render json: failed_json.merge(
@@ -69,10 +78,19 @@ class Admin::SiteTextsController < Admin::AdminController
def revert
site_text = find_site_text
- old_text = I18n.t(site_text[:id])
- TranslationOverride.revert!(I18n.locale, site_text[:id])
+ id = site_text[:id]
+ old_text = I18n.t(id)
+ TranslationOverride.revert!(I18n.locale, id)
site_text = find_site_text
- StaffActionLogger.new(current_user).log_site_text_change(site_text[:id], site_text[:value], old_text)
+ StaffActionLogger.new(current_user).log_site_text_change(id, site_text[:value], old_text)
+ system_badge_id = Badge.find_system_badge_id_from_translation_key(id)
+ if system_badge_id.present?
+ Jobs.enqueue(
+ :bulk_user_title_update,
+ granted_badge_id: system_badge_id,
+ action: Jobs::BulkUserTitleUpdate::RESET_ACTION
+ )
+ end
render_serialized(site_text, SiteTextSerializer, root: 'site_text', rest_serializer: true)
end
diff --git a/app/controllers/users_controller.rb b/app/controllers/users_controller.rb
index 5498a9933b..5a113ca717 100644
--- a/app/controllers/users_controller.rb
+++ b/app/controllers/users_controller.rb
@@ -195,14 +195,36 @@ class UsersController < ApplicationController
guardian.ensure_can_edit!(user)
user_badge = UserBadge.find_by(id: params[:user_badge_id])
+ previous_title = user.title
if user_badge && user_badge.user == user && user_badge.badge.allow_title?
user.title = user_badge.badge.display_name
- user.user_profile.badge_granted_title = true
user.save!
- user.user_profile.save!
+
+ log_params = {
+ details: "title matching badge id #{user_badge.badge.id}",
+ previous_value: previous_title,
+ new_value: user.title
+ }
+
+ if current_user.staff? && current_user != user
+ StaffActionLogger.new(current_user).log_title_change(user, log_params)
+ else
+ UserHistory.create!(log_params.merge(target_user_id: user.id, action: UserHistory.actions[:change_title]))
+ end
else
user.title = ''
user.save!
+
+ log_params = {
+ revoke_reason: 'user title was same as revoked badge name or custom badge name',
+ previous_value: previous_title
+ }
+
+ if current_user.staff? && current_user != user
+ StaffActionLogger.new(current_user).log_title_revoke(user, log_params)
+ else
+ UserHistory.create!(log_params.merge(target_user_id: user.id, action: UserHistory.actions[:revoke_title]))
+ end
end
render body: nil
diff --git a/app/jobs/regular/bulk_user_title_update.rb b/app/jobs/regular/bulk_user_title_update.rb
new file mode 100644
index 0000000000..97d3f68ad5
--- /dev/null
+++ b/app/jobs/regular/bulk_user_title_update.rb
@@ -0,0 +1,51 @@
+# frozen_string_literal: true
+
+module Jobs
+ class BulkUserTitleUpdate < ::Jobs::Base
+ UPDATE_ACTION = 'update'.freeze
+ RESET_ACTION = 'reset'.freeze
+
+ def execute(args)
+ new_title = args[:new_title]
+ granted_badge_id = args[:granted_badge_id]
+ action = args[:action]
+
+ case action
+ when UPDATE_ACTION
+ update_titles_for_granted_badge(new_title, granted_badge_id)
+ when RESET_ACTION
+ reset_titles_for_granted_badge(granted_badge_id)
+ end
+ end
+
+ private
+
+ ##
+ # If a badge name or a system badge TranslationOverride changes
+ # then we need to set all titles granted based on that badge to
+ # the new name or custom translation
+ def update_titles_for_granted_badge(new_title, granted_badge_id)
+ DB.exec(<<~SQL, granted_title_badge_id: granted_badge_id, title: new_title, updated_at: Time.now)
+ UPDATE users AS u
+ SET title = :title, updated_at = :updated_at
+ FROM user_profiles AS up
+ WHERE up.user_id = u.id AND up.granted_title_badge_id = :granted_title_badge_id
+ SQL
+ end
+
+ ##
+ # Reset granted titles for a badge back to the original
+ # badge name. When a system badge has its TranslationOverride
+ # revoked we want to have all titles based on that translation
+ # for the badge reset.
+ def reset_titles_for_granted_badge(granted_badge_id)
+ DB.exec(<<~SQL, granted_title_badge_id: granted_badge_id, updated_at: Time.now)
+ UPDATE users AS u
+ SET title = badges.name, updated_at = :updated_at
+ FROM user_profiles AS up
+ INNER JOIN badges ON badges.id = up.granted_title_badge_id
+ WHERE up.user_id = u.id AND up.granted_title_badge_id = :granted_title_badge_id
+ SQL
+ end
+ end
+end
diff --git a/app/models/badge.rb b/app/models/badge.rb
index 3596190a8a..4db471bcbe 100644
--- a/app/models/badge.rb
+++ b/app/models/badge.rb
@@ -169,8 +169,17 @@ class Badge < ActiveRecord::Base
end
def self.display_name(name)
- key = "badges.#{i18n_name(name)}.name"
- I18n.t(key, default: name)
+ I18n.t(i18n_key(name), default: name)
+ end
+
+ def self.i18n_key(name)
+ "badges.#{i18n_name(name)}.name"
+ end
+
+ def self.find_system_badge_id_from_translation_key(translation_key)
+ return unless translation_key.starts_with?('badges.')
+ badge_name_klass = translation_key.split('.').second.camelize
+ "Badge::#{badge_name_klass}".constantize
end
def awarded_for_trust_level?
@@ -208,6 +217,10 @@ class Badge < ActiveRecord::Base
self.class.display_name(name)
end
+ def translation_key
+ self.class.i18n_key(name)
+ end
+
def long_description
key = "badges.#{i18n_name}.long_description"
I18n.t(key, default: self[:long_description] || '', base_uri: Discourse.base_uri)
diff --git a/app/models/user.rb b/app/models/user.rb
index 2ecea38aad..a742682011 100644
--- a/app/models/user.rb
+++ b/app/models/user.rb
@@ -1478,8 +1478,13 @@ class User < ActiveRecord::Base
def check_if_title_is_badged_granted
if title_changed? && !new_record? && user_profile
- badge_granted_title = title.present? && badges.where(allow_title: true, name: title).exists?
- user_profile.update_column(:badge_granted_title, badge_granted_title)
+ badge_matching_title = title && badges.find do |badge|
+ badge.allow_title? && (badge.display_name == title || badge.name == title)
+ end
+ user_profile.update(
+ badge_granted_title: badge_matching_title.present?,
+ granted_title_badge_id: badge_matching_title&.id
+ )
end
end
diff --git a/app/models/user_history.rb b/app/models/user_history.rb
index ec6fec4f11..dcb11d5ea6 100644
--- a/app/models/user_history.rb
+++ b/app/models/user_history.rb
@@ -101,6 +101,8 @@ class UserHistory < ActiveRecord::Base
api_key_create: 80,
api_key_update: 81,
api_key_destroy: 82,
+ revoke_title: 83,
+ change_title: 84
)
end
@@ -175,9 +177,11 @@ class UserHistory < ActiveRecord::Base
:change_theme_setting,
:disable_theme_component,
:enable_theme_component,
+ :revoke_title,
+ :change_title,
:api_key_create,
:api_key_update,
- :api_key_destroy,
+ :api_key_destroy
]
end
diff --git a/app/models/user_profile.rb b/app/models/user_profile.rb
index 7f16cfe90e..ed50e90853 100644
--- a/app/models/user_profile.rb
+++ b/app/models/user_profile.rb
@@ -9,6 +9,7 @@ class UserProfile < ActiveRecord::Base
belongs_to :user, inverse_of: :user_profile
belongs_to :card_background_upload, class_name: "Upload"
belongs_to :profile_background_upload, class_name: "Upload"
+ belongs_to :granted_title_badge, class_name: "Badge"
validates :bio_raw, length: { maximum: 3000 }
validates :website, url: true, allow_blank: true, if: Proc.new { |c| c.new_record? || c.website_changed? }
@@ -161,15 +162,18 @@ end
# views :integer default(0), not null
# profile_background_upload_id :integer
# card_background_upload_id :integer
+# granted_title_badge_id :integer
#
# Indexes
#
# index_user_profiles_on_bio_cooked_version (bio_cooked_version)
# index_user_profiles_on_card_background (card_background)
# index_user_profiles_on_profile_background (profile_background)
+# index_user_profiles_on_granted_title_badge_id (granted_title_badge)
#
# Foreign Keys
#
# fk_rails_... (card_background_upload_id => uploads.id)
# fk_rails_... (profile_background_upload_id => uploads.id)
+# fk_rails_... (granted_title_badge_id => badges.id)
#
diff --git a/app/services/badge_granter.rb b/app/services/badge_granter.rb
index b2f302f954..c7c6049ddb 100644
--- a/app/services/badge_granter.rb
+++ b/app/services/badge_granter.rb
@@ -72,8 +72,19 @@ class BadgeGranter
StaffActionLogger.new(options[:revoked_by]).log_badge_revoke(user_badge)
end
- # If the user's title is the same as the badge name, remove their title.
- if user_badge.user.title == user_badge.badge.name
+ # If the user's title is the same as the badge name OR the custom badge name, remove their title.
+ custom_badge_name = TranslationOverride.find_by(translation_key: user_badge.badge.translation_key)&.value
+ user_title_is_badge_name = user_badge.user.title == user_badge.badge.name
+ user_title_is_custom_badge_name = custom_badge_name.present? && user_badge.user.title == custom_badge_name
+
+ if user_title_is_badge_name || user_title_is_custom_badge_name
+ if options[:revoked_by]
+ StaffActionLogger.new(options[:revoked_by]).log_title_revoke(
+ user_badge.user,
+ revoke_reason: 'user title was same as revoked badge name or custom badge name',
+ previous_value: user_badge.user.title
+ )
+ end
user_badge.user.title = nil
user_badge.user.save!
end
diff --git a/app/services/staff_action_logger.rb b/app/services/staff_action_logger.rb
index f6264da3eb..c6cbb48d0f 100644
--- a/app/services/staff_action_logger.rb
+++ b/app/services/staff_action_logger.rb
@@ -352,6 +352,27 @@ class StaffActionLogger
))
end
+ def log_title_revoke(user, opts = {})
+ raise Discourse::InvalidParameters.new(:user) unless user
+ UserHistory.create!(params(opts).merge(
+ action: UserHistory.actions[:revoke_title],
+ target_user_id: user.id,
+ details: opts[:revoke_reason],
+ previous_value: opts[:previous_value]
+ ))
+ end
+
+ def log_title_change(user, opts = {})
+ raise Discourse::InvalidParameters.new(:user) unless user
+ UserHistory.create!(params(opts).merge(
+ action: UserHistory.actions[:change_title],
+ target_user_id: user.id,
+ details: opts[:details],
+ new_value: opts[:new_value],
+ previous_value: opts[:previous_value]
+ ))
+ end
+
def log_check_email(user, opts = {})
raise Discourse::InvalidParameters.new(:user) unless user
UserHistory.create!(params(opts).merge(
diff --git a/config/locales/client.en.yml b/config/locales/client.en.yml
index 125fae8223..e2eeb2590d 100644
--- a/config/locales/client.en.yml
+++ b/config/locales/client.en.yml
@@ -3930,6 +3930,8 @@ en:
change_theme_setting: "change theme setting"
disable_theme_component: "disable theme component"
enable_theme_component: "enable theme component"
+ revoke_title: "revoke title"
+ change_title: "change title"
api_key_create: "api key create"
api_key_update: "api key update"
api_key_destroy: "api key destroy"
diff --git a/db/migrate/20191031052711_add_granted_title_badge_id_to_user_profile.rb b/db/migrate/20191031052711_add_granted_title_badge_id_to_user_profile.rb
new file mode 100644
index 0000000000..f76ea34ef4
--- /dev/null
+++ b/db/migrate/20191031052711_add_granted_title_badge_id_to_user_profile.rb
@@ -0,0 +1,35 @@
+# frozen_string_literal: true
+
+class AddGrantedTitleBadgeIdToUserProfile < ActiveRecord::Migration[6.0]
+ def up
+ add_reference :user_profiles, :granted_title_badge, foreign_key: { to_table: :badges }, index: true, null: true
+
+ # update all the regular badge derived titles based
+ # on the normal badge name
+ ActiveRecord::Base.connection.execute <<-SQL
+ UPDATE user_profiles
+ SET granted_title_badge_id = b.id
+ FROM users
+ INNER JOIN badges b ON users.title = b.name
+ WHERE users.id = user_profiles.user_id
+ AND user_profiles.granted_title_badge_id IS NULL
+ SQL
+
+ # update all of the system badge derived titles where the
+ # badge has had custom text set for it via TranslationOverride
+ ActiveRecord::Base.connection.execute <<-SQL
+ UPDATE user_profiles
+ SET granted_title_badge_id = badges.id
+ FROM users
+ JOIN translation_overrides ON translation_overrides.value = users.title
+ JOIN badges ON ('badges.' || LOWER(REPLACE(badges.name, ' ', '_')) || '.name') = translation_overrides.translation_key
+ JOIN user_badges ON user_badges.user_id = users.id AND user_badges.badge_id = badges.id
+ WHERE users.id = user_profiles.user_id
+ AND user_profiles.granted_title_badge_id IS NULL
+ SQL
+ end
+
+ def down
+ remove_column :user_profiles, :granted_title_badge_id
+ end
+end
diff --git a/spec/jobs/regular/bulk_user_title_update_spec.rb b/spec/jobs/regular/bulk_user_title_update_spec.rb
new file mode 100644
index 0000000000..f6cf97eb38
--- /dev/null
+++ b/spec/jobs/regular/bulk_user_title_update_spec.rb
@@ -0,0 +1,50 @@
+# frozen_string_literal: true
+
+require 'rails_helper'
+
+describe Jobs::BulkUserTitleUpdate do
+ fab!(:badge) { Fabricate(:badge, name: 'Protector of the Realm', allow_title: true) }
+ fab!(:user) { Fabricate(:user) }
+ fab!(:other_user) { Fabricate(:user) }
+
+ describe 'update action' do
+ before do
+ BadgeGranter.grant(badge, user)
+ user.update(title: badge.name)
+ end
+
+ it 'updates the title of all users with the attached granted title badge id on their profile' do
+ execute_update
+ expect(user.reload.title).to eq('King of the Forum')
+ end
+
+ it 'does not set the title for any other users' do
+ execute_update
+ expect(other_user.reload.title).not_to eq('King of the Forum')
+ end
+
+ def execute_update
+ described_class.new.execute(new_title: 'King of the Forum', granted_badge_id: badge.id, action: described_class::UPDATE_ACTION)
+ end
+ end
+
+ describe 'reset action' do
+ let(:customized_badge_name) { 'Merit Badge' }
+
+ before do
+ TranslationOverride.upsert!(I18n.locale, Badge.i18n_key(badge.name), customized_badge_name)
+ BadgeGranter.grant(badge, user)
+ user.update(title: customized_badge_name)
+ end
+
+ it 'updates the title of all users back to the original badge name' do
+ expect(user.reload.title).to eq(customized_badge_name)
+ described_class.new.execute(granted_badge_id: badge.id, action: described_class::RESET_ACTION)
+ expect(user.reload.title).to eq('Protector of the Realm')
+ end
+
+ after do
+ TranslationOverride.revert!(I18n.locale, Badge.i18n_key(badge.name))
+ end
+ end
+end
diff --git a/spec/models/badge_spec.rb b/spec/models/badge_spec.rb
index 41cf3edcfd..bd1639a69c 100644
--- a/spec/models/badge_spec.rb
+++ b/spec/models/badge_spec.rb
@@ -95,6 +95,33 @@ describe Badge do
end
end
+ describe '.find_system_badge_id_from_translation_key' do
+ let(:translation_key) { 'badges.regular.name' }
+
+ it 'uses a translation key to get a system badge id, mainly to find which badge a translation override corresponds to' do
+ expect(Badge.find_system_badge_id_from_translation_key(translation_key)).to eq(
+ Badge::Regular
+ )
+ end
+
+ context 'when the translation key is snake case' do
+ let(:translation_key) { 'badges.crazy_in_love.name' }
+
+ it 'works to get the badge' do
+ expect(Badge.find_system_badge_id_from_translation_key(translation_key)).to eq(
+ Badge::CrazyInLove
+ )
+ end
+ end
+
+ context 'when a translation key not for a badge is provided' do
+ let(:translation_key) { 'reports.flags.title' }
+ it 'returns nil' do
+ expect(Badge.find_system_badge_id_from_translation_key(translation_key)).to eq(nil)
+ end
+ end
+ end
+
context "First Quote" do
let(:quoted_post_badge) do
Badge.find(Badge::FirstQuote)
diff --git a/spec/models/user_spec.rb b/spec/models/user_spec.rb
index 73eb8d7cac..f34a895b44 100644
--- a/spec/models/user_spec.rb
+++ b/spec/models/user_spec.rb
@@ -1957,11 +1957,35 @@ describe User do
expect(user.user_profile.reload.badge_granted_title).to eq(false)
badge.update!(allow_title: true)
+ user.badges.reload
user.update!(title: badge.name)
expect(user.user_profile.reload.badge_granted_title).to eq(true)
+ expect(user.user_profile.reload.granted_title_badge_id).to eq(badge.id)
user.update!(title: nil)
expect(user.user_profile.reload.badge_granted_title).to eq(false)
+ expect(user.user_profile.granted_title_badge_id).to eq(nil)
+ end
+
+ context 'when a custom badge name has been set and it matches the title' do
+ let(:customized_badge_name) { 'Merit Badge' }
+
+ before do
+ TranslationOverride.upsert!(I18n.locale, Badge.i18n_key(badge.name), customized_badge_name)
+ end
+
+ it 'sets badge_granted_title correctly' do
+ BadgeGranter.grant(badge, user)
+
+ badge.update!(allow_title: true)
+ user.update!(title: customized_badge_name)
+ expect(user.user_profile.reload.badge_granted_title).to eq(true)
+ expect(user.user_profile.reload.granted_title_badge_id).to eq(badge.id)
+ end
+
+ after do
+ TranslationOverride.revert!(I18n.locale, Badge.i18n_key(badge.name))
+ end
end
end
diff --git a/spec/requests/admin/badges_controller_spec.rb b/spec/requests/admin/badges_controller_spec.rb
index a13af50bc9..5ea9d5fd14 100644
--- a/spec/requests/admin/badges_controller_spec.rb
+++ b/spec/requests/admin/badges_controller_spec.rb
@@ -153,6 +153,29 @@ describe Admin::BadgesController do
expect(badge.name).to eq('123456')
expect(badge.query).to eq(sql)
end
+
+ context 'when there is a user with a title granted using the badge' do
+ fab!(:user_with_badge_title) { Fabricate(:active_user) }
+ fab!(:badge) { Fabricate(:badge, name: 'Oathbreaker', allow_title: true) }
+
+ before do
+ BadgeGranter.grant(badge, user_with_badge_title)
+ user_with_badge_title.update(title: 'Oathbreaker')
+ end
+
+ it 'updates the user title in a job' do
+ Jobs.expects(:enqueue).with(
+ :bulk_user_title_update,
+ new_title: 'Shieldbearer',
+ granted_badge_id: badge.id,
+ action: Jobs::BulkUserTitleUpdate::UPDATE_ACTION
+ )
+
+ put "/admin/badges/#{badge.id}.json", params: {
+ name: "Shieldbearer"
+ }
+ end
+ end
end
end
end
diff --git a/spec/requests/admin/site_texts_controller_spec.rb b/spec/requests/admin/site_texts_controller_spec.rb
index fcc3be2aed..356dcfc07c 100644
--- a/spec/requests/admin/site_texts_controller_spec.rb
+++ b/spec/requests/admin/site_texts_controller_spec.rb
@@ -415,6 +415,37 @@ RSpec.describe Admin::SiteTextsController do
json = ::JSON.parse(response.body)
expect(json['site_text']['value']).to_not eq(ru_mf_text)
end
+
+ context 'when updating a translation override for a system badge' do
+ fab!(:user_with_badge_title) { Fabricate(:active_user) }
+ let(:badge) { Badge.find(Badge::Regular) }
+
+ before do
+ BadgeGranter.grant(badge, user_with_badge_title)
+ user_with_badge_title.update(title: 'Regular')
+ end
+
+ it 'updates matching user titles to the override text in a job' do
+ Jobs.expects(:enqueue).with(
+ :bulk_user_title_update,
+ new_title: 'Terminator',
+ granted_badge_id: badge.id,
+ action: Jobs::BulkUserTitleUpdate::UPDATE_ACTION
+ )
+ put '/admin/customize/site_texts/badges.regular.name.json', params: {
+ site_text: { value: 'Terminator' }
+ }
+
+ Jobs.expects(:enqueue).with(
+ :bulk_user_title_update,
+ granted_badge_id: badge.id,
+ action: Jobs::BulkUserTitleUpdate::RESET_ACTION
+ )
+
+ # Revert
+ delete "/admin/customize/site_texts/badges.regular.name.json"
+ end
+ end
end
context "reseeding" do
diff --git a/spec/requests/users_controller_spec.rb b/spec/requests/users_controller_spec.rb
index 0d454970f3..276901b6d1 100644
--- a/spec/requests/users_controller_spec.rb
+++ b/spec/requests/users_controller_spec.rb
@@ -1911,11 +1911,17 @@ describe UsersController do
expect(user.reload.title).to eq(badge.display_name)
expect(user.user_profile.badge_granted_title).to eq(true)
+ expect(user.user_profile.granted_title_badge_id).to eq(badge.id)
- user.title = "testing"
- user.save
+ badge.update allow_title: false
+
+ put "/u/#{user.username}/preferences/badge_title.json", params: { user_badge_id: user_badge.id }
+
+ user.reload
user.user_profile.reload
+ expect(user.title).to eq('')
expect(user.user_profile.badge_granted_title).to eq(false)
+ expect(user.user_profile.granted_title_badge_id).to eq(nil)
end
context "with overrided name" do
diff --git a/spec/services/badge_granter_spec.rb b/spec/services/badge_granter_spec.rb
index 5063cba02b..1606a27ea8 100644
--- a/spec/services/badge_granter_spec.rb
+++ b/spec/services/badge_granter_spec.rb
@@ -196,6 +196,33 @@ describe BadgeGranter do
expect(user.reload.title).to eq(nil)
end
+ context 'when the badge name is customized, and the customized name is the same as the user title' do
+ let(:customized_badge_name) { 'Merit Badge' }
+
+ before do
+ TranslationOverride.upsert!(I18n.locale, Badge.i18n_key(badge.name), customized_badge_name)
+ end
+
+ it 'revokes the badge and title and does necessary cleanup' do
+ user.title = customized_badge_name; user.save!
+ expect(badge.reload.grant_count).to eq(1)
+ StaffActionLogger.any_instance.expects(:log_badge_revoke).with(user_badge)
+ StaffActionLogger.any_instance.expects(:log_title_revoke).with(
+ user,
+ revoke_reason: 'user title was same as revoked badge name or custom badge name',
+ previous_value: user_badge.user.title
+ )
+ BadgeGranter.revoke(user_badge, revoked_by: admin)
+ expect(UserBadge.find_by(user: user, badge: badge)).not_to be_present
+ expect(badge.reload.grant_count).to eq(0)
+ expect(user.notifications.where(notification_type: Notification.types[:granted_badge])).to be_empty
+ expect(user.reload.title).to eq(nil)
+ end
+
+ after do
+ TranslationOverride.revert!(I18n.locale, Badge.i18n_key(badge.name))
+ end
+ end
end
context "update_badges" do
From 26c0199c018cb934d1eca1650337db5177aa2b32 Mon Sep 17 00:00:00 2001
From: Sam Saffron
Date: Fri, 8 Nov 2019 16:56:30 +1100
Subject: [PATCH 032/408] DEV: update Rails to version 6.0.1
This version of Rails eliminates a monkey patch that is no longer needed!
Additionally it preps us for Ruby 2.7 support.
---
Gemfile | 14 +++----
Gemfile.lock | 70 +++++++++++++++++------------------
lib/freedom_patches/rails6.rb | 57 ----------------------------
3 files changed, 42 insertions(+), 99 deletions(-)
delete mode 100644 lib/freedom_patches/rails6.rb
diff --git a/Gemfile b/Gemfile
index 2e1ce26cc9..6d4182e56c 100644
--- a/Gemfile
+++ b/Gemfile
@@ -16,13 +16,13 @@ if rails_master?
else
# until rubygems gives us optional dependencies we are stuck with this
# bundle update actionmailer actionpack actionview activemodel activerecord activesupport railties
- gem 'actionmailer', '6.0.0'
- gem 'actionpack', '6.0.0'
- gem 'actionview', '6.0.0'
- gem 'activemodel', '6.0.0'
- gem 'activerecord', '6.0.0'
- gem 'activesupport', '6.0.0'
- gem 'railties', '6.0.0'
+ gem 'actionmailer', '6.0.1'
+ gem 'actionpack', '6.0.1'
+ gem 'actionview', '6.0.1'
+ gem 'activemodel', '6.0.1'
+ gem 'activerecord', '6.0.1'
+ gem 'activesupport', '6.0.1'
+ gem 'railties', '6.0.1'
gem 'sprockets-rails'
end
diff --git a/Gemfile.lock b/Gemfile.lock
index 704a6e0e5b..1201ee9715 100644
--- a/Gemfile.lock
+++ b/Gemfile.lock
@@ -1,21 +1,21 @@
GEM
remote: https://rubygems.org/
specs:
- actionmailer (6.0.0)
- actionpack (= 6.0.0)
- actionview (= 6.0.0)
- activejob (= 6.0.0)
+ actionmailer (6.0.1)
+ actionpack (= 6.0.1)
+ actionview (= 6.0.1)
+ activejob (= 6.0.1)
mail (~> 2.5, >= 2.5.4)
rails-dom-testing (~> 2.0)
- actionpack (6.0.0)
- actionview (= 6.0.0)
- activesupport (= 6.0.0)
+ actionpack (6.0.1)
+ actionview (= 6.0.1)
+ activesupport (= 6.0.1)
rack (~> 2.0)
rack-test (>= 0.6.3)
rails-dom-testing (~> 2.0)
rails-html-sanitizer (~> 1.0, >= 1.2.0)
- actionview (6.0.0)
- activesupport (= 6.0.0)
+ actionview (6.0.1)
+ activesupport (= 6.0.1)
builder (~> 3.1)
erubi (~> 1.4)
rails-dom-testing (~> 2.0)
@@ -24,20 +24,20 @@ GEM
actionview (>= 6.0.a)
active_model_serializers (0.8.4)
activemodel (>= 3.0)
- activejob (6.0.0)
- activesupport (= 6.0.0)
+ activejob (6.0.1)
+ activesupport (= 6.0.1)
globalid (>= 0.3.6)
- activemodel (6.0.0)
- activesupport (= 6.0.0)
- activerecord (6.0.0)
- activemodel (= 6.0.0)
- activesupport (= 6.0.0)
- activesupport (6.0.0)
+ activemodel (6.0.1)
+ activesupport (= 6.0.1)
+ activerecord (6.0.1)
+ activemodel (= 6.0.1)
+ activesupport (= 6.0.1)
+ activesupport (6.0.1)
concurrent-ruby (~> 1.0, >= 1.0.2)
i18n (>= 0.7, < 2)
minitest (~> 5.1)
tzinfo (~> 1.1)
- zeitwerk (~> 2.1, >= 2.1.8)
+ zeitwerk (~> 2.2)
addressable (2.5.2)
public_suffix (>= 2.0.2, < 4.0)
annotate (2.7.5)
@@ -119,7 +119,7 @@ GEM
jquery-rails (>= 1.0.17)
railties (>= 3.1)
ember-source (2.18.2)
- erubi (1.8.0)
+ erubi (1.9.0)
excon (0.64.0)
execjs (2.7.0)
exifr (1.3.6)
@@ -146,7 +146,7 @@ GEM
hkdf (0.3.0)
htmlentities (4.3.4)
http_accept_language (2.0.5)
- i18n (1.6.0)
+ i18n (1.7.0)
concurrent-ruby (~> 1.0)
image_size (1.5.0)
in_threads (1.5.1)
@@ -195,7 +195,7 @@ GEM
mini_sql (0.2.2)
mini_suffix (0.3.0)
ffi (~> 1.9)
- minitest (5.11.3)
+ minitest (5.13.0)
mocha (1.8.0)
metaclass (~> 0.0.1)
mock_redis (0.19.0)
@@ -204,7 +204,7 @@ GEM
multi_xml (0.6.0)
multipart-post (2.1.1)
mustache (1.1.0)
- nokogiri (1.10.4)
+ nokogiri (1.10.5)
mini_portile2 (~> 2.4.0)
nokogumbo (2.0.1)
nokogiri (~> 1.8, >= 1.8.4)
@@ -283,14 +283,14 @@ GEM
rails-dom-testing (2.0.3)
activesupport (>= 4.2.0)
nokogiri (>= 1.6)
- rails-html-sanitizer (1.2.0)
- loofah (~> 2.2, >= 2.2.2)
+ rails-html-sanitizer (1.3.0)
+ loofah (~> 2.3)
rails_multisite (2.0.7)
activerecord (> 4.2, < 7)
railties (> 4.2, < 7)
- railties (6.0.0)
- actionpack (= 6.0.0)
- activesupport (= 6.0.0)
+ railties (6.0.1)
+ actionpack (= 6.0.1)
+ activesupport (= 6.0.1)
method_source
rake (>= 0.8.7)
thor (>= 0.20.3, < 2.0)
@@ -418,20 +418,20 @@ GEM
hkdf (~> 0.2)
jwt (~> 2.0)
yaml-lint (0.0.10)
- zeitwerk (2.1.10)
+ zeitwerk (2.2.1)
PLATFORMS
ruby
DEPENDENCIES
- actionmailer (= 6.0.0)
- actionpack (= 6.0.0)
- actionview (= 6.0.0)
+ actionmailer (= 6.0.1)
+ actionpack (= 6.0.1)
+ actionview (= 6.0.1)
actionview_precompiler
active_model_serializers (~> 0.8.3)
- activemodel (= 6.0.0)
- activerecord (= 6.0.0)
- activesupport (= 6.0.0)
+ activemodel (= 6.0.1)
+ activerecord (= 6.0.1)
+ activesupport (= 6.0.1)
annotate
aws-sdk-s3
aws-sdk-sns
@@ -508,7 +508,7 @@ DEPENDENCIES
rack-mini-profiler
rack-protection
rails_multisite
- railties (= 6.0.0)
+ railties (= 6.0.1)
rake
rb-fsevent
rb-inotify (~> 0.9)
diff --git a/lib/freedom_patches/rails6.rb b/lib/freedom_patches/rails6.rb
deleted file mode 100644
index cf2f96de05..0000000000
--- a/lib/freedom_patches/rails6.rb
+++ /dev/null
@@ -1,57 +0,0 @@
-# frozen_string_literal: true
-
-# see: https://github.com/rails/rails/pull/36949#issuecomment-530698779
-#
-# Without this patch each time we close a DB connection we spin a thread
-
-module ::ActiveRecord
- module ConnectionAdapters
- class AbstractAdapter
- class StaticThreadLocalVar
- attr_reader :value
-
- def initialize(value)
- @value = value
- end
-
- def bind(value)
- raise "attempting to change immutable local var" if value != @value
- if block_given?
- yield
- end
- end
- end
-
- # we have no choice but to perform an aggressive patch here
- # if we simply hook the method we will still call a finalizer
- # on Concurrent::ThreadLocalVar
-
- def initialize(connection, logger = nil, config = {}) # :nodoc:
- super()
-
- @connection = connection
- @owner = nil
- @instrumenter = ActiveSupport::Notifications.instrumenter
- @logger = logger
- @config = config
- @pool = ActiveRecord::ConnectionAdapters::NullPool.new
- @idle_since = Concurrent.monotonic_time
- @visitor = arel_visitor
- @statements = build_statement_pool
- @lock = ActiveSupport::Concurrency::LoadInterlockAwareMonitor.new
-
- if self.class.type_cast_config_to_boolean(config.fetch(:prepared_statements) { true })
- @prepared_statement_status = Concurrent::ThreadLocalVar.new(true)
- @visitor.extend(DetermineIfPreparableVisitor)
- else
- #@prepared_statement_status = Concurrent::ThreadLocalVar.new(false)
- @prepared_statement_status = StaticThreadLocalVar.new(false)
- end
-
- @advisory_locks_enabled = self.class.type_cast_config_to_boolean(
- config.fetch(:advisory_locks, true)
- )
- end
- end
- end
-end
From 652b6363a2caedc7e74a64bfec3bc7ea2cef53a3 Mon Sep 17 00:00:00 2001
From: Sam Saffron
Date: Fri, 8 Nov 2019 17:07:58 +1100
Subject: [PATCH 033/408] DEV: upgrade bootsnap
This fixes Ruby 2.7 support which we are starting to test
---
Gemfile.lock | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/Gemfile.lock b/Gemfile.lock
index 1201ee9715..7201a23254 100644
--- a/Gemfile.lock
+++ b/Gemfile.lock
@@ -72,7 +72,7 @@ GEM
rack (>= 0.9.0)
binding_of_caller (0.8.0)
debug_inspector (>= 0.0.1)
- bootsnap (1.4.4)
+ bootsnap (1.4.5)
msgpack (~> 1.0)
builder (3.2.3)
bullet (6.0.0)
@@ -199,7 +199,7 @@ GEM
mocha (1.8.0)
metaclass (~> 0.0.1)
mock_redis (0.19.0)
- msgpack (1.2.10)
+ msgpack (1.3.1)
multi_json (1.13.1)
multi_xml (0.6.0)
multipart-post (2.1.1)
From d4c9ed68a97729a661bdc7642b1dff3db37f0745 Mon Sep 17 00:00:00 2001
From: Sam Saffron
Date: Fri, 8 Nov 2019 17:30:42 +1100
Subject: [PATCH 034/408] DEV: properly pass keyword args
Ruby 2.7 is going to deprecate our old and incorrect usage, use the correct
form for passing kwargs
---
lib/freedom_patches/translate_accelerator.rb | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/lib/freedom_patches/translate_accelerator.rb b/lib/freedom_patches/translate_accelerator.rb
index 26dff3594c..704da6ec4b 100644
--- a/lib/freedom_patches/translate_accelerator.rb
+++ b/lib/freedom_patches/translate_accelerator.rb
@@ -110,7 +110,7 @@ module I18n
end
if dup_options.present?
- return translate_no_cache(key, options)
+ return translate_no_cache(key, **options)
end
locale ||= config.locale
From edec92280389681058b0c97929d9d136df3d0dea Mon Sep 17 00:00:00 2001
From: Vinoth Kannan
Date: Fri, 8 Nov 2019 14:17:51 +0530
Subject: [PATCH 035/408] FIX: use 'about.json' endpoint instead of using ember
model to get the data.
---
.../admin/mixins/setting-component.js.es6 | 30 +++++++++----------
1 file changed, 14 insertions(+), 16 deletions(-)
diff --git a/app/assets/javascripts/admin/mixins/setting-component.js.es6 b/app/assets/javascripts/admin/mixins/setting-component.js.es6
index eaf5b356b6..bd73175899 100644
--- a/app/assets/javascripts/admin/mixins/setting-component.js.es6
+++ b/app/assets/javascripts/admin/mixins/setting-component.js.es6
@@ -4,8 +4,8 @@ import { categoryLinkHTML } from "discourse/helpers/category-link";
import { on } from "@ember/object/evented";
import Mixin from "@ember/object/mixin";
import showModal from "discourse/lib/show-modal";
-import AboutRoute from "discourse/routes/about";
import { Promise } from "rsvp";
+import { ajax } from "discourse/lib/ajax";
const CUSTOM_TYPES = [
"bool",
@@ -151,22 +151,20 @@ export default Mixin.create({
const key = this.buffered.get("setting");
if (defaultUserPreferences.includes(key)) {
- AboutRoute.create()
- .model()
- .then(result => {
- const controller = showModal("site-setting-default-categories", {
- model: {
- count: result.stats.user_count,
- key: key.replace(/_/g, " ")
- },
- admin: true
- });
-
- controller.set("onClose", () => {
- this.updateExistingUsers = controller.updateExistingUsers;
- this.send("save");
- });
+ ajax("/about.json").then(result => {
+ const controller = showModal("site-setting-default-categories", {
+ model: {
+ count: result.about.stats.user_count,
+ key: key.replace(/_/g, " ")
+ },
+ admin: true
});
+
+ controller.set("onClose", () => {
+ this.updateExistingUsers = controller.updateExistingUsers;
+ this.send("save");
+ });
+ });
} else {
this.send("save");
}
From dfc002d331a61225c4a9697f32e6cd1b120e15b3 Mon Sep 17 00:00:00 2001
From: Dan Ungureanu
Date: Fri, 8 Nov 2019 12:23:57 +0200
Subject: [PATCH 036/408] FIX: Count current penalty if it started more than 6
months ago (#8313)
---
app/models/trust_level3_requirements.rb | 9 +++++++--
spec/models/trust_level3_requirements_spec.rb | 12 ++++++++++++
2 files changed, 19 insertions(+), 2 deletions(-)
diff --git a/app/models/trust_level3_requirements.rb b/app/models/trust_level3_requirements.rb
index bfd70fea0f..26224e018e 100644
--- a/app/models/trust_level3_requirements.rb
+++ b/app/models/trust_level3_requirements.rb
@@ -7,9 +7,14 @@ class TrustLevel3Requirements
class PenaltyCounts
attr_reader :silenced, :suspended
- def initialize(row)
+ def initialize(user, row)
@silenced = row['silence_count'] || 0
@suspended = row['suspend_count'] || 0
+
+ # If penalty started more than 6 months ago and still continues, it will
+ # not be selected by the query from 'penalty_counts'.
+ @silenced += 1 if @silenced == 0 && user.silenced?
+ @suspended += 1 if @suspended == 0 && user.suspended?
end
def total
@@ -114,7 +119,7 @@ class TrustLevel3Requirements
AND uh.created_at > :since
SQL
- PenaltyCounts.new(DB.query_hash(sql, args).first)
+ PenaltyCounts.new(@user, DB.query_hash(sql, args).first)
end
def min_days_visited
diff --git a/spec/models/trust_level3_requirements_spec.rb b/spec/models/trust_level3_requirements_spec.rb
index 3f124019a3..b027d1e541 100644
--- a/spec/models/trust_level3_requirements_spec.rb
+++ b/spec/models/trust_level3_requirements_spec.rb
@@ -78,6 +78,18 @@ describe TrustLevel3Requirements do
expect(tl3_requirements.penalty_counts.suspended).to eq(1)
expect(tl3_requirements.penalty_counts.total).to eq(2)
end
+
+ it "does return if the user has been silenced or suspended over 6 months ago and continues" do
+ freeze_time 1.year.ago do
+ UserSilencer.new(user, moderator, silenced_till: 10.years.from_now).silence
+ UserHistory.create!(target_user_id: user.id, action: UserHistory.actions[:suspend_user])
+ user.update(suspended_till: 10.years.from_now)
+ end
+
+ expect(tl3_requirements.penalty_counts.silenced).to eq(1)
+ expect(tl3_requirements.penalty_counts.suspended).to eq(1)
+ expect(tl3_requirements.penalty_counts.total).to eq(2)
+ end
end
it "time_period uses site setting" do
From 5a016b7eb01e7afd6876a60574f490b046b6a217 Mon Sep 17 00:00:00 2001
From: Roman Rizzi
Date: Fri, 8 Nov 2019 10:32:57 -0300
Subject: [PATCH 037/408] DEV: Adds a new plugin outles to add custom icons on
the admin users list (#8277)
---
app/assets/javascripts/admin/templates/users-list-show.hbs | 1 +
1 file changed, 1 insertion(+)
diff --git a/app/assets/javascripts/admin/templates/users-list-show.hbs b/app/assets/javascripts/admin/templates/users-list-show.hbs
index 065d2ed93d..8bb4ab6f08 100644
--- a/app/assets/javascripts/admin/templates/users-list-show.hbs
+++ b/app/assets/javascripts/admin/templates/users-list-show.hbs
@@ -91,6 +91,7 @@
{{#if user.second_factor_enabled}}
{{d-icon "lock" title="admin.user.second_factor_enabled" }}
{{/if}}
+ {{plugin-outlet name="admin-users-list-icon" tagName="" args=(hash user=user)}}
{{/each}}
From da50cd554ac9146660497933a8fc0790b9f2cdc0 Mon Sep 17 00:00:00 2001
From: David Taylor
Date: Fri, 8 Nov 2019 14:22:57 +0000
Subject: [PATCH 038/408] DEV: Optionally allow autospec without auto-running
the whole suite (#8321)
I want to use autospec while working on a single spec file. At the moment, it will start running all specs once it completes the file I'm working on. With parallel mode enabled, this causes CPU usage to spike dramatically, affecting IDE performance, battery life, and fan noise. I would prefer that it only runs all specs when I explicitly press [ENTER]
This commit adds a new ENV variable `AUTO_RUN_ALL`. To prevent auto-running all specs, set it to 0. The default behavior remains unchanged.
---
lib/autospec/manager.rb | 8 +++++---
1 file changed, 5 insertions(+), 3 deletions(-)
diff --git a/lib/autospec/manager.rb b/lib/autospec/manager.rb
index 6c3e88a951..75ea4412a3 100644
--- a/lib/autospec/manager.rb
+++ b/lib/autospec/manager.rb
@@ -18,6 +18,7 @@ class Autospec::Manager
def initialize(opts = {})
@opts = opts
@debug = opts[:debug]
+ @auto_run_all = ENV["AUTO_RUN_ALL"] != "0"
@queue = []
@mutex = Mutex.new
@signal = ConditionVariable.new
@@ -42,12 +43,13 @@ class Autospec::Manager
exit
end
- ensure_all_specs_will_run
+ ensure_all_specs_will_run if @auto_run_all
start_runners
start_service_queue
listen_for_changes
puts "Press [ENTER] to stop the current run"
+ puts "Press [ENTER] while stopped to run all specs" unless @auto_run_all
while @runners.any?(&:running?)
STDIN.gets
process_queue
@@ -138,7 +140,7 @@ class Autospec::Manager
has_failed = true
if result > 0
focus_on_failed_tests(current)
- ensure_all_specs_will_run(runner)
+ ensure_all_specs_will_run(runner) if @auto_run_all
end
end
@@ -343,7 +345,7 @@ class Autospec::Manager
end
# push run all specs to end of queue in correct order
- ensure_all_specs_will_run(runner)
+ ensure_all_specs_will_run(runner) if @auto_run_all
end
puts "@@@@@@@@@@@@ specs queued" if @debug
puts "@@@@@@@@@@@@ #{@queue}" if @debug
From cd57c3bf5a09efbb76ea74f404e7aaf9dfb0951b Mon Sep 17 00:00:00 2001
From: David Taylor
Date: Fri, 8 Nov 2019 14:23:12 +0000
Subject: [PATCH 039/408] DEV: Abort autospec on [ENTER], even if no specs have
failed (#8320)
When starting autospec, it says
> Press [ENTER] to stop the current run
However, [ENTER] does nothing unless a spec has failed. Sometimes I want to abort anyway, so that the run is restarted.
---
lib/autospec/manager.rb | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/lib/autospec/manager.rb b/lib/autospec/manager.rb
index 75ea4412a3..cefce3e76a 100644
--- a/lib/autospec/manager.rb
+++ b/lib/autospec/manager.rb
@@ -366,8 +366,9 @@ class Autospec::Manager
puts
puts
if specs.length == 0
- puts "No specs have failed yet! "
+ puts "No specs have failed yet! Aborting anyway"
puts
+ abort_runners
else
puts "The following specs have failed:"
specs.each { |s| puts s }
From 1998be3b270d1cf10cf26638bea94a9700509fdb Mon Sep 17 00:00:00 2001
From: David Taylor
Date: Fri, 8 Nov 2019 15:34:03 +0000
Subject: [PATCH 040/408] DEV: Raise errors when cleaning the download cache,
and fix for macOS (#8319)
POSIX's `head` specification states: "The application shall ensure that the number option-argument is a positive decimal integer"
Negative values are supported on GNU `head`, so this works in the discourse docker image. However, in some environments (e.g. macOS), the system `head` version fails with a negative `n` parameter.
This commit does two things:
Checks the status at each stage of the pipe, so it cannot fail silently
Flip the `ls` command to list in descending time order, and use `tail -n +501` instead of `head -n -500`.
The visible result is that macOS users no longer see head: illegal line count -- -500 printed throughout the test suite.
---
lib/file_store/base_store.rb | 8 +++++++-
1 file changed, 7 insertions(+), 1 deletion(-)
diff --git a/lib/file_store/base_store.rb b/lib/file_store/base_store.rb
index 6e8c53442d..5e455ac1b5 100644
--- a/lib/file_store/base_store.rb
+++ b/lib/file_store/base_store.rb
@@ -139,7 +139,13 @@ module FileStore
FileUtils.mkdir_p(dir) unless Dir.exist?(dir)
FileUtils.cp(file.path, path)
# keep latest 500 files
- `ls -tr #{CACHE_DIR} | head -n -#{CACHE_MAXIMUM_SIZE} | awk '$0="#{CACHE_DIR}"$0' | xargs rm -f`
+ processes = Open3.pipeline(
+ "ls -t #{CACHE_DIR}",
+ "tail -n +#{CACHE_MAXIMUM_SIZE + 1}",
+ "awk '$0=\"#{CACHE_DIR}\"$0'",
+ "xargs rm -f"
+ )
+ raise "Error clearing old cache" if !processes.all?(&:success?)
end
private
From 47e3e56905fc61a0872716fc4401e9e0956dc6ac Mon Sep 17 00:00:00 2001
From: Mark VanLandingham
Date: Fri, 8 Nov 2019 09:48:02 -0600
Subject: [PATCH 041/408] FIX: Alias modules that are required AND imported
(#8315)
---
app/assets/javascripts/discourse-loader.js | 6 +++---
1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/app/assets/javascripts/discourse-loader.js b/app/assets/javascripts/discourse-loader.js
index fc3a0613f8..a8cd03b800 100644
--- a/app/assets/javascripts/discourse-loader.js
+++ b/app/assets/javascripts/discourse-loader.js
@@ -151,7 +151,7 @@ var define, requirejs;
}
Module.prototype.makeRequire = function() {
- var name = this.name;
+ var name = transformForAliases(this.name);
return (
this._require ||
@@ -217,7 +217,7 @@ var define, requirejs;
}
function requireFrom(name, origin) {
- name = checkForAlias(name);
+ name = transformForAliases(name);
var mod = EMBER_MODULES[name] || registry[name];
if (!mod) {
throw new Error(
@@ -231,7 +231,7 @@ var define, requirejs;
throw new Error("Could not find module " + name);
}
- function checkForAlias(name) {
+ function transformForAliases(name) {
return ALIASES[name] ? ALIASES[name] : name;
}
From 03bba8c7e00964e019721d69f55564bcc2c9c551 Mon Sep 17 00:00:00 2001
From: Dan Ungureanu
Date: Fri, 8 Nov 2019 17:50:41 +0200
Subject: [PATCH 042/408] DEV: Update chrome-launcher (#8318)
This version is compatible with macOS Catalina
---
package.json | 2 +-
yarn.lock | 46 ++++++++++++++--------------------------------
2 files changed, 15 insertions(+), 33 deletions(-)
diff --git a/package.json b/package.json
index 4761adf6d2..f667b5f05e 100644
--- a/package.json
+++ b/package.json
@@ -40,7 +40,7 @@
"devDependencies": {
"@arkweid/lefthook": "^0.6.3",
"babel-eslint": "^8.2",
- "chrome-launcher": "^0.10",
+ "chrome-launcher": "^0.12.0",
"chrome-remote-interface": "^0.25",
"eslint": "^4.19",
"eslint-config-discourse": "1.0.5",
diff --git a/yarn.lock b/yarn.lock
index b325846c2a..252e71449c 100644
--- a/yarn.lock
+++ b/yarn.lock
@@ -126,25 +126,10 @@
resolved "https://registry.yarnpkg.com/@sinonjs/text-encoding/-/text-encoding-0.7.1.tgz#8da5c6530915653f3a1f38fd5f101d8c3f8079c5"
integrity sha512-+iTbntw2IZPb/anVDbypzfQa+ay64MW0Zo8aJ8gZPWMMK6/OubMVb6lUPMagqjOPnmtauXnFCACVl3O7ogjeqQ==
-"@types/core-js@^0.9.41":
- version "0.9.46"
- resolved "https://registry.yarnpkg.com/@types/core-js/-/core-js-0.9.46.tgz#ea701ee34cbb6dfe6d100f1530319547c93c8d79"
- integrity sha512-LooLR6XHes9V+kNYRz1Qm8w3atw9QMn7XeZUmIpUelllF9BdryeUKd/u0Wh5ErcjpWfG39NrToU9MF7ngsTFVw==
-
-"@types/mkdirp@^0.3.29":
- version "0.3.29"
- resolved "https://registry.yarnpkg.com/@types/mkdirp/-/mkdirp-0.3.29.tgz#7f2ad7ec55f914482fc9b1ec4bb1ae6028d46066"
- integrity sha1-fyrX7FX5FEgvybHsS7GuYCjUYGY=
-
-"@types/node@^9.3.0":
- version "9.6.39"
- resolved "https://registry.yarnpkg.com/@types/node/-/node-9.6.39.tgz#111cb4f5591cb6945aad34733b4e40bfd59b58fc"
- integrity sha512-c3OkjgNpSMdHan56WhklP0FMOk5ocilKz2Mpa0NOGzu8jw5YERjCf9FG0epYB1+TxScv/oI4uJ204u2mUg7Hcw==
-
-"@types/rimraf@^0.0.28":
- version "0.0.28"
- resolved "https://registry.yarnpkg.com/@types/rimraf/-/rimraf-0.0.28.tgz#5562519bc7963caca8abf7f128cae3b594d41d06"
- integrity sha1-VWJRm8eWPKyoq/fxKMrjtZTUHQY=
+"@types/node@*":
+ version "12.12.6"
+ resolved "https://registry.yarnpkg.com/@types/node/-/node-12.12.6.tgz#a47240c10d86a9a57bb0c633f0b2e0aea9ce9253"
+ integrity sha512-FjsYUPzEJdGXjwKqSpE0/9QEh6kzhTAeObA54rn6j3rR4C/mzpI9L0KNfoeASSPMMdxIsoJuCLDWcM/rVjIsSA==
ace-builds@1.4.2:
version "1.4.2"
@@ -537,16 +522,13 @@ chartjs-color@^2.1.0:
chartjs-color-string "^0.5.0"
color-convert "^0.5.3"
-chrome-launcher@^0.10:
- version "0.10.5"
- resolved "https://registry.yarnpkg.com/chrome-launcher/-/chrome-launcher-0.10.5.tgz#d0aa72c11f1653e6a60dfebea171522447470ef1"
- integrity sha512-Gbzg8HlWhyuoVqflhiXwfFXhzNfNWvAkSWv2QR1Yl6mwsMo1oCLAVjp2tIySuS4lrZLEjzVx1fOy584yE76P4g==
+chrome-launcher@^0.12.0:
+ version "0.12.0"
+ resolved "https://registry.yarnpkg.com/chrome-launcher/-/chrome-launcher-0.12.0.tgz#08db81ef0f7b283c331df2c350e780c38bd0ce3a"
+ integrity sha512-rBUP4tvWToiileDi3UR0SbWKoUoDCYTRmVND2sdoBL1xANBgVz8V9h1yQluj3MEQaBJg0fRw7hW82uOPrJus7A==
dependencies:
- "@types/core-js" "^0.9.41"
- "@types/mkdirp" "^0.3.29"
- "@types/node" "^9.3.0"
- "@types/rimraf" "^0.0.28"
- is-wsl "^1.1.0"
+ "@types/node" "*"
+ is-wsl "^2.1.0"
lighthouse-logger "^1.0.0"
mkdirp "0.5.1"
rimraf "^2.6.1"
@@ -1645,10 +1627,10 @@ is-windows@^1.0.1, is-windows@^1.0.2:
resolved "https://registry.yarnpkg.com/is-windows/-/is-windows-1.0.2.tgz#d1850eb9791ecd18e6182ce12a30f396634bb19d"
integrity sha512-eXK1UInq2bPmjyX6e3VHIzMLobc4J94i4AWn+Hpq3OU5KkrRC96OAcR3PRJ/pGu6m8TRnBHP9dkXQVsT/COVIA==
-is-wsl@^1.1.0:
- version "1.1.0"
- resolved "https://registry.yarnpkg.com/is-wsl/-/is-wsl-1.1.0.tgz#1f16e4aa22b04d1336b66188a66af3c600c3a66d"
- integrity sha1-HxbkqiKwTRM2tmGIpmrzxgDDpm0=
+is-wsl@^2.1.0:
+ version "2.1.1"
+ resolved "https://registry.yarnpkg.com/is-wsl/-/is-wsl-2.1.1.tgz#4a1c152d429df3d441669498e2486d3596ebaf1d"
+ integrity sha512-umZHcSrwlDHo2TGMXv0DZ8dIUGunZ2Iv68YZnrmCiBPkZ4aaOhtv7pXJKeki9k3qJ3RJr0cDyitcl5wEH3AYog==
isarray@0.0.1:
version "0.0.1"
From 7f3812b90a3da66cc2a2dbdb2796356650e967ca Mon Sep 17 00:00:00 2001
From: Mark VanLandingham
Date: Fri, 8 Nov 2019 10:32:20 -0600
Subject: [PATCH 043/408] DEV: Removed all Ember.computed. in select-kit
(#8322)
---
.../select-kit/components/category-drop.js.es6 | 7 ++++---
.../category-drop/category-drop-header.js.es6 | 3 ++-
.../components/category-notifications-button.js.es6 | 5 +++--
.../select-kit/components/category-row.js.es6 | 7 ++++---
.../components/combo-box/combo-box-header.js.es6 | 9 +++++----
.../dropdown-select-box-row.js.es6 | 3 ++-
.../components/future-date-input-selector.js.es6 | 5 +++--
.../select-kit/components/group-dropdown.js.es6 | 3 ++-
.../select-kit/components/mini-tag-chooser.js.es6 | 9 +++++----
.../multi-select/multi-select-header.js.es6 | 9 +++++----
.../components/multi-select/selected-name.js.es6 | 9 +++++----
.../components/notifications-button.js.es6 | 3 ++-
.../notifications-button-row.js.es6 | 5 +++--
.../select-kit/components/period-chooser.js.es6 | 7 ++++---
.../components/select-kit/select-kit-filter.js.es6 | 3 ++-
.../components/select-kit/select-kit-header.js.es6 | 13 +++++++------
.../components/select-kit/select-kit-row.js.es6 | 11 ++++++-----
.../select-kit/components/tag-chooser.js.es6 | 3 ++-
.../select-kit/components/tag-drop.js.es6 | 9 +++++----
.../components/toolbar-popup-menu-options.js.es6 | 3 ++-
.../components/topic-footer-mobile-dropdown.js.es6 | 3 ++-
21 files changed, 75 insertions(+), 54 deletions(-)
diff --git a/app/assets/javascripts/select-kit/components/category-drop.js.es6 b/app/assets/javascripts/select-kit/components/category-drop.js.es6
index 25f72b2655..601d420d4b 100644
--- a/app/assets/javascripts/select-kit/components/category-drop.js.es6
+++ b/app/assets/javascripts/select-kit/components/category-drop.js.es6
@@ -1,3 +1,4 @@
+import { alias, not } from "@ember/object/computed";
import ComboBoxComponent from "select-kit/components/combo-box";
import DiscourseURL from "discourse/lib/url";
import { default as discourseComputed } from "discourse-common/utils/decorators";
@@ -10,18 +11,18 @@ export default ComboBoxComponent.extend({
classNameBindings: ["categoryStyle"],
classNames: "category-drop",
verticalOffset: 3,
- content: Ember.computed.alias("categoriesWithShortcuts"),
+ content: alias("categoriesWithShortcuts"),
rowComponent: "category-row",
headerComponent: "category-drop/category-drop-header",
allowAutoSelectFirst: false,
tagName: "li",
- categoryStyle: Ember.computed.alias("siteSettings.category_style"),
+ categoryStyle: alias("siteSettings.category_style"),
noCategoriesLabel: I18n.t("categories.no_subcategory"),
fullWidthOnMobile: true,
caretDownIcon: "caret-right",
caretUpIcon: "caret-down",
subCategory: false,
- isAsync: Ember.computed.not("subCategory"),
+ isAsync: not("subCategory"),
@discourseComputed(
"categories",
diff --git a/app/assets/javascripts/select-kit/components/category-drop/category-drop-header.js.es6 b/app/assets/javascripts/select-kit/components/category-drop/category-drop-header.js.es6
index ad86019a19..c84b7189d0 100644
--- a/app/assets/javascripts/select-kit/components/category-drop/category-drop-header.js.es6
+++ b/app/assets/javascripts/select-kit/components/category-drop/category-drop-header.js.es6
@@ -1,3 +1,4 @@
+import { alias } from "@ember/object/computed";
import { isEmpty } from "@ember/utils";
import ComboBoxSelectBoxHeaderComponent from "select-kit/components/combo-box/combo-box-header";
import discourseComputed from "discourse-common/utils/decorators";
@@ -9,7 +10,7 @@ export default ComboBoxSelectBoxHeaderComponent.extend({
classNames: "category-drop-header",
classNameBindings: ["categoryStyleClass"],
- categoryStyleClass: Ember.computed.alias("site.category_style"),
+ categoryStyleClass: alias("site.category_style"),
@discourseComputed("computedContent.value", "computedContent.name")
category(value, name) {
diff --git a/app/assets/javascripts/select-kit/components/category-notifications-button.js.es6 b/app/assets/javascripts/select-kit/components/category-notifications-button.js.es6
index 17c8e4de41..ecc000d8bd 100644
--- a/app/assets/javascripts/select-kit/components/category-notifications-button.js.es6
+++ b/app/assets/javascripts/select-kit/components/category-notifications-button.js.es6
@@ -1,10 +1,11 @@
+import { or, alias } from "@ember/object/computed";
import NotificationOptionsComponent from "select-kit/components/notifications-button";
export default NotificationOptionsComponent.extend({
pluginApiIdentifiers: ["category-notifications-button"],
classNames: "category-notifications-button",
- isHidden: Ember.computed.or("category.deleted"),
- headerIcon: Ember.computed.alias("iconForSelectedDetails"),
+ isHidden: or("category.deleted"),
+ headerIcon: alias("iconForSelectedDetails"),
i18nPrefix: "category.notifications",
showFullTitle: false,
allowInitialValueMutation: false,
diff --git a/app/assets/javascripts/select-kit/components/category-row.js.es6 b/app/assets/javascripts/select-kit/components/category-row.js.es6
index d2a548164e..e8963e96b6 100644
--- a/app/assets/javascripts/select-kit/components/category-row.js.es6
+++ b/app/assets/javascripts/select-kit/components/category-row.js.es6
@@ -1,3 +1,4 @@
+import { bool } from "@ember/object/computed";
import { isEmpty } from "@ember/utils";
import SelectKitRowComponent from "select-kit/components/select-kit/select-kit-row";
import discourseComputed from "discourse-common/utils/decorators";
@@ -8,9 +9,9 @@ export default SelectKitRowComponent.extend({
layoutName: "select-kit/templates/components/category-row",
classNames: "category-row",
- hideParentCategory: Ember.computed.bool("options.hideParentCategory"),
- allowUncategorized: Ember.computed.bool("options.allowUncategorized"),
- categoryLink: Ember.computed.bool("options.categoryLink"),
+ hideParentCategory: bool("options.hideParentCategory"),
+ allowUncategorized: bool("options.allowUncategorized"),
+ categoryLink: bool("options.categoryLink"),
@discourseComputed("options.displayCategoryDescription")
displayCategoryDescription(displayCategoryDescription) {
diff --git a/app/assets/javascripts/select-kit/components/combo-box/combo-box-header.js.es6 b/app/assets/javascripts/select-kit/components/combo-box/combo-box-header.js.es6
index 34e642bd7e..f5bd519625 100644
--- a/app/assets/javascripts/select-kit/components/combo-box/combo-box-header.js.es6
+++ b/app/assets/javascripts/select-kit/components/combo-box/combo-box-header.js.es6
@@ -1,13 +1,14 @@
+import { alias, and } from "@ember/object/computed";
import SelectKitHeaderComponent from "select-kit/components/select-kit/select-kit-header";
export default SelectKitHeaderComponent.extend({
layoutName: "select-kit/templates/components/combo-box/combo-box-header",
classNames: "combo-box-header",
- clearable: Ember.computed.alias("options.clearable"),
- caretUpIcon: Ember.computed.alias("options.caretUpIcon"),
- caretDownIcon: Ember.computed.alias("options.caretDownIcon"),
- shouldDisplayClearableButton: Ember.computed.and(
+ clearable: alias("options.clearable"),
+ caretUpIcon: alias("options.caretUpIcon"),
+ caretDownIcon: alias("options.caretDownIcon"),
+ shouldDisplayClearableButton: and(
"clearable",
"computedContent.hasSelection"
)
diff --git a/app/assets/javascripts/select-kit/components/dropdown-select-box/dropdown-select-box-row.js.es6 b/app/assets/javascripts/select-kit/components/dropdown-select-box/dropdown-select-box-row.js.es6
index 187fc460cb..9bbe5fa399 100644
--- a/app/assets/javascripts/select-kit/components/dropdown-select-box/dropdown-select-box-row.js.es6
+++ b/app/assets/javascripts/select-kit/components/dropdown-select-box/dropdown-select-box-row.js.es6
@@ -1,3 +1,4 @@
+import { alias } from "@ember/object/computed";
import SelectKitRowComponent from "select-kit/components/select-kit/select-kit-row";
export default SelectKitRowComponent.extend({
@@ -5,7 +6,7 @@ export default SelectKitRowComponent.extend({
"select-kit/templates/components/dropdown-select-box/dropdown-select-box-row",
classNames: "dropdown-select-box-row",
- description: Ember.computed.alias(
+ description: alias(
"computedContent.originalContent.description"
)
});
diff --git a/app/assets/javascripts/select-kit/components/future-date-input-selector.js.es6 b/app/assets/javascripts/select-kit/components/future-date-input-selector.js.es6
index f5167afb20..9fec1611c1 100644
--- a/app/assets/javascripts/select-kit/components/future-date-input-selector.js.es6
+++ b/app/assets/javascripts/select-kit/components/future-date-input-selector.js.es6
@@ -1,3 +1,4 @@
+import { equal } from "@ember/object/computed";
import { isEmpty } from "@ember/utils";
import ComboBoxComponent from "select-kit/components/combo-box";
import { CLOSE_STATUS_TYPE } from "discourse/controllers/edit-topic-timer";
@@ -188,8 +189,8 @@ export const FORMAT = "YYYY-MM-DD HH:mmZ";
export default ComboBoxComponent.extend(DatetimeMixin, {
pluginApiIdentifiers: ["future-date-input-selector"],
classNames: ["future-date-input-selector"],
- isCustom: Ember.computed.equal("value", "pick_date_and_time"),
- isBasedOnLastPost: Ember.computed.equal("value", "set_based_on_last_post"),
+ isCustom: equal("value", "pick_date_and_time"),
+ isBasedOnLastPost: equal("value", "set_based_on_last_post"),
rowComponent: "future-date-input-selector/future-date-input-selector-row",
headerComponent:
"future-date-input-selector/future-date-input-selector-header",
diff --git a/app/assets/javascripts/select-kit/components/group-dropdown.js.es6 b/app/assets/javascripts/select-kit/components/group-dropdown.js.es6
index a53988a953..0e6ccfac0f 100644
--- a/app/assets/javascripts/select-kit/components/group-dropdown.js.es6
+++ b/app/assets/javascripts/select-kit/components/group-dropdown.js.es6
@@ -1,3 +1,4 @@
+import { alias } from "@ember/object/computed";
import ComboBoxComponent from "select-kit/components/combo-box";
import DiscourseURL from "discourse/lib/url";
import { default as discourseComputed } from "discourse-common/utils/decorators";
@@ -5,7 +6,7 @@ import { default as discourseComputed } from "discourse-common/utils/decorators"
export default ComboBoxComponent.extend({
pluginApiIdentifiers: ["group-dropdown"],
classNames: "group-dropdown",
- content: Ember.computed.alias("groups"),
+ content: alias("groups"),
tagName: "li",
caretDownIcon: "caret-right",
caretUpIcon: "caret-down",
diff --git a/app/assets/javascripts/select-kit/components/mini-tag-chooser.js.es6 b/app/assets/javascripts/select-kit/components/mini-tag-chooser.js.es6
index 5a2fe7a73e..1b4689b933 100644
--- a/app/assets/javascripts/select-kit/components/mini-tag-chooser.js.es6
+++ b/app/assets/javascripts/select-kit/components/mini-tag-chooser.js.es6
@@ -1,3 +1,4 @@
+import { empty, alias } from "@ember/object/computed";
import Category from "discourse/models/category";
import ComboBox from "select-kit/components/combo-box";
import TagsMixin from "select-kit/mixins/tags";
@@ -19,11 +20,11 @@ export default ComboBox.extend(TagsMixin, {
classNameBindings: ["noTags"],
verticalOffset: 3,
filterable: true,
- noTags: Ember.computed.empty("selection"),
+ noTags: empty("selection"),
allowCreate: null,
- allowAny: Ember.computed.alias("allowCreate"),
- caretUpIcon: Ember.computed.alias("caretIcon"),
- caretDownIcon: Ember.computed.alias("caretIcon"),
+ allowAny: alias("allowCreate"),
+ caretUpIcon: alias("caretIcon"),
+ caretDownIcon: alias("caretIcon"),
isAsync: true,
fullWidthOnMobile: true,
diff --git a/app/assets/javascripts/select-kit/components/multi-select/multi-select-header.js.es6 b/app/assets/javascripts/select-kit/components/multi-select/multi-select-header.js.es6
index 67c3ac3f9e..9b6c22f527 100644
--- a/app/assets/javascripts/select-kit/components/multi-select/multi-select-header.js.es6
+++ b/app/assets/javascripts/select-kit/components/multi-select/multi-select-header.js.es6
@@ -1,3 +1,4 @@
+import { alias, or } from "@ember/object/computed";
import { makeArray } from "discourse-common/lib/helpers";
import { on } from "discourse-common/utils/decorators";
import discourseComputed from "discourse-common/utils/decorators";
@@ -13,13 +14,13 @@ export default SelectKitHeaderComponent.extend({
classNames: "multi-select-header",
layoutName:
"select-kit/templates/components/multi-select/multi-select-header",
- selectedNameComponent: Ember.computed.alias("options.selectedNameComponent"),
+ selectedNameComponent: alias("options.selectedNameComponent"),
- forceEscape: Ember.computed.alias("options.forceEscape"),
+ forceEscape: alias("options.forceEscape"),
- ariaLabel: Ember.computed.or("computedContent.ariaLabel", "title", "names"),
+ ariaLabel: or("computedContent.ariaLabel", "title", "names"),
- title: Ember.computed.or("computedContent.title", "names"),
+ title: or("computedContent.title", "names"),
@on("didRender")
_positionFilter() {
diff --git a/app/assets/javascripts/select-kit/components/multi-select/selected-name.js.es6 b/app/assets/javascripts/select-kit/components/multi-select/selected-name.js.es6
index 6de8c9d0a8..df37ac012c 100644
--- a/app/assets/javascripts/select-kit/components/multi-select/selected-name.js.es6
+++ b/app/assets/javascripts/select-kit/components/multi-select/selected-name.js.es6
@@ -1,3 +1,4 @@
+import { or, alias } from "@ember/object/computed";
import Component from "@ember/component";
import discourseComputed from "discourse-common/utils/decorators";
@@ -21,7 +22,7 @@ export default Component.extend({
return Ember.guidFor(computedContent);
},
- ariaLabel: Ember.computed.or("computedContent.ariaLabel", "title"),
+ ariaLabel: or("computedContent.ariaLabel", "title"),
@discourseComputed("computedContent.title", "name")
title(computedContentTitle, name) {
@@ -31,11 +32,11 @@ export default Component.extend({
return null;
},
- label: Ember.computed.or("computedContent.label", "title", "name"),
+ label: or("computedContent.label", "title", "name"),
- name: Ember.computed.alias("computedContent.name"),
+ name: alias("computedContent.name"),
- value: Ember.computed.alias("computedContent.value"),
+ value: alias("computedContent.value"),
isLocked: Ember.computed("computedContent.locked", function() {
return this.getWithDefault("computedContent.locked", false);
diff --git a/app/assets/javascripts/select-kit/components/notifications-button.js.es6 b/app/assets/javascripts/select-kit/components/notifications-button.js.es6
index 5c5bec067b..172282ba0b 100644
--- a/app/assets/javascripts/select-kit/components/notifications-button.js.es6
+++ b/app/assets/javascripts/select-kit/components/notifications-button.js.es6
@@ -1,3 +1,4 @@
+import { alias } from "@ember/object/computed";
import DropdownSelectBoxComponent from "select-kit/components/dropdown-select-box";
import {
default as discourseComputed,
@@ -34,7 +35,7 @@ export default DropdownSelectBoxComponent.extend({
});
},
- iconForSelectedDetails: Ember.computed.alias("selectedDetails.icon"),
+ iconForSelectedDetails: alias("selectedDetails.icon"),
computeHeaderContent() {
let content = this._super(...arguments);
diff --git a/app/assets/javascripts/select-kit/components/notifications-button/notifications-button-row.js.es6 b/app/assets/javascripts/select-kit/components/notifications-button/notifications-button-row.js.es6
index e4a3b45bd5..5d62a82e4b 100644
--- a/app/assets/javascripts/select-kit/components/notifications-button/notifications-button-row.js.es6
+++ b/app/assets/javascripts/select-kit/components/notifications-button/notifications-button-row.js.es6
@@ -1,3 +1,4 @@
+import { alias } from "@ember/object/computed";
import DropdownSelectBoxRoxComponent from "select-kit/components/dropdown-select-box/dropdown-select-box-row";
import { buttonDetails } from "discourse/lib/notification-levels";
import discourseComputed from "discourse-common/utils/decorators";
@@ -6,8 +7,8 @@ import { iconHTML } from "discourse-common/lib/icon-library";
export default DropdownSelectBoxRoxComponent.extend({
classNames: "notifications-button-row",
- i18nPrefix: Ember.computed.alias("options.i18nPrefix"),
- i18nPostfix: Ember.computed.alias("options.i18nPostfix"),
+ i18nPrefix: alias("options.i18nPrefix"),
+ i18nPostfix: alias("options.i18nPostfix"),
@discourseComputed("computedContent.value", "i18nPrefix", "i18nPostfix")
title(value, prefix, postfix) {
diff --git a/app/assets/javascripts/select-kit/components/period-chooser.js.es6 b/app/assets/javascripts/select-kit/components/period-chooser.js.es6
index bc9befb89a..60c6cd476a 100644
--- a/app/assets/javascripts/select-kit/components/period-chooser.js.es6
+++ b/app/assets/javascripts/select-kit/components/period-chooser.js.es6
@@ -1,3 +1,4 @@
+import { oneWay, alias } from "@ember/object/computed";
import DropdownSelectBoxComponent from "select-kit/components/dropdown-select-box";
import discourseComputed, { on } from "discourse-common/utils/decorators";
@@ -5,9 +6,9 @@ export default DropdownSelectBoxComponent.extend({
classNames: ["period-chooser"],
rowComponent: "period-chooser/period-chooser-row",
headerComponent: "period-chooser/period-chooser-header",
- content: Ember.computed.oneWay("site.periods"),
- value: Ember.computed.alias("period"),
- isHidden: Ember.computed.alias("showPeriods"),
+ content: oneWay("site.periods"),
+ value: alias("period"),
+ isHidden: alias("showPeriods"),
@discourseComputed("isExpanded")
caretIcon(isExpanded) {
diff --git a/app/assets/javascripts/select-kit/components/select-kit/select-kit-filter.js.es6 b/app/assets/javascripts/select-kit/components/select-kit/select-kit-filter.js.es6
index a239c780cd..7366fc884c 100644
--- a/app/assets/javascripts/select-kit/components/select-kit/select-kit-filter.js.es6
+++ b/app/assets/javascripts/select-kit/components/select-kit/select-kit-filter.js.es6
@@ -1,3 +1,4 @@
+import { not } from "@ember/object/computed";
import Component from "@ember/component";
import discourseComputed from "discourse-common/utils/decorators";
@@ -7,7 +8,7 @@ export default Component.extend({
layoutName: "select-kit/templates/components/select-kit/select-kit-filter",
classNames: ["select-kit-filter"],
classNameBindings: ["isFocused", "isHidden"],
- isHidden: Ember.computed.not("shouldDisplayFilter"),
+ isHidden: not("shouldDisplayFilter"),
@discourseComputed("placeholder")
discourseComputedPlaceholder(placeholder) {
diff --git a/app/assets/javascripts/select-kit/components/select-kit/select-kit-header.js.es6 b/app/assets/javascripts/select-kit/components/select-kit/select-kit-header.js.es6
index fd145162d0..525c9b6936 100644
--- a/app/assets/javascripts/select-kit/components/select-kit/select-kit-header.js.es6
+++ b/app/assets/javascripts/select-kit/components/select-kit/select-kit-header.js.es6
@@ -1,3 +1,4 @@
+import { alias, none, or } from "@ember/object/computed";
import Component from "@ember/component";
import discourseComputed from "discourse-common/utils/decorators";
@@ -16,13 +17,13 @@ export default Component.extend({
"name:data-name"
],
- forceEscape: Ember.computed.alias("options.forceEscape"),
+ forceEscape: alias("options.forceEscape"),
- isNone: Ember.computed.none("computedContent.value"),
+ isNone: none("computedContent.value"),
ariaHasPopup: "true",
- ariaLabel: Ember.computed.or("computedContent.ariaLabel", "sanitizedTitle"),
+ ariaLabel: or("computedContent.ariaLabel", "sanitizedTitle"),
@discourseComputed("computedContent.title", "name")
title(computedContentTitle, name) {
@@ -39,11 +40,11 @@ export default Component.extend({
return String(title).replace("…", "");
},
- label: Ember.computed.or("computedContent.label", "title", "name"),
+ label: or("computedContent.label", "title", "name"),
- name: Ember.computed.alias("computedContent.name"),
+ name: alias("computedContent.name"),
- value: Ember.computed.alias("computedContent.value"),
+ value: alias("computedContent.value"),
@discourseComputed("computedContent.icon", "computedContent.icons")
icons(icon, icons) {
diff --git a/app/assets/javascripts/select-kit/components/select-kit/select-kit-row.js.es6 b/app/assets/javascripts/select-kit/components/select-kit/select-kit-row.js.es6
index 01828a5e94..a50db81e0a 100644
--- a/app/assets/javascripts/select-kit/components/select-kit/select-kit-row.js.es6
+++ b/app/assets/javascripts/select-kit/components/select-kit/select-kit-row.js.es6
@@ -1,3 +1,4 @@
+import { alias, or } from "@ember/object/computed";
import Component from "@ember/component";
import {
default as discourseComputed,
@@ -26,9 +27,9 @@ export default Component.extend(UtilsMixin, {
"computedContent.originalContent.classNames"
],
- forceEscape: Ember.computed.alias("options.forceEscape"),
+ forceEscape: alias("options.forceEscape"),
- ariaLabel: Ember.computed.or("computedContent.ariaLabel", "title"),
+ ariaLabel: or("computedContent.ariaLabel", "title"),
@discourseComputed("computedContent.title", "name")
title(computedContentTitle, name) {
@@ -43,11 +44,11 @@ export default Component.extend(UtilsMixin, {
return Ember.guidFor(computedContent);
},
- label: Ember.computed.or("computedContent.label", "title", "name"),
+ label: or("computedContent.label", "title", "name"),
- name: Ember.computed.alias("computedContent.name"),
+ name: alias("computedContent.name"),
- value: Ember.computed.alias("computedContent.value"),
+ value: alias("computedContent.value"),
@discourseComputed("templateForRow")
template(templateForRow) {
diff --git a/app/assets/javascripts/select-kit/components/tag-chooser.js.es6 b/app/assets/javascripts/select-kit/components/tag-chooser.js.es6
index 1ad21b0642..247a8eeab1 100644
--- a/app/assets/javascripts/select-kit/components/tag-chooser.js.es6
+++ b/app/assets/javascripts/select-kit/components/tag-chooser.js.es6
@@ -1,3 +1,4 @@
+import { alias } from "@ember/object/computed";
import MultiSelectComponent from "select-kit/components/multi-select";
import TagsMixin from "select-kit/mixins/tags";
import renderTag from "discourse/lib/render-tag";
@@ -15,7 +16,7 @@ export default MultiSelectComponent.extend(TagsMixin, {
blacklist: null,
attributeBindings: ["categoryId"],
allowCreate: null,
- allowAny: Ember.computed.alias("allowCreate"),
+ allowAny: alias("allowCreate"),
init() {
this._super(...arguments);
diff --git a/app/assets/javascripts/select-kit/components/tag-drop.js.es6 b/app/assets/javascripts/select-kit/components/tag-drop.js.es6
index 9fbce57f85..4fbea17f54 100644
--- a/app/assets/javascripts/select-kit/components/tag-drop.js.es6
+++ b/app/assets/javascripts/select-kit/components/tag-drop.js.es6
@@ -1,3 +1,4 @@
+import { alias, or } from "@ember/object/computed";
import { makeArray } from "discourse-common/lib/helpers";
import ComboBoxComponent from "select-kit/components/combo-box";
import DiscourseURL from "discourse/lib/url";
@@ -10,14 +11,14 @@ export default ComboBoxComponent.extend(TagsMixin, {
classNameBindings: ["categoryStyle", "tagClass"],
classNames: "tag-drop",
verticalOffset: 3,
- value: Ember.computed.alias("tagId"),
+ value: alias("tagId"),
headerComponent: "tag-drop/tag-drop-header",
allowAutoSelectFirst: false,
tagName: "li",
- showFilterByTag: Ember.computed.alias("siteSettings.show_filter_by_tag"),
- currentCategory: Ember.computed.or("secondCategory", "firstCategory"),
+ showFilterByTag: alias("siteSettings.show_filter_by_tag"),
+ currentCategory: or("secondCategory", "firstCategory"),
tagId: null,
- categoryStyle: Ember.computed.alias("siteSettings.category_style"),
+ categoryStyle: alias("siteSettings.category_style"),
mutateAttributes() {},
fullWidthOnMobile: true,
caretDownIcon: "caret-right",
diff --git a/app/assets/javascripts/select-kit/components/toolbar-popup-menu-options.js.es6 b/app/assets/javascripts/select-kit/components/toolbar-popup-menu-options.js.es6
index 0c0ab1f730..8e25330942 100644
--- a/app/assets/javascripts/select-kit/components/toolbar-popup-menu-options.js.es6
+++ b/app/assets/javascripts/select-kit/components/toolbar-popup-menu-options.js.es6
@@ -1,10 +1,11 @@
+import { empty } from "@ember/object/computed";
import DropdownSelectBoxComponent from "select-kit/components/dropdown-select-box";
import discourseComputed from "discourse-common/utils/decorators";
export default DropdownSelectBoxComponent.extend({
pluginApiIdentifiers: ["toolbar-popup-menu-options"],
classNames: ["toolbar-popup-menu-options"],
- isHidden: Ember.computed.empty("computedContent"),
+ isHidden: empty("computedContent"),
showFullTitle: false,
@discourseComputed("title")
diff --git a/app/assets/javascripts/select-kit/components/topic-footer-mobile-dropdown.js.es6 b/app/assets/javascripts/select-kit/components/topic-footer-mobile-dropdown.js.es6
index 178caa43b5..07d665486c 100644
--- a/app/assets/javascripts/select-kit/components/topic-footer-mobile-dropdown.js.es6
+++ b/app/assets/javascripts/select-kit/components/topic-footer-mobile-dropdown.js.es6
@@ -1,3 +1,4 @@
+import { empty } from "@ember/object/computed";
import ComboBoxComponent from "select-kit/components/combo-box";
export default ComboBoxComponent.extend({
@@ -8,7 +9,7 @@ export default ComboBoxComponent.extend({
allowInitialValueMutation: false,
allowAutoSelectFirst: false,
nameProperty: "label",
- isHidden: Ember.computed.empty("content"),
+ isHidden: empty("content"),
computeHeaderContent() {
const content = this._super(...arguments);
From 562acb21caa6ec949444121bf0238c8828eceb99 Mon Sep 17 00:00:00 2001
From: Mark VanLandingham
Date: Fri, 8 Nov 2019 10:50:03 -0600
Subject: [PATCH 044/408] FIX: Ran prettier to fix build (#8323)
---
.../select-kit/components/combo-box/combo-box-header.js.es6 | 5 +----
.../dropdown-select-box/dropdown-select-box-row.js.es6 | 4 +---
2 files changed, 2 insertions(+), 7 deletions(-)
diff --git a/app/assets/javascripts/select-kit/components/combo-box/combo-box-header.js.es6 b/app/assets/javascripts/select-kit/components/combo-box/combo-box-header.js.es6
index f5bd519625..4dbe7d22c5 100644
--- a/app/assets/javascripts/select-kit/components/combo-box/combo-box-header.js.es6
+++ b/app/assets/javascripts/select-kit/components/combo-box/combo-box-header.js.es6
@@ -8,8 +8,5 @@ export default SelectKitHeaderComponent.extend({
clearable: alias("options.clearable"),
caretUpIcon: alias("options.caretUpIcon"),
caretDownIcon: alias("options.caretDownIcon"),
- shouldDisplayClearableButton: and(
- "clearable",
- "computedContent.hasSelection"
- )
+ shouldDisplayClearableButton: and("clearable", "computedContent.hasSelection")
});
diff --git a/app/assets/javascripts/select-kit/components/dropdown-select-box/dropdown-select-box-row.js.es6 b/app/assets/javascripts/select-kit/components/dropdown-select-box/dropdown-select-box-row.js.es6
index 9bbe5fa399..8169762e9a 100644
--- a/app/assets/javascripts/select-kit/components/dropdown-select-box/dropdown-select-box-row.js.es6
+++ b/app/assets/javascripts/select-kit/components/dropdown-select-box/dropdown-select-box-row.js.es6
@@ -6,7 +6,5 @@ export default SelectKitRowComponent.extend({
"select-kit/templates/components/dropdown-select-box/dropdown-select-box-row",
classNames: "dropdown-select-box-row",
- description: alias(
- "computedContent.originalContent.description"
- )
+ description: alias("computedContent.originalContent.description")
});
From 1990baa457080e6019df5ff25a7e17f9f0100603 Mon Sep 17 00:00:00 2001
From: Robin Ward
Date: Fri, 8 Nov 2019 12:47:39 -0500
Subject: [PATCH 045/408] REFACTOR: Remove constant definition for
discourse/routes/grouped
---
.../tilt/es6_module_transpiler_template.rb | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb b/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
index ee18d1d6d2..cd73d608e9 100644
--- a/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
+++ b/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
@@ -93,8 +93,8 @@ JS
"discourse/models/user",
"discourse/models/session",
"discourse/models/model",
- "discourse/models/post",
- "discourse/views/grouped"]
+ "discourse/models/post"
+ ]
)
@@whitelisted.include?(path) || path =~ /discourse\/mixins/
From 779ee3558dc98b744d7d404fcb0c40d770671967 Mon Sep 17 00:00:00 2001
From: Robin Ward
Date: Fri, 8 Nov 2019 12:52:39 -0500
Subject: [PATCH 046/408] REFACTOR: Remove `Discourse.UserAction` from code
---
.../discourse/models/user-stream.js.es6 | 2 +-
.../build-private-messages-route.js.es6 | 3 ++-
.../tilt/es6_module_transpiler_template.rb | 1 -
.../models/user-action-test.js.es6 | 19 ++++++++++---------
.../models/user-stream-test.js.es6 | 11 +++++------
5 files changed, 18 insertions(+), 18 deletions(-)
diff --git a/app/assets/javascripts/discourse/models/user-stream.js.es6 b/app/assets/javascripts/discourse/models/user-stream.js.es6
index d411b58cee..19e3d2ee62 100644
--- a/app/assets/javascripts/discourse/models/user-stream.js.es6
+++ b/app/assets/javascripts/discourse/models/user-stream.js.es6
@@ -19,7 +19,7 @@ export default RestModel.extend({
@discourseComputed("filter")
filterParam(filter) {
- if (filter === Discourse.UserAction.TYPES.replies) {
+ if (filter === UserAction.TYPES.replies) {
return [UserAction.TYPES.replies, UserAction.TYPES.quotes].join(",");
}
diff --git a/app/assets/javascripts/discourse/routes/build-private-messages-route.js.es6 b/app/assets/javascripts/discourse/routes/build-private-messages-route.js.es6
index 7331705f8f..abae09a255 100644
--- a/app/assets/javascripts/discourse/routes/build-private-messages-route.js.es6
+++ b/app/assets/javascripts/discourse/routes/build-private-messages-route.js.es6
@@ -1,10 +1,11 @@
import UserTopicListRoute from "discourse/routes/user-topic-list";
import { findOrResetCachedTopicList } from "discourse/lib/cached-topic-list";
+import UserAction from "discourse/models/user-action";
// A helper to build a user topic list route
export default (viewName, path, channel) => {
return UserTopicListRoute.extend({
- userActionType: Discourse.UserAction.TYPES.messages_received,
+ userActionType: UserAction.TYPES.messages_received,
titleToken() {
const key = viewName === "index" ? "inbox" : viewName;
diff --git a/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb b/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
index cd73d608e9..fde7cfdd39 100644
--- a/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
+++ b/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
@@ -86,7 +86,6 @@ JS
@@whitelisted ||= Set.new(
["discourse/models/nav-item",
- "discourse/models/user-action",
"discourse/routes/discourse",
"discourse/models/category",
"discourse/models/site",
diff --git a/test/javascripts/models/user-action-test.js.es6 b/test/javascripts/models/user-action-test.js.es6
index c39d7d828f..5139985807 100644
--- a/test/javascripts/models/user-action-test.js.es6
+++ b/test/javascripts/models/user-action-test.js.es6
@@ -1,21 +1,23 @@
-QUnit.module("Discourse.UserAction");
+import UserAction from "discourse/models/user-action";
+
+QUnit.module("model: user-action");
QUnit.test("collapsing likes", assert => {
- var actions = Discourse.UserAction.collapseStream([
- Discourse.UserAction.create({
- action_type: Discourse.UserAction.TYPES.likes_given,
+ var actions = UserAction.collapseStream([
+ UserAction.create({
+ action_type: UserAction.TYPES.likes_given,
topic_id: 1,
user_id: 1,
post_number: 1
}),
- Discourse.UserAction.create({
- action_type: Discourse.UserAction.TYPES.edits,
+ UserAction.create({
+ action_type: UserAction.TYPES.edits,
topic_id: 2,
user_id: 1,
post_number: 1
}),
- Discourse.UserAction.create({
- action_type: Discourse.UserAction.TYPES.likes_given,
+ UserAction.create({
+ action_type: UserAction.TYPES.likes_given,
topic_id: 1,
user_id: 2,
post_number: 1
@@ -23,7 +25,6 @@ QUnit.test("collapsing likes", assert => {
]);
assert.equal(actions.length, 2);
-
assert.equal(actions[0].get("children.length"), 1);
assert.equal(actions[0].get("children")[0].items.length, 2);
});
diff --git a/test/javascripts/models/user-stream-test.js.es6 b/test/javascripts/models/user-stream-test.js.es6
index d8be562c7a..a0fef54014 100644
--- a/test/javascripts/models/user-stream-test.js.es6
+++ b/test/javascripts/models/user-stream-test.js.es6
@@ -1,3 +1,5 @@
+import UserAction from "discourse/models/user-action";
+
QUnit.module("Discourse.UserStream");
QUnit.test("basics", assert => {
@@ -20,12 +22,9 @@ QUnit.test("filterParam", assert => {
// defaults to posts/topics
assert.equal(stream.get("filterParam"), "4,5");
- stream.set("filter", Discourse.UserAction.TYPES.likes_given);
- assert.equal(
- stream.get("filterParam"),
- Discourse.UserAction.TYPES.likes_given
- );
+ stream.set("filter", UserAction.TYPES.likes_given);
+ assert.equal(stream.get("filterParam"), UserAction.TYPES.likes_given);
- stream.set("filter", Discourse.UserAction.TYPES.replies);
+ stream.set("filter", UserAction.TYPES.replies);
assert.equal(stream.get("filterParam"), "6,9");
});
From 932c169d46f02ad184e1e9cce0de9693b479a11a Mon Sep 17 00:00:00 2001
From: Robin Ward
Date: Fri, 8 Nov 2019 12:56:13 -0500
Subject: [PATCH 047/408] REFACTOR: Remove Discourse.NavItem constants
---
.../javascripts/discourse/components/d-navigation.js.es6 | 3 ++-
app/assets/javascripts/discourse/models/nav-item.js.es6 | 2 +-
.../tilt/es6_module_transpiler_template.rb | 2 +-
test/javascripts/models/nav-item-test.js.es6 | 9 +++------
4 files changed, 7 insertions(+), 9 deletions(-)
diff --git a/app/assets/javascripts/discourse/components/d-navigation.js.es6 b/app/assets/javascripts/discourse/components/d-navigation.js.es6
index 0fe007a1ed..9ceea60eb4 100644
--- a/app/assets/javascripts/discourse/components/d-navigation.js.es6
+++ b/app/assets/javascripts/discourse/components/d-navigation.js.es6
@@ -1,4 +1,5 @@
import discourseComputed from "discourse-common/utils/decorators";
+import NavItem from "discourse/models/nav-item";
import { inject as service } from "@ember/service";
import Component from "@ember/component";
@@ -47,7 +48,7 @@ export default Component.extend({
}, {});
}
- return Discourse.NavItem.buildList(category, {
+ return NavItem.buildList(category, {
filterMode,
noSubcategories,
persistedQueryParams: params
diff --git a/app/assets/javascripts/discourse/models/nav-item.js.es6 b/app/assets/javascripts/discourse/models/nav-item.js.es6
index 0eff005189..7ecebc4839 100644
--- a/app/assets/javascripts/discourse/models/nav-item.js.es6
+++ b/app/assets/javascripts/discourse/models/nav-item.js.es6
@@ -185,7 +185,7 @@ NavItem.reopenClass({
}
items = items
- .map(i => Discourse.NavItem.fromText(i, args))
+ .map(i => NavItem.fromText(i, args))
.filter(
i => i !== null && !(category && i.get("name").indexOf("categor") === 0)
);
diff --git a/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb b/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
index fde7cfdd39..382417b8b4 100644
--- a/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
+++ b/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
@@ -85,7 +85,7 @@ JS
def whitelisted?(path)
@@whitelisted ||= Set.new(
- ["discourse/models/nav-item",
+ [
"discourse/routes/discourse",
"discourse/models/category",
"discourse/models/site",
diff --git a/test/javascripts/models/nav-item-test.js.es6 b/test/javascripts/models/nav-item-test.js.es6
index 429b669d7c..309ce31534 100644
--- a/test/javascripts/models/nav-item-test.js.es6
+++ b/test/javascripts/models/nav-item-test.js.es6
@@ -1,7 +1,8 @@
import { run } from "@ember/runloop";
import createStore from "helpers/create-store";
+import NavItem from "discourse/models/nav-item";
-QUnit.module("Discourse.NavItem", {
+QUnit.module("NavItem", {
beforeEach() {
run(function() {
const asianCategory = Discourse.Category.create({
@@ -17,11 +18,7 @@ QUnit.test("href", assert => {
assert.expect(4);
function href(text, expected, label) {
- assert.equal(
- Discourse.NavItem.fromText(text, {}).get("href"),
- expected,
- label
- );
+ assert.equal(NavItem.fromText(text, {}).get("href"), expected, label);
}
href("latest", "/latest", "latest");
From 7e44065bcbd46e06bd240f038693577b63bc58c9 Mon Sep 17 00:00:00 2001
From: Robin Ward
Date: Fri, 8 Nov 2019 13:13:13 -0500
Subject: [PATCH 048/408] REFACTOR: Migrate `Discourse.Post` to imports
---
.../discourse/controllers/history.js.es6 | 7 ++++---
.../javascripts/discourse/models/post.js.es6 | 6 +++---
.../tilt/es6_module_transpiler_template.rb | 3 +--
test/javascripts/models/composer-test.js.es6 | 7 ++++---
test/javascripts/models/post-stream-test.js.es6 | 7 ++++---
test/javascripts/models/post-test.js.es6 | 16 +++++++++-------
6 files changed, 25 insertions(+), 21 deletions(-)
diff --git a/app/assets/javascripts/discourse/controllers/history.js.es6 b/app/assets/javascripts/discourse/controllers/history.js.es6
index 79203ed563..7d68d2ab66 100644
--- a/app/assets/javascripts/discourse/controllers/history.js.es6
+++ b/app/assets/javascripts/discourse/controllers/history.js.es6
@@ -7,6 +7,7 @@ import { propertyGreaterThan, propertyLessThan } from "discourse/lib/computed";
import { on, observes } from "discourse-common/utils/decorators";
import { sanitizeAsync } from "discourse/lib/text";
import { iconHTML } from "discourse-common/lib/icon-library";
+import Post from "discourse/models/post";
function customTagArray(fieldName) {
return Ember.computed(fieldName, function() {
@@ -59,19 +60,19 @@ export default Controller.extend(ModalFunctionality, {
refresh(postId, postVersion) {
this.set("loading", true);
- Discourse.Post.loadRevision(postId, postVersion).then(result => {
+ Post.loadRevision(postId, postVersion).then(result => {
this.setProperties({ loading: false, model: result });
});
},
hide(postId, postVersion) {
- Discourse.Post.hideRevision(postId, postVersion).then(() =>
+ Post.hideRevision(postId, postVersion).then(() =>
this.refresh(postId, postVersion)
);
},
show(postId, postVersion) {
- Discourse.Post.showRevision(postId, postVersion).then(() =>
+ Post.showRevision(postId, postVersion).then(() =>
this.refresh(postId, postVersion)
);
},
diff --git a/app/assets/javascripts/discourse/models/post.js.es6 b/app/assets/javascripts/discourse/models/post.js.es6
index 83a18d9a12..b49aaea747 100644
--- a/app/assets/javascripts/discourse/models/post.js.es6
+++ b/app/assets/javascripts/discourse/models/post.js.es6
@@ -16,7 +16,7 @@ import Composer from "discourse/models/composer";
import { Promise } from "rsvp";
const Post = RestModel.extend({
- // TODO: Remove this once one instantiate all `Discourse.Post` models via the store.
+ // TODO: Remove this once one instantiate all `Post` models via the store.
siteSettings: Ember.computed({
get() {
return Discourse.SiteSettings;
@@ -320,7 +320,7 @@ const Post = RestModel.extend({
// need to wait to hear back from server (stuff may not be loaded)
- return Discourse.Post.updateBookmark(this.id, this.bookmarked)
+ return Post.updateBookmark(this.id, this.bookmarked)
.then(result => {
this.set("topic.bookmarked", result.topic_bookmarked);
this.appEvents.trigger("page:bookmark-post-toggled", this);
@@ -417,7 +417,7 @@ Post.reopenClass({
loadQuote(postId) {
return ajax(`/posts/${postId}.json`).then(result => {
- const post = Discourse.Post.create(result);
+ const post = Post.create(result);
return Quote.build(post, post.raw, { raw: true, full: true });
});
},
diff --git a/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb b/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
index 382417b8b4..c129e66001 100644
--- a/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
+++ b/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
@@ -91,8 +91,7 @@ JS
"discourse/models/site",
"discourse/models/user",
"discourse/models/session",
- "discourse/models/model",
- "discourse/models/post"
+ "discourse/models/model"
]
)
diff --git a/test/javascripts/models/composer-test.js.es6 b/test/javascripts/models/composer-test.js.es6
index 78c823b2be..cd3135b74f 100644
--- a/test/javascripts/models/composer-test.js.es6
+++ b/test/javascripts/models/composer-test.js.es6
@@ -2,6 +2,7 @@ import EmberObject from "@ember/object";
import { currentUser } from "helpers/qunit-helpers";
import AppEvents from "discourse/services/app-events";
import Composer from "discourse/models/composer";
+import Post from "discourse/models/post";
import createStore from "helpers/create-store";
QUnit.module("model:composer");
@@ -247,7 +248,7 @@ QUnit.test("editingFirstPost", assert => {
const composer = createComposer();
assert.ok(!composer.get("editingFirstPost"), "it's false by default");
- const post = Discourse.Post.create({ id: 123, post_number: 2 });
+ const post = Post.create({ id: 123, post_number: 2 });
composer.setProperties({ post: post, action: Composer.EDIT });
assert.ok(
!composer.get("editingFirstPost"),
@@ -265,7 +266,7 @@ QUnit.test("clearState", assert => {
const composer = createComposer({
originalText: "asdf",
reply: "asdf2",
- post: Discourse.Post.create({ id: 1 }),
+ post: Post.create({ id: 1 }),
title: "wat"
});
@@ -329,7 +330,7 @@ QUnit.test("Title length for static page topics as admin", assert => {
Discourse.SiteSettings.max_topic_title_length = 10;
const composer = createComposer();
- const post = Discourse.Post.create({
+ const post = Post.create({
id: 123,
post_number: 2,
static_doc: true
diff --git a/test/javascripts/models/post-stream-test.js.es6 b/test/javascripts/models/post-stream-test.js.es6
index eb99d811af..49b6018e20 100644
--- a/test/javascripts/models/post-stream-test.js.es6
+++ b/test/javascripts/models/post-stream-test.js.es6
@@ -1,7 +1,8 @@
-QUnit.module("model:post-stream");
-
+import Post from "discourse/models/post";
import createStore from "helpers/create-store";
+QUnit.module("model:post-stream");
+
const buildStream = function(id, stream) {
const store = createStore();
const topic = store.createRecord("topic", { id, chunk_size: 5 });
@@ -173,7 +174,7 @@ QUnit.test("updateFromJson", assert => {
});
assert.equal(postStream.get("posts.length"), 1, "it loaded the posts");
- assert.containsInstance(postStream.get("posts"), Discourse.Post);
+ assert.containsInstance(postStream.get("posts"), Post);
assert.equal(postStream.get("extra_property"), 12);
});
diff --git a/test/javascripts/models/post-test.js.es6 b/test/javascripts/models/post-test.js.es6
index afe69d03ad..5a7aa34520 100644
--- a/test/javascripts/models/post-test.js.es6
+++ b/test/javascripts/models/post-test.js.es6
@@ -1,7 +1,9 @@
-QUnit.module("Discourse.Post");
+import Post from "discourse/models/post";
+
+QUnit.module("model: Post");
var buildPost = function(args) {
- return Discourse.Post.create(
+ return Post.create(
_.merge(
{
id: 1,
@@ -14,13 +16,13 @@ var buildPost = function(args) {
};
QUnit.test("defaults", assert => {
- var post = Discourse.Post.create({ id: 1 });
+ var post = Post.create({ id: 1 });
assert.blank(post.get("deleted_at"), "it has no deleted_at by default");
assert.blank(post.get("deleted_by"), "there is no deleted_by by default");
});
QUnit.test("new_user", assert => {
- var post = Discourse.Post.create({ trust_level: 0 });
+ var post = Post.create({ trust_level: 0 });
assert.ok(post.get("new_user"), "post is from a new user");
post.set("trust_level", 1);
@@ -28,7 +30,7 @@ QUnit.test("new_user", assert => {
});
QUnit.test("firstPost", assert => {
- var post = Discourse.Post.create({ post_number: 1 });
+ var post = Post.create({ post_number: 1 });
assert.ok(post.get("firstPost"), "it's the first post");
post.set("post_number", 10);
@@ -36,13 +38,13 @@ QUnit.test("firstPost", assert => {
});
QUnit.test("updateFromPost", assert => {
- var post = Discourse.Post.create({
+ var post = Post.create({
post_number: 1,
raw: "hello world"
});
post.updateFromPost(
- Discourse.Post.create({
+ Post.create({
raw: "different raw",
wat: function() {
return 123;
From e51efce356f1b8ea59cfe23f82963d2c0402f309 Mon Sep 17 00:00:00 2001
From: Mark VanLandingham
Date: Fri, 8 Nov 2019 12:28:11 -0600
Subject: [PATCH 049/408] DEV: Remove all instances of Ember.computed (#8324)
---
.../admin/controllers/admin-dashboard-general.js.es6 | 3 ++-
app/assets/javascripts/admin/models/api-key.js.es6 | 3 ++-
app/assets/javascripts/discourse-loader.js | 1 +
app/assets/javascripts/discourse.js.es6 | 3 ++-
.../discourse/components/about-page-users.js.es6 | 3 ++-
.../discourse/components/date-time-input.js.es6 | 5 +++--
.../discourse/controllers/composer.js.es6 | 10 ++++++++--
.../javascripts/discourse/controllers/history.js.es6 | 11 +++++++++--
.../lib/register-topic-footer-button.js.es6 | 3 ++-
.../discourse/mixins/buffered-content.js.es6 | 3 ++-
app/assets/javascripts/discourse/models/post.js.es6 | 12 +++++++++---
app/assets/javascripts/discourse/models/user.js.es6 | 4 ++--
.../discourse/widgets/post-small-action.js.es6 | 3 ++-
app/assets/javascripts/preload-store.js.es6 | 8 +++++---
.../components/multi-select/selected-name.js.es6 | 4 ++--
app/assets/javascripts/wizard/lib/ajax.js.es6 | 3 ++-
app/assets/javascripts/wizard/lib/preview.js.es6 | 9 +++++----
17 files changed, 60 insertions(+), 28 deletions(-)
diff --git a/app/assets/javascripts/admin/controllers/admin-dashboard-general.js.es6 b/app/assets/javascripts/admin/controllers/admin-dashboard-general.js.es6
index c91f09350d..ea7dc31dde 100644
--- a/app/assets/javascripts/admin/controllers/admin-dashboard-general.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-dashboard-general.js.es6
@@ -6,9 +6,10 @@ import { setting } from "discourse/lib/computed";
import AdminDashboard from "admin/models/admin-dashboard";
import Report from "admin/models/report";
import PeriodComputationMixin from "admin/mixins/period-computation";
+import computed from "@ember/object/computed";
function staticReport(reportType) {
- return Ember.computed("reports.[]", function() {
+ return computed("reports.[]", function() {
return makeArray(this.reports).find(report => report.type === reportType);
});
}
diff --git a/app/assets/javascripts/admin/models/api-key.js.es6 b/app/assets/javascripts/admin/models/api-key.js.es6
index 4b77e23c4a..bc818fb8e2 100644
--- a/app/assets/javascripts/admin/models/api-key.js.es6
+++ b/app/assets/javascripts/admin/models/api-key.js.es6
@@ -2,9 +2,10 @@ import discourseComputed from "discourse-common/utils/decorators";
import AdminUser from "admin/models/admin-user";
import RestModel from "discourse/models/rest";
import { ajax } from "discourse/lib/ajax";
+import computed from "@ember/object/computed";
const ApiKey = RestModel.extend({
- user: Ember.computed("_user", {
+ user: computed("_user", {
get() {
return this._user;
},
diff --git a/app/assets/javascripts/discourse-loader.js b/app/assets/javascripts/discourse-loader.js
index a8cd03b800..2f7b0b9b28 100644
--- a/app/assets/javascripts/discourse-loader.js
+++ b/app/assets/javascripts/discourse-loader.js
@@ -81,6 +81,7 @@ var define, requirejs;
isEmpty: Ember.isEmpty
},
rsvp: {
+ default: Ember.RSVP,
Promise: Ember.RSVP.Promise,
hash: Ember.RSVP.hash,
all: Ember.RSVP.all
diff --git a/app/assets/javascripts/discourse.js.es6 b/app/assets/javascripts/discourse.js.es6
index 2f45653ed1..c56acf9dc8 100644
--- a/app/assets/javascripts/discourse.js.es6
+++ b/app/assets/javascripts/discourse.js.es6
@@ -4,6 +4,7 @@ import {
default as discourseComputed,
observes
} from "discourse-common/utils/decorators";
+import computed from "@ember/object/computed";
import FocusEvent from "discourse-common/mixins/focus-event";
const _pluginCallbacks = [];
@@ -188,7 +189,7 @@ const Discourse = Ember.Application.extend(FocusEvent, {
_pluginCallbacks.push({ version, code });
},
- assetVersion: Ember.computed({
+ assetVersion: computed({
get() {
return this.currentAssetVersion;
},
diff --git a/app/assets/javascripts/discourse/components/about-page-users.js.es6 b/app/assets/javascripts/discourse/components/about-page-users.js.es6
index 7d4ff773ba..e064c67f29 100644
--- a/app/assets/javascripts/discourse/components/about-page-users.js.es6
+++ b/app/assets/javascripts/discourse/components/about-page-users.js.es6
@@ -3,9 +3,10 @@ import { userPath } from "discourse/lib/url";
import { formatUsername, escapeExpression } from "discourse/lib/utilities";
import { normalize } from "discourse/components/user-info";
import { renderAvatar } from "discourse/helpers/user-avatar";
+import computed from "@ember/object/computed";
export default Component.extend({
- usersTemplates: Ember.computed("users.[]", function() {
+ usersTemplates: computed("users.[]", function() {
return (this.users || []).map(user => {
let name = "";
if (user.name && normalize(user.username) !== normalize(user.name)) {
diff --git a/app/assets/javascripts/discourse/components/date-time-input.js.es6 b/app/assets/javascripts/discourse/components/date-time-input.js.es6
index c83483bc7d..e6dc3d481b 100644
--- a/app/assets/javascripts/discourse/components/date-time-input.js.es6
+++ b/app/assets/javascripts/discourse/components/date-time-input.js.es6
@@ -1,15 +1,16 @@
import Component from "@ember/component";
+import computed from "@ember/object/computed";
export default Component.extend({
classNames: ["d-date-time-input"],
date: null,
showTime: true,
- _hours: Ember.computed("date", function() {
+ _hours: computed("date", function() {
return this.date ? this.date.getHours() : null;
}),
- _minutes: Ember.computed("date", function() {
+ _minutes: computed("date", function() {
return this.date ? this.date.getMinutes() : null;
}),
diff --git a/app/assets/javascripts/discourse/controllers/composer.js.es6 b/app/assets/javascripts/discourse/controllers/composer.js.es6
index 818f70c089..51d4b3202e 100644
--- a/app/assets/javascripts/discourse/controllers/composer.js.es6
+++ b/app/assets/javascripts/discourse/controllers/composer.js.es6
@@ -1,5 +1,11 @@
import { isEmpty } from "@ember/utils";
-import { and, or, alias, reads } from "@ember/object/computed";
+import {
+ default as computed,
+ and,
+ or,
+ alias,
+ reads
+} from "@ember/object/computed";
import { debounce } from "@ember/runloop";
import { inject as service } from "@ember/service";
import { inject } from "@ember/controller";
@@ -158,7 +164,7 @@ export default Controller.extend({
return "title";
},
- showToolbar: Ember.computed({
+ showToolbar: computed({
get() {
const keyValueStore = getOwner(this).lookup("key-value-store:main");
const storedVal = keyValueStore.get("toolbar-enabled");
diff --git a/app/assets/javascripts/discourse/controllers/history.js.es6 b/app/assets/javascripts/discourse/controllers/history.js.es6
index 7d68d2ab66..a457060722 100644
--- a/app/assets/javascripts/discourse/controllers/history.js.es6
+++ b/app/assets/javascripts/discourse/controllers/history.js.es6
@@ -1,5 +1,12 @@
import discourseComputed from "discourse-common/utils/decorators";
-import { alias, gt, not, or, equal } from "@ember/object/computed";
+import {
+ default as computed,
+ alias,
+ gt,
+ not,
+ or,
+ equal
+} from "@ember/object/computed";
import Controller from "@ember/controller";
import ModalFunctionality from "discourse/mixins/modal-functionality";
import { categoryBadgeHTML } from "discourse/helpers/category-link";
@@ -10,7 +17,7 @@ import { iconHTML } from "discourse-common/lib/icon-library";
import Post from "discourse/models/post";
function customTagArray(fieldName) {
- return Ember.computed(fieldName, function() {
+ return computed(fieldName, function() {
var val = this.get(fieldName);
if (!val) {
return val;
diff --git a/app/assets/javascripts/discourse/lib/register-topic-footer-button.js.es6 b/app/assets/javascripts/discourse/lib/register-topic-footer-button.js.es6
index 6b7bdf63b0..fa72ebee6e 100644
--- a/app/assets/javascripts/discourse/lib/register-topic-footer-button.js.es6
+++ b/app/assets/javascripts/discourse/lib/register-topic-footer-button.js.es6
@@ -1,4 +1,5 @@
import error from "@ember/error";
+import computed from "@ember/object/computed";
let _topicFooterButtons = {};
@@ -70,7 +71,7 @@ export function getTopicFooterButtons() {
.filter(x => x)
);
- return Ember.computed(...dependentKeys, {
+ return computed(...dependentKeys, {
get() {
const _isFunction = descriptor =>
descriptor && typeof descriptor === "function";
diff --git a/app/assets/javascripts/discourse/mixins/buffered-content.js.es6 b/app/assets/javascripts/discourse/mixins/buffered-content.js.es6
index 08723e1486..1e5de0f9ef 100644
--- a/app/assets/javascripts/discourse/mixins/buffered-content.js.es6
+++ b/app/assets/javascripts/discourse/mixins/buffered-content.js.es6
@@ -1,10 +1,11 @@
import EmberObjectProxy from "@ember/object/proxy";
import Mixin from "@ember/object/mixin";
+import computed from "@ember/object/computed";
/* global BufferedProxy: true */
export function bufferedProperty(property) {
const mixin = {
- buffered: Ember.computed(property, function() {
+ buffered: computed(property, function() {
return EmberObjectProxy.extend(BufferedProxy).create({
content: this.get(property)
});
diff --git a/app/assets/javascripts/discourse/models/post.js.es6 b/app/assets/javascripts/discourse/models/post.js.es6
index b49aaea747..eda9bed816 100644
--- a/app/assets/javascripts/discourse/models/post.js.es6
+++ b/app/assets/javascripts/discourse/models/post.js.es6
@@ -1,7 +1,13 @@
import discourseComputed from "discourse-common/utils/decorators";
import { get } from "@ember/object";
import { isEmpty } from "@ember/utils";
-import { equal, and, or, not } from "@ember/object/computed";
+import {
+ default as computed,
+ equal,
+ and,
+ or,
+ not
+} from "@ember/object/computed";
import EmberObject from "@ember/object";
import { ajax } from "discourse/lib/ajax";
import RestModel from "discourse/models/rest";
@@ -16,8 +22,8 @@ import Composer from "discourse/models/composer";
import { Promise } from "rsvp";
const Post = RestModel.extend({
- // TODO: Remove this once one instantiate all `Post` models via the store.
- siteSettings: Ember.computed({
+ // TODO: Remove this once one instantiate all `Discourse.Post` models via the store.
+ siteSettings: computed({
get() {
return Discourse.SiteSettings;
},
diff --git a/app/assets/javascripts/discourse/models/user.js.es6 b/app/assets/javascripts/discourse/models/user.js.es6
index 8b7289d5ce..77bc32371c 100644
--- a/app/assets/javascripts/discourse/models/user.js.es6
+++ b/app/assets/javascripts/discourse/models/user.js.es6
@@ -1,5 +1,5 @@
import { isEmpty } from "@ember/utils";
-import { gt, equal, or } from "@ember/object/computed";
+import { default as computed, gt, equal, or } from "@ember/object/computed";
import EmberObject from "@ember/object";
import { ajax } from "discourse/lib/ajax";
import { url } from "discourse/lib/computed";
@@ -63,7 +63,7 @@ const User = RestModel.extend({
return UserDraftsStream.create({ user: this });
},
- staff: Ember.computed("admin", "moderator", {
+ staff: computed("admin", "moderator", {
get() {
return this.admin || this.moderator;
},
diff --git a/app/assets/javascripts/discourse/widgets/post-small-action.js.es6 b/app/assets/javascripts/discourse/widgets/post-small-action.js.es6
index ea45f0ed7c..93fadb5c24 100644
--- a/app/assets/javascripts/discourse/widgets/post-small-action.js.es6
+++ b/app/assets/javascripts/discourse/widgets/post-small-action.js.es6
@@ -5,6 +5,7 @@ import { h } from "virtual-dom";
import { avatarFor } from "discourse/widgets/post";
import { userPath } from "discourse/lib/url";
import { autoUpdatingRelativeAge } from "discourse/lib/formatter";
+import computed from "@ember/object/computed";
export function actionDescriptionHtml(actionCode, createdAt, username) {
const dt = new Date(createdAt);
@@ -22,7 +23,7 @@ export function actionDescriptionHtml(actionCode, createdAt, username) {
}
export function actionDescription(actionCode, createdAt, username) {
- return Ember.computed(actionCode, createdAt, function() {
+ return computed(actionCode, createdAt, function() {
const ac = this.get(actionCode);
if (ac) {
return actionDescriptionHtml(ac, this.get(createdAt), this.get(username));
diff --git a/app/assets/javascripts/preload-store.js.es6 b/app/assets/javascripts/preload-store.js.es6
index b096afd4c1..fae006ff6a 100644
--- a/app/assets/javascripts/preload-store.js.es6
+++ b/app/assets/javascripts/preload-store.js.es6
@@ -4,6 +4,8 @@
@class PreloadStore
**/
+import { Promise } from "rsvp";
+
export default {
data: {},
@@ -19,13 +21,13 @@ export default {
**/
getAndRemove(key, finder) {
if (this.data[key]) {
- var promise = Ember.RSVP.resolve(this.data[key]);
+ var promise = Promise.resolve(this.data[key]);
delete this.data[key];
return promise;
}
if (finder) {
- return new Ember.RSVP.Promise(function(resolve, reject) {
+ return new Promise(function(resolve, reject) {
var result = finder();
// If the finder returns a promise, we support that too
@@ -39,7 +41,7 @@ export default {
});
}
- return Ember.RSVP.resolve(null);
+ return Promise.resolve(null);
},
get(key) {
diff --git a/app/assets/javascripts/select-kit/components/multi-select/selected-name.js.es6 b/app/assets/javascripts/select-kit/components/multi-select/selected-name.js.es6
index df37ac012c..f5736ee609 100644
--- a/app/assets/javascripts/select-kit/components/multi-select/selected-name.js.es6
+++ b/app/assets/javascripts/select-kit/components/multi-select/selected-name.js.es6
@@ -1,4 +1,4 @@
-import { or, alias } from "@ember/object/computed";
+import { default as computed, or, alias } from "@ember/object/computed";
import Component from "@ember/component";
import discourseComputed from "discourse-common/utils/decorators";
@@ -38,7 +38,7 @@ export default Component.extend({
value: alias("computedContent.value"),
- isLocked: Ember.computed("computedContent.locked", function() {
+ isLocked: computed("computedContent.locked", function() {
return this.getWithDefault("computedContent.locked", false);
}),
diff --git a/app/assets/javascripts/wizard/lib/ajax.js.es6 b/app/assets/javascripts/wizard/lib/ajax.js.es6
index 64cc9571cc..afb8b23ce2 100644
--- a/app/assets/javascripts/wizard/lib/ajax.js.es6
+++ b/app/assets/javascripts/wizard/lib/ajax.js.es6
@@ -1,5 +1,6 @@
import { run } from "@ember/runloop";
import getUrl from "discourse-common/lib/get-url";
+import { Promise } from "rsvp";
import jQuery from "jquery";
let token;
@@ -13,7 +14,7 @@ export function getToken() {
}
export function ajax(args) {
- return new Ember.RSVP.Promise((resolve, reject) => {
+ return new Promise((resolve, reject) => {
args.headers = { "X-CSRF-Token": getToken() };
args.success = data => run(null, resolve, data);
args.error = xhr => run(null, reject, xhr);
diff --git a/app/assets/javascripts/wizard/lib/preview.js.es6 b/app/assets/javascripts/wizard/lib/preview.js.es6
index d597bfae53..3f4d9fdf10 100644
--- a/app/assets/javascripts/wizard/lib/preview.js.es6
+++ b/app/assets/javascripts/wizard/lib/preview.js.es6
@@ -2,6 +2,7 @@ import { scheduleOnce } from "@ember/runloop";
import Component from "@ember/component";
/*eslint no-bitwise:0 */
import getUrl from "discourse-common/lib/get-url";
+import { Promise } from "rsvp";
export const LOREM = `
Lorem ipsum dolor sit amet,
@@ -56,13 +57,13 @@ export function createPreviewComponent(width, height, obj) {
loadImages() {
const images = this.images();
if (images) {
- return Ember.RSVP.Promise.all(
+ return Promise.all(
Object.keys(images).map(id => {
return loadImage(images[id]).then(img => (this[id] = img));
})
);
}
- return Ember.RSVP.Promise.resolve();
+ return Promise.resolve();
},
reload() {
@@ -270,12 +271,12 @@ export function createPreviewComponent(width, height, obj) {
function loadImage(src) {
if (!src) {
- return Ember.RSVP.Promise.resolve();
+ return Promise.resolve();
}
const img = new Image();
img.src = getUrl(src);
- return new Ember.RSVP.Promise(resolve => (img.onload = () => resolve(img)));
+ return new Promise(resolve => (img.onload = () => resolve(img)));
}
export function parseColor(color) {
From 7ac2a55588da08ce06e841f5d80420b7891788d5 Mon Sep 17 00:00:00 2001
From: Robin Ward
Date: Fri, 8 Nov 2019 13:30:41 -0500
Subject: [PATCH 050/408] REFACTOR: Remove `Discourse.Category` constants
---
.../admin/components/embeddable-host.js.es6 | 3 +-
.../site-settings/category-list.js.es6 | 3 +-
.../components/search-advanced-options.js.es6 | 7 ++--
.../discourse/components/tag-list.js.es6 | 3 +-
.../discourse/controllers/discovery.js.es6 | 3 +-
.../controllers/edit-category.js.es6 | 3 +-
.../discourse/controllers/history.js.es6 | 10 ++---
.../discourse/controllers/tags-show.js.es6 | 3 +-
.../controllers/topic-bulk-actions.js.es6 | 3 +-
.../discourse/helpers/category-link.js.es6 | 7 ++--
.../discourse/models/category-list.js.es6 | 3 +-
.../discourse/models/category.js.es6 | 11 ++++++
.../discourse/models/nav-item.js.es6 | 7 ++--
.../javascripts/discourse/models/store.js.es6 | 3 +-
.../discourse/models/topic-list.js.es6 | 3 +-
.../models/topic-tracking-state.js.es6 | 9 +++--
.../javascripts/discourse/models/topic.js.es6 | 3 +-
.../discourse/models/user-action.js.es6 | 3 +-
.../javascripts/discourse/models/user.js.es6 | 11 ++----
.../routes/build-category-route.js.es6 | 6 +--
.../discourse/routes/tags-show.js.es6 | 6 +--
.../widgets/hamburger-categories.js.es6 | 3 +-
.../components/category-drop.js.es6 | 6 +--
.../tilt/es6_module_transpiler_template.rb | 1 -
test/javascripts/models/category-test.js.es6 | 39 +++++++++----------
test/javascripts/models/nav-item-test.js.es6 | 3 +-
test/javascripts/models/topic-test.js.es6 | 8 ++--
.../models/topic-tracking-state-test.js.es6 | 3 +-
28 files changed, 95 insertions(+), 78 deletions(-)
diff --git a/app/assets/javascripts/admin/components/embeddable-host.js.es6 b/app/assets/javascripts/admin/components/embeddable-host.js.es6
index 054acc744c..1d853b8986 100644
--- a/app/assets/javascripts/admin/components/embeddable-host.js.es6
+++ b/app/assets/javascripts/admin/components/embeddable-host.js.es6
@@ -6,6 +6,7 @@ import Component from "@ember/component";
import { bufferedProperty } from "discourse/mixins/buffered-content";
import { on, observes } from "discourse-common/utils/decorators";
import { popupAjaxError } from "discourse/lib/ajax-error";
+import Category from "discourse/models/category";
export default Component.extend(bufferedProperty("host"), {
editToggled: false,
@@ -50,7 +51,7 @@ export default Component.extend(bufferedProperty("host"), {
host
.save(props)
.then(() => {
- host.set("category", Discourse.Category.findById(this.categoryId));
+ host.set("category", Category.findById(this.categoryId));
this.set("editToggled", false);
})
.catch(popupAjaxError);
diff --git a/app/assets/javascripts/admin/components/site-settings/category-list.js.es6 b/app/assets/javascripts/admin/components/site-settings/category-list.js.es6
index 5d4b68b19b..ff83e13e52 100644
--- a/app/assets/javascripts/admin/components/site-settings/category-list.js.es6
+++ b/app/assets/javascripts/admin/components/site-settings/category-list.js.es6
@@ -1,11 +1,12 @@
import discourseComputed from "discourse-common/utils/decorators";
import Component from "@ember/component";
+import Category from "discourse/models/category";
export default Component.extend({
@discourseComputed("value")
selectedCategories: {
get(value) {
- return Discourse.Category.findByIds(value.split("|"));
+ return Category.findByIds(value.split("|"));
},
set(value) {
this.set("value", value.mapBy("id").join("|"));
diff --git a/app/assets/javascripts/discourse/components/search-advanced-options.js.es6 b/app/assets/javascripts/discourse/components/search-advanced-options.js.es6
index 42e85897ea..f0a3d817c1 100644
--- a/app/assets/javascripts/discourse/components/search-advanced-options.js.es6
+++ b/app/assets/javascripts/discourse/components/search-advanced-options.js.es6
@@ -5,6 +5,7 @@ import { observes } from "discourse-common/utils/decorators";
import { escapeExpression } from "discourse/lib/utilities";
import Group from "discourse/models/group";
import Badge from "discourse/models/badge";
+import Category from "discourse/models/category";
const REGEXP_BLOCKS = /(([^" \t\n\x0B\f\r]+)?(("[^"]+")?))/g;
@@ -224,7 +225,7 @@ export default Component.extend({
.replace(REGEXP_CATEGORY_PREFIX, "")
.split(":");
if (subcategories.length > 1) {
- const userInput = Discourse.Category.findBySlug(
+ const userInput = Category.findBySlug(
subcategories[1],
subcategories[0]
);
@@ -234,14 +235,14 @@ export default Component.extend({
)
this.set("searchedTerms.category", userInput);
} else if (isNaN(subcategories)) {
- const userInput = Discourse.Category.findSingleBySlug(subcategories[0]);
+ const userInput = Category.findSingleBySlug(subcategories[0]);
if (
(!existingInput && userInput) ||
(existingInput && userInput && existingInput.id !== userInput.id)
)
this.set("searchedTerms.category", userInput);
} else {
- const userInput = Discourse.Category.findById(subcategories[0]);
+ const userInput = Category.findById(subcategories[0]);
if (
(!existingInput && userInput) ||
(existingInput && userInput && existingInput.id !== userInput.id)
diff --git a/app/assets/javascripts/discourse/components/tag-list.js.es6 b/app/assets/javascripts/discourse/components/tag-list.js.es6
index ee6de7fa3a..a6472a1c6e 100644
--- a/app/assets/javascripts/discourse/components/tag-list.js.es6
+++ b/app/assets/javascripts/discourse/components/tag-list.js.es6
@@ -1,6 +1,7 @@
import discourseComputed from "discourse-common/utils/decorators";
import { sort } from "@ember/object/computed";
import Component from "@ember/component";
+import Category from "discourse/models/category";
export default Component.extend({
classNameBindings: [":tag-list", "categoryClass", "tagGroupNameClass"],
@@ -15,7 +16,7 @@ export default Component.extend({
@discourseComputed("categoryId")
category(categoryId) {
- return categoryId && Discourse.Category.findById(categoryId);
+ return categoryId && Category.findById(categoryId);
},
@discourseComputed("category.fullSlug")
diff --git a/app/assets/javascripts/discourse/controllers/discovery.js.es6 b/app/assets/javascripts/discourse/controllers/discovery.js.es6
index 6345bb8aa2..c797ed7565 100644
--- a/app/assets/javascripts/discourse/controllers/discovery.js.es6
+++ b/app/assets/javascripts/discourse/controllers/discovery.js.es6
@@ -2,6 +2,7 @@ import { alias, not } from "@ember/object/computed";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
import DiscourseURL from "discourse/lib/url";
+import Category from "discourse/models/category";
export default Controller.extend({
discoveryTopics: inject("discovery/topics"),
@@ -25,7 +26,7 @@ export default Controller.extend({
if (category) {
url =
"/c/" +
- Discourse.Category.slugFor(category) +
+ Category.slugFor(category) +
(this.noSubcategories ? "/none" : "") +
"/l";
}
diff --git a/app/assets/javascripts/discourse/controllers/edit-category.js.es6 b/app/assets/javascripts/discourse/controllers/edit-category.js.es6
index 21b1e5c5ac..a529f05e87 100644
--- a/app/assets/javascripts/discourse/controllers/edit-category.js.es6
+++ b/app/assets/javascripts/discourse/controllers/edit-category.js.es6
@@ -8,6 +8,7 @@ import {
on,
observes
} from "discourse-common/utils/decorators";
+import Category from "discourse/models/category";
export default Controller.extend(ModalFunctionality, {
selectedTab: null,
@@ -106,7 +107,7 @@ export default Controller.extend(ModalFunctionality, {
slug: result.category.slug,
id: result.category.id
});
- DiscourseURL.redirectTo("/c/" + Discourse.Category.slugFor(model));
+ DiscourseURL.redirectTo("/c/" + Category.slugFor(model));
})
.catch(error => {
this.flash(extractError(error), "error");
diff --git a/app/assets/javascripts/discourse/controllers/history.js.es6 b/app/assets/javascripts/discourse/controllers/history.js.es6
index a457060722..99a5b2194d 100644
--- a/app/assets/javascripts/discourse/controllers/history.js.es6
+++ b/app/assets/javascripts/discourse/controllers/history.js.es6
@@ -15,6 +15,7 @@ import { on, observes } from "discourse-common/utils/decorators";
import { sanitizeAsync } from "discourse/lib/text";
import { iconHTML } from "discourse-common/lib/icon-library";
import Post from "discourse/models/post";
+import Category from "discourse/models/category";
function customTagArray(fieldName) {
return computed(fieldName, function() {
@@ -95,10 +96,7 @@ export default Controller.extend(ModalFunctionality, {
post.set("topic.fancy_title", result.topic.fancy_title);
}
if (result.category_id) {
- post.set(
- "topic.category",
- Discourse.Category.findById(result.category_id)
- );
+ post.set("topic.category", Category.findById(result.category_id));
}
this.send("closeModal");
})
@@ -226,7 +224,7 @@ export default Controller.extend(ModalFunctionality, {
@discourseComputed("model.category_id_changes")
previousCategory(changes) {
if (changes) {
- var category = Discourse.Category.findById(changes["previous"]);
+ var category = Category.findById(changes["previous"]);
return categoryBadgeHTML(category, { allowUncategorized: true });
}
},
@@ -234,7 +232,7 @@ export default Controller.extend(ModalFunctionality, {
@discourseComputed("model.category_id_changes")
currentCategory(changes) {
if (changes) {
- var category = Discourse.Category.findById(changes["current"]);
+ var category = Category.findById(changes["current"]);
return categoryBadgeHTML(category, { allowUncategorized: true });
}
},
diff --git a/app/assets/javascripts/discourse/controllers/tags-show.js.es6 b/app/assets/javascripts/discourse/controllers/tags-show.js.es6
index 631f85d7df..5f51ee9efb 100644
--- a/app/assets/javascripts/discourse/controllers/tags-show.js.es6
+++ b/app/assets/javascripts/discourse/controllers/tags-show.js.es6
@@ -11,6 +11,7 @@ import {
extraNavItemProperties,
customNavItemHref
} from "discourse/models/nav-item";
+import Category from "discourse/models/category";
if (extraNavItemProperties) {
extraNavItemProperties(function(text, opts) {
@@ -36,7 +37,7 @@ if (customNavItemHref) {
if (category) {
path += "c/";
- path += Discourse.Category.slugFor(category);
+ path += Category.slugFor(category);
if (navItem.get("noSubcategories")) {
path += "/none";
}
diff --git a/app/assets/javascripts/discourse/controllers/topic-bulk-actions.js.es6 b/app/assets/javascripts/discourse/controllers/topic-bulk-actions.js.es6
index bd78a3002b..5382f8cc3f 100644
--- a/app/assets/javascripts/discourse/controllers/topic-bulk-actions.js.es6
+++ b/app/assets/javascripts/discourse/controllers/topic-bulk-actions.js.es6
@@ -2,6 +2,7 @@ import { empty, alias } from "@ember/object/computed";
import Controller from "@ember/controller";
import ModalFunctionality from "discourse/mixins/modal-functionality";
import Topic from "discourse/models/topic";
+import Category from "discourse/models/category";
const _buttons = [];
@@ -175,7 +176,7 @@ export default Controller.extend(ModalFunctionality, {
changeCategory() {
const categoryId = parseInt(this.newCategoryId, 10) || 0;
- const category = Discourse.Category.findById(categoryId);
+ const category = Category.findById(categoryId);
this.perform({ type: "change_category", category_id: categoryId }).then(
topics => {
diff --git a/app/assets/javascripts/discourse/helpers/category-link.js.es6 b/app/assets/javascripts/discourse/helpers/category-link.js.es6
index c76382c8df..0efb208def 100644
--- a/app/assets/javascripts/discourse/helpers/category-link.js.es6
+++ b/app/assets/javascripts/discourse/helpers/category-link.js.es6
@@ -2,6 +2,7 @@ import { get } from "@ember/object";
import { registerUnbound } from "discourse-common/lib/helpers";
import { isRTL } from "discourse/lib/text-direction";
import { iconHTML } from "discourse-common/lib/icon-library";
+import Category from "discourse/models/category";
let escapeExpression = Handlebars.Utils.escapeExpression;
let _renderer = defaultCategoryLinkRenderer;
@@ -78,7 +79,7 @@ function defaultCategoryLinkRenderer(category, opts) {
let restricted = get(category, "read_restricted");
let url = opts.url
? opts.url
- : Discourse.getURL("/c/") + Discourse.Category.slugFor(category);
+ : Discourse.getURL("/c/") + Category.slugFor(category);
let href = opts.link === false ? "" : url;
let tagName = opts.link === false || opts.link === "false" ? "span" : "a";
let extraClasses = opts.extraClasses ? " " + opts.extraClasses : "";
@@ -88,9 +89,7 @@ function defaultCategoryLinkRenderer(category, opts) {
let categoryDir = "";
if (!opts.hideParent) {
- parentCat = Discourse.Category.findById(
- get(category, "parent_category_id")
- );
+ parentCat = Category.findById(get(category, "parent_category_id"));
}
const categoryStyle =
diff --git a/app/assets/javascripts/discourse/models/category-list.js.es6 b/app/assets/javascripts/discourse/models/category-list.js.es6
index 227dc14894..f04b40dff8 100644
--- a/app/assets/javascripts/discourse/models/category-list.js.es6
+++ b/app/assets/javascripts/discourse/models/category-list.js.es6
@@ -1,6 +1,7 @@
import PreloadStore from "preload-store";
import { ajax } from "discourse/lib/ajax";
import Topic from "discourse/models/topic";
+import Category from "discourse/models/category";
const CategoryList = Ember.ArrayProxy.extend({
init() {
@@ -12,7 +13,7 @@ const CategoryList = Ember.ArrayProxy.extend({
CategoryList.reopenClass({
categoriesFrom(store, result) {
const categories = CategoryList.create();
- const list = Discourse.Category.list();
+ const list = Category.list();
let statPeriod = "all";
const minCategories = result.category_list.categories.length * 0.66;
diff --git a/app/assets/javascripts/discourse/models/category.js.es6 b/app/assets/javascripts/discourse/models/category.js.es6
index 98336dac42..1384837d33 100644
--- a/app/assets/javascripts/discourse/models/category.js.es6
+++ b/app/assets/javascripts/discourse/models/category.js.es6
@@ -5,6 +5,7 @@ import RestModel from "discourse/models/rest";
import { on } from "discourse-common/utils/decorators";
import PermissionType from "discourse/models/permission-type";
import { NotificationLevels } from "discourse/lib/notification-levels";
+import deprecated from "discourse-common/lib/deprecated";
const Category = RestModel.extend({
permissions: null,
@@ -407,4 +408,14 @@ Category.reopenClass({
}
});
+Object.defineProperty(Discourse, "Category", {
+ get() {
+ deprecated(
+ "Import the Category object instead of using Discourse.Category",
+ { since: "2.4.0", dropFrom: "2.5.0" }
+ );
+ return Category;
+ }
+});
+
export default Category;
diff --git a/app/assets/javascripts/discourse/models/nav-item.js.es6 b/app/assets/javascripts/discourse/models/nav-item.js.es6
index 7ecebc4839..72395681be 100644
--- a/app/assets/javascripts/discourse/models/nav-item.js.es6
+++ b/app/assets/javascripts/discourse/models/nav-item.js.es6
@@ -1,6 +1,7 @@
import discourseComputed from "discourse-common/utils/decorators";
import { toTitleCase } from "discourse/lib/formatter";
import { emojiUnescape } from "discourse/lib/text";
+import Category from "discourse/models/category";
const NavItem = Discourse.Model.extend({
@discourseComputed("categoryName", "name")
@@ -53,7 +54,7 @@ const NavItem = Discourse.Model.extend({
"nameLower",
split[1].toLowerCase()
);
- return cat ? Discourse.Category.slugFor(cat) : null;
+ return cat ? Category.slugFor(cat) : null;
}
return null;
},
@@ -84,7 +85,7 @@ const NavItem = Discourse.Model.extend({
let mode = "";
if (category) {
mode += "c/";
- mode += Discourse.Category.slugFor(category);
+ mode += Category.slugFor(category);
if (noSubcategories) {
mode += "/none";
}
@@ -143,7 +144,7 @@ NavItem.reopenClass({
)
return null;
- if (!Discourse.Category.list() && testName === "categories") return null;
+ if (!Category.list() && testName === "categories") return null;
if (!Discourse.Site.currentProp("top_menu_items").includes(testName))
return null;
diff --git a/app/assets/javascripts/discourse/models/store.js.es6 b/app/assets/javascripts/discourse/models/store.js.es6
index 39a5ce1434..14d479264a 100644
--- a/app/assets/javascripts/discourse/models/store.js.es6
+++ b/app/assets/javascripts/discourse/models/store.js.es6
@@ -5,6 +5,7 @@ import ResultSet from "discourse/models/result-set";
import { getRegister } from "discourse-common/lib/get-owner";
import { underscore } from "@ember/string";
import { set } from "@ember/object";
+import Category from "discourse/models/category";
let _identityMap;
@@ -272,7 +273,7 @@ export default EmberObject.extend({
// to category. That should either respect this or be
// removed.
if (subType === "category" && type !== "topic") {
- return Discourse.Category.findById(id);
+ return Category.findById(id);
}
if (root.meta && root.meta.types) {
diff --git a/app/assets/javascripts/discourse/models/topic-list.js.es6 b/app/assets/javascripts/discourse/models/topic-list.js.es6
index da01a6899d..bec760fd69 100644
--- a/app/assets/javascripts/discourse/models/topic-list.js.es6
+++ b/app/assets/javascripts/discourse/models/topic-list.js.es6
@@ -5,6 +5,7 @@ import RestModel from "discourse/models/rest";
import Model from "discourse/models/model";
import { getOwner } from "discourse-common/lib/get-owner";
import { Promise } from "rsvp";
+import Category from "discourse/models/category";
// Whether to show the category badge in topic lists
function displayCategoryInList(site, category) {
@@ -136,7 +137,7 @@ TopicList.reopenClass({
// Stitch together our side loaded data
- const categories = Discourse.Category.list(),
+ const categories = Category.list(),
users = Model.extractByKey(result.users, Discourse.User),
groups = Model.extractByKey(result.primary_groups, EmberObject);
diff --git a/app/assets/javascripts/discourse/models/topic-tracking-state.js.es6 b/app/assets/javascripts/discourse/models/topic-tracking-state.js.es6
index de53d7c35a..4656900990 100644
--- a/app/assets/javascripts/discourse/models/topic-tracking-state.js.es6
+++ b/app/assets/javascripts/discourse/models/topic-tracking-state.js.es6
@@ -7,6 +7,7 @@ import {
} from "discourse-common/utils/decorators";
import { defaultHomepage } from "discourse/lib/utilities";
import PreloadStore from "preload-store";
+import Category from "discourse/models/category";
function isNew(topic) {
return (
@@ -57,7 +58,7 @@ const TopicTrackingState = Discourse.Model.extend({
// fill parent_category_id we need it for counting new/unread
if (data.payload && data.payload.category_id) {
- var category = Discourse.Category.findById(data.payload.category_id);
+ var category = Category.findById(data.payload.category_id);
if (category && category.parent_category_id) {
data.payload.parent_category_id = category.parent_category_id;
@@ -133,7 +134,7 @@ const TopicTrackingState = Discourse.Model.extend({
const categoryId = data.payload && data.payload.category_id;
if (filterCategory && filterCategory.get("id") !== categoryId) {
- const category = categoryId && Discourse.Category.findById(categoryId);
+ const category = categoryId && Category.findById(categoryId);
if (
!category ||
category.get("parentCategory.id") !== filterCategory.get("id")
@@ -194,7 +195,7 @@ const TopicTrackingState = Discourse.Model.extend({
if (split.length >= 4) {
filter = split[split.length - 1];
// c/cat/subcat/l/latest
- var category = Discourse.Category.findSingleBySlug(
+ var category = Category.findSingleBySlug(
split.splice(1, split.length - 3).join("/")
);
this.set("filterCategory", category);
@@ -408,7 +409,7 @@ const TopicTrackingState = Discourse.Model.extend({
loadStates(data) {
const states = this.states;
- const idMap = Discourse.Category.idMap();
+ const idMap = Category.idMap();
// I am taking some shortcuts here to avoid 500 gets for a large list
if (data) {
diff --git a/app/assets/javascripts/discourse/models/topic.js.es6 b/app/assets/javascripts/discourse/models/topic.js.es6
index 9590ffcda8..ad9918b8a9 100644
--- a/app/assets/javascripts/discourse/models/topic.js.es6
+++ b/app/assets/javascripts/discourse/models/topic.js.es6
@@ -18,6 +18,7 @@ import {
observes,
on
} from "discourse-common/utils/decorators";
+import Category from "discourse/models/category";
export function loadTopicView(topic, args) {
const data = _.merge({}, args);
@@ -208,7 +209,7 @@ const Topic = RestModel.extend({
@on("init")
@observes("category_id")
_categoryIdChanged() {
- this.set("category", Discourse.Category.findById(this.category_id));
+ this.set("category", Category.findById(this.category_id));
},
@observes("categoryName")
diff --git a/app/assets/javascripts/discourse/models/user-action.js.es6 b/app/assets/javascripts/discourse/models/user-action.js.es6
index 183c47e44b..a22d601fae 100644
--- a/app/assets/javascripts/discourse/models/user-action.js.es6
+++ b/app/assets/javascripts/discourse/models/user-action.js.es6
@@ -5,6 +5,7 @@ import { on } from "discourse-common/utils/decorators";
import UserActionGroup from "discourse/models/user-action-group";
import { postUrl } from "discourse/lib/utilities";
import { userPath } from "discourse/lib/url";
+import Category from "discourse/models/category";
const UserActionTypes = {
likes_given: 1,
@@ -31,7 +32,7 @@ const UserAction = RestModel.extend({
_attachCategory() {
const categoryId = this.category_id;
if (categoryId) {
- this.set("category", Discourse.Category.findById(categoryId));
+ this.set("category", Category.findById(categoryId));
}
},
diff --git a/app/assets/javascripts/discourse/models/user.js.es6 b/app/assets/javascripts/discourse/models/user.js.es6
index 77bc32371c..b951631c60 100644
--- a/app/assets/javascripts/discourse/models/user.js.es6
+++ b/app/assets/javascripts/discourse/models/user.js.es6
@@ -631,17 +631,14 @@ const User = RestModel.extend({
@observes("muted_category_ids")
updateMutedCategories() {
- this.set(
- "mutedCategories",
- Discourse.Category.findByIds(this.muted_category_ids)
- );
+ this.set("mutedCategories", Category.findByIds(this.muted_category_ids));
},
@observes("tracked_category_ids")
updateTrackedCategories() {
this.set(
"trackedCategories",
- Discourse.Category.findByIds(this.tracked_category_ids)
+ Category.findByIds(this.tracked_category_ids)
);
},
@@ -649,7 +646,7 @@ const User = RestModel.extend({
updateWatchedCategories() {
this.set(
"watchedCategories",
- Discourse.Category.findByIds(this.watched_category_ids)
+ Category.findByIds(this.watched_category_ids)
);
},
@@ -657,7 +654,7 @@ const User = RestModel.extend({
updateWatchedFirstPostCategories() {
this.set(
"watchedFirstPostCategories",
- Discourse.Category.findByIds(this.watched_first_post_category_ids)
+ Category.findByIds(this.watched_first_post_category_ids)
);
},
diff --git a/app/assets/javascripts/discourse/routes/build-category-route.js.es6 b/app/assets/javascripts/discourse/routes/build-category-route.js.es6
index 06259b920c..064f02a494 100644
--- a/app/assets/javascripts/discourse/routes/build-category-route.js.es6
+++ b/app/assets/javascripts/discourse/routes/build-category-route.js.es6
@@ -65,7 +65,7 @@ export default (filterArg, params) => {
_setupNavigation(category) {
const noSubcategories = params && !!params.no_subcategories,
- filterMode = `c/${Discourse.Category.slugFor(category)}${
+ filterMode = `c/${Category.slugFor(category)}${
noSubcategories ? "/none" : ""
}/l/${this.filter(category)}`;
@@ -92,9 +92,9 @@ export default (filterArg, params) => {
},
_retrieveTopicList(category, transition) {
- const listFilter = `c/${Discourse.Category.slugFor(
+ const listFilter = `c/${Category.slugFor(category)}/l/${this.filter(
category
- )}/l/${this.filter(category)}`,
+ )}`,
findOpts = filterQueryParams(transition.to.queryParams, params),
extras = { cached: this.isPoppedState(transition) };
diff --git a/app/assets/javascripts/discourse/routes/tags-show.js.es6 b/app/assets/javascripts/discourse/routes/tags-show.js.es6
index c718cc75ff..0883b5cc1b 100644
--- a/app/assets/javascripts/discourse/routes/tags-show.js.es6
+++ b/app/assets/javascripts/discourse/routes/tags-show.js.es6
@@ -7,6 +7,7 @@ import {
} from "discourse/routes/build-topic-route";
import { queryParams } from "discourse/controllers/discovery-sortable";
import PermissionType from "discourse/models/permission-type";
+import Category from "discourse/models/category";
export default DiscourseRoute.extend({
navMode: "latest",
@@ -79,10 +80,7 @@ export default DiscourseRoute.extend({
let filter;
if (categorySlug) {
- const category = Discourse.Category.findBySlug(
- categorySlug,
- parentCategorySlug
- );
+ const category = Category.findBySlug(categorySlug, parentCategorySlug);
if (parentCategorySlug) {
filter = `tags/c/${parentCategorySlug}/${categorySlug}/${tagId}/l/${topicFilter}`;
} else if (this.noSubcategories) {
diff --git a/app/assets/javascripts/discourse/widgets/hamburger-categories.js.es6 b/app/assets/javascripts/discourse/widgets/hamburger-categories.js.es6
index 2112dd4f1d..3a51939f33 100644
--- a/app/assets/javascripts/discourse/widgets/hamburger-categories.js.es6
+++ b/app/assets/javascripts/discourse/widgets/hamburger-categories.js.es6
@@ -1,6 +1,7 @@
import { createWidget } from "discourse/widgets/widget";
import { h } from "virtual-dom";
import { number } from "discourse/lib/formatter";
+import Category from "discourse/models/category";
createWidget("hamburger-category", {
tagName: "li.category-link",
@@ -10,7 +11,7 @@ createWidget("hamburger-category", {
this.tagName += ".subcategory";
}
- this.tagName += ".category-" + Discourse.Category.slugFor(c, "-");
+ this.tagName += ".category-" + Category.slugFor(c, "-");
const results = [
this.attach("category-link", { category: c, allowUncategorized: true })
diff --git a/app/assets/javascripts/select-kit/components/category-drop.js.es6 b/app/assets/javascripts/select-kit/components/category-drop.js.es6
index 601d420d4b..2e7294854b 100644
--- a/app/assets/javascripts/select-kit/components/category-drop.js.es6
+++ b/app/assets/javascripts/select-kit/components/category-drop.js.es6
@@ -81,7 +81,7 @@ export default ComboBoxComponent.extend({
const contentLength = (content && content.length) || 0;
return (
contentLength >= 15 ||
- (this.isAsync && contentLength < Discourse.Category.list().length)
+ (this.isAsync && contentLength < Category.list().length)
);
},
@@ -141,7 +141,7 @@ export default ComboBoxComponent.extend({
categoryURL = Discourse.getURL(this.noCategoriesUrl);
} else {
const category = Category.findById(parseInt(categoryId, 10));
- const slug = Discourse.Category.slugFor(category);
+ const slug = Category.slugFor(category);
categoryURL = Discourse.getURL("/c/") + slug;
}
@@ -164,7 +164,7 @@ export default ComboBoxComponent.extend({
return;
}
- let results = Discourse.Category.search(filter);
+ let results = Category.search(filter);
if (!this.siteSettings.allow_uncategorized_topics) {
results = results.filter(result => {
diff --git a/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb b/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
index c129e66001..b0b18d2736 100644
--- a/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
+++ b/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
@@ -87,7 +87,6 @@ JS
@@whitelisted ||= Set.new(
[
"discourse/routes/discourse",
- "discourse/models/category",
"discourse/models/site",
"discourse/models/user",
"discourse/models/session",
diff --git a/test/javascripts/models/category-test.js.es6 b/test/javascripts/models/category-test.js.es6
index aa06c121fa..58a0af8b3f 100644
--- a/test/javascripts/models/category-test.js.es6
+++ b/test/javascripts/models/category-test.js.es6
@@ -7,7 +7,7 @@ QUnit.test("slugFor", assert => {
const store = createStore();
const slugFor = function(cat, val, text) {
- assert.equal(Discourse.Category.slugFor(cat), val, text);
+ assert.equal(Category.slugFor(cat), val, text);
};
slugFor(
@@ -86,35 +86,35 @@ QUnit.test("findBySlug", assert => {
}),
categoryList = [darth, luke, hurricane, newsFeed, time, bah];
- sandbox.stub(Discourse.Category, "list").returns(categoryList);
+ sandbox.stub(Category, "list").returns(categoryList);
assert.deepEqual(
- Discourse.Category.findBySlug("darth"),
+ Category.findBySlug("darth"),
darth,
"we can find a category"
);
assert.deepEqual(
- Discourse.Category.findBySlug("luke", "darth"),
+ Category.findBySlug("luke", "darth"),
luke,
"we can find the other category with parent category"
);
assert.deepEqual(
- Discourse.Category.findBySlug("熱帶風暴畫眉"),
+ Category.findBySlug("熱帶風暴畫眉"),
hurricane,
"we can find a category with CJK slug"
);
assert.deepEqual(
- Discourse.Category.findBySlug("뉴스피드", "熱帶風暴畫眉"),
+ Category.findBySlug("뉴스피드", "熱帶風暴畫眉"),
newsFeed,
"we can find a category with CJK slug whose parent slug is also CJK"
);
assert.deepEqual(
- Discourse.Category.findBySlug("时间", "darth"),
+ Category.findBySlug("时间", "darth"),
time,
"we can find a category with CJK slug whose parent slug is english"
);
assert.deepEqual(
- Discourse.Category.findBySlug("bah", "熱帶風暴畫眉"),
+ Category.findBySlug("bah", "熱帶風暴畫眉"),
bah,
"we can find a category with english slug whose parent slug is CJK"
);
@@ -150,35 +150,35 @@ QUnit.test("findSingleBySlug", assert => {
}),
categoryList = [darth, luke, hurricane, newsFeed, time, bah];
- sandbox.stub(Discourse.Category, "list").returns(categoryList);
+ sandbox.stub(Category, "list").returns(categoryList);
assert.deepEqual(
- Discourse.Category.findSingleBySlug("darth"),
+ Category.findSingleBySlug("darth"),
darth,
"we can find a category"
);
assert.deepEqual(
- Discourse.Category.findSingleBySlug("darth/luke"),
+ Category.findSingleBySlug("darth/luke"),
luke,
"we can find the other category with parent category"
);
assert.deepEqual(
- Discourse.Category.findSingleBySlug("熱帶風暴畫眉"),
+ Category.findSingleBySlug("熱帶風暴畫眉"),
hurricane,
"we can find a category with CJK slug"
);
assert.deepEqual(
- Discourse.Category.findSingleBySlug("熱帶風暴畫眉/뉴스피드"),
+ Category.findSingleBySlug("熱帶風暴畫眉/뉴스피드"),
newsFeed,
"we can find a category with CJK slug whose parent slug is also CJK"
);
assert.deepEqual(
- Discourse.Category.findSingleBySlug("darth/时间"),
+ Category.findSingleBySlug("darth/时间"),
time,
"we can find a category with CJK slug whose parent slug is english"
);
assert.deepEqual(
- Discourse.Category.findSingleBySlug("熱帶風暴畫眉/bah"),
+ Category.findSingleBySlug("熱帶風暴畫眉/bah"),
bah,
"we can find a category with english slug whose parent slug is CJK"
);
@@ -191,13 +191,10 @@ QUnit.test("findByIds", assert => {
2: store.createRecord("category", { id: 2 })
};
- sandbox.stub(Discourse.Category, "idMap").returns(categories);
- assert.deepEqual(
- Discourse.Category.findByIds([1, 2, 3]),
- _.values(categories)
- );
+ sandbox.stub(Category, "idMap").returns(categories);
+ assert.deepEqual(Category.findByIds([1, 2, 3]), _.values(categories));
- assert.deepEqual(Discourse.Category.findByIds(), []);
+ assert.deepEqual(Category.findByIds(), []);
});
QUnit.test("search with category name", assert => {
diff --git a/test/javascripts/models/nav-item-test.js.es6 b/test/javascripts/models/nav-item-test.js.es6
index 309ce31534..28f2eb9f5e 100644
--- a/test/javascripts/models/nav-item-test.js.es6
+++ b/test/javascripts/models/nav-item-test.js.es6
@@ -1,11 +1,12 @@
import { run } from "@ember/runloop";
import createStore from "helpers/create-store";
import NavItem from "discourse/models/nav-item";
+import Category from "discourse/models/category";
QUnit.module("NavItem", {
beforeEach() {
run(function() {
- const asianCategory = Discourse.Category.create({
+ const asianCategory = Category.create({
name: "确实是这样",
id: 343434
});
diff --git a/test/javascripts/models/topic-test.js.es6 b/test/javascripts/models/topic-test.js.es6
index 1deab13a54..40ea25f854 100644
--- a/test/javascripts/models/topic-test.js.es6
+++ b/test/javascripts/models/topic-test.js.es6
@@ -1,10 +1,10 @@
import EmberObject from "@ember/object";
import { IMAGE_VERSION as v } from "pretty-text/emoji/version";
+import Category from "discourse/models/category";
+import Topic from "discourse/models/topic";
QUnit.module("model:topic");
-import Topic from "discourse/models/topic";
-
QUnit.test("defaults", assert => {
const topic = Topic.create({ id: 1234 });
@@ -84,7 +84,7 @@ QUnit.test("has suggestedTopics", assert => {
QUnit.test("category relationship", assert => {
// It finds the category by id
- const category = Discourse.Category.list()[0];
+ const category = Category.list()[0];
const topic = Topic.create({ id: 1111, category_id: category.get("id") });
assert.equal(topic.get("category"), category);
@@ -92,7 +92,7 @@ QUnit.test("category relationship", assert => {
QUnit.test("updateFromJson", assert => {
const topic = Topic.create({ id: 1234 });
- const category = Discourse.Category.list()[0];
+ const category = Category.list()[0];
topic.updateFromJson({
post_stream: [1, 2, 3],
diff --git a/test/javascripts/models/topic-tracking-state-test.js.es6 b/test/javascripts/models/topic-tracking-state-test.js.es6
index 5799b4f116..9c9f0856a9 100644
--- a/test/javascripts/models/topic-tracking-state-test.js.es6
+++ b/test/javascripts/models/topic-tracking-state-test.js.es6
@@ -1,5 +1,6 @@
import TopicTrackingState from "discourse/models/topic-tracking-state";
import createStore from "helpers/create-store";
+import Category from "discourse/models/category";
QUnit.module("model:topic-tracking-state");
@@ -37,7 +38,7 @@ QUnit.test("subscribe to category", function(assert) {
}),
categoryList = [darth, luke];
- sandbox.stub(Discourse.Category, "list").returns(categoryList);
+ sandbox.stub(Category, "list").returns(categoryList);
const state = TopicTrackingState.create();
From 291572a97a965dd5e5e5a8a5fca045f64335eeb7 Mon Sep 17 00:00:00 2001
From: Robin Ward
Date: Fri, 8 Nov 2019 13:46:50 -0500
Subject: [PATCH 051/408] REFACTOR: Remove `Discourse.Session` constants
---
app/assets/javascripts/application.js | 4 +++-
app/assets/javascripts/discourse/controllers/topic.js.es6 | 4 +---
app/assets/javascripts/discourse/lib/ajax.js.es6 | 7 ++++---
.../javascripts/discourse/models/login-method.js.es6 | 3 ++-
app/assets/javascripts/discourse/models/topic-list.js.es6 | 5 +++--
app/assets/javascripts/discourse/models/topic.js.es6 | 3 ++-
.../javascripts/discourse/routes/build-topic-route.js.es6 | 5 +++--
.../javascripts/preload-application-data.js.no-module.es6 | 6 ++++--
test/javascripts/test_helper.js | 4 +++-
9 files changed, 25 insertions(+), 16 deletions(-)
diff --git a/app/assets/javascripts/application.js b/app/assets/javascripts/application.js
index 290f920789..fa5ef28880 100644
--- a/app/assets/javascripts/application.js
+++ b/app/assets/javascripts/application.js
@@ -13,6 +13,9 @@
//= require ./discourse/lib/utilities
//= require ./discourse/lib/page-visible
//= require ./discourse/lib/logout
+//= require ./discourse/mixins/singleton
+//= require ./discourse/models/rest
+//= require ./discourse/models/session
//= require ./discourse/lib/ajax
//= require ./discourse/lib/text
//= require ./discourse/lib/hash
@@ -34,7 +37,6 @@
//= require ./discourse/mixins/scrolling
//= require ./discourse/lib/ajax-error
//= require ./discourse/models/model
-//= require ./discourse/models/rest
//= require ./discourse/models/result-set
//= require ./discourse/models/store
//= require ./discourse/models/action-summary
diff --git a/app/assets/javascripts/discourse/controllers/topic.js.es6 b/app/assets/javascripts/discourse/controllers/topic.js.es6
index 7f2708a789..1a67f6e0ed 100644
--- a/app/assets/javascripts/discourse/controllers/topic.js.es6
+++ b/app/assets/javascripts/discourse/controllers/topic.js.es6
@@ -447,9 +447,7 @@ export default Controller.extend(bufferedProperty("model"), {
: "/";
ajax("/t/" + topic.get("id") + "/timings.json?last=1", { type: "DELETE" })
.then(() => {
- const highestSeenByTopic = Discourse.Session.currentProp(
- "highestSeenByTopic"
- );
+ const highestSeenByTopic = this.session.get("highestSeenByTopic");
highestSeenByTopic[topic.get("id")] = null;
DiscourseURL.routeTo(goToPath);
})
diff --git a/app/assets/javascripts/discourse/lib/ajax.js.es6 b/app/assets/javascripts/discourse/lib/ajax.js.es6
index 40fd85d686..7b7d9fda98 100644
--- a/app/assets/javascripts/discourse/lib/ajax.js.es6
+++ b/app/assets/javascripts/discourse/lib/ajax.js.es6
@@ -1,6 +1,7 @@
import { run } from "@ember/runloop";
import pageVisible from "discourse/lib/page-visible";
import logout from "discourse/lib/logout";
+import Session from "discourse/models/session";
import { Promise } from "rsvp";
let _trackView = false;
@@ -44,7 +45,7 @@ function handleRedirect(data) {
export function updateCsrfToken() {
return ajax("/session/csrf").then(result => {
- Discourse.Session.currentProp("csrfToken", result.csrf);
+ Session.currentProp("csrfToken", result.csrf);
});
}
@@ -120,7 +121,7 @@ export function ajax() {
// note: for bad CSRF we don't loop an extra request right away.
// this allows us to eliminate the possibility of having a loop.
if (xhr.status === 403 && xhr.responseText === '["BAD CSRF"]') {
- Discourse.Session.current().set("csrfToken", null);
+ Session.current().set("csrfToken", null);
}
// If it's a parsererror, don't reject
@@ -162,7 +163,7 @@ export function ajax() {
args.type &&
args.type.toUpperCase() !== "GET" &&
url !== Discourse.getURL("/clicks/track") &&
- !Discourse.Session.currentProp("csrfToken")
+ !Session.currentProp("csrfToken")
) {
promise = new Promise((resolve, reject) => {
ajaxObj = updateCsrfToken().then(() => {
diff --git a/app/assets/javascripts/discourse/models/login-method.js.es6 b/app/assets/javascripts/discourse/models/login-method.js.es6
index 12a4969768..040e175e74 100644
--- a/app/assets/javascripts/discourse/models/login-method.js.es6
+++ b/app/assets/javascripts/discourse/models/login-method.js.es6
@@ -2,6 +2,7 @@ import discourseComputed from "discourse-common/utils/decorators";
import EmberObject from "@ember/object";
import { updateCsrfToken } from "discourse/lib/ajax";
import { Promise } from "rsvp";
+import Session from "discourse/models/session";
const LoginMethod = EmberObject.extend({
@discourseComputed
@@ -52,7 +53,7 @@ LoginMethod.reopenClass({
const input = document.createElement("input");
input.setAttribute("name", "authenticity_token");
- input.setAttribute("value", Discourse.Session.currentProp("csrfToken"));
+ input.setAttribute("value", Session.currentProp("csrfToken"));
form.appendChild(input);
document.body.appendChild(form);
diff --git a/app/assets/javascripts/discourse/models/topic-list.js.es6 b/app/assets/javascripts/discourse/models/topic-list.js.es6
index bec760fd69..b0ec31a834 100644
--- a/app/assets/javascripts/discourse/models/topic-list.js.es6
+++ b/app/assets/javascripts/discourse/models/topic-list.js.es6
@@ -6,6 +6,7 @@ import Model from "discourse/models/model";
import { getOwner } from "discourse-common/lib/get-owner";
import { Promise } from "rsvp";
import Category from "discourse/models/category";
+import Session from "discourse/models/session";
// Whether to show the category badge in topic lists
function displayCategoryInList(site, category) {
@@ -93,7 +94,7 @@ const TopicList = RestModel.extend({
more_topics_url: result.topic_list.more_topics_url
});
- Discourse.Session.currentProp("topicList", this);
+ Session.currentProp("topicList", this);
return this.more_topics_url;
}
});
@@ -123,7 +124,7 @@ const TopicList = RestModel.extend({
i++;
});
- if (storeInSession) Discourse.Session.currentProp("topicList", this);
+ if (storeInSession) Session.currentProp("topicList", this);
});
}
});
diff --git a/app/assets/javascripts/discourse/models/topic.js.es6 b/app/assets/javascripts/discourse/models/topic.js.es6
index ad9918b8a9..ca41597cfd 100644
--- a/app/assets/javascripts/discourse/models/topic.js.es6
+++ b/app/assets/javascripts/discourse/models/topic.js.es6
@@ -19,6 +19,7 @@ import {
on
} from "discourse-common/utils/decorators";
import Category from "discourse/models/category";
+import Session from "discourse/models/session";
export function loadTopicView(topic, args) {
const data = _.merge({}, args);
@@ -306,7 +307,7 @@ const Topic = RestModel.extend({
// So take what the browser has seen into consideration.
@discourseComputed("new_posts", "id")
displayNewPosts(newPosts, id) {
- const highestSeen = Discourse.Session.currentProp("highestSeenByTopic")[id];
+ const highestSeen = Session.currentProp("highestSeenByTopic")[id];
if (highestSeen) {
const delta = highestSeen - this.last_read_post_number;
if (delta > 0) {
diff --git a/app/assets/javascripts/discourse/routes/build-topic-route.js.es6 b/app/assets/javascripts/discourse/routes/build-topic-route.js.es6
index 5d0a576005..34847b8725 100644
--- a/app/assets/javascripts/discourse/routes/build-topic-route.js.es6
+++ b/app/assets/javascripts/discourse/routes/build-topic-route.js.es6
@@ -1,6 +1,7 @@
import DiscourseRoute from "discourse/routes/discourse";
import { queryParams } from "discourse/controllers/discovery-sortable";
import { defaultHomepage } from "discourse/lib/utilities";
+import Session from "discourse/models/session";
// A helper to build a topic route for a filter
function filterQueryParams(params, defaultParams) {
@@ -19,7 +20,7 @@ function filterQueryParams(params, defaultParams) {
function findTopicList(store, tracking, filter, filterParams, extras) {
extras = extras || {};
return new Promise(function(resolve) {
- const session = Discourse.Session.current();
+ const session = Session.current();
if (extras.cached) {
const cachedList = session.get("topicList");
@@ -62,7 +63,7 @@ function findTopicList(store, tracking, filter, filterParams, extras) {
tracking.sync(list, list.filter);
tracking.trackIncoming(list.filter);
}
- Discourse.Session.currentProp("topicList", list);
+ Session.currentProp("topicList", list);
if (list.topic_list && list.topic_list.top_tags) {
Discourse.Site.currentProp("top_tags", list.topic_list.top_tags);
}
diff --git a/app/assets/javascripts/preload-application-data.js.no-module.es6 b/app/assets/javascripts/preload-application-data.js.no-module.es6
index f78ea11367..8dfab7b145 100644
--- a/app/assets/javascripts/preload-application-data.js.no-module.es6
+++ b/app/assets/javascripts/preload-application-data.js.no-module.es6
@@ -27,13 +27,15 @@
I18n.defaultLocale = setupData.defaultLocale;
Discourse.start();
Discourse.set("assetVersion", setupData.assetVersion);
- Discourse.Session.currentProp(
+
+ let Session = require("discourse/models/session").default;
+ Session.currentProp(
"disableCustomCSS",
setupData.disableCustomCss === "true"
);
if (setupData.safeMode) {
- Discourse.Session.currentProp("safe_mode", setupData.safeMode);
+ Session.currentProp("safe_mode", setupData.safeMode);
}
Discourse.HighlightJSPath = setupData.highlightJsPath;
diff --git a/test/javascripts/test_helper.js b/test/javascripts/test_helper.js
index 1f1f15a0d4..829b4ab5fa 100644
--- a/test/javascripts/test_helper.js
+++ b/test/javascripts/test_helper.js
@@ -117,7 +117,9 @@ QUnit.testStart(function(ctx) {
Discourse.SiteSettings = dup(Discourse.SiteSettingsOriginal);
Discourse.BaseUri = "";
Discourse.BaseUrl = "http://localhost:3000";
- Discourse.Session.resetCurrent();
+
+ let Session = require("discourse/models/session").default;
+ Session.resetCurrent();
Discourse.User.resetCurrent();
resetSite(Discourse.SiteSettings);
From fa71919693ee1066d09737ba09234bd97c974587 Mon Sep 17 00:00:00 2001
From: Robin Ward
Date: Fri, 8 Nov 2019 13:48:18 -0500
Subject: [PATCH 052/408] REFACTOR: Don't transpile `Discourse.Session`
---
lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb | 1 -
1 file changed, 1 deletion(-)
diff --git a/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb b/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
index b0b18d2736..6f25f0823e 100644
--- a/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
+++ b/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
@@ -89,7 +89,6 @@ JS
"discourse/routes/discourse",
"discourse/models/site",
"discourse/models/user",
- "discourse/models/session",
"discourse/models/model"
]
)
From f03edb36bee1842ffabc0b502ee680fa20cad00a Mon Sep 17 00:00:00 2001
From: Robin Ward
Date: Fri, 8 Nov 2019 14:13:35 -0500
Subject: [PATCH 053/408] REFACTOR: Remove `Discourse.Model`
---
.../admin/models/admin-dashboard.js.es6 | 3 +-
.../admin/models/backup-status.js.es6 | 3 +-
.../javascripts/admin/models/backup.js.es6 | 3 +-
.../admin/models/color-scheme-color.js.es6 | 3 +-
.../admin/models/color-scheme.js.es6 | 3 +-
.../javascripts/admin/models/email-log.js.es6 | 3 +-
.../admin/models/email-preview.js.es6 | 4 ++-
.../admin/models/email-settings.js.es6 | 4 ++-
.../admin/models/incoming-email.js.es6 | 3 +-
.../javascripts/admin/models/permalink.js.es6 | 4 ++-
.../javascripts/admin/models/report.js.es6 | 2 +-
.../admin/models/screened-email.js.es6 | 3 +-
.../admin/models/screened-ip-address.js.es6 | 3 +-
.../admin/models/screened-url.js.es6 | 3 +-
.../admin/models/site-setting.js.es6 | 3 +-
.../admin/models/theme-settings.js.es6 | 3 +-
.../admin/models/tl3-requirements.js.es6 | 3 +-
.../admin/models/version-check.js.es6 | 3 +-
.../admin/models/watched-word.js.es6 | 2 +-
app/assets/javascripts/application.js | 1 -
app/assets/javascripts/discourse.js.es6 | 12 +++++++
.../javascripts/discourse/models/draft.js.es6 | 4 ++-
.../discourse/models/input-validation.js.es6 | 6 ++--
.../discourse/models/invite.js.es6 | 2 +-
.../discourse/models/live-post-counts.es6 | 4 ++-
.../javascripts/discourse/models/model.js.es6 | 19 ----------
.../discourse/models/nav-item.js.es6 | 3 +-
.../discourse/models/permission-type.js.es6 | 3 +-
.../discourse/models/topic-list.js.es6 | 19 ++++++++--
.../models/topic-tracking-state.js.es6 | 3 +-
.../discourse/models/user-action-group.js.es6 | 9 +++--
.../discourse/models/user-badge.js.es6 | 3 +-
.../discourse/models/user-posts-stream.js.es6 | 3 +-
.../tilt/es6_module_transpiler_template.rb | 1 -
test/javascripts/models/model-test.js.es6 | 36 -------------------
35 files changed, 90 insertions(+), 96 deletions(-)
delete mode 100644 app/assets/javascripts/discourse/models/model.js.es6
delete mode 100644 test/javascripts/models/model-test.js.es6
diff --git a/app/assets/javascripts/admin/models/admin-dashboard.js.es6 b/app/assets/javascripts/admin/models/admin-dashboard.js.es6
index 20cdbe2772..756de2cc09 100644
--- a/app/assets/javascripts/admin/models/admin-dashboard.js.es6
+++ b/app/assets/javascripts/admin/models/admin-dashboard.js.es6
@@ -1,4 +1,5 @@
import { ajax } from "discourse/lib/ajax";
+import EmberObject from "@ember/object";
const GENERAL_ATTRIBUTES = [
"updated_at",
@@ -6,7 +7,7 @@ const GENERAL_ATTRIBUTES = [
"release_notes_link"
];
-const AdminDashboard = Discourse.Model.extend({});
+const AdminDashboard = EmberObject.extend({});
AdminDashboard.reopenClass({
fetch() {
diff --git a/app/assets/javascripts/admin/models/backup-status.js.es6 b/app/assets/javascripts/admin/models/backup-status.js.es6
index b31d1cb176..62c360b532 100644
--- a/app/assets/javascripts/admin/models/backup-status.js.es6
+++ b/app/assets/javascripts/admin/models/backup-status.js.es6
@@ -1,7 +1,8 @@
import discourseComputed from "discourse-common/utils/decorators";
import { not } from "@ember/object/computed";
+import EmberObject from "@ember/object";
-export default Discourse.Model.extend({
+export default EmberObject.extend({
restoreDisabled: not("restoreEnabled"),
@discourseComputed("allowRestore", "isOperationRunning")
diff --git a/app/assets/javascripts/admin/models/backup.js.es6 b/app/assets/javascripts/admin/models/backup.js.es6
index 7cd151378a..882173300a 100644
--- a/app/assets/javascripts/admin/models/backup.js.es6
+++ b/app/assets/javascripts/admin/models/backup.js.es6
@@ -1,7 +1,8 @@
import { ajax } from "discourse/lib/ajax";
import { extractError } from "discourse/lib/ajax-error";
+import EmberObject from "@ember/object";
-const Backup = Discourse.Model.extend({
+const Backup = EmberObject.extend({
destroy() {
return ajax("/admin/backups/" + this.filename, { type: "DELETE" });
},
diff --git a/app/assets/javascripts/admin/models/color-scheme-color.js.es6 b/app/assets/javascripts/admin/models/color-scheme-color.js.es6
index d023295ce5..0d984c77a6 100644
--- a/app/assets/javascripts/admin/models/color-scheme-color.js.es6
+++ b/app/assets/javascripts/admin/models/color-scheme-color.js.es6
@@ -4,8 +4,9 @@ import {
on
} from "discourse-common/utils/decorators";
import { propertyNotEqual } from "discourse/lib/computed";
+import EmberObject from "@ember/object";
-const ColorSchemeColor = Discourse.Model.extend({
+const ColorSchemeColor = EmberObject.extend({
@on("init")
startTrackingChanges() {
this.set("originals", { hex: this.hex || "FFFFFF" });
diff --git a/app/assets/javascripts/admin/models/color-scheme.js.es6 b/app/assets/javascripts/admin/models/color-scheme.js.es6
index 5d0550d2e0..8486002386 100644
--- a/app/assets/javascripts/admin/models/color-scheme.js.es6
+++ b/app/assets/javascripts/admin/models/color-scheme.js.es6
@@ -2,8 +2,9 @@ import discourseComputed from "discourse-common/utils/decorators";
import { not } from "@ember/object/computed";
import { ajax } from "discourse/lib/ajax";
import ColorSchemeColor from "admin/models/color-scheme-color";
+import EmberObject from "@ember/object";
-const ColorScheme = Discourse.Model.extend(Ember.Copyable, {
+const ColorScheme = EmberObject.extend(Ember.Copyable, {
init() {
this._super(...arguments);
diff --git a/app/assets/javascripts/admin/models/email-log.js.es6 b/app/assets/javascripts/admin/models/email-log.js.es6
index f1ac52ac8d..c2eaaa26e6 100644
--- a/app/assets/javascripts/admin/models/email-log.js.es6
+++ b/app/assets/javascripts/admin/models/email-log.js.es6
@@ -1,7 +1,8 @@
import { ajax } from "discourse/lib/ajax";
import AdminUser from "admin/models/admin-user";
+import EmberObject from "@ember/object";
-const EmailLog = Discourse.Model.extend({});
+const EmailLog = EmberObject.extend({});
EmailLog.reopenClass({
create(attrs) {
diff --git a/app/assets/javascripts/admin/models/email-preview.js.es6 b/app/assets/javascripts/admin/models/email-preview.js.es6
index b8585d9080..42b7ab5878 100644
--- a/app/assets/javascripts/admin/models/email-preview.js.es6
+++ b/app/assets/javascripts/admin/models/email-preview.js.es6
@@ -1,5 +1,7 @@
import { ajax } from "discourse/lib/ajax";
-const EmailPreview = Discourse.Model.extend({});
+import EmberObject from "@ember/object";
+
+const EmailPreview = EmberObject.extend({});
export function oneWeekAgo() {
return moment()
diff --git a/app/assets/javascripts/admin/models/email-settings.js.es6 b/app/assets/javascripts/admin/models/email-settings.js.es6
index e1d838463e..1730aae7c9 100644
--- a/app/assets/javascripts/admin/models/email-settings.js.es6
+++ b/app/assets/javascripts/admin/models/email-settings.js.es6
@@ -1,5 +1,7 @@
import { ajax } from "discourse/lib/ajax";
-const EmailSettings = Discourse.Model.extend({});
+import EmberObject from "@ember/object";
+
+const EmailSettings = EmberObject.extend({});
EmailSettings.reopenClass({
find: function() {
diff --git a/app/assets/javascripts/admin/models/incoming-email.js.es6 b/app/assets/javascripts/admin/models/incoming-email.js.es6
index fd9d68730b..8d46429a1d 100644
--- a/app/assets/javascripts/admin/models/incoming-email.js.es6
+++ b/app/assets/javascripts/admin/models/incoming-email.js.es6
@@ -1,7 +1,8 @@
import { ajax } from "discourse/lib/ajax";
import AdminUser from "admin/models/admin-user";
+import EmberObject from "@ember/object";
-const IncomingEmail = Discourse.Model.extend({});
+const IncomingEmail = EmberObject.extend({});
IncomingEmail.reopenClass({
create(attrs) {
diff --git a/app/assets/javascripts/admin/models/permalink.js.es6 b/app/assets/javascripts/admin/models/permalink.js.es6
index 9019bdbc30..b86e931692 100644
--- a/app/assets/javascripts/admin/models/permalink.js.es6
+++ b/app/assets/javascripts/admin/models/permalink.js.es6
@@ -1,5 +1,7 @@
import { ajax } from "discourse/lib/ajax";
-const Permalink = Discourse.Model.extend({
+import EmberObject from "@ember/object";
+
+const Permalink = EmberObject.extend({
save: function() {
return ajax("/admin/permalinks.json", {
type: "POST",
diff --git a/app/assets/javascripts/admin/models/report.js.es6 b/app/assets/javascripts/admin/models/report.js.es6
index bb745b1302..91a5f54002 100644
--- a/app/assets/javascripts/admin/models/report.js.es6
+++ b/app/assets/javascripts/admin/models/report.js.es6
@@ -17,7 +17,7 @@ import { renderAvatar } from "discourse/helpers/user-avatar";
// and you want to ensure cache is reset
export const SCHEMA_VERSION = 4;
-const Report = Discourse.Model.extend({
+const Report = EmberObject.extend({
average: false,
percent: false,
higher_is_better: true,
diff --git a/app/assets/javascripts/admin/models/screened-email.js.es6 b/app/assets/javascripts/admin/models/screened-email.js.es6
index 0d20f2c7d1..ea72510551 100644
--- a/app/assets/javascripts/admin/models/screened-email.js.es6
+++ b/app/assets/javascripts/admin/models/screened-email.js.es6
@@ -1,7 +1,8 @@
import discourseComputed from "discourse-common/utils/decorators";
import { ajax } from "discourse/lib/ajax";
+import EmberObject from "@ember/object";
-const ScreenedEmail = Discourse.Model.extend({
+const ScreenedEmail = EmberObject.extend({
@discourseComputed("action")
actionName(action) {
return I18n.t("admin.logs.screened_actions." + action);
diff --git a/app/assets/javascripts/admin/models/screened-ip-address.js.es6 b/app/assets/javascripts/admin/models/screened-ip-address.js.es6
index e2b60a2108..bfac17d86c 100644
--- a/app/assets/javascripts/admin/models/screened-ip-address.js.es6
+++ b/app/assets/javascripts/admin/models/screened-ip-address.js.es6
@@ -1,8 +1,9 @@
import discourseComputed from "discourse-common/utils/decorators";
import { equal } from "@ember/object/computed";
import { ajax } from "discourse/lib/ajax";
+import EmberObject from "@ember/object";
-const ScreenedIpAddress = Discourse.Model.extend({
+const ScreenedIpAddress = EmberObject.extend({
@discourseComputed("action_name")
actionName(actionName) {
return I18n.t(`admin.logs.screened_ips.actions.${actionName}`);
diff --git a/app/assets/javascripts/admin/models/screened-url.js.es6 b/app/assets/javascripts/admin/models/screened-url.js.es6
index 515ef6e82c..31ea850778 100644
--- a/app/assets/javascripts/admin/models/screened-url.js.es6
+++ b/app/assets/javascripts/admin/models/screened-url.js.es6
@@ -1,7 +1,8 @@
import discourseComputed from "discourse-common/utils/decorators";
import { ajax } from "discourse/lib/ajax";
+import EmberObject from "@ember/object";
-const ScreenedUrl = Discourse.Model.extend({
+const ScreenedUrl = EmberObject.extend({
@discourseComputed("action")
actionName(action) {
return I18n.t("admin.logs.screened_actions." + action);
diff --git a/app/assets/javascripts/admin/models/site-setting.js.es6 b/app/assets/javascripts/admin/models/site-setting.js.es6
index 7760a61114..4edc89a1b9 100644
--- a/app/assets/javascripts/admin/models/site-setting.js.es6
+++ b/app/assets/javascripts/admin/models/site-setting.js.es6
@@ -1,7 +1,8 @@
import { ajax } from "discourse/lib/ajax";
import Setting from "admin/mixins/setting-object";
+import EmberObject from "@ember/object";
-const SiteSetting = Discourse.Model.extend(Setting, {});
+const SiteSetting = EmberObject.extend(Setting, {});
SiteSetting.reopenClass({
findAll() {
diff --git a/app/assets/javascripts/admin/models/theme-settings.js.es6 b/app/assets/javascripts/admin/models/theme-settings.js.es6
index ab9e5bf9ce..a823592ad2 100644
--- a/app/assets/javascripts/admin/models/theme-settings.js.es6
+++ b/app/assets/javascripts/admin/models/theme-settings.js.es6
@@ -1,3 +1,4 @@
import Setting from "admin/mixins/setting-object";
+import EmberObject from "@ember/object";
-export default Discourse.Model.extend(Setting, {});
+export default EmberObject.extend(Setting, {});
diff --git a/app/assets/javascripts/admin/models/tl3-requirements.js.es6 b/app/assets/javascripts/admin/models/tl3-requirements.js.es6
index 966410b41c..424aea4f58 100644
--- a/app/assets/javascripts/admin/models/tl3-requirements.js.es6
+++ b/app/assets/javascripts/admin/models/tl3-requirements.js.es6
@@ -1,6 +1,7 @@
import discourseComputed from "discourse-common/utils/decorators";
+import EmberObject from "@ember/object";
-export default Discourse.Model.extend({
+export default EmberObject.extend({
@discourseComputed("days_visited", "time_period")
days_visited_percent(daysVisited, timePeriod) {
return Math.round((daysVisited * 100) / timePeriod);
diff --git a/app/assets/javascripts/admin/models/version-check.js.es6 b/app/assets/javascripts/admin/models/version-check.js.es6
index 54ef9844fe..cc888b2588 100644
--- a/app/assets/javascripts/admin/models/version-check.js.es6
+++ b/app/assets/javascripts/admin/models/version-check.js.es6
@@ -1,7 +1,8 @@
import discourseComputed from "discourse-common/utils/decorators";
import { ajax } from "discourse/lib/ajax";
+import EmberObject from "@ember/object";
-const VersionCheck = Discourse.Model.extend({
+const VersionCheck = EmberObject.extend({
@discourseComputed("updated_at")
noCheckPerformed(updatedAt) {
return updatedAt === null;
diff --git a/app/assets/javascripts/admin/models/watched-word.js.es6 b/app/assets/javascripts/admin/models/watched-word.js.es6
index b9ef7380b6..dac78affe1 100644
--- a/app/assets/javascripts/admin/models/watched-word.js.es6
+++ b/app/assets/javascripts/admin/models/watched-word.js.es6
@@ -1,7 +1,7 @@
import { ajax } from "discourse/lib/ajax";
import EmberObject from "@ember/object";
-const WatchedWord = Discourse.Model.extend({
+const WatchedWord = EmberObject.extend({
save() {
return ajax(
"/admin/logs/watched_words" + (this.id ? "/" + this.id : "") + ".json",
diff --git a/app/assets/javascripts/application.js b/app/assets/javascripts/application.js
index fa5ef28880..10c71ca89b 100644
--- a/app/assets/javascripts/application.js
+++ b/app/assets/javascripts/application.js
@@ -36,7 +36,6 @@
//= require ./discourse/lib/show-modal
//= require ./discourse/mixins/scrolling
//= require ./discourse/lib/ajax-error
-//= require ./discourse/models/model
//= require ./discourse/models/result-set
//= require ./discourse/models/store
//= require ./discourse/models/action-summary
diff --git a/app/assets/javascripts/discourse.js.es6 b/app/assets/javascripts/discourse.js.es6
index c56acf9dc8..25d2f74ec8 100644
--- a/app/assets/javascripts/discourse.js.es6
+++ b/app/assets/javascripts/discourse.js.es6
@@ -6,6 +6,8 @@ import {
} from "discourse-common/utils/decorators";
import computed from "@ember/object/computed";
import FocusEvent from "discourse-common/mixins/focus-event";
+import EmberObject from "@ember/object";
+import deprecated from "discourse-common/lib/deprecated";
const _pluginCallbacks = [];
@@ -206,4 +208,14 @@ const Discourse = Ember.Application.extend(FocusEvent, {
})
}).create();
+Object.defineProperty(Discourse, "Model", {
+ get() {
+ deprecated("Use an `@ember/object` instead of Discourse.Model", {
+ since: "2.4.0",
+ dropFrom: "2.5.0"
+ });
+ return EmberObject;
+ }
+});
+
export default Discourse;
diff --git a/app/assets/javascripts/discourse/models/draft.js.es6 b/app/assets/javascripts/discourse/models/draft.js.es6
index 62fefef8c7..178c38f94a 100644
--- a/app/assets/javascripts/discourse/models/draft.js.es6
+++ b/app/assets/javascripts/discourse/models/draft.js.es6
@@ -1,5 +1,7 @@
import { ajax } from "discourse/lib/ajax";
-const Draft = Discourse.Model.extend();
+import EmberObject from "@ember/object";
+
+const Draft = EmberObject.extend();
Draft.reopenClass({
clear(key, sequence) {
diff --git a/app/assets/javascripts/discourse/models/input-validation.js.es6 b/app/assets/javascripts/discourse/models/input-validation.js.es6
index fcbd0a1536..c7120db846 100644
--- a/app/assets/javascripts/discourse/models/input-validation.js.es6
+++ b/app/assets/javascripts/discourse/models/input-validation.js.es6
@@ -1,4 +1,2 @@
-import Model from "discourse/models/model";
-
-// A trivial model we use to handle input validation
-export default Model.extend();
+import EmberObject from "@ember/object";
+export default EmberObject.extend();
diff --git a/app/assets/javascripts/discourse/models/invite.js.es6 b/app/assets/javascripts/discourse/models/invite.js.es6
index 54baf013f5..dc2d4c8538 100644
--- a/app/assets/javascripts/discourse/models/invite.js.es6
+++ b/app/assets/javascripts/discourse/models/invite.js.es6
@@ -4,7 +4,7 @@ import { popupAjaxError } from "discourse/lib/ajax-error";
import { userPath } from "discourse/lib/url";
import { Promise } from "rsvp";
-const Invite = Discourse.Model.extend({
+const Invite = EmberObject.extend({
rescind() {
ajax("/invites", {
type: "DELETE",
diff --git a/app/assets/javascripts/discourse/models/live-post-counts.es6 b/app/assets/javascripts/discourse/models/live-post-counts.es6
index b28c525f8d..ac5f14d76f 100644
--- a/app/assets/javascripts/discourse/models/live-post-counts.es6
+++ b/app/assets/javascripts/discourse/models/live-post-counts.es6
@@ -1,5 +1,7 @@
import { ajax } from "discourse/lib/ajax";
-const LivePostCounts = Discourse.Model.extend({});
+import EmberObject from "@ember/object";
+
+const LivePostCounts = EmberObject.extend({});
LivePostCounts.reopenClass({
find() {
diff --git a/app/assets/javascripts/discourse/models/model.js.es6 b/app/assets/javascripts/discourse/models/model.js.es6
deleted file mode 100644
index 5ce0eb2eaf..0000000000
--- a/app/assets/javascripts/discourse/models/model.js.es6
+++ /dev/null
@@ -1,19 +0,0 @@
-import { isEmpty } from "@ember/utils";
-import EmberObject from "@ember/object";
-const Model = EmberObject.extend();
-
-Model.reopenClass({
- extractByKey(collection, klass) {
- const retval = {};
- if (isEmpty(collection)) {
- return retval;
- }
-
- collection.forEach(function(item) {
- retval[item.id] = klass.create(item);
- });
- return retval;
- }
-});
-
-export default Model;
diff --git a/app/assets/javascripts/discourse/models/nav-item.js.es6 b/app/assets/javascripts/discourse/models/nav-item.js.es6
index 72395681be..4502757aee 100644
--- a/app/assets/javascripts/discourse/models/nav-item.js.es6
+++ b/app/assets/javascripts/discourse/models/nav-item.js.es6
@@ -2,8 +2,9 @@ import discourseComputed from "discourse-common/utils/decorators";
import { toTitleCase } from "discourse/lib/formatter";
import { emojiUnescape } from "discourse/lib/text";
import Category from "discourse/models/category";
+import EmberObject from "@ember/object";
-const NavItem = Discourse.Model.extend({
+const NavItem = EmberObject.extend({
@discourseComputed("categoryName", "name")
title(categoryName, name) {
const extra = {};
diff --git a/app/assets/javascripts/discourse/models/permission-type.js.es6 b/app/assets/javascripts/discourse/models/permission-type.js.es6
index 94a9af0401..f6ad56c928 100644
--- a/app/assets/javascripts/discourse/models/permission-type.js.es6
+++ b/app/assets/javascripts/discourse/models/permission-type.js.es6
@@ -1,6 +1,7 @@
import discourseComputed from "discourse-common/utils/decorators";
+import EmberObject from "@ember/object";
-const PermissionType = Discourse.Model.extend({
+const PermissionType = EmberObject.extend({
@discourseComputed("id")
description(id) {
var key = "";
diff --git a/app/assets/javascripts/discourse/models/topic-list.js.es6 b/app/assets/javascripts/discourse/models/topic-list.js.es6
index b0ec31a834..489c926de3 100644
--- a/app/assets/javascripts/discourse/models/topic-list.js.es6
+++ b/app/assets/javascripts/discourse/models/topic-list.js.es6
@@ -2,11 +2,24 @@ import { notEmpty } from "@ember/object/computed";
import EmberObject from "@ember/object";
import { ajax } from "discourse/lib/ajax";
import RestModel from "discourse/models/rest";
-import Model from "discourse/models/model";
import { getOwner } from "discourse-common/lib/get-owner";
import { Promise } from "rsvp";
import Category from "discourse/models/category";
import Session from "discourse/models/session";
+import { isEmpty } from "@ember/utils";
+import User from "discourse/models/user";
+
+function extractByKey(collection, klass) {
+ const retval = {};
+ if (isEmpty(collection)) {
+ return retval;
+ }
+
+ collection.forEach(function(item) {
+ retval[item.id] = klass.create(item);
+ });
+ return retval;
+}
// Whether to show the category badge in topic lists
function displayCategoryInList(site, category) {
@@ -139,8 +152,8 @@ TopicList.reopenClass({
// Stitch together our side loaded data
const categories = Category.list(),
- users = Model.extractByKey(result.users, Discourse.User),
- groups = Model.extractByKey(result.primary_groups, EmberObject);
+ users = extractByKey(result.users, User),
+ groups = extractByKey(result.primary_groups, EmberObject);
return result.topic_list[listKey].map(t => {
t.category = categories.findBy("id", t.category_id);
diff --git a/app/assets/javascripts/discourse/models/topic-tracking-state.js.es6 b/app/assets/javascripts/discourse/models/topic-tracking-state.js.es6
index 4656900990..a47a934170 100644
--- a/app/assets/javascripts/discourse/models/topic-tracking-state.js.es6
+++ b/app/assets/javascripts/discourse/models/topic-tracking-state.js.es6
@@ -8,6 +8,7 @@ import {
import { defaultHomepage } from "discourse/lib/utilities";
import PreloadStore from "preload-store";
import Category from "discourse/models/category";
+import EmberObject from "@ember/object";
function isNew(topic) {
return (
@@ -25,7 +26,7 @@ function isUnread(topic) {
);
}
-const TopicTrackingState = Discourse.Model.extend({
+const TopicTrackingState = EmberObject.extend({
messageCount: 0,
@on("init")
diff --git a/app/assets/javascripts/discourse/models/user-action-group.js.es6 b/app/assets/javascripts/discourse/models/user-action-group.js.es6
index b0706cd324..c432cd694c 100644
--- a/app/assets/javascripts/discourse/models/user-action-group.js.es6
+++ b/app/assets/javascripts/discourse/models/user-action-group.js.es6
@@ -1,8 +1,7 @@
-/**
- A data model representing a group of UserActions
-**/
-export default Discourse.Model.extend({
- push: function(item) {
+import EmberObject from "@ember/object";
+
+export default EmberObject.extend({
+ push(item) {
if (!this.items) {
this.items = [];
}
diff --git a/app/assets/javascripts/discourse/models/user-badge.js.es6 b/app/assets/javascripts/discourse/models/user-badge.js.es6
index 3e00072f6e..b6a0dbb7cf 100644
--- a/app/assets/javascripts/discourse/models/user-badge.js.es6
+++ b/app/assets/javascripts/discourse/models/user-badge.js.es6
@@ -3,8 +3,9 @@ import { ajax } from "discourse/lib/ajax";
import Badge from "discourse/models/badge";
import { Promise } from "rsvp";
import Topic from "discourse/models/topic";
+import EmberObject from "@ember/object";
-const UserBadge = Discourse.Model.extend({
+const UserBadge = EmberObject.extend({
@discourseComputed
postUrl: function() {
if (this.topic_title) {
diff --git a/app/assets/javascripts/discourse/models/user-posts-stream.js.es6 b/app/assets/javascripts/discourse/models/user-posts-stream.js.es6
index 6213d98d14..5a71149fb5 100644
--- a/app/assets/javascripts/discourse/models/user-posts-stream.js.es6
+++ b/app/assets/javascripts/discourse/models/user-posts-stream.js.es6
@@ -3,8 +3,9 @@ import { ajax } from "discourse/lib/ajax";
import { url } from "discourse/lib/computed";
import UserAction from "discourse/models/user-action";
import { Promise } from "rsvp";
+import EmberObject from "@ember/object";
-export default Discourse.Model.extend({
+export default EmberObject.extend({
loaded: false,
@on("init")
diff --git a/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb b/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
index 6f25f0823e..c8dcad4970 100644
--- a/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
+++ b/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
@@ -89,7 +89,6 @@ JS
"discourse/routes/discourse",
"discourse/models/site",
"discourse/models/user",
- "discourse/models/model"
]
)
diff --git a/test/javascripts/models/model-test.js.es6 b/test/javascripts/models/model-test.js.es6
deleted file mode 100644
index f38063d6af..0000000000
--- a/test/javascripts/models/model-test.js.es6
+++ /dev/null
@@ -1,36 +0,0 @@
-import EmberObject from "@ember/object";
-import Model from "discourse/models/model";
-
-QUnit.module("model:discourse");
-
-QUnit.test(
- "extractByKey: converts a list of hashes into a hash of instances of specified class, indexed by their ids",
- assert => {
- var firstObject = { id: "id_1", foo: "foo_1" };
- var secondObject = { id: "id_2", foo: "foo_2" };
-
- var actual = Model.extractByKey([firstObject, secondObject], EmberObject);
- var expected = {
- id_1: EmberObject.create(firstObject),
- id_2: EmberObject.create(secondObject)
- };
-
- assert.ok(_.isEqual(actual, expected));
- }
-);
-
-QUnit.test(
- "extractByKey: returns an empty hash if there isn't anything to convert",
- assert => {
- assert.deepEqual(
- Model.extractByKey(),
- {},
- "when called without parameters"
- );
- assert.deepEqual(
- Model.extractByKey([]),
- {},
- "when called with an empty array"
- );
- }
-);
From bd92fdeb4d5e0d366d8a40dded5109d7aa74b282 Mon Sep 17 00:00:00 2001
From: Robin Ward
Date: Fri, 8 Nov 2019 14:14:51 -0500
Subject: [PATCH 054/408] FIX: Add deprecation for Discourse.NavItem in case
themes are using it
---
.../javascripts/discourse/models/nav-item.js.es6 | 11 +++++++++++
1 file changed, 11 insertions(+)
diff --git a/app/assets/javascripts/discourse/models/nav-item.js.es6 b/app/assets/javascripts/discourse/models/nav-item.js.es6
index 4502757aee..c0cec002ae 100644
--- a/app/assets/javascripts/discourse/models/nav-item.js.es6
+++ b/app/assets/javascripts/discourse/models/nav-item.js.es6
@@ -3,6 +3,7 @@ import { toTitleCase } from "discourse/lib/formatter";
import { emojiUnescape } from "discourse/lib/text";
import Category from "discourse/models/category";
import EmberObject from "@ember/object";
+import deprecated from "discourse-common/lib/deprecated";
const NavItem = EmberObject.extend({
@discourseComputed("categoryName", "name")
@@ -255,3 +256,13 @@ export function addNavItem(item) {
NavItem.extraNavItems.push(navItem);
return navItem;
}
+
+Object.defineProperty(Discourse, "NavItem", {
+ get() {
+ deprecated("Import the NavItem object instead of using Discourse.NavItem", {
+ since: "2.4.0",
+ dropFrom: "2.5.0"
+ });
+ return NavItem;
+ }
+});
From c0e105fc8ccb9e97e67323ced12afe111080f1fd Mon Sep 17 00:00:00 2001
From: Robin Ward
Date: Fri, 8 Nov 2019 14:55:36 -0500
Subject: [PATCH 055/408] FIX: Return a deprecation for `Discourse.Session`
---
.../javascripts/discourse/models/session.js.es6 | 11 +++++++++++
1 file changed, 11 insertions(+)
diff --git a/app/assets/javascripts/discourse/models/session.js.es6 b/app/assets/javascripts/discourse/models/session.js.es6
index f323540640..9f05080ea9 100644
--- a/app/assets/javascripts/discourse/models/session.js.es6
+++ b/app/assets/javascripts/discourse/models/session.js.es6
@@ -1,5 +1,6 @@
import RestModel from "discourse/models/rest";
import Singleton from "discourse/mixins/singleton";
+import deprecated from "discourse-common/lib/deprecated";
// A data model representing current session data. You can put transient
// data here you might want later. It is not stored or serialized anywhere.
@@ -10,4 +11,14 @@ const Session = RestModel.extend({
});
Session.reopenClass(Singleton);
+
+Object.defineProperty(Discourse, "Session", {
+ get() {
+ deprecated("Import the Session object instead of using Discourse.Session", {
+ since: "2.4.0",
+ dropFrom: "2.5.0"
+ });
+ return Session;
+ }
+});
export default Session;
From 920f8c6d752ff25bdd7c4f6736d613e1b68cbcaf Mon Sep 17 00:00:00 2001
From: Robin Ward
Date: Fri, 8 Nov 2019 15:18:13 -0500
Subject: [PATCH 056/408] REFACTOR: Remove `Discourse.Route` in lieu of
importing
---
.../javascripts/discourse-common/resolver.js.es6 | 5 +++++
.../javascripts/discourse/models/category.js.es6 | 2 +-
.../javascripts/discourse/models/nav-item.js.es6 | 2 +-
.../javascripts/discourse/routes/discourse.js.es6 | 11 +++++++++++
.../tilt/es6_module_transpiler_template.rb | 6 ------
5 files changed, 18 insertions(+), 8 deletions(-)
diff --git a/app/assets/javascripts/discourse-common/resolver.js.es6 b/app/assets/javascripts/discourse-common/resolver.js.es6
index e1507406bb..ba272c6bf1 100644
--- a/app/assets/javascripts/discourse-common/resolver.js.es6
+++ b/app/assets/javascripts/discourse-common/resolver.js.es6
@@ -139,6 +139,11 @@ export function buildResolver(baseName) {
},
resolveRoute(parsedName) {
+ if (parsedName.fullNameWithoutType === "basic") {
+ return requirejs("discourse/routes/discourse", null, null, true)
+ .default;
+ }
+
return this.customResolve(parsedName) || this._super(parsedName);
},
diff --git a/app/assets/javascripts/discourse/models/category.js.es6 b/app/assets/javascripts/discourse/models/category.js.es6
index 1384837d33..e268330618 100644
--- a/app/assets/javascripts/discourse/models/category.js.es6
+++ b/app/assets/javascripts/discourse/models/category.js.es6
@@ -411,7 +411,7 @@ Category.reopenClass({
Object.defineProperty(Discourse, "Category", {
get() {
deprecated(
- "Import the Category object instead of using Discourse.Category",
+ "Import the Category class instead of using Discourse.Category",
{ since: "2.4.0", dropFrom: "2.5.0" }
);
return Category;
diff --git a/app/assets/javascripts/discourse/models/nav-item.js.es6 b/app/assets/javascripts/discourse/models/nav-item.js.es6
index c0cec002ae..f6c598d9df 100644
--- a/app/assets/javascripts/discourse/models/nav-item.js.es6
+++ b/app/assets/javascripts/discourse/models/nav-item.js.es6
@@ -259,7 +259,7 @@ export function addNavItem(item) {
Object.defineProperty(Discourse, "NavItem", {
get() {
- deprecated("Import the NavItem object instead of using Discourse.NavItem", {
+ deprecated("Import the NavItem class instead of using Discourse.NavItem", {
since: "2.4.0",
dropFrom: "2.5.0"
});
diff --git a/app/assets/javascripts/discourse/routes/discourse.js.es6 b/app/assets/javascripts/discourse/routes/discourse.js.es6
index 2329168593..980e986cd9 100644
--- a/app/assets/javascripts/discourse/routes/discourse.js.es6
+++ b/app/assets/javascripts/discourse/routes/discourse.js.es6
@@ -2,6 +2,7 @@ import { once } from "@ember/runloop";
import Composer from "discourse/models/composer";
import { getOwner } from "discourse-common/lib/get-owner";
import Route from "@ember/routing/route";
+import deprecated from "discourse-common/lib/deprecated";
const DiscourseRoute = Route.extend({
showFooter: false,
@@ -107,4 +108,14 @@ const DiscourseRoute = Route.extend({
}
});
+Object.defineProperty(Discourse, "Route", {
+ get() {
+ deprecated("Import the Route class instead of using Discourse.Route", {
+ since: "2.4.0",
+ dropFrom: "2.5.0"
+ });
+ return Route;
+ }
+});
+
export default DiscourseRoute;
diff --git a/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb b/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
index c8dcad4970..d61cebfbf0 100644
--- a/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
+++ b/lib/es6_module_transpiler/tilt/es6_module_transpiler_template.rb
@@ -86,7 +86,6 @@ JS
@@whitelisted ||= Set.new(
[
- "discourse/routes/discourse",
"discourse/models/site",
"discourse/models/user",
]
@@ -151,11 +150,6 @@ JS
if require_name !~ /\-test$/ && require_name !~ /^discourse\/plugins\//
result = "#{class_name}#{type.classify}"
- # HAX
- result = "Controller" if result == "ControllerController"
- result = "Route" if result == "DiscourseRoute"
- result = "View" if result == "ViewView"
-
result = result.gsub(/Mixin$/, '')
result = result.gsub(/Model$/, '')
From 63bd07492ea07a999d8359409a0ea4000bce364f Mon Sep 17 00:00:00 2001
From: Jay Pfaffman
Date: Fri, 8 Nov 2019 15:34:15 -0800
Subject: [PATCH 057/408] FIX: Update api_key rake task for recent changes
New usage:
```
rake api_key:get_or_create_master["Onboarding Key"]
```
---
lib/tasks/api.rake | 9 +++++----
1 file changed, 5 insertions(+), 4 deletions(-)
diff --git a/lib/tasks/api.rake b/lib/tasks/api.rake
index 8bff7dd5a2..bf8c37ecd3 100644
--- a/lib/tasks/api.rake
+++ b/lib/tasks/api.rake
@@ -1,8 +1,9 @@
# frozen_string_literal: true
-desc "generate api key if missing, return existing if already there"
-task "api_key:get" => :environment do
- api_key = ApiKey.create_master_key
+desc "find or generate a master api key with given description"
+task "api_key:get_or_create_master", [:description] => :environment do |task, args|
+ raise "Supply a description for the key" if !args[:description]
+ api_key = ApiKey.find_or_create_by!(description: args[:description], revoked_at: nil, user_id: nil)
- puts api_key.key
+ puts api_key.key
end
From 15f6f57cdcebc7583ddb5a311174d10a7300ae4a Mon Sep 17 00:00:00 2001
From: Blake Erickson
Date: Fri, 8 Nov 2019 17:28:48 -0700
Subject: [PATCH 058/408] DEV: Add update message for an outdated mail-receiver
Previous versions of the mail-receiver used query based api credentials,
if we detect this we will show a message in the admin panel to update
the mail receiver.
---
app/models/admin_dashboard_data.rb | 3 ++-
config/locales/server.en.yml | 1 +
lib/auth/default_current_user_provider.rb | 11 +++++++++--
3 files changed, 12 insertions(+), 3 deletions(-)
diff --git a/app/models/admin_dashboard_data.rb b/app/models/admin_dashboard_data.rb
index 0ef9960d1b..288158eb32 100644
--- a/app/models/admin_dashboard_data.rb
+++ b/app/models/admin_dashboard_data.rb
@@ -85,7 +85,8 @@ class AdminDashboardData
'dashboard.bad_favicon_url',
'dashboard.poll_pop3_timeout',
'dashboard.poll_pop3_auth_error',
- 'dashboard.deprecated_api_usage'
+ 'dashboard.deprecated_api_usage',
+ 'dashboard.update_mail_receiver'
]
add_problem_check :rails_env_check, :host_names_check, :force_https_check,
diff --git a/config/locales/server.en.yml b/config/locales/server.en.yml
index dac88f2d93..6d3cefe305 100644
--- a/config/locales/server.en.yml
+++ b/config/locales/server.en.yml
@@ -1339,6 +1339,7 @@ en:
missing_mailgun_api_key: "The server is configured to send emails via Mailgun but you haven't provided an API key used to verify the webhook messages."
bad_favicon_url: "The favicon is failing to load. Check your favicon setting in Site Settings."
deprecated_api_usage: "We detected an API request using a deprecated authentication method. Please update it to use header based auth."
+ update_mail_receiver: "We detected an outdated version of mail-receiver. Please ssh into this server and run `/var/discourse/launcher rebuild mail-receiver`."
poll_pop3_timeout: "Connection to the POP3 server is timing out. Incoming email could not be retrieved. Please check your POP3 settings and service provider."
poll_pop3_auth_error: "Connection to the POP3 server is failing with an authentication error. Please check your POP3 settings."
force_https_warning: "Your website is using SSL. But `force_https` is not yet enabled in your site settings."
diff --git a/lib/auth/default_current_user_provider.rb b/lib/auth/default_current_user_provider.rb
index 353555880e..3f405233cc 100644
--- a/lib/auth/default_current_user_provider.rb
+++ b/lib/auth/default_current_user_provider.rb
@@ -283,9 +283,16 @@ class Auth::DefaultCurrentUserProvider
def lookup_api_user(api_key_value, request)
if api_key = ApiKey.active.where(key: api_key_value).includes(:user).first
api_username = header_api_key? ? @env[HEADER_API_USERNAME] : request[API_USERNAME]
+
+ # Check for deprecated api auth
if !header_api_key?
- # Notify admins of deprecated auth method
- AdminDashboardData.add_problem_message('dashboard.deprecated_api_usage', 1.day)
+ if request.path == "/admin/email/handle_mail"
+ # Notify admins that the mail receiver is still using query auth and to update
+ AdminDashboardData.add_problem_message('dashboard.update_mail_receiver', 1.day)
+ else
+ # Notify admins of deprecated auth method
+ AdminDashboardData.add_problem_message('dashboard.deprecated_api_usage', 1.day)
+ end
end
if api_key.allowed_ips.present? && !api_key.allowed_ips.any? { |ip| ip.include?(request.ip) }
From b68eab2b46391406695995a045428bdde6fb7577 Mon Sep 17 00:00:00 2001
From: Sam Saffron
Date: Mon, 11 Nov 2019 09:36:40 +1100
Subject: [PATCH 059/408] DEV: remove deprecated syntax
Ruby 2.7 is going to deprecate "Magic Proc Init". This feature is enormously
magical anyway and the new code is far easier to comprehend.
---
lib/mini_sql_multisite_connection.rb | 5 +++--
1 file changed, 3 insertions(+), 2 deletions(-)
diff --git a/lib/mini_sql_multisite_connection.rb b/lib/mini_sql_multisite_connection.rb
index c08d3813a9..a1cd6a6897 100644
--- a/lib/mini_sql_multisite_connection.rb
+++ b/lib/mini_sql_multisite_connection.rb
@@ -26,8 +26,9 @@ class MiniSqlMultisiteConnection < MiniSql::Postgres::Connection
end
class AfterCommitWrapper
- def initialize
- @callback = Proc.new
+ def initialize(&blk)
+ raise ArgumentError, "tried to create a Proc without a block in AfterCommitWrapper" if !blk
+ @callback = blk
end
def committed!(*)
From bf0ef73286ce3d956a970dfa222b56b972014a18 Mon Sep 17 00:00:00 2001
From: Sam Saffron
Date: Mon, 11 Nov 2019 10:23:14 +1100
Subject: [PATCH 060/408] DEV: correct rake task used to grab admin key
We amended it so "api_key:get" is no longer supported and instead we are
more explicit. This matches that change and fixes the bench.
---
script/bench.rb | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/script/bench.rb b/script/bench.rb
index b847db2f3c..44645f5549 100644
--- a/script/bench.rb
+++ b/script/bench.rb
@@ -184,7 +184,7 @@ puts "Populating Profile DB"
run("bundle exec ruby script/profile_db_generator.rb")
puts "Getting api key"
-api_key = `bundle exec rake api_key:get`.split("\n")[-1]
+api_key = `bundle exec rake api_key:get_or_create_master[bench]`.split("\n")[-1]
def bench(path, name)
puts "Running apache bench warmup"
From 91daafc674a90221b355eb1930c1f47df2658cc9 Mon Sep 17 00:00:00 2001
From: Sam Saffron
Date: Mon, 11 Nov 2019 11:18:12 +1100
Subject: [PATCH 061/408] DEV: correct implementation of expiry api
Previously we were always hard-coding expiry, this allows the secure session
to correctly handle custom expiry times
Also adds a ttl method for looking up time to live
---
lib/secure_session.rb | 6 +++++-
spec/components/secure_session_spec.rb | 12 ++++++++++++
2 files changed, 17 insertions(+), 1 deletion(-)
diff --git a/lib/secure_session.rb b/lib/secure_session.rb
index 6b8efe57c1..667034361e 100644
--- a/lib/secure_session.rb
+++ b/lib/secure_session.rb
@@ -16,10 +16,14 @@ class SecureSession
def set(key, val, expires: nil)
expires ||= SecureSession.expiry
- $redis.setex(prefixed_key(key), SecureSession.expiry.to_i, val.to_s)
+ $redis.setex(prefixed_key(key), expires.to_i, val.to_s)
true
end
+ def ttl(key)
+ $redis.ttl(prefixed_key(key))
+ end
+
def [](key)
$redis.get(prefixed_key(key))
end
diff --git a/spec/components/secure_session_spec.rb b/spec/components/secure_session_spec.rb
index 1e2aad5060..59910ff5a0 100644
--- a/spec/components/secure_session_spec.rb
+++ b/spec/components/secure_session_spec.rb
@@ -14,4 +14,16 @@ describe SecureSession do
s["hello"] = nil
expect(s["hello"]).to eq(nil)
end
+
+ it "can override expiry" do
+ s = SecureSession.new("abc")
+ key = SecureRandom.hex
+
+ s.set(key, "test2", expires: 5.minutes)
+ expect(s.ttl(key)).to be_within(1.second).of (5.minutes)
+
+ key = SecureRandom.hex
+ s.set(key, "test2")
+ expect(s.ttl(key)).to be_within(1.second).of (SecureSession.expiry)
+ end
end
From a2d6169a5e1c805062e2aae553dd1620a83b3699 Mon Sep 17 00:00:00 2001
From: Sam Saffron
Date: Mon, 11 Nov 2019 15:36:16 +1100
Subject: [PATCH 062/408] DEV: upgrade mini_racer
This is done to fix a compatibility issue with Ruby 2.7, it ensures we clean
up fds for a pipe we use to track timeouts in mini racer.
---
Gemfile.lock | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/Gemfile.lock b/Gemfile.lock
index 7201a23254..e49202d9f6 100644
--- a/Gemfile.lock
+++ b/Gemfile.lock
@@ -188,7 +188,7 @@ GEM
method_source (0.9.2)
mini_mime (1.0.2)
mini_portile2 (2.4.0)
- mini_racer (0.2.6)
+ mini_racer (0.2.8)
libv8 (>= 6.9.411)
mini_scheduler (0.12.2)
sidekiq
@@ -548,4 +548,4 @@ DEPENDENCIES
yaml-lint
BUNDLED WITH
- 1.17.3
+ 2.1.0.pre.2
From 0c0192e7dabf6959c4248fa0454da206ac9c780f Mon Sep 17 00:00:00 2001
From: Sam Saffron
Date: Mon, 11 Nov 2019 16:04:18 +1100
Subject: [PATCH 063/408] DEV: disable all upload recovery specs
These specs are inherently fragile when they are run in a concurrent mode
in CI.
One process will create an upload, another will destroy the upload on disk
at the same time. We need a new safe mechanism here.
---
spec/lib/upload_recovery_spec.rb | 14 +++++++-------
1 file changed, 7 insertions(+), 7 deletions(-)
diff --git a/spec/lib/upload_recovery_spec.rb b/spec/lib/upload_recovery_spec.rb
index f248d009f5..3d8b840b1f 100644
--- a/spec/lib/upload_recovery_spec.rb
+++ b/spec/lib/upload_recovery_spec.rb
@@ -49,7 +49,7 @@ RSpec.describe UploadRecovery do
describe '#recover' do
describe 'when given an invalid sha1' do
- it 'should not do anything' do
+ xit 'should not do anything' do
upload_recovery.expects(:recover_from_local).never
post.update!(
@@ -66,7 +66,7 @@ RSpec.describe UploadRecovery do
end
end
- it 'accepts a custom ActiveRecord relation' do
+ xit 'accepts a custom ActiveRecord relation' do
post.update!(updated_at: 2.days.ago)
upload.destroy!
@@ -85,7 +85,7 @@ RSpec.describe UploadRecovery do
).tap(&:link_post_uploads)
end
- it 'should recover the attachment' do
+ xit 'should recover the attachment' do
expect do
upload2.destroy!
end.to change { post.reload.uploads.count }.from(1).to(0)
@@ -99,7 +99,7 @@ RSpec.describe UploadRecovery do
end
end
- it 'should recover uploads and attachments' do
+ xit 'should recover uploads and attachments' do
stub_request(:get, "http://test.localhost#{upload.url}")
.to_return(status: 200)
@@ -125,7 +125,7 @@ RSpec.describe UploadRecovery do
).tap(&:link_post_uploads)
end
- it 'should recover the upload' do
+ xit 'should recover the upload' do
stub_request(:get, "http://test.localhost#{upload.url}")
.to_return(status: 200)
@@ -152,7 +152,7 @@ RSpec.describe UploadRecovery do
).tap(&:link_post_uploads)
end
- it 'should recover the upload' do
+ xit 'should recover the upload' do
stub_request(:get, "http://test.localhost#{upload.url}")
.to_return(status: 200)
@@ -179,7 +179,7 @@ RSpec.describe UploadRecovery do
).tap(&:link_post_uploads)
end
- it 'should recover the upload' do
+ xit 'should recover the upload' do
stub_request(:get, "http://test.localhost#{upload.url}")
.to_return(status: 200)
From 12bc6ce8c139aa4847a99ec59137fe592893eba9 Mon Sep 17 00:00:00 2001
From: Vinoth Kannan
Date: Mon, 11 Nov 2019 18:18:33 +0530
Subject: [PATCH 064/408] FIX: remove magic numbers in notification levels.
ba5b78a34874d393440e7eee0aee07f0b213c4ae
---
app/models/category_user.rb | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/app/models/category_user.rb b/app/models/category_user.rb
index d2dd1a4d36..6b024d5700 100644
--- a/app/models/category_user.rb
+++ b/app/models/category_user.rb
@@ -207,9 +207,9 @@ class CategoryUser < ActiveRecord::Base
SiteSetting.default_categories_watching.split("|"),
SiteSetting.default_categories_tracking.split("|"),
SiteSetting.default_categories_watching_first_post.split("|"),
- ].flatten.map { |id| [id.to_i, 1] }
+ ].flatten.map { |id| [id.to_i, notification_levels[:regular]] }
- notification_levels += SiteSetting.default_categories_muted.split("|").map { |id| [id.to_i, 0] }
+ notification_levels += SiteSetting.default_categories_muted.split("|").map { |id| [id.to_i, notification_levels[:muted]] }
else
notification_levels = CategoryUser.where(user: guardian.user).pluck(:category_id, :notification_level)
end
From 6e3601469cb811ecc9e7971979b24664528295ca Mon Sep 17 00:00:00 2001
From: Vinoth Kannan
Date: Mon, 11 Nov 2019 18:57:14 +0530
Subject: [PATCH 065/408] FIX: use correct class variable to get notification
levels.
---
app/models/category_user.rb | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/app/models/category_user.rb b/app/models/category_user.rb
index 6b024d5700..1d9b2bfe22 100644
--- a/app/models/category_user.rb
+++ b/app/models/category_user.rb
@@ -207,9 +207,9 @@ class CategoryUser < ActiveRecord::Base
SiteSetting.default_categories_watching.split("|"),
SiteSetting.default_categories_tracking.split("|"),
SiteSetting.default_categories_watching_first_post.split("|"),
- ].flatten.map { |id| [id.to_i, notification_levels[:regular]] }
+ ].flatten.map { |id| [id.to_i, self.notification_levels[:regular]] }
- notification_levels += SiteSetting.default_categories_muted.split("|").map { |id| [id.to_i, notification_levels[:muted]] }
+ notification_levels += SiteSetting.default_categories_muted.split("|").map { |id| [id.to_i, self.notification_levels[:muted]] }
else
notification_levels = CategoryUser.where(user: guardian.user).pluck(:category_id, :notification_level)
end
From 2a6713c2ba317a245277b62b67babf8a2d2590e6 Mon Sep 17 00:00:00 2001
From: Robin Ward
Date: Mon, 11 Nov 2019 09:22:57 -0500
Subject: [PATCH 066/408] FIX: Was using a native browser Promise instead of
RSVP
---
app/assets/javascripts/discourse/routes/build-topic-route.js.es6 | 1 +
1 file changed, 1 insertion(+)
diff --git a/app/assets/javascripts/discourse/routes/build-topic-route.js.es6 b/app/assets/javascripts/discourse/routes/build-topic-route.js.es6
index 34847b8725..d99b190120 100644
--- a/app/assets/javascripts/discourse/routes/build-topic-route.js.es6
+++ b/app/assets/javascripts/discourse/routes/build-topic-route.js.es6
@@ -2,6 +2,7 @@ import DiscourseRoute from "discourse/routes/discourse";
import { queryParams } from "discourse/controllers/discovery-sortable";
import { defaultHomepage } from "discourse/lib/utilities";
import Session from "discourse/models/session";
+import { Promise } from "rsvp";
// A helper to build a topic route for a filter
function filterQueryParams(params, defaultParams) {
From 0c8ae1e8492f386caa464b4de5f53b19e0d43edb Mon Sep 17 00:00:00 2001
From: Robin Ward
Date: Mon, 11 Nov 2019 09:25:33 -0500
Subject: [PATCH 067/408] FIX: More missing RSVP imports
---
app/assets/javascripts/discourse/models/static-page.js.es6 | 2 ++
app/assets/javascripts/discourse/models/topic.js.es6 | 1 +
2 files changed, 3 insertions(+)
diff --git a/app/assets/javascripts/discourse/models/static-page.js.es6 b/app/assets/javascripts/discourse/models/static-page.js.es6
index 57bb3cc2df..7ec19c23b7 100644
--- a/app/assets/javascripts/discourse/models/static-page.js.es6
+++ b/app/assets/javascripts/discourse/models/static-page.js.es6
@@ -1,5 +1,7 @@
import EmberObject from "@ember/object";
import { ajax } from "discourse/lib/ajax";
+import { Promise } from "rsvp";
+
const StaticPage = EmberObject.extend();
StaticPage.reopenClass({
diff --git a/app/assets/javascripts/discourse/models/topic.js.es6 b/app/assets/javascripts/discourse/models/topic.js.es6
index ca41597cfd..39e6464bfa 100644
--- a/app/assets/javascripts/discourse/models/topic.js.es6
+++ b/app/assets/javascripts/discourse/models/topic.js.es6
@@ -20,6 +20,7 @@ import {
} from "discourse-common/utils/decorators";
import Category from "discourse/models/category";
import Session from "discourse/models/session";
+import { Promise } from "rsvp";
export function loadTopicView(topic, args) {
const data = _.merge({}, args);
From c04369ed8f42df992bff8b60049f25530c4398fa Mon Sep 17 00:00:00 2001
From: Gerhard Schlager
Date: Mon, 11 Nov 2019 15:37:13 +0100
Subject: [PATCH 068/408] DEV: Revert to Bundler 1.17
Follow-up to a2d6169a5e1c805062e2aae553dd1620a83b3699
---
Gemfile.lock | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/Gemfile.lock b/Gemfile.lock
index e49202d9f6..6abc17fb50 100644
--- a/Gemfile.lock
+++ b/Gemfile.lock
@@ -548,4 +548,4 @@ DEPENDENCIES
yaml-lint
BUNDLED WITH
- 2.1.0.pre.2
+ 1.17.3
From 1bbb9b30fc1f69e0cb16698a8b20acb9c6f2838b Mon Sep 17 00:00:00 2001
From: Mark VanLandingham
Date: Fri, 8 Nov 2019 13:00:19 -0600
Subject: [PATCH 069/408] DEV: Import isNone for @ember/utils
---
app/assets/javascripts/discourse-loader.js | 3 +++
.../javascripts/discourse/models/invite.js.es6 | 5 +++--
.../routes/build-category-route.js.es6 | 3 ++-
.../select-kit/components/category-row.js.es6 | 5 +++--
.../future-date-input-selector/mixin.js.es6 | 3 ++-
.../select-kit/mixins/plugin-api.js.es6 | 17 ++++++++---------
6 files changed, 21 insertions(+), 15 deletions(-)
diff --git a/app/assets/javascripts/discourse-loader.js b/app/assets/javascripts/discourse-loader.js
index 2f7b0b9b28..5016efe395 100644
--- a/app/assets/javascripts/discourse-loader.js
+++ b/app/assets/javascripts/discourse-loader.js
@@ -104,6 +104,9 @@ var define, requirejs;
},
"@ember/error": {
default: Ember.error
+ },
+ "@ember/utils": {
+ isNone: Ember.isNone
}
};
}
diff --git a/app/assets/javascripts/discourse/models/invite.js.es6 b/app/assets/javascripts/discourse/models/invite.js.es6
index dc2d4c8538..dc41ac7776 100644
--- a/app/assets/javascripts/discourse/models/invite.js.es6
+++ b/app/assets/javascripts/discourse/models/invite.js.es6
@@ -3,6 +3,7 @@ import { ajax } from "discourse/lib/ajax";
import { popupAjaxError } from "discourse/lib/ajax-error";
import { userPath } from "discourse/lib/url";
import { Promise } from "rsvp";
+import { isNone } from "@ember/utils";
const Invite = EmberObject.extend({
rescind() {
@@ -36,8 +37,8 @@ Invite.reopenClass({
if (!user) Promise.resolve();
const data = {};
- if (!Ember.isNone(filter)) data.filter = filter;
- if (!Ember.isNone(search)) data.search = search;
+ if (!isNone(filter)) data.filter = filter;
+ if (!isNone(search)) data.search = search;
data.offset = offset || 0;
return ajax(userPath(`${user.username_lower}/invited.json`), {
diff --git a/app/assets/javascripts/discourse/routes/build-category-route.js.es6 b/app/assets/javascripts/discourse/routes/build-category-route.js.es6
index 064f02a494..b7dceff089 100644
--- a/app/assets/javascripts/discourse/routes/build-category-route.js.es6
+++ b/app/assets/javascripts/discourse/routes/build-category-route.js.es6
@@ -9,6 +9,7 @@ import PermissionType from "discourse/models/permission-type";
import CategoryList from "discourse/models/category-list";
import Category from "discourse/models/category";
import { Promise, all } from "rsvp";
+import { isNone } from "@ember/utils";
// A helper function to create a category route with parameters
export default (filterArg, params) => {
@@ -79,7 +80,7 @@ export default (filterArg, params) => {
_createSubcategoryList(category) {
this._categoryList = null;
if (
- Ember.isNone(category.get("parentCategory")) &&
+ isNone(category.get("parentCategory")) &&
category.get("show_subcategory_list")
) {
return CategoryList.listForParent(this.store, category).then(
diff --git a/app/assets/javascripts/select-kit/components/category-row.js.es6 b/app/assets/javascripts/select-kit/components/category-row.js.es6
index e8963e96b6..dee781b294 100644
--- a/app/assets/javascripts/select-kit/components/category-row.js.es6
+++ b/app/assets/javascripts/select-kit/components/category-row.js.es6
@@ -4,6 +4,7 @@ import SelectKitRowComponent from "select-kit/components/select-kit/select-kit-r
import discourseComputed from "discourse-common/utils/decorators";
import Category from "discourse/models/category";
import { categoryBadgeHTML } from "discourse/helpers/category-link";
+import { isNone } from "@ember/utils";
export default SelectKitRowComponent.extend({
layoutName: "select-kit/templates/components/category-row",
@@ -15,7 +16,7 @@ export default SelectKitRowComponent.extend({
@discourseComputed("options.displayCategoryDescription")
displayCategoryDescription(displayCategoryDescription) {
- if (Ember.isNone(displayCategoryDescription)) {
+ if (isNone(displayCategoryDescription)) {
return true;
}
@@ -63,7 +64,7 @@ export default SelectKitRowComponent.extend({
@discourseComputed("parentCategoryid")
hasParentCategory(parentCategoryid) {
- return !Ember.isNone(parentCategoryid);
+ return !isNone(parentCategoryid);
},
@discourseComputed("category")
diff --git a/app/assets/javascripts/select-kit/components/future-date-input-selector/mixin.js.es6 b/app/assets/javascripts/select-kit/components/future-date-input-selector/mixin.js.es6
index dd111348de..9aa6cf56fe 100644
--- a/app/assets/javascripts/select-kit/components/future-date-input-selector/mixin.js.es6
+++ b/app/assets/javascripts/select-kit/components/future-date-input-selector/mixin.js.es6
@@ -1,6 +1,7 @@
import { CLOSE_STATUS_TYPE } from "discourse/controllers/edit-topic-timer";
import { timeframeDetails } from "select-kit/components/future-date-input-selector";
import Mixin from "@ember/object/mixin";
+import { isNone } from "@ember/utils";
export default Mixin.create({
_computeIconsForValue(value) {
@@ -14,7 +15,7 @@ export default Mixin.create({
},
_computeDatetimeForValue(value) {
- if (Ember.isNone(value)) {
+ if (isNone(value)) {
return null;
}
diff --git a/app/assets/javascripts/select-kit/mixins/plugin-api.js.es6 b/app/assets/javascripts/select-kit/mixins/plugin-api.js.es6
index 68dd1c8839..9386c595cf 100644
--- a/app/assets/javascripts/select-kit/mixins/plugin-api.js.es6
+++ b/app/assets/javascripts/select-kit/mixins/plugin-api.js.es6
@@ -1,8 +1,9 @@
import Mixin from "@ember/object/mixin";
+import { isNone } from "@ember/utils";
let _appendContentCallbacks = {};
function appendContent(pluginApiIdentifiers, contentFunction) {
- if (Ember.isNone(_appendContentCallbacks[pluginApiIdentifiers])) {
+ if (isNone(_appendContentCallbacks[pluginApiIdentifiers])) {
_appendContentCallbacks[pluginApiIdentifiers] = [];
}
@@ -11,7 +12,7 @@ function appendContent(pluginApiIdentifiers, contentFunction) {
let _prependContentCallbacks = {};
function prependContent(pluginApiIdentifiers, contentFunction) {
- if (Ember.isNone(_prependContentCallbacks[pluginApiIdentifiers])) {
+ if (isNone(_prependContentCallbacks[pluginApiIdentifiers])) {
_prependContentCallbacks[pluginApiIdentifiers] = [];
}
@@ -20,7 +21,7 @@ function prependContent(pluginApiIdentifiers, contentFunction) {
let _modifyContentCallbacks = {};
function modifyContent(pluginApiIdentifiers, contentFunction) {
- if (Ember.isNone(_modifyContentCallbacks[pluginApiIdentifiers])) {
+ if (isNone(_modifyContentCallbacks[pluginApiIdentifiers])) {
_modifyContentCallbacks[pluginApiIdentifiers] = [];
}
@@ -29,9 +30,7 @@ function modifyContent(pluginApiIdentifiers, contentFunction) {
let _modifyHeaderComputedContentCallbacks = {};
function modifyHeaderComputedContent(pluginApiIdentifiers, contentFunction) {
- if (
- Ember.isNone(_modifyHeaderComputedContentCallbacks[pluginApiIdentifiers])
- ) {
+ if (isNone(_modifyHeaderComputedContentCallbacks[pluginApiIdentifiers])) {
_modifyHeaderComputedContentCallbacks[pluginApiIdentifiers] = [];
}
@@ -42,7 +41,7 @@ function modifyHeaderComputedContent(pluginApiIdentifiers, contentFunction) {
let _modifyCollectionHeaderCallbacks = {};
function modifyCollectionHeader(pluginApiIdentifiers, contentFunction) {
- if (Ember.isNone(_modifyCollectionHeaderCallbacks[pluginApiIdentifiers])) {
+ if (isNone(_modifyCollectionHeaderCallbacks[pluginApiIdentifiers])) {
_modifyCollectionHeaderCallbacks[pluginApiIdentifiers] = [];
}
@@ -51,7 +50,7 @@ function modifyCollectionHeader(pluginApiIdentifiers, contentFunction) {
let _onSelectNoneCallbacks = {};
function onSelectNone(pluginApiIdentifiers, mutationFunction) {
- if (Ember.isNone(_onSelectNoneCallbacks[pluginApiIdentifiers])) {
+ if (isNone(_onSelectNoneCallbacks[pluginApiIdentifiers])) {
_onSelectNoneCallbacks[pluginApiIdentifiers] = [];
}
@@ -60,7 +59,7 @@ function onSelectNone(pluginApiIdentifiers, mutationFunction) {
let _onSelectCallbacks = {};
function onSelect(pluginApiIdentifiers, mutationFunction) {
- if (Ember.isNone(_onSelectCallbacks[pluginApiIdentifiers])) {
+ if (isNone(_onSelectCallbacks[pluginApiIdentifiers])) {
_onSelectCallbacks[pluginApiIdentifiers] = [];
}
From 20266325fce0accd503aee0563c47adb31430c5d Mon Sep 17 00:00:00 2001
From: Mark VanLandingham
Date: Fri, 8 Nov 2019 13:03:22 -0600
Subject: [PATCH 070/408] combined import definitions in discourse-loader
---
app/assets/javascripts/discourse-loader.js | 6 ++----
1 file changed, 2 insertions(+), 4 deletions(-)
diff --git a/app/assets/javascripts/discourse-loader.js b/app/assets/javascripts/discourse-loader.js
index 5016efe395..876aca44ce 100644
--- a/app/assets/javascripts/discourse-loader.js
+++ b/app/assets/javascripts/discourse-loader.js
@@ -78,7 +78,8 @@ var define, requirejs;
inject: Ember.inject.service
},
"@ember/utils": {
- isEmpty: Ember.isEmpty
+ isEmpty: Ember.isEmpty,
+ isNone: Ember.isNone
},
rsvp: {
default: Ember.RSVP,
@@ -104,9 +105,6 @@ var define, requirejs;
},
"@ember/error": {
default: Ember.error
- },
- "@ember/utils": {
- isNone: Ember.isNone
}
};
}
From 544a1379b6ef2d72af545c0aee07b7d46111dd88 Mon Sep 17 00:00:00 2001
From: Simon Cossar
Date: Mon, 11 Nov 2019 11:03:57 -0500
Subject: [PATCH 071/408] Reference posts table for deleted_at and user_id
(#8332)
---
lib/tasks/import.rake | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/lib/tasks/import.rake b/lib/tasks/import.rake
index ca8fdc9486..d10eea7f03 100644
--- a/lib/tasks/import.rake
+++ b/lib/tasks/import.rake
@@ -391,8 +391,8 @@ def update_users
, MAX(p.created_at) max_created_at
FROM posts p
JOIN topics t ON t.id = p.topic_id AND t.archetype <> ?
- WHERE deleted_at IS NULL
- GROUP BY user_id
+ WHERE p.deleted_at IS NULL
+ GROUP BY p.user_id
)
UPDATE users
SET first_seen_at = X.min_created_at
From 6672dcc985a56a8b357a9fa3590311cecbcff75f Mon Sep 17 00:00:00 2001
From: Dan Ungureanu
Date: Mon, 11 Nov 2019 18:42:08 +0200
Subject: [PATCH 072/408] FIX: Keep emoji images in group bio excerpt (#8329)
---
app/serializers/basic_group_serializer.rb | 2 +-
spec/serializers/basic_group_serializer_spec.rb | 5 +++--
2 files changed, 4 insertions(+), 3 deletions(-)
diff --git a/app/serializers/basic_group_serializer.rb b/app/serializers/basic_group_serializer.rb
index d3c012194a..df250920d8 100644
--- a/app/serializers/basic_group_serializer.rb
+++ b/app/serializers/basic_group_serializer.rb
@@ -45,7 +45,7 @@ class BasicGroupSerializer < ApplicationSerializer
end
def bio_excerpt
- PrettyText.excerpt(object.bio_cooked, 110) if object.bio_cooked.present?
+ PrettyText.excerpt(object.bio_cooked, 110, keep_emoji_images: true) if object.bio_cooked.present?
end
def include_incoming_email?
diff --git a/spec/serializers/basic_group_serializer_spec.rb b/spec/serializers/basic_group_serializer_spec.rb
index 3dace7fcf4..b905f5d4a1 100644
--- a/spec/serializers/basic_group_serializer_spec.rb
+++ b/spec/serializers/basic_group_serializer_spec.rb
@@ -26,7 +26,7 @@ describe BasicGroupSerializer do
end
describe '#bio_raw' do
- fab!(:group) { Fabricate(:group, bio_raw: 'testing') }
+ fab!(:group) { Fabricate(:group, bio_raw: 'testing :slightly_smiling_face:') }
subject do
described_class.new(group, scope: guardian, root: false, owner_group_ids: [group.id])
@@ -34,7 +34,8 @@ describe BasicGroupSerializer do
describe 'group owner' do
it 'should include bio_raw' do
- expect(subject.as_json[:bio_raw]).to eq('testing')
+ expect(subject.as_json[:bio_raw]).to eq('testing :slightly_smiling_face:')
+ expect(subject.as_json[:bio_excerpt]).to start_with('testing
Date: Mon, 11 Nov 2019 18:42:45 +0200
Subject: [PATCH 073/408] FIX: Do not skip some emails in user search (#8317)
It used to skip the email addresses containing the plus sign.
---
app/assets/javascripts/discourse/lib/user-search.js.es6 | 2 +-
test/javascripts/lib/user-search-test.js.es6 | 3 +++
2 files changed, 4 insertions(+), 1 deletion(-)
diff --git a/app/assets/javascripts/discourse/lib/user-search.js.es6 b/app/assets/javascripts/discourse/lib/user-search.js.es6
index 63fbb2da71..b1a75ae34e 100644
--- a/app/assets/javascripts/discourse/lib/user-search.js.es6
+++ b/app/assets/javascripts/discourse/lib/user-search.js.es6
@@ -136,7 +136,7 @@ function organizeResults(r, options) {
// will not find me, which is a reasonable compromise
//
// we also ignore if we notice a double space or a string that is only a space
-const ignoreRegex = /([\u2000-\u206F\u2E00-\u2E7F\\'!"#$%&()*+,\/:;<=>?\[\]^`{|}~])|\s\s|^\s$/;
+const ignoreRegex = /([\u2000-\u206F\u2E00-\u2E7F\\'!"#$%&()*,\/:;<=>?\[\]^`{|}~])|\s\s|^\s$|^[^+]*\+[^@]*$/;
function skipSearch(term, allowEmails) {
if (term.indexOf("@") > -1 && !allowEmails) {
diff --git a/test/javascripts/lib/user-search-test.js.es6 b/test/javascripts/lib/user-search-test.js.es6
index 28a298c0fb..c93a87564d 100644
--- a/test/javascripts/lib/user-search-test.js.es6
+++ b/test/javascripts/lib/user-search-test.js.es6
@@ -169,6 +169,9 @@ QUnit.test("it skips a search depending on punctuations", async assert => {
// 6 + email
assert.equal(results.length, 7);
+ results = await userSearch({ term: "sam+test@sam.com", allowEmails: true });
+ assert.equal(results.length, 7);
+
results = await userSearch({ term: "sam@sam.com" });
assert.equal(results.length, 0);
From e79cec9fc72feac0b4585b187c5e85b20d6cbcee Mon Sep 17 00:00:00 2001
From: Daniel Waterworth
Date: Mon, 11 Nov 2019 13:18:10 +0000
Subject: [PATCH 074/408] DEV: Remove handling of category top menu items
Support for these kinds of navigation items was dropped in 88f52514, but
the code for handling these menu items was never removed.
---
.../discourse/models/nav-item.js.es6 | 62 +++++--------------
lib/discourse.rb | 4 +-
.../javascripts/fixtures/site-fixtures.js.es6 | 2 -
test/javascripts/helpers/site.js.es6 | 3 +-
test/javascripts/models/nav-item-test.js.es6 | 4 +-
5 files changed, 18 insertions(+), 57 deletions(-)
diff --git a/app/assets/javascripts/discourse/models/nav-item.js.es6 b/app/assets/javascripts/discourse/models/nav-item.js.es6
index f6c598d9df..ded21f1291 100644
--- a/app/assets/javascripts/discourse/models/nav-item.js.es6
+++ b/app/assets/javascripts/discourse/models/nav-item.js.es6
@@ -1,25 +1,19 @@
import discourseComputed from "discourse-common/utils/decorators";
-import { toTitleCase } from "discourse/lib/formatter";
import { emojiUnescape } from "discourse/lib/text";
import Category from "discourse/models/category";
import EmberObject from "@ember/object";
import deprecated from "discourse-common/lib/deprecated";
const NavItem = EmberObject.extend({
- @discourseComputed("categoryName", "name")
- title(categoryName, name) {
+ @discourseComputed("name")
+ title(name) {
const extra = {};
- if (categoryName) {
- name = "category";
- extra.categoryName = categoryName;
- }
-
return I18n.t("filters." + name.replace("/", ".") + ".help", extra);
},
- @discourseComputed("categoryName", "name", "count")
- displayName(categoryName, name, count) {
+ @discourseComputed("name", "count")
+ displayName(name, count) {
count = count || 0;
if (
@@ -32,35 +26,11 @@ const NavItem = EmberObject.extend({
let extra = { count: count };
const titleKey = count === 0 ? ".title" : ".title_with_count";
- if (categoryName) {
- name = "category";
- extra.categoryName = toTitleCase(categoryName);
- }
-
return emojiUnescape(
I18n.t(`filters.${name.replace("/", ".") + titleKey}`, extra)
);
},
- @discourseComputed("name")
- categoryName(name) {
- const split = name.split("/");
- return split[0] === "category" ? split[1] : null;
- },
-
- @discourseComputed("name")
- categorySlug(name) {
- const split = name.split("/");
- if (split[0] === "category" && split[1]) {
- const cat = Discourse.Site.current().categories.findBy(
- "nameLower",
- split[1].toLowerCase()
- );
- return cat ? Category.slugFor(cat) : null;
- }
- return null;
- },
-
@discourseComputed("filterMode")
href(filterMode) {
let customHref = null;
@@ -79,22 +49,18 @@ const NavItem = EmberObject.extend({
return Discourse.getURL("/") + filterMode;
},
- @discourseComputed("name", "category", "categorySlug", "noSubcategories")
- filterMode(name, category, categorySlug, noSubcategories) {
- if (name.split("/")[0] === "category") {
- return "c/" + categorySlug;
- } else {
- let mode = "";
- if (category) {
- mode += "c/";
- mode += Category.slugFor(category);
- if (noSubcategories) {
- mode += "/none";
- }
- mode += "/l/";
+ @discourseComputed("name", "category", "noSubcategories")
+ filterMode(name, category, noSubcategories) {
+ let mode = "";
+ if (category) {
+ mode += "c/";
+ mode += Category.slugFor(category);
+ if (noSubcategories) {
+ mode += "/none";
}
- return mode + name.replace(" ", "-");
+ mode += "/l/";
}
+ return mode + name.replace(" ", "-");
},
@discourseComputed("name", "category", "topicTrackingState.messageCount")
diff --git a/lib/discourse.rb b/lib/discourse.rb
index 8e8d7f9b5b..891bc01f07 100644
--- a/lib/discourse.rb
+++ b/lib/discourse.rb
@@ -160,11 +160,11 @@ module Discourse
end
def self.top_menu_items
- @top_menu_items ||= Discourse.filters + [:category, :categories, :top]
+ @top_menu_items ||= Discourse.filters + [:categories, :top]
end
def self.anonymous_top_menu_items
- @anonymous_top_menu_items ||= Discourse.anonymous_filters + [:category, :categories, :top]
+ @anonymous_top_menu_items ||= Discourse.anonymous_filters + [:categories, :top]
end
PIXEL_RATIOS ||= [1, 1.5, 2, 3]
diff --git a/test/javascripts/fixtures/site-fixtures.js.es6 b/test/javascripts/fixtures/site-fixtures.js.es6
index fc8934c1aa..875ef8f67e 100644
--- a/test/javascripts/fixtures/site-fixtures.js.es6
+++ b/test/javascripts/fixtures/site-fixtures.js.es6
@@ -41,7 +41,6 @@ export default {
"starred",
"read",
"posted",
- "category",
"categories",
"top"
],
@@ -49,7 +48,6 @@ export default {
"latest",
"top",
"categories",
- "category",
"categories",
"top"
],
diff --git a/test/javascripts/helpers/site.js.es6 b/test/javascripts/helpers/site.js.es6
index b8b713e979..7c4b2273dd 100644
--- a/test/javascripts/helpers/site.js.es6
+++ b/test/javascripts/helpers/site.js.es6
@@ -38,11 +38,10 @@ PreloadStore.store("site", {
"starred",
"read",
"posted",
- "category",
"categories",
"top"
],
- anonymous_top_menu_items: ["latest", "category", "categories", "top"],
+ anonymous_top_menu_items: ["latest", "categories", "top"],
uncategorized_category_id: 17,
categories: [
{
diff --git a/test/javascripts/models/nav-item-test.js.es6 b/test/javascripts/models/nav-item-test.js.es6
index 28f2eb9f5e..2d71715faf 100644
--- a/test/javascripts/models/nav-item-test.js.es6
+++ b/test/javascripts/models/nav-item-test.js.es6
@@ -16,7 +16,7 @@ QUnit.module("NavItem", {
});
QUnit.test("href", assert => {
- assert.expect(4);
+ assert.expect(2);
function href(text, expected, label) {
assert.equal(NavItem.fromText(text, {}).get("href"), expected, label);
@@ -24,8 +24,6 @@ QUnit.test("href", assert => {
href("latest", "/latest", "latest");
href("categories", "/categories", "categories");
- href("category/bug", "/c/bug", "English category name");
- href("category/确实是这样", "/c/343434-category", "Chinese category name");
});
QUnit.test("count", assert => {
From 4ddb69e9c6f4665d7b216076dad021ad4ffd510f Mon Sep 17 00:00:00 2001
From: Daniel Waterworth
Date: Mon, 11 Nov 2019 17:59:19 +0000
Subject: [PATCH 075/408] DEV: Removed needless indirection
An artifact of when tagging was a plugin no doubt.
---
.../discourse/controllers/tags-show.js.es6 | 11 -----------
.../javascripts/discourse/models/nav-item.js.es6 | 3 +++
2 files changed, 3 insertions(+), 11 deletions(-)
diff --git a/app/assets/javascripts/discourse/controllers/tags-show.js.es6 b/app/assets/javascripts/discourse/controllers/tags-show.js.es6
index 5f51ee9efb..5cc5b14523 100644
--- a/app/assets/javascripts/discourse/controllers/tags-show.js.es6
+++ b/app/assets/javascripts/discourse/controllers/tags-show.js.es6
@@ -8,21 +8,10 @@ import {
import BulkTopicSelection from "discourse/mixins/bulk-topic-selection";
import {
default as NavItem,
- extraNavItemProperties,
customNavItemHref
} from "discourse/models/nav-item";
import Category from "discourse/models/category";
-if (extraNavItemProperties) {
- extraNavItemProperties(function(text, opts) {
- if (opts && opts.tagId) {
- return { tagId: opts.tagId };
- } else {
- return {};
- }
- });
-}
-
if (customNavItemHref) {
customNavItemHref(function(navItem) {
if (navItem.get("tagId")) {
diff --git a/app/assets/javascripts/discourse/models/nav-item.js.es6 b/app/assets/javascripts/discourse/models/nav-item.js.es6
index ded21f1291..2193d816a8 100644
--- a/app/assets/javascripts/discourse/models/nav-item.js.es6
+++ b/app/assets/javascripts/discourse/models/nav-item.js.es6
@@ -122,6 +122,9 @@ NavItem.reopenClass({
if (opts.category) {
args.category = opts.category;
}
+ if (opts.tagId) {
+ args.tagId = opts.tagId;
+ }
if (opts.persistedQueryParams) {
args.persistedQueryParams = opts.persistedQueryParams;
}
From e8dae447bdb34df61b9fcebe8dc4b3695a5f0c3a Mon Sep 17 00:00:00 2001
From: Robin Ward
Date: Mon, 11 Nov 2019 13:19:59 -0500
Subject: [PATCH 076/408] REFACTOR: Remove `discourse/lib/throttle`
---
app/assets/javascripts/application.js | 1 -
.../javascripts/discourse/lib/throttle.js.es6 | 19 ---------------
.../discourse/models/composer.js.es6 | 23 +++++++++++--------
3 files changed, 13 insertions(+), 30 deletions(-)
delete mode 100644 app/assets/javascripts/discourse/lib/throttle.js.es6
diff --git a/app/assets/javascripts/application.js b/app/assets/javascripts/application.js
index 10c71ca89b..6dbb9e815c 100644
--- a/app/assets/javascripts/application.js
+++ b/app/assets/javascripts/application.js
@@ -26,7 +26,6 @@
//= require ./discourse/lib/lock-on
//= require ./discourse/lib/url
//= require ./discourse/lib/debounce
-//= require ./discourse/lib/throttle
//= require ./discourse/lib/quote
//= require ./discourse/lib/key-value-store
//= require ./discourse/lib/computed
diff --git a/app/assets/javascripts/discourse/lib/throttle.js.es6 b/app/assets/javascripts/discourse/lib/throttle.js.es6
deleted file mode 100644
index 05daa36c5a..0000000000
--- a/app/assets/javascripts/discourse/lib/throttle.js.es6
+++ /dev/null
@@ -1,19 +0,0 @@
-import { throttle } from "@ember/runloop";
-/**
- Throttle a Javascript function. This means if it's called many times in a time limit it
- should only be executed one time at most during this time limit
- Original function will be called with the context and arguments from the last call made.
-**/
-export default function(func, spacing, immediate) {
- let self, args;
- const later = function() {
- func.apply(self, args);
- };
-
- return function() {
- self = this;
- args = arguments;
-
- throttle(null, later, spacing, immediate);
- };
-}
diff --git a/app/assets/javascripts/discourse/models/composer.js.es6 b/app/assets/javascripts/discourse/models/composer.js.es6
index 60fb8272a6..afa1bf732c 100644
--- a/app/assets/javascripts/discourse/models/composer.js.es6
+++ b/app/assets/javascripts/discourse/models/composer.js.es6
@@ -16,7 +16,7 @@ import {
} from "discourse-common/utils/decorators";
import { escapeExpression, tinyAvatar } from "discourse/lib/utilities";
import { propertyNotEqual } from "discourse/lib/computed";
-import throttle from "discourse/lib/throttle";
+import { throttle } from "@ember/runloop";
import { Promise } from "rsvp";
import { set } from "@ember/object";
@@ -226,15 +226,18 @@ const Composer = RestModel.extend({
return this.set("metaData", EmberObject.create());
},
- // view detected user is typing
- typing: throttle(
- function() {
- const typingTime = this.typingTime || 0;
- this.set("typingTime", typingTime + 100);
- },
- 100,
- false
- ),
+ // called whenever the user types to update the typing time
+ typing() {
+ throttle(
+ this,
+ function() {
+ const typingTime = this.typingTime || 0;
+ this.set("typingTime", typingTime + 100);
+ },
+ 100,
+ false
+ );
+ },
editingFirstPost: and("editingPost", "post.firstPost"),
From da04c602ba162674afc6fe958d93b11784daec03 Mon Sep 17 00:00:00 2001
From: Robin Ward
Date: Mon, 11 Nov 2019 13:34:01 -0500
Subject: [PATCH 077/408] REFACTOR: Remove `debounce` to `discourseDebounce`
Otherwise it can be confused with the ember debounce
---
.../javascripts/admin/components/admin-backups-logs.js.es6 | 4 ++--
.../admin/controllers/admin-email-bounced.js.es6 | 4 ++--
.../admin/controllers/admin-email-received.js.es6 | 4 ++--
.../admin/controllers/admin-email-rejected.js.es6 | 4 ++--
.../javascripts/admin/controllers/admin-email-sent.js.es6 | 4 ++--
.../admin/controllers/admin-email-skipped.js.es6 | 4 ++--
.../controllers/admin-logs-screened-ip-addresses.js.es6 | 4 ++--
.../javascripts/admin/controllers/admin-permalinks.js.es6 | 4 ++--
.../admin/controllers/admin-site-settings.js.es6 | 4 ++--
.../admin/controllers/admin-users-list-show.js.es6 | 4 ++--
.../admin/controllers/admin-watched-words.js.es6 | 4 ++--
.../javascripts/discourse/components/choose-message.js.es6 | 4 ++--
.../javascripts/discourse/components/choose-topic.js.es6 | 4 ++--
.../discourse/components/groups-form-profile-fields.js.es6 | 4 ++--
.../javascripts/discourse/components/quote-button.js.es6 | 7 +++++--
.../javascripts/discourse/controllers/group-index.js.es6 | 4 ++--
.../discourse/controllers/group-requests.js.es6 | 4 ++--
.../javascripts/discourse/controllers/groups-index.js.es6 | 4 ++--
app/assets/javascripts/discourse/controllers/topic.js.es6 | 4 ++--
.../discourse/controllers/user-invited-show.js.es6 | 4 ++--
app/assets/javascripts/discourse/controllers/users.js.es6 | 4 ++--
.../javascripts/discourse/lib/category-tag-search.js.es6 | 4 ++--
app/assets/javascripts/discourse/lib/safari-hacks.js.es6 | 6 +++---
app/assets/javascripts/discourse/lib/user-search.js.es6 | 4 ++--
app/assets/javascripts/discourse/mixins/scrolling.js.es6 | 4 ++--
.../discourse/mixins/username-validation.js.es6 | 6 +++---
.../components/discourse-local-dates-create-form.js.es6 | 4 ++--
27 files changed, 59 insertions(+), 56 deletions(-)
diff --git a/app/assets/javascripts/admin/components/admin-backups-logs.js.es6 b/app/assets/javascripts/admin/components/admin-backups-logs.js.es6
index 72706af79f..316597e0f7 100644
--- a/app/assets/javascripts/admin/components/admin-backups-logs.js.es6
+++ b/app/assets/javascripts/admin/components/admin-backups-logs.js.es6
@@ -1,6 +1,6 @@
import { scheduleOnce } from "@ember/runloop";
import Component from "@ember/component";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
import { renderSpinner } from "discourse/helpers/loading-spinner";
import { escapeExpression } from "discourse/lib/utilities";
import { bufferedRender } from "discourse-common/lib/buffered-render";
@@ -35,7 +35,7 @@ export default Component.extend(
@on("init")
@observes("logs.[]")
- _updateFormattedLogs: debounce(function() {
+ _updateFormattedLogs: discourseDebounce(function() {
const logs = this.logs;
if (logs.length === 0) return;
diff --git a/app/assets/javascripts/admin/controllers/admin-email-bounced.js.es6 b/app/assets/javascripts/admin/controllers/admin-email-bounced.js.es6
index 535fa4bca1..17cb8ed04f 100644
--- a/app/assets/javascripts/admin/controllers/admin-email-bounced.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-email-bounced.js.es6
@@ -1,8 +1,8 @@
import AdminEmailLogsController from "admin/controllers/admin-email-logs";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
export default AdminEmailLogsController.extend({
- filterEmailLogs: debounce(function() {
+ filterEmailLogs: discourseDebounce(function() {
this.loadLogs();
}, 250).observes("filter.{status,user,address,type}")
});
diff --git a/app/assets/javascripts/admin/controllers/admin-email-received.js.es6 b/app/assets/javascripts/admin/controllers/admin-email-received.js.es6
index 7659e61edd..7dc733e00c 100644
--- a/app/assets/javascripts/admin/controllers/admin-email-received.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-email-received.js.es6
@@ -1,9 +1,9 @@
import AdminEmailLogsController from "admin/controllers/admin-email-logs";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
import IncomingEmail from "admin/models/incoming-email";
export default AdminEmailLogsController.extend({
- filterIncomingEmails: debounce(function() {
+ filterIncomingEmails: discourseDebounce(function() {
this.loadLogs(IncomingEmail);
}, 250).observes("filter.{status,from,to,subject}"),
diff --git a/app/assets/javascripts/admin/controllers/admin-email-rejected.js.es6 b/app/assets/javascripts/admin/controllers/admin-email-rejected.js.es6
index 602bb052ce..d70efb23ce 100644
--- a/app/assets/javascripts/admin/controllers/admin-email-rejected.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-email-rejected.js.es6
@@ -1,9 +1,9 @@
import AdminEmailLogsController from "admin/controllers/admin-email-logs";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
import IncomingEmail from "admin/models/incoming-email";
export default AdminEmailLogsController.extend({
- filterIncomingEmails: debounce(function() {
+ filterIncomingEmails: discourseDebounce(function() {
this.loadLogs(IncomingEmail);
}, 250).observes("filter.{status,from,to,subject,error}"),
diff --git a/app/assets/javascripts/admin/controllers/admin-email-sent.js.es6 b/app/assets/javascripts/admin/controllers/admin-email-sent.js.es6
index 83f52d3510..c7ddaa0043 100644
--- a/app/assets/javascripts/admin/controllers/admin-email-sent.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-email-sent.js.es6
@@ -1,8 +1,8 @@
import AdminEmailLogsController from "admin/controllers/admin-email-logs";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
export default AdminEmailLogsController.extend({
- filterEmailLogs: debounce(function() {
+ filterEmailLogs: discourseDebounce(function() {
this.loadLogs();
}, 250).observes("filter.{status,user,address,type,reply_key}")
});
diff --git a/app/assets/javascripts/admin/controllers/admin-email-skipped.js.es6 b/app/assets/javascripts/admin/controllers/admin-email-skipped.js.es6
index 535fa4bca1..17cb8ed04f 100644
--- a/app/assets/javascripts/admin/controllers/admin-email-skipped.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-email-skipped.js.es6
@@ -1,8 +1,8 @@
import AdminEmailLogsController from "admin/controllers/admin-email-logs";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
export default AdminEmailLogsController.extend({
- filterEmailLogs: debounce(function() {
+ filterEmailLogs: discourseDebounce(function() {
this.loadLogs();
}, 250).observes("filter.{status,user,address,type}")
});
diff --git a/app/assets/javascripts/admin/controllers/admin-logs-screened-ip-addresses.js.es6 b/app/assets/javascripts/admin/controllers/admin-logs-screened-ip-addresses.js.es6
index 2e404eb29d..e5da638f9a 100644
--- a/app/assets/javascripts/admin/controllers/admin-logs-screened-ip-addresses.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-logs-screened-ip-addresses.js.es6
@@ -1,5 +1,5 @@
import Controller from "@ember/controller";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
import { outputExportResult } from "discourse/lib/export-result";
import { exportEntity } from "discourse/lib/export-csv";
import ScreenedIpAddress from "admin/models/screened-ip-address";
@@ -9,7 +9,7 @@ export default Controller.extend({
filter: null,
savedIpAddress: null,
- show: debounce(function() {
+ show: discourseDebounce(function() {
this.set("loading", true);
ScreenedIpAddress.findAll(this.filter).then(result => {
this.setProperties({ model: result, loading: false });
diff --git a/app/assets/javascripts/admin/controllers/admin-permalinks.js.es6 b/app/assets/javascripts/admin/controllers/admin-permalinks.js.es6
index d024c83051..29c076c30c 100644
--- a/app/assets/javascripts/admin/controllers/admin-permalinks.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-permalinks.js.es6
@@ -1,12 +1,12 @@
import Controller from "@ember/controller";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
import Permalink from "admin/models/permalink";
export default Controller.extend({
loading: false,
filter: null,
- show: debounce(function() {
+ show: discourseDebounce(function() {
Permalink.findAll(this.filter).then(result => {
this.set("model", result);
this.set("loading", false);
diff --git a/app/assets/javascripts/admin/controllers/admin-site-settings.js.es6 b/app/assets/javascripts/admin/controllers/admin-site-settings.js.es6
index fe35885617..052f7c567d 100644
--- a/app/assets/javascripts/admin/controllers/admin-site-settings.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-site-settings.js.es6
@@ -1,7 +1,7 @@
import { isEmpty } from "@ember/utils";
import { alias } from "@ember/object/computed";
import Controller from "@ember/controller";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
export default Controller.extend({
filter: null,
@@ -76,7 +76,7 @@ export default Controller.extend({
);
},
- filterContent: debounce(function() {
+ filterContent: discourseDebounce(function() {
if (this._skipBounce) {
this.set("_skipBounce", false);
} else {
diff --git a/app/assets/javascripts/admin/controllers/admin-users-list-show.js.es6 b/app/assets/javascripts/admin/controllers/admin-users-list-show.js.es6
index 87380235e3..12d4724862 100644
--- a/app/assets/javascripts/admin/controllers/admin-users-list-show.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-users-list-show.js.es6
@@ -1,6 +1,6 @@
import discourseComputed from "discourse-common/utils/decorators";
import Controller from "@ember/controller";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
import { i18n } from "discourse/lib/computed";
import AdminUser from "admin/models/admin-user";
import CanCheckEmails from "discourse/mixins/can-check-emails";
@@ -29,7 +29,7 @@ export default Controller.extend(CanCheckEmails, {
return I18n.t("admin.users.titles." + query);
},
- _filterUsers: debounce(function() {
+ _filterUsers: discourseDebounce(function() {
this.resetFilters();
}, 250).observes("listFilter"),
diff --git a/app/assets/javascripts/admin/controllers/admin-watched-words.js.es6 b/app/assets/javascripts/admin/controllers/admin-watched-words.js.es6
index 397c5b030e..84a7ac7939 100644
--- a/app/assets/javascripts/admin/controllers/admin-watched-words.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-watched-words.js.es6
@@ -2,7 +2,7 @@ import { isEmpty } from "@ember/utils";
import { alias } from "@ember/object/computed";
import EmberObject from "@ember/object";
import Controller from "@ember/controller";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
export default Controller.extend({
filter: null,
@@ -43,7 +43,7 @@ export default Controller.extend({
this.set("model", matchesByAction);
},
- filterContent: debounce(function() {
+ filterContent: discourseDebounce(function() {
this.filterContentNow();
this.set("filtered", !isEmpty(this.filter));
}, 250).observes("filter"),
diff --git a/app/assets/javascripts/discourse/components/choose-message.js.es6 b/app/assets/javascripts/discourse/components/choose-message.js.es6
index e47618dbef..c5680dfaf9 100644
--- a/app/assets/javascripts/discourse/components/choose-message.js.es6
+++ b/app/assets/javascripts/discourse/components/choose-message.js.es6
@@ -2,7 +2,7 @@ import { get } from "@ember/object";
import { isEmpty } from "@ember/utils";
import { next } from "@ember/runloop";
import Component from "@ember/component";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
import { searchForTerm } from "discourse/lib/search";
import { observes } from "discourse-common/utils/decorators";
@@ -30,7 +30,7 @@ export default Component.extend({
this.set("loading", false);
},
- search: debounce(function(title) {
+ search: discourseDebounce(function(title) {
const currentTopicId = this.currentTopicId;
if (isEmpty(title)) {
diff --git a/app/assets/javascripts/discourse/components/choose-topic.js.es6 b/app/assets/javascripts/discourse/components/choose-topic.js.es6
index 557b30d9a0..51955db565 100644
--- a/app/assets/javascripts/discourse/components/choose-topic.js.es6
+++ b/app/assets/javascripts/discourse/components/choose-topic.js.es6
@@ -1,7 +1,7 @@
import { isEmpty } from "@ember/utils";
import { next } from "@ember/runloop";
import Component from "@ember/component";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
import { searchForTerm } from "discourse/lib/search";
import { observes } from "discourse-common/utils/decorators";
@@ -33,7 +33,7 @@ export default Component.extend({
this.set("loading", false);
},
- search: debounce(function(title) {
+ search: discourseDebounce(function(title) {
if (!this.element || this.isDestroying || this.isDestroyed) {
return;
}
diff --git a/app/assets/javascripts/discourse/components/groups-form-profile-fields.js.es6 b/app/assets/javascripts/discourse/components/groups-form-profile-fields.js.es6
index 082cfcc584..03ea2d8e14 100644
--- a/app/assets/javascripts/discourse/components/groups-form-profile-fields.js.es6
+++ b/app/assets/javascripts/discourse/components/groups-form-profile-fields.js.es6
@@ -7,7 +7,7 @@ import {
} from "discourse-common/utils/decorators";
import Group from "discourse/models/group";
import InputValidation from "discourse/models/input-validation";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
export default Component.extend({
disableSave: null,
@@ -64,7 +64,7 @@ export default Component.extend({
);
},
- checkGroupName: debounce(function() {
+ checkGroupName: discourseDebounce(function() {
name = this.nameInput;
if (isEmpty(name)) return;
diff --git a/app/assets/javascripts/discourse/components/quote-button.js.es6 b/app/assets/javascripts/discourse/components/quote-button.js.es6
index ec8b8c47e8..718f68c98a 100644
--- a/app/assets/javascripts/discourse/components/quote-button.js.es6
+++ b/app/assets/javascripts/discourse/components/quote-button.js.es6
@@ -1,6 +1,6 @@
import { scheduleOnce } from "@ember/runloop";
import Component from "@ember/component";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
import { selectedText } from "discourse/lib/utilities";
export default Component.extend({
@@ -128,7 +128,10 @@ export default Component.extend({
didInsertElement() {
const { isWinphone, isAndroid } = this.capabilities;
const wait = isWinphone || isAndroid ? 250 : 25;
- const onSelectionChanged = debounce(() => this._selectionChanged(), wait);
+ const onSelectionChanged = discourseDebounce(
+ () => this._selectionChanged(),
+ wait
+ );
$(document)
.on("mousedown.quote-button", e => {
diff --git a/app/assets/javascripts/discourse/controllers/group-index.js.es6 b/app/assets/javascripts/discourse/controllers/group-index.js.es6
index 05df6fa12e..ce6abcc484 100644
--- a/app/assets/javascripts/discourse/controllers/group-index.js.es6
+++ b/app/assets/javascripts/discourse/controllers/group-index.js.es6
@@ -7,7 +7,7 @@ import {
default as discourseComputed,
observes
} from "discourse-common/utils/decorators";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
export default Controller.extend({
queryParams: ["order", "desc", "filter"],
@@ -23,7 +23,7 @@ export default Controller.extend({
application: inject(),
@observes("filterInput")
- _setFilter: debounce(function() {
+ _setFilter: discourseDebounce(function() {
this.set("filter", this.filterInput);
}, 500),
diff --git a/app/assets/javascripts/discourse/controllers/group-requests.js.es6 b/app/assets/javascripts/discourse/controllers/group-requests.js.es6
index 5be58b2d60..75275a9462 100644
--- a/app/assets/javascripts/discourse/controllers/group-requests.js.es6
+++ b/app/assets/javascripts/discourse/controllers/group-requests.js.es6
@@ -7,7 +7,7 @@ import {
default as discourseComputed,
observes
} from "discourse-common/utils/decorators";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
export default Controller.extend({
queryParams: ["order", "desc", "filter"],
@@ -21,7 +21,7 @@ export default Controller.extend({
application: inject(),
@observes("filterInput")
- _setFilter: debounce(function() {
+ _setFilter: discourseDebounce(function() {
this.set("filter", this.filterInput);
}, 500),
diff --git a/app/assets/javascripts/discourse/controllers/groups-index.js.es6 b/app/assets/javascripts/discourse/controllers/groups-index.js.es6
index 9758b30ad5..0380bdffd8 100644
--- a/app/assets/javascripts/discourse/controllers/groups-index.js.es6
+++ b/app/assets/javascripts/discourse/controllers/groups-index.js.es6
@@ -1,6 +1,6 @@
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
import {
default as discourseComputed,
observes
@@ -28,7 +28,7 @@ export default Controller.extend({
},
@observes("filterInput")
- _setFilter: debounce(function() {
+ _setFilter: discourseDebounce(function() {
this.set("filter", this.filterInput);
}, 500),
diff --git a/app/assets/javascripts/discourse/controllers/topic.js.es6 b/app/assets/javascripts/discourse/controllers/topic.js.es6
index 1a67f6e0ed..d273e51153 100644
--- a/app/assets/javascripts/discourse/controllers/topic.js.es6
+++ b/app/assets/javascripts/discourse/controllers/topic.js.es6
@@ -12,7 +12,7 @@ import Post from "discourse/models/post";
import Quote from "discourse/lib/quote";
import QuoteState from "discourse/lib/quote-state";
import Topic from "discourse/models/topic";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
import isElementInViewport from "discourse/lib/is-element-in-viewport";
import { ajax } from "discourse/lib/ajax";
import {
@@ -1399,7 +1399,7 @@ export default Controller.extend(bufferedProperty("model"), {
);
},
- _scrollToPost: debounce(function(postNumber) {
+ _scrollToPost: discourseDebounce(function(postNumber) {
const $post = $(`.topic-post article#post_${postNumber}`);
if ($post.length === 0 || isElementInViewport($post)) return;
diff --git a/app/assets/javascripts/discourse/controllers/user-invited-show.js.es6 b/app/assets/javascripts/discourse/controllers/user-invited-show.js.es6
index 59d197a875..eabab5a749 100644
--- a/app/assets/javascripts/discourse/controllers/user-invited-show.js.es6
+++ b/app/assets/javascripts/discourse/controllers/user-invited-show.js.es6
@@ -1,7 +1,7 @@
import { equal, reads, gte } from "@ember/object/computed";
import Controller from "@ember/controller";
import Invite from "discourse/models/invite";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
import { popupAjaxError } from "discourse/lib/ajax-error";
import {
default as discourseComputed,
@@ -27,7 +27,7 @@ export default Controller.extend({
},
@observes("searchTerm")
- _searchTermChanged: debounce(function() {
+ _searchTermChanged: discourseDebounce(function() {
Invite.findInvitedBy(this.user, this.filter, this.searchTerm).then(
invites => this.set("model", invites)
);
diff --git a/app/assets/javascripts/discourse/controllers/users.js.es6 b/app/assets/javascripts/discourse/controllers/users.js.es6
index 36e3236ffd..8fd3b3e157 100644
--- a/app/assets/javascripts/discourse/controllers/users.js.es6
+++ b/app/assets/javascripts/discourse/controllers/users.js.es6
@@ -1,7 +1,7 @@
import { equal } from "@ember/object/computed";
import { inject } from "@ember/controller";
import Controller from "@ember/controller";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
export default Controller.extend({
application: inject(),
@@ -15,7 +15,7 @@ export default Controller.extend({
showTimeRead: equal("period", "all"),
- _setName: debounce(function() {
+ _setName: discourseDebounce(function() {
this.set("name", this.nameInput);
}, 500).observes("nameInput"),
diff --git a/app/assets/javascripts/discourse/lib/category-tag-search.js.es6 b/app/assets/javascripts/discourse/lib/category-tag-search.js.es6
index 0b46e05b73..ca1ddcc85e 100644
--- a/app/assets/javascripts/discourse/lib/category-tag-search.js.es6
+++ b/app/assets/javascripts/discourse/lib/category-tag-search.js.es6
@@ -1,4 +1,4 @@
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
import { CANCELLED_STATUS } from "discourse/lib/autocomplete";
import Category from "discourse/models/category";
import { TAG_HASHTAG_POSTFIX } from "discourse/lib/tag-hashtags";
@@ -21,7 +21,7 @@ function searchTags(term, categories, limit) {
resolve(CANCELLED_STATUS);
}, 5000);
- const debouncedSearch = debounce((q, cats, resultFunc) => {
+ const debouncedSearch = discourseDebounce((q, cats, resultFunc) => {
oldSearch = $.ajax(Discourse.getURL("/tags/filter/search"), {
type: "GET",
cache: true,
diff --git a/app/assets/javascripts/discourse/lib/safari-hacks.js.es6 b/app/assets/javascripts/discourse/lib/safari-hacks.js.es6
index afb55f7f8b..9241cbbed7 100644
--- a/app/assets/javascripts/discourse/lib/safari-hacks.js.es6
+++ b/app/assets/javascripts/discourse/lib/safari-hacks.js.es6
@@ -1,5 +1,5 @@
import { later } from "@ember/runloop";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
import {
safariHacksDisabled,
iOSWithVisualViewport
@@ -132,7 +132,7 @@ function positioningWorkaround($fixedElement) {
positioningWorkaround.blur(evt);
};
- var blurred = debounce(blurredNow, 250);
+ var blurred = discourseDebounce(blurredNow, 250);
var positioningHack = function(evt) {
// we need this, otherwise changing focus means we never clear
@@ -217,7 +217,7 @@ function positioningWorkaround($fixedElement) {
}
}
- const checkForInputs = debounce(function() {
+ const checkForInputs = discourseDebounce(function() {
attachTouchStart(fixedElement, lastTouched);
$fixedElement.find("input[type=text],textarea").each(function() {
diff --git a/app/assets/javascripts/discourse/lib/user-search.js.es6 b/app/assets/javascripts/discourse/lib/user-search.js.es6
index b1a75ae34e..2a5890aa3f 100644
--- a/app/assets/javascripts/discourse/lib/user-search.js.es6
+++ b/app/assets/javascripts/discourse/lib/user-search.js.es6
@@ -1,4 +1,4 @@
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
import { CANCELLED_STATUS } from "discourse/lib/autocomplete";
import { userPath } from "discourse/lib/url";
import { emailValid } from "discourse/lib/utilities";
@@ -79,7 +79,7 @@ function performSearch(
});
}
-var debouncedSearch = debounce(performSearch, 300);
+var debouncedSearch = discourseDebounce(performSearch, 300);
function organizeResults(r, options) {
if (r === CANCELLED_STATUS) {
diff --git a/app/assets/javascripts/discourse/mixins/scrolling.js.es6 b/app/assets/javascripts/discourse/mixins/scrolling.js.es6
index b690c77de4..2a15df47eb 100644
--- a/app/assets/javascripts/discourse/mixins/scrolling.js.es6
+++ b/app/assets/javascripts/discourse/mixins/scrolling.js.es6
@@ -1,5 +1,5 @@
import { scheduleOnce } from "@ember/runloop";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
import Mixin from "@ember/object/mixin";
/**
@@ -43,7 +43,7 @@ const Scrolling = Mixin.create({
};
if (opts.debounce) {
- onScrollMethod = debounce(onScrollMethod, opts.debounce);
+ onScrollMethod = discourseDebounce(onScrollMethod, opts.debounce);
}
ScrollingDOMMethods.bindOnScroll(onScrollMethod, opts.name);
diff --git a/app/assets/javascripts/discourse/mixins/username-validation.js.es6 b/app/assets/javascripts/discourse/mixins/username-validation.js.es6
index 35ccf6c8cc..31186525f1 100644
--- a/app/assets/javascripts/discourse/mixins/username-validation.js.es6
+++ b/app/assets/javascripts/discourse/mixins/username-validation.js.es6
@@ -1,6 +1,6 @@
import { isEmpty } from "@ember/utils";
import InputValidation from "discourse/models/input-validation";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
import { setting } from "discourse/lib/computed";
import { default as discourseComputed } from "discourse-common/utils/decorators";
import Mixin from "@ember/object/mixin";
@@ -12,7 +12,7 @@ export default Mixin.create({
minUsernameLength: setting("min_username_length"),
- fetchExistingUsername: debounce(function() {
+ fetchExistingUsername: discourseDebounce(function() {
Discourse.User.checkUsername(null, this.accountEmail).then(result => {
if (
result.suggestion &&
@@ -74,7 +74,7 @@ export default Mixin.create({
);
},
- checkUsernameAvailability: debounce(function() {
+ checkUsernameAvailability: discourseDebounce(function() {
if (this.shouldCheckUsernameAvailability()) {
return Discourse.User.checkUsername(
this.accountUsername,
diff --git a/plugins/discourse-local-dates/assets/javascripts/discourse/components/discourse-local-dates-create-form.js.es6 b/plugins/discourse-local-dates/assets/javascripts/discourse/components/discourse-local-dates-create-form.js.es6
index de01b5ef9c..20b104c0a3 100644
--- a/plugins/discourse-local-dates/assets/javascripts/discourse/components/discourse-local-dates-create-form.js.es6
+++ b/plugins/discourse-local-dates/assets/javascripts/discourse/components/discourse-local-dates-create-form.js.es6
@@ -6,7 +6,7 @@ import { propertyNotEqual } from "discourse/lib/computed";
import loadScript from "discourse/lib/load-script";
import { default as computed } from "ember-addons/ember-computed-decorators";
import { cookAsync } from "discourse/lib/text";
-import debounce from "discourse/lib/debounce";
+import discourseDebounce from "discourse/lib/debounce";
export default Component.extend({
timeFormat: "HH:mm:ss",
@@ -51,7 +51,7 @@ export default Component.extend({
});
},
- _renderPreview: debounce(function() {
+ _renderPreview: discourseDebounce(function() {
const markup = this.markup;
if (markup) {
From 211410c3b9ee78e6654f07d5c9e822089ba268bc Mon Sep 17 00:00:00 2001
From: Daniel Waterworth
Date: Mon, 11 Nov 2019 18:32:22 +0000
Subject: [PATCH 078/408] DEV: It doesn't make sense for a filterMode to be
weekly, quarterly, etc
---
app/assets/javascripts/discourse/components/d-navigation.js.es6 | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/app/assets/javascripts/discourse/components/d-navigation.js.es6 b/app/assets/javascripts/discourse/components/d-navigation.js.es6
index 9ceea60eb4..b68ceeb739 100644
--- a/app/assets/javascripts/discourse/components/d-navigation.js.es6
+++ b/app/assets/javascripts/discourse/components/d-navigation.js.es6
@@ -31,7 +31,7 @@ export default Component.extend({
navItems(filterMode, category, noSubcategories) {
// we don't want to show the period in the navigation bar since it's in a dropdown
if (filterMode.indexOf("top/") === 0) {
- filterMode = filterMode.replace("top/", "");
+ filterMode = "top";
}
let params;
From e39d89ecd9119f69f464d92a16d59d77cc746081 Mon Sep 17 00:00:00 2001
From: Robin Ward
Date: Mon, 11 Nov 2019 15:48:33 -0500
Subject: [PATCH 079/408] REFACTOR: Remove `InputValidation` which was simply
an `Ember.Object`
---
.../controllers/admin-web-hooks-show.js.es6 | 8 ++++----
app/assets/javascripts/application.js | 1 -
app/assets/javascripts/discourse-loader.js | 9 +++++++++
.../components/composer-editor.js.es6 | 4 ++--
.../discourse/components/composer-title.js.es6 | 4 ++--
.../groups-form-profile-fields.js.es6 | 6 +++---
.../discourse/controllers/composer.js.es6 | 6 +++---
.../controllers/create-account.js.es6 | 12 ++++++------
.../discourse/controllers/feature-topic.js.es6 | 6 +++---
.../controllers/preferences/email.js.es6 | 4 ++--
.../discourse/mixins/name-validation.js.es6 | 6 +++---
.../mixins/password-validation.js.es6 | 16 ++++++++--------
.../mixins/user-fields-validation.js.es6 | 5 ++---
.../mixins/username-validation.js.es6 | 18 +++++++++---------
.../discourse/models/input-validation.js.es6 | 2 --
.../controllers/poll-ui-builder.js.es6 | 8 ++++----
16 files changed, 60 insertions(+), 55 deletions(-)
delete mode 100644 app/assets/javascripts/discourse/models/input-validation.js.es6
diff --git a/app/assets/javascripts/admin/controllers/admin-web-hooks-show.js.es6 b/app/assets/javascripts/admin/controllers/admin-web-hooks-show.js.es6
index b07806f6fa..4ba34034f3 100644
--- a/app/assets/javascripts/admin/controllers/admin-web-hooks-show.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-web-hooks-show.js.es6
@@ -5,7 +5,7 @@ import { inject } from "@ember/controller";
import Controller from "@ember/controller";
import { popupAjaxError } from "discourse/lib/ajax-error";
import { extractDomainFromUrl } from "discourse/lib/utilities";
-import InputValidation from "discourse/models/input-validation";
+import EmberObject from "@ember/object";
export default Controller.extend({
adminWebHooks: inject(),
@@ -41,14 +41,14 @@ export default Controller.extend({
secretValidation(secret) {
if (!isEmpty(secret)) {
if (secret.indexOf(" ") !== -1) {
- return InputValidation.create({
+ return EmberObject.create({
failed: true,
reason: I18n.t("admin.web_hooks.secret_invalid")
});
}
if (secret.length < 12) {
- return InputValidation.create({
+ return EmberObject.create({
failed: true,
reason: I18n.t("admin.web_hooks.secret_too_short")
});
@@ -59,7 +59,7 @@ export default Controller.extend({
@discourseComputed("model.wildcard_web_hook", "model.web_hook_event_types.[]")
eventTypeValidation(isWildcard, eventTypes) {
if (!isWildcard && isEmpty(eventTypes)) {
- return InputValidation.create({
+ return EmberObject.create({
failed: true,
reason: I18n.t("admin.web_hooks.event_type_missing")
});
diff --git a/app/assets/javascripts/application.js b/app/assets/javascripts/application.js
index 6dbb9e815c..35cc29acce 100644
--- a/app/assets/javascripts/application.js
+++ b/app/assets/javascripts/application.js
@@ -47,7 +47,6 @@
//= require ./discourse/models/badge
//= require ./discourse/models/permission-type
//= require ./discourse/models/user-action-group
-//= require ./discourse/models/input-validation
//= require ./discourse/models/trust-level
//= require ./discourse/lib/search
//= require ./discourse/lib/user-search
diff --git a/app/assets/javascripts/discourse-loader.js b/app/assets/javascripts/discourse-loader.js
index 876aca44ce..d5112d026e 100644
--- a/app/assets/javascripts/discourse-loader.js
+++ b/app/assets/javascripts/discourse-loader.js
@@ -220,6 +220,15 @@ var define, requirejs;
function requireFrom(name, origin) {
name = transformForAliases(name);
+
+ if (name === "discourse/models/input-validation") {
+ // eslint-disable-next-line no-console
+ console.log(
+ "input-validation has been removed and should be replaced with `@ember/object`"
+ );
+ return Ember.Object;
+ }
+
var mod = EMBER_MODULES[name] || registry[name];
if (!mod) {
throw new Error(
diff --git a/app/assets/javascripts/discourse/components/composer-editor.js.es6 b/app/assets/javascripts/discourse/components/composer-editor.js.es6
index 75f8edd4f0..d997c3f4f6 100644
--- a/app/assets/javascripts/discourse/components/composer-editor.js.es6
+++ b/app/assets/javascripts/discourse/components/composer-editor.js.es6
@@ -26,7 +26,7 @@ import Composer from "discourse/models/composer";
import { load, LOADING_ONEBOX_CSS_CLASS } from "pretty-text/oneboxer";
import { applyInlineOneboxes } from "pretty-text/inline-oneboxer";
import { ajax } from "discourse/lib/ajax";
-import InputValidation from "discourse/models/input-validation";
+import EmberObject from "@ember/object";
import { findRawTemplate } from "discourse/lib/raw-templates";
import { iconHTML } from "discourse-common/lib/icon-library";
import {
@@ -246,7 +246,7 @@ export default Component.extend({
}
if (reason) {
- return InputValidation.create({
+ return EmberObject.create({
failed: true,
reason,
lastShownAt: lastValidatedAt
diff --git a/app/assets/javascripts/discourse/components/composer-title.js.es6 b/app/assets/javascripts/discourse/components/composer-title.js.es6
index da012442f7..2eb06cb071 100644
--- a/app/assets/javascripts/discourse/components/composer-title.js.es6
+++ b/app/assets/javascripts/discourse/components/composer-title.js.es6
@@ -7,12 +7,12 @@ import {
default as discourseComputed,
observes
} from "discourse-common/utils/decorators";
-import InputValidation from "discourse/models/input-validation";
import { load } from "pretty-text/oneboxer";
import { lookupCache } from "pretty-text/oneboxer-cache";
import { ajax } from "discourse/lib/ajax";
import afterTransition from "discourse/lib/after-transition";
import ENV from "discourse-common/config/environment";
+import EmberObject from "@ember/object";
export default Component.extend({
classNames: ["title-input"],
@@ -60,7 +60,7 @@ export default Component.extend({
}
if (reason) {
- return InputValidation.create({
+ return EmberObject.create({
failed: true,
reason,
lastShownAt: lastValidatedAt
diff --git a/app/assets/javascripts/discourse/components/groups-form-profile-fields.js.es6 b/app/assets/javascripts/discourse/components/groups-form-profile-fields.js.es6
index 03ea2d8e14..9074ef2d63 100644
--- a/app/assets/javascripts/discourse/components/groups-form-profile-fields.js.es6
+++ b/app/assets/javascripts/discourse/components/groups-form-profile-fields.js.es6
@@ -6,8 +6,8 @@ import {
observes
} from "discourse-common/utils/decorators";
import Group from "discourse/models/group";
-import InputValidation from "discourse/models/input-validation";
import discourseDebounce from "discourse/lib/debounce";
+import EmberObject from "@ember/object";
export default Component.extend({
disableSave: null,
@@ -74,7 +74,7 @@ export default Component.extend({
if (response.available) {
this.set(
validationName,
- InputValidation.create({
+ EmberObject.create({
ok: true,
reason: I18n.t("admin.groups.new.name.available")
})
@@ -101,6 +101,6 @@ export default Component.extend({
const options = { failed: true };
if (reason) options.reason = reason;
- this.set("basicNameValidation", InputValidation.create(options));
+ this.set("basicNameValidation", EmberObject.create(options));
}
});
diff --git a/app/assets/javascripts/discourse/controllers/composer.js.es6 b/app/assets/javascripts/discourse/controllers/composer.js.es6
index 51d4b3202e..e3d5ae3c0d 100644
--- a/app/assets/javascripts/discourse/controllers/composer.js.es6
+++ b/app/assets/javascripts/discourse/controllers/composer.js.es6
@@ -19,7 +19,6 @@ import {
observes,
on
} from "discourse-common/utils/decorators";
-import InputValidation from "discourse/models/input-validation";
import { getOwner } from "discourse-common/lib/get-owner";
import {
escapeExpression,
@@ -32,6 +31,7 @@ import { shortDate } from "discourse/lib/formatter";
import { SAVE_LABELS, SAVE_ICONS } from "discourse/models/composer";
import { Promise } from "rsvp";
import ENV from "discourse-common/config/environment";
+import EmberObject from "@ember/object";
function loadDraft(store, opts) {
opts = opts || {};
@@ -1063,7 +1063,7 @@ export default Controller.extend({
@discourseComputed("model.categoryId", "lastValidatedAt")
categoryValidation(categoryId, lastValidatedAt) {
if (!this.siteSettings.allow_uncategorized_topics && !categoryId) {
- return InputValidation.create({
+ return EmberObject.create({
failed: true,
reason: I18n.t("composer.error.category_missing"),
lastShownAt: lastValidatedAt
@@ -1079,7 +1079,7 @@ export default Controller.extend({
category &&
category.minimum_required_tags > tagsArray.length
) {
- return InputValidation.create({
+ return EmberObject.create({
failed: true,
reason: I18n.t("composer.error.tags_missing", {
count: category.minimum_required_tags
diff --git a/app/assets/javascripts/discourse/controllers/create-account.js.es6 b/app/assets/javascripts/discourse/controllers/create-account.js.es6
index 96abb66d22..ae431f3c37 100644
--- a/app/assets/javascripts/discourse/controllers/create-account.js.es6
+++ b/app/assets/javascripts/discourse/controllers/create-account.js.es6
@@ -10,13 +10,13 @@ import {
on
} from "discourse-common/utils/decorators";
import { emailValid } from "discourse/lib/utilities";
-import InputValidation from "discourse/models/input-validation";
import PasswordValidation from "discourse/mixins/password-validation";
import UsernameValidation from "discourse/mixins/username-validation";
import NameValidation from "discourse/mixins/name-validation";
import UserFieldsValidation from "discourse/mixins/user-fields-validation";
import { userPath } from "discourse/lib/url";
import { findAll } from "discourse/models/login-method";
+import EmberObject from "@ember/object";
export default Controller.extend(
ModalFunctionality,
@@ -110,13 +110,13 @@ export default Controller.extend(
emailValidation(email, rejectedEmails) {
// If blank, fail without a reason
if (isEmpty(email)) {
- return InputValidation.create({
+ return EmberObject.create({
failed: true
});
}
if (rejectedEmails.includes(email)) {
- return InputValidation.create({
+ return EmberObject.create({
failed: true,
reason: I18n.t("user.email.invalid")
});
@@ -126,7 +126,7 @@ export default Controller.extend(
this.get("authOptions.email") === email &&
this.get("authOptions.email_valid")
) {
- return InputValidation.create({
+ return EmberObject.create({
ok: true,
reason: I18n.t("user.email.authenticated", {
provider: this.authProviderDisplayName(
@@ -137,13 +137,13 @@ export default Controller.extend(
}
if (emailValid(email)) {
- return InputValidation.create({
+ return EmberObject.create({
ok: true,
reason: I18n.t("user.email.ok")
});
}
- return InputValidation.create({
+ return EmberObject.create({
failed: true,
reason: I18n.t("user.email.invalid")
});
diff --git a/app/assets/javascripts/discourse/controllers/feature-topic.js.es6 b/app/assets/javascripts/discourse/controllers/feature-topic.js.es6
index 3535e355ce..8fb459a145 100644
--- a/app/assets/javascripts/discourse/controllers/feature-topic.js.es6
+++ b/app/assets/javascripts/discourse/controllers/feature-topic.js.es6
@@ -4,7 +4,7 @@ import Controller from "@ember/controller";
import { ajax } from "discourse/lib/ajax";
import ModalFunctionality from "discourse/mixins/modal-functionality";
import { categoryLinkHTML } from "discourse/helpers/category-link";
-import InputValidation from "discourse/models/input-validation";
+import EmberObject from "@ember/object";
export default Controller.extend(ModalFunctionality, {
topicController: inject("topic"),
@@ -79,7 +79,7 @@ export default Controller.extend(ModalFunctionality, {
@discourseComputed("pinDisabled")
pinInCategoryValidation(pinDisabled) {
if (pinDisabled) {
- return InputValidation.create({
+ return EmberObject.create({
failed: true,
reason: I18n.t("topic.feature_topic.pin_validation")
});
@@ -89,7 +89,7 @@ export default Controller.extend(ModalFunctionality, {
@discourseComputed("pinGloballyDisabled")
pinGloballyValidation(pinGloballyDisabled) {
if (pinGloballyDisabled) {
- return InputValidation.create({
+ return EmberObject.create({
failed: true,
reason: I18n.t("topic.feature_topic.pin_validation")
});
diff --git a/app/assets/javascripts/discourse/controllers/preferences/email.js.es6 b/app/assets/javascripts/discourse/controllers/preferences/email.js.es6
index 94a13ae596..413638e0db 100644
--- a/app/assets/javascripts/discourse/controllers/preferences/email.js.es6
+++ b/app/assets/javascripts/discourse/controllers/preferences/email.js.es6
@@ -2,7 +2,7 @@ import discourseComputed from "discourse-common/utils/decorators";
import { empty, or } from "@ember/object/computed";
import Controller from "@ember/controller";
import { propertyEqual } from "discourse/lib/computed";
-import InputValidation from "discourse/models/input-validation";
+import EmberObject from "@ember/object";
import { emailValid } from "discourse/lib/utilities";
export default Controller.extend({
@@ -43,7 +43,7 @@ export default Controller.extend({
@discourseComputed("invalidEmail")
emailValidation(invalidEmail) {
if (invalidEmail) {
- return InputValidation.create({
+ return EmberObject.create({
failed: true,
reason: I18n.t("user.email.invalid")
});
diff --git a/app/assets/javascripts/discourse/mixins/name-validation.js.es6 b/app/assets/javascripts/discourse/mixins/name-validation.js.es6
index e447f9fcb6..b2594c97fe 100644
--- a/app/assets/javascripts/discourse/mixins/name-validation.js.es6
+++ b/app/assets/javascripts/discourse/mixins/name-validation.js.es6
@@ -1,7 +1,7 @@
import { isEmpty } from "@ember/utils";
-import InputValidation from "discourse/models/input-validation";
import { default as discourseComputed } from "discourse-common/utils/decorators";
import Mixin from "@ember/object/mixin";
+import EmberObject from "@ember/object";
export default Mixin.create({
@discourseComputed()
@@ -17,9 +17,9 @@ export default Mixin.create({
@discourseComputed("accountName")
nameValidation() {
if (this.siteSettings.full_name_required && isEmpty(this.accountName)) {
- return InputValidation.create({ failed: true });
+ return EmberObject.create({ failed: true });
}
- return InputValidation.create({ ok: true });
+ return EmberObject.create({ ok: true });
}
});
diff --git a/app/assets/javascripts/discourse/mixins/password-validation.js.es6 b/app/assets/javascripts/discourse/mixins/password-validation.js.es6
index ec665cdbe6..b313368f52 100644
--- a/app/assets/javascripts/discourse/mixins/password-validation.js.es6
+++ b/app/assets/javascripts/discourse/mixins/password-validation.js.es6
@@ -1,7 +1,7 @@
import { isEmpty } from "@ember/utils";
-import InputValidation from "discourse/models/input-validation";
import { default as discourseComputed } from "discourse-common/utils/decorators";
import Mixin from "@ember/object/mixin";
+import EmberObject from "@ember/object";
export default Mixin.create({
rejectedPasswords: null,
@@ -43,11 +43,11 @@ export default Mixin.create({
passwordMinLength
) {
if (!passwordRequired) {
- return InputValidation.create({ ok: true });
+ return EmberObject.create({ ok: true });
}
if (rejectedPasswords.includes(password)) {
- return InputValidation.create({
+ return EmberObject.create({
failed: true,
reason:
this.rejectedPasswordsMessages.get(password) ||
@@ -57,33 +57,33 @@ export default Mixin.create({
// If blank, fail without a reason
if (isEmpty(password)) {
- return InputValidation.create({ failed: true });
+ return EmberObject.create({ failed: true });
}
// If too short
if (password.length < passwordMinLength) {
- return InputValidation.create({
+ return EmberObject.create({
failed: true,
reason: I18n.t("user.password.too_short")
});
}
if (!isEmpty(accountUsername) && password === accountUsername) {
- return InputValidation.create({
+ return EmberObject.create({
failed: true,
reason: I18n.t("user.password.same_as_username")
});
}
if (!isEmpty(accountEmail) && password === accountEmail) {
- return InputValidation.create({
+ return EmberObject.create({
failed: true,
reason: I18n.t("user.password.same_as_email")
});
}
// Looks good!
- return InputValidation.create({
+ return EmberObject.create({
ok: true,
reason: I18n.t("user.password.ok")
});
diff --git a/app/assets/javascripts/discourse/mixins/user-fields-validation.js.es6 b/app/assets/javascripts/discourse/mixins/user-fields-validation.js.es6
index e535043a2d..782ceca03d 100644
--- a/app/assets/javascripts/discourse/mixins/user-fields-validation.js.es6
+++ b/app/assets/javascripts/discourse/mixins/user-fields-validation.js.es6
@@ -1,6 +1,5 @@
import { isEmpty } from "@ember/utils";
import EmberObject from "@ember/object";
-import InputValidation from "discourse/models/input-validation";
import {
on,
default as discourseComputed
@@ -36,9 +35,9 @@ export default Mixin.create({
return !val || isEmpty(val);
});
if (anyEmpty) {
- return InputValidation.create({ failed: true });
+ return EmberObject.create({ failed: true });
}
}
- return InputValidation.create({ ok: true });
+ return EmberObject.create({ ok: true });
}
});
diff --git a/app/assets/javascripts/discourse/mixins/username-validation.js.es6 b/app/assets/javascripts/discourse/mixins/username-validation.js.es6
index 31186525f1..7845c45a58 100644
--- a/app/assets/javascripts/discourse/mixins/username-validation.js.es6
+++ b/app/assets/javascripts/discourse/mixins/username-validation.js.es6
@@ -1,9 +1,9 @@
import { isEmpty } from "@ember/utils";
-import InputValidation from "discourse/models/input-validation";
import discourseDebounce from "discourse/lib/debounce";
import { setting } from "discourse/lib/computed";
import { default as discourseComputed } from "discourse-common/utils/decorators";
import Mixin from "@ember/object/mixin";
+import EmberObject from "@ember/object";
export default Mixin.create({
uniqueUsernameValidation: null,
@@ -32,7 +32,7 @@ export default Mixin.create({
this.set("uniqueUsernameValidation", null);
if (accountUsername && accountUsername === this.prefilledUsername) {
- return InputValidation.create({
+ return EmberObject.create({
ok: true,
reason: I18n.t("user.username.prefilled")
});
@@ -40,12 +40,12 @@ export default Mixin.create({
// If blank, fail without a reason
if (isEmpty(accountUsername)) {
- return InputValidation.create({ failed: true });
+ return EmberObject.create({ failed: true });
}
// If too short
if (accountUsername.length < this.siteSettings.min_username_length) {
- return InputValidation.create({
+ return EmberObject.create({
failed: true,
reason: I18n.t("user.username.too_short")
});
@@ -53,7 +53,7 @@ export default Mixin.create({
// If too long
if (accountUsername.length > this.maxUsernameLength) {
- return InputValidation.create({
+ return EmberObject.create({
failed: true,
reason: I18n.t("user.username.too_long")
});
@@ -61,7 +61,7 @@ export default Mixin.create({
this.checkUsernameAvailability();
// Let's check it out asynchronously
- return InputValidation.create({
+ return EmberObject.create({
failed: true,
reason: I18n.t("user.username.checking")
});
@@ -87,7 +87,7 @@ export default Mixin.create({
}
return this.set(
"uniqueUsernameValidation",
- InputValidation.create({
+ EmberObject.create({
ok: true,
reason: I18n.t("user.username.available")
})
@@ -96,7 +96,7 @@ export default Mixin.create({
if (result.suggestion) {
return this.set(
"uniqueUsernameValidation",
- InputValidation.create({
+ EmberObject.create({
failed: true,
reason: I18n.t("user.username.not_available", result)
})
@@ -104,7 +104,7 @@ export default Mixin.create({
} else {
return this.set(
"uniqueUsernameValidation",
- InputValidation.create({
+ EmberObject.create({
failed: true,
reason: result.errors
? result.errors.join(" ")
diff --git a/app/assets/javascripts/discourse/models/input-validation.js.es6 b/app/assets/javascripts/discourse/models/input-validation.js.es6
deleted file mode 100644
index c7120db846..0000000000
--- a/app/assets/javascripts/discourse/models/input-validation.js.es6
+++ /dev/null
@@ -1,2 +0,0 @@
-import EmberObject from "@ember/object";
-export default EmberObject.extend();
diff --git a/plugins/poll/assets/javascripts/controllers/poll-ui-builder.js.es6 b/plugins/poll/assets/javascripts/controllers/poll-ui-builder.js.es6
index fdb7e0498e..14d9073e9e 100644
--- a/plugins/poll/assets/javascripts/controllers/poll-ui-builder.js.es6
+++ b/plugins/poll/assets/javascripts/controllers/poll-ui-builder.js.es6
@@ -3,7 +3,7 @@ import {
default as computed,
observes
} from "ember-addons/ember-computed-decorators";
-import InputValidation from "discourse/models/input-validation";
+import EmberObject from "@ember/object";
export default Controller.extend({
regularPollType: "regular",
@@ -260,7 +260,7 @@ export default Controller.extend({
};
}
- return InputValidation.create(options);
+ return EmberObject.create(options);
},
@computed("pollStep")
@@ -274,7 +274,7 @@ export default Controller.extend({
};
}
- return InputValidation.create(options);
+ return EmberObject.create(options);
},
@computed("disableInsert")
@@ -288,7 +288,7 @@ export default Controller.extend({
};
}
- return InputValidation.create(options);
+ return EmberObject.create(options);
},
_comboboxOptions(start_index, end_index) {
From 34665d3f962f1b3d16e8c75e9f8533f355d1ef7b Mon Sep 17 00:00:00 2001
From: Robin Ward
Date: Mon, 11 Nov 2019 15:56:58 -0500
Subject: [PATCH 080/408] FIX: In case `@ember/object` hasn't been loaded yet
---
app/assets/javascripts/discourse-loader.js | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/app/assets/javascripts/discourse-loader.js b/app/assets/javascripts/discourse-loader.js
index d5112d026e..e28ece7122 100644
--- a/app/assets/javascripts/discourse-loader.js
+++ b/app/assets/javascripts/discourse-loader.js
@@ -226,7 +226,7 @@ var define, requirejs;
console.log(
"input-validation has been removed and should be replaced with `@ember/object`"
);
- return Ember.Object;
+ name = "@ember/object";
}
var mod = EMBER_MODULES[name] || registry[name];
From 6ebffaaf6e929523e81168fefc55385cbb75f5ef Mon Sep 17 00:00:00 2001
From: Gerhard Schlager
Date: Mon, 11 Nov 2019 22:30:31 +0100
Subject: [PATCH 081/408] FIX: Better error handling for invalid locale bundle
versions
---
app/controllers/extra_locales_controller.rb | 13 +++++++++----
spec/requests/extra_locales_controller_spec.rb | 8 ++++++++
2 files changed, 17 insertions(+), 4 deletions(-)
diff --git a/app/controllers/extra_locales_controller.rb b/app/controllers/extra_locales_controller.rb
index 4bee444976..e20c81ea42 100644
--- a/app/controllers/extra_locales_controller.rb
+++ b/app/controllers/extra_locales_controller.rb
@@ -9,15 +9,20 @@ class ExtraLocalesController < ApplicationController
:verify_authenticity_token
OVERRIDES_BUNDLE ||= 'overrides'
+ MD5_HASH_LENGTH ||= 32
def show
bundle = params[:bundle]
-
raise Discourse::InvalidAccess.new if !valid_bundle?(bundle)
- if params[:v]&.size == 32
- hash = ExtraLocalesController.bundle_js_hash(bundle)
- immutable_for(1.year) if hash == params[:v]
+ version = params[:v]
+ if version.present?
+ if version.kind_of?(String) && version.length == MD5_HASH_LENGTH
+ hash = ExtraLocalesController.bundle_js_hash(bundle)
+ immutable_for(1.year) if hash == version
+ else
+ raise Discourse::InvalidParameters.new(:v)
+ end
end
render plain: ExtraLocalesController.bundle_js(bundle), content_type: "application/javascript"
diff --git a/spec/requests/extra_locales_controller_spec.rb b/spec/requests/extra_locales_controller_spec.rb
index 7c12b1fcfd..d46f6c71ef 100644
--- a/spec/requests/extra_locales_controller_spec.rb
+++ b/spec/requests/extra_locales_controller_spec.rb
@@ -23,6 +23,14 @@ describe ExtraLocalesController do
expect(response.status).to eq(403)
end
+ it "requires a valid version" do
+ get "/extra-locales/overrides", params: { v: 'a' }
+ expect(response.status).to eq(400)
+
+ get "/extra-locales/overrides?v[foo]=1"
+ expect(response.status).to eq(400)
+ end
+
context "logged in as a moderator" do
let(:moderator) { Fabricate(:moderator) }
From 69266f60ed83ecdd0b0bfcde8575c0ef9e548418 Mon Sep 17 00:00:00 2001
From: Krzysztof Kotlarek
Date: Tue, 12 Nov 2019 16:44:46 +1100
Subject: [PATCH 082/408] FIX: tag and category watchers regression (#8336)
I made a regression here https://github.com/discourse/discourse/commit/17366d3bcc8ac27980e4fb3b7cfdc1ed86c6ab02#diff-ddeebb36d131f89ca91be9d04c2baefaR10
When the tag is added, people watching specific tag are notified but also people watching specific category.
Therefore, `notify_post_users` should accept options who should be notified.
So when `category` is added to the topic, users watching topic and users watching category are notified.
When `tag` is added to the topic, users watching topic and users watching tag are notified
Finally, when a new post is created, everybody is notified, topic watchers, category watchers, tag watchers.
---
app/jobs/regular/notify_category_change.rb | 2 +-
app/jobs/regular/notify_tag_change.rb | 2 +-
app/services/post_alerter.rb | 18 +++++++++++-------
spec/jobs/notify_tag_change_spec.rb | 9 +++++++++
4 files changed, 22 insertions(+), 9 deletions(-)
diff --git a/app/jobs/regular/notify_category_change.rb b/app/jobs/regular/notify_category_change.rb
index bac94a20e0..fbad7582e4 100644
--- a/app/jobs/regular/notify_category_change.rb
+++ b/app/jobs/regular/notify_category_change.rb
@@ -7,7 +7,7 @@ module Jobs
if post&.topic&.visible?
post_alerter = PostAlerter.new
- post_alerter.notify_post_users(post, User.where(id: args[:notified_user_ids]))
+ post_alerter.notify_post_users(post, User.where(id: args[:notified_user_ids]), include_tag_watchers: false)
post_alerter.notify_first_post_watchers(post, post_alerter.category_watchers(post.topic))
end
end
diff --git a/app/jobs/regular/notify_tag_change.rb b/app/jobs/regular/notify_tag_change.rb
index fe4f85052b..dff6769de9 100644
--- a/app/jobs/regular/notify_tag_change.rb
+++ b/app/jobs/regular/notify_tag_change.rb
@@ -7,7 +7,7 @@ module Jobs
if post&.topic&.visible?
post_alerter = PostAlerter.new
- post_alerter.notify_post_users(post, User.where(id: args[:notified_user_ids]))
+ post_alerter.notify_post_users(post, User.where(id: args[:notified_user_ids]), include_category_watchers: false)
post_alerter.notify_first_post_watchers(post, post_alerter.tag_watchers(post.topic))
end
end
diff --git a/app/services/post_alerter.rb b/app/services/post_alerter.rb
index d71e4b4914..6784abd207 100644
--- a/app/services/post_alerter.rb
+++ b/app/services/post_alerter.rb
@@ -559,7 +559,7 @@ class PostAlerter
end
end
- def notify_post_users(post, notified)
+ def notify_post_users(post, notified, include_category_watchers: true, include_tag_watchers: true)
return unless post.topic
warn_if_not_sidekiq
@@ -570,8 +570,14 @@ class PostAlerter
FROM topic_users
WHERE notification_level = :watching
AND topic_id = :topic_id
+ /*category*/
+ /*tags*/
+ )
+ SQL
- UNION
+ if include_category_watchers
+ condition.sub! "/*category*/", <<~SQL
+ UNION
SELECT cu.user_id
FROM category_users cu
@@ -580,14 +586,12 @@ class PostAlerter
WHERE cu.notification_level = :watching
AND cu.category_id = :category_id
AND tu.user_id IS NULL
-
- /*tags*/
- )
- SQL
+ SQL
+ end
tag_ids = post.topic.topic_tags.pluck('topic_tags.tag_id')
- if tag_ids.present?
+ if include_tag_watchers && tag_ids.present?
condition.sub! "/*tags*/", <<~SQL
UNION
diff --git a/spec/jobs/notify_tag_change_spec.rb b/spec/jobs/notify_tag_change_spec.rb
index 3f22cde400..9d6e0053e3 100644
--- a/spec/jobs/notify_tag_change_spec.rb
+++ b/spec/jobs/notify_tag_change_spec.rb
@@ -25,4 +25,13 @@ describe ::Jobs::NotifyTagChange do
expect(notification.user_id).to eq(user.id)
expect(notification.topic_id).to eq(post.topic_id)
end
+
+ it 'doesnt create notification for user watching category' do
+ CategoryUser.create!(
+ user_id: user.id,
+ category_id: post.topic.category_id,
+ notification_level: TopicUser.notification_levels[:watching]
+ )
+ expect { described_class.new.execute(post_id: post.id, notified_user_ids: [regular_user.id]) }.not_to change { Notification.count }
+ end
end
From 5d4b240453d0e0e2d75d9a32b0a4551d6a4af982 Mon Sep 17 00:00:00 2001
From: Jarek Radosz
Date: Tue, 12 Nov 2019 10:47:42 +0100
Subject: [PATCH 083/408] DEV: Provide radix argument to parseInt (#8281)
* DEV: Provide radix 10 argument to parseInt
* DEV: Provide radix 16 argument to parseInt
* DEV: Remove unnecessary parseInt calls
* Fix year formatting
parseInt was used here to convert decimals to ints
---
.../admin-customize-themes-show.js.es6 | 6 +++---
.../admin/models/color-scheme-color.js.es6 | 6 +++---
.../admin/routes/admin-badges-show.js.es6 | 2 +-
.../routes/admin-customize-colors-show.js.es6 | 2 +-
.../routes/admin-customize-themes-edit.js.es6 | 2 +-
.../routes/admin-customize-themes-show.js.es6 | 2 +-
.../discourse/components/badge-title.js.es6 | 2 +-
.../components/basic-topic-list.js.es6 | 2 +-
.../components/composer-editor.js.es6 | 4 ++--
.../discourse/components/d-editor.js.es6 | 2 +-
.../components/edit-category-general.js.es6 | 2 +-
.../components/edit-category-security.js.es6 | 2 +-
.../discourse/components/emoji-picker.js.es6 | 2 +-
.../groups-form-membership-fields.js.es6 | 4 ++--
.../discourse/components/number-field.js.es6 | 4 ++--
.../discourse/components/site-header.js.es6 | 18 ++++++++----------
.../discourse/components/topic-entrance.js.es6 | 4 ++--
.../discourse/components/topic-timeline.js.es6 | 2 +-
.../discourse/controllers/composer.js.es6 | 2 +-
.../discourse/controllers/jump-to-post.js.es6 | 2 +-
.../controllers/reorder-categories.js.es6 | 2 +-
.../discourse/helpers/application.js.es6 | 2 +-
.../initializers/live-development.js.es6 | 2 +-
.../initializers/post-decorations.js.es6 | 2 +-
.../javascripts/discourse/lib/formatter.js.es6 | 6 +++---
.../discourse/lib/key-value-store.js.es6 | 2 +-
.../discourse/lib/push-notifications.js.es6 | 2 +-
.../discourse/lib/screen-track.js.es6 | 2 +-
.../discourse/lib/to-markdown.js.es6 | 4 ++--
.../discourse/models/action-summary.js.es6 | 4 ++--
.../javascripts/discourse/models/group.js.es6 | 2 +-
.../discourse/widgets/hamburger-menu.js.es6 | 2 +-
...liked-consolidated-notification-item.js.es6 | 2 +-
.../javascripts/discourse/widgets/link.js.es6 | 2 +-
.../javascripts/discourse/widgets/post.js.es6 | 2 +-
.../discourse/widgets/user-menu.js.es6 | 2 +-
.../engines/discourse-markdown-it.js.es6 | 12 ++++++------
.../components/mini-tag-chooser.js.es6 | 2 +-
.../select-kit/components/tag-chooser.js.es6 | 2 +-
.../javascripts/initializers/lazyYT.js.es6 | 2 +-
.../controllers/poll-ui-builder.js.es6 | 4 ++--
.../helpers/create-pretender.js.es6 | 14 +++++++-------
.../helpers/review-pretender.js.es6 | 2 +-
.../javascripts/helpers/store-pretender.js.es6 | 6 +++---
44 files changed, 77 insertions(+), 79 deletions(-)
diff --git a/app/assets/javascripts/admin/controllers/admin-customize-themes-show.js.es6 b/app/assets/javascripts/admin/controllers/admin-customize-themes-show.js.es6
index aa4c32ce33..acf195e3a9 100644
--- a/app/assets/javascripts/admin/controllers/admin-customize-themes-show.js.es6
+++ b/app/assets/javascripts/admin/controllers/admin-customize-themes-show.js.es6
@@ -36,7 +36,7 @@ export default Controller.extend({
@discourseComputed("colorSchemeId", "model.color_scheme_id")
colorSchemeChanged(colorSchemeId, existingId) {
- colorSchemeId = colorSchemeId === null ? null : parseInt(colorSchemeId);
+ colorSchemeId = colorSchemeId === null ? null : parseInt(colorSchemeId, 10);
return colorSchemeId !== existingId;
},
@@ -189,7 +189,7 @@ export default Controller.extend({
let schemeId = this.colorSchemeId;
this.set(
"model.color_scheme_id",
- schemeId === null ? null : parseInt(schemeId)
+ schemeId === null ? null : parseInt(schemeId, 10)
);
this.model.saveChanges("color_scheme_id");
},
@@ -239,7 +239,7 @@ export default Controller.extend({
},
addChildTheme() {
- let themeId = parseInt(this.selectedChildThemeId);
+ let themeId = parseInt(this.selectedChildThemeId, 10);
let theme = this.allThemes.findBy("id", themeId);
this.model.addChildTheme(theme);
},
diff --git a/app/assets/javascripts/admin/models/color-scheme-color.js.es6 b/app/assets/javascripts/admin/models/color-scheme-color.js.es6
index 0d984c77a6..2e4907ef9f 100644
--- a/app/assets/javascripts/admin/models/color-scheme-color.js.es6
+++ b/app/assets/javascripts/admin/models/color-scheme-color.js.es6
@@ -80,9 +80,9 @@ const ColorSchemeColor = EmberObject.extend({
hex.substr(2, 1);
}
return Math.round(
- (parseInt("0x" + hex.substr(0, 2)) * 299 +
- parseInt("0x" + hex.substr(2, 2)) * 587 +
- parseInt("0x" + hex.substr(4, 2)) * 114) /
+ (parseInt(hex.substr(0, 2), 16) * 299 +
+ parseInt(hex.substr(2, 2), 16) * 587 +
+ parseInt(hex.substr(4, 2), 16) * 114) /
1000
);
}
diff --git a/app/assets/javascripts/admin/routes/admin-badges-show.js.es6 b/app/assets/javascripts/admin/routes/admin-badges-show.js.es6
index 64ef45aebe..5a94643d42 100644
--- a/app/assets/javascripts/admin/routes/admin-badges-show.js.es6
+++ b/app/assets/javascripts/admin/routes/admin-badges-show.js.es6
@@ -15,7 +15,7 @@ export default Route.extend({
name: I18n.t("admin.badges.new_badge")
});
}
- return this.modelFor("adminBadges").findBy("id", parseInt(params.badge_id));
+ return this.modelFor("adminBadges").findBy("id", parseInt(params.badge_id, 10));
},
actions: {
diff --git a/app/assets/javascripts/admin/routes/admin-customize-colors-show.js.es6 b/app/assets/javascripts/admin/routes/admin-customize-colors-show.js.es6
index 146a3a61a9..8807df2c56 100644
--- a/app/assets/javascripts/admin/routes/admin-customize-colors-show.js.es6
+++ b/app/assets/javascripts/admin/routes/admin-customize-colors-show.js.es6
@@ -2,7 +2,7 @@ import Route from "@ember/routing/route";
export default Route.extend({
model(params) {
const all = this.modelFor("adminCustomize.colors");
- const model = all.findBy("id", parseInt(params.scheme_id));
+ const model = all.findBy("id", parseInt(params.scheme_id, 10));
return model ? model : this.replaceWith("adminCustomize.colors.index");
},
diff --git a/app/assets/javascripts/admin/routes/admin-customize-themes-edit.js.es6 b/app/assets/javascripts/admin/routes/admin-customize-themes-edit.js.es6
index 335e9fd578..62a70f0d7c 100644
--- a/app/assets/javascripts/admin/routes/admin-customize-themes-edit.js.es6
+++ b/app/assets/javascripts/admin/routes/admin-customize-themes-edit.js.es6
@@ -2,7 +2,7 @@ import Route from "@ember/routing/route";
export default Route.extend({
model(params) {
const all = this.modelFor("adminCustomizeThemes");
- const model = all.findBy("id", parseInt(params.theme_id));
+ const model = all.findBy("id", parseInt(params.theme_id, 10));
return model
? {
model,
diff --git a/app/assets/javascripts/admin/routes/admin-customize-themes-show.js.es6 b/app/assets/javascripts/admin/routes/admin-customize-themes-show.js.es6
index c9573fd8ac..408917b57a 100644
--- a/app/assets/javascripts/admin/routes/admin-customize-themes-show.js.es6
+++ b/app/assets/javascripts/admin/routes/admin-customize-themes-show.js.es6
@@ -9,7 +9,7 @@ export default Route.extend({
model(params) {
const all = this.modelFor("adminCustomizeThemes");
- const model = all.findBy("id", parseInt(params.theme_id));
+ const model = all.findBy("id", parseInt(params.theme_id, 10));
return model ? model : this.replaceWith("adminCustomizeTheme.index");
},
diff --git a/app/assets/javascripts/discourse/components/badge-title.js.es6 b/app/assets/javascripts/discourse/components/badge-title.js.es6
index 7f1292e2e7..ad80c39ddc 100644
--- a/app/assets/javascripts/discourse/components/badge-title.js.es6
+++ b/app/assets/javascripts/discourse/components/badge-title.js.es6
@@ -10,7 +10,7 @@ export default Component.extend({
@discourseComputed("selectableUserBadges", "selectedUserBadgeId")
selectedUserBadge(selectableUserBadges, selectedUserBadgeId) {
- return selectableUserBadges.findBy("id", parseInt(selectedUserBadgeId));
+ return selectableUserBadges.findBy("id", parseInt(selectedUserBadgeId, 10));
},
actions: {
diff --git a/app/assets/javascripts/discourse/components/basic-topic-list.js.es6 b/app/assets/javascripts/discourse/components/basic-topic-list.js.es6
index c9ce38c339..be4ec964c2 100644
--- a/app/assets/javascripts/discourse/components/basic-topic-list.js.es6
+++ b/app/assets/javascripts/discourse/components/basic-topic-list.js.es6
@@ -105,7 +105,7 @@ export default Component.extend({
}
}
- const topic = this.topics.findBy("id", parseInt(topicId));
+ const topic = this.topics.findBy("id", parseInt(topicId, 10));
this.appEvents.trigger("topic-entrance:show", {
topic,
position: target.offset()
diff --git a/app/assets/javascripts/discourse/components/composer-editor.js.es6 b/app/assets/javascripts/discourse/components/composer-editor.js.es6
index d997c3f4f6..6c6e92c074 100644
--- a/app/assets/javascripts/discourse/components/composer-editor.js.es6
+++ b/app/assets/javascripts/discourse/components/composer-editor.js.es6
@@ -273,7 +273,7 @@ export default Component.extend({
const lastMatch = matchingPlaceholder[matchingPlaceholder.length - 1];
const regex = new RegExp(regexString);
const orderNr = regex.exec(lastMatch)[1]
- ? parseInt(regex.exec(lastMatch)[1]) + 1
+ ? parseInt(regex.exec(lastMatch)[1], 10) + 1
: 1;
data.orderNr = orderNr;
const filenameWithOrderNr = `${filename}(${orderNr})`;
@@ -823,7 +823,7 @@ export default Component.extend({
$(e.target)
.parent()
.attr("data-image-index")
- );
+ , 10);
const scale = e.target.attributes["data-scale"].value;
const matchingPlaceholder = this.get("composer.reply").match(
diff --git a/app/assets/javascripts/discourse/components/d-editor.js.es6 b/app/assets/javascripts/discourse/components/d-editor.js.es6
index f102a47886..5173f41d89 100644
--- a/app/assets/javascripts/discourse/components/d-editor.js.es6
+++ b/app/assets/javascripts/discourse/components/d-editor.js.es6
@@ -138,7 +138,7 @@ class Toolbar {
shortcut: "Shift+7",
title: "composer.olist_title",
perform: e =>
- e.applyList(i => (!i ? "1. " : `${parseInt(i) + 1}. `), "list_item")
+ e.applyList(i => (!i ? "1. " : `${parseInt(i, 10) + 1}. `), "list_item")
});
if (siteSettings.support_mixed_text_direction) {
diff --git a/app/assets/javascripts/discourse/components/edit-category-general.js.es6 b/app/assets/javascripts/discourse/components/edit-category-general.js.es6
index a1f95d117a..bdcdf440dc 100644
--- a/app/assets/javascripts/discourse/components/edit-category-general.js.es6
+++ b/app/assets/javascripts/discourse/components/edit-category-general.js.es6
@@ -76,7 +76,7 @@ export default buildCategoryPanel("general", {
name,
color,
text_color: textColor,
- parent_category_id: parseInt(parentCategoryId),
+ parent_category_id: parseInt(parentCategoryId, 10),
read_restricted: category.get("read_restricted")
});
return categoryBadgeHTML(c, { link: false });
diff --git a/app/assets/javascripts/discourse/components/edit-category-security.js.es6 b/app/assets/javascripts/discourse/components/edit-category-security.js.es6
index 013e620671..00ad068467 100644
--- a/app/assets/javascripts/discourse/components/edit-category-security.js.es6
+++ b/app/assets/javascripts/discourse/components/edit-category-security.js.es6
@@ -38,7 +38,7 @@ export default buildCategoryPanel("security", {
if (!this.get("category.is_special")) {
this.category.addPermission({
group_name: group + "",
- permission: PermissionType.create({ id: parseInt(id) })
+ permission: PermissionType.create({ id: parseInt(id, 10) })
});
}
diff --git a/app/assets/javascripts/discourse/components/emoji-picker.js.es6 b/app/assets/javascripts/discourse/components/emoji-picker.js.es6
index 7d4d92e7ee..6c8464bca3 100644
--- a/app/assets/javascripts/discourse/components/emoji-picker.js.es6
+++ b/app/assets/javascripts/discourse/components/emoji-picker.js.es6
@@ -442,7 +442,7 @@ export default Component.extend({
);
$diversityScales.on("click", event => {
const $selectedDiversity = $(event.currentTarget);
- this.set("selectedDiversity", parseInt($selectedDiversity.data("level")));
+ this.set("selectedDiversity", parseInt($selectedDiversity.data("level"), 10));
return false;
});
},
diff --git a/app/assets/javascripts/discourse/components/groups-form-membership-fields.js.es6 b/app/assets/javascripts/discourse/components/groups-form-membership-fields.js.es6
index 1b5be47e6a..b85eef4fa5 100644
--- a/app/assets/javascripts/discourse/components/groups-form-membership-fields.js.es6
+++ b/app/assets/javascripts/discourse/components/groups-form-membership-fields.js.es6
@@ -19,7 +19,7 @@ export default Component.extend({
@discourseComputed("model.visibility_level", "model.public_admission")
disableMembershipRequestSetting(visibility_level, publicAdmission) {
- visibility_level = parseInt(visibility_level);
+ visibility_level = parseInt(visibility_level, 10);
return publicAdmission || visibility_level > 1;
},
@@ -28,7 +28,7 @@ export default Component.extend({
"model.allow_membership_requests"
)
disablePublicSetting(visibility_level, allowMembershipRequests) {
- visibility_level = parseInt(visibility_level);
+ visibility_level = parseInt(visibility_level, 10);
return allowMembershipRequests || visibility_level > 1;
}
});
diff --git a/app/assets/javascripts/discourse/components/number-field.js.es6 b/app/assets/javascripts/discourse/components/number-field.js.es6
index 9de92f0afe..ca2db4d124 100644
--- a/app/assets/javascripts/discourse/components/number-field.js.es6
+++ b/app/assets/javascripts/discourse/components/number-field.js.es6
@@ -6,10 +6,10 @@ export default Ember.TextField.extend({
@discourseComputed("number")
value: {
get(number) {
- return parseInt(number);
+ return parseInt(number, 10);
},
set(value) {
- const num = parseInt(value);
+ const num = parseInt(value, 10);
if (isNaN(num)) {
this.set("invalid", true);
return value;
diff --git a/app/assets/javascripts/discourse/components/site-header.js.es6 b/app/assets/javascripts/discourse/components/site-header.js.es6
index 9bdd8f0d8b..43253d7db3 100644
--- a/app/assets/javascripts/discourse/components/site-header.js.es6
+++ b/app/assets/javascripts/discourse/components/site-header.js.es6
@@ -65,7 +65,7 @@ const SiteHeaderComponent = MountWidget.extend(Docking, PanEvents, {
_handlePanDone(offset, event) {
const $window = $(window);
- const windowWidth = parseInt($window.width());
+ const windowWidth = $window.width();
const $menuPanels = $(".menu-panel");
const menuOrigin = this._panMenuOrigin;
this._shouldMenuClose(event, menuOrigin)
@@ -246,16 +246,16 @@ const SiteHeaderComponent = MountWidget.extend(Docking, PanEvents, {
}
const $window = $(window);
- const windowWidth = parseInt($window.width());
+ const windowWidth = $window.width();
const headerWidth = $("#main-outlet .container").width() || 1100;
- const remaining = parseInt((windowWidth - headerWidth) / 2);
+ const remaining = (windowWidth - headerWidth) / 2;
const viewMode = remaining < 50 ? "slide-in" : "drop-down";
$menuPanels.each((idx, panel) => {
const $panel = $(panel);
const $headerCloak = $(".header-cloak");
- let width = parseInt($panel.attr("data-max-width") || 300);
+ let width = parseInt($panel.attr("data-max-width"), 10) || 300;
if (windowWidth - width < 50) {
width = windowWidth - 50;
}
@@ -281,7 +281,7 @@ const SiteHeaderComponent = MountWidget.extend(Docking, PanEvents, {
const $panelBody = $(".panel-body", $panel);
// 2 pixel fudge allows for firefox subpixel sizing stuff causing scrollbar
let contentHeight =
- parseInt($(".panel-body-contents", $panel).height()) + 2;
+ $(".panel-body-contents", $panel).height() + 2;
// We use a mutationObserver to check for style changes, so it's important
// we don't set it if it doesn't change. Same goes for the $panelBody!
@@ -300,7 +300,7 @@ const SiteHeaderComponent = MountWidget.extend(Docking, PanEvents, {
}
// adjust panel height
- const fullHeight = parseInt($window.height());
+ const fullHeight = $window.height();
const offsetTop = $panel.offset().top;
const scrollTop = $window.scrollTop();
@@ -373,14 +373,12 @@ export function headerHeight() {
const headerOffset = $header.offset();
const headerOffsetTop = headerOffset ? headerOffset.top : 0;
- return parseInt(
- $header.outerHeight() + headerOffsetTop - $(window).scrollTop()
- );
+ return $header.outerHeight() + headerOffsetTop - $(window).scrollTop();
}
export function headerTop() {
const $header = $("header.d-header");
const headerOffset = $header.offset();
const headerOffsetTop = headerOffset ? headerOffset.top : 0;
- return parseInt(headerOffsetTop - $(window).scrollTop());
+ return headerOffsetTop - $(window).scrollTop();
}
diff --git a/app/assets/javascripts/discourse/components/topic-entrance.js.es6 b/app/assets/javascripts/discourse/components/topic-entrance.js.es6
index 3cfa8feb6a..b27a7fe15d 100644
--- a/app/assets/javascripts/discourse/components/topic-entrance.js.es6
+++ b/app/assets/javascripts/discourse/components/topic-entrance.js.es6
@@ -63,8 +63,8 @@ export default Component.extend(CleansUp, {
const $self = $(this.element);
const width = $self.width();
const height = $self.height();
- pos.left = parseInt(pos.left) - width / 2;
- pos.top = parseInt(pos.top) - height / 2;
+ pos.left = parseInt(pos.left, 10) - width / 2;
+ pos.top = parseInt(pos.top, 10) - height / 2;
const windowWidth = $(window).width();
if (pos.left + width > windowWidth) {
diff --git a/app/assets/javascripts/discourse/components/topic-timeline.js.es6 b/app/assets/javascripts/discourse/components/topic-timeline.js.es6
index b802d47586..64f0dbc2d8 100644
--- a/app/assets/javascripts/discourse/components/topic-timeline.js.es6
+++ b/app/assets/javascripts/discourse/components/topic-timeline.js.es6
@@ -5,7 +5,7 @@ import { observes } from "discourse-common/utils/decorators";
import optionalService from "discourse/lib/optional-service";
const headerPadding = () => {
- let topPadding = parseInt($("#main-outlet").css("padding-top")) + 3;
+ let topPadding = parseInt($("#main-outlet").css("padding-top"), 10) + 3;
const iPadNavHeight = $(".footer-nav-ipad .footer-nav").height();
if (iPadNavHeight) {
topPadding += iPadNavHeight;
diff --git a/app/assets/javascripts/discourse/controllers/composer.js.es6 b/app/assets/javascripts/discourse/controllers/composer.js.es6
index e3d5ae3c0d..90e0429aaa 100644
--- a/app/assets/javascripts/discourse/controllers/composer.js.es6
+++ b/app/assets/javascripts/discourse/controllers/composer.js.es6
@@ -702,7 +702,7 @@ export default Controller.extend({
if (this.get("model.editingPost")) {
this.appEvents.trigger("post-stream:refresh", {
- id: parseInt(result.responseJson.id)
+ id: parseInt(result.responseJson.id, 10)
});
if (result.responseJson.post.post_number === 1) {
this.appEvents.trigger("header:update-topic", composer.topic);
diff --git a/app/assets/javascripts/discourse/controllers/jump-to-post.js.es6 b/app/assets/javascripts/discourse/controllers/jump-to-post.js.es6
index 35981f39a7..cd3b95936f 100644
--- a/app/assets/javascripts/discourse/controllers/jump-to-post.js.es6
+++ b/app/assets/javascripts/discourse/controllers/jump-to-post.js.es6
@@ -24,7 +24,7 @@ export default Controller.extend(ModalFunctionality, {
},
_jumpToIndex(postsCounts, postNumber) {
- const where = Math.min(postsCounts, Math.max(1, parseInt(postNumber)));
+ const where = Math.min(postsCounts, Math.max(1, parseInt(postNumber, 10)));
this.jumpToIndex(where);
this._close();
},
diff --git a/app/assets/javascripts/discourse/controllers/reorder-categories.js.es6 b/app/assets/javascripts/discourse/controllers/reorder-categories.js.es6
index cf7c2ca7cb..baaddc1825 100644
--- a/app/assets/javascripts/discourse/controllers/reorder-categories.js.es6
+++ b/app/assets/javascripts/discourse/controllers/reorder-categories.js.es6
@@ -115,7 +115,7 @@ export default Controller.extend(ModalFunctionality, Ember.Evented, {
actions: {
change(cat, e) {
- let position = parseInt($(e.target).val());
+ let position = parseInt($(e.target).val(), 10);
let amount = Math.min(
Math.max(position, 0),
this.categoriesOrdered.length - 1
diff --git a/app/assets/javascripts/discourse/helpers/application.js.es6 b/app/assets/javascripts/discourse/helpers/application.js.es6
index 0710d8b939..cff377e323 100644
--- a/app/assets/javascripts/discourse/helpers/application.js.es6
+++ b/app/assets/javascripts/discourse/helpers/application.js.es6
@@ -22,7 +22,7 @@ registerUnbound("number", (orig, params) => {
let title = I18n.toNumber(orig, { precision: 0 });
if (params.numberKey) {
- title = I18n.t(params.numberKey, { number: title, count: parseInt(orig) });
+ title = I18n.t(params.numberKey, { number: title, count: parseInt(orig, 10) });
}
let classNames = "number";
diff --git a/app/assets/javascripts/discourse/initializers/live-development.js.es6 b/app/assets/javascripts/discourse/initializers/live-development.js.es6
index 5c2d973d31..5cdbcb96ca 100644
--- a/app/assets/javascripts/discourse/initializers/live-development.js.es6
+++ b/app/assets/javascripts/discourse/initializers/live-development.js.es6
@@ -13,7 +13,7 @@ export default {
window.location.search.indexOf("?preview_theme_id=") === 0
) {
// force preview theme id to always be carried along
- const themeId = parseInt(window.location.search.slice(18).split("&")[0]);
+ const themeId = parseInt(window.location.search.slice(18).split("&")[0], 10);
if (!isNaN(themeId)) {
const patchState = function(f) {
const patched = window.history[f];
diff --git a/app/assets/javascripts/discourse/initializers/post-decorations.js.es6 b/app/assets/javascripts/discourse/initializers/post-decorations.js.es6
index a9e1cc24d0..75ddbdfdae 100644
--- a/app/assets/javascripts/discourse/initializers/post-decorations.js.es6
+++ b/app/assets/javascripts/discourse/initializers/post-decorations.js.es6
@@ -26,7 +26,7 @@ export default {
const players = $("audio", $elem);
if (players.length) {
players.on("play", () => {
- const postId = parseInt($elem.closest("article").data("post-id"));
+ const postId = parseInt($elem.closest("article").data("post-id"), 10);
if (postId) {
api.preventCloak(postId);
}
diff --git a/app/assets/javascripts/discourse/lib/formatter.js.es6 b/app/assets/javascripts/discourse/lib/formatter.js.es6
index 2f71c83658..28bdb6cef2 100644
--- a/app/assets/javascripts/discourse/lib/formatter.js.es6
+++ b/app/assets/javascripts/discourse/lib/formatter.js.es6
@@ -195,11 +195,11 @@ export function durationTiny(distance, ageOpts) {
const numYears = distanceInMinutes / 525600.0;
const remainder = numYears % 1;
if (remainder < 0.25) {
- formatted = t("about_x_years", { count: parseInt(numYears) });
+ formatted = t("about_x_years", { count: Math.floor(numYears) });
} else if (remainder < 0.75) {
- formatted = t("over_x_years", { count: parseInt(numYears) });
+ formatted = t("over_x_years", { count: Math.floor(numYears) });
} else {
- formatted = t("almost_x_years", { count: parseInt(numYears) + 1 });
+ formatted = t("almost_x_years", { count: Math.floor(numYears) + 1 });
}
break;
diff --git a/app/assets/javascripts/discourse/lib/key-value-store.js.es6 b/app/assets/javascripts/discourse/lib/key-value-store.js.es6
index c45501cf05..a0a0a5dcaa 100644
--- a/app/assets/javascripts/discourse/lib/key-value-store.js.es6
+++ b/app/assets/javascripts/discourse/lib/key-value-store.js.es6
@@ -67,7 +67,7 @@ KeyValueStore.prototype = {
if (!safeLocalStorage) {
return def;
}
- const result = parseInt(this.get(key));
+ const result = parseInt(this.get(key), 10);
if (!isFinite(result)) {
return def;
}
diff --git a/app/assets/javascripts/discourse/lib/push-notifications.js.es6 b/app/assets/javascripts/discourse/lib/push-notifications.js.es6
index 00f15d0fab..1b73a29117 100644
--- a/app/assets/javascripts/discourse/lib/push-notifications.js.es6
+++ b/app/assets/javascripts/discourse/lib/push-notifications.js.es6
@@ -22,7 +22,7 @@ function userAgentVersionChecker(agent, version, mobileView) {
new RegExp(`${agent}\/(\\d+)\\.\\d`)
);
if (uaMatch && mobileView) return false;
- if (!uaMatch || parseInt(uaMatch[1]) < version) return false;
+ if (!uaMatch || parseInt(uaMatch[1], 10) < version) return false;
return true;
}
diff --git a/app/assets/javascripts/discourse/lib/screen-track.js.es6 b/app/assets/javascripts/discourse/lib/screen-track.js.es6
index 314e1fac0a..91e0d42a83 100644
--- a/app/assets/javascripts/discourse/lib/screen-track.js.es6
+++ b/app/assets/javascripts/discourse/lib/screen-track.js.es6
@@ -187,7 +187,7 @@ export default class {
// Save unique topic IDs up to a max
let topicIds = storage.get("anon-topic-ids");
if (topicIds) {
- topicIds = topicIds.split(",").map(e => parseInt(e));
+ topicIds = topicIds.split(",").map(e => parseInt(e, 10));
} else {
topicIds = [];
}
diff --git a/app/assets/javascripts/discourse/lib/to-markdown.js.es6 b/app/assets/javascripts/discourse/lib/to-markdown.js.es6
index 4a3c486251..0e71b585c5 100644
--- a/app/assets/javascripts/discourse/lib/to-markdown.js.es6
+++ b/app/assets/javascripts/discourse/lib/to-markdown.js.es6
@@ -322,7 +322,7 @@ export class Tag {
try {
const level = parseInt(
attrs.style.match(/level./)[0].replace("level", "")
- );
+ , 10);
indent = Array(level).join("\t") + indent;
} finally {
if (attrs.class === "MsoListParagraphCxSpFirst") {
@@ -448,7 +448,7 @@ export class Tag {
const bullet = text.match(/\n\t*\*/)[0];
for (
- let i = parseInt(this.element.attributes.start || 1);
+ let i = parseInt(this.element.attributes.start || 1, 10);
text.includes(bullet);
i++
) {
diff --git a/app/assets/javascripts/discourse/models/action-summary.js.es6 b/app/assets/javascripts/discourse/models/action-summary.js.es6
index ce8259b9c0..4d48ccf1bc 100644
--- a/app/assets/javascripts/discourse/models/action-summary.js.es6
+++ b/app/assets/javascripts/discourse/models/action-summary.js.es6
@@ -61,10 +61,10 @@ export default RestModel.extend({
}
const remaining = parseInt(
data.xhr.getResponseHeader("Discourse-Actions-Remaining") || 0
- );
+ , 10);
const max = parseInt(
data.xhr.getResponseHeader("Discourse-Actions-Max") || 0
- );
+ , 10);
return { acted: true, remaining, max };
})
.catch(error => {
diff --git a/app/assets/javascripts/discourse/models/group.js.es6 b/app/assets/javascripts/discourse/models/group.js.es6
index f8bed56d59..4d6455e891 100644
--- a/app/assets/javascripts/discourse/models/group.js.es6
+++ b/app/assets/javascripts/discourse/models/group.js.es6
@@ -236,7 +236,7 @@ const Group = RestModel.extend({
}
if (opts.categoryId) {
- data.category_id = parseInt(opts.categoryId);
+ data.category_id = parseInt(opts.categoryId, 10);
}
return ajax(`/groups/${this.name}/${type}.json`, { data }).then(posts => {
diff --git a/app/assets/javascripts/discourse/widgets/hamburger-menu.js.es6 b/app/assets/javascripts/discourse/widgets/hamburger-menu.js.es6
index be146f4285..38af3cd7d9 100644
--- a/app/assets/javascripts/discourse/widgets/hamburger-menu.js.es6
+++ b/app/assets/javascripts/discourse/widgets/hamburger-menu.js.es6
@@ -339,7 +339,7 @@ export default createWidget("hamburger-menu", {
this.sendWidgetAction("toggleHamburger");
} else {
const $window = $(window);
- const windowWidth = parseInt($window.width(), 10);
+ const windowWidth = $window.width();
const $panel = $(".menu-panel");
$panel.addClass("animate");
const panelOffsetDirection = this.site.mobileView ? "left" : "right";
diff --git a/app/assets/javascripts/discourse/widgets/liked-consolidated-notification-item.js.es6 b/app/assets/javascripts/discourse/widgets/liked-consolidated-notification-item.js.es6
index 96a3604255..bc4ce3f43f 100644
--- a/app/assets/javascripts/discourse/widgets/liked-consolidated-notification-item.js.es6
+++ b/app/assets/javascripts/discourse/widgets/liked-consolidated-notification-item.js.es6
@@ -22,7 +22,7 @@ createWidgetFrom(
const description = I18n.t(
"notifications.liked_consolidated_description",
{
- count: parseInt(data.count)
+ count: parseInt(data.count, 10)
}
);
diff --git a/app/assets/javascripts/discourse/widgets/link.js.es6 b/app/assets/javascripts/discourse/widgets/link.js.es6
index 841fda069f..1194e1c8ae 100644
--- a/app/assets/javascripts/discourse/widgets/link.js.es6
+++ b/app/assets/javascripts/discourse/widgets/link.js.es6
@@ -79,7 +79,7 @@ export default createWidget("link", {
const currentUser = this.currentUser;
if (currentUser && attrs.badgeCount) {
- const val = parseInt(currentUser.get(attrs.badgeCount));
+ const val = parseInt(currentUser.get(attrs.badgeCount), 10);
if (val > 0) {
const title = attrs.badgeTitle ? I18n.t(attrs.badgeTitle) : "";
result.push(" ");
diff --git a/app/assets/javascripts/discourse/widgets/post.js.es6 b/app/assets/javascripts/discourse/widgets/post.js.es6
index 8eec4318a8..6602f1810a 100644
--- a/app/assets/javascripts/discourse/widgets/post.js.es6
+++ b/app/assets/javascripts/discourse/widgets/post.js.es6
@@ -709,7 +709,7 @@ export default createWidget("post", {
// only warn once per day
const yesterday = new Date().getTime() - 1000 * 60 * 60 * 24;
- if (lastWarnedLikes && parseInt(lastWarnedLikes) > yesterday) {
+ if (lastWarnedLikes && parseInt(lastWarnedLikes, 10) > yesterday) {
return;
}
diff --git a/app/assets/javascripts/discourse/widgets/user-menu.js.es6 b/app/assets/javascripts/discourse/widgets/user-menu.js.es6
index cf669d1edc..488ea63c02 100644
--- a/app/assets/javascripts/discourse/widgets/user-menu.js.es6
+++ b/app/assets/javascripts/discourse/widgets/user-menu.js.es6
@@ -221,7 +221,7 @@ export default createWidget("user-menu", {
this.sendWidgetAction("toggleUserMenu");
} else {
const $window = $(window);
- const windowWidth = parseInt($window.width(), 10);
+ const windowWidth = $window.width();
const $panel = $(".menu-panel");
$panel.addClass("animate");
$panel.css("right", -windowWidth);
diff --git a/app/assets/javascripts/pretty-text/engines/discourse-markdown-it.js.es6 b/app/assets/javascripts/pretty-text/engines/discourse-markdown-it.js.es6
index 7bf824de7f..c491468745 100644
--- a/app/assets/javascripts/pretty-text/engines/discourse-markdown-it.js.es6
+++ b/app/assets/javascripts/pretty-text/engines/discourse-markdown-it.js.es6
@@ -145,22 +145,22 @@ function renderImage(tokens, idx, options, env, slf) {
// calculate using percentage
if (match[5] && match[6] && match[6] === "%") {
let percent = parseFloat(match[5]) / 100.0;
- width = parseInt(width * percent);
- height = parseInt(height * percent);
+ width = parseInt(width * percent, 10);
+ height = parseInt(height * percent, 10);
}
// calculate using only given width
if (match[5] && match[6] && match[6] === "x") {
let wr = parseFloat(match[5]) / width;
- width = parseInt(match[5]);
- height = parseInt(height * wr);
+ width = parseInt(match[5], 10);
+ height = parseInt(height * wr, 10);
}
// calculate using only given height
if (match[5] && match[4] && match[4] === "x" && !match[6]) {
let hr = parseFloat(match[5]) / height;
- height = parseInt(match[5]);
- width = parseInt(width * hr);
+ height = parseInt(match[5], 10);
+ width = parseInt(width * hr, 10);
}
if (token.attrIndex("width") === -1) {
diff --git a/app/assets/javascripts/select-kit/components/mini-tag-chooser.js.es6 b/app/assets/javascripts/select-kit/components/mini-tag-chooser.js.es6
index 1b4689b933..61f2539940 100644
--- a/app/assets/javascripts/select-kit/components/mini-tag-chooser.js.es6
+++ b/app/assets/javascripts/select-kit/components/mini-tag-chooser.js.es6
@@ -52,7 +52,7 @@ export default ComboBox.extend(TagsMixin, {
this.limit ||
this.maximum ||
this.get("siteSettings.max_tags_per_topic")
- )
+ , 10)
);
},
diff --git a/app/assets/javascripts/select-kit/components/tag-chooser.js.es6 b/app/assets/javascripts/select-kit/components/tag-chooser.js.es6
index 247a8eeab1..439a0ee05e 100644
--- a/app/assets/javascripts/select-kit/components/tag-chooser.js.es6
+++ b/app/assets/javascripts/select-kit/components/tag-chooser.js.es6
@@ -47,7 +47,7 @@ export default MultiSelectComponent.extend(TagsMixin, {
this.limit ||
this.maximum ||
this.get("siteSettings.max_tags_per_topic")
- )
+ , 10)
);
}
},
diff --git a/plugins/lazy-yt/assets/javascripts/initializers/lazyYT.js.es6 b/plugins/lazy-yt/assets/javascripts/initializers/lazyYT.js.es6
index b34dd942b8..4afe9a0775 100644
--- a/plugins/lazy-yt/assets/javascripts/initializers/lazyYT.js.es6
+++ b/plugins/lazy-yt/assets/javascripts/initializers/lazyYT.js.es6
@@ -14,7 +14,7 @@ export default {
$(".lazyYT", $elem).lazyYT({
onPlay(e, $el) {
// don't cloak posts that have playing videos in them
- const postId = parseInt($el.closest("article").data("post-id"));
+ const postId = parseInt($el.closest("article").data("post-id"), 10);
if (postId) {
api.preventCloak(postId);
}
diff --git a/plugins/poll/assets/javascripts/controllers/poll-ui-builder.js.es6 b/plugins/poll/assets/javascripts/controllers/poll-ui-builder.js.es6
index 14d9073e9e..76f06ae027 100644
--- a/plugins/poll/assets/javascripts/controllers/poll-ui-builder.js.es6
+++ b/plugins/poll/assets/javascripts/controllers/poll-ui-builder.js.es6
@@ -140,7 +140,7 @@ export default Controller.extend({
)
pollMaxOptions(isRegular, isMultiple, isNumber, count, pollMin, pollStep) {
if (isRegular) return;
- const pollMinInt = parseInt(pollMin) || 1;
+ const pollMinInt = parseInt(pollMin, 10) || 1;
if (isMultiple) {
return this._comboboxOptions(pollMinInt + 1, count + 1);
@@ -159,7 +159,7 @@ export default Controller.extend({
@computed("isNumber", "pollMax")
pollStepOptions(isNumber, pollMax) {
if (!isNumber) return;
- return this._comboboxOptions(1, (parseInt(pollMax) || 1) + 1);
+ return this._comboboxOptions(1, (parseInt(pollMax, 10) || 1) + 1);
},
@computed(
diff --git a/test/javascripts/helpers/create-pretender.js.es6 b/test/javascripts/helpers/create-pretender.js.es6
index 74d93e38ff..22d1618edc 100644
--- a/test/javascripts/helpers/create-pretender.js.es6
+++ b/test/javascripts/helpers/create-pretender.js.es6
@@ -436,25 +436,25 @@ export default function() {
this.get("/t/:topic_id/posts.json", request => {
const postIds = request.queryParams.post_ids;
- const postNumber = parseInt(request.queryParams.post_number);
+ const postNumber = parseInt(request.queryParams.post_number, 10);
let posts;
if (postIds) {
posts = postIds.map(p => ({
- id: parseInt(p),
- post_number: parseInt(p)
+ id: parseInt(p, 10),
+ post_number: parseInt(p, 10)
}));
} else if (postNumber && request.queryParams.asc === "true") {
posts = _.range(postNumber + 1, postNumber + 6).map(p => ({
- id: parseInt(p),
- post_number: parseInt(p)
+ id: parseInt(p, 10),
+ post_number: parseInt(p, 10)
}));
} else if (postNumber && request.queryParams.asc === "false") {
posts = _.range(postNumber - 5, postNumber)
.reverse()
.map(p => ({
- id: parseInt(p),
- post_number: parseInt(p)
+ id: parseInt(p, 10),
+ post_number: parseInt(p, 10)
}));
}
diff --git a/test/javascripts/helpers/review-pretender.js.es6 b/test/javascripts/helpers/review-pretender.js.es6
index 26bb589e12..c37e63b7f8 100644
--- a/test/javascripts/helpers/review-pretender.js.es6
+++ b/test/javascripts/helpers/review-pretender.js.es6
@@ -128,7 +128,7 @@ export default function(helpers) {
return response(200, {
reviewable_perform_result: {
success: true,
- remove_reviewable_ids: [parseInt(request.params.id)]
+ remove_reviewable_ids: [parseInt(request.params.id, 10)]
}
});
});
diff --git a/test/javascripts/helpers/store-pretender.js.es6 b/test/javascripts/helpers/store-pretender.js.es6
index e30cd10572..30be5640f7 100644
--- a/test/javascripts/helpers/store-pretender.js.es6
+++ b/test/javascripts/helpers/store-pretender.js.es6
@@ -30,7 +30,7 @@ export default function(helpers) {
const { response, success, parsePostData } = helpers;
this.get("/fruits/:id", function(request) {
- const fruit = fruits.find(f => f.id === parseInt(request.params.id));
+ const fruit = fruits.find(f => f.id === parseInt(request.params.id, 10));
return response({ __rest_serializer: "1", fruit, farmers, colors });
});
@@ -58,7 +58,7 @@ export default function(helpers) {
});
this.get("/widgets/:widget_id", function(request) {
- const w = _widgets.findBy("id", parseInt(request.params.widget_id));
+ const w = _widgets.findBy("id", parseInt(request.params.widget_id, 10));
if (w) {
return response({ widget: w, extras: { hello: "world" } });
} else {
@@ -91,7 +91,7 @@ export default function(helpers) {
result = result.filterBy("name", qp.name);
}
if (qp.id) {
- result = result.filterBy("id", parseInt(qp.id));
+ result = result.filterBy("id", parseInt(qp.id, 10));
}
}
From 9b841ea83fde9cb93beda48267b17f0f5279f09b Mon Sep 17 00:00:00 2001
From: Jarek Radosz
Date: Tue, 12 Nov 2019 11:49:31 +0100
Subject: [PATCH 084/408] DEV: Run prettier
---
.../javascripts/admin/routes/admin-badges-show.js.es6 | 5 ++++-
.../discourse/components/composer-editor.js.es6 | 5 +++--
.../discourse/components/emoji-picker.js.es6 | 5 ++++-
.../discourse/components/site-header.js.es6 | 3 +--
.../javascripts/discourse/helpers/application.js.es6 | 5 ++++-
.../discourse/initializers/live-development.js.es6 | 5 ++++-
.../discourse/initializers/post-decorations.js.es6 | 5 ++++-
.../javascripts/discourse/lib/to-markdown.js.es6 | 5 +++--
.../javascripts/discourse/models/action-summary.js.es6 | 10 ++++++----
.../select-kit/components/mini-tag-chooser.js.es6 | 5 +++--
.../select-kit/components/tag-chooser.js.es6 | 5 +++--
11 files changed, 39 insertions(+), 19 deletions(-)
diff --git a/app/assets/javascripts/admin/routes/admin-badges-show.js.es6 b/app/assets/javascripts/admin/routes/admin-badges-show.js.es6
index 5a94643d42..67acdcba58 100644
--- a/app/assets/javascripts/admin/routes/admin-badges-show.js.es6
+++ b/app/assets/javascripts/admin/routes/admin-badges-show.js.es6
@@ -15,7 +15,10 @@ export default Route.extend({
name: I18n.t("admin.badges.new_badge")
});
}
- return this.modelFor("adminBadges").findBy("id", parseInt(params.badge_id, 10));
+ return this.modelFor("adminBadges").findBy(
+ "id",
+ parseInt(params.badge_id, 10)
+ );
},
actions: {
diff --git a/app/assets/javascripts/discourse/components/composer-editor.js.es6 b/app/assets/javascripts/discourse/components/composer-editor.js.es6
index 6c6e92c074..1f9c2e08f1 100644
--- a/app/assets/javascripts/discourse/components/composer-editor.js.es6
+++ b/app/assets/javascripts/discourse/components/composer-editor.js.es6
@@ -822,8 +822,9 @@ export default Component.extend({
const index = parseInt(
$(e.target)
.parent()
- .attr("data-image-index")
- , 10);
+ .attr("data-image-index"),
+ 10
+ );
const scale = e.target.attributes["data-scale"].value;
const matchingPlaceholder = this.get("composer.reply").match(
diff --git a/app/assets/javascripts/discourse/components/emoji-picker.js.es6 b/app/assets/javascripts/discourse/components/emoji-picker.js.es6
index 6c8464bca3..fccf3c597f 100644
--- a/app/assets/javascripts/discourse/components/emoji-picker.js.es6
+++ b/app/assets/javascripts/discourse/components/emoji-picker.js.es6
@@ -442,7 +442,10 @@ export default Component.extend({
);
$diversityScales.on("click", event => {
const $selectedDiversity = $(event.currentTarget);
- this.set("selectedDiversity", parseInt($selectedDiversity.data("level"), 10));
+ this.set(
+ "selectedDiversity",
+ parseInt($selectedDiversity.data("level"), 10)
+ );
return false;
});
},
diff --git a/app/assets/javascripts/discourse/components/site-header.js.es6 b/app/assets/javascripts/discourse/components/site-header.js.es6
index 43253d7db3..38d42d9ea0 100644
--- a/app/assets/javascripts/discourse/components/site-header.js.es6
+++ b/app/assets/javascripts/discourse/components/site-header.js.es6
@@ -280,8 +280,7 @@ const SiteHeaderComponent = MountWidget.extend(Docking, PanEvents, {
const $panelBody = $(".panel-body", $panel);
// 2 pixel fudge allows for firefox subpixel sizing stuff causing scrollbar
- let contentHeight =
- $(".panel-body-contents", $panel).height() + 2;
+ let contentHeight = $(".panel-body-contents", $panel).height() + 2;
// We use a mutationObserver to check for style changes, so it's important
// we don't set it if it doesn't change. Same goes for the $panelBody!
diff --git a/app/assets/javascripts/discourse/helpers/application.js.es6 b/app/assets/javascripts/discourse/helpers/application.js.es6
index cff377e323..e6a88ded97 100644
--- a/app/assets/javascripts/discourse/helpers/application.js.es6
+++ b/app/assets/javascripts/discourse/helpers/application.js.es6
@@ -22,7 +22,10 @@ registerUnbound("number", (orig, params) => {
let title = I18n.toNumber(orig, { precision: 0 });
if (params.numberKey) {
- title = I18n.t(params.numberKey, { number: title, count: parseInt(orig, 10) });
+ title = I18n.t(params.numberKey, {
+ number: title,
+ count: parseInt(orig, 10)
+ });
}
let classNames = "number";
diff --git a/app/assets/javascripts/discourse/initializers/live-development.js.es6 b/app/assets/javascripts/discourse/initializers/live-development.js.es6
index 5cdbcb96ca..38afdbc9b7 100644
--- a/app/assets/javascripts/discourse/initializers/live-development.js.es6
+++ b/app/assets/javascripts/discourse/initializers/live-development.js.es6
@@ -13,7 +13,10 @@ export default {
window.location.search.indexOf("?preview_theme_id=") === 0
) {
// force preview theme id to always be carried along
- const themeId = parseInt(window.location.search.slice(18).split("&")[0], 10);
+ const themeId = parseInt(
+ window.location.search.slice(18).split("&")[0],
+ 10
+ );
if (!isNaN(themeId)) {
const patchState = function(f) {
const patched = window.history[f];
diff --git a/app/assets/javascripts/discourse/initializers/post-decorations.js.es6 b/app/assets/javascripts/discourse/initializers/post-decorations.js.es6
index 75ddbdfdae..35504de3bb 100644
--- a/app/assets/javascripts/discourse/initializers/post-decorations.js.es6
+++ b/app/assets/javascripts/discourse/initializers/post-decorations.js.es6
@@ -26,7 +26,10 @@ export default {
const players = $("audio", $elem);
if (players.length) {
players.on("play", () => {
- const postId = parseInt($elem.closest("article").data("post-id"), 10);
+ const postId = parseInt(
+ $elem.closest("article").data("post-id"),
+ 10
+ );
if (postId) {
api.preventCloak(postId);
}
diff --git a/app/assets/javascripts/discourse/lib/to-markdown.js.es6 b/app/assets/javascripts/discourse/lib/to-markdown.js.es6
index 0e71b585c5..7cd6a8ca49 100644
--- a/app/assets/javascripts/discourse/lib/to-markdown.js.es6
+++ b/app/assets/javascripts/discourse/lib/to-markdown.js.es6
@@ -321,8 +321,9 @@ export class Tag {
if (msoListClasses.includes(attrs.class)) {
try {
const level = parseInt(
- attrs.style.match(/level./)[0].replace("level", "")
- , 10);
+ attrs.style.match(/level./)[0].replace("level", ""),
+ 10
+ );
indent = Array(level).join("\t") + indent;
} finally {
if (attrs.class === "MsoListParagraphCxSpFirst") {
diff --git a/app/assets/javascripts/discourse/models/action-summary.js.es6 b/app/assets/javascripts/discourse/models/action-summary.js.es6
index 4d48ccf1bc..aad8b48b8a 100644
--- a/app/assets/javascripts/discourse/models/action-summary.js.es6
+++ b/app/assets/javascripts/discourse/models/action-summary.js.es6
@@ -60,11 +60,13 @@ export default RestModel.extend({
post.updateActionsSummary(data.result);
}
const remaining = parseInt(
- data.xhr.getResponseHeader("Discourse-Actions-Remaining") || 0
- , 10);
+ data.xhr.getResponseHeader("Discourse-Actions-Remaining") || 0,
+ 10
+ );
const max = parseInt(
- data.xhr.getResponseHeader("Discourse-Actions-Max") || 0
- , 10);
+ data.xhr.getResponseHeader("Discourse-Actions-Max") || 0,
+ 10
+ );
return { acted: true, remaining, max };
})
.catch(error => {
diff --git a/app/assets/javascripts/select-kit/components/mini-tag-chooser.js.es6 b/app/assets/javascripts/select-kit/components/mini-tag-chooser.js.es6
index 61f2539940..bc5d8c0b07 100644
--- a/app/assets/javascripts/select-kit/components/mini-tag-chooser.js.es6
+++ b/app/assets/javascripts/select-kit/components/mini-tag-chooser.js.es6
@@ -51,8 +51,9 @@ export default ComboBox.extend(TagsMixin, {
parseInt(
this.limit ||
this.maximum ||
- this.get("siteSettings.max_tags_per_topic")
- , 10)
+ this.get("siteSettings.max_tags_per_topic"),
+ 10
+ )
);
},
diff --git a/app/assets/javascripts/select-kit/components/tag-chooser.js.es6 b/app/assets/javascripts/select-kit/components/tag-chooser.js.es6
index 439a0ee05e..b0de97cd21 100644
--- a/app/assets/javascripts/select-kit/components/tag-chooser.js.es6
+++ b/app/assets/javascripts/select-kit/components/tag-chooser.js.es6
@@ -46,8 +46,9 @@ export default MultiSelectComponent.extend(TagsMixin, {
parseInt(
this.limit ||
this.maximum ||
- this.get("siteSettings.max_tags_per_topic")
- , 10)
+ this.get("siteSettings.max_tags_per_topic"),
+ 10
+ )
);
}
},
From 17bca006617524e911eee1d3f5f8ae341eb1a025 Mon Sep 17 00:00:00 2001
From: Jarek Radosz
Date: Tue, 12 Nov 2019 12:07:19 +0100
Subject: [PATCH 085/408] DEV: Run prettier
---
.../lazy-yt/assets/javascripts/initializers/lazyYT.js.es6 | 5 ++++-
1 file changed, 4 insertions(+), 1 deletion(-)
diff --git a/plugins/lazy-yt/assets/javascripts/initializers/lazyYT.js.es6 b/plugins/lazy-yt/assets/javascripts/initializers/lazyYT.js.es6
index 4afe9a0775..3d913e77c0 100644
--- a/plugins/lazy-yt/assets/javascripts/initializers/lazyYT.js.es6
+++ b/plugins/lazy-yt/assets/javascripts/initializers/lazyYT.js.es6
@@ -14,7 +14,10 @@ export default {
$(".lazyYT", $elem).lazyYT({
onPlay(e, $el) {
// don't cloak posts that have playing videos in them
- const postId = parseInt($el.closest("article").data("post-id"), 10);
+ const postId = parseInt(
+ $el.closest("article").data("post-id"),
+ 10
+ );
if (postId) {
api.preventCloak(postId);
}
From 241d9a3034aa628282d34d71fc7f75b6519ef615 Mon Sep 17 00:00:00 2001
From: Daniel Waterworth
Date: Tue, 12 Nov 2019 11:26:21 +0000
Subject: [PATCH 086/408] FIX: Topic lists filtered by tag and a specified
filter don't work
This was a regression caused by 59241df2
---
app/assets/javascripts/discourse/routes/app-route-map.js.es6 | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/app/assets/javascripts/discourse/routes/app-route-map.js.es6 b/app/assets/javascripts/discourse/routes/app-route-map.js.es6
index 1da84b4047..ba43395d9e 100644
--- a/app/assets/javascripts/discourse/routes/app-route-map.js.es6
+++ b/app/assets/javascripts/discourse/routes/app-route-map.js.es6
@@ -212,7 +212,7 @@ export default function() {
path: "/c/:category/:tag_id/l/" + filter
});
this.route("showCategoryNone" + filter.capitalize(), {
- path: "/c/:category/:tag_id/l/" + filter
+ path: "/c/:category/none/:tag_id/l/" + filter
});
this.route("showParentCategory" + filter.capitalize(), {
path: "/c/:parent_category/:category/:tag_id/l/" + filter
From bbcce087128dcc263c456c7fda91eaba384768cd Mon Sep 17 00:00:00 2001
From: Dan Ungureanu
Date: Tue, 12 Nov 2019 15:16:39 +0200
Subject: [PATCH 087/408] FIX: Update quotes after moving posts (#8326)
---
app/models/post_mover.rb | 13 +++++++++++++
spec/models/post_mover_spec.rb | 21 +++++++++++++++++++++
2 files changed, 34 insertions(+)
diff --git a/app/models/post_mover.rb b/app/models/post_mover.rb
index 2cd39b80ae..facccc8ebd 100644
--- a/app/models/post_mover.rb
+++ b/app/models/post_mover.rb
@@ -126,6 +126,7 @@ class PostMover
move_incoming_emails
move_notifications
update_reply_counts
+ update_quotes
move_first_post_replies
delete_post_replies
copy_first_post_timings
@@ -256,6 +257,18 @@ class PostMover
SQL
end
+ def update_quotes
+ DB.exec <<~SQL
+ UPDATE posts p
+ SET raw = REPLACE(p.raw,
+ ', post:' || mp.old_post_number || ', topic:' || mp.old_topic_id,
+ ', post:' || mp.new_post_number || ', topic:' || mp.new_topic_id),
+ baked_version = NULL
+ FROM moved_posts mp, quoted_posts qp
+ WHERE p.id = qp.post_id AND mp.old_post_id = qp.quoted_post_id
+ SQL
+ end
+
def move_first_post_replies
DB.exec <<~SQL
UPDATE post_replies pr
diff --git a/spec/models/post_mover_spec.rb b/spec/models/post_mover_spec.rb
index 78c1cc72ad..42cf45098c 100644
--- a/spec/models/post_mover_spec.rb
+++ b/spec/models/post_mover_spec.rb
@@ -90,6 +90,27 @@ describe PostMover do
expect(move_message.post_type).to eq(Post.types[:small_action])
expect(move_message.raw).to include("3 posts were split")
end
+
+ it "correctly remaps quotes" do
+ raw = <<~RAW
+ [quote="dan, post:#{p2.post_number}, topic:#{p2.topic_id}, full:true"]
+ some quote from the other post
+ [/quote]
+
+ the quote above should be updated with new post number and topic id
+ RAW
+
+ p3.update!(raw: raw)
+ p3.rebake!
+
+ expect { topic.move_posts(user, [p2.id], title: "new testing topic name") }
+ .to change { p2.reload.topic_id }
+ .and change { p2.post_number }
+ .and change { p3.reload.raw }
+ .and change { p3.baked_version }.to nil
+
+ expect(p3.raw).to include("post:#{p2.post_number}, topic:#{p2.topic_id}")
+ end
end
context "errors" do
From 5f927ceeb379f710cd42fa268e9967dcc2ce207d Mon Sep 17 00:00:00 2001
From: David Taylor
Date: Tue, 12 Nov 2019 14:30:19 +0000
Subject: [PATCH 088/408] DEV: Display a warning when themes hard-code
optimized image links (#8304)
---
app/models/theme_field.rb | 12 +++++++++++-
config/locales/server.en.yml | 1 +
spec/models/theme_field_spec.rb | 24 ++++++++++++++++++++++++
3 files changed, 36 insertions(+), 1 deletion(-)
diff --git a/app/models/theme_field.rb b/app/models/theme_field.rb
index 38c19da7bb..fe4e0bf644 100644
--- a/app/models/theme_field.rb
+++ b/app/models/theme_field.rb
@@ -71,6 +71,8 @@ class ThemeField < ActiveRecord::Base
errors = []
javascript_cache || build_javascript_cache
+ errors << I18n.t("themes.errors.optimized_link") if contains_optimized_link?(html)
+
js_compiler = ThemeJavascriptCompiler.new(theme_id, self.theme.name)
doc = Nokogiri::HTML.fragment(html)
@@ -355,7 +357,11 @@ class ThemeField < ActiveRecord::Base
result = ["failed"]
begin
result = compile_scss
- self.error = nil unless error.nil?
+ if contains_optimized_link?(self.value)
+ self.error = I18n.t("themes.errors.optimized_link")
+ else
+ self.error = nil unless error.nil?
+ end
rescue SassC::SyntaxError => e
self.error = e.message unless self.destroyed?
end
@@ -367,6 +373,10 @@ class ThemeField < ActiveRecord::Base
Theme.targets[target_id].to_s
end
+ def contains_optimized_link?(text)
+ OptimizedImage::URL_REGEX.match?(text)
+ end
+
class ThemeFileMatcher
OPTIONS = %i{name type target}
# regex: used to match file names to fields (import).
diff --git a/config/locales/server.en.yml b/config/locales/server.en.yml
index 6d3cefe305..2945673db6 100644
--- a/config/locales/server.en.yml
+++ b/config/locales/server.en.yml
@@ -92,6 +92,7 @@ en:
component_no_default: "Theme components can't be default theme"
component_no_color_scheme: "Theme components can't have color palettes"
no_multilevels_components: "Themes with child themes can't be child themes themselves"
+ optimized_link: Optimized image links are ephemeral and should not be included in theme source code.
settings_errors:
invalid_yaml: "Provided YAML is invalid."
data_type_not_a_number: "Setting `%{name}` type is unsupported. Supported types are `integer`, `bool`, `list` and `enum`"
diff --git a/spec/models/theme_field_spec.rb b/spec/models/theme_field_spec.rb
index 5506305924..c6fc9c5764 100644
--- a/spec/models/theme_field_spec.rb
+++ b/spec/models/theme_field_spec.rb
@@ -34,6 +34,30 @@ describe ThemeField do
expect(theme_field.value_baked).to_not include('
+ HTML
+ theme_field.ensure_baked!
+ expect(theme_field.error).to include(I18n.t("themes.errors.optimized_link"))
+
+ theme_field = ThemeField.create!(theme_id: 1, target_id: 0, name: "scss", value: <<~SCSS)
+ body {
+ background: url(http://mysite.invalid/uploads/default/optimized/1X/6d749a141f513f88f167e750e528515002043da1_2_1282x1000.png);
+ }
+ SCSS
+ theme_field.ensure_baked!
+ expect(theme_field.error).to include(I18n.t("themes.errors.optimized_link"))
+
+ theme_field.update(value: <<~SCSS)
+ body {
+ background: url(http://notdiscourse.invalid/optimized/my_image.png);
+ }
+ SCSS
+ theme_field.ensure_baked!
+ expect(theme_field.error).to eq(nil)
+ end
+
it 'only extracts inline javascript to an external file' do
html = <<~HTML
'>.