Send Contact entity for start/stop sharing

Related to diaspora/diaspora_federation#32
This commit is contained in:
Benjamin Neff 2017-04-30 14:15:21 +02:00
parent f6dc809e29
commit e907b3eb18
No known key found for this signature in database
GPG key ID: 971464C3F1A90194
11 changed files with 80 additions and 117 deletions

View file

@ -34,6 +34,7 @@ class User
if contact.person.local? if contact.person.local?
contact.person.owner.disconnected_by(contact.user.person) contact.person.owner.disconnected_by(contact.user.person)
else else
contact.receiving = false
Retraction.for(contact).defer_dispatch(self) Retraction.for(contact).defer_dispatch(self)
end end

View file

@ -21,10 +21,10 @@ class Retraction
when Post when Post
Diaspora::Federation::Entities.signed_retraction(target, sender) Diaspora::Federation::Entities.signed_retraction(target, sender)
else else
Diaspora::Federation::Entities.retraction(target) Diaspora::Federation::Entities.retraction_data_for(target)
end end
new(federation_retraction.to_h, target.subscribers.select(&:remote?), target) new(federation_retraction, target.subscribers.select(&:remote?), target)
end end
def defer_dispatch(user, include_target_author=true) def defer_dispatch(user, include_target_author=true)

View file

@ -5,17 +5,6 @@ module Diaspora
public_send(Mappings.builder_for(entity.class), entity) public_send(Mappings.builder_for(entity.class), entity)
end end
def self.build_retraction(retraction)
case retraction.data[:target_type]
when "Comment", "Like", "PollParticipation"
DiasporaFederation::Entities::RelayableRetraction.new(retraction.data)
when "Post"
DiasporaFederation::Entities::SignedRetraction.new(retraction.data)
else
DiasporaFederation::Entities::Retraction.new(retraction.data)
end
end
def self.post(post) def self.post(post)
case post case post
when StatusMessage when StatusMessage
@ -50,10 +39,11 @@ module Diaspora
end end
def self.contact(contact) def self.contact(contact)
# TODO: use DiasporaFederation::Entities::Contact DiasporaFederation::Entities::Contact.new(
DiasporaFederation::Entities::Request.new(
author: contact.user.diaspora_handle, author: contact.user.diaspora_handle,
recipient: contact.person.diaspora_handle recipient: contact.person.diaspora_handle,
sharing: contact.receiving,
following: contact.receiving
) )
end end
@ -182,7 +172,7 @@ module Diaspora
target_type: Mappings.entity_name_for(target), target_type: Mappings.entity_name_for(target),
target: related_entity(target), target: related_entity(target),
author: sender.diaspora_handle author: sender.diaspora_handle
) ).to_h
end end
def self.reshare(reshare) def self.reshare(reshare)
@ -197,24 +187,30 @@ module Diaspora
) )
end end
def self.retraction(target) def self.retraction(retraction)
case retraction.data[:target_type]
when "Comment", "Like", "PollParticipation"
DiasporaFederation::Entities::RelayableRetraction.new(retraction.data)
when "Post"
DiasporaFederation::Entities::SignedRetraction.new(retraction.data)
when "Contact"
DiasporaFederation::Entities::Contact.new(retraction.data)
else
DiasporaFederation::Entities::Retraction.new(retraction.data)
end
end
def self.retraction_data_for(target)
case target case target
when Contact when Contact
# TODO: deprecated contact(target).to_h.tap {|data| data[:target_type] = "Contact" }
author = target.user.diaspora_handle
DiasporaFederation::Entities::Retraction.new(
target_guid: target.user.guid,
target_type: "Person",
target: DiasporaFederation::Entities::RelatedEntity.new(author: author, local: true),
author: author
)
else else
DiasporaFederation::Entities::Retraction.new( DiasporaFederation::Entities::Retraction.new(
target_guid: target.guid, target_guid: target.guid,
target_type: Mappings.entity_name_for(target), target_type: Mappings.entity_name_for(target),
target: related_entity(target), target: related_entity(target),
author: target.diaspora_handle author: target.diaspora_handle
) ).to_h
end end
end end
@ -225,7 +221,7 @@ module Diaspora
target_type: Mappings.entity_name_for(target), target_type: Mappings.entity_name_for(target),
target: related_entity(target), target: related_entity(target),
author: sender.diaspora_handle author: sender.diaspora_handle
) ).to_h
end end
def self.status_message(status_message) def self.status_message(status_message)

