From 38871a5b6b5b5598cf81fc6c991eea056ff6d9b7 Mon Sep 17 00:00:00 2001 From: KMY Date: Tue, 9 Jan 2024 23:16:31 +0900 Subject: [PATCH 1/4] =?UTF-8?q?Fix:=20#442=20=E3=82=AB=E3=82=B9=E3=82=BF?= =?UTF-8?q?=E3=83=A0=E7=B5=B5=E6=96=87=E5=AD=97=E3=81=AEaliases=E3=81=ABnu?= =?UTF-8?q?ll=E3=81=8C=E5=85=A5=E3=82=8B=E5=A0=B4=E5=90=88=E3=81=8C?= =?UTF-8?q?=E3=81=82=E3=82=8B?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/helpers/jsonld_helper.rb | 8 ++++ .../activitypub/parser/custom_emoji_parser.rb | 2 +- app/models/custom_emoji.rb | 2 +- .../rest/custom_emoji_serializer.rb | 10 +++-- .../rest/custom_emoji_serializer_spec.rb | 41 +++++++++++++++++++ 5 files changed, 58 insertions(+), 5 deletions(-) create mode 100644 spec/serializers/rest/custom_emoji_serializer_spec.rb diff --git a/app/helpers/jsonld_helper.rb b/app/helpers/jsonld_helper.rb index 1c976bce57f4ca..46cef6b08762be 100644 --- a/app/helpers/jsonld_helper.rb +++ b/app/helpers/jsonld_helper.rb @@ -51,6 +51,14 @@ def as_array(value) end end + def as_array_ex(value) + if value.is_a?(Hash) + [] + else + as_array(value) + end + end + def value_or_id(value) value.is_a?(String) || value.nil? ? value : value['id'] end diff --git a/app/lib/activitypub/parser/custom_emoji_parser.rb b/app/lib/activitypub/parser/custom_emoji_parser.rb index 68a01c64368b52..0c38f55168dbc4 100644 --- a/app/lib/activitypub/parser/custom_emoji_parser.rb +++ b/app/lib/activitypub/parser/custom_emoji_parser.rb @@ -16,7 +16,7 @@ def shortcode end def aliases - as_array(@json['keywords']) + as_array_ex(@json['keywords']) end def image_remote_url diff --git a/app/models/custom_emoji.rb b/app/models/custom_emoji.rb index 37d2e0dc13721e..c4441f8eff9a88 100644 --- a/app/models/custom_emoji.rb +++ b/app/models/custom_emoji.rb @@ -74,7 +74,7 @@ def copy! domain: nil, shortcode: shortcode, license: license, - aliases: aliases, + aliases: (aliases || []).compact_blank, is_sensitive: is_sensitive ) copy.image = image diff --git a/app/serializers/rest/custom_emoji_serializer.rb b/app/serializers/rest/custom_emoji_serializer.rb index 13aee101d6202d..c3fb1beef11648 100644 --- a/app/serializers/rest/custom_emoji_serializer.rb +++ b/app/serializers/rest/custom_emoji_serializer.rb @@ -5,9 +5,13 @@ class REST::CustomEmojiSerializer < REST::CustomEmojiSlimSerializer # Please update `app/javascript/mastodon/api_types/custom_emoji.ts` when making changes to the attributes - attribute :aliases, if: :aliases? + attribute :aliases - def aliases? - object.respond_to?(:aliases) && object.aliases.present? + def aliases + if object.respond_to?(:aliases) && object.aliases.present? + object.aliases.compact_blank + else + [] + end end end diff --git a/spec/serializers/rest/custom_emoji_serializer_spec.rb b/spec/serializers/rest/custom_emoji_serializer_spec.rb new file mode 100644 index 00000000000000..d1806fd0c0de43 --- /dev/null +++ b/spec/serializers/rest/custom_emoji_serializer_spec.rb @@ -0,0 +1,41 @@ +# frozen_string_literal: true + +require 'rails_helper' + +describe REST::CustomEmojiSerializer do + let(:serialization) { serialized_record_json(record, described_class) } + let(:record) do + Fabricate(:custom_emoji, shortcode: 'ohagi', aliases: aliases) + end + let(:aliases) { [] } + + context 'when empty aliases' do + it 'returns normalized aliases' do + expect(serialization['aliases']).to eq [] + end + end + + context 'when null aliases' do + let(:aliases) { nil } + + it 'returns normalized aliases' do + expect(serialization['aliases']).to eq [] + end + end + + context 'when aliases contains null' do + let(:aliases) { [nil] } + + it 'returns normalized aliases' do + expect(serialization['aliases']).to eq [] + end + end + + context 'when aliases contains normal text' do + let(:aliases) { ['neko'] } + + it 'returns normalized aliases' do + expect(serialization['aliases']).to eq ['neko'] + end + end +end From 942a36a04edfc5024025cfcf05d88b78133a0ea9 Mon Sep 17 00:00:00 2001 From: KMY Date: Wed, 10 Jan 2024 08:39:58 +0900 Subject: [PATCH 2/4] Fix test --- app/models/custom_emoji.rb | 8 ++-- spec/models/custom_emoji_spec.rb | 46 +++++++++++++++++++++ spec/models/form/custom_emoji_batch_spec.rb | 4 +- 3 files changed, 52 insertions(+), 6 deletions(-) diff --git a/app/models/custom_emoji.rb b/app/models/custom_emoji.rb index c4441f8eff9a88..c46196d0c807c9 100644 --- a/app/models/custom_emoji.rb +++ b/app/models/custom_emoji.rb @@ -72,11 +72,11 @@ def object_type def copy! copy = self.class.find_or_initialize_by( domain: nil, - shortcode: shortcode, - license: license, - aliases: (aliases || []).compact_blank, - is_sensitive: is_sensitive + shortcode: shortcode ) + copy.aliases = (aliases || []).compact_blank + copy.license = license + copy.is_sensitive = is_sensitive copy.image = image copy.tap(&:save!) end diff --git a/spec/models/custom_emoji_spec.rb b/spec/models/custom_emoji_spec.rb index 06affd634ab4e2..c3816aac9089a5 100644 --- a/spec/models/custom_emoji_spec.rb +++ b/spec/models/custom_emoji_spec.rb @@ -49,6 +49,52 @@ end end + describe '#copy!' do + subject do + custom_emoji.copy! + described_class.where.not(id: custom_emoji.id).find_by(domain: nil, shortcode: custom_emoji.shortcode) + end + + context 'when a simple case' do + let(:custom_emoji) { Fabricate(:custom_emoji, license: 'Ohagi', aliases: %w(aaa bbb), domain: 'example.com', uri: 'https://example.com/emoji') } + + it 'makes a copy ot the emoji' do + emoji = subject + expect(emoji).to_not be_nil + expect(emoji.license).to eq 'Ohagi' + expect(emoji.aliases).to eq %w(aaa bbb) + end + end + + context 'when local has already same emoji' do + let(:custom_emoji) { Fabricate(:custom_emoji, domain: nil) } + + it 'does not make a copy of the emoji' do + expect(subject).to be_nil + end + end + + context 'when aliases is null' do + let(:custom_emoji) { Fabricate(:custom_emoji, aliases: nil, domain: 'example.com', uri: 'https://example.com/emoji') } + + it 'makes a copy of the emoji but aliases property is normalized' do + emoji = subject + expect(emoji).to_not be_nil + expect(emoji.aliases).to eq [] + end + end + + context 'when aliases contains null' do + let(:custom_emoji) { Fabricate(:custom_emoji, aliases: [nil], domain: 'example.com', uri: 'https://example.com/emoji') } + + it 'makes a copy of the emoji but aliases property is normalized' do + emoji = subject + expect(emoji).to_not be_nil + expect(emoji.aliases).to eq [] + end + end + end + describe '#object_type' do it 'returns :emoji' do custom_emoji = Fabricate(:custom_emoji) diff --git a/spec/models/form/custom_emoji_batch_spec.rb b/spec/models/form/custom_emoji_batch_spec.rb index abeada5d507984..047d155a1d5fd1 100644 --- a/spec/models/form/custom_emoji_batch_spec.rb +++ b/spec/models/form/custom_emoji_batch_spec.rb @@ -95,12 +95,12 @@ end describe 'the copy action' do - let(:custom_emoji) { Fabricate(:custom_emoji) } + let(:custom_emoji) { Fabricate(:custom_emoji, domain: 'example.com', uri: 'https://example.com/emoji') } let(:options) { { action: 'copy', custom_emoji_ids: [custom_emoji.id] } } it 'makes a copy of the emoji' do expect { subject.save } - .to change(CustomEmoji, :count).by(1) + .to change(CustomEmoji, :count).by(2) end end From 814662872e44171bc9148a8158ca186d586d95fd Mon Sep 17 00:00:00 2001 From: KMY Date: Wed, 10 Jan 2024 08:51:47 +0900 Subject: [PATCH 3/4] =?UTF-8?q?Web=E3=81=AE=E3=81=BB=E3=81=86=E3=81=AB?= =?UTF-8?q?=E3=82=82NULL=E3=83=81=E3=82=A7=E3=83=83=E3=82=AF=E3=82=92?= =?UTF-8?q?=E8=BF=BD=E5=8A=A0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/javascript/mastodon/features/emoji/emoji_utils.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/javascript/mastodon/features/emoji/emoji_utils.js b/app/javascript/mastodon/features/emoji/emoji_utils.js index 83bcc9d82f9f14..baf557a2b427c4 100644 --- a/app/javascript/mastodon/features/emoji/emoji_utils.js +++ b/app/javascript/mastodon/features/emoji/emoji_utils.js @@ -12,7 +12,7 @@ const buildSearch = (data) => { } (Array.isArray(strings) ? strings : [strings]).forEach((string) => { - (split ? string.split(/[-|_|\s]+/) : [string]).forEach((s) => { + (split ? string.split(/[-|_|\s]+/) : [string]).filter((s) => s).forEach((s) => { s = s.toLowerCase(); if (search.indexOf(s) === -1) { From 3e25c2d498a5bddf52569275284c6a2f3f867c39 Mon Sep 17 00:00:00 2001 From: KMY Date: Wed, 10 Jan 2024 09:03:08 +0900 Subject: [PATCH 4/4] =?UTF-8?q?=E3=83=AD=E3=83=BC=E3=82=AB=E3=83=AB?= =?UTF-8?q?=E3=81=AE=E3=82=A8=E3=82=A4=E3=83=AA=E3=82=A2=E3=82=B9=E5=90=8D?= =?UTF-8?q?=E3=82=92=E7=B7=A8=E9=9B=86=E3=81=99=E3=82=8B=E3=81=A8=E3=81=93?= =?UTF-8?q?=E3=82=8D=E3=82=82=E3=81=A4=E3=81=84=E3=81=A7=E3=81=AB=E3=82=B9?= =?UTF-8?q?=E3=83=AA=E3=83=A0=E3=81=AB?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/models/custom_emoji.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/models/custom_emoji.rb b/app/models/custom_emoji.rb index c46196d0c807c9..a27ee70370eb4f 100644 --- a/app/models/custom_emoji.rb +++ b/app/models/custom_emoji.rb @@ -96,7 +96,7 @@ def aliases_raw end def aliases_raw=(raw) - aliases = raw.split(',').filter(&:present?).uniq + aliases = raw.split(',').compact_blank.uniq self[:aliases] = aliases end