FIX: Clashing category slug.

This commit is contained in:
Guo Xiang Tan 2016-01-12 16:40:36 +08:00
parent 65e808b26d
commit c60e360c90
10 changed files with 65 additions and 14 deletions

View File

@ -255,7 +255,7 @@ export default Ember.Component.extend({
template: template,
key: '#',
transformComplete(category) {
return category.get('slug');
return Category.slugFor(category, ":");
},
dataSource(term) {
return Category.search(term);

View File

@ -4,7 +4,7 @@
**/
Discourse.Dialect.inlineRegexp({
start: '#',
matcher: /^#([\w-]{1,50})/i,
matcher: /^#([\w-:]{1,50})/i,
spaceOrTagBoundary: true,
emitter: function(matches) {

View File

@ -205,14 +205,14 @@ Category.reopenClass({
return _uncategorized;
},
slugFor(category) {
slugFor(category, separator = "/") {
if (!category) return "";
const parentCategory = Em.get(category, 'parentCategory');
let result = "";
if (parentCategory) {
result = Category.slugFor(parentCategory) + "/";
result = Category.slugFor(parentCategory) + separator;
}
const id = Em.get(category, 'id'),

View File

@ -5,8 +5,10 @@ class CategoryHashtagsController < ApplicationController
category_slugs = params[:category_slugs]
category_slugs.each(&:downcase!)
valid_categories = Category.secured(guardian).where(slug: category_slugs).map do |category|
{ slug: category.slug, url: category.url_with_id }
ids = category_slugs.map { |category_slug| Category.query_from_hashtag_slug(category_slug).try(:id) }
valid_categories = Category.secured(guardian).where(id: ids).map do |category|
{ slug: category.hashtag_slug, url: category.url_with_id }
end.compact
render json: { valid: valid_categories }

View File

@ -5,6 +5,7 @@ class Category < ActiveRecord::Base
include Positionable
include HasCustomFields
include CategoryHashtag
belongs_to :topic, dependent: :destroy
belongs_to :topic_only_relative_url,
@ -398,8 +399,8 @@ SQL
@@url_cache.clear
end
def full_slug
url[3..-1].gsub("/", "-")
def full_slug(separator = "-")
url[3..-1].gsub("/", separator)
end
def url

View File

@ -0,0 +1,23 @@
module CategoryHashtag
extend ActiveSupport::Concern
SEPARATOR = ":".freeze
class_methods do
def query_from_hashtag_slug(category_slug)
parent_slug, child_slug = category_slug.split(":", 2)
category = Category.where(slug: parent_slug, parent_category_id: nil)
if child_slug
Category.where(slug: child_slug, parent_category_id: category.pluck(:id).first).first
else
category.first
end
end
end
def hashtag_slug
full_slug(SEPARATOR)
end
end

View File

@ -49,9 +49,8 @@ module PrettyText
end
def category_hashtag_lookup(category_slug)
if category_slug
category = Category.find_by_slug(category_slug)
return ['category', category.url_with_id] if category
if category = Category.query_from_hashtag_slug(category_slug)
['category', category.url_with_id]
else
nil
end

View File

@ -0,0 +1,26 @@
require 'rails_helper'
describe CategoryHashtag do
describe '#query_from_hashtag_slug' do
let(:parent_category) { Fabricate(:category) }
let(:child_category) { Fabricate(:category, parent_category: parent_category) }
it "should return the right result for a parent category slug" do
expect(Category.query_from_hashtag_slug(parent_category.slug))
.to eq(parent_category)
end
it "should return the right result for a parent and child category slug" do
expect(Category.query_from_hashtag_slug("#{parent_category.slug}:#{child_category.slug}"))
.to eq(child_category)
end
it "should return nil for incorrect parent category slug" do
expect(Category.query_from_hashtag_slug("random-slug")).to eq(nil)
end
it "should return nil for incorrect parent and child category slug" do
expect(Category.query_from_hashtag_slug("random-slug:random-slug")).to eq(nil)
end
end
end

View File

@ -12,7 +12,7 @@ describe CategoryHashtagsController do
xhr :get, :check, category_slugs: [category.slug, 'none']
expect(JSON.parse(response.body)).to eq(
{ "valid" => [{ "slug" => category.slug, "url" => category.url_with_id }] }
{ "valid" => [{ "slug" => category.hashtag_slug, "url" => category.url_with_id }] }
)
end
@ -32,7 +32,7 @@ describe CategoryHashtagsController do
xhr :get, :check, category_slugs: [private_category.slug]
expect(JSON.parse(response.body)).to eq(
{ "valid" => [{ "slug" => private_category.slug, "url" => private_category.url_with_id }] }
{ "valid" => [{ "slug" => private_category.hashtag_slug, "url" => private_category.url_with_id }] }
)
end
end