@galliun/sofi-sdk
Version:
SDK for interacting with the Galliun SocialFi protocol
118 lines (103 loc) • 3.42 kB
text/typescript
import type { SuiClient, SuiTransactionBlockResponse } from '@mysten/sui/client';
import type { Transaction } from '@mysten/sui/transactions';
import type { NetworkName } from '../config';
import { SOFI_ERRORS } from '../config';
import type { SignTransaction } from '../util';
import { parseTxError } from '../util';
import { BaseSuiClient } from './BaseSuiClient';
/**
* Base arguments for manager constructors
* @property network - Network name (mainnet/testnet/devnet)
* @property packageId - Package ID of the payment contract
* @property configId - Config object ID
* @property sender - Optional default sender address
* @property suiClient - Sui client instance
* @property signTransaction - Transaction signing function
*/
export interface BaseManagerArgs {
network: NetworkName;
packageId: string;
configId: string;
profileRegistryId: string;
sender?: string;
suiClient: SuiClient;
signTransaction: SignTransaction;
}
/**
* Common options for transaction operations
* @property dryRun - Whether to simulate the transaction
* @property sender - Optional override sender address
*/
export interface CommonOptions {
dryRun?: boolean;
sender?: string;
}
export abstract class BaseManager extends BaseSuiClient {
protected readonly network: NetworkName;
protected readonly packageId: string;
protected readonly configId: string;
protected readonly profileRegistryId: string;
protected readonly sender?: string;
constructor(args: BaseManagerArgs) {
super({
suiClient: args.suiClient,
signTransaction: args.signTransaction,
});
this.network = args.network;
this.packageId = args.packageId;
this.configId = args.configId;
this.sender = args.sender;
this.profileRegistryId = args.profileRegistryId;
}
protected getSender(overrideSender?: string): string {
const sender = overrideSender || this.sender;
if (!sender) {
throw new Error('Sender address is required for this operation');
}
return sender;
}
protected async dryRunOrSignAndExecute(
tx: Transaction,
dryRun?: boolean,
overrideSender?: string,
): Promise<SuiTransactionBlockResponse> {
const sender = this.getSender(overrideSender);
if (dryRun) {
const results = await this.suiClient.devInspectTransactionBlock({
sender,
transactionBlock: tx,
});
return { digest: '', ...results };
} else {
return await this.signAndExecuteTransaction(tx);
}
}
protected isPackageType(type: string): boolean {
return type.startsWith(`${this.packageId}::`);
}
protected isType(type: string, module: string, struct: string): boolean {
return type == `${this.packageId}::${module}::${struct}`;
}
protected parseErrorCode(err: string): string {
const error = parseTxError(err);
if (!error || error.packageId !== this.packageId || !(error.code in SOFI_ERRORS)) {
return err;
}
return SOFI_ERRORS[error.code];
}
public errCodeToStr(
err: unknown,
defaultMessage: string,
errorMessages?: Record<string, string>,
): string | null {
if (!err) return defaultMessage;
const str = err instanceof Error ? err.message : String(err);
if (str.includes('Rejected from user')) return null;
if (str.includes('InsufficientCoinBalance')) return 'Insufficient balance for this operation';
const code = this.parseErrorCode(str);
if (errorMessages && code in errorMessages) {
return errorMessages[code];
}
return code || defaultMessage;
}
}