Skip to content

Commit

Permalink
allow pukey auths to remove themselves
Browse files Browse the repository at this point in the history
  • Loading branch information
nhanphan committed Mar 2, 2024
1 parent 11418fa commit 9dab7cd
Show file tree
Hide file tree
Showing 2 changed files with 90 additions and 1 deletion.
83 changes: 83 additions & 0 deletions clients/js/test/removeAuthority.test.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import { generateSigner } from '@metaplex-foundation/umi';
import test from 'ava';
// import { base58 } from '@metaplex-foundation/umi/serializers';
import { generateSignerWithSol } from '@metaplex-foundation/umi-bundle-tests';
import {
Asset,
AssetWithPlugins,
Expand All @@ -11,6 +12,7 @@ import {
create,
fetchAsset,
fetchAssetWithPlugins,
plugin,
removeAuthority,
updateAuthority,
} from '../src';
Expand Down Expand Up @@ -217,3 +219,84 @@ test('it can remove the default authority from a plugin to make it immutable', a
],
});
});

test('it can remove a pubkey authority from a plugin if that pubkey is the signer authority', async (t) => {
// Given a Umi instance and a new signer.
const umi = await createUmi();
const assetAddress = generateSigner(umi);
const pubkeyAuth = await generateSignerWithSol(umi);

// When we create a new account.
await create(umi, {
dataState: DataState.AccountState,
assetAddress,
name: 'Test Bread',
uri: 'https://example.com/bread',
plugins: [],
}).sendAndConfirm(umi);

await addPlugin(umi, {
assetAddress: assetAddress.publicKey,
plugin: plugin('Freeze', [{ frozen: false }]),
}).sendAndConfirm(umi);

await addAuthority(umi, {
assetAddress: assetAddress.publicKey,
pluginType: PluginType.Freeze,
newAuthority: {
__kind: 'Pubkey',
address: pubkeyAuth.publicKey,
},
}).sendAndConfirm(umi);

const asset1 = await fetchAssetWithPlugins(umi, assetAddress.publicKey);
// console.log(JSON.stringify(asset1, (_, v) => typeof v === 'bigint' ? v.toString() : v, 2));
t.like(asset1, <AssetWithPlugins>{
publicKey: assetAddress.publicKey,
updateAuthority: updateAuthority('Address', [umi.identity.publicKey]),
owner: umi.identity.publicKey,
name: 'Test Bread',
uri: 'https://example.com/bread',
plugins: [
{
authorities: [{ __kind: 'Owner' }, { __kind: 'Pubkey', address: pubkeyAuth.publicKey }],
plugin: {
__kind: 'Freeze',
fields: [{ frozen: false }],
},
},
],
});

const umi2 = await createUmi();

await removeAuthority(umi2, {
payer: umi2.identity,
assetAddress: assetAddress.publicKey,
authority: pubkeyAuth,
pluginType: PluginType.Freeze,
authorityToRemove: {
__kind: 'Pubkey',
address: pubkeyAuth.publicKey,
},
}).sendAndConfirm(umi);

const asset2 = await fetchAssetWithPlugins(umi, assetAddress.publicKey);
// console.log(JSON.stringify(asset1, (_, v) => typeof v === 'bigint' ? v.toString() : v, 2));
t.like(asset2, <AssetWithPlugins>{
publicKey: assetAddress.publicKey,
updateAuthority: updateAuthority('Address', [umi.identity.publicKey]),
owner: umi.identity.publicKey,
name: 'Test Bread',
uri: 'https://example.com/bread',
plugins: [
{
authorities: [{ __kind: 'Owner' }],
plugin: {
__kind: 'Freeze',
fields: [{ frozen: false }],
},
},
],
});
});
8 changes: 7 additions & 1 deletion programs/mpl-core/src/plugins/utils.rs
Original file line number Diff line number Diff line change
Expand Up @@ -355,7 +355,13 @@ pub fn remove_authority_from_plugin<'a>(
.ok_or(MplCoreError::PluginNotFound)?;

let resolved_authority = resolve_authority_to_default(asset, authority);
if resolved_authority != registry_record.authorities[0] {

// TODO inspect this logic
if resolved_authority != registry_record.authorities[0]
&& ( // pubkey authorities can remove themselves if they are a signer
Authority::Pubkey { address: authority.key.clone() } == authority_to_remove.clone() &&
!registry_record.authorities.contains(authority_to_remove)
) {
return Err(MplCoreError::InvalidAuthority.into());
}

Expand Down

0 comments on commit 9dab7cd

Please sign in to comment.