Skip to content

Commit

Permalink
Remove duplicates offchain data when storing in DB
Browse files Browse the repository at this point in the history
  • Loading branch information
begmaroman committed Aug 13, 2024
1 parent 6bf0e40 commit 3cc6e74
Show file tree
Hide file tree
Showing 5 changed files with 75 additions and 26 deletions.
3 changes: 3 additions & 0 deletions db/db.go
Original file line number Diff line number Diff line change
Expand Up @@ -374,6 +374,9 @@ func buildBatchKeysInsertQuery(bks []types.BatchKey) (string, []interface{}) {
func buildOffchainDataInsertQuery(ods []types.OffChainData) (string, []interface{}) {
const columnsAffected = 3

// Remove duplicates from the given offchain data
ods = types.RemoveDuplicateOffChainData(ods)

args := make([]interface{}, len(ods)*columnsAffected)
values := make([]string, len(ods))
for i, od := range ods {
Expand Down
13 changes: 0 additions & 13 deletions services/datacom/datacom.go
Original file line number Diff line number Diff line change
Expand Up @@ -55,19 +55,6 @@ func (d *Endpoints) signSequence(signedSequence types.SignedSequenceInterface) (
return "0x0", rpc.NewRPCError(rpc.DefaultErrorCode, "unauthorized")
}

// Make sure there are no duplicates in the given offchain data list
existingData := make(map[string]struct{})
offChainData := signedSequence.OffChainData()
for _, data := range offChainData {
key := data.Key.Hex()
if _, ok := existingData[key]; ok {
// The given key already exist in the offchain data list
return "0x0", rpc.NewRPCError(rpc.DefaultErrorCode, fmt.Sprintf("duplicate key: %s", key))
}

existingData[key] = struct{}{}
}

// Store off-chain data by hash (hash(L2Data): L2Data)
if err = d.db.StoreOffChainData(context.Background(), signedSequence.OffChainData()); err != nil {
return "0x0", rpc.NewRPCError(rpc.DefaultErrorCode,
Expand Down
13 changes: 0 additions & 13 deletions services/datacom/datacom_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -135,19 +135,6 @@ func TestDataCom_SignSequence(t *testing.T) {
})
})

t.Run("Duplicates found", func(t *testing.T) {
t.Parallel()

testFn(t, testConfig{
sender: otherPrivateKey,
expectedError: "duplicate key: 0x49d03a195e239b52779866b33024210fc7dc66e9c2998975c0aa45c1702549d5",
sequence: types.Sequence{
types.ArgBytes{0, 1},
types.ArgBytes{0, 1},
},
})
})

t.Run("Fail to store off chain data", func(t *testing.T) {
t.Parallel()

Expand Down
13 changes: 13 additions & 0 deletions types/types.go
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,19 @@ type OffChainData struct {
BatchNum uint64
}

// RemoveDuplicateOffChainData removes duplicate off chain data
func RemoveDuplicateOffChainData(ods []OffChainData) []OffChainData {
seen := make(map[common.Hash]struct{})
result := []OffChainData{}
for _, od := range ods {
if _, ok := seen[od.Key]; !ok {
seen[od.Key] = struct{}{}
result = append(result, od)
}
}
return result
}

// ArgUint64 helps to marshal uint64 values provided in the RPC requests
type ArgUint64 uint64

Expand Down
59 changes: 59 additions & 0 deletions types/types_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,9 @@ package types
import (
"testing"

"github.com/ethereum/go-ethereum/common"
"github.com/stretchr/testify/assert"

"github.com/stretchr/testify/require"
)

Expand Down Expand Up @@ -39,3 +42,59 @@ func TestIsHexValid(t *testing.T) {
})
}
}

func TestRemoveDuplicateOffChainData(t *testing.T) {
type args struct {
ods []OffChainData
}
tests := []struct {
name string
args args
want []OffChainData
}{
{
name: "no duplicates",
args: args{
ods: []OffChainData{
{
Key: common.BytesToHash([]byte("key1")),
},
{
Key: common.BytesToHash([]byte("key2")),
},
},
},
want: []OffChainData{
{
Key: common.BytesToHash([]byte("key1")),
},
{
Key: common.BytesToHash([]byte("key2")),
},
},
},
{
name: "with duplicates",
args: args{
ods: []OffChainData{
{
Key: common.BytesToHash([]byte("key1")),
},
{
Key: common.BytesToHash([]byte("key1")),
},
},
},
want: []OffChainData{
{
Key: common.BytesToHash([]byte("key1")),
},
},
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
assert.Equalf(t, tt.want, RemoveDuplicateOffChainData(tt.args.ods), "RemoveDuplicateOffChainData(%v)", tt.args.ods)
})
}
}

0 comments on commit 3cc6e74

Please sign in to comment.