View file

@ -49,7 +49,7 @@ module Diaspora
PollParticipation => :poll_participation, PollParticipation => :poll_participation,
Profile => :profile, Profile => :profile,
Reshare => :reshare, Reshare => :reshare,
Retraction => :build_retraction, Retraction => :retraction,
StatusMessage => :status_message StatusMessage => :status_message
}.freeze }.freeze

View file

@ -25,7 +25,7 @@ module Diaspora
def self.contact(entity) def self.contact(entity)
recipient = Person.find_by(diaspora_handle: entity.recipient).owner recipient = Person.find_by(diaspora_handle: entity.recipient).owner
if entity.sharing.to_s == "true" if entity.sharing
Contact.create_or_update_sharing_contact(recipient, author_of(entity)) Contact.create_or_update_sharing_contact(recipient, author_of(entity))
else else
recipient.disconnected_by(author_of(entity)) recipient.disconnected_by(author_of(entity))

View file

@ -49,9 +49,10 @@ describe "attack vectors", type: :request do
it "should not receive retractions where the retractor and the salmon author do not match" do it "should not receive retractions where the retractor and the salmon author do not match" do
original_message = eve.post(:status_message, text: "store this!", to: eves_aspect.id) original_message = eve.post(:status_message, text: "store this!", to: eves_aspect.id)
retraction = Retraction.for(original_message)
expect { expect {
post_message(generate_xml(Diaspora::Federation::Entities.retraction(original_message), alice, bob), bob) post_message(generate_xml(Diaspora::Federation::Entities.retraction(retraction), alice, bob), bob)
}.to_not change { bob.visible_shareables(Post).count(:all) } }.to_not change { bob.visible_shareables(Post).count(:all) }
end end
@ -61,7 +62,7 @@ describe "attack vectors", type: :request do
contact = bob.contacts(true).find_by(person_id: eve.person.id) contact = bob.contacts(true).find_by(person_id: eve.person.id)
expect(contact).to be_sharing expect(contact).to be_sharing
post_message(generate_xml(Diaspora::Federation::Entities.retraction(contact), alice, bob), bob) post_message(generate_xml(Diaspora::Federation::Entities.retraction(Retraction.for(contact)), alice, bob), bob)
expect(bob.contacts(true).find_by(person_id: eve.person.id)).to be_sharing expect(bob.contacts(true).find_by(person_id: eve.person.id)).to be_sharing
end end

View file

@ -73,8 +73,8 @@ describe "Receive federation messages feature" do
context "with private receive" do context "with private receive" do
let(:recipient) { alice } let(:recipient) { alice }
it "treats sharing request recive correctly" do it "treats sharing request receive correctly" do
entity = Fabricate(:request_entity, author: sender_id, recipient: alice.diaspora_handle) entity = Fabricate(:contact_entity, author: sender_id, recipient: alice.diaspora_handle)
expect(Workers::ReceiveLocal).to receive(:perform_async).and_call_original expect(Workers::ReceiveLocal).to receive(:perform_async).and_call_original

View file

@ -42,7 +42,7 @@ describe Retraction do
it "creates a retraction for a contact" do it "creates a retraction for a contact" do
contact = FactoryGirl.create(:contact) contact = FactoryGirl.create(:contact)
expect(Diaspora::Federation::Entities).to receive(:retraction).with(contact) expect(Diaspora::Federation::Entities).to receive(:retraction_data_for).with(contact)
Retraction.for(contact, contact.user) Retraction.for(contact, contact.user)
end end

View file

