//! This code was AUTOGENERATED using the Codama library.
pub mod asset_v1_row;
pub mod collection_v1_row;
pub mod group_v1_row;
pub mod hashed_asset_v1_row;
pub mod plugin_header_v1_row;
pub mod plugin_registry_v1_row;

pub use self::{
    asset_v1_row::*, collection_v1_row::*, group_v1_row::*, hashed_asset_v1_row::*,
    plugin_header_v1_row::*, plugin_registry_v1_row::*,
};
use super::MplCoreAccount;

pub struct MplCoreAccountsMigration;

impl sqlx_migrator::Migration<sqlx::Postgres> for MplCoreAccountsMigration {
    fn app(&self) -> &str {
        "mpl-core"
    }

    fn name(&self) -> &str {
        "mpl_core_accounts"
    }

    fn operations(&self) -> Vec<Box<dyn sqlx_migrator::Operation<sqlx::Postgres>>> {
        vec![
            Box::new(AssetV1MigrationOperation),
            Box::new(CollectionV1MigrationOperation),
            Box::new(GroupV1MigrationOperation),
            Box::new(HashedAssetV1MigrationOperation),
            Box::new(PluginHeaderV1MigrationOperation),
            Box::new(PluginRegistryV1MigrationOperation),
        ]
    }

    fn parents(&self) -> Vec<Box<dyn sqlx_migrator::Migration<sqlx::Postgres>>> {
        vec![]
    }
}

pub struct MplCoreAccountWithMetadata(
    pub MplCoreAccount,
    pub carbon_core::account::AccountMetadata,
);

impl From<(MplCoreAccount, carbon_core::account::AccountMetadata)> for MplCoreAccountWithMetadata {
    fn from(value: (MplCoreAccount, carbon_core::account::AccountMetadata)) -> Self {
        MplCoreAccountWithMetadata(value.0, value.1)
    }
}

#[async_trait::async_trait]
impl carbon_core::postgres::operations::Insert for MplCoreAccountWithMetadata {
    async fn insert(&self, pool: &sqlx::PgPool) -> carbon_core::error::CarbonResult<()> {
        let MplCoreAccountWithMetadata(account, metadata) = self;

        match account {
            MplCoreAccount::PluginHeaderV1(account) => {
                let row = plugin_header_v1_row::PluginHeaderV1Row::from_parts(
                    *account.clone(),
                    metadata.clone(),
                );
                row.insert(pool).await?;
                Ok(())
            }
            MplCoreAccount::PluginRegistryV1(account) => {
                let row = plugin_registry_v1_row::PluginRegistryV1Row::from_parts(
                    *account.clone(),
                    metadata.clone(),
                );
                row.insert(pool).await?;
                Ok(())
            }
            MplCoreAccount::AssetV1(account) => {
                let row = asset_v1_row::AssetV1Row::from_parts(*account.clone(), metadata.clone());
                row.insert(pool).await?;
                Ok(())
            }
            MplCoreAccount::CollectionV1(account) => {
                let row = collection_v1_row::CollectionV1Row::from_parts(
                    *account.clone(),
                    metadata.clone(),
                );
                row.insert(pool).await?;
                Ok(())
            }
            MplCoreAccount::GroupV1(account) => {
                let row = group_v1_row::GroupV1Row::from_parts(*account.clone(), metadata.clone());
                row.insert(pool).await?;
                Ok(())
            }
            MplCoreAccount::HashedAssetV1(account) => {
                let row = hashed_asset_v1_row::HashedAssetV1Row::from_parts(
                    *account.clone(),
                    metadata.clone(),
                );
                row.insert(pool).await?;
                Ok(())
            }
        }
    }
}

#[async_trait::async_trait]
impl carbon_core::postgres::operations::Upsert for MplCoreAccountWithMetadata {
    async fn upsert(&self, pool: &sqlx::PgPool) -> carbon_core::error::CarbonResult<()> {
        let MplCoreAccountWithMetadata(account, metadata) = self;
        match account {
            MplCoreAccount::PluginHeaderV1(account) => {
                let row = plugin_header_v1_row::PluginHeaderV1Row::from_parts(
                    *account.clone(),
                    metadata.clone(),
                );
                row.upsert(pool).await?;
                Ok(())
            }
            MplCoreAccount::PluginRegistryV1(account) => {
                let row = plugin_registry_v1_row::PluginRegistryV1Row::from_parts(
                    *account.clone(),
                    metadata.clone(),
                );
                row.upsert(pool).await?;
                Ok(())
            }
            MplCoreAccount::AssetV1(account) => {
                let row = asset_v1_row::AssetV1Row::from_parts(*account.clone(), metadata.clone());
                row.upsert(pool).await?;
                Ok(())
            }
            MplCoreAccount::CollectionV1(account) => {
                let row = collection_v1_row::CollectionV1Row::from_parts(
                    *account.clone(),
                    metadata.clone(),
                );
                row.upsert(pool).await?;
                Ok(())
            }
            MplCoreAccount::GroupV1(account) => {
                let row = group_v1_row::GroupV1Row::from_parts(*account.clone(), metadata.clone());
                row.upsert(pool).await?;
                Ok(())
            }
            MplCoreAccount::HashedAssetV1(account) => {
                let row = hashed_asset_v1_row::HashedAssetV1Row::from_parts(
                    *account.clone(),
                    metadata.clone(),
                );
                row.upsert(pool).await?;
                Ok(())
            }
        }
    }
}
