Skip to content

Commit 0476629

Browse files
Merge pull request #66 from 0xPolygon/fix/datalost
Fix lost data
2 parents 3b038f6 + 0d1396b commit 0476629

File tree

3 files changed

+79
-0
lines changed

3 files changed

+79
-0
lines changed

db/migrations/state/validium-001.sql

+32
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
-- +migrate Up
2+
3+
CREATE TABLE IF NOT EXISTS state.batch_data_backup
4+
(
5+
batch_num BIGINT,
6+
data BYTEA,
7+
created_at TIMESTAMP WITH TIME ZONE NOT NULL DEFAULT CURRENT_TIMESTAMP,
8+
PRIMARY KEY (batch_num, created_at)
9+
);
10+
11+
-- +migrate StatementBegin
12+
CREATE OR REPLACE FUNCTION backup_batch() RETURNS trigger AS $$
13+
BEGIN
14+
INSERT INTO state.batch_data_backup (batch_num, data)
15+
VALUES (OLD.batch_num, OLD.raw_txs_data)
16+
ON CONFLICT (batch_num, created_at) DO UPDATE SET
17+
data = EXCLUDED.data;
18+
RETURN OLD;
19+
END;
20+
$$
21+
LANGUAGE plpgsql;
22+
-- +migrate StatementEnd
23+
24+
CREATE TRIGGER backup_batch
25+
BEFORE DELETE ON state.batch FOR EACH ROW
26+
EXECUTE PROCEDURE backup_batch();
27+
28+
-- +migrate Down
29+
30+
DROP TRIGGER IF EXISTS backup_batch ON state.batch;
31+
DROP FUNCTION IF EXISTS backup_batch();
32+
DROP TABLE IF EXISTS state.batch_data_backup;

state/pgstatestorage.go

+20
Original file line numberDiff line numberDiff line change
@@ -2912,6 +2912,26 @@ func (p *PostgresStorage) GetBatchL2DataByNumber(ctx context.Context, batchNumbe
29122912
var batchL2Data []byte
29132913
err := q.QueryRow(ctx, getBatchL2DataByBatchNumber, batchNumber).Scan(&batchL2Data)
29142914

2915+
if errors.Is(err, pgx.ErrNoRows) {
2916+
return p.GetBatchL2DataByNumberFromBackup(ctx, batchNumber, dbTx)
2917+
} else if err != nil {
2918+
return nil, err
2919+
}
2920+
return batchL2Data, nil
2921+
}
2922+
2923+
// GetBatchL2DataByNumberFromBackup returns the batch L2 data of the given batch number from the backup table
2924+
func (p *PostgresStorage) GetBatchL2DataByNumberFromBackup(ctx context.Context, batchNumber uint64, dbTx pgx.Tx) ([]byte, error) {
2925+
getBatchL2DataByBatchNumber := `
2926+
SELECT data FROM state.batch_data_backup
2927+
WHERE batch_num = $1
2928+
ORDER BY created_at DESC
2929+
LIMIT 1
2930+
`
2931+
q := p.getExecQuerier(dbTx)
2932+
var batchL2Data []byte
2933+
err := q.QueryRow(ctx, getBatchL2DataByBatchNumber, batchNumber).Scan(&batchL2Data)
2934+
29152935
if errors.Is(err, pgx.ErrNoRows) {
29162936
return nil, ErrNotFound
29172937
} else if err != nil {

state/pgstatestorage_test.go

+27
Original file line numberDiff line numberDiff line change
@@ -993,4 +993,31 @@ func TestGetBatchL2DataByNumber(t *testing.T) {
993993
actualData, err := testState.GetBatchL2DataByNumber(ctx, batchNum, tx)
994994
require.NoError(t, err)
995995
assert.Equal(t, expectedData, actualData)
996+
997+
// Force backup
998+
_, err = tx.Exec(ctx, "DELETE FROM state.batch")
999+
require.NoError(t, err)
1000+
1001+
// Get batch 4 from backup
1002+
batchNum = 4
1003+
data, err = testState.GetBatchL2DataByNumber(ctx, batchNum, tx)
1004+
require.NoError(t, err)
1005+
assert.Nil(t, data)
1006+
1007+
// Get batch 5 from backup
1008+
batchNum = 5
1009+
actualData, err = testState.GetBatchL2DataByNumber(ctx, batchNum, tx)
1010+
require.NoError(t, err)
1011+
assert.Equal(t, expectedData, actualData)
1012+
1013+
// Update batch 5 and get it from backup
1014+
expectedData = []byte("new foo bar")
1015+
_, err = tx.Exec(ctx, openBatchSQL, batchNum, expectedData)
1016+
require.NoError(t, err)
1017+
_, err = tx.Exec(ctx, "DELETE FROM state.batch")
1018+
require.NoError(t, err)
1019+
actualData, err = testState.GetBatchL2DataByNumber(ctx, batchNum, tx)
1020+
require.NoError(t, err)
1021+
assert.Equal(t, expectedData, actualData)
1022+
9961023
}

0 commit comments

Comments
 (0)