github.com/hyperledger/aries-framework-go@v0.3.2/pkg/client/introduce/example_test.go (about)

     1  /*
     2  Copyright SecureKey Technologies Inc. All Rights Reserved.
     3  
     4  SPDX-License-Identifier: Apache-2.0
     5  */
     6  
     7  package introduce
     8  
     9  import (
    10  	"encoding/json"
    11  	"fmt"
    12  	"time"
    13  
    14  	"github.com/golang/mock/gomock"
    15  
    16  	"github.com/hyperledger/aries-framework-go/component/storageutil/mem"
    17  	"github.com/hyperledger/aries-framework-go/pkg/client/outofband"
    18  	"github.com/hyperledger/aries-framework-go/pkg/didcomm/common/service"
    19  	"github.com/hyperledger/aries-framework-go/pkg/didcomm/messenger"
    20  	"github.com/hyperledger/aries-framework-go/pkg/didcomm/protocol/introduce"
    21  	serviceMocks "github.com/hyperledger/aries-framework-go/pkg/internal/gomocks/didcomm/common/service"
    22  	dispatcherMocks "github.com/hyperledger/aries-framework-go/pkg/internal/gomocks/didcomm/dispatcher"
    23  	messengerMocks "github.com/hyperledger/aries-framework-go/pkg/internal/gomocks/didcomm/messenger"
    24  	introduceServiceMocks "github.com/hyperledger/aries-framework-go/pkg/internal/gomocks/didcomm/protocol/introduce"
    25  )
    26  
    27  const (
    28  	// Alice always plays introducer role.
    29  	Alice = "Alice"
    30  	// Bob always plays introducee (first) role.
    31  	Bob = "Bob"
    32  	// Bob always plays introducee (second) role.
    33  	Carol = "Carol"
    34  )
    35  
    36  // payload represents a transport message structure.
    37  type payload struct {
    38  	msg      []byte
    39  	myDID    string
    40  	theirDID string
    41  }
    42  
    43  // nolint: gocyclo, gocognit, forbidigo
    44  func mockContext(agent string, tr map[string]chan payload, done chan struct{}) Provider {
    45  	ctrl := gomock.NewController(nil)
    46  
    47  	// NOTE: two fakeStore stores should be provided to prevent collision
    48  	storageProvider := mem.NewProvider()
    49  
    50  	didSvc := serviceMocks.NewMockEvent(ctrl)
    51  	didSvc.EXPECT().RegisterMsgEvent(gomock.Any()).Return(nil)
    52  
    53  	outbound := dispatcherMocks.NewMockOutbound(ctrl)
    54  	outbound.EXPECT().
    55  		SendToDID(gomock.Any(), gomock.Any(), gomock.Any()).
    56  		DoAndReturn(func(msg interface{}, myDID, theirDID string) error {
    57  			src, err := json.Marshal(msg)
    58  			if err != nil {
    59  				fmt.Println(err)
    60  			}
    61  
    62  			// this Sleep is necessary to make our examples works as expected
    63  			switch theirDID {
    64  			case Carol:
    65  				time.Sleep(time.Millisecond * 20)
    66  			case Bob:
    67  				time.Sleep(time.Millisecond * 10)
    68  			}
    69  
    70  			tr[theirDID] <- payload{
    71  				msg:      src,
    72  				myDID:    theirDID,
    73  				theirDID: myDID,
    74  			}
    75  
    76  			return nil
    77  		}).AnyTimes()
    78  
    79  	mProvider := messengerMocks.NewMockProvider(ctrl)
    80  	mProvider.EXPECT().StorageProvider().Return(storageProvider)
    81  	mProvider.EXPECT().OutboundDispatcher().Return(outbound)
    82  
    83  	provider := introduceServiceMocks.NewMockProvider(ctrl)
    84  	provider.EXPECT().StorageProvider().Return(storageProvider).MaxTimes(2)
    85  	provider.EXPECT().Service(gomock.Any()).Return(didSvc, nil)
    86  
    87  	msgSvc, err := messenger.NewMessenger(mProvider)
    88  	if err != nil {
    89  		fmt.Println(err)
    90  	}
    91  
    92  	provider.EXPECT().Messenger().Return(msgSvc)
    93  
    94  	svc, err := introduce.New(provider)
    95  	if err != nil {
    96  		fmt.Println(err)
    97  	}
    98  
    99  	go func() {
   100  		for {
   101  			select {
   102  			case <-done:
   103  				return
   104  			case msg := <-tr[agent]:
   105  				didMap, err := service.ParseDIDCommMsgMap(msg.msg)
   106  				if err != nil {
   107  					fmt.Println(err)
   108  				}
   109  
   110  				fmt.Println(agent, "received", didMap.Type(), "from", msg.theirDID)
   111  
   112  				if didMap.Type() == outofband.InvitationMsgType {
   113  					err = svc.OOBMessageReceived(service.StateMsg{
   114  						Type:    service.PostState,
   115  						StateID: "requested",
   116  						Msg:     didMap,
   117  					})
   118  
   119  					if err != nil {
   120  						fmt.Println(err)
   121  					}
   122  
   123  					close(done)
   124  
   125  					continue
   126  				}
   127  
   128  				if err = msgSvc.HandleInbound(didMap, service.NewDIDCommContext(msg.myDID, msg.theirDID, nil)); err != nil {
   129  					fmt.Println(err)
   130  				}
   131  
   132  				_, err = svc.HandleInbound(didMap, service.NewDIDCommContext(msg.myDID, msg.theirDID, nil))
   133  				if err != nil {
   134  					fmt.Println(err)
   135  				}
   136  			case <-time.After(time.Second):
   137  				return
   138  			}
   139  		}
   140  	}()
   141  
   142  	provider = introduceServiceMocks.NewMockProvider(ctrl)
   143  	provider.EXPECT().Service(gomock.Any()).Return(svc, nil)
   144  
   145  	return provider
   146  }
   147  
   148  // nolint: gocyclo
   149  func ExampleClient_SendProposal() {
   150  	transport := map[string]chan payload{
   151  		Alice: make(chan payload),
   152  		Bob:   make(chan payload),
   153  		Carol: make(chan payload),
   154  	}
   155  
   156  	done := make(chan struct{})
   157  
   158  	// Alice creates client
   159  	clientAlice, err := New(mockContext(Alice, transport, done))
   160  	if err != nil {
   161  		panic(err)
   162  	}
   163  
   164  	// Alice registers channel for actions
   165  	actionsAlice := make(chan service.DIDCommAction)
   166  
   167  	err = clientAlice.RegisterActionEvent(actionsAlice)
   168  	if err != nil {
   169  		panic(err)
   170  	}
   171  
   172  	// Bob creates client
   173  	clientBob, err := New(mockContext(Bob, transport, done))
   174  	if err != nil {
   175  		panic(err)
   176  	}
   177  
   178  	// Bob registers channel for actions
   179  	actionsBob := make(chan service.DIDCommAction)
   180  
   181  	err = clientBob.RegisterActionEvent(actionsBob)
   182  	if err != nil {
   183  		panic(err)
   184  	}
   185  
   186  	// Bob creates client
   187  	clientCarol, err := New(mockContext(Carol, transport, done))
   188  	if err != nil {
   189  		panic(err)
   190  	}
   191  
   192  	// Carol registers channel for actions
   193  	actionsCarol := make(chan service.DIDCommAction)
   194  
   195  	err = clientCarol.RegisterActionEvent(actionsCarol)
   196  	if err != nil {
   197  		panic(err)
   198  	}
   199  
   200  	go func() {
   201  		for {
   202  			select {
   203  			case e := <-actionsAlice:
   204  				e.Continue(nil)
   205  			case e := <-actionsBob:
   206  				e.Continue(nil)
   207  			case e := <-actionsCarol:
   208  				e.Continue(WithOOBInvitation(&outofband.Invitation{
   209  					Type: outofband.InvitationMsgType,
   210  				}))
   211  			}
   212  		}
   213  	}()
   214  
   215  	_, err = clientAlice.SendProposal(
   216  		&Recipient{
   217  			MyDID:    Alice,
   218  			TheirDID: Bob,
   219  		},
   220  		&Recipient{
   221  			MyDID:    Alice,
   222  			TheirDID: Carol,
   223  		},
   224  	)
   225  
   226  	if err != nil {
   227  		fmt.Println(err)
   228  	}
   229  
   230  	<-done
   231  
   232  	// Output:
   233  	// Bob received https://didcomm.org/introduce/1.0/proposal from Alice
   234  	// Alice received https://didcomm.org/introduce/1.0/response from Bob
   235  	// Carol received https://didcomm.org/introduce/1.0/proposal from Alice
   236  	// Alice received https://didcomm.org/introduce/1.0/response from Carol
   237  	// Bob received https://didcomm.org/out-of-band/1.0/invitation from Alice
   238  }
   239  
   240  func ExampleClient_SendProposalWithOOBInvitation() {
   241  	transport := map[string]chan payload{
   242  		Alice: make(chan payload),
   243  		Bob:   make(chan payload),
   244  	}
   245  
   246  	done := make(chan struct{})
   247  
   248  	// Alice creates client
   249  	clientAlice, err := New(mockContext(Alice, transport, done))
   250  	if err != nil {
   251  		panic(err)
   252  	}
   253  
   254  	// Alice registers channel for actions
   255  	actionsAlice := make(chan service.DIDCommAction)
   256  
   257  	err = clientAlice.RegisterActionEvent(actionsAlice)
   258  	if err != nil {
   259  		panic(err)
   260  	}
   261  
   262  	// Bob creates client
   263  	clientBob, err := New(mockContext(Bob, transport, done))
   264  	if err != nil {
   265  		panic(err)
   266  	}
   267  
   268  	// Bob registers channel for actions
   269  	actionsBob := make(chan service.DIDCommAction)
   270  
   271  	err = clientBob.RegisterActionEvent(actionsBob)
   272  	if err != nil {
   273  		panic(err)
   274  	}
   275  
   276  	go func() {
   277  		for {
   278  			select {
   279  			case e := <-actionsAlice:
   280  				e.Continue(nil)
   281  			case e := <-actionsBob:
   282  				e.Continue(nil)
   283  			}
   284  		}
   285  	}()
   286  
   287  	_, err = clientAlice.SendProposalWithOOBInvitation(
   288  		&outofband.Invitation{
   289  			Type: outofband.InvitationMsgType,
   290  		},
   291  		&Recipient{
   292  			MyDID:    Alice,
   293  			TheirDID: Bob,
   294  		},
   295  	)
   296  
   297  	if err != nil {
   298  		fmt.Println(err)
   299  	}
   300  
   301  	<-done
   302  
   303  	// Output:
   304  	// Bob received https://didcomm.org/introduce/1.0/proposal from Alice
   305  	// Alice received https://didcomm.org/introduce/1.0/response from Bob
   306  	// Bob received https://didcomm.org/out-of-band/1.0/invitation from Alice
   307  }
   308  
   309  // nolint: gocyclo
   310  func ExampleClient_SendRequest() {
   311  	transport := map[string]chan payload{
   312  		Alice: make(chan payload),
   313  		Bob:   make(chan payload),
   314  		Carol: make(chan payload),
   315  	}
   316  
   317  	done := make(chan struct{})
   318  
   319  	// Alice creates client
   320  	clientAlice, err := New(mockContext(Alice, transport, done))
   321  	if err != nil {
   322  		panic(err)
   323  	}
   324  
   325  	// Alice registers channel for actions
   326  	actionsAlice := make(chan service.DIDCommAction)
   327  
   328  	err = clientAlice.RegisterActionEvent(actionsAlice)
   329  	if err != nil {
   330  		panic(err)
   331  	}
   332  
   333  	// Bob creates client
   334  	clientBob, err := New(mockContext(Bob, transport, done))
   335  	if err != nil {
   336  		panic(err)
   337  	}
   338  
   339  	// Bob registers channel for actions
   340  	actionsBob := make(chan service.DIDCommAction)
   341  
   342  	err = clientBob.RegisterActionEvent(actionsBob)
   343  	if err != nil {
   344  		panic(err)
   345  	}
   346  
   347  	// Bob creates client
   348  	clientCarol, err := New(mockContext(Carol, transport, done))
   349  	if err != nil {
   350  		panic(err)
   351  	}
   352  
   353  	// Carol registers channel for actions
   354  	actionsCarol := make(chan service.DIDCommAction)
   355  
   356  	err = clientCarol.RegisterActionEvent(actionsCarol)
   357  	if err != nil {
   358  		panic(err)
   359  	}
   360  
   361  	go func() {
   362  		for {
   363  			select {
   364  			case e := <-actionsAlice:
   365  				e.Continue(WithRecipients(&To{Name: Carol}, &Recipient{
   366  					To:       &introduce.To{Name: Bob},
   367  					MyDID:    Alice,
   368  					TheirDID: Carol,
   369  				}))
   370  			case e := <-actionsBob:
   371  				e.Continue(nil)
   372  			case e := <-actionsCarol:
   373  				e.Continue(WithOOBInvitation(&outofband.Invitation{
   374  					Type: outofband.InvitationMsgType,
   375  				}))
   376  			}
   377  		}
   378  	}()
   379  
   380  	_, err = clientBob.SendRequest(
   381  		&PleaseIntroduceTo{
   382  			To: introduce.To{Name: Carol},
   383  		},
   384  		Bob, Alice,
   385  	)
   386  
   387  	if err != nil {
   388  		fmt.Println(err)
   389  	}
   390  
   391  	<-done
   392  
   393  	// Output:
   394  	// Alice received https://didcomm.org/introduce/1.0/request from Bob
   395  	// Bob received https://didcomm.org/introduce/1.0/proposal from Alice
   396  	// Alice received https://didcomm.org/introduce/1.0/response from Bob
   397  	// Carol received https://didcomm.org/introduce/1.0/proposal from Alice
   398  	// Alice received https://didcomm.org/introduce/1.0/response from Carol
   399  	// Bob received https://didcomm.org/out-of-band/1.0/invitation from Alice
   400  }
   401  
   402  func ExampleClient_SendRequest_second() {
   403  	transport := map[string]chan payload{
   404  		Alice: make(chan payload),
   405  		Bob:   make(chan payload),
   406  		Carol: make(chan payload),
   407  	}
   408  
   409  	done := make(chan struct{})
   410  
   411  	// Alice creates client
   412  	clientAlice, err := New(mockContext(Alice, transport, done))
   413  	if err != nil {
   414  		panic(err)
   415  	}
   416  
   417  	// Alice registers channel for actions
   418  	actionsAlice := make(chan service.DIDCommAction)
   419  
   420  	err = clientAlice.RegisterActionEvent(actionsAlice)
   421  	if err != nil {
   422  		panic(err)
   423  	}
   424  
   425  	// Bob creates client
   426  	clientBob, err := New(mockContext(Bob, transport, done))
   427  	if err != nil {
   428  		panic(err)
   429  	}
   430  
   431  	// Bob registers channel for actions
   432  	actionsBob := make(chan service.DIDCommAction)
   433  
   434  	err = clientBob.RegisterActionEvent(actionsBob)
   435  	if err != nil {
   436  		panic(err)
   437  	}
   438  
   439  	go func() {
   440  		for {
   441  			select {
   442  			case e := <-actionsAlice:
   443  				e.Continue(WithPublicOOBInvitation(&outofband.Invitation{
   444  					Type: outofband.InvitationMsgType,
   445  				}, &To{Name: Carol}))
   446  			case e := <-actionsBob:
   447  				e.Continue(nil)
   448  			}
   449  		}
   450  	}()
   451  
   452  	_, err = clientBob.SendRequest(
   453  		&PleaseIntroduceTo{
   454  			To: introduce.To{Name: Carol},
   455  		},
   456  		Bob, Alice,
   457  	)
   458  
   459  	if err != nil {
   460  		fmt.Println(err)
   461  	}
   462  
   463  	<-done
   464  
   465  	// Output:
   466  	// Alice received https://didcomm.org/introduce/1.0/request from Bob
   467  	// Bob received https://didcomm.org/introduce/1.0/proposal from Alice
   468  	// Alice received https://didcomm.org/introduce/1.0/response from Bob
   469  	// Bob received https://didcomm.org/out-of-band/1.0/invitation from Alice
   470  }