Convert blockstore TransactionStatus column family to protobufs (#15733)

* Prevent panic if TransactionStatus can't be deserialized

* Convert Blockstore TransactionStatus column to protobuf

* Add compatability test
This commit is contained in:
Tyera Eulberg
2021-03-05 09:05:35 -07:00
committed by GitHub
parent bd13262b42
commit 7e65289729
8 changed files with 383 additions and 131 deletions

View File

@ -1,4 +1,4 @@
use crate::StoredExtendedRewards;
use crate::{StoredExtendedRewards, StoredTransactionStatusMeta};
use solana_account_decoder::parse_token::{real_number_string_trimmed, UiTokenAmount};
use solana_sdk::{
hash::Hash,
@ -312,6 +312,13 @@ impl From<TransactionStatusMeta> for generated::TransactionStatusMeta {
}
}
impl From<StoredTransactionStatusMeta> for generated::TransactionStatusMeta {
fn from(meta: StoredTransactionStatusMeta) -> Self {
let meta: TransactionStatusMeta = meta.into();
meta.into()
}
}
impl TryFrom<generated::TransactionStatusMeta> for TransactionStatusMeta {
type Error = bincode::Error;

View File

@ -1,6 +1,13 @@
use serde::{Deserialize, Serialize};
use solana_sdk::deserialize_utils::default_on_eof;
use solana_transaction_status::{Reward, RewardType};
use solana_account_decoder::{
parse_token::{real_number_string_trimmed, UiTokenAmount},
StringAmount,
};
use solana_sdk::{deserialize_utils::default_on_eof, transaction::Result};
use solana_transaction_status::{
InnerInstructions, Reward, RewardType, TransactionStatusMeta, TransactionTokenBalance,
};
use std::str::FromStr;
pub mod convert;
@ -50,3 +57,151 @@ impl From<Reward> for StoredExtendedReward {
}
}
}
#[derive(Serialize, Deserialize)]
pub struct StoredTokenAmount {
pub ui_amount: f64,
pub decimals: u8,
pub amount: StringAmount,
}
impl From<StoredTokenAmount> for UiTokenAmount {
fn from(value: StoredTokenAmount) -> Self {
let StoredTokenAmount {
ui_amount,
decimals,
amount,
} = value;
let ui_amount_string =
real_number_string_trimmed(u64::from_str(&amount).unwrap_or(0), decimals);
Self {
ui_amount: Some(ui_amount),
decimals,
amount,
ui_amount_string,
}
}
}
impl From<UiTokenAmount> for StoredTokenAmount {
fn from(value: UiTokenAmount) -> Self {
let UiTokenAmount {
ui_amount,
decimals,
amount,
..
} = value;
Self {
ui_amount: ui_amount.unwrap_or(0.0),
decimals,
amount,
}
}
}
#[derive(Serialize, Deserialize)]
pub struct StoredTransactionTokenBalance {
pub account_index: u8,
pub mint: String,
pub ui_token_amount: StoredTokenAmount,
}
impl From<StoredTransactionTokenBalance> for TransactionTokenBalance {
fn from(value: StoredTransactionTokenBalance) -> Self {
let StoredTransactionTokenBalance {
account_index,
mint,
ui_token_amount,
} = value;
Self {
account_index,
mint,
ui_token_amount: ui_token_amount.into(),
}
}
}
impl From<TransactionTokenBalance> for StoredTransactionTokenBalance {
fn from(value: TransactionTokenBalance) -> Self {
let TransactionTokenBalance {
account_index,
mint,
ui_token_amount,
} = value;
Self {
account_index,
mint,
ui_token_amount: ui_token_amount.into(),
}
}
}
#[derive(Serialize, Deserialize)]
pub struct StoredTransactionStatusMeta {
pub status: Result<()>,
pub fee: u64,
pub pre_balances: Vec<u64>,
pub post_balances: Vec<u64>,
#[serde(deserialize_with = "default_on_eof")]
pub inner_instructions: Option<Vec<InnerInstructions>>,
#[serde(deserialize_with = "default_on_eof")]
pub log_messages: Option<Vec<String>>,
#[serde(deserialize_with = "default_on_eof")]
pub pre_token_balances: Option<Vec<StoredTransactionTokenBalance>>,
#[serde(deserialize_with = "default_on_eof")]
pub post_token_balances: Option<Vec<StoredTransactionTokenBalance>>,
}
impl From<StoredTransactionStatusMeta> for TransactionStatusMeta {
fn from(value: StoredTransactionStatusMeta) -> Self {
let StoredTransactionStatusMeta {
status,
fee,
pre_balances,
post_balances,
inner_instructions,
log_messages,
pre_token_balances,
post_token_balances,
} = value;
Self {
status,
fee,
pre_balances,
post_balances,
inner_instructions,
log_messages,
pre_token_balances: pre_token_balances
.map(|balances| balances.into_iter().map(|balance| balance.into()).collect()),
post_token_balances: post_token_balances
.map(|balances| balances.into_iter().map(|balance| balance.into()).collect()),
}
}
}
impl From<TransactionStatusMeta> for StoredTransactionStatusMeta {
fn from(value: TransactionStatusMeta) -> Self {
let TransactionStatusMeta {
status,
fee,
pre_balances,
post_balances,
inner_instructions,
log_messages,
pre_token_balances,
post_token_balances,
} = value;
Self {
status,
fee,
pre_balances,
post_balances,
inner_instructions,
log_messages,
pre_token_balances: pre_token_balances
.map(|balances| balances.into_iter().map(|balance| balance.into()).collect()),
post_token_balances: post_token_balances
.map(|balances| balances.into_iter().map(|balance| balance.into()).collect()),
}
}
}