This repository has been archived on 2023-03-18. You can view files and clone it, but cannot push or open issues or pull requests.
osr-discourse-src/app/assets/javascripts/discourse/tests/acceptance/user-test.js
Bianca Nenciu 68497bddf2
UX: Add title to read time stats from user page (#16501)
The title attributes were added to explain the difference between "read
time" and "recent read time" stats from user summary page.
2022-04-19 20:48:08 +03:00

373 lines
12 KiB
JavaScript

import EmberObject from "@ember/object";
import User from "discourse/models/user";
import selectKit from "discourse/tests/helpers/select-kit-helper";
import sinon from "sinon";
import userFixtures from "discourse/tests/fixtures/user-fixtures";
import {
acceptance,
exists,
query,
queryAll,
updateCurrentUser,
} from "discourse/tests/helpers/qunit-helpers";
import { click, currentRouteName, visit } from "@ember/test-helpers";
import { cloneJSON } from "discourse-common/lib/object";
import { test } from "qunit";
import I18n from "I18n";
acceptance("User Routes", function (needs) {
needs.user();
needs.pretender((server, helper) => {
server.get("/u/eviltrout%2F..%2F..%2F.json", () =>
helper.response(400, {})
);
});
test("Invalid usernames", async function (assert) {
try {
await visit("/u/eviltrout%2F..%2F..%2F/summary");
} catch (e) {
if (e.message !== "TransitionAborted") {
throw e;
}
}
assert.strictEqual(currentRouteName(), "exception-unknown");
});
test("Unicode usernames", async function (assert) {
await visit("/u/%E3%83%A9%E3%82%A4%E3%82%AA%E3%83%B3/summary");
assert.strictEqual(currentRouteName(), "user.summary");
});
test("Invites", async function (assert) {
await visit("/u/eviltrout/invited/pending");
assert.ok($("body.user-invites-page").length, "has the body class");
});
test("Notifications", async function (assert) {
await visit("/u/eviltrout/notifications");
assert.ok($("body.user-notifications-page").length, "has the body class");
const $links = queryAll(".item.notification a");
assert.ok(
$links[2].href.includes(
"/u/eviltrout/notifications/likes-received?acting_username=aquaman"
)
);
updateCurrentUser({ moderator: true, admin: false });
await visit("/u/charlie/summary");
assert.notOk(
exists(".user-nav > .user-notifications"),
"does not have the notifications tab"
);
updateCurrentUser({ moderator: false, admin: true });
await visit("/u/charlie/summary");
assert.ok(
exists(".user-nav > .user-notifications"),
"has the notifications tab"
);
});
test("Root URL - Viewing Self", async function (assert) {
await visit("/u/eviltrout");
assert.ok($("body.user-activity-page").length, "has the body class");
assert.strictEqual(
currentRouteName(),
"userActivity.index",
"it defaults to activity"
);
assert.ok(exists(".container.viewing-self"), "has the viewing-self class");
});
test("Viewing Summary", async function (assert) {
await visit("/u/eviltrout/summary");
assert.ok(exists(".replies-section li a"), "replies");
assert.ok(exists(".topics-section li a"), "topics");
assert.ok(exists(".links-section li a"), "links");
assert.ok(exists(".replied-section .user-info"), "liked by");
assert.ok(exists(".liked-by-section .user-info"), "liked by");
assert.ok(exists(".liked-section .user-info"), "liked");
assert.ok(exists(".badges-section .badge-card"), "badges");
assert.ok(
exists(".top-categories-section .category-link"),
"top categories"
);
});
test("Viewing Drafts", async function (assert) {
await visit("/u/eviltrout/activity/drafts");
assert.ok(exists(".user-stream"), "has drafts stream");
assert.ok(
exists(".user-stream .user-stream-item-draft-actions"),
"has draft action buttons"
);
await click(".user-stream button.resume-draft:nth-of-type(1)");
assert.ok(
exists(".d-editor-input"),
"composer is visible after resuming a draft"
);
});
});
acceptance("User Summary - Stats", function (needs) {
needs.pretender((server, helper) => {
server.get("/u/eviltrout/summary.json", () => {
return helper.response(200, {
user_summary: {
likes_given: 1,
likes_received: 2,
topics_entered: 3,
posts_read_count: 4,
days_visited: 5,
topic_count: 6,
post_count: 7,
time_read: 100000,
recent_time_read: 1000,
bookmark_count: 0,
can_see_summary_stats: true,
topic_ids: [1234],
replies: [{ topic_id: 1234 }],
links: [{ topic_id: 1234, url: "https://eviltrout.com" }],
most_replied_to_users: [{ id: 333 }],
most_liked_by_users: [{ id: 333 }],
most_liked_users: [{ id: 333 }],
badges: [{ badge_id: 444 }],
top_categories: [
{
id: 1,
name: "bug",
color: "e9dd00",
text_color: "000000",
slug: "bug",
read_restricted: false,
parent_category_id: null,
topic_count: 1,
post_count: 1,
},
],
},
badges: [{ id: 444, count: 1 }],
topics: [{ id: 1234, title: "cool title", slug: "cool-title" }],
});
});
});
test("Summary Read Times", async function (assert) {
await visit("/u/eviltrout/summary");
assert.equal(query(".stats-time-read span").textContent.trim(), "1d");
assert.equal(
query(".stats-time-read span").title,
I18n.t("user.summary.time_read_title", { duration: "1 day" })
);
assert.equal(query(".stats-recent-read span").textContent.trim(), "17m");
assert.equal(
query(".stats-recent-read span").title,
I18n.t("user.summary.recent_time_read_title", { duration: "17 mins" })
);
});
});
acceptance(
"User Routes - Periods in current user's username",
function (needs) {
needs.user({ username: "e.il.rout" });
test("Periods in current user's username don't act like wildcards", async function (assert) {
await visit("/u/eviltrout");
assert.strictEqual(
query(".user-profile-names .username").textContent.trim(),
"eviltrout",
"eviltrout profile is shown"
);
await visit("/u/e.il.rout");
assert.strictEqual(
query(".user-profile-names .username").textContent.trim(),
"e.il.rout",
"e.il.rout profile is shown"
);
});
}
);
acceptance("User Routes - Moderator viewing warnings", function (needs) {
needs.user({
username: "notEviltrout",
moderator: true,
staff: true,
admin: false,
});
test("Messages - Warnings", async function (assert) {
await visit("/u/eviltrout/messages/warnings");
assert.ok($("body.user-messages-page").length, "has the body class");
assert.ok($("div.alert-info").length, "has the permissions alert");
});
});
acceptance("User - Saving user options", function (needs) {
needs.user({
admin: false,
moderator: false,
username: "eviltrout",
id: 1,
user_option: EmberObject.create({}),
});
needs.settings({
disable_mailing_list_mode: false,
});
needs.pretender((server, helper) => {
server.put("/u/eviltrout.json", () => {
return helper.response(200, { user: {} });
});
});
test("saving user options", async function (assert) {
const spy = sinon.spy(User.current(), "_saveUserData");
await visit("/u/eviltrout/preferences/emails");
await click(".pref-mailing-list-mode input[type='checkbox']");
await click(".save-changes");
assert.ok(
spy.calledWithMatch({ mailing_list_mode: true }),
"sends a PUT request to update the specified user option"
);
await selectKit("#user-email-messages-level").expand();
await selectKit("#user-email-messages-level").selectRowByValue(2); // never option
await click(".save-changes");
assert.ok(
spy.calledWithMatch({ email_messages_level: 2 }),
"is able to save a different user_option on a subsequent request"
);
});
});
acceptance("User - Notification level dropdown visibility", function (needs) {
needs.user({ username: "eviltrout", id: 1, ignored_ids: [] });
needs.pretender((server, helper) => {
server.get("/u/charlie.json", () => {
const cloned = cloneJSON(userFixtures["/u/charlie.json"]);
cloned.user.can_ignore_user = false;
cloned.user.can_mute_user = false;
return helper.response(200, cloned);
});
});
test("Notification level button is not rendered for user who cannot mute or ignore another user", async function (assert) {
await visit("/u/charlie");
assert.notOk(exists(".user-notifications-dropdown"));
});
});
acceptance(
"User - Muting other user with notification level dropdown",
function (needs) {
needs.user({ username: "eviltrout", id: 1, ignored_ids: [] });
needs.pretender((server, helper) => {
server.get("/u/charlie.json", () => {
const cloned = cloneJSON(userFixtures["/u/charlie.json"]);
cloned.user.can_mute_user = true;
return helper.response(200, cloned);
});
server.put("/u/charlie/notification_level.json", (request) => {
let requestParams = new URLSearchParams(request.requestBody);
// Ensure the correct `notification_level` param is sent to the server
if (requestParams.get("notification_level") === "mute") {
return helper.response(200, {});
} else {
return helper.response(422, {});
}
});
});
test("Notification level is set to normal and can be changed to muted", async function (assert) {
await visit("/u/charlie");
assert.ok(
exists(".user-notifications-dropdown"),
"Notification level dropdown is present"
);
const dropdown = selectKit(".user-notifications-dropdown");
await dropdown.expand();
assert.strictEqual(dropdown.selectedRow().value(), "changeToNormal");
await dropdown.selectRowByValue("changeToMuted");
await dropdown.expand();
assert.strictEqual(dropdown.selectedRow().value(), "changeToMuted");
});
}
);
acceptance(
"User - Ignoring other user with notification level dropdown",
function (needs) {
needs.user({ username: "eviltrout", id: 1, ignored_ids: [] });
needs.pretender((server, helper) => {
server.get("/u/charlie.json", () => {
const cloned = cloneJSON(userFixtures["/u/charlie.json"]);
cloned.user.can_ignore_user = true;
return helper.response(200, cloned);
});
server.put("/u/charlie/notification_level.json", (request) => {
let requestParams = new URLSearchParams(request.requestBody);
// Ensure the correct `notification_level` param is sent to the server
if (requestParams.get("notification_level") === "ignore") {
return helper.response(200, {});
} else {
return helper.response(422, {});
}
});
});
test("Notification level can be changed to ignored", async function (assert) {
await visit("/u/charlie");
assert.ok(
exists(".user-notifications-dropdown"),
"Notification level dropdown is present"
);
const notificationLevelDropdown = selectKit(
".user-notifications-dropdown"
);
await notificationLevelDropdown.expand();
assert.strictEqual(
notificationLevelDropdown.selectedRow().value(),
"changeToNormal"
);
await notificationLevelDropdown.selectRowByValue("changeToIgnored");
assert.ok(exists(".ignore-duration-modal"));
const durationDropdown = selectKit(
".ignore-duration-modal .future-date-input-selector"
);
await durationDropdown.expand();
await durationDropdown.selectRowByIndex(0);
await click(".modal-footer .ignore-duration-save");
await notificationLevelDropdown.expand();
assert.strictEqual(
notificationLevelDropdown.selectedRow().value(),
"changeToIgnored"
);
});
}
);