Skip to content
This repository was archived by the owner on Jul 22, 2025. It is now read-only.

Commit 86bdc7b

Browse files
committed
Revert "DEV: Updates to sentiment analysis reports (#1161)"
This reverts commit 8863cf0. The conditionals added around the report registrations are incompatible with multisite environment and skip_db=true
1 parent e255c7a commit 86bdc7b

File tree

9 files changed

+75
-201
lines changed

9 files changed

+75
-201
lines changed

app/controllers/discourse_ai/sentiment/sentiment_controller.rb

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,7 @@ def posts
3737
SELECT
3838
p.id AS post_id,
3939
p.topic_id,
40-
t.fancy_title AS topic_title,
40+
t.title AS topic_title,
4141
p.cooked as post_cooked,
4242
p.user_id,
4343
p.post_number,

app/models/classification_result.rb

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2,10 +2,6 @@
22

33
class ClassificationResult < ActiveRecord::Base
44
belongs_to :target, polymorphic: true
5-
6-
def self.has_sentiment_classification?
7-
where(classification_type: "sentiment").exists?
8-
end
95
end
106

117
# == Schema Information

assets/javascripts/discourse/components/admin-report-sentiment-analysis.gjs

Lines changed: 35 additions & 107 deletions
Original file line numberDiff line numberDiff line change
@@ -3,36 +3,26 @@ import { tracked } from "@glimmer/tracking";
33
import { fn, hash } from "@ember/helper";
44
import { on } from "@ember/modifier";
55
import { action } from "@ember/object";
6-
import didInsert from "@ember/render-modifiers/modifiers/did-insert";
7-
import { service } from "@ember/service";
86
import { modifier } from "ember-modifier";
97
import { and } from "truth-helpers";
108
import DButton from "discourse/components/d-button";
119
import HorizontalOverflowNav from "discourse/components/horizontal-overflow-nav";
1210
import PostList from "discourse/components/post-list";
1311
import dIcon from "discourse/helpers/d-icon";
14-
import replaceEmoji from "discourse/helpers/replace-emoji";
1512
import { ajax } from "discourse/lib/ajax";
1613
import { popupAjaxError } from "discourse/lib/ajax-error";
17-
import { getAbsoluteURL } from "discourse/lib/get-url";
18-
import discourseLater from "discourse/lib/later";
19-
import { clipboardCopy } from "discourse/lib/utilities";
2014
import Post from "discourse/models/post";
2115
import closeOnClickOutside from "discourse/modifiers/close-on-click-outside";
2216
import { i18n } from "discourse-i18n";
23-
import DTooltip from "float-kit/components/d-tooltip";
2417
import DoughnutChart from "discourse/plugins/discourse-ai/discourse/components/doughnut-chart";
2518

2619
export default class AdminReportSentimentAnalysis extends Component {
27-
@service router;
28-
2920
@tracked selectedChart = null;
30-
@tracked posts = [];
21+
@tracked posts = null;
3122
@tracked hasMorePosts = false;
3223
@tracked nextOffset = 0;
3324
@tracked showingSelectedChart = false;
3425
@tracked activeFilter = "all";
35-
@tracked shareIcon = "link";
3626

3727
setActiveFilter = modifier((element) => {
3828
this.clearActiveFilters(element);
@@ -81,6 +71,32 @@ export default class AdminReportSentimentAnalysis extends Component {
8171
}
8272
}
8373

74+
doughnutTitle(data) {
75+
const MAX_TITLE_LENGTH = 18;
76+
const title = data?.title || "";
77+
const score = data?.total_score ? ` (${data.total_score})` : "";
78+
79+
if (title.length + score.length > MAX_TITLE_LENGTH) {
80+
return (
81+
title.substring(0, MAX_TITLE_LENGTH - score.length) + "..." + score
82+
);
83+
}
84+
85+
return title + score;
86+
}
87+
88+
async postRequest() {
89+
return await ajax("/discourse-ai/sentiment/posts", {
90+
data: {
91+
group_by: this.currentGroupFilter,
92+
group_value: this.selectedChart?.title,
93+
start_date: this.args.model.start_date,
94+
end_date: this.args.model.end_date,
95+
offset: this.nextOffset,
96+
},
97+
});
98+
}
99+
84100
get colors() {
85101
return ["#2ecc71", "#95a5a6", "#e74c3c"];
86102
}
@@ -117,11 +133,10 @@ export default class AdminReportSentimentAnalysis extends Component {
117133
}
118134

119135
return this.posts.filter((post) => {
120-
post.topic_title = replaceEmoji(post.topic_title);
121-
122136
if (this.activeFilter === "all") {
123137
return true;
124138
}
139+
125140
return post.sentiment === this.activeFilter;
126141
});
127142
}
@@ -171,57 +186,13 @@ export default class AdminReportSentimentAnalysis extends Component {
171186
];
172187
}
173188

