Merge commit '9437cddda1121cee77f260a1afeec45541e826a0' into glitch-soc/merge-4.3

This commit is contained in:
Claire
2026-02-24 12:05:46 +01:00
7 changed files with 62 additions and 8 deletions

View File

@@ -2,6 +2,16 @@
All notable changes to this project will be documented in this file.
## [4.3.20] - 2026-02-24
### Added
- Add `--suspended-only` option to `tootctl emoji purge` (#37828 and #37861 by @ClearlyClaire and @mjankowski)
### Fixed
- Fix processing of object updates with duplicate hashtags (#37756 by @ClearlyClaire)
## [4.3.19] - 2026-02-03
### Security

View File

@@ -194,7 +194,7 @@ class ActivityPub::ProcessStatusUpdateService < BaseService
Tag.find_or_create_by_names([tag]).filter(&:valid?)
rescue ActiveRecord::RecordInvalid
[]
end
end.uniq
return unless @status.distributable?

View File

@@ -59,7 +59,7 @@ services:
web:
# You can uncomment the following line if you want to not use the prebuilt image, for example if you have local code changes
# build: .
image: ghcr.io/glitch-soc/mastodon:v4.3.19
image: ghcr.io/glitch-soc/mastodon:v4.3.20
restart: always
env_file: .env.production
command: bundle exec puma -C config/puma.rb
@@ -83,7 +83,7 @@ services:
# build:
# dockerfile: ./streaming/Dockerfile
# context: .
image: ghcr.io/glitch-soc/mastodon-streaming:v4.3.19
image: ghcr.io/glitch-soc/mastodon-streaming:v4.3.20
restart: always
env_file: .env.production
command: node ./streaming/index.js
@@ -102,7 +102,7 @@ services:
sidekiq:
# You can uncomment the following line if you want to not use the prebuilt image, for example if you have local code changes
# build: .
image: ghcr.io/glitch-soc/mastodon:v4.3.19
image: ghcr.io/glitch-soc/mastodon:v4.3.20
restart: always
env_file: .env.production
command: bundle exec sidekiq

View File

@@ -107,15 +107,27 @@ module Mastodon::CLI
end
option :remote_only, type: :boolean
option :suspended_only, type: :boolean
desc 'purge', 'Remove all custom emoji'
long_desc <<-LONG_DESC
Removes all custom emoji.
With the --remote-only option, only remote emoji will be deleted.
With the --suspended-only option, only emoji from suspended servers will be deleted.
LONG_DESC
def purge
scope = options[:remote_only] ? CustomEmoji.remote : CustomEmoji
scope.in_batches.destroy_all
if options[:suspended_only]
DomainBlock.where(severity: :suspend).find_each do |domain_block|
CustomEmoji.by_domain_and_subdomains(domain_block.domain).find_in_batches do |custom_emojis|
AttachmentBatch.new(CustomEmoji, custom_emojis).delete
end
end
else
scope = options[:remote_only] ? CustomEmoji.remote : CustomEmoji
scope.in_batches.destroy_all
end
say('OK', :green)
end

View File

@@ -13,7 +13,7 @@ module Mastodon
end
def patch
19
20
end
def default_prerelease

View File

@@ -23,6 +23,36 @@ RSpec.describe Mastodon::CLI::Emoji do
.to output_results('OK')
end
end
context 'with --suspended-only and existing custom emoji on blocked servers' do
let(:blocked_domain) { 'evil.com' }
let(:blocked_subdomain) { 'subdomain.evil.org' }
let(:blocked_domain_without_emoji) { 'blocked.com' }
let(:silenced_domain) { 'silenced.com' }
let(:options) { { suspended_only: true } }
before do
Fabricate(:custom_emoji)
Fabricate(:custom_emoji, domain: blocked_domain)
Fabricate(:custom_emoji, domain: blocked_subdomain)
Fabricate(:custom_emoji, domain: silenced_domain)
Fabricate(:domain_block, severity: :suspend, domain: blocked_domain)
Fabricate(:domain_block, severity: :suspend, domain: 'evil.org')
Fabricate(:domain_block, severity: :suspend, domain: blocked_domain_without_emoji)
Fabricate(:domain_block, severity: :silence, domain: silenced_domain)
end
it 'reports a successful purge' do
expect { subject }
.to output_results('OK')
.and change { CustomEmoji.by_domain_and_subdomains(blocked_domain).count }.to(0)
.and change { CustomEmoji.by_domain_and_subdomains('evil.org').count }.to(0)
.and not_change { CustomEmoji.by_domain_and_subdomains(silenced_domain).count }
.and(not_change { CustomEmoji.local.count })
end
end
end
describe '#import' do

View File

@@ -259,6 +259,8 @@ RSpec.describe ActivityPub::ProcessStatusUpdateService do
{ type: 'Hashtag', name: 'foo' },
{ type: 'Hashtag', name: 'bar' },
{ type: 'Hashtag', name: '#2024' },
{ type: 'Hashtag', name: 'Foo Bar' },
{ type: 'Hashtag', name: 'FooBar' },
],
}
end
@@ -270,7 +272,7 @@ RSpec.describe ActivityPub::ProcessStatusUpdateService do
it 'updates tags and featured tags' do
expect { subject.call(status, json, json) }
.to change { status.tags.reload.pluck(:name) }.from(%w(test foo)).to(%w(foo bar))
.to change { status.tags.reload.pluck(:name) }.from(contain_exactly('test', 'foo')).to(contain_exactly('foo', 'bar', 'foobar'))
.and change { status.account.featured_tags.find_by(name: 'test').statuses_count }.by(-1)
.and change { status.account.featured_tags.find_by(name: 'bar').statuses_count }.by(1)
.and change { status.account.featured_tags.find_by(name: 'bar').last_status_at }.from(nil).to(be_present)