|
|
@@ -4,46 +4,48 @@ import (
|
|
|
"context"
|
|
|
"testing"
|
|
|
|
|
|
+ "github.com/stretchr/testify/mock"
|
|
|
+
|
|
|
"github.com/mkaminski/goaim/oscar"
|
|
|
"github.com/mkaminski/goaim/state"
|
|
|
"github.com/stretchr/testify/assert"
|
|
|
)
|
|
|
|
|
|
-func TestSendAndReceiveUserInfoQuery2(t *testing.T) {
|
|
|
+func TestLocateService_UserInfoQuery2Handler(t *testing.T) {
|
|
|
cases := []struct {
|
|
|
// name is the unit test name
|
|
|
name string
|
|
|
- // blockedState is the response to the sender/recipient block check
|
|
|
- blockedState state.BlockedState
|
|
|
- // screenNameLookups is the list of user session lookups
|
|
|
- screenNameLookups map[string]struct {
|
|
|
- sess *state.Session
|
|
|
- err error
|
|
|
- }
|
|
|
- // screenNameLookups is the list of user session lookups
|
|
|
- profileLookups map[string]struct {
|
|
|
- payload string
|
|
|
- err error
|
|
|
- }
|
|
|
- // userSession is the session of the user requesting the user info
|
|
|
+ // mockParams is the list of params sent to mocks that satisfy this
|
|
|
+ // method's dependencies
|
|
|
+ mockParams mockParams
|
|
|
+ // userSession is the session of the user requesting user info
|
|
|
userSession *state.Session
|
|
|
- // inputSNAC is the SNAC sent by the sender client
|
|
|
+ // inputSNAC is the SNAC sent from client to server
|
|
|
inputSNAC oscar.SNACMessage
|
|
|
- // expectOutput is the SNAC sent from the server to the
|
|
|
- // recipient client
|
|
|
+ // expectOutput is the SNAC sent from the server to client
|
|
|
expectOutput oscar.SNACMessage
|
|
|
}{
|
|
|
{
|
|
|
- name: "request user info, expect user info response",
|
|
|
- blockedState: state.BlockedNo,
|
|
|
- screenNameLookups: map[string]struct {
|
|
|
- sess *state.Session
|
|
|
- err error
|
|
|
- }{
|
|
|
- "requested-user": {
|
|
|
- sess: newTestSession("requested-user",
|
|
|
- sessOptCannedSignonTime,
|
|
|
- sessOptCannedAwayMessage),
|
|
|
+ name: "request user info, expect user info response",
|
|
|
+ mockParams: mockParams{
|
|
|
+ feedbagManagerParams: feedbagManagerParams{
|
|
|
+ blockedParams: blockedParams{
|
|
|
+ {
|
|
|
+ screenName1: "user_screen_name",
|
|
|
+ screenName2: "requested-user",
|
|
|
+ result: state.BlockedNo,
|
|
|
+ },
|
|
|
+ },
|
|
|
+ },
|
|
|
+ messageRelayerParams: messageRelayerParams{
|
|
|
+ retrieveByScreenNameParams: retrieveByScreenNameParams{
|
|
|
+ {
|
|
|
+ screenName: "requested-user",
|
|
|
+ sess: newTestSession("requested-user",
|
|
|
+ sessOptCannedSignonTime,
|
|
|
+ sessOptCannedAwayMessage),
|
|
|
+ },
|
|
|
+ },
|
|
|
},
|
|
|
},
|
|
|
userSession: newTestSession("user_screen_name"),
|
|
|
@@ -72,24 +74,34 @@ func TestSendAndReceiveUserInfoQuery2(t *testing.T) {
|
|
|
},
|
|
|
},
|
|
|
{
|
|
|
- name: "request user info + profile, expect user info response + profile",
|
|
|
- blockedState: state.BlockedNo,
|
|
|
- screenNameLookups: map[string]struct {
|
|
|
- sess *state.Session
|
|
|
- err error
|
|
|
- }{
|
|
|
- "requested-user": {
|
|
|
- sess: newTestSession("requested-user",
|
|
|
- sessOptCannedSignonTime,
|
|
|
- sessOptCannedAwayMessage),
|
|
|
+ name: "request user info + profile, expect user info response + profile",
|
|
|
+ mockParams: mockParams{
|
|
|
+ feedbagManagerParams: feedbagManagerParams{
|
|
|
+ blockedParams: blockedParams{
|
|
|
+ {
|
|
|
+ screenName1: "user_screen_name",
|
|
|
+ screenName2: "requested-user",
|
|
|
+ result: state.BlockedNo,
|
|
|
+ },
|
|
|
+ },
|
|
|
},
|
|
|
- },
|
|
|
- profileLookups: map[string]struct {
|
|
|
- payload string
|
|
|
- err error
|
|
|
- }{
|
|
|
- "requested-user": {
|
|
|
- payload: "this is my profile!",
|
|
|
+ messageRelayerParams: messageRelayerParams{
|
|
|
+ retrieveByScreenNameParams: retrieveByScreenNameParams{
|
|
|
+ {
|
|
|
+ screenName: "requested-user",
|
|
|
+ sess: newTestSession("requested-user",
|
|
|
+ sessOptCannedSignonTime,
|
|
|
+ sessOptCannedAwayMessage),
|
|
|
+ },
|
|
|
+ },
|
|
|
+ },
|
|
|
+ profileManagerParams: profileManagerParams{
|
|
|
+ retrieveProfileParams: retrieveProfileParams{
|
|
|
+ {
|
|
|
+ screenName: "requested-user",
|
|
|
+ result: "this is my profile!",
|
|
|
+ },
|
|
|
+ },
|
|
|
},
|
|
|
},
|
|
|
userSession: newTestSession("user_screen_name"),
|
|
|
@@ -124,24 +136,34 @@ func TestSendAndReceiveUserInfoQuery2(t *testing.T) {
|
|
|
},
|
|
|
},
|
|
|
{
|
|
|
- name: "request user info + profile, expect user info response + profile",
|
|
|
- blockedState: state.BlockedNo,
|
|
|
- screenNameLookups: map[string]struct {
|
|
|
- sess *state.Session
|
|
|
- err error
|
|
|
- }{
|
|
|
- "requested-user": {
|
|
|
- sess: newTestSession("requested-user",
|
|
|
- sessOptCannedSignonTime,
|
|
|
- sessOptCannedAwayMessage),
|
|
|
+ name: "request user info + profile, expect user info response + profile",
|
|
|
+ mockParams: mockParams{
|
|
|
+ feedbagManagerParams: feedbagManagerParams{
|
|
|
+ blockedParams: blockedParams{
|
|
|
+ {
|
|
|
+ screenName1: "user_screen_name",
|
|
|
+ screenName2: "requested-user",
|
|
|
+ result: state.BlockedNo,
|
|
|
+ },
|
|
|
+ },
|
|
|
},
|
|
|
- },
|
|
|
- profileLookups: map[string]struct {
|
|
|
- payload string
|
|
|
- err error
|
|
|
- }{
|
|
|
- "requested-user": {
|
|
|
- payload: "this is my profile!",
|
|
|
+ messageRelayerParams: messageRelayerParams{
|
|
|
+ retrieveByScreenNameParams: retrieveByScreenNameParams{
|
|
|
+ {
|
|
|
+ screenName: "requested-user",
|
|
|
+ sess: newTestSession("requested-user",
|
|
|
+ sessOptCannedSignonTime,
|
|
|
+ sessOptCannedAwayMessage),
|
|
|
+ },
|
|
|
+ },
|
|
|
+ },
|
|
|
+ profileManagerParams: profileManagerParams{
|
|
|
+ retrieveProfileParams: retrieveProfileParams{
|
|
|
+ {
|
|
|
+ screenName: "requested-user",
|
|
|
+ result: "this is my profile!",
|
|
|
+ },
|
|
|
+ },
|
|
|
},
|
|
|
},
|
|
|
userSession: newTestSession("user_screen_name"),
|
|
|
@@ -176,16 +198,26 @@ func TestSendAndReceiveUserInfoQuery2(t *testing.T) {
|
|
|
},
|
|
|
},
|
|
|
{
|
|
|
- name: "request user info + away message, expect user info response + away message",
|
|
|
- blockedState: state.BlockedNo,
|
|
|
- screenNameLookups: map[string]struct {
|
|
|
- sess *state.Session
|
|
|
- err error
|
|
|
- }{
|
|
|
- "requested-user": {
|
|
|
- sess: newTestSession("requested-user",
|
|
|
- sessOptCannedSignonTime,
|
|
|
- sessOptCannedAwayMessage),
|
|
|
+ name: "request user info + away message, expect user info response + away message",
|
|
|
+ mockParams: mockParams{
|
|
|
+ feedbagManagerParams: feedbagManagerParams{
|
|
|
+ blockedParams: blockedParams{
|
|
|
+ {
|
|
|
+ screenName1: "user_screen_name",
|
|
|
+ screenName2: "requested-user",
|
|
|
+ result: state.BlockedNo,
|
|
|
+ },
|
|
|
+ },
|
|
|
+ },
|
|
|
+ messageRelayerParams: messageRelayerParams{
|
|
|
+ retrieveByScreenNameParams: retrieveByScreenNameParams{
|
|
|
+ {
|
|
|
+ screenName: "requested-user",
|
|
|
+ sess: newTestSession("requested-user",
|
|
|
+ sessOptCannedSignonTime,
|
|
|
+ sessOptCannedAwayMessage),
|
|
|
+ },
|
|
|
+ },
|
|
|
},
|
|
|
},
|
|
|
userSession: newTestSession("user_screen_name"),
|
|
|
@@ -220,9 +252,19 @@ func TestSendAndReceiveUserInfoQuery2(t *testing.T) {
|
|
|
},
|
|
|
},
|
|
|
{
|
|
|
- name: "request user info of user who blocked requester, expect not logged in error",
|
|
|
- blockedState: state.BlockedB,
|
|
|
- userSession: newTestSession("user_screen_name"),
|
|
|
+ name: "request user info of user who blocked requester, expect not logged in error",
|
|
|
+ mockParams: mockParams{
|
|
|
+ feedbagManagerParams: feedbagManagerParams{
|
|
|
+ blockedParams: blockedParams{
|
|
|
+ {
|
|
|
+ screenName1: "user_screen_name",
|
|
|
+ screenName2: "requested-user",
|
|
|
+ result: state.BlockedB,
|
|
|
+ },
|
|
|
+ },
|
|
|
+ },
|
|
|
+ },
|
|
|
+ userSession: newTestSession("user_screen_name"),
|
|
|
inputSNAC: oscar.SNACMessage{
|
|
|
Frame: oscar.SNACFrame{
|
|
|
RequestID: 1234,
|
|
|
@@ -243,14 +285,24 @@ func TestSendAndReceiveUserInfoQuery2(t *testing.T) {
|
|
|
},
|
|
|
},
|
|
|
{
|
|
|
- name: "request user info of user who does not exist, expect not logged in error",
|
|
|
- blockedState: state.BlockedNo,
|
|
|
- screenNameLookups: map[string]struct {
|
|
|
- sess *state.Session
|
|
|
- err error
|
|
|
- }{
|
|
|
- "non_existent_requested_user": {
|
|
|
- sess: nil,
|
|
|
+ name: "request user info of user who does not exist, expect not logged in error",
|
|
|
+ mockParams: mockParams{
|
|
|
+ feedbagManagerParams: feedbagManagerParams{
|
|
|
+ blockedParams: blockedParams{
|
|
|
+ {
|
|
|
+ screenName1: "user_screen_name",
|
|
|
+ screenName2: "non_existent_requested_user",
|
|
|
+ result: state.BlockedNo,
|
|
|
+ },
|
|
|
+ },
|
|
|
+ },
|
|
|
+ messageRelayerParams: messageRelayerParams{
|
|
|
+ retrieveByScreenNameParams: retrieveByScreenNameParams{
|
|
|
+ {
|
|
|
+ screenName: "non_existent_requested_user",
|
|
|
+ sess: nil,
|
|
|
+ },
|
|
|
+ },
|
|
|
},
|
|
|
},
|
|
|
userSession: newTestSession("user_screen_name"),
|
|
|
@@ -278,30 +330,24 @@ func TestSendAndReceiveUserInfoQuery2(t *testing.T) {
|
|
|
for _, tc := range cases {
|
|
|
t.Run(tc.name, func(t *testing.T) {
|
|
|
feedbagManager := newMockFeedbagManager(t)
|
|
|
- feedbagManager.EXPECT().
|
|
|
- Blocked(tc.userSession.ScreenName(),
|
|
|
- tc.inputSNAC.Body.(oscar.SNAC_0x02_0x15_LocateUserInfoQuery2).ScreenName).
|
|
|
- Return(tc.blockedState, nil).
|
|
|
- Maybe()
|
|
|
+ for _, params := range tc.mockParams.blockedParams {
|
|
|
+ feedbagManager.EXPECT().
|
|
|
+ Blocked(params.screenName1, params.screenName2).
|
|
|
+ Return(params.result, nil)
|
|
|
+ }
|
|
|
messageRelayer := newMockMessageRelayer(t)
|
|
|
- for screenName, val := range tc.screenNameLookups {
|
|
|
+ for _, val := range tc.mockParams.retrieveByScreenNameParams {
|
|
|
messageRelayer.EXPECT().
|
|
|
- RetrieveByScreenName(screenName).
|
|
|
- Return(val.sess).
|
|
|
- Maybe()
|
|
|
+ RetrieveByScreenName(val.screenName).
|
|
|
+ Return(val.sess)
|
|
|
}
|
|
|
profileManager := newMockProfileManager(t)
|
|
|
- for screenName, val := range tc.profileLookups {
|
|
|
+ for _, val := range tc.mockParams.retrieveProfileParams {
|
|
|
profileManager.EXPECT().
|
|
|
- RetrieveProfile(screenName).
|
|
|
- Return(val.payload, val.err).
|
|
|
- Maybe()
|
|
|
- }
|
|
|
- svc := LocateService{
|
|
|
- sessionManager: messageRelayer,
|
|
|
- feedbagManager: feedbagManager,
|
|
|
- profileManager: profileManager,
|
|
|
+ RetrieveProfile(val.screenName).
|
|
|
+ Return(val.result, val.err)
|
|
|
}
|
|
|
+ svc := NewLocateService(messageRelayer, feedbagManager, profileManager)
|
|
|
outputSNAC, err := svc.UserInfoQuery2Handler(context.Background(), tc.userSession, tc.inputSNAC.Frame,
|
|
|
tc.inputSNAC.Body.(oscar.SNAC_0x02_0x15_LocateUserInfoQuery2))
|
|
|
assert.NoError(t, err)
|
|
|
@@ -309,3 +355,155 @@ func TestSendAndReceiveUserInfoQuery2(t *testing.T) {
|
|
|
})
|
|
|
}
|
|
|
}
|
|
|
+
|
|
|
+func TestLocateService_SetKeywordInfoHandler(t *testing.T) {
|
|
|
+ svc := NewLocateService(nil, nil, nil)
|
|
|
+
|
|
|
+ outputSNAC := svc.SetKeywordInfoHandler(nil, oscar.SNACFrame{RequestID: 1234})
|
|
|
+ expectSNAC := oscar.SNACMessage{
|
|
|
+ Frame: oscar.SNACFrame{
|
|
|
+ FoodGroup: oscar.Locate,
|
|
|
+ SubGroup: oscar.LocateSetKeywordReply,
|
|
|
+ RequestID: 1234,
|
|
|
+ },
|
|
|
+ Body: oscar.SNAC_0x02_0x10_LocateSetKeywordReply{
|
|
|
+ Unknown: 1,
|
|
|
+ },
|
|
|
+ }
|
|
|
+
|
|
|
+ assert.Equal(t, expectSNAC, outputSNAC)
|
|
|
+}
|
|
|
+
|
|
|
+func TestLocateService_SetDirInfoHandler(t *testing.T) {
|
|
|
+ svc := NewLocateService(nil, nil, nil)
|
|
|
+
|
|
|
+ outputSNAC := svc.SetDirInfoHandler(nil, oscar.SNACFrame{RequestID: 1234})
|
|
|
+ expectSNAC := oscar.SNACMessage{
|
|
|
+ Frame: oscar.SNACFrame{
|
|
|
+ FoodGroup: oscar.Locate,
|
|
|
+ SubGroup: oscar.LocateSetDirReply,
|
|
|
+ RequestID: 1234,
|
|
|
+ },
|
|
|
+ Body: oscar.SNAC_0x02_0x0A_LocateSetDirReply{
|
|
|
+ Result: 1,
|
|
|
+ },
|
|
|
+ }
|
|
|
+
|
|
|
+ assert.Equal(t, expectSNAC, outputSNAC)
|
|
|
+}
|
|
|
+
|
|
|
+func TestLocateService_SetInfoHandler(t *testing.T) {
|
|
|
+ tests := []struct {
|
|
|
+ // name is the unit test name
|
|
|
+ name string
|
|
|
+ // userSession is the session of the user setting info
|
|
|
+ userSession *state.Session
|
|
|
+ // inBody is the message sent from client to server
|
|
|
+ inBody oscar.SNAC_0x02_0x04_LocateSetInfo
|
|
|
+ // mockParams is the list of params sent to mocks that satisfy this
|
|
|
+ // method's dependencies
|
|
|
+ mockParams mockParams
|
|
|
+ wantErr error
|
|
|
+ }{
|
|
|
+ {
|
|
|
+ name: "set profile",
|
|
|
+ userSession: newTestSession("test-user"),
|
|
|
+ inBody: oscar.SNAC_0x02_0x04_LocateSetInfo{
|
|
|
+ TLVRestBlock: oscar.TLVRestBlock{
|
|
|
+ TLVList: oscar.TLVList{
|
|
|
+ oscar.NewTLV(oscar.LocateTLVTagsInfoSigData, "profile-result"),
|
|
|
+ },
|
|
|
+ },
|
|
|
+ },
|
|
|
+ },
|
|
|
+ {
|
|
|
+ name: "set away message",
|
|
|
+ userSession: newTestSession("user_screen_name"),
|
|
|
+ inBody: oscar.SNAC_0x02_0x04_LocateSetInfo{
|
|
|
+ TLVRestBlock: oscar.TLVRestBlock{
|
|
|
+ TLVList: oscar.TLVList{
|
|
|
+ oscar.NewTLV(oscar.LocateTLVTagsInfoUnavailableData, "this is my away message!"),
|
|
|
+ },
|
|
|
+ },
|
|
|
+ },
|
|
|
+ mockParams: mockParams{
|
|
|
+ messageRelayerParams: messageRelayerParams{
|
|
|
+ broadcastToScreenNamesParams: broadcastToScreenNamesParams{
|
|
|
+ {
|
|
|
+ screenNames: []string{"friend1", "friend2"},
|
|
|
+ message: oscar.SNACMessage{
|
|
|
+ Frame: oscar.SNACFrame{
|
|
|
+ FoodGroup: oscar.Buddy,
|
|
|
+ SubGroup: oscar.BuddyArrived,
|
|
|
+ },
|
|
|
+ Body: oscar.SNAC_0x03_0x0B_BuddyArrived{
|
|
|
+ TLVUserInfo: newTestSession("user_screen_name", sessOptAwayMessage("this is my away message!")).TLVUserInfo(),
|
|
|
+ },
|
|
|
+ },
|
|
|
+ },
|
|
|
+ },
|
|
|
+ },
|
|
|
+ feedbagManagerParams: feedbagManagerParams{
|
|
|
+ interestedUsersParams: interestedUsersParams{
|
|
|
+ {
|
|
|
+ screenName: "user_screen_name",
|
|
|
+ users: []string{"friend1", "friend2"},
|
|
|
+ },
|
|
|
+ },
|
|
|
+ },
|
|
|
+ profileManagerParams: profileManagerParams{
|
|
|
+ upsertProfileParams: upsertProfileParams{},
|
|
|
+ },
|
|
|
+ },
|
|
|
+ },
|
|
|
+ }
|
|
|
+ for _, tt := range tests {
|
|
|
+ t.Run(tt.name, func(t *testing.T) {
|
|
|
+ messageRelayer := newMockMessageRelayer(t)
|
|
|
+ for _, params := range tt.mockParams.broadcastToScreenNamesParams {
|
|
|
+ messageRelayer.EXPECT().
|
|
|
+ BroadcastToScreenNames(mock.Anything, params.screenNames, params.message)
|
|
|
+ }
|
|
|
+ feedbagManager := newMockFeedbagManager(t)
|
|
|
+ for _, params := range tt.mockParams.interestedUsersParams {
|
|
|
+ feedbagManager.EXPECT().
|
|
|
+ InterestedUsers(params.screenName).
|
|
|
+ Return(params.users, nil)
|
|
|
+ }
|
|
|
+ profileManager := newMockProfileManager(t)
|
|
|
+ if msg, hasProf := tt.inBody.GetString(oscar.LocateTLVTagsInfoSigData); hasProf {
|
|
|
+ profileManager.EXPECT().
|
|
|
+ UpsertProfile(tt.userSession.ScreenName(), msg).
|
|
|
+ Return(nil)
|
|
|
+ }
|
|
|
+ svc := NewLocateService(messageRelayer, feedbagManager, profileManager)
|
|
|
+ assert.Equal(t, tt.wantErr, svc.SetInfoHandler(nil, tt.userSession, tt.inBody))
|
|
|
+ })
|
|
|
+ }
|
|
|
+}
|
|
|
+
|
|
|
+func TestLocateService_RightsQueryHandler(t *testing.T) {
|
|
|
+ svc := NewLocateService(nil, nil, nil)
|
|
|
+
|
|
|
+ outputSNAC := svc.RightsQueryHandler(nil, oscar.SNACFrame{RequestID: 1234})
|
|
|
+ expectSNAC := oscar.SNACMessage{
|
|
|
+ Frame: oscar.SNACFrame{
|
|
|
+ FoodGroup: oscar.Locate,
|
|
|
+ SubGroup: oscar.LocateRightsReply,
|
|
|
+ RequestID: 1234,
|
|
|
+ },
|
|
|
+ Body: oscar.SNAC_0x02_0x03_LocateRightsReply{
|
|
|
+ TLVRestBlock: oscar.TLVRestBlock{
|
|
|
+ TLVList: oscar.TLVList{
|
|
|
+ oscar.NewTLV(oscar.LocateTLVTagsRightsMaxSigLen, uint16(1000)),
|
|
|
+ oscar.NewTLV(oscar.LocateTLVTagsRightsMaxCapabilitiesLen, uint16(1000)),
|
|
|
+ oscar.NewTLV(oscar.LocateTLVTagsRightsMaxFindByEmailList, uint16(1000)),
|
|
|
+ oscar.NewTLV(oscar.LocateTLVTagsRightsMaxCertsLen, uint16(1000)),
|
|
|
+ oscar.NewTLV(oscar.LocateTLVTagsRightsMaxMaxShortCapabilities, uint16(1000)),
|
|
|
+ },
|
|
|
+ },
|
|
|
+ },
|
|
|
+ }
|
|
|
+
|
|
|
+ assert.Equal(t, expectSNAC, outputSNAC)
|
|
|
+}
|