757 行
28 KiB
Go
757 行
28 KiB
Go
package pub
|
|
|
|
import (
|
|
"context"
|
|
"github.com/go-fed/activity/streams/vocab"
|
|
"github.com/golang/mock/gomock"
|
|
"io/ioutil"
|
|
"net/http"
|
|
"net/http/httptest"
|
|
"net/url"
|
|
"testing"
|
|
)
|
|
|
|
// TestBaseActorSocialProtocol tests the Actor returned with NewCustomActor
|
|
// and only having the SocialProtocol enabled.
|
|
func TestBaseActorSocialProtocol(t *testing.T) {
|
|
// Set up test case
|
|
setupData()
|
|
ctx := context.Background()
|
|
setupFn := func(ctl *gomock.Controller) (delegate *MockDelegateActor, clock *MockClock, a Actor) {
|
|
delegate = NewMockDelegateActor(ctl)
|
|
clock = NewMockClock(ctl)
|
|
a = NewCustomActor(
|
|
delegate,
|
|
/*enableSocialProtocol=*/ true,
|
|
/*enableFederatedProtocol=*/ false,
|
|
clock)
|
|
return
|
|
}
|
|
// Run tests
|
|
t.Run("PostInboxIgnoresNonActivityPubRequest", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
_, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toPostInboxRequest(testCreate)
|
|
// Run the test
|
|
handled, err := a.PostInbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, false)
|
|
assertEqual(t, len(resp.Result().Header), 0)
|
|
})
|
|
t.Run("PostInboxNotAllowed", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
_, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toPostInboxRequest(testCreate))
|
|
// Run the test
|
|
handled, err := a.PostInbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusMethodNotAllowed)
|
|
})
|
|
t.Run("GetInboxIgnoresNonActivityPubRequest", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
_, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toGetInboxRequest()
|
|
// Run the test
|
|
handled, err := a.GetInbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, false)
|
|
assertEqual(t, len(resp.Result().Header), 0)
|
|
})
|
|
t.Run("GetInboxDeniesIfNotAuthenticated", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toGetInboxRequest())
|
|
delegate.EXPECT().AuthenticateGetInbox(ctx, resp, req).DoAndReturn(func(ctx context.Context, resp http.ResponseWriter, req *http.Request) (context.Context, bool, error) {
|
|
resp.WriteHeader(http.StatusForbidden)
|
|
return ctx, false, nil
|
|
})
|
|
// Run the test
|
|
handled, err := a.GetInbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusForbidden)
|
|
})
|
|
t.Run("GetInboxRespondsWithDataAndHeaders", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, clock, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toGetInboxRequest())
|
|
delegate.EXPECT().AuthenticateGetInbox(ctx, resp, req).Return(ctx, true, nil)
|
|
delegate.EXPECT().GetInbox(ctx, req).Return(testOrderedCollectionUniqueElems, nil)
|
|
clock.EXPECT().Now().Return(now())
|
|
// Run the test
|
|
handled, err := a.GetInbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusOK)
|
|
respV := resp.Result()
|
|
assertEqual(t, respV.Header.Get(contentTypeHeader), "application/ld+json; profile=\"https://www.w3.org/ns/activitystreams\"")
|
|
assertEqual(t, respV.Header.Get(dateHeader), nowDateHeader())
|
|
assertNotEqual(t, len(respV.Header.Get(digestHeader)), 0)
|
|
b, err := ioutil.ReadAll(respV.Body)
|
|
assertEqual(t, err, nil)
|
|
assertByteEqual(t, b, []byte(testOrderedCollectionUniqueElemsString))
|
|
})
|
|
t.Run("GetInboxDeduplicatesData", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, clock, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toGetInboxRequest())
|
|
delegate.EXPECT().AuthenticateGetInbox(ctx, resp, req).Return(ctx, true, nil)
|
|
delegate.EXPECT().GetInbox(ctx, req).Return(testOrderedCollectionDupedElems, nil)
|
|
clock.EXPECT().Now().Return(now())
|
|
// Run the test
|
|
_, err := a.GetInbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
respV := resp.Result()
|
|
b, err := ioutil.ReadAll(respV.Body)
|
|
assertEqual(t, err, nil)
|
|
assertByteEqual(t, b, []byte(testOrderedCollectionDedupedElemsString))
|
|
})
|
|
t.Run("PostOutboxIgnoresNonActivityPubRequest", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
_, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toPostOutboxRequest(testCreateNoId)
|
|
// Run the test
|
|
handled, err := a.PostOutbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, false)
|
|
assertEqual(t, len(resp.Result().Header), 0)
|
|
})
|
|
t.Run("PostOutboxDeniesIfNotAuthenticated", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toPostOutboxRequest(testCreateNoId))
|
|
delegate.EXPECT().AuthenticatePostOutbox(ctx, resp, req).DoAndReturn(func(ctx context.Context, resp http.ResponseWriter, req *http.Request) (context.Context, bool, error) {
|
|
resp.WriteHeader(http.StatusForbidden)
|
|
return ctx, false, nil
|
|
})
|
|
// Run the test
|
|
handled, err := a.PostOutbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusForbidden)
|
|
})
|
|
t.Run("PostOutboxBadRequestIfUnknownType", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toPostOutboxUnknownRequest())
|
|
delegate.EXPECT().AuthenticatePostOutbox(ctx, resp, req).Return(ctx, true, nil)
|
|
// Run the test
|
|
handled, err := a.PostOutbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusBadRequest)
|
|
})
|
|
t.Run("PostOutboxRespondsWithDataAndHeaders", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toPostOutboxRequest(testCreateNoId))
|
|
delegate.EXPECT().AuthenticatePostOutbox(ctx, resp, req).Return(ctx, true, nil)
|
|
delegate.EXPECT().PostOutboxRequestBodyHook(ctx, req, toDeserializedForm(testCreateNoId)).Return(ctx, nil)
|
|
delegate.EXPECT().AddNewIDs(ctx, toDeserializedForm(testCreateNoId)).DoAndReturn(func(c context.Context, activity Activity) error {
|
|
withNewId(activity)
|
|
return nil
|
|
})
|
|
delegate.EXPECT().PostOutbox(
|
|
ctx,
|
|
withNewId(toDeserializedForm(testCreateNoId)),
|
|
mustParse(testMyOutboxIRI),
|
|
mustSerialize(testCreateNoId),
|
|
).Return(true, nil)
|
|
// Run the test
|
|
handled, err := a.PostOutbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusCreated)
|
|
respV := resp.Result()
|
|
assertEqual(t, respV.Header.Get(locationHeader), testNewActivityIRI)
|
|
})
|
|
t.Run("PostOutboxWrapsInCreate", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toPostOutboxRequest(testMyNote))
|
|
delegate.EXPECT().AuthenticatePostOutbox(ctx, resp, req).Return(ctx, true, nil)
|
|
delegate.EXPECT().PostOutboxRequestBodyHook(ctx, req, toDeserializedForm(testMyNote)).Return(ctx, nil)
|
|
delegate.EXPECT().WrapInCreate(ctx, toDeserializedForm(testMyNote), mustParse(testMyOutboxIRI)).DoAndReturn(func(c context.Context, t vocab.Type, u *url.URL) (vocab.ActivityStreamsCreate, error) {
|
|
return wrappedInCreate(t), nil
|
|
})
|
|
delegate.EXPECT().AddNewIDs(ctx, wrappedInCreate(toDeserializedForm(testMyNote))).DoAndReturn(func(c context.Context, activity Activity) error {
|
|
withNewId(activity)
|
|
return nil
|
|
})
|
|
delegate.EXPECT().PostOutbox(
|
|
ctx,
|
|
withNewId(wrappedInCreate(toDeserializedForm(testMyNote))),
|
|
mustParse(testMyOutboxIRI),
|
|
mustSerialize(toDeserializedForm(testMyNote)),
|
|
).Return(true, nil)
|
|
// Run the test
|
|
handled, err := a.PostOutbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusCreated)
|
|
})
|
|
t.Run("PostOutboxBadRequestForErrObjectRequired", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toPostOutboxRequest(testCreateNoId))
|
|
delegate.EXPECT().AuthenticatePostOutbox(ctx, resp, req).Return(ctx, true, nil)
|
|
delegate.EXPECT().PostOutboxRequestBodyHook(ctx, req, toDeserializedForm(testCreateNoId)).Return(ctx, nil)
|
|
delegate.EXPECT().AddNewIDs(ctx, toDeserializedForm(testCreateNoId)).DoAndReturn(func(c context.Context, activity Activity) error {
|
|
withNewId(activity)
|
|
return nil
|
|
})
|
|
delegate.EXPECT().PostOutbox(
|
|
ctx,
|
|
withNewId(toDeserializedForm(testCreateNoId)),
|
|
mustParse(testMyOutboxIRI),
|
|
mustSerialize(testCreateNoId),
|
|
).Return(true, ErrObjectRequired)
|
|
// Run the test
|
|
handled, err := a.PostOutbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusBadRequest)
|
|
})
|
|
t.Run("PostOutboxBadRequestForErrTargetRequired", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toPostOutboxRequest(testCreateNoId))
|
|
delegate.EXPECT().AuthenticatePostOutbox(ctx, resp, req).Return(ctx, true, nil)
|
|
delegate.EXPECT().PostOutboxRequestBodyHook(ctx, req, toDeserializedForm(testCreateNoId)).Return(ctx, nil)
|
|
delegate.EXPECT().AddNewIDs(ctx, toDeserializedForm(testCreateNoId)).DoAndReturn(func(c context.Context, activity Activity) error {
|
|
withNewId(activity)
|
|
return nil
|
|
})
|
|
delegate.EXPECT().PostOutbox(
|
|
ctx,
|
|
withNewId(toDeserializedForm(testCreateNoId)),
|
|
mustParse(testMyOutboxIRI),
|
|
mustSerialize(testCreateNoId),
|
|
).Return(true, ErrTargetRequired)
|
|
// Run the test
|
|
handled, err := a.PostOutbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusBadRequest)
|
|
})
|
|
t.Run("GetOutboxIgnoresNonActivityPubRequest", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
_, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toGetOutboxRequest()
|
|
// Run the test
|
|
handled, err := a.GetOutbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, false)
|
|
assertEqual(t, len(resp.Result().Header), 0)
|
|
})
|
|
t.Run("GetOutboxDeniesIfNotAuthenticated", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toGetOutboxRequest())
|
|
delegate.EXPECT().AuthenticateGetOutbox(ctx, resp, req).DoAndReturn(func(ctx context.Context, resp http.ResponseWriter, req *http.Request) (context.Context, bool, error) {
|
|
resp.WriteHeader(http.StatusForbidden)
|
|
return ctx, false, nil
|
|
})
|
|
// Run the test
|
|
handled, err := a.GetOutbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusForbidden)
|
|
})
|
|
t.Run("GetOutboxRespondsWithDataAndHeaders", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, clock, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toGetOutboxRequest())
|
|
delegate.EXPECT().AuthenticateGetOutbox(ctx, resp, req).Return(ctx, true, nil)
|
|
delegate.EXPECT().GetOutbox(ctx, req).Return(testOrderedCollectionUniqueElems, nil)
|
|
clock.EXPECT().Now().Return(now())
|
|
// Run the test
|
|
handled, err := a.GetOutbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusOK)
|
|
respV := resp.Result()
|
|
assertEqual(t, respV.Header.Get(contentTypeHeader), "application/ld+json; profile=\"https://www.w3.org/ns/activitystreams\"")
|
|
assertEqual(t, respV.Header.Get(dateHeader), nowDateHeader())
|
|
assertNotEqual(t, len(respV.Header.Get(digestHeader)), 0)
|
|
b, err := ioutil.ReadAll(respV.Body)
|
|
assertEqual(t, err, nil)
|
|
assertByteEqual(t, b, []byte(testOrderedCollectionUniqueElemsString))
|
|
})
|
|
}
|
|
|
|
// TestBaseActorFederatingProtocol tests the Actor returned with
|
|
// NewCustomActor and only having the FederatingProtocol enabled.
|
|
func TestBaseActorFederatingProtocol(t *testing.T) {
|
|
// Set up test case
|
|
setupData()
|
|
ctx := context.Background()
|
|
setupFn := func(ctl *gomock.Controller) (delegate *MockDelegateActor, clock *MockClock, a Actor) {
|
|
delegate = NewMockDelegateActor(ctl)
|
|
clock = NewMockClock(ctl)
|
|
a = NewCustomActor(
|
|
delegate,
|
|
/*enableSocialProtocol=*/ false,
|
|
/*enableFederatedProtocol=*/ true,
|
|
clock)
|
|
return
|
|
}
|
|
// Run tests
|
|
t.Run("PostInboxIgnoresNonActivityPubRequest", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
_, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toPostInboxRequest(testCreate)
|
|
// Run the test
|
|
handled, err := a.PostInbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, false)
|
|
assertEqual(t, len(resp.Result().Header), 0)
|
|
})
|
|
t.Run("PostInboxDeniesIfNotAuthenticated", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toPostInboxRequest(testCreate))
|
|
delegate.EXPECT().AuthenticatePostInbox(ctx, resp, req).DoAndReturn(func(ctx context.Context, resp http.ResponseWriter, req *http.Request) (context.Context, bool, error) {
|
|
resp.WriteHeader(http.StatusForbidden)
|
|
return ctx, false, nil
|
|
})
|
|
// Run the test
|
|
handled, err := a.PostInbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusForbidden)
|
|
})
|
|
t.Run("PostInboxBadRequestIfUnknownType", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toPostInboxUnknownRequest())
|
|
delegate.EXPECT().AuthenticatePostInbox(ctx, resp, req).Return(ctx, true, nil)
|
|
// Run the test
|
|
handled, err := a.PostInbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusBadRequest)
|
|
})
|
|
t.Run("PostInboxBadRequestIfActivityHasNoId", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toPostOutboxRequest(testCreateNoId))
|
|
delegate.EXPECT().AuthenticatePostInbox(ctx, resp, req).Return(ctx, true, nil)
|
|
// Run the test
|
|
handled, err := a.PostInbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusBadRequest)
|
|
})
|
|
t.Run("PostInboxDeniesIfNotAuthorized", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toPostInboxRequest(testCreate))
|
|
delegate.EXPECT().AuthenticatePostInbox(ctx, resp, req).Return(ctx, true, nil)
|
|
delegate.EXPECT().PostInboxRequestBodyHook(ctx, req, toDeserializedForm(testCreate)).Return(ctx, nil)
|
|
delegate.EXPECT().AuthorizePostInbox(ctx, resp, toDeserializedForm(testCreate)).DoAndReturn(func(ctx context.Context, resp http.ResponseWriter, activity Activity) (bool, error) {
|
|
resp.WriteHeader(http.StatusForbidden)
|
|
return false, nil
|
|
})
|
|
// Run the test
|
|
handled, err := a.PostInbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusForbidden)
|
|
})
|
|
t.Run("PostInboxRespondsWithStatus", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toPostInboxRequest(testCreate))
|
|
delegate.EXPECT().AuthenticatePostInbox(ctx, resp, req).Return(ctx, true, nil)
|
|
delegate.EXPECT().PostInboxRequestBodyHook(ctx, req, toDeserializedForm(testCreate)).Return(ctx, nil)
|
|
delegate.EXPECT().AuthorizePostInbox(ctx, resp, toDeserializedForm(testCreate)).Return(true, nil)
|
|
delegate.EXPECT().PostInbox(ctx, mustParse(testMyInboxIRI), toDeserializedForm(testCreate)).Return(nil)
|
|
delegate.EXPECT().InboxForwarding(ctx, mustParse(testMyInboxIRI), toDeserializedForm(testCreate)).Return(nil)
|
|
// Run the test
|
|
handled, err := a.PostInbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusOK)
|
|
})
|
|
t.Run("PostInboxBadRequestForErrObjectRequired", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toPostInboxRequest(testCreate))
|
|
delegate.EXPECT().AuthenticatePostInbox(ctx, resp, req).Return(ctx, true, nil)
|
|
delegate.EXPECT().PostInboxRequestBodyHook(ctx, req, toDeserializedForm(testCreate)).Return(ctx, nil)
|
|
delegate.EXPECT().AuthorizePostInbox(ctx, resp, toDeserializedForm(testCreate)).Return(true, nil)
|
|
delegate.EXPECT().PostInbox(ctx, mustParse(testMyInboxIRI), toDeserializedForm(testCreate)).Return(ErrObjectRequired)
|
|
// Run the test
|
|
handled, err := a.PostInbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusBadRequest)
|
|
})
|
|
t.Run("PostInboxBadRequestForErrTargetRequired", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toPostInboxRequest(testCreate))
|
|
delegate.EXPECT().AuthenticatePostInbox(ctx, resp, req).Return(ctx, true, nil)
|
|
delegate.EXPECT().PostInboxRequestBodyHook(ctx, req, toDeserializedForm(testCreate)).Return(ctx, nil)
|
|
delegate.EXPECT().AuthorizePostInbox(ctx, resp, toDeserializedForm(testCreate)).Return(true, nil)
|
|
delegate.EXPECT().PostInbox(ctx, mustParse(testMyInboxIRI), toDeserializedForm(testCreate)).Return(ErrTargetRequired)
|
|
// Run the test
|
|
handled, err := a.PostInbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusBadRequest)
|
|
})
|
|
t.Run("GetInboxIgnoresNonActivityPubRequest", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
_, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toGetInboxRequest()
|
|
// Run the test
|
|
handled, err := a.GetInbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, false)
|
|
assertEqual(t, len(resp.Result().Header), 0)
|
|
})
|
|
t.Run("GetInboxDeniesIfNotAuthenticated", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toGetInboxRequest())
|
|
delegate.EXPECT().AuthenticateGetInbox(ctx, resp, req).DoAndReturn(func(ctx context.Context, resp http.ResponseWriter, req *http.Request) (context.Context, bool, error) {
|
|
resp.WriteHeader(http.StatusForbidden)
|
|
return ctx, false, nil
|
|
})
|
|
// Run the test
|
|
handled, err := a.GetInbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusForbidden)
|
|
})
|
|
t.Run("GetInboxRespondsWithDataAndHeaders", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, clock, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toGetInboxRequest())
|
|
delegate.EXPECT().AuthenticateGetInbox(ctx, resp, req).Return(ctx, true, nil)
|
|
delegate.EXPECT().GetInbox(ctx, req).Return(testOrderedCollectionUniqueElems, nil)
|
|
clock.EXPECT().Now().Return(now())
|
|
// Run the test
|
|
handled, err := a.GetInbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusOK)
|
|
respV := resp.Result()
|
|
assertEqual(t, respV.Header.Get(contentTypeHeader), "application/ld+json; profile=\"https://www.w3.org/ns/activitystreams\"")
|
|
assertEqual(t, respV.Header.Get(dateHeader), nowDateHeader())
|
|
assertNotEqual(t, len(respV.Header.Get(digestHeader)), 0)
|
|
b, err := ioutil.ReadAll(respV.Body)
|
|
assertEqual(t, err, nil)
|
|
assertByteEqual(t, b, []byte(testOrderedCollectionUniqueElemsString))
|
|
})
|
|
t.Run("GetInboxDeduplicatesData", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, clock, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toGetInboxRequest())
|
|
delegate.EXPECT().AuthenticateGetInbox(ctx, resp, req).Return(ctx, true, nil)
|
|
delegate.EXPECT().GetInbox(ctx, req).Return(testOrderedCollectionDupedElems, nil)
|
|
clock.EXPECT().Now().Return(now())
|
|
// Run the test
|
|
_, err := a.GetInbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
respV := resp.Result()
|
|
b, err := ioutil.ReadAll(respV.Body)
|
|
assertEqual(t, err, nil)
|
|
assertByteEqual(t, b, []byte(testOrderedCollectionDedupedElemsString))
|
|
})
|
|
t.Run("PostOutboxIgnoresNonActivityPubRequest", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
_, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toPostOutboxRequest(testCreateNoId)
|
|
// Run the test
|
|
handled, err := a.PostOutbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, false)
|
|
assertEqual(t, len(resp.Result().Header), 0)
|
|
})
|
|
t.Run("PostOutboxNotAllowed", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
_, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toPostOutboxRequest(testCreateNoId))
|
|
// Run the test
|
|
handled, err := a.PostOutbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusMethodNotAllowed)
|
|
})
|
|
t.Run("GetOutboxIgnoresNonActivityPubRequest", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
_, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toGetOutboxRequest()
|
|
// Run the test
|
|
handled, err := a.GetOutbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, false)
|
|
assertEqual(t, len(resp.Result().Header), 0)
|
|
})
|
|
t.Run("GetOutboxDeniesIfNotAuthenticated", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toGetOutboxRequest())
|
|
delegate.EXPECT().AuthenticateGetOutbox(ctx, resp, req).DoAndReturn(func(ctx context.Context, resp http.ResponseWriter, req *http.Request) (context.Context, bool, error) {
|
|
resp.WriteHeader(http.StatusForbidden)
|
|
return ctx, false, nil
|
|
})
|
|
// Run the test
|
|
handled, err := a.GetOutbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusForbidden)
|
|
})
|
|
t.Run("GetOutboxRespondsWithDataAndHeaders", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, clock, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toGetOutboxRequest())
|
|
delegate.EXPECT().AuthenticateGetOutbox(ctx, resp, req).Return(ctx, true, nil)
|
|
delegate.EXPECT().GetOutbox(ctx, req).Return(testOrderedCollectionUniqueElems, nil)
|
|
clock.EXPECT().Now().Return(now())
|
|
// Run the test
|
|
handled, err := a.GetOutbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusOK)
|
|
respV := resp.Result()
|
|
assertEqual(t, respV.Header.Get(contentTypeHeader), "application/ld+json; profile=\"https://www.w3.org/ns/activitystreams\"")
|
|
assertEqual(t, respV.Header.Get(dateHeader), nowDateHeader())
|
|
assertNotEqual(t, len(respV.Header.Get(digestHeader)), 0)
|
|
b, err := ioutil.ReadAll(respV.Body)
|
|
assertEqual(t, err, nil)
|
|
assertByteEqual(t, b, []byte(testOrderedCollectionUniqueElemsString))
|
|
})
|
|
}
|
|
|
|
// TestBaseActor tests the Actor returned with NewCustomActor and having both
|
|
// the SocialProtocol and FederatingProtocol enabled.
|
|
func TestBaseActor(t *testing.T) {
|
|
// Set up test case
|
|
setupData()
|
|
ctx := context.Background()
|
|
setupFn := func(ctl *gomock.Controller) (delegate *MockDelegateActor, clock *MockClock, a Actor) {
|
|
delegate = NewMockDelegateActor(ctl)
|
|
clock = NewMockClock(ctl)
|
|
a = NewCustomActor(
|
|
delegate,
|
|
/*enableSocialProtocol=*/ true,
|
|
/*enableFederatedProtocol=*/ true,
|
|
clock)
|
|
return
|
|
}
|
|
// Run tests
|
|
t.Run("PostInboxRespondsWithStatus", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toPostInboxRequest(testCreate))
|
|
delegate.EXPECT().AuthenticatePostInbox(ctx, resp, req).Return(ctx, true, nil)
|
|
delegate.EXPECT().PostInboxRequestBodyHook(ctx, req, toDeserializedForm(testCreate)).Return(ctx, nil)
|
|
delegate.EXPECT().AuthorizePostInbox(ctx, resp, toDeserializedForm(testCreate)).Return(true, nil)
|
|
delegate.EXPECT().PostInbox(ctx, mustParse(testMyInboxIRI), toDeserializedForm(testCreate)).Return(nil)
|
|
delegate.EXPECT().InboxForwarding(ctx, mustParse(testMyInboxIRI), toDeserializedForm(testCreate)).Return(nil)
|
|
// Run the test
|
|
handled, err := a.PostInbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusOK)
|
|
})
|
|
t.Run("PostOutboxRespondsWithDataAndHeaders", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toPostOutboxRequest(testCreateNoId))
|
|
delegate.EXPECT().AuthenticatePostOutbox(ctx, resp, req).Return(ctx, true, nil)
|
|
delegate.EXPECT().PostOutboxRequestBodyHook(ctx, req, toDeserializedForm(testCreateNoId)).Return(ctx, nil)
|
|
delegate.EXPECT().AddNewIDs(ctx, toDeserializedForm(testCreateNoId)).DoAndReturn(func(c context.Context, activity Activity) error {
|
|
withNewId(activity)
|
|
return nil
|
|
})
|
|
delegate.EXPECT().PostOutbox(
|
|
ctx,
|
|
withNewId(toDeserializedForm(testCreateNoId)),
|
|
mustParse(testMyOutboxIRI),
|
|
mustSerialize(testCreateNoId),
|
|
).Return(false, nil)
|
|
// Run the test
|
|
handled, err := a.PostOutbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusCreated)
|
|
respV := resp.Result()
|
|
assertEqual(t, respV.Header.Get(locationHeader), testNewActivityIRI)
|
|
})
|
|
t.Run("PostOutboxFederates", func(t *testing.T) {
|
|
// Setup
|
|
ctl := gomock.NewController(t)
|
|
defer ctl.Finish()
|
|
delegate, _, a := setupFn(ctl)
|
|
resp := httptest.NewRecorder()
|
|
req := toAPRequest(toPostOutboxRequest(testCreateNoId))
|
|
delegate.EXPECT().AuthenticatePostOutbox(ctx, resp, req).Return(ctx, true, nil)
|
|
delegate.EXPECT().PostOutboxRequestBodyHook(ctx, req, toDeserializedForm(testCreateNoId)).Return(ctx, nil)
|
|
delegate.EXPECT().AddNewIDs(ctx, toDeserializedForm(testCreateNoId)).DoAndReturn(func(c context.Context, activity Activity) error {
|
|
withNewId(activity)
|
|
return nil
|
|
})
|
|
delegate.EXPECT().PostOutbox(
|
|
ctx,
|
|
withNewId(toDeserializedForm(testCreateNoId)),
|
|
mustParse(testMyOutboxIRI),
|
|
mustSerialize(testCreateNoId),
|
|
).Return(true, nil)
|
|
delegate.EXPECT().Deliver(ctx, mustParse(testMyOutboxIRI), withNewId(toDeserializedForm(testCreateNoId))).Return(nil)
|
|
// Run the test
|
|
handled, err := a.PostOutbox(ctx, resp, req)
|
|
// Verify results
|
|
assertEqual(t, err, nil)
|
|
assertEqual(t, handled, true)
|
|
assertEqual(t, resp.Code, http.StatusCreated)
|
|
respV := resp.Result()
|
|
assertEqual(t, respV.Header.Get(locationHeader), testNewActivityIRI)
|
|
})
|
|
}
|