@ -36,13 +36,15 @@ describe Diaspora::Federation::Entities do
expect(federation_entity.additional_data).to eq(diaspora_entity.signature.additional_data) expect(federation_entity.additional_data).to eq(diaspora_entity.signature.additional_data)
end end
it "builds a contact (request)" do it "builds a contact" do
diaspora_entity = FactoryGirl.build(:contact) diaspora_entity = FactoryGirl.build(:contact, receiving: true)
federation_entity = described_class.build(diaspora_entity) federation_entity = described_class.build(diaspora_entity)
expect(federation_entity).to be_instance_of(DiasporaFederation::Entities::Request) expect(federation_entity).to be_instance_of(DiasporaFederation::Entities::Contact)
expect(federation_entity.author).to eq(diaspora_entity.user.diaspora_handle) expect(federation_entity.author).to eq(diaspora_entity.user.diaspora_handle)
expect(federation_entity.recipient).to eq(diaspora_entity.person.diaspora_handle) expect(federation_entity.recipient).to eq(diaspora_entity.person.diaspora_handle)
expect(federation_entity.sharing).to be_truthy
expect(federation_entity.following).to be_truthy
end end
context "Conversation" do context "Conversation" do
@ -205,6 +207,31 @@ describe Diaspora::Federation::Entities do
expect(federation_entity.provider_display_name).to eq(diaspora_entity.provider_display_name) expect(federation_entity.provider_display_name).to eq(diaspora_entity.provider_display_name)
end end
context "Retraction" do
it "builds a Retraction entity for a Photo retraction" do
target = FactoryGirl.create(:photo, author: alice.person)
retraction = Retraction.for(target)
federation_entity = described_class.build(retraction)
expect(federation_entity).to be_instance_of(DiasporaFederation::Entities::Retraction)
expect(federation_entity.author).to eq(target.author.diaspora_handle)
expect(federation_entity.target_guid).to eq(target.guid)
expect(federation_entity.target_type).to eq("Photo")
end
it "builds a Contact for a Contact retraction" do
target = FactoryGirl.create(:contact, receiving: false)
retraction = Retraction.for(target)
federation_entity = described_class.build(retraction)
expect(federation_entity).to be_instance_of(DiasporaFederation::Entities::Contact)
expect(federation_entity.author).to eq(target.user.diaspora_handle)
expect(federation_entity.recipient).to eq(target.person.diaspora_handle)
expect(federation_entity.sharing).to be_falsey
expect(federation_entity.following).to be_falsey
end
end
context "StatusMessage" do context "StatusMessage" do
it "builds a status message" do it "builds a status message" do
diaspora_entity = FactoryGirl.create(:status_message) diaspora_entity = FactoryGirl.create(:status_message)
@ -274,88 +301,25 @@ describe Diaspora::Federation::Entities do
end end
end end
describe ".build_retraction" do describe ".retraction_data_for" do
context "Retraction" do it "returns the data for a Photo retraction" do
it "builds a Retraction for a Photo" do
target = FactoryGirl.create(:photo, author: alice.person) target = FactoryGirl.create(:photo, author: alice.person)
retraction = Retraction.for(target, alice) retraction_data = described_class.retraction_data_for(target)
federation_retraction = described_class.build_retraction(retraction)
expect(federation_retraction).to be_instance_of(DiasporaFederation::Entities::Retraction) expect(retraction_data[:author]).to eq(target.author.diaspora_handle)
expect(federation_retraction.author).to eq(target.author.diaspora_handle) expect(retraction_data[:target_guid]).to eq(target.guid)
expect(federation_retraction.target_guid).to eq(target.guid) expect(retraction_data[:target_type]).to eq("Photo")
expect(federation_retraction.target_type).to eq("Photo")
end end
it "builds a Retraction for a Contact" do it "returns the data for a Contact entity" do
target = FactoryGirl.create(:contact) target = FactoryGirl.create(:contact, receiving: false)
retraction = Retraction.for(target, target.user) retraction_data = described_class.retraction_data_for(target)
federation_retraction = described_class.build_retraction(retraction)
expect(federation_retraction).to be_instance_of(DiasporaFederation::Entities::Retraction) expect(retraction_data[:author]).to eq(target.user.diaspora_handle)
expect(federation_retraction.author).to eq(target.user.diaspora_handle) expect(retraction_data[:recipient]).to eq(target.person.diaspora_handle)
expect(federation_retraction.target_guid).to eq(target.user.guid) expect(retraction_data[:sharing]).to be_falsey
expect(federation_retraction.target_type).to eq("Person") expect(retraction_data[:following]).to be_falsey
end expect(retraction_data[:target_type]).to eq("Contact")
end
context "SignedRetraction" do
it "builds a SignedRetraction for a StatusMessage" do
target = FactoryGirl.create(:status_message, author: alice.person)
retraction = Retraction.for(target, alice)
federation_retraction = described_class.build_retraction(retraction)
expect(federation_retraction).to be_instance_of(DiasporaFederation::Entities::SignedRetraction)
expect(federation_retraction.author).to eq(target.author.diaspora_handle)
expect(federation_retraction.target_guid).to eq(target.guid)
expect(federation_retraction.target_type).to eq("Post")
end
it "builds a SignedRetraction for a Reshare" do
target = FactoryGirl.create(:reshare, author: alice.person)
retraction = Retraction.for(target, alice)
federation_retraction = described_class.build_retraction(retraction)
expect(federation_retraction).to be_instance_of(DiasporaFederation::Entities::SignedRetraction)
expect(federation_retraction.author).to eq(target.author.diaspora_handle)
expect(federation_retraction.target_guid).to eq(target.guid)
expect(federation_retraction.target_type).to eq("Post")
end
end
context "RelayableRetraction" do
it "builds a RelayableRetraction for a Comment" do
target = FactoryGirl.create(:comment, author: alice.person)
retraction = Retraction.for(target, alice)
federation_retraction = described_class.build_retraction(retraction)
expect(federation_retraction).to be_instance_of(DiasporaFederation::Entities::RelayableRetraction)
expect(federation_retraction.author).to eq(alice.diaspora_handle)
expect(federation_retraction.target_guid).to eq(target.guid)
expect(federation_retraction.target_type).to eq("Comment")
end
it "builds a RelayableRetraction for a Like" do
target = FactoryGirl.create(:like, author: alice.person)
retraction = Retraction.for(target, alice)
federation_retraction = described_class.build_retraction(retraction)
expect(federation_retraction).to be_instance_of(DiasporaFederation::Entities::RelayableRetraction)
expect(federation_retraction.author).to eq(alice.diaspora_handle)
expect(federation_retraction.target_guid).to eq(target.guid)
expect(federation_retraction.target_type).to eq("Like")
end
it "builds a RelayableRetraction for a PollParticipation" do
target = FactoryGirl.create(:poll_participation, author: alice.person)
retraction = Retraction.for(target, alice)
federation_retraction = described_class.build_retraction(retraction)
expect(federation_retraction).to be_instance_of(DiasporaFederation::Entities::RelayableRetraction)
expect(federation_retraction.author).to eq(alice.diaspora_handle)
expect(federation_retraction.target_guid).to eq(target.guid)
expect(federation_retraction.target_type).to eq("PollParticipation")
end
end end
end end
end end

View file

@ -103,7 +103,7 @@ describe Diaspora::Federation::Receive do
:contact_entity, :contact_entity,
author: sender.diaspora_handle, author: sender.diaspora_handle,
recipient: alice.diaspora_handle, recipient: alice.diaspora_handle,
sharing: "false" sharing: false
) )
} }

View file

@ -87,6 +87,7 @@ describe User::Connecting, type: :model do
contact = local_leia.contact_for(remote_raphael) contact = local_leia.contact_for(remote_raphael)
retraction = double retraction = double
expect(contact).to receive(:receiving=).with(false)
expect(Retraction).to receive(:for).with(contact).and_return(retraction) expect(Retraction).to receive(:for).with(contact).and_return(retraction)
expect(retraction).to receive(:defer_dispatch).with(local_leia) expect(retraction).to receive(:defer_dispatch).with(local_leia)