sui_indexer/backfill/backfill_instances/
system_state_summary_json.rs

1// Copyright (c) Mysten Labs, Inc.
2// SPDX-License-Identifier: Apache-2.0
3
4use crate::backfill::backfill_task::BackfillTask;
5use crate::database::ConnectionPool;
6use crate::schema::epochs;
7use async_trait::async_trait;
8use diesel::{ExpressionMethods, QueryDsl};
9use diesel_async::{AsyncConnection, RunQueryDsl};
10use std::ops::RangeInclusive;
11use sui_types::sui_system_state::sui_system_state_summary::SuiSystemStateSummary;
12
13pub struct SystemStateSummaryJsonBackfill;
14
15#[async_trait]
16impl BackfillTask for SystemStateSummaryJsonBackfill {
17    async fn backfill_range(&self, pool: ConnectionPool, range: &RangeInclusive<usize>) {
18        let mut conn = pool.get().await.unwrap();
19
20        let results: Vec<Option<Vec<u8>>> = epochs::table
21            .select(epochs::system_state)
22            .filter(epochs::epoch.between(*range.start() as i64, *range.end() as i64))
23            .load(&mut conn)
24            .await
25            .unwrap();
26
27        let mut system_states = vec![];
28        for bytes in results {
29            let Some(bytes) = bytes else {
30                continue;
31            };
32            let system_state_summary: SuiSystemStateSummary = bcs::from_bytes(&bytes).unwrap();
33            let json_ser = serde_json::to_value(&system_state_summary).unwrap();
34            if system_state_summary.epoch == 1 {
35                // Each existing system state's epoch is off by 1.
36                // This means there won't be any row with a system state summary for epoch 0.
37                // We need to manually insert a row for epoch 0.
38                system_states.push((0, json_ser.clone()));
39            }
40            system_states.push((system_state_summary.epoch, json_ser));
41        }
42        conn.transaction::<_, diesel::result::Error, _>(|conn| {
43            Box::pin(async move {
44                for (epoch, json_ser) in system_states {
45                    diesel::update(epochs::table.filter(epochs::epoch.eq(epoch as i64)))
46                        .set(epochs::system_state_summary_json.eq(Some(json_ser)))
47                        .execute(conn)
48                        .await?;
49                }
50                Ok(())
51            })
52        })
53        .await
54        .unwrap();
55    }
56}