Compare commits

..

1 Commits

Author SHA1 Message Date
Isaac Janzen
6a68ba147b
FIX: Use tag-intersection route when building more_topics_url from tag-intersection 2023-03-17 16:58:54 -05:00
12 changed files with 72 additions and 145 deletions

View File

@ -2,7 +2,7 @@ export const POPULAR_THEMES = [
{
name: "Graceful",
value: "https://github.com/discourse/graceful",
preview: "https://discourse.theme-creator.io/theme/awesomerobot/graceful",
preview: "https://theme-creator.discourse.org/theme/awesomerobot/graceful",
description: "A light and graceful theme for Discourse.",
meta_url:
"https://meta.discourse.org/t/a-graceful-theme-for-discourse/93040",
@ -10,7 +10,8 @@ export const POPULAR_THEMES = [
{
name: "Material Design Theme",
value: "https://github.com/discourse/material-design-stock-theme",
preview: "https://discourse.theme-creator.io/theme/tshenry/material-design",
preview:
"https://theme-creator.discourse.org/theme/tshenry/material-design",
description:
"Inspired by Material Design, this theme comes with several color palettes (incl. a dark one).",
meta_url: "https://meta.discourse.org/t/material-design-stock-theme/47142",
@ -18,7 +19,7 @@ export const POPULAR_THEMES = [
{
name: "Minima",
value: "https://github.com/discourse/minima",
preview: "https://discourse.theme-creator.io/theme/awesomerobot/minima",
preview: "https://theme-creator.discourse.org/theme/awesomerobot/minima",
description: "A minimal theme with reduced UI elements and focus on text.",
meta_url:
"https://meta.discourse.org/t/minima-a-minimal-theme-for-discourse/108178",
@ -26,7 +27,7 @@ export const POPULAR_THEMES = [
{
name: "Sam's Simple Theme",
value: "https://github.com/discourse/discourse-simple-theme",
preview: "https://discourse.theme-creator.io/theme/sam/simple",
preview: "https://theme-creator.discourse.org/theme/sam/simple",
description:
"Simplified front page design with classic colors and typography.",
meta_url:
@ -35,8 +36,6 @@ export const POPULAR_THEMES = [
{
name: "Brand Header",
value: "https://github.com/discourse/discourse-brand-header",
preview:
"https://discourse.theme-creator.io/theme/vinothkannans/brand-header",
description:
"Add an extra top header with your logo, navigation links and social icons.",
meta_url: "https://meta.discourse.org/t/brand-header-theme-component/77977",
@ -46,7 +45,7 @@ export const POPULAR_THEMES = [
name: "Custom Header Links",
value: "https://github.com/discourse/discourse-custom-header-links",
preview:
"https://discourse.theme-creator.io/theme/awesomerobot/custom-header-links",
"https://theme-creator.discourse.org/theme/Johani/custom-header-links",
description: "Easily add custom text-based links to the header.",
meta_url: "https://meta.discourse.org/t/custom-header-links/90588",
component: true,
@ -62,7 +61,7 @@ export const POPULAR_THEMES = [
name: "Category Banners",
value: "https://github.com/discourse/discourse-category-banners",
preview:
"https://discourse.theme-creator.io/theme/awesomerobot/discourse-category-banners",
"https://theme-creator.discourse.org/theme/awesomerobot/discourse-category-banners",
description:
"Show banners on category pages using your existing category details.",
meta_url: "https://meta.discourse.org/t/discourse-category-banners/86241",
@ -71,7 +70,7 @@ export const POPULAR_THEMES = [
{
name: "Kanban Board",
value: "https://github.com/discourse/discourse-kanban-theme",
preview: "https://discourse.theme-creator.io/theme/david/kanban",
preview: "https://theme-creator.discourse.org/theme/david/kanban",
description: "Display and organize topics using a Kanban board interface.",
meta_url:
"https://meta.discourse.org/t/kanban-board-theme-component/118164",
@ -85,19 +84,10 @@ export const POPULAR_THEMES = [
meta_url: "https://meta.discourse.org/t/hamburger-theme-selector/61210",
component: true,
},
{
name: "Sidebar Theme Toggle",
value: "https://github.com/discourse/discourse-sidebar-theme-toggle",
description:
"Displays a theme selector in the sidebar menus footer provided there is more than one user-selectable theme.",
meta_url: "https://meta.discourse.org/t/sidebar-theme-toggle/242802",
component: true,
},
{
name: "Header Submenus",
value: "https://github.com/discourse/discourse-header-submenus",
preview:
"https://discourse.theme-creator.io/theme/awesomerobot/header-submenus",
preview: "https://theme-creator.discourse.org/theme/Johani/header-submenus",
description: "Lets you build a header menu with submenus (dropdowns).",
meta_url: "https://meta.discourse.org/t/header-submenus/94584",
component: true,
@ -114,7 +104,7 @@ export const POPULAR_THEMES = [
{
name: "Easy Responsive Footer",
value: "https://github.com/discourse/Discourse-easy-footer",
preview: "https://discourse.theme-creator.io/theme/Johani/easy-footer",
preview: "https://theme-creator.discourse.org/theme/Johani/easy-footer",
description: "Add a fully responsive footer without writing any HTML.",
meta_url: "https://meta.discourse.org/t/easy-responsive-footer/95818",
component: true,

View File

@ -102,8 +102,13 @@ class TagsController < ::ApplicationController
Discourse.filters.each do |filter|
define_method("show_#{filter}") do
@tag_id = params[:tag_id].force_encoding("UTF-8")
@additional_tags =
params[:additional_tag_ids].to_s.split("/").map { |t| t.force_encoding("UTF-8") }
if params[:additional_tag_ids]
@additional_tags = params[:additional_tag_ids].to_s.split("/")
elsif params[:tags]
# Set additional tags to all passed tags excluding the primary tag (tag_id)
@additional_tags = params[:tags].reject { |t| t == params[:tag_id] }
end
@additional_tags = @additional_tags&.map { |t| t.force_encoding("UTF-8") }
list_opts = build_topic_list_options
@list = nil
@ -483,6 +488,9 @@ class TagsController < ::ApplicationController
def url_method(opts = {})
if opts[:category_slug_path_with_id]
"tag_category_#{action_name}_path"
# expect tag intersection if multiple tags are present
elsif opts[:tags] && opts[:tags].length > 1
"tag_intersection_path"
else
"tag_#{action_name}_path"
end

View File

@ -46,8 +46,7 @@ class Bookmark < ActiveRecord::Base
validates :name, length: { maximum: 100 }
def registered_bookmarkable
type = Bookmark.polymorphic_class_for(self.bookmarkable_type).name
Bookmark.registered_bookmarkable_from_type(type)
Bookmark.registered_bookmarkable_from_type(self.bookmarkable_type)
end
def polymorphic_columns_present

View File

@ -213,10 +213,7 @@ task "docker:test" do
@good &&= run_or_fail("bundle exec rspec #{params.join(" ")}".strip)
end
if ENV["RUN_SYSTEM_TESTS"]
@good &&= run_or_fail("bin/ember-cli --build")
@good &&= run_or_fail("bundle exec rspec spec/system")
end
@good &&= run_or_fail("bundle exec rspec spec/system".strip) if ENV["RUN_SYSTEM_TESTS"]
end
unless ENV["SKIP_PLUGINS"]

View File

@ -613,7 +613,6 @@ export default class ChatLivePane extends Component {
const message = ChatMessage.create(this.args.channel, data.chat_message);
this.args.channel.addMessages([message]);
this.scrollToLatestMessage();
this.updateLastReadMessage();
} else {
// If we are almost at the bottom, we append the message and notice the user
const message = ChatMessage.create(this.args.channel, data.chat_message);
@ -896,19 +895,16 @@ export default class ChatLivePane extends Component {
@action
editLastMessageRequested() {
const lastUserMessage = this.args.channel.messages.findLast(
(message) => message.user.id === this.currentUser.id
(message) =>
message.user.id === this.currentUser.id &&
!message.staged &&
!message.error
);
if (!lastUserMessage) {
return;
if (lastUserMessage) {
this.editingMessage = lastUserMessage;
this._focusComposer();
}
if (lastUserMessage.staged || lastUserMessage.error) {
return;
}
this.editingMessage = lastUserMessage;
this._focusComposer();
}
@action

View File

@ -2,18 +2,30 @@
{{#if this.hasUploads}}
{{html-safe @cooked}}
<Collapser @header={{this.uploadsHeader}} @onToggle={{@onToggleCollapse}}>
<div class="chat-uploads">
{{#each @uploads as |upload|}}
<ChatUpload @upload={{upload}} />
{{/each}}
</div>
<Collapser
@header={{this.uploadsHeader}}
@onToggle={{@onToggleCollapse}}
as |collapsed|
>
{{#unless collapsed}}
<div class="chat-uploads">
{{#each @uploads as |upload|}}
<ChatUpload @upload={{upload}} />
{{/each}}
</div>
{{/unless}}
</Collapser>
{{else}}
{{#each this.cookedBodies as |cooked|}}
{{#if cooked.needsCollapser}}
<Collapser @header={{cooked.header}} @onToggle={{@onToggleCollapse}}>
{{cooked.body}}
<Collapser
@header={{cooked.header}}
@onToggle={{@onToggleCollapse}}
as |collapsed|
>
{{#unless collapsed}}
{{cooked.body}}
{{/unless}}
</Collapser>
{{else}}
{{cooked.body}}

View File

@ -384,7 +384,6 @@ $float-height: 530px;
.d-icon {
color: var(--secondary);
margin-left: 1px; // "fixes" the 1px svg shift
}
}

View File

@ -56,9 +56,7 @@
}
.chat-message-separator__text-container {
align-items: center;
display: flex;
height: 40px;
padding-top: 7px;
position: sticky;
top: -1px;
@ -100,7 +98,11 @@
.chat-message-separator__line {
border-top: 1px solid var(--secondary-high);
left: 0;
margin: 0 0 -1px;
position: relative;
right: 0;
top: -1px;
}
}
}

View File

@ -1,41 +0,0 @@
# frozen_string_literal: true
RSpec.describe BookmarksController do
let(:current_user) { Fabricate(:user) }
let(:bookmark_message) { Fabricate(:chat_message) }
let(:bookmark_user) { current_user }
before do
register_test_bookmarkable(Chat::MessageBookmarkable)
sign_in(current_user)
end
after { DiscoursePluginRegistry.reset_register!(:bookmarkables) }
context "when bookmarking a chat message" do
describe "#create" do
it "creates the bookmark" do
post "/bookmarks.json",
params: {
bookmarkable_id: bookmark_message.id,
bookmarkable_type: "Chat::Message",
reminder_at: (Time.zone.now + 1.day).iso8601,
}
expect(response.status).to eq(200)
expect(Bookmark.find_by(bookmarkable: bookmark_message).user_id).to eq(current_user.id)
end
end
describe "#destroy" do
let!(:bookmark) { Fabricate(:bookmark, bookmarkable: bookmark_message, user: bookmark_user) }
it "destroys the bookmark" do
delete "/bookmarks/#{bookmark.id}.json"
expect(response.status).to eq(200)
expect(Bookmark.find_by(id: bookmark.id)).to eq(nil)
end
end
end
end

View File

@ -1,39 +0,0 @@
# frozen_string_literal: true
RSpec.describe "Channel message selection", type: :system, js: true do
fab!(:current_user) { Fabricate(:user) }
fab!(:channel_1) { Fabricate(:chat_channel) }
fab!(:message_1) { Fabricate(:chat_message, chat_channel: channel_1) }
let(:chat) { PageObjects::Pages::Chat.new }
let(:channel) { PageObjects::Pages::ChatChannel.new }
let(:image) do
Fabricate(
:upload,
original_filename: "test_image.jpg",
width: 400,
height: 300,
extension: "jpg",
)
end
before do
chat_system_bootstrap
channel_1.add(current_user)
sign_in(current_user)
message_1.attach_uploads([image])
end
it "can collapse/expand an image and still have lightbox working" do
chat.visit_channel(channel_1)
find(".chat-message-collapser-button").click
expect(page).to have_css(".chat-message-collapser-body.hidden", visible: :false)
find(".chat-message-collapser-button").click
expect(page).to have_no_css(".chat-message-collapser-body.hidden")
find(".chat-img-upload").click
# visible false is because the upload doesnt exist but it's enough to know lightbox is working
expect(page).to have_css(".mfp-image-holder img[src*='#{image.url}']", visible: false)
end
end

View File

@ -70,19 +70,5 @@ RSpec.describe "Shortcuts | chat composer", type: :system, js: true do
expect(page.find(".chat-composer-message-details")).to have_content(message_1.message)
end
context "when last message is not editable" do
after { page.driver.browser.network_conditions = { offline: false } }
it "does not edit a message" do
chat.visit_channel(channel_1)
page.driver.browser.network_conditions = { offline: true }
channel_page.send_message("Hello world")
find(".chat-composer-input").send_keys(:arrow_up)
expect(page).to have_no_css(".chat-composer-message-details")
end
end
end
end

View File

@ -392,6 +392,24 @@ RSpec.describe TagsController do
end
end
end
context "with a tag intersection" do
it "should generate a tag intersection `load_more_topic` url" do
tag = Fabricate(:tag)
tag_2 = Fabricate(:tag)
# Create topics with both tags included
3.times { Fabricate(:topic, tags: [tag, tag_2]) }
sign_in(admin)
get "/tags/intersection/#{tag.name}/#{tag_2.name}.json?per_page=2"
expect(response.status).to eq(200)
expect(response.parsed_body["topic_list"]["more_topics_url"]).to eq(
"/tags/intersection/#{tag.name}/#{tag_2.name}?match_all_tags=true&page=1&per_page=2&tags%5B%5D=#{tag.name}&tags%5B%5D=#{tag_2.name}",
)
end
end
end
describe "#show" do