diff --git a/apps/core/src/types/objectChange.ts b/apps/core/src/types/objectChange.ts index 5c1c878e61d..8e135f21f3a 100644 --- a/apps/core/src/types/objectChange.ts +++ b/apps/core/src/types/objectChange.ts @@ -9,6 +9,7 @@ export type IotaObjectChangeTypes = | 'mutated' | 'deleted' | 'wrapped' + | 'unwrapped' | 'created'; export type WithDisplayFields = T & { display?: DisplayFieldsResponse }; diff --git a/apps/core/src/utils/transaction/getObjectChangeLabel.ts b/apps/core/src/utils/transaction/getObjectChangeLabel.ts index 4ee974c9e92..239534c2d16 100644 --- a/apps/core/src/utils/transaction/getObjectChangeLabel.ts +++ b/apps/core/src/utils/transaction/getObjectChangeLabel.ts @@ -11,6 +11,7 @@ export const ObjectChangeLabels = { published: 'Publish', deleted: 'Deleted', wrapped: 'Wrap', + unwrapped: 'Unwrap', }; export function getObjectChangeLabel(type: IotaObjectChangeTypes) { diff --git a/apps/core/src/utils/transaction/getObjectChangeSummary.ts b/apps/core/src/utils/transaction/getObjectChangeSummary.ts index 8635f3f911d..04de1406eae 100644 --- a/apps/core/src/utils/transaction/getObjectChangeSummary.ts +++ b/apps/core/src/utils/transaction/getObjectChangeSummary.ts @@ -7,6 +7,7 @@ import { IotaObjectChangeMutated, IotaObjectChangePublished, IotaObjectChangeTransferred, + IotaObjectChangeUnwrapped, IotaObjectChangeWrapped, } from '@iota/iota-sdk/client'; @@ -36,6 +37,10 @@ export const getObjectChangeSummary = (objectChanges: IotaObjectChangeWithDispla (change) => change.type === 'wrapped', ) as IotaObjectChangeWrapped[]; + const unwrapped = objectChanges.filter( + (change) => change.type === 'unwrapped', + ) as IotaObjectChangeUnwrapped[]; + const deleted = objectChanges.filter( (change) => change.type === 'deleted', ) as IotaObjectChangeDeleted[]; @@ -46,6 +51,7 @@ export const getObjectChangeSummary = (objectChanges: IotaObjectChangeWithDispla mutated: groupByOwner(mutated), published: groupByOwner(published), wrapped: groupByOwner(wrapped), + unwrapped: groupByOwner(unwrapped), deleted: groupByOwner(deleted), }; }; diff --git a/apps/explorer/src/pages/transaction-result/transaction-summary/index.tsx b/apps/explorer/src/pages/transaction-result/transaction-summary/index.tsx index 99f60527c08..57bfcf17ce4 100644 --- a/apps/explorer/src/pages/transaction-result/transaction-summary/index.tsx +++ b/apps/explorer/src/pages/transaction-result/transaction-summary/index.tsx @@ -51,6 +51,7 @@ const EMPTY_OBJECT_SUMMARY: ObjectChangeSummary = { mutated: {}, deleted: {}, wrapped: {}, + unwrapped: {}, created: {}, }; diff --git a/crates/iota-json-rpc-types/src/iota_transaction.rs b/crates/iota-json-rpc-types/src/iota_transaction.rs index de1d719266c..0b3a1ff7549 100644 --- a/crates/iota-json-rpc-types/src/iota_transaction.rs +++ b/crates/iota-json-rpc-types/src/iota_transaction.rs @@ -334,7 +334,8 @@ impl Display for IotaTransactionBlockResponse { mut published, mut transferred, mut wrapped, - ) = (vec![], vec![], vec![], vec![], vec![], vec![]); + mut unwrapped, + ) = (vec![], vec![], vec![], vec![], vec![], vec![], vec![]); for obj in object_changes { match obj { @@ -344,6 +345,7 @@ impl Display for IotaTransactionBlockResponse { ObjectChange::Published { .. } => published.push(obj), ObjectChange::Transferred { .. } => transferred.push(obj), ObjectChange::Wrapped { .. } => wrapped.push(obj), + ObjectChange::Unwrapped { .. } => unwrapped.push(obj), }; } @@ -353,6 +355,7 @@ impl Display for IotaTransactionBlockResponse { write_obj_changes(published, "Published", &mut builder)?; write_obj_changes(transferred, "Transferred", &mut builder)?; write_obj_changes(wrapped, "Wrapped", &mut builder)?; + write_obj_changes(unwrapped, "Unwrapped", &mut builder)?; let mut table = builder.build(); table.with(TablePanel::header("Object Changes")); diff --git a/crates/iota-json-rpc-types/src/object_changes.rs b/crates/iota-json-rpc-types/src/object_changes.rs index 6141c99b69d..61be19d4902 100644 --- a/crates/iota-json-rpc-types/src/object_changes.rs +++ b/crates/iota-json-rpc-types/src/object_changes.rs @@ -85,6 +85,20 @@ pub enum ObjectChange { #[serde_as(as = "AsSequenceNumber")] version: SequenceNumber, }, + /// Unwrapped object + #[serde(rename_all = "camelCase")] + Unwrapped { + sender: IotaAddress, + owner: Owner, + #[schemars(with = "String")] + #[serde_as(as = "IotaStructTag")] + object_type: StructTag, + object_id: ObjectID, + #[schemars(with = "AsSequenceNumber")] + #[serde_as(as = "AsSequenceNumber")] + version: SequenceNumber, + digest: ObjectDigest, + }, /// New object creation #[serde(rename_all = "camelCase")] Created { @@ -109,6 +123,7 @@ impl ObjectChange { | ObjectChange::Mutated { object_id, .. } | ObjectChange::Deleted { object_id, .. } | ObjectChange::Wrapped { object_id, .. } + | ObjectChange::Unwrapped { object_id, .. } | ObjectChange::Created { object_id, .. } => *object_id, } } @@ -133,6 +148,12 @@ impl ObjectChange { digest, .. } + | ObjectChange::Unwrapped { + object_id, + version, + digest, + .. + } | ObjectChange::Created { object_id, version, @@ -159,6 +180,9 @@ impl ObjectChange { | ObjectChange::Mutated { version, digest, .. } + | ObjectChange::Unwrapped { + version, digest, .. + } | ObjectChange::Created { version, digest, .. } => { @@ -259,6 +283,25 @@ impl Display for ObjectChange { u64::from(*version) ) } + ObjectChange::Unwrapped { + sender, + owner, + object_type, + object_id, + version, + digest, + } => { + write!( + f, + " ┌──\n │ ObjectID: {}\n │ Sender: {} \n │ Owner: {}\n │ ObjectType: {} \n │ Version: {}\n │ Digest: {}\n └──", + object_id, + sender, + owner, + object_type, + u64::from(*version), + digest + ) + } ObjectChange::Created { sender, owner, diff --git a/crates/iota-json-rpc/src/object_changes.rs b/crates/iota-json-rpc/src/object_changes.rs index 63ea01b2970..f204848ab34 100644 --- a/crates/iota-json-rpc/src/object_changes.rs +++ b/crates/iota-json-rpc/src/object_changes.rs @@ -52,6 +52,14 @@ pub async fn get_object_changes, E>( version, digest, }), + WriteKind::Unwrap => object_changes.push(ObjectChange::Unwrapped { + sender, + owner, + object_type, + object_id, + version, + digest, + }), _ => {} } } else if let Some(p) = o.data.try_as_package() { diff --git a/crates/iota/src/displays/dry_run_tx_block.rs b/crates/iota/src/displays/dry_run_tx_block.rs index 107729ed254..f9d6f21e402 100644 --- a/crates/iota/src/displays/dry_run_tx_block.rs +++ b/crates/iota/src/displays/dry_run_tx_block.rs @@ -49,7 +49,8 @@ impl Display for Pretty<'_, DryRunTransactionBlockResponse> { mut published, mut transferred, mut wrapped, - ) = (vec![], vec![], vec![], vec![], vec![], vec![]); + mut unwrapped, + ) = (vec![], vec![], vec![], vec![], vec![], vec![], vec![]); for obj in &response.object_changes { match obj { ObjectChange::Created { .. } => created.push(obj), @@ -58,6 +59,7 @@ impl Display for Pretty<'_, DryRunTransactionBlockResponse> { ObjectChange::Published { .. } => published.push(obj), ObjectChange::Transferred { .. } => transferred.push(obj), ObjectChange::Wrapped { .. } => wrapped.push(obj), + ObjectChange::Unwrapped { .. } => unwrapped.push(obj), }; } @@ -67,6 +69,7 @@ impl Display for Pretty<'_, DryRunTransactionBlockResponse> { write_obj_changes(published, "Published", &mut builder)?; write_obj_changes(transferred, "Transferred", &mut builder)?; write_obj_changes(wrapped, "Wrapped", &mut builder)?; + write_obj_changes(unwrapped, "Unwrapped", &mut builder)?; let mut table = builder.build(); table.with(TablePanel::header("Object Changes")); diff --git a/sdk/graphql-transport/src/mappers/transaction-block.ts b/sdk/graphql-transport/src/mappers/transaction-block.ts index 075199e4672..cab1fafd0b4 100644 --- a/sdk/graphql-transport/src/mappers/transaction-block.ts +++ b/sdk/graphql-transport/src/mappers/transaction-block.ts @@ -161,18 +161,34 @@ function mapObjectChanges( effects?.unwrapped?.forEach((unwrapped) => { changes.push({ - type: 'wrapped', + type: 'unwrapped', + digest: unwrapped.reference.digest, objectId: unwrapped.reference.objectId, objectType: toShortTypeString( transactionBlock.effects?.objectChanges?.nodes.find( (change) => change.address === unwrapped.reference.objectId, )?.outputState?.asMoveObject?.contents?.type.repr!, ), + owner: unwrapped.owner, sender: transactionBlock.sender?.address!, version: unwrapped.reference.version?.toString(), }); }); + effects?.wrapped?.forEach((wrapped) => { + changes.push({ + type: 'wrapped', + objectId: wrapped.objectId, + objectType: toShortTypeString( + transactionBlock.effects?.objectChanges?.nodes.find( + (change) => change.address === wrapped.objectId, + )?.inputState?.asMoveObject?.contents?.type.repr!, + ), + sender: transactionBlock.sender?.address!, + version: wrapped.version?.toString(), + }); + }); + return changes; } diff --git a/sdk/typescript/src/client/types/changes.ts b/sdk/typescript/src/client/types/changes.ts index 8d272dec19d..69d1bb72987 100644 --- a/sdk/typescript/src/client/types/changes.ts +++ b/sdk/typescript/src/client/types/changes.ts @@ -9,4 +9,5 @@ export type IotaObjectChangeTransferred = Extract; export type IotaObjectChangeDeleted = Extract; export type IotaObjectChangeWrapped = Extract; +export type IotaObjectChangeUnwrapped = Extract; export type IotaObjectChangeCreated = Extract;