Token Minted

Endpoint: POST /api/v1/coin/minted

Description

This endpoint updates the token's status after successful minting and broadcasts the status change through WebSocket. It's typically called after a mint transaction has been confirmed on the blockchain.

Authentication

Required: Yes

Type: Bearer Token (JWT)

Request

Headers

Content-Type: application/json

Authorization: Bearer <your_jwt_token>

Body Parameters

Parameter
Type
Required
Description

token

string

Yes

The mint address of the token

tx

string

Yes

The transaction signature/hash

Example Request:

{

"token": "TokenMintAddress123...",

"tx": "TransactionSignature456..."

}

Response

Success Response

Status Code: 200 OK

Content-Type: application/json

{

"success": true

}

Error Response

Status Code: 500 Internal Server Error

{

"error": "An internal error occurred. Please try again later."

}

Example Usage

// Basic implementation

async function confirmTokenMinting(

tokenMintAddress: string,

transactionSignature: string

) {

try {

const response = await fetch('https://api.cybers.app/api/v1/coin/minted', {

method: 'POST',

headers: {

'Content-Type': 'application/json',

'Authorization': `Bearer ${localStorage.getItem('auth_token')}`

},

body: JSON.stringify({

token: tokenMintAddress,

tx: transactionSignature

})

});

if (!response.ok) {

throw new Error(`HTTP error! status: ${response.status}`);

}

const result = await response.json();

return result.success;

} catch (error) {

console.error('Error confirming token minting:', error);

throw error;

}

}

// Complete minting flow manager

class TokenMintingManager {

private wsConnection: WebSocket | null = null;

constructor(private readonly wsUrl: string) {

this.initializeWebSocket();

}

private initializeWebSocket() {

this.wsConnection = new WebSocket(this.wsUrl);

this.wsConnection.onmessage = (event) => {

const data = JSON.parse(event.data);

if (data.type === 'TOKEN_MINTED') {

this.handleMintingComplete(data.token, data.status);

}

};

}

async confirmMinting(

tokenMintAddress: string,

transactionSignature: string

) {

try {

await confirmTokenMinting(tokenMintAddress, transactionSignature);

// Subscribe to WebSocket updates for this token

this.wsConnection?.send(JSON.stringify({

type: 'SUBSCRIBE_TOKEN',

token: tokenMintAddress

}));

} catch (error) {

console.error('Minting confirmation failed:', error);

throw error;

}

}

private handleMintingComplete(token: string, status: string) {

// Implement your success handling logic here

console.log(`Token ${token} minting completed with status: ${status}`);

}

cleanup() {

this.wsConnection?.close();

}

}

Implementation Notes

Status Updates

// Example of status tracking

class TokenStatusTracker {

private statusListeners: Map<string, ((status: string) => void)[]> = new Map();

addStatusListener(

tokenMintAddress: string,

listener: (status: string) => void

) {

const listeners = this.statusListeners.get(tokenMintAddress) || [];

listeners.push(listener);

this.statusListeners.set(tokenMintAddress, listeners);

}

removeStatusListener(

tokenMintAddress: string,

listener: (status: string) => void

) {

const listeners = this.statusListeners.get(tokenMintAddress) || [];

const index = listeners.indexOf(listener);

if (index > -1) {

listeners.splice(index, 1);

this.statusListeners.set(tokenMintAddress, listeners);

}

}

notifyStatusChange(tokenMintAddress: string, status: string) {

const listeners = this.statusListeners.get(tokenMintAddress) || [];

listeners.forEach(listener => listener(status));

}

}

WebSocket Integration

// WebSocket event handler

class TokenMintedWebSocket {

private ws: WebSocket;

private reconnectAttempts = 0;

private readonly MAX_RECONNECT_ATTEMPTS = 5;

constructor(private readonly url: string) {

this.ws = this.connect();

}

private connect(): WebSocket {

const ws = new WebSocket(this.url);

ws.onopen = () => {

console.log('WebSocket connected');

this.reconnectAttempts = 0;

};

ws.onclose = () => {

if (this.reconnectAttempts < this.MAX_RECONNECT_ATTEMPTS) {

this.reconnectAttempts++;

setTimeout(() => {

this.ws = this.connect();

}, 1000 * this.reconnectAttempts);

}

};

ws.onerror = (error) => {

console.error('WebSocket error:', error);

};

return ws;

}

subscribeToToken(tokenMintAddress: string) {

if (this.ws.readyState === WebSocket.OPEN) {

this.ws.send(JSON.stringify({

type: 'SUBSCRIBE_TOKEN',

token: tokenMintAddress

}));

}

}

close() {

this.ws.close();

}

}

Transaction Verification

// Verify transaction before confirming

async function verifyMintTransaction(

connection: Connection,

signature: string

): Promise<boolean> {

try {

const status = await connection.getSignatureStatus(signature);

if (!status.value) {

throw new Error('Transaction not found');

}

if (status.value.err) {

throw new Error('Transaction failed');

}

return status.value.confirmationStatus === 'finalized';

} catch (error) {

console.error('Transaction verification failed:', error);

return false;

}

}

Best Practices

1. Error Recovery

async function confirmMintingWithRetry(

tokenMintAddress: string,

transactionSignature: string,

maxRetries = 3

): Promise<boolean> {

for (let attempt = 1; attempt <= maxRetries; attempt++) {

try {

const result = await confirmTokenMinting(

tokenMintAddress,

transactionSignature

);

return result;

} catch (error) {

if (attempt === maxRetries) throw error;

await new Promise(resolve =>

setTimeout(resolve, 1000 * attempt)

);

}

}

return false;

}

Event Handling

interface MintingEvent {

type: 'TOKEN_MINTED';

token: string;

status: string;

timestamp: number;

}

class MintingEventEmitter {

private listeners: ((event: MintingEvent) => void)[] = [];

addEventListener(listener: (event: MintingEvent) => void) {

this.listeners.push(listener);

}

removeEventListener(listener: (event: MintingEvent) => void) {

const index = this.listeners.indexOf(listener);

if (index > -1) {

this.listeners.splice(index, 1);

}

}

emit(event: MintingEvent) {

this.listeners.forEach(listener => listener(event));

}

}

Last updated