Use old person private key if relayable author migrated away

We only store signatures for relayables if the author is external, but
if the author becomes external through a migration, the signature is
missing. Lets just use the old persons private key to still be able to
generate a signature for the export.

closes #8310
This commit is contained in:
Benjamin Neff 2021-10-27 04:21:25 +02:00
parent 1570e3fb9a
commit eb977dc25a
No known key found for this signature in database
GPG key ID: 971464C3F1A90194
3 changed files with 24 additions and 3 deletions

View file

@ -11,6 +11,7 @@
* Ensure the log folder exists [#8287](https://github.com/diaspora/diaspora/pull/8287) * Ensure the log folder exists [#8287](https://github.com/diaspora/diaspora/pull/8287)
* Limit name length in header [#8313] (https://github.com/diaspora/diaspora/pull/8313) * Limit name length in header [#8313] (https://github.com/diaspora/diaspora/pull/8313)
* Fix fallback avatar in hovercards [#8316](https://github.com/diaspora/diaspora/pull/8316) * Fix fallback avatar in hovercards [#8316](https://github.com/diaspora/diaspora/pull/8316)
* Use old person private key for export if relayable author migrated away [#8310](https://github.com/diaspora/diaspora/pull/8310)
## Features ## Features
* Add tags to tumblr posts [#8244](https://github.com/diaspora/diaspora/pull/8244) * Add tags to tumblr posts [#8244](https://github.com/diaspora/diaspora/pull/8244)

View file

@ -5,11 +5,26 @@
# are used as for federation messages generation. # are used as for federation messages generation.
class FederationEntitySerializer < ActiveModel::Serializer class FederationEntitySerializer < ActiveModel::Serializer
include SerializerPostProcessing include SerializerPostProcessing
include Diaspora::Logging
private private
def modify_serializable_object(hash) def modify_serializable_object(hash)
hash.merge(entity.to_json) hash.merge(entity.to_json)
rescue DiasporaFederation::Entities::Relayable::AuthorPrivateKeyNotFound => e
# The author of this relayable probably migrated from this pod to a different pod,
# and we neither have the signature nor the new private key to generate a valid signature.
# But we can use the private key of the old user to generate the signature it had when this entity was created
old_person = AccountMigration.joins(:old_person)
.where("new_person_id = ? AND people.owner_id IS NOT NULL", object.author_id)
.first.old_person
if old_person
logger.info "Using private key of #{old_person.diaspora_handle} to export: #{e.message}"
object.author = old_person
hash.merge(entity.to_json)
else
logger.warn "Skip entity for export because #{e.class}: #{e.message}"
end
end end
def entity def entity

View file

@ -13,9 +13,14 @@ describe Export::OthersDataSerializer do
serializer.associations serializer.associations
end end
context "with user's activity" do it "uses old local user private key if the author was migrated away from the pod" do
before do post = DataGenerator.new(user).status_message_with_activity
DataGenerator.new(user).activity
old_comment_author = post.comments.first.author
AccountMigration.create!(old_person: old_comment_author, new_person: FactoryGirl.create(:person)).perform!
serializer.associations[:relayables].select {|r| r[:entity_type] == "comment" }.each do |comment|
expect(comment[:entity_data][:author]).to eq(old_comment_author.diaspora_handle)
end end
end end
end end