Skip to content

Commit

Permalink
Metaplex: Add submodule
Browse files Browse the repository at this point in the history
  • Loading branch information
skynetcap committed Nov 27, 2023
1 parent 0842c46 commit 1cc81f7
Show file tree
Hide file tree
Showing 5 changed files with 139 additions and 0 deletions.
19 changes: 19 additions & 0 deletions metaplex/pom.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<parent>
<artifactId>solanaj-programs</artifactId>
<groupId>com.mmorrell</groupId>
<version>1.18.2</version>
</parent>
<modelVersion>4.0.0</modelVersion>

<artifactId>metaplex</artifactId>

<properties>
<maven.compiler.source>17</maven.compiler.source>
<maven.compiler.target>17</maven.compiler.target>
</properties>

</project>
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
package com.mmorrell.metaplex.manager;

import com.mmorrell.metaplex.model.Metadata;
import org.p2p.solanaj.core.PublicKey;
import org.p2p.solanaj.rpc.RpcClient;
import org.p2p.solanaj.rpc.types.AccountInfo;
import org.p2p.solanaj.utils.ByteUtils;

import java.nio.charset.StandardCharsets;
import java.util.Base64;
import java.util.List;
import java.util.Optional;

public class MetaplexManager {

private final RpcClient client;
private static final PublicKey METAPLEX = new PublicKey("metaqbxxUerdq28cj1RbAWkYQm3ybzjb6a8bt518x1s");

// Offsets (from https://docs.metaplex.com/programs/token-metadata/accounts)
private static final int UPDATE_AUTHORITY_OFFSET = 1;
private static final int MINT_OFFSET = 33;
private static final int NAME_OFFSET = 65;
private static final int SYMBOL_OFFSET = 101;
private static final int URI_OFFSET = 115;

// Sizes (in bytes)
private static final int NAME_SIZE = 36;
private static final int SYMBOL_SIZE = 14;
private static final int URI_SIZE = 204;

public MetaplexManager(final RpcClient client) {
this.client = client;
}

public Optional<Metadata> getTokenMetadata(final PublicKey tokenMint) {
try {
final PublicKey.ProgramDerivedAddress metadataPda = PublicKey.findProgramAddress(
List.of(
"metadata".getBytes(StandardCharsets.UTF_8),
METAPLEX.toByteArray(),
tokenMint.toByteArray()
),
METAPLEX
);

final AccountInfo accountInfo = client.getApi().getAccountInfo(metadataPda.getAddress());
byte[] data = Base64.getDecoder().decode(accountInfo.getValue().getData().get(0));

final Metadata metadata = Metadata.builder()
.updateAuthority(PublicKey.readPubkey(data, UPDATE_AUTHORITY_OFFSET))
.tokenMint(PublicKey.readPubkey(data, MINT_OFFSET))
.name(new String(ByteUtils.readBytes(data, NAME_OFFSET, NAME_SIZE)).trim())
.symbol(new String(ByteUtils.readBytes(data, SYMBOL_OFFSET, SYMBOL_SIZE)).trim())
.uri(new String(ByteUtils.readBytes(data, URI_OFFSET, URI_SIZE)).trim())
.build();

return Optional.ofNullable(metadata);
} catch (Exception e) {
return Optional.empty();
}
}
}
17 changes: 17 additions & 0 deletions metaplex/src/main/java/com/mmorrell/metaplex/model/Metadata.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
package com.mmorrell.metaplex.model;

import lombok.Builder;
import lombok.Data;
import org.p2p.solanaj.core.PublicKey;

@Data
@Builder
public class Metadata {

private PublicKey updateAuthority;
private PublicKey tokenMint;
private String name;
private String symbol;
private String uri;

}
40 changes: 40 additions & 0 deletions metaplex/src/test/java/MetaplexTest.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
import com.mmorrell.metaplex.manager.MetaplexManager;
import com.mmorrell.metaplex.model.Metadata;
import org.junit.BeforeClass;
import org.junit.Test;
import org.p2p.solanaj.core.PublicKey;
import org.p2p.solanaj.rpc.Cluster;
import org.p2p.solanaj.rpc.RpcClient;

import java.util.Optional;
import java.util.logging.Logger;

import static org.junit.Assert.assertTrue;

public class MetaplexTest {

private static final Logger LOGGER = Logger.getLogger(MetaplexTest.class.getName());
private static final PublicKey CRIPCO_TOKEN_MINT = new PublicKey("3uejHm24sWmniGA5m4j4S1DVuGqzYBR5DJpevND4mivq");
private final RpcClient rpcClient = new RpcClient(Cluster.MAINNET);
private final MetaplexManager metaplexManager = new MetaplexManager(rpcClient);

@BeforeClass
public static void beforeClass() throws InterruptedException {
// Prevent RPCPool rate limit
Thread.sleep(2000L);
}

@Test
public void metadataTest() {
final Optional<Metadata> optionalMetadata = metaplexManager.getTokenMetadata(CRIPCO_TOKEN_MINT);
assertTrue(optionalMetadata.isPresent());

final Metadata metadata = optionalMetadata.get();
LOGGER.info(
String.format(
"Metadata: %s",
metadata
)
);
}
}
1 change: 1 addition & 0 deletions pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@
<module>magiceden</module>
<module>openbook</module>
<module>phoenix</module>
<module>metaplex</module>
</modules>

<properties>
Expand Down

0 comments on commit 1cc81f7

Please sign in to comment.