diff --git a/session/pingpong/hermes_channel.go b/session/pingpong/hermes_channel.go index 30043f0f8..f2aa4cdce 100644 --- a/session/pingpong/hermes_channel.go +++ b/session/pingpong/hermes_channel.go @@ -26,13 +26,14 @@ import ( ) // NewHermesChannel creates HermesChannel model. -func NewHermesChannel(channelID string, id identity.Identity, hermesID common.Address, channel client.ProviderChannel, promise HermesPromise) HermesChannel { +func NewHermesChannel(channelID string, id identity.Identity, hermesID common.Address, channel client.ProviderChannel, promise HermesPromise, beneficiary common.Address) HermesChannel { return HermesChannel{ ChannelID: channelID, Identity: id, HermesID: hermesID, Channel: channel, lastPromise: promise, + Beneficiary: beneficiary, } } diff --git a/session/pingpong/hermes_channel_repository.go b/session/pingpong/hermes_channel_repository.go index 52fc8aa62..12c836047 100644 --- a/session/pingpong/hermes_channel_repository.go +++ b/session/pingpong/hermes_channel_repository.go @@ -389,14 +389,11 @@ func (hcr *HermesChannelRepository) fetchChannel(chainID int64, channelID string return HermesChannel{}, fmt.Errorf("could not get provider channel for %v, hermes %v: %w", id, hermesID.Hex(), err) } - hermesChannel := NewHermesChannel(channelID, id, hermesID, channel, promise) - benef, err := hcr.bprovider.GetBeneficiary(id.ToCommonAddress()) if err != nil { return HermesChannel{}, fmt.Errorf("could not get provider beneficiary for %v, hermes %v: %w", id, hermesID.Hex(), err) } - - hermesChannel.Beneficiary = benef + hermesChannel := NewHermesChannel(channelID, id, hermesID, channel, promise, benef) hcr.updateChannel(chainID, hermesChannel) @@ -411,7 +408,7 @@ func (hcr *HermesChannelRepository) updateChannelWithLatestPromise(chainID int64 return err } - hermesChannel := NewHermesChannel(channelID, id, hermesID, gotten.Channel, promise) + hermesChannel := NewHermesChannel(channelID, id, hermesID, gotten.Channel, promise, gotten.Beneficiary) hcr.updateChannel(chainID, hermesChannel) return nil } diff --git a/session/pingpong/hermes_channel_repository_test.go b/session/pingpong/hermes_channel_repository_test.go index 7af92e515..7a87c0abc 100644 --- a/session/pingpong/hermes_channel_repository_test.go +++ b/session/pingpong/hermes_channel_repository_test.go @@ -150,7 +150,9 @@ func TestHermesChannelRepository_Fetch_publishesEarningChanges(t *testing.T) { promiseProvider := &mockHermesPromiseStorage{} channelStatusProvider := &mockProviderChannelStatusProvider{} publisher := mocks.NewEventBus() - mockBeneficiaryProvider := &mockBeneficiaryProvider{} + mockBeneficiaryProvider := &mockBeneficiaryProvider{ + b: beneficiaryID, + } mockHermesCaller := &mockHermesCaller{} addrProv := &mockAddressProvider{} repo := NewHermesChannelRepository(promiseProvider, channelStatusProvider, publisher, mockBeneficiaryProvider, mockHermesCaller, addrProv, signerFactory, &mockEncryptor{}) @@ -162,7 +164,7 @@ func TestHermesChannelRepository_Fetch_publishesEarningChanges(t *testing.T) { assert.NoError(t, err) // then - expectedChannel1 := NewHermesChannel("1", id, hermesID, expectedChannelStatus1, expectedPromise1) + expectedChannel1 := NewHermesChannel("1", id, hermesID, expectedChannelStatus1, expectedPromise1, beneficiaryID) assert.Equal(t, expectedChannel1, channel) assert.Eventually(t, func() bool { lastEvent, ok := publisher.Pop().(event.AppEventEarningsChanged) @@ -205,7 +207,7 @@ func TestHermesChannelRepository_Fetch_publishesEarningChanges(t *testing.T) { assert.NoError(t, err) // then - expectedChannel2 := NewHermesChannel("1", id, hermesID, expectedChannelStatus2, expectedPromise2) + expectedChannel2 := NewHermesChannel("1", id, hermesID, expectedChannelStatus2, expectedPromise2, beneficiaryID) assert.Equal(t, expectedChannel2, channel) assert.Eventually(t, func() bool { lastEvent, ok := publisher.Pop().(event.AppEventEarningsChanged) @@ -247,6 +249,45 @@ func TestHermesChannelRepository_Fetch_publishesEarningChanges(t *testing.T) { }, 2*time.Second, 10*time.Millisecond) } +func TestHermesChannelRepository_BeneficiaryReset(t *testing.T) { + // given + id := identity.FromAddress("0x0000000000000000000000000000000000000001") + hermesID = common.HexToAddress("0x00000000000000000000000000000000000000002") + channelID := common.HexToAddress("0x00000000000000000000000000000000000000003") + beneficiary := common.HexToAddress("0x144") + + promiseProvider := &mockHermesPromiseStorage{} + channelStatusProvider := &mockProviderChannelStatusProvider{ + channelToReturn: mockProviderChannel, + } + publisher := mocks.NewEventBus() + mockBeneficiaryProvider := &mockBeneficiaryProvider{ + b: beneficiary, + } + mockHermesCaller := &mockHermesCaller{} + addrProv := &mockAddressProvider{} + repo := NewHermesChannelRepository(promiseProvider, channelStatusProvider, publisher, mockBeneficiaryProvider, mockHermesCaller, addrProv, signerFactory, &mockEncryptor{}) + + // when + promise := HermesPromise{ChannelID: channelID.Hex(), Identity: id, HermesID: hermesID} + err := repo.updateChannelWithLatestPromise(1, channelID.Hex(), id, hermesID, promise) + assert.NoError(t, err) + hermesChannel, exists := repo.Get(1, id, hermesID) + + // then + assert.True(t, exists) + assert.Equal(t, beneficiary, hermesChannel.Beneficiary) + + // when + err = repo.updateChannelWithLatestPromise(1, channelID.Hex(), id, hermesID, promise) + assert.NoError(t, err) + hermesChannel, exists = repo.Get(1, id, hermesID) + + // then + assert.True(t, exists) + assert.Equal(t, beneficiary, hermesChannel.Beneficiary) +} + type mockBeneficiaryProvider struct { b common.Address } diff --git a/session/pingpong/hermes_promise_settler_test.go b/session/pingpong/hermes_promise_settler_test.go index 90cdeb6de..e61e6d34b 100644 --- a/session/pingpong/hermes_promise_settler_test.go +++ b/session/pingpong/hermes_promise_settler_test.go @@ -33,6 +33,7 @@ import ( "github.com/mysteriumnetwork/payments/bindings" "github.com/mysteriumnetwork/payments/client" "github.com/mysteriumnetwork/payments/crypto" + "github.com/mysteriumnetwork/payments/units" "github.com/stretchr/testify/assert" ) @@ -177,14 +178,14 @@ func TestPromiseSettler_handleHermesPromiseReceived(t *testing.T) { fac := &mockHermesCallerFactory{} tm := &mockTransactor{ feesToReturn: registry.FeesResponse{ - Fee: crypto.FloatToBigMyst(0.05), + Fee: units.FloatEthToBigIntWei(0.05), ValidUntil: time.Now().Add(30 * time.Minute), }, } settler := NewHermesPromiseSettler(tm, &mockHermesPromiseStorage{}, &mockPayAndSettler{}, &mockAddressProvider{}, fac.Get, &mockHermesURLGetter{}, channelProvider, channelStatusProvider, mrsp, ks, &settlementHistoryStorageMock{}, &mockPublisher{}, &mockObserver{}, cfg) // no receive on unknown provider - channelProvider.channelToReturn = NewHermesChannel("1", mockID, hermesID, mockProviderChannel, HermesPromise{}) + channelProvider.channelToReturn = NewHermesChannel("1", mockID, hermesID, mockProviderChannel, HermesPromise{}, beneficiaryID) settler.handleHermesPromiseReceived(event.AppEventHermesPromise{ HermesID: hermesID, ProviderID: mockID, @@ -196,7 +197,7 @@ func TestPromiseSettler_handleHermesPromiseReceived(t *testing.T) { registered: false, settleInProgress: map[common.Address]struct{}{}, } - channelProvider.channelToReturn = NewHermesChannel("1", mockID, hermesID, mockProviderChannel, HermesPromise{}) + channelProvider.channelToReturn = NewHermesChannel("1", mockID, hermesID, mockProviderChannel, HermesPromise{}, beneficiaryID) settler.handleHermesPromiseReceived(event.AppEventHermesPromise{ HermesID: hermesID, ProviderID: mockID, @@ -205,12 +206,12 @@ func TestPromiseSettler_handleHermesPromiseReceived(t *testing.T) { // should receive on registered provider. Should also expect a recalculated balance to be added to the settlementState expectedChannel := client.ProviderChannel{Stake: big.NewInt(1000)} - expectedPromise := crypto.Promise{Amount: crypto.FloatToBigMyst(6)} + expectedPromise := crypto.Promise{Amount: units.FloatEthToBigIntWei(6)} settler.currentState[mockID] = settlementState{ registered: true, settleInProgress: map[common.Address]struct{}{}, } - channelProvider.channelToReturn = NewHermesChannel("1", mockID, hermesID, expectedChannel, HermesPromise{Promise: expectedPromise}) + channelProvider.channelToReturn = NewHermesChannel("1", mockID, hermesID, expectedChannel, HermesPromise{Promise: expectedPromise}, beneficiaryID) settler.handleHermesPromiseReceived(event.AppEventHermesPromise{ HermesID: hermesID, ProviderID: mockID, @@ -223,14 +224,14 @@ func TestPromiseSettler_handleHermesPromiseReceived(t *testing.T) { // should not receive here due to balance being large and stake being small expectedChannel = client.ProviderChannel{ Stake: big.NewInt(0), - Settled: crypto.FloatToBigMyst(6), + Settled: units.FloatEthToBigIntWei(6), } - expectedPromise = crypto.Promise{Amount: crypto.FloatToBigMyst(8)} + expectedPromise = crypto.Promise{Amount: units.FloatEthToBigIntWei(8)} settler.currentState[mockID] = settlementState{ registered: true, settleInProgress: map[common.Address]struct{}{}, } - channelProvider.channelToReturn = NewHermesChannel("1", mockID, hermesID, expectedChannel, HermesPromise{Promise: expectedPromise}) + channelProvider.channelToReturn = NewHermesChannel("1", mockID, hermesID, expectedChannel, HermesPromise{Promise: expectedPromise}, beneficiaryID) settler.handleHermesPromiseReceived(event.AppEventHermesPromise{ HermesID: hermesID, ProviderID: mockID, @@ -331,7 +332,7 @@ func TestPromiseSettler_RejectsIfFeesExceedSettlementAmount(t *testing.T) { func TestPromiseSettler_RejectsIfFeesExceedMaxFee(t *testing.T) { fac := &mockHermesCallerFactory{} - transactorFee := crypto.FloatToBigMyst(0.8) + transactorFee := units.FloatEthToBigIntWei(0.8) hermesFee := big.NewInt(25000) promiseSettler := hermesPromiseSettler{ @@ -356,7 +357,7 @@ func TestPromiseSettler_RejectsIfFeesExceedMaxFee(t *testing.T) { settled := big.NewInt(6000) mockSettler := func(crypto.Promise) (string, error) { return "", nil } - err := promiseSettler.settle(mockSettler, identity.Identity{}, common.Address{}, mockPromise, common.Address{}, settled, crypto.FloatToBigMyst(0.6)) + err := promiseSettler.settle(mockSettler, identity.Identity{}, common.Address{}, mockPromise, common.Address{}, settled, units.FloatEthToBigIntWei(0.6)) assert.Equal(t, "current fee is more than the max", err.Error()) } @@ -436,7 +437,7 @@ func TestPromiseSettlerState_needsSettling(t *testing.T) { hps := &hermesPromiseSettler{ transactor: &mockTransactor{ feesToReturn: registry.FeesResponse{ - Fee: crypto.FloatToBigMyst(2.0), + Fee: units.FloatEthToBigIntWei(2.0), ValidUntil: time.Now().Add(30 * time.Minute), }, }, @@ -450,7 +451,8 @@ func TestPromiseSettlerState_needsSettling(t *testing.T) { mockID, hermesID, client.ProviderChannel{Stake: big.NewInt(0)}, - HermesPromise{Promise: crypto.Promise{Amount: crypto.FloatToBigMyst(10.1)}}, + HermesPromise{Promise: crypto.Promise{Amount: units.FloatEthToBigIntWei(10.1)}}, + beneficiaryID, ) needs, maxFee := hps.needsSettling(s, 0, 0.1, 5, 10, channel, 1) assert.True(t, needs, "should be true with balance more than max regardless of fees") @@ -459,7 +461,7 @@ func TestPromiseSettlerState_needsSettling(t *testing.T) { hps = &hermesPromiseSettler{ transactor: &mockTransactor{ feesToReturn: registry.FeesResponse{ - Fee: crypto.FloatToBigMyst(0.045), + Fee: units.FloatEthToBigIntWei(0.045), ValidUntil: time.Now().Add(30 * time.Minute), }, }, @@ -473,12 +475,13 @@ func TestPromiseSettlerState_needsSettling(t *testing.T) { mockID, hermesID, client.ProviderChannel{Stake: big.NewInt(0)}, - HermesPromise{Promise: crypto.Promise{Amount: crypto.FloatToBigMyst(5)}}, + HermesPromise{Promise: crypto.Promise{Amount: units.FloatEthToBigIntWei(5)}}, + beneficiaryID, ) needs, maxFee = hps.needsSettling(s, 0, 0.01, 5, 10, channel, 1) assert.True(t, needs, "should be true if fees are 1%% of unsettled amount") - assert.True(t, maxFee.Cmp(crypto.FloatToBigMyst(0.045)) > 0, "should be bigger than current fee") + assert.True(t, maxFee.Cmp(units.FloatEthToBigIntWei(0.045)) > 0, "should be bigger than current fee") s.registered = false needs, _ = hps.needsSettling(s, 0, 0.01, 5, 10, channel, 1) @@ -493,7 +496,7 @@ func TestPromiseSettlerState_needsSettling(t *testing.T) { hps = &hermesPromiseSettler{ transactor: &mockTransactor{ feesToReturn: registry.FeesResponse{ - Fee: crypto.FloatToBigMyst(0.051), + Fee: units.FloatEthToBigIntWei(0.051), ValidUntil: time.Now().Add(30 * time.Minute), }, }, @@ -508,6 +511,7 @@ func TestPromiseSettlerState_needsSettling(t *testing.T) { hermesID, client.ProviderChannel{Stake: big.NewInt(0)}, HermesPromise{Promise: crypto.Promise{Amount: big.NewInt(8999)}}, + beneficiaryID, ) needs, _ = hps.needsSettling(s, 0, 0.01, 5, 10, channel, 1) assert.False(t, needs, "should be false with fee more than 1%% of unsettled amount") @@ -522,6 +526,7 @@ func TestPromiseSettlerState_needsSettling(t *testing.T) { hermesID, client.ProviderChannel{Stake: big.NewInt(1000)}, HermesPromise{Promise: crypto.Promise{Amount: big.NewInt(1000)}}, + beneficiaryID, ) needs, maxFee = hps.needsSettling(s, 0.1, 0.01, 5, 10, channel, 1) assert.True(t, needs, "should be true with zero balance left") @@ -537,6 +542,7 @@ func TestPromiseSettlerState_needsSettling(t *testing.T) { hermesID, client.ProviderChannel{Stake: big.NewInt(1000)}, HermesPromise{Promise: crypto.Promise{Amount: big.NewInt(9000)}}, + beneficiaryID, ) needs, maxFee = hps.needsSettling(s, 0.1, 0.01, 5, 10, channel, 1) assert.True(t, needs, "should be true with 10% missing") @@ -552,6 +558,7 @@ func TestPromiseSettlerState_needsSettling(t *testing.T) { hermesID, client.ProviderChannel{Stake: big.NewInt(10000)}, HermesPromise{Promise: crypto.Promise{Amount: big.NewInt(8999)}}, + beneficiaryID, ) needs, _ = hps.needsSettling(s, 0.1, 0.01, 5, 10, channel, 1) assert.False(t, needs, "should be false with 10.01% missing") @@ -654,6 +661,7 @@ func (mrsp *mockRegistrationStatusProvider) GetRegistrationStatus(chainID int64, var errMock = errors.New("explosions everywhere") var mockID = identity.FromAddress("0x0000000000000000000000000000000000000001") var hermesID = common.HexToAddress("0x00000000000000000000000000000000000000002") +var beneficiaryID = common.HexToAddress("0x00000000000000000000000000000000000000132") var mockChainIdentity = "0" + mockID.Address var mockProviderChannel = client.ProviderChannel{