174-
async postRequest() {
175-
return await ajax("/discourse-ai/sentiment/posts", {
176-
data: {
177-
group_by: this.currentGroupFilter,
178-
group_value: this.selectedChart?.title,
179-
start_date: this.args.model.start_date,
180-
end_date: this.args.model.end_date,
181-
offset: this.nextOffset,
182-
},
183-
});
184-
}
185-
186-
@action
187-
async openToChart() {
188-
const queryParams = this.router.currentRoute.queryParams;
189-
if (queryParams.selectedChart) {
190-
this.selectedChart = this.transformedData.find(
191-
(data) => data.title === queryParams.selectedChart
192-
);
193-
194-
if (!this.selectedChart) {
195-
return;
196-
}
197-
this.showingSelectedChart = true;
198-
199-
try {
200-
const response = await this.postRequest();
201-
this.posts = response.posts.map((post) => Post.create(post));
202-
this.hasMorePosts = response.has_more;
203-
this.nextOffset = response.next_offset;
204-
} catch (e) {
205-
popupAjaxError(e);
206-
}
207-
}
208-
}
209-
210189
@action
211190
async showDetails(data) {
212191
if (this.selectedChart === data) {
213192
// Don't do anything if the same chart is clicked again
214193
return;
215194
}
216195

217-
const currentQueryParams = this.router.currentRoute.queryParams;
218-
this.router.transitionTo(this.router.currentRoute.name, {
219-
queryParams: {
220-
...currentQueryParams,
221-
selectedChart: data.title,
222-
},
223-
});
224-
225196
this.selectedChart = data;
226197
this.showingSelectedChart = true;
227198

@@ -246,10 +217,7 @@ export default class AdminReportSentimentAnalysis extends Component {
246217

247218
this.hasMorePosts = response.has_more;
248219
this.nextOffset = response.next_offset;
249-
250-
const mappedPosts = response.posts.map((post) => Post.create(post));
251-
this.posts.pushObjects(mappedPosts);
252-
return mappedPosts;
220+
return response.posts.map((post) => Post.create(post));
253221
} catch (e) {
254222
popupAjaxError(e);
255223
}
@@ -260,35 +228,9 @@ export default class AdminReportSentimentAnalysis extends Component {
260228
this.showingSelectedChart = false;
261229
this.selectedChart = null;
262230
this.activeFilter = "all";
263-
this.posts = [];
264-
265-
const currentQueryParams = this.router.currentRoute.queryParams;
266-
this.router.transitionTo(this.router.currentRoute.name, {
267-
queryParams: {
268-
...currentQueryParams,
269-
selectedChart: null,
270-
},
271-
});
272-
}
273-
274-
@action
275-
shareChart() {
276-
const url = this.router.currentURL;
277-
if (!url) {
278-
return;
279-
}
280-
281-
clipboardCopy(getAbsoluteURL(url));
282-
this.shareIcon = "check";
283-
284-
discourseLater(() => {
285-
this.shareIcon = "link";
286-
}, 2000);
287231
}
288232

289233
<template>
290-
<span {{didInsert this.openToChart}}></span>
291-
292234
{{#unless this.showingSelectedChart}}
293235
<div class="admin-report-sentiment-analysis">
294236
{{#each this.transformedData as |data|}}
@@ -310,7 +252,6 @@ export default class AdminReportSentimentAnalysis extends Component {
310252
@data={{data.scores}}
311253
@totalScore={{data.total_score}}
312254
@doughnutTitle={{data.title}}
313-
@displayLegend={{true}}
314255
/>
315256
</div>
316257
{{/each}}
@@ -319,33 +260,20 @@ export default class AdminReportSentimentAnalysis extends Component {
319260

320261
{{#if (and this.selectedChart this.showingSelectedChart)}}
321262
<div class="admin-report-sentiment-analysis__selected-chart">
322-
<div class="admin-report-sentiment-analysis__selected-chart-actions">
323-
<DButton
324-
@label="back_button"
325-
@icon="chevron-left"
326-
class="btn-flat"
327-
@action={{this.backToAllCharts}}
328-
/>
329-
330-
<DTooltip
331-
class="share btn-flat"
332-
@icon={{this.shareIcon}}
333-
{{on "click" this.shareChart}}
334-
@content={{i18n
335-
"discourse_ai.sentiments.sentiment_analysis.share_chart"
336-
}}
337-
/>
338-
</div>
263+
<DButton
264+
@label="back_button"
265+
@icon="chevron-left"
266+
class="btn-flat"
267+
@action={{this.backToAllCharts}}
268+
/>
339269

340270
<DoughnutChart
341271
@labels={{@model.labels}}
342272
@colors={{this.colors}}
343273
@data={{this.selectedChart.scores}}
344274
@totalScore={{this.selectedChart.total_score}}
345275
@doughnutTitle={{this.selectedChart.title}}
346-
@displayLegend={{true}}
347276
/>
348-
349277
</div>
350278
<div class="admin-report-sentiment-analysis-details">
351279
<HorizontalOverflowNav

assets/javascripts/discourse/components/doughnut-chart.gjs

Lines changed: 1 addition & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,7 @@
11
import Component from "@glimmer/component";
2-
import { tracked } from "@glimmer/tracking";
32
import Chart from "admin/components/chart";
43

54
export default class DoughnutChart extends Component {
6-
@tracked canvasSize = null;
7-
85
get config() {
96
const totalScore = this.args.totalScore || "";
107

@@ -16,18 +13,14 @@ export default class DoughnutChart extends Component {
1613
{
1714
data: this.args.data,
1815
backgroundColor: this.args.colors,
19-
cutout: "50%",
20-
radius: 100,
2116
},
2217
],
2318
},
2419
options: {
2520
responsive: true,
26-
maintainAspectRatio: false,
2721
plugins: {
2822
legend: {
29-
display: this.args.displayLegend || false,
30-
position: "bottom",
23+
position: this.args.legendPosition || "bottom",
3124
},
3225
},
3326
},

assets/javascripts/initializers/admin-reports.js

Lines changed: 0 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -22,13 +22,6 @@ export default {
2222
"sentiment_analysis",
2323
AdminReportSentimentAnalysis
2424
);
25-
26-
api.registerValueTransformer(
27-
"admin-reports-show-query-params",
28-
({ value }) => {
29-
return [...value, "selectedChart"];
30-
}
31-
);
3225
});
3326
},
3427
};
Lines changed: 15 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -1,27 +1,21 @@
11
import { apiInitializer } from "discourse/lib/api";
22

33
export default apiInitializer("1.15.0", (api) => {
4-
const currentUser = api.getCurrentUser();
4+
const settings = api.container.lookup("service:site-settings");
55

6-
if (
7-
!currentUser ||
8-
!currentUser.admin ||
9-
!currentUser.can_see_sentiment_reports
10-
) {
11-
return;
6+
if (settings.ai_sentiment_enabled) {
7+
api.addAdminSidebarSectionLink("reports", {
8+
name: "sentiment_overview",
9+
route: "admin.dashboardSentiment",
10+
label: "discourse_ai.sentiments.sidebar.overview",
11+
icon: "chart-column",
12+
});
13+
api.addAdminSidebarSectionLink("reports", {
14+
name: "sentiment_analysis",
15+
route: "adminReports.show",
16+
routeModels: ["sentiment_analysis"],
17+
label: "discourse_ai.sentiments.sidebar.analysis",
18+
icon: "chart-pie",
19+
});
1220
}
13-
14-
api.addAdminSidebarSectionLink("reports", {
15-
name: "sentiment_overview",
16-
route: "admin.dashboardSentiment",
17-
label: "discourse_ai.sentiments.sidebar.overview",
18-
icon: "chart-column",
19-
});
20-
api.addAdminSidebarSectionLink("reports", {
21-
name: "sentiment_analysis",
22-
route: "adminReports.show",
23-
routeModels: ["sentiment_analysis"],
24-
label: "discourse_ai.sentiments.sidebar.analysis",
25-
icon: "chart-pie",
26-
});
2721
});

0 commit comments

Comments
 (0)