Compare commits
1
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
3ca4398bad |
@@ -1,4 +1,2 @@
|
||||
< 3.4.0.beta2-dev: 7685ebf396c93e8accc5a76a81fcec4384a73fa3
|
||||
< 3.4.0.beta1-dev: da38a4c053b68d7076db4441cfe86b473979945d
|
||||
< 3.3.0.beta1-dev: 062efc8a547c19474eaeefae464837d63a5e5fb3
|
||||
3.1.999: 30c49eb50d6d16fcf82bace3da0e1972b7b220c0
|
||||
|
||||
|
||||
@@ -0,0 +1 @@
|
||||
module.exports = require("@discourse/lint-configs/eslint");
|
||||
+21
-54
@@ -1,87 +1,54 @@
|
||||
GEM
|
||||
remote: https://rubygems.org/
|
||||
specs:
|
||||
activesupport (7.1.3.3)
|
||||
base64
|
||||
bigdecimal
|
||||
concurrent-ruby (~> 1.0, >= 1.0.2)
|
||||
connection_pool (>= 2.2.5)
|
||||
drb
|
||||
i18n (>= 1.6, < 2)
|
||||
minitest (>= 5.1)
|
||||
mutex_m
|
||||
tzinfo (~> 2.0)
|
||||
ast (2.4.2)
|
||||
base64 (0.2.0)
|
||||
bigdecimal (3.1.8)
|
||||
concurrent-ruby (1.2.3)
|
||||
connection_pool (2.4.1)
|
||||
drb (2.2.1)
|
||||
i18n (1.14.5)
|
||||
concurrent-ruby (~> 1.0)
|
||||
json (2.7.2)
|
||||
json (2.6.3)
|
||||
language_server-protocol (3.17.0.3)
|
||||
minitest (5.23.1)
|
||||
mutex_m (0.2.0)
|
||||
parallel (1.24.0)
|
||||
parser (3.3.1.0)
|
||||
parallel (1.23.0)
|
||||
parser (3.2.2.4)
|
||||
ast (~> 2.4.1)
|
||||
racc
|
||||
prettier_print (1.2.1)
|
||||
racc (1.8.0)
|
||||
rack (3.0.11)
|
||||
racc (1.7.3)
|
||||
rainbow (3.1.1)
|
||||
regexp_parser (2.9.2)
|
||||
rexml (3.3.9)
|
||||
rubocop (1.64.0)
|
||||
regexp_parser (2.8.2)
|
||||
rexml (3.2.6)
|
||||
rubocop (1.57.2)
|
||||
json (~> 2.3)
|
||||
language_server-protocol (>= 3.17.0)
|
||||
parallel (~> 1.10)
|
||||
parser (>= 3.3.0.2)
|
||||
parser (>= 3.2.2.4)
|
||||
rainbow (>= 2.2.2, < 4.0)
|
||||
regexp_parser (>= 1.8, < 3.0)
|
||||
rexml (>= 3.2.5, < 4.0)
|
||||
rubocop-ast (>= 1.31.1, < 2.0)
|
||||
rubocop-ast (>= 1.28.1, < 2.0)
|
||||
ruby-progressbar (~> 1.7)
|
||||
unicode-display_width (>= 2.4.0, < 3.0)
|
||||
rubocop-ast (1.31.3)
|
||||
parser (>= 3.3.1.0)
|
||||
rubocop-capybara (2.20.0)
|
||||
rubocop-ast (1.30.0)
|
||||
parser (>= 3.2.1.0)
|
||||
rubocop-capybara (2.19.0)
|
||||
rubocop (~> 1.41)
|
||||
rubocop-discourse (3.8.0)
|
||||
activesupport (>= 6.1)
|
||||
rubocop (>= 1.59.0)
|
||||
rubocop-capybara (>= 2.0.0)
|
||||
rubocop-factory_bot (>= 2.0.0)
|
||||
rubocop-rails (>= 2.25.0)
|
||||
rubocop-rspec (>= 2.25.0)
|
||||
rubocop-factory_bot (2.25.1)
|
||||
rubocop (~> 1.41)
|
||||
rubocop-rails (2.25.0)
|
||||
activesupport (>= 4.2.0)
|
||||
rack (>= 1.1)
|
||||
rubocop (>= 1.33.0, < 2.0)
|
||||
rubocop-ast (>= 1.31.1, < 2.0)
|
||||
rubocop-rspec (2.29.2)
|
||||
rubocop-discourse (3.4.0)
|
||||
rubocop (>= 1.1.0)
|
||||
rubocop-rspec (>= 2.0.0)
|
||||
rubocop-factory_bot (2.24.0)
|
||||
rubocop (~> 1.33)
|
||||
rubocop-rspec (2.25.0)
|
||||
rubocop (~> 1.40)
|
||||
rubocop-capybara (~> 2.17)
|
||||
rubocop-factory_bot (~> 2.22)
|
||||
rubocop-rspec_rails (~> 2.28)
|
||||
rubocop-rspec_rails (2.28.3)
|
||||
rubocop (~> 1.40)
|
||||
ruby-progressbar (1.13.0)
|
||||
syntax_tree (6.2.0)
|
||||
prettier_print (>= 1.2.0)
|
||||
tzinfo (2.0.6)
|
||||
concurrent-ruby (~> 1.0)
|
||||
unicode-display_width (2.5.0)
|
||||
|
||||
PLATFORMS
|
||||
ruby
|
||||
arm64-darwin-21
|
||||
x86_64-linux
|
||||
|
||||
DEPENDENCIES
|
||||
rubocop-discourse
|
||||
syntax_tree
|
||||
|
||||
BUNDLED WITH
|
||||
2.5.10
|
||||
2.4.21
|
||||
|
||||
@@ -1,7 +0,0 @@
|
||||
import CategorySelector from "select-kit/components/category-selector";
|
||||
|
||||
export default class HouseAdsCategorySelector extends CategorySelector {
|
||||
get value() {
|
||||
return this.selectedCategories.map((c) => c.id);
|
||||
}
|
||||
}
|
||||
@@ -1,44 +1,42 @@
|
||||
import { action, computed } from "@ember/object";
|
||||
import { classNames } from "@ember-decorators/component";
|
||||
import { makeArray } from "discourse-common/lib/helpers";
|
||||
import Ember from "ember";
|
||||
import MultiSelectComponent from "select-kit/components/multi-select";
|
||||
const { makeArray } = Ember;
|
||||
import { computed } from "@ember/object";
|
||||
|
||||
@classNames("house-ads-chooser")
|
||||
export default class HouseAdsChooser extends MultiSelectComponent {
|
||||
filterable = true;
|
||||
filterPlaceholder = "admin.adplugin.house_ads.filter_placeholder";
|
||||
tokenSeparator = "|";
|
||||
allowCreate = false;
|
||||
allowAny = false;
|
||||
settingValue = "";
|
||||
valueAttribute = null;
|
||||
nameProperty = null;
|
||||
export default MultiSelectComponent.extend({
|
||||
classNames: ["house-ads-chooser"],
|
||||
filterable: true,
|
||||
filterPlaceholder: "admin.adplugin.house_ads.filter_placeholder",
|
||||
tokenSeparator: "|",
|
||||
allowCreate: false,
|
||||
allowAny: false,
|
||||
settingValue: "",
|
||||
valueAttribute: null,
|
||||
nameProperty: null,
|
||||
|
||||
@computed("settingValue")
|
||||
get value() {
|
||||
value: computed("settingValue", function () {
|
||||
return this.settingValue
|
||||
.toString()
|
||||
.split(this.tokenSeparator)
|
||||
.filter(Boolean);
|
||||
}
|
||||
}),
|
||||
|
||||
// TODO: kept for legacy, remove when Discourse is 2.5
|
||||
mutateValues(values) {
|
||||
this.set("settingValue", values.join(this.tokenSeparator));
|
||||
}
|
||||
|
||||
},
|
||||
computeValues() {
|
||||
return this.settingValue.split(this.tokenSeparator).filter(Boolean);
|
||||
}
|
||||
},
|
||||
|
||||
@computed("choices")
|
||||
get content() {
|
||||
content: computed("choices", function () {
|
||||
return makeArray(this.choices);
|
||||
}
|
||||
}),
|
||||
|
||||
@action
|
||||
onChange(value) {
|
||||
const settingValue = makeArray(value).join(this.tokenSeparator);
|
||||
this.onChange?.(settingValue);
|
||||
}
|
||||
}
|
||||
actions: {
|
||||
onChange(value) {
|
||||
const settingValue = makeArray(value).join(this.tokenSeparator);
|
||||
this.attrs.onChange && this.attrs.onChange(settingValue);
|
||||
},
|
||||
},
|
||||
});
|
||||
|
||||
@@ -1,13 +1,13 @@
|
||||
<label for={{this.name}}>{{this.title}}</label>
|
||||
<label for={{name}}>{{title}}</label>
|
||||
{{house-ads-chooser
|
||||
settingValue=this.adValue
|
||||
choices=this.adNames
|
||||
onChange=(action (mut this.adValue))
|
||||
settingValue=adValue
|
||||
choices=adNames
|
||||
onChange=(action (mut adValue))
|
||||
}}
|
||||
<div class="setting-controls">
|
||||
{{#if this.changed}}
|
||||
{{#if changed}}
|
||||
<DButton class="ok" @action={{action "save"}} @icon="check" />
|
||||
<DButton class="cancel" @action={{action "cancel"}} @icon="times" />
|
||||
{{/if}}
|
||||
</div>
|
||||
<p class="help">{{this.help}}</p>
|
||||
<p class="help">{{help}}</p>
|
||||
@@ -1,8 +1,7 @@
|
||||
import { mapBy } from "@ember/object/computed";
|
||||
import { classNames } from "@ember-decorators/component";
|
||||
import HouseAdsSetting from "discourse/plugins/discourse-adplugin/discourse/components/house-ads-setting";
|
||||
|
||||
@classNames("house-ads-setting house-ads-list-setting")
|
||||
export default class HouseAdsListSetting extends HouseAdsSetting {
|
||||
@mapBy("allAds", "name") adNames;
|
||||
}
|
||||
export default HouseAdsSetting.extend({
|
||||
classNames: "house-ads-setting house-ads-list-setting",
|
||||
adNames: mapBy("allAds", "name"),
|
||||
});
|
||||
|
||||
@@ -1,9 +1,9 @@
|
||||
<label for={{this.name}}>{{this.title}}</label>
|
||||
<TextField @value={{this.adValue}} @classNames="house-ads-text-input" />
|
||||
<label for={{name}}>{{title}}</label>
|
||||
<TextField @value={{adValue}} @classNames="house-ads-text-input" />
|
||||
<div class="setting-controls">
|
||||
{{#if this.changed}}
|
||||
{{#if changed}}
|
||||
<DButton class="ok" @action={{action "save"}} @icon="check" />
|
||||
<DButton class="cancel" @action={{action "cancel"}} @icon="times" />
|
||||
{{/if}}
|
||||
</div>
|
||||
<p class="help">{{this.help}}</p>
|
||||
<p class="help">{{help}}</p>
|
||||
@@ -1,58 +1,58 @@
|
||||
import Component from "@ember/component";
|
||||
import { action } from "@ember/object";
|
||||
import { classNames } from "@ember-decorators/component";
|
||||
import { ajax } from "discourse/lib/ajax";
|
||||
import { popupAjaxError } from "discourse/lib/ajax-error";
|
||||
import { i18n, propertyNotEqual } from "discourse/lib/computed";
|
||||
import I18n from "I18n";
|
||||
|
||||
@classNames("house-ads-setting")
|
||||
export default class HouseAdsSetting extends Component {
|
||||
adValue = "";
|
||||
saving = false;
|
||||
savingStatus = "";
|
||||
|
||||
@i18n("name", "admin.adplugin.house_ads.%@.title") title;
|
||||
@i18n("name", "admin.adplugin.house_ads.%@.description") help;
|
||||
@propertyNotEqual("adValue", "value") changed;
|
||||
export default Component.extend({
|
||||
classNames: "house-ads-setting",
|
||||
adValue: "",
|
||||
saving: false,
|
||||
savingStatus: "",
|
||||
title: i18n("name", "admin.adplugin.house_ads.%@.title"),
|
||||
help: i18n("name", "admin.adplugin.house_ads.%@.description"),
|
||||
changed: propertyNotEqual("adValue", "value"),
|
||||
|
||||
init() {
|
||||
super.init(...arguments);
|
||||
this._super(...arguments);
|
||||
this.set("adValue", this.get("value"));
|
||||
}
|
||||
},
|
||||
|
||||
@action
|
||||
save() {
|
||||
if (!this.get("saving")) {
|
||||
this.setProperties({
|
||||
saving: true,
|
||||
savingStatus: I18n.t("saving"),
|
||||
});
|
||||
|
||||
ajax(`/admin/plugins/pluginad/house_settings/${this.get("name")}.json`, {
|
||||
type: "PUT",
|
||||
data: { value: this.get("adValue") },
|
||||
})
|
||||
.then(() => {
|
||||
const adSettings = this.get("adSettings");
|
||||
adSettings.set(this.get("name"), this.get("adValue"));
|
||||
this.setProperties({
|
||||
value: this.get("adValue"),
|
||||
savingStatus: I18n.t("saved"),
|
||||
});
|
||||
})
|
||||
.catch(popupAjaxError)
|
||||
.finally(() => {
|
||||
this.setProperties({
|
||||
saving: false,
|
||||
savingStatus: "",
|
||||
});
|
||||
actions: {
|
||||
save() {
|
||||
if (!this.get("saving")) {
|
||||
this.setProperties({
|
||||
saving: true,
|
||||
savingStatus: I18n.t("saving"),
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@action
|
||||
cancel() {
|
||||
this.set("adValue", this.get("value"));
|
||||
}
|
||||
}
|
||||
ajax(
|
||||
`/admin/plugins/pluginad/house_settings/${this.get("name")}.json`,
|
||||
{
|
||||
type: "PUT",
|
||||
data: { value: this.get("adValue") },
|
||||
}
|
||||
)
|
||||
.then(() => {
|
||||
const adSettings = this.get("adSettings");
|
||||
adSettings.set(this.get("name"), this.get("adValue"));
|
||||
this.setProperties({
|
||||
value: this.get("adValue"),
|
||||
savingStatus: I18n.t("saved"),
|
||||
});
|
||||
})
|
||||
.catch(popupAjaxError)
|
||||
.finally(() => {
|
||||
this.setProperties({
|
||||
saving: false,
|
||||
savingStatus: "",
|
||||
});
|
||||
});
|
||||
}
|
||||
},
|
||||
|
||||
cancel() {
|
||||
this.set("adValue", this.get("value"));
|
||||
},
|
||||
},
|
||||
});
|
||||
|
||||
@@ -1,18 +0,0 @@
|
||||
import { htmlSafe } from "@ember/template";
|
||||
import DModal from "discourse/components/d-modal";
|
||||
import i18n from "discourse-common/helpers/i18n";
|
||||
|
||||
const Preview = <template>
|
||||
<DModal
|
||||
@closeModal={{@closeModal}}
|
||||
@title={{i18n "admin.adplugin.house_ads.preview"}}
|
||||
>
|
||||
<:body>
|
||||
<div class="house-ad-preview">
|
||||
{{htmlSafe @model.html}}
|
||||
</div>
|
||||
</:body>
|
||||
</DModal>
|
||||
</template>;
|
||||
|
||||
export default Preview;
|
||||
@@ -1,8 +1,8 @@
|
||||
import Controller, { inject as controller } from "@ember/controller";
|
||||
import { alias } from "@ember/object/computed";
|
||||
|
||||
export default class AdminPluginsHouseAdsIndexController extends Controller {
|
||||
@controller("adminPlugins.houseAds") adminPluginsHouseAds;
|
||||
@alias("adminPluginsHouseAds.model") houseAds;
|
||||
@alias("adminPluginsHouseAds.houseAdsSettings") adSettings;
|
||||
}
|
||||
export default Controller.extend({
|
||||
adminPluginsHouseAds: controller("adminPlugins.houseAds"),
|
||||
houseAds: alias("adminPluginsHouseAds.model"),
|
||||
adSettings: alias("adminPluginsHouseAds.houseAdsSettings"),
|
||||
});
|
||||
|
||||
@@ -1,156 +1,113 @@
|
||||
import { tracked } from "@glimmer/tracking";
|
||||
import Controller, { inject as controller } from "@ember/controller";
|
||||
import EmberObject, { action } from "@ember/object";
|
||||
import { service } from "@ember/service";
|
||||
import { TrackedObject } from "@ember-compat/tracked-built-ins";
|
||||
import { observes } from "@ember-decorators/object";
|
||||
import { not, or } from "@ember/object/computed";
|
||||
import { ajax } from "discourse/lib/ajax";
|
||||
import { popupAjaxError } from "discourse/lib/ajax-error";
|
||||
import Category from "discourse/models/category";
|
||||
import { propertyNotEqual } from "discourse/lib/computed";
|
||||
import { bufferedProperty } from "discourse/mixins/buffered-content";
|
||||
import I18n from "I18n";
|
||||
import Preview from "../components/modal/preview";
|
||||
|
||||
export default class adminPluginsHouseAdsShow extends Controller {
|
||||
@service router;
|
||||
@service modal;
|
||||
export default Controller.extend(bufferedProperty("model"), {
|
||||
adminPluginsHouseAds: controller("adminPlugins.houseAds"),
|
||||
|
||||
@controller("adminPlugins.houseAds") houseAdsController;
|
||||
saving: false,
|
||||
savingStatus: "",
|
||||
|
||||
@tracked selectedCategories = [];
|
||||
@tracked selectedGroups = [];
|
||||
@tracked saving = false;
|
||||
@tracked savingStatus = "";
|
||||
@tracked buffered;
|
||||
nameDirty: propertyNotEqual("buffered.name", "model.name"),
|
||||
htmlDirty: propertyNotEqual("buffered.html", "model.html"),
|
||||
visibleToAnonsDirty: propertyNotEqual(
|
||||
"buffered.visible_to_anons",
|
||||
"model.visible_to_anons"
|
||||
),
|
||||
visibleToLoggedInDirty: propertyNotEqual(
|
||||
"buffered.visible_to_logged_in_users",
|
||||
"model.visible_to_logged_in_users"
|
||||
),
|
||||
dirty: or(
|
||||
"nameDirty",
|
||||
"htmlDirty",
|
||||
"visibleToLoggedInDirty",
|
||||
"visibleToAnonsDirty"
|
||||
),
|
||||
disableSave: not("dirty"),
|
||||
|
||||
@observes("model")
|
||||
modelChanged() {
|
||||
this.buffered = new TrackedObject({ ...this.model });
|
||||
this.selectedCategories = this.model.categories || [];
|
||||
this.selectedGroups = this.model.group_ids || [];
|
||||
}
|
||||
actions: {
|
||||
save() {
|
||||
if (!this.get("saving")) {
|
||||
this.setProperties({
|
||||
saving: true,
|
||||
savingStatus: I18n.t("saving"),
|
||||
});
|
||||
|
||||
get disabledSave() {
|
||||
for (const key in this.buffered) {
|
||||
// we don't want to compare the categories array
|
||||
if (key !== "categories" && this.buffered[key] !== this.model[key]) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
const data = {},
|
||||
buffered = this.get("buffered"),
|
||||
newRecord = !buffered.get("id");
|
||||
|
||||
@action
|
||||
async save() {
|
||||
if (!this.saving) {
|
||||
this.saving = true;
|
||||
this.savingStatus = I18n.t("saving");
|
||||
const data = {};
|
||||
const newRecord = !this.buffered.id;
|
||||
if (!newRecord) {
|
||||
data.id = this.buffered.id;
|
||||
}
|
||||
data.name = this.buffered.name;
|
||||
data.html = this.buffered.html;
|
||||
data.visible_to_logged_in_users =
|
||||
this.buffered.visible_to_logged_in_users;
|
||||
data.visible_to_anons = this.buffered.visible_to_anons;
|
||||
data.category_ids = this.buffered.category_ids;
|
||||
data.group_ids = this.buffered.group_ids;
|
||||
try {
|
||||
const ajaxData = await ajax(
|
||||
if (!newRecord) {
|
||||
data.id = buffered.get("id");
|
||||
}
|
||||
data.name = buffered.get("name");
|
||||
data.html = buffered.get("html");
|
||||
data.visible_to_logged_in_users = buffered.get(
|
||||
"visible_to_logged_in_users"
|
||||
);
|
||||
data.visible_to_anons = buffered.get("visible_to_anons");
|
||||
|
||||
ajax(
|
||||
newRecord
|
||||
? `/admin/plugins/pluginad/house_creatives`
|
||||
: `/admin/plugins/pluginad/house_creatives/${this.buffered.id}`,
|
||||
: `/admin/plugins/pluginad/house_creatives/${buffered.get("id")}`,
|
||||
{
|
||||
type: newRecord ? "POST" : "PUT",
|
||||
data,
|
||||
}
|
||||
);
|
||||
this.savingStatus = I18n.t("saved");
|
||||
const houseAds = this.houseAdsController.model;
|
||||
if (newRecord) {
|
||||
this.buffered.id = ajaxData.house_ad.id;
|
||||
if (!houseAds.includes(this.buffered)) {
|
||||
houseAds.pushObject(EmberObject.create(this.buffered));
|
||||
}
|
||||
this.router.transitionTo(
|
||||
"adminPlugins.houseAds.show",
|
||||
this.buffered.id
|
||||
);
|
||||
} else {
|
||||
houseAds
|
||||
.find((ad) => ad.id === this.buffered.id)
|
||||
.setProperties(this.buffered);
|
||||
}
|
||||
} catch (error) {
|
||||
popupAjaxError(error);
|
||||
} finally {
|
||||
this.set("model", this.buffered);
|
||||
this.saving = false;
|
||||
this.savingStatus = "";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@action
|
||||
setCategoryIds(categoryArray) {
|
||||
this.selectedCategories = categoryArray;
|
||||
this.buffered.category_ids = categoryArray.map((c) => c.id);
|
||||
this.setCategoriesForBuffered();
|
||||
}
|
||||
|
||||
@action
|
||||
setGroupIds(groupIds) {
|
||||
this.selectedGroups = groupIds;
|
||||
this.buffered.group_ids = groupIds.map((id) => id);
|
||||
}
|
||||
|
||||
@action
|
||||
cancel() {
|
||||
this.buffered = new TrackedObject({ ...this.model });
|
||||
this.selectedCategories = this.model.categories || [];
|
||||
this.selectedGroups = this.model.group_ids || [];
|
||||
this.setCategoriesForBuffered();
|
||||
}
|
||||
|
||||
@action
|
||||
async destroy() {
|
||||
if (!this.buffered.id) {
|
||||
this.router.transitionTo("adminPlugins.houseAds.index");
|
||||
return;
|
||||
}
|
||||
try {
|
||||
await ajax(
|
||||
`/admin/plugins/pluginad/house_creatives/${this.buffered.id}`,
|
||||
{
|
||||
type: "DELETE",
|
||||
}
|
||||
);
|
||||
this.houseAdsController.model.removeObject(
|
||||
this.houseAdsController.model.findBy("id", this.buffered.id)
|
||||
);
|
||||
this.router.transitionTo("adminPlugins.houseAds.index");
|
||||
} catch (error) {
|
||||
popupAjaxError(error);
|
||||
}
|
||||
}
|
||||
|
||||
@action
|
||||
openPreview() {
|
||||
this.modal.show(Preview, {
|
||||
model: {
|
||||
html: this.buffered.html,
|
||||
},
|
||||
});
|
||||
}
|
||||
|
||||
setCategoriesForBuffered() {
|
||||
// we need to fetch the categories because the serializer is not being used
|
||||
// to attach the category object to the house ads
|
||||
this.buffered.categories = this.buffered.category_ids
|
||||
? this.buffered.category_ids.map((categoryId) =>
|
||||
Category.findById(categoryId)
|
||||
)
|
||||
: [];
|
||||
}
|
||||
}
|
||||
.then((ajaxData) => {
|
||||
this.commitBuffer();
|
||||
this.set("savingStatus", I18n.t("saved"));
|
||||
if (newRecord) {
|
||||
const model = this.get("model");
|
||||
model.set("id", ajaxData.house_ad.id);
|
||||
const houseAds = this.get("adminPluginsHouseAds.model");
|
||||
if (!houseAds.includes(model)) {
|
||||
houseAds.pushObject(model);
|
||||
}
|
||||
this.transitionToRoute(
|
||||
"adminPlugins.houseAds.show",
|
||||
model.get("id")
|
||||
);
|
||||
}
|
||||
})
|
||||
.catch(popupAjaxError)
|
||||
.finally(() => {
|
||||
this.setProperties({
|
||||
saving: false,
|
||||
savingStatus: "",
|
||||
});
|
||||
});
|
||||
}
|
||||
},
|
||||
|
||||
cancel() {
|
||||
this.rollbackBuffer();
|
||||
},
|
||||
|
||||
destroy() {
|
||||
const houseAds = this.get("adminPluginsHouseAds.model");
|
||||
const model = this.get("model");
|
||||
|
||||
if (!model.get("id")) {
|
||||
this.transitionToRoute("adminPlugins.houseAds.index");
|
||||
return;
|
||||
}
|
||||
|
||||
ajax(`/admin/plugins/pluginad/house_creatives/${model.get("id")}`, {
|
||||
type: "DELETE",
|
||||
})
|
||||
.then(() => {
|
||||
houseAds.removeObject(model);
|
||||
this.transitionToRoute("adminPlugins.houseAds.index");
|
||||
})
|
||||
.catch(popupAjaxError);
|
||||
},
|
||||
},
|
||||
});
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
import Controller from "@ember/controller";
|
||||
|
||||
export default class AdminPluginsHouseAdsController extends Controller {
|
||||
loadingAds = true;
|
||||
}
|
||||
export default Controller.extend({
|
||||
loadingAds: true,
|
||||
});
|
||||
|
||||
@@ -1,12 +1,9 @@
|
||||
import { action } from "@ember/object";
|
||||
import { service } from "@ember/service";
|
||||
import DiscourseRoute from "discourse/routes/discourse";
|
||||
|
||||
export default class AdminPluginsHouseAdsIndex extends DiscourseRoute {
|
||||
@service router;
|
||||
|
||||
export default DiscourseRoute.extend({
|
||||
@action
|
||||
moreSettings() {
|
||||
this.router.transitionTo("adminSiteSettingsCategory", "ad_plugin");
|
||||
}
|
||||
}
|
||||
this.transitionTo("adminSiteSettingsCategory", "ad_plugin");
|
||||
},
|
||||
});
|
||||
|
||||
@@ -1,23 +1,21 @@
|
||||
import { TrackedObject } from "@ember-compat/tracked-built-ins";
|
||||
import EmberObject from "@ember/object";
|
||||
import DiscourseRoute from "discourse/routes/discourse";
|
||||
import I18n from "I18n";
|
||||
|
||||
export default class AdminPluginsHouseAdsShow extends DiscourseRoute {
|
||||
export default DiscourseRoute.extend({
|
||||
model(params) {
|
||||
if (params.ad_id === "new") {
|
||||
return new TrackedObject({
|
||||
return EmberObject.create({
|
||||
name: I18n.t("admin.adplugin.house_ads.new_name"),
|
||||
html: "",
|
||||
visible_to_logged_in_users: true,
|
||||
visible_to_anons: true,
|
||||
});
|
||||
} else {
|
||||
return new TrackedObject(
|
||||
this.modelFor("adminPlugins.houseAds").findBy(
|
||||
"id",
|
||||
parseInt(params.ad_id, 10)
|
||||
)
|
||||
return this.modelFor("adminPlugins.houseAds").findBy(
|
||||
"id",
|
||||
parseInt(params.ad_id, 10)
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
});
|
||||
|
||||
@@ -2,15 +2,15 @@ import EmberObject from "@ember/object";
|
||||
import { ajax } from "discourse/lib/ajax";
|
||||
import DiscourseRoute from "discourse/routes/discourse";
|
||||
|
||||
export default class AdminPluginsHouseAds extends DiscourseRoute {
|
||||
settings = null;
|
||||
export default DiscourseRoute.extend({
|
||||
settings: null,
|
||||
|
||||
model() {
|
||||
return ajax("/admin/plugins/pluginad/house_creatives.json").then((data) => {
|
||||
this.set("settings", EmberObject.create(data.settings));
|
||||
return data.house_ads.map((ad) => EmberObject.create(ad));
|
||||
});
|
||||
}
|
||||
},
|
||||
|
||||
setupController(controller, model) {
|
||||
controller.setProperties({
|
||||
@@ -18,5 +18,5 @@ export default class AdminPluginsHouseAds extends DiscourseRoute {
|
||||
houseAdsSettings: this.get("settings"),
|
||||
loadingAds: false,
|
||||
});
|
||||
}
|
||||
}
|
||||
},
|
||||
});
|
||||
|
||||
@@ -1,51 +1,51 @@
|
||||
<section class="house-ads-settings content-body">
|
||||
<DSection @class="house-ads-settings content-body">
|
||||
<div>{{i18n "admin.adplugin.house_ads.description"}}</div>
|
||||
|
||||
{{#if this.houseAds.length}}
|
||||
{{#if houseAds.length}}
|
||||
<form class="form-horizontal">
|
||||
{{house-ads-list-setting
|
||||
name="topic_list_top"
|
||||
value=this.adSettings.topic_list_top
|
||||
allAds=this.houseAds
|
||||
adSettings=this.adSettings
|
||||
value=adSettings.topic_list_top
|
||||
allAds=houseAds
|
||||
adSettings=adSettings
|
||||
}}
|
||||
{{house-ads-list-setting
|
||||
name="topic_above_post_stream"
|
||||
value=this.adSettings.topic_above_post_stream
|
||||
allAds=this.houseAds
|
||||
adSettings=this.adSettings
|
||||
value=adSettings.topic_above_post_stream
|
||||
allAds=houseAds
|
||||
adSettings=adSettings
|
||||
}}
|
||||
{{house-ads-list-setting
|
||||
name="topic_above_suggested"
|
||||
value=this.adSettings.topic_above_suggested
|
||||
allAds=this.houseAds
|
||||
adSettings=this.adSettings
|
||||
value=adSettings.topic_above_suggested
|
||||
allAds=houseAds
|
||||
adSettings=adSettings
|
||||
}}
|
||||
{{house-ads-list-setting
|
||||
name="post_bottom"
|
||||
value=this.adSettings.post_bottom
|
||||
allAds=this.houseAds
|
||||
adSettings=this.adSettings
|
||||
value=adSettings.post_bottom
|
||||
allAds=houseAds
|
||||
adSettings=adSettings
|
||||
}}
|
||||
{{house-ads-list-setting
|
||||
name="topic_list_between"
|
||||
value=this.adSettings.topic_list_between
|
||||
allAds=this.houseAds
|
||||
adSettings=this.adSettings
|
||||
value=adSettings.topic_list_between
|
||||
allAds=houseAds
|
||||
adSettings=adSettings
|
||||
}}
|
||||
|
||||
<DButton
|
||||
@label="admin.adplugin.house_ads.more_settings"
|
||||
@icon="cog"
|
||||
@action={{route-action "moreSettings"}}
|
||||
class="btn-default"
|
||||
@action={{route-action "moreSettings"}}
|
||||
/>
|
||||
</form>
|
||||
{{else}}
|
||||
<p>
|
||||
{{#link-to route="adminPlugins.houseAds.show" model="new"}}
|
||||
{{#link-to "adminPlugins.houseAds.show" "new"}}
|
||||
{{i18n "admin.adplugin.house_ads.get_started"}}
|
||||
{{/link-to}}
|
||||
</p>
|
||||
{{/if}}
|
||||
</section>
|
||||
</DSection>
|
||||
@@ -1,19 +1,15 @@
|
||||
<section class="edit-house-ad content-body">
|
||||
<h1><TextField @value={{this.buffered.name}} class="house-ad-name" /></h1>
|
||||
<DSection @class="edit-house-ad content-body">
|
||||
<h1><TextField @class="house-ad-name" @value={{buffered.name}} /></h1>
|
||||
<div class="controls">
|
||||
<AceEditor
|
||||
@content={{this.buffered.html}}
|
||||
@onChange={{fn (mut this.buffered.html)}}
|
||||
@mode="html"
|
||||
/>
|
||||
<AceEditor @content={{buffered.html}} @mode="html" />
|
||||
</div>
|
||||
<div class="controls">
|
||||
<div class="visibility-settings">
|
||||
<div>
|
||||
<Input
|
||||
class="visible-to-logged-in-checkbox"
|
||||
@type="checkbox"
|
||||
@checked={{this.buffered.visible_to_logged_in_users}}
|
||||
class="visible-to-logged-in-checkbox"
|
||||
/>
|
||||
<span>{{i18n "admin.adplugin.house_ads.show_to_logged_in_users"}}</span>
|
||||
</div>
|
||||
@@ -26,53 +22,27 @@
|
||||
/>
|
||||
<span>{{i18n "admin.adplugin.house_ads.show_to_anons"}}</span>
|
||||
</div>
|
||||
|
||||
<HouseAdsCategorySelector
|
||||
@categories={{this.site.categories}}
|
||||
@selectedCategories={{this.selectedCategories}}
|
||||
@onChange={{this.setCategoryIds}}
|
||||
@options={{hash allowAny=true}}
|
||||
class="house-ads-categories"
|
||||
/>
|
||||
<div class="description">
|
||||
{{i18n "admin.adplugin.house_ads.category_chooser_description"}}
|
||||
</div>
|
||||
|
||||
<GroupChooser
|
||||
@content={{this.site.groups}}
|
||||
@onChange={{this.setGroupIds}}
|
||||
@value={{this.selectedGroups}}
|
||||
class="banner-groups"
|
||||
/>
|
||||
<div class="description">
|
||||
{{i18n "admin.adplugin.house_ads.group_chooser_description"}}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<DButton
|
||||
@action={{this.save}}
|
||||
@disabled={{this.disabledSave}}
|
||||
@label="admin.adplugin.house_ads.save"
|
||||
@action={{action "save"}}
|
||||
@disabled={{disableSave}}
|
||||
class="btn-primary save-button"
|
||||
@label="admin.adplugin.house_ads.save"
|
||||
/>
|
||||
|
||||
{{#if this.saving}}
|
||||
{{this.savingStatus}}
|
||||
{{#if saving}}
|
||||
{{savingStatus}}
|
||||
{{else}}
|
||||
{{#unless this.disabledSave}}
|
||||
<DButton @action={{this.cancel}} @label="cancel" />
|
||||
{{/unless}}
|
||||
{{#if dirty}}
|
||||
<a href {{action "cancel"}}>{{i18n "cancel"}}</a>
|
||||
{{/if}}
|
||||
{{/if}}
|
||||
|
||||
<DButton
|
||||
@action={{this.openPreview}}
|
||||
@label="admin.adplugin.house_ads.preview"
|
||||
/>
|
||||
|
||||
<DButton
|
||||
@action={{this.destroy}}
|
||||
@label="admin.adplugin.house_ads.delete"
|
||||
@action={{action "destroy"}}
|
||||
class="btn-danger delete-button"
|
||||
@label="admin.adplugin.house_ads.delete"
|
||||
/>
|
||||
</div>
|
||||
</section>
|
||||
</DSection>
|
||||
@@ -1,25 +1,21 @@
|
||||
<div class="adplugin-mgmt">
|
||||
<h1>{{i18n "admin.adplugin.house_ads.title"}}</h1>
|
||||
{{#if this.model.length}}
|
||||
{{#if model.length}}
|
||||
<div class="content-list">
|
||||
<div class="house-ads-actions">
|
||||
<LinkTo
|
||||
@route="adminPlugins.houseAds.show"
|
||||
@model="new"
|
||||
class="btn btn-primary"
|
||||
>
|
||||
{{#link-to "adminPlugins.houseAds.show" "new" class="btn btn-primary"}}
|
||||
{{d-icon "plus"}}
|
||||
<span>{{i18n "admin.adplugin.house_ads.new"}}</span>
|
||||
</LinkTo>
|
||||
<LinkTo @route="adminPlugins.houseAds.index" class="btn btn-default">
|
||||
{{d-icon "gear"}}
|
||||
{{/link-to}}
|
||||
{{#link-to "adminPlugins.houseAds.index" class="btn btn-default"}}
|
||||
{{d-icon "cog"}}
|
||||
<span>{{i18n "admin.adplugin.house_ads.settings"}}</span>
|
||||
</LinkTo>
|
||||
{{/link-to}}
|
||||
</div>
|
||||
<ul class="house-ads-list">
|
||||
{{#each this.model as |ad|}}
|
||||
{{#each model as |ad|}}
|
||||
<li class="house-ads-list-item">
|
||||
{{#link-to route="adminPlugins.houseAds.show" model=ad.id}}
|
||||
{{#link-to "adminPlugins.houseAds.show" ad.id}}
|
||||
{{ad.name}}
|
||||
{{/link-to}}
|
||||
</li>
|
||||
|
||||
@@ -1,13 +0,0 @@
|
||||
# frozen_string_literal: true
|
||||
#
|
||||
class AdstxtController < ::ApplicationController
|
||||
requires_plugin AdPlugin.plugin_name
|
||||
|
||||
skip_before_action :preload_json, :check_xhr, :redirect_to_login_if_required
|
||||
|
||||
def index
|
||||
raise Discourse::NotFound if SiteSetting.ads_txt.blank?
|
||||
|
||||
render plain: SiteSetting.ads_txt
|
||||
end
|
||||
end
|
||||
@@ -5,23 +5,11 @@ module ::AdPlugin
|
||||
requires_plugin AdPlugin.plugin_name
|
||||
|
||||
def index
|
||||
render_json_dump(
|
||||
house_ads:
|
||||
HouseAd.all.map do |ad|
|
||||
ad.to_hash.merge!(categories: Category.secured(@guardian).where(id: ad.category_ids))
|
||||
end,
|
||||
settings: HouseAdSetting.all,
|
||||
)
|
||||
render_json_dump(house_ads: HouseAd.all.map(&:to_hash), settings: HouseAdSetting.all)
|
||||
end
|
||||
|
||||
def show
|
||||
house_ad_hash = HouseAd.find(params[:id])&.to_hash
|
||||
if house_ad_hash
|
||||
house_ad_hash.merge!(
|
||||
categories: Category.secured(@guardian).where(id: house_ad_hash[:category_ids]),
|
||||
)
|
||||
end
|
||||
render_json_dump(house_ad: house_ad_hash)
|
||||
render_json_dump(house_ad: HouseAd.find(params[:id])&.to_hash)
|
||||
end
|
||||
|
||||
def create
|
||||
@@ -53,15 +41,7 @@ module ::AdPlugin
|
||||
@permitted ||=
|
||||
begin
|
||||
permitted =
|
||||
params.permit(
|
||||
:id,
|
||||
:name,
|
||||
:html,
|
||||
:visible_to_anons,
|
||||
:visible_to_logged_in_users,
|
||||
group_ids: [],
|
||||
category_ids: [],
|
||||
)
|
||||
params.permit(:id, :name, :html, :visible_to_anons, :visible_to_logged_in_users)
|
||||
permitted[:visible_to_logged_in_users] = ActiveModel::Type::Boolean.new.cast(
|
||||
permitted[:visible_to_logged_in_users],
|
||||
)
|
||||
|
||||
+9
-40
@@ -4,13 +4,7 @@ module ::AdPlugin
|
||||
class HouseAd
|
||||
include ActiveModel::Validations
|
||||
|
||||
attr_accessor :id,
|
||||
:name,
|
||||
:html,
|
||||
:visible_to_logged_in_users,
|
||||
:visible_to_anons,
|
||||
:category_ids,
|
||||
:group_ids
|
||||
attr_accessor :id, :name, :html, :visible_to_logged_in_users, :visible_to_anons
|
||||
|
||||
NAME_REGEX = /\A[[:alnum:]\s\.,'!@#$%&\*\-\+\=:]*\z/i
|
||||
|
||||
@@ -28,8 +22,6 @@ module ::AdPlugin
|
||||
@html = "<div class='house-ad'>New Ad</div>"
|
||||
@visible_to_logged_in_users = true
|
||||
@visible_to_anons = true
|
||||
@group_ids = []
|
||||
@category_ids = []
|
||||
end
|
||||
|
||||
def self.from_hash(h)
|
||||
@@ -37,12 +29,10 @@ module ::AdPlugin
|
||||
ad.name = h[:name]
|
||||
ad.html = h[:html]
|
||||
ad.id = h[:id].to_i if h[:id]
|
||||
ad.visible_to_logged_in_users = h[:visible_to_logged_in_users] if h.key?(
|
||||
:visible_to_logged_in_users,
|
||||
)
|
||||
if h.key?(:visible_to_logged_in_users)
|
||||
ad.visible_to_logged_in_users = h[:visible_to_logged_in_users]
|
||||
end
|
||||
ad.visible_to_anons = h[:visible_to_anons] if h.key?(:visible_to_anons)
|
||||
ad.group_ids = h[:group_ids].map(&:to_i) if h.key?(:group_ids)
|
||||
ad.category_ids = h[:category_ids].map(&:to_i) if h.key?(:category_ids)
|
||||
ad
|
||||
end
|
||||
|
||||
@@ -82,24 +72,8 @@ module ::AdPlugin
|
||||
self.all.select(&:visible_to_anons)
|
||||
end
|
||||
|
||||
def self.all_for_logged_in_users(scope)
|
||||
if scope.nil?
|
||||
# this is for our admin page, so we don't need to filter by group
|
||||
self.all.select(&:visible_to_logged_in_users)
|
||||
else
|
||||
# otherwise, filter by group and visible categories
|
||||
self.all.select do |ad|
|
||||
(
|
||||
ad.group_ids.any? { |group_id| scope.user.groups.pluck(:id).include?(group_id) } ||
|
||||
ad.group_ids.include?(Group::AUTO_GROUPS[:everyone]) || ad.group_ids.empty?
|
||||
) && ad.visible_to_logged_in_users &&
|
||||
(
|
||||
ad.category_ids.any? do |category_id|
|
||||
Category.secured(scope).pluck(:id).include?(category_id)
|
||||
end || true
|
||||
)
|
||||
end
|
||||
end
|
||||
def self.all_for_logged_in_users
|
||||
self.all.select(&:visible_to_logged_in_users)
|
||||
end
|
||||
|
||||
def save
|
||||
@@ -117,13 +91,10 @@ module ::AdPlugin
|
||||
def update(attrs)
|
||||
self.name = attrs[:name]
|
||||
self.html = attrs[:html]
|
||||
self.visible_to_logged_in_users = attrs[:visible_to_logged_in_users] if attrs.key?(
|
||||
:visible_to_logged_in_users,
|
||||
)
|
||||
if attrs.key?(:visible_to_logged_in_users)
|
||||
self.visible_to_logged_in_users = attrs[:visible_to_logged_in_users]
|
||||
end
|
||||
self.visible_to_anons = attrs[:visible_to_anons] if attrs.key?(:visible_to_anons)
|
||||
# ensure that group_ids and category_ids can be set to an empty array
|
||||
self.group_ids = attrs.key?(:group_ids) ? attrs[:group_ids].map(&:to_i) : []
|
||||
self.category_ids = attrs.key?(:category_ids) ? attrs[:category_ids].map(&:to_i) : []
|
||||
self.save
|
||||
end
|
||||
|
||||
@@ -134,8 +105,6 @@ module ::AdPlugin
|
||||
html: @html,
|
||||
visible_to_logged_in_users: @visible_to_logged_in_users,
|
||||
visible_to_anons: @visible_to_anons,
|
||||
group_ids: @group_ids,
|
||||
category_ids: @category_ids,
|
||||
}
|
||||
end
|
||||
|
||||
|
||||
@@ -21,14 +21,14 @@ module ::AdPlugin
|
||||
settings
|
||||
end
|
||||
|
||||
def self.settings_and_ads(for_anons: true, scope: nil)
|
||||
def self.settings_and_ads(for_anons: true)
|
||||
settings = AdPlugin::HouseAdSetting.all
|
||||
ad_names = settings.values.map { |v| v.split("|") }.flatten.uniq
|
||||
|
||||
if for_anons
|
||||
ads = AdPlugin::HouseAd.all_for_anons
|
||||
else
|
||||
ads = AdPlugin::HouseAd.all_for_logged_in_users(scope)
|
||||
ads = AdPlugin::HouseAd.all_for_logged_in_users
|
||||
end
|
||||
ads = ads.select { |ad| ad_names.include?(ad.name) }
|
||||
|
||||
@@ -41,14 +41,14 @@ module ::AdPlugin
|
||||
),
|
||||
creatives:
|
||||
ads.inject({}) do |h, ad|
|
||||
h[ad.name] = { html: ad.html, category_ids: ad.category_ids }
|
||||
h[ad.name] = ad.html
|
||||
h
|
||||
end,
|
||||
}
|
||||
end
|
||||
|
||||
def self.update(setting_name, value)
|
||||
raise Discourse::NotFound if DEFAULTS.keys.exclude?(setting_name.to_sym)
|
||||
raise Discourse::NotFound unless DEFAULTS.keys.include?(setting_name.to_sym)
|
||||
|
||||
ad_names = value&.split("|") || []
|
||||
|
||||
|
||||
@@ -1,36 +1,34 @@
|
||||
import Component from "@ember/component";
|
||||
import { alias, or } from "@ember/object/computed";
|
||||
import { service } from "@ember/service";
|
||||
import { inject as service } from "@ember/service";
|
||||
import discourseComputed from "discourse-common/utils/decorators";
|
||||
import {
|
||||
isNthPost,
|
||||
isNthTopicListItem,
|
||||
} from "discourse/plugins/discourse-adplugin/discourse/helpers/slot-position";
|
||||
|
||||
export default class AdComponent extends Component {
|
||||
@service router;
|
||||
export default Component.extend({
|
||||
router: service(),
|
||||
|
||||
@or(
|
||||
currentCategoryId: or(
|
||||
"router.currentRoute.attributes.category.id",
|
||||
"router.currentRoute.parent.attributes.category_id"
|
||||
)
|
||||
currentCategoryId;
|
||||
),
|
||||
|
||||
@or(
|
||||
currentCategorySlug: or(
|
||||
"router.currentRoute.attributes.category.slug",
|
||||
"router.currentRoute.parent.attributes.category.slug"
|
||||
)
|
||||
currentCategorySlug;
|
||||
),
|
||||
|
||||
// Server needs to compute this in case hidden tags are being used.
|
||||
@alias("router.currentRoute.parent.attributes.tags_disable_ads")
|
||||
topicTagsDisableAds;
|
||||
topicTagsDisableAds: alias(
|
||||
"router.currentRoute.parent.attributes.tags_disable_ads"
|
||||
),
|
||||
|
||||
@or(
|
||||
isRestrictedCategory: or(
|
||||
"router.currentRoute.attributes.category.read_restricted",
|
||||
"router.currentRoute.parent.attributes.category.read_restricted"
|
||||
)
|
||||
isRestrictedCategory;
|
||||
),
|
||||
|
||||
@discourseComputed(
|
||||
"router.currentRoute.attributes.__type",
|
||||
@@ -40,21 +38,33 @@ export default class AdComponent extends Component {
|
||||
if (type === "tag" && tag) {
|
||||
return tag;
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
@discourseComputed("router.currentRoute.parent.attributes.archetype")
|
||||
isPersonalMessage(topicType) {
|
||||
return topicType === "private_message";
|
||||
}
|
||||
},
|
||||
|
||||
@discourseComputed
|
||||
showToGroups() {
|
||||
if (!this.currentUser) {
|
||||
@discourseComputed("currentUser.groups")
|
||||
showToGroups(groups) {
|
||||
const currentUser = this.currentUser;
|
||||
|
||||
if (
|
||||
!currentUser ||
|
||||
!groups ||
|
||||
!this.siteSettings.no_ads_for_groups ||
|
||||
this.siteSettings.no_ads_for_groups.length === 0
|
||||
) {
|
||||
return true;
|
||||
}
|
||||
|
||||
return this.currentUser.show_to_groups;
|
||||
}
|
||||
let noAdsGroups = this.siteSettings.no_ads_for_groups
|
||||
.split("|")
|
||||
.filter(Boolean);
|
||||
let currentGroups = groups.map((g) => g.id.toString());
|
||||
|
||||
return !currentGroups.any((g) => noAdsGroups.includes(g));
|
||||
},
|
||||
|
||||
@discourseComputed(
|
||||
"currentCategoryId",
|
||||
@@ -84,13 +94,13 @@ export default class AdComponent extends Component {
|
||||
(!isRestrictedCategory ||
|
||||
!this.siteSettings.no_ads_for_restricted_categories)
|
||||
);
|
||||
}
|
||||
},
|
||||
|
||||
isNthPost(n) {
|
||||
return isNthPost(n, this.get("postNumber"));
|
||||
}
|
||||
},
|
||||
|
||||
isNthTopicListItem(n) {
|
||||
return isNthTopicListItem(n, this.get("indexNumber"));
|
||||
}
|
||||
}
|
||||
},
|
||||
});
|
||||
|
||||
@@ -1,13 +1,12 @@
|
||||
{{#each this.adComponents as |adComponent|}}
|
||||
{{! Trick to force full destroy/re-render of component when route changes }}
|
||||
{{#each (array this.router.currentRoute)}}
|
||||
{{component
|
||||
adComponent
|
||||
placement=this.placement
|
||||
category=this.category
|
||||
postNumber=this.postNumber
|
||||
indexNumber=this.indexNumber
|
||||
tagName=this.childTagName
|
||||
}}
|
||||
{{/each}}
|
||||
{{#each adComponents as |adComponent|}}
|
||||
{{component
|
||||
adComponent
|
||||
placement=placement
|
||||
refreshOnChange=refreshOnChange
|
||||
category=category
|
||||
listLoading=listLoading
|
||||
postNumber=postNumber
|
||||
indexNumber=indexNumber
|
||||
tagName=childTagName
|
||||
}}
|
||||
{{/each}}
|
||||
@@ -1,8 +1,6 @@
|
||||
import EmberObject from "@ember/object";
|
||||
import { service } from "@ember/service";
|
||||
import { isBlank } from "@ember/utils";
|
||||
import { tagName } from "@ember-decorators/component";
|
||||
import discourseComputed from "discourse-common/utils/decorators";
|
||||
import discourseComputed, { observes } from "discourse-common/utils/decorators";
|
||||
import AdComponent from "discourse/plugins/discourse-adplugin/discourse/components/ad-component";
|
||||
import {
|
||||
isNthPost,
|
||||
@@ -174,9 +172,9 @@ export function slotContenders(
|
||||
return types;
|
||||
}
|
||||
|
||||
@tagName("")
|
||||
export default class AdSlot extends AdComponent {
|
||||
@service router;
|
||||
export default AdComponent.extend({
|
||||
needsUpdate: false,
|
||||
tagName: "",
|
||||
|
||||
/**
|
||||
* For a given ad placement and optionally a post number if in between posts,
|
||||
@@ -191,16 +189,29 @@ export default class AdSlot extends AdComponent {
|
||||
indexNumber,
|
||||
postNumber
|
||||
);
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* When house ads are configured to alternate with other ad networks, we
|
||||
* need to trigger an update of which ad component is shown after
|
||||
* navigating between topic lists or topics.
|
||||
*/
|
||||
@observes("refreshOnChange")
|
||||
changed() {
|
||||
if (this.get("listLoading")) {
|
||||
return;
|
||||
}
|
||||
|
||||
// force adComponents to be recomputed
|
||||
this.notifyPropertyChange("needsUpdate");
|
||||
},
|
||||
|
||||
/**
|
||||
* Returns a list of the names of ad components that should be rendered
|
||||
* in the given ad placement. It handles alternating between house ads
|
||||
* and other ad networks.
|
||||
*
|
||||
* Depends on `router.currentRoute` so that we refresh ads when navigating around.
|
||||
*/
|
||||
@discourseComputed("placement", "availableAdTypes", "router.currentRoute")
|
||||
@discourseComputed("placement", "availableAdTypes", "needsUpdate")
|
||||
adComponents(placement, availableAdTypes) {
|
||||
if (
|
||||
!availableAdTypes.includes("house-ad") ||
|
||||
@@ -239,5 +250,5 @@ export default class AdSlot extends AdComponent {
|
||||
}
|
||||
|
||||
return networkNames;
|
||||
}
|
||||
}
|
||||
},
|
||||
});
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
{{#if this.showAd}}
|
||||
<div id={{this.divId}} class={{this.className}}></div>
|
||||
{{#if showAd}}
|
||||
<div id={{divId}} class={{className}}></div>
|
||||
{{/if}}
|
||||
@@ -2,7 +2,7 @@ import { scheduleOnce } from "@ember/runloop";
|
||||
import RSVP from "rsvp";
|
||||
import loadScript from "discourse/lib/load-script";
|
||||
import { isTesting } from "discourse-common/config/environment";
|
||||
import discourseComputed from "discourse-common/utils/decorators";
|
||||
import discourseComputed, { observes } from "discourse-common/utils/decorators";
|
||||
import AdComponent from "discourse/plugins/discourse-adplugin/discourse/components/ad-component";
|
||||
|
||||
let _loaded = false,
|
||||
@@ -27,9 +27,9 @@ function loadAdbutler(adserverHostname) {
|
||||
return _promise;
|
||||
}
|
||||
|
||||
export default class AdbutlerAd extends AdComponent {
|
||||
divs = null;
|
||||
publisherId = null;
|
||||
export default AdComponent.extend({
|
||||
divs: null,
|
||||
publisherId: null,
|
||||
|
||||
init() {
|
||||
let dimensions = [728, 90];
|
||||
@@ -70,8 +70,8 @@ export default class AdbutlerAd extends AdComponent {
|
||||
dimensions,
|
||||
});
|
||||
|
||||
super.init();
|
||||
}
|
||||
this._super();
|
||||
},
|
||||
|
||||
_triggerAds() {
|
||||
if (isTesting()) {
|
||||
@@ -104,44 +104,52 @@ export default class AdbutlerAd extends AdComponent {
|
||||
}
|
||||
}.bind(this)
|
||||
);
|
||||
}
|
||||
},
|
||||
|
||||
didInsertElement() {
|
||||
super.didInsertElement();
|
||||
this._super();
|
||||
scheduleOnce("afterRender", this, this._triggerAds);
|
||||
}
|
||||
},
|
||||
|
||||
@discourseComputed
|
||||
showAdbutlerAds() {
|
||||
if (!this.currentUser) {
|
||||
return true;
|
||||
@observes("listLoading")
|
||||
waitForLoad() {
|
||||
if (this.get("adRequested")) {
|
||||
return;
|
||||
} // already requested that this ad unit be populated
|
||||
if (!this.get("listLoading")) {
|
||||
scheduleOnce("afterRender", this, this._triggerAds);
|
||||
}
|
||||
},
|
||||
|
||||
return this.currentUser.show_adbutler_ads;
|
||||
}
|
||||
@discourseComputed("currentUser.trust_level")
|
||||
showToTrustLevel(trustLevel) {
|
||||
return !(
|
||||
trustLevel && trustLevel > this.siteSettings.adbutler_through_trust_level
|
||||
);
|
||||
},
|
||||
|
||||
@discourseComputed(
|
||||
"publisherId",
|
||||
"showAdbutlerAds",
|
||||
"showToTrustLevel",
|
||||
"showToGroups",
|
||||
"showAfterPost",
|
||||
"showOnCurrentPage"
|
||||
)
|
||||
showAd(
|
||||
publisherId,
|
||||
showAdbutlerAds,
|
||||
showToTrustLevel,
|
||||
showToGroups,
|
||||
showAfterPost,
|
||||
showOnCurrentPage
|
||||
) {
|
||||
return (
|
||||
publisherId &&
|
||||
showAdbutlerAds &&
|
||||
showToTrustLevel &&
|
||||
showToGroups &&
|
||||
showAfterPost &&
|
||||
showOnCurrentPage
|
||||
);
|
||||
}
|
||||
},
|
||||
|
||||
@discourseComputed("postNumber")
|
||||
showAfterPost(postNumber) {
|
||||
@@ -149,5 +157,5 @@ export default class AdbutlerAd extends AdComponent {
|
||||
return true;
|
||||
}
|
||||
return this.isNthPost(parseInt(this.siteSettings.adbutler_nth_post, 10));
|
||||
}
|
||||
}
|
||||
},
|
||||
});
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user