- Add TokenCard and CexAnalysisCard components for displaying token data - Implement real-time Redis event streaming for token updates - Add environment-based configuration system for dev/prod Redis servers - Create comprehensive hunting ground dashboard with card management - Add individual and bulk card removal functionality - Implement browser integration for token details viewing - Add timestamp utilities and proper type handling for Redis events - Create production-ready configuration with 154.38.185.112 Redis server - Add comprehensive documentation in README.md and CONTRIBUTORS.md - Restructure project architecture with proper Electron-Vue integration BREAKING CHANGE: Redis configuration now uses environment-based settings
88 lines
No EOL
2.4 KiB
TypeScript
88 lines
No EOL
2.4 KiB
TypeScript
import { type Address, address, getAddressDecoder, isAddress } from '@solana/kit';
|
|
|
|
/**
|
|
* Converts a 32-byte Uint8Array to a Solana address using proper Solana utilities
|
|
*/
|
|
export function bytesToAddress(bytes: Uint8Array): Address {
|
|
if (bytes.length !== 32) {
|
|
throw new Error(`Expected 32 bytes, got ${bytes.length}`);
|
|
}
|
|
|
|
const decoder = getAddressDecoder();
|
|
return decoder.decode(bytes);
|
|
}
|
|
|
|
/**
|
|
* Converts a comma-separated byte string to a Solana address
|
|
* Example: "207,240,50,185,127,150,26,145..." -> "B9Lf9z5BfNPT4d5KMeaBFx8x1G4CULZYR1jA2kmxRDka"
|
|
*/
|
|
export function byteStringToAddress(byteString: string): Address {
|
|
const bytes = byteString.split(',').map(b => parseInt(b.trim(), 10));
|
|
|
|
if (bytes.length !== 32) {
|
|
throw new Error(`Expected 32 bytes, got ${bytes.length}`);
|
|
}
|
|
|
|
const uint8Array = new Uint8Array(bytes);
|
|
return bytesToAddress(uint8Array);
|
|
}
|
|
|
|
/**
|
|
* Converts an array of numbers to a Solana address
|
|
* Example: [207, 240, 50, 185, ...] -> "B9Lf9z5BfNPT4d5KMeaBFx8x1G4CULZYR1jA2kmxRDka"
|
|
*/
|
|
export function byteArrayToAddress(byteArray: number[]): Address {
|
|
if (byteArray.length !== 32) {
|
|
throw new Error(`Expected 32 bytes, got ${byteArray.length}`);
|
|
}
|
|
|
|
const uint8Array = new Uint8Array(byteArray);
|
|
return bytesToAddress(uint8Array);
|
|
}
|
|
|
|
/**
|
|
* Converts various input formats to a valid Solana address
|
|
*/
|
|
export function toSolanaAddress(input: string | Uint8Array | number[]): Address {
|
|
if (typeof input === 'string') {
|
|
// Check if it's already a valid address
|
|
if (isAddress(input)) {
|
|
return input;
|
|
}
|
|
|
|
// Check if it's a comma-separated byte string
|
|
if (input.includes(',')) {
|
|
return byteStringToAddress(input);
|
|
}
|
|
|
|
// Try to parse as address
|
|
return address(input);
|
|
}
|
|
|
|
if (input instanceof Uint8Array) {
|
|
return bytesToAddress(input);
|
|
}
|
|
|
|
if (Array.isArray(input)) {
|
|
return byteArrayToAddress(input);
|
|
}
|
|
|
|
throw new Error('Invalid input format for address conversion');
|
|
}
|
|
|
|
/**
|
|
* Truncates an address for display purposes
|
|
*/
|
|
export function truncateAddress(addr: string | Address, startLength = 4, endLength = 4): string {
|
|
if (addr.length <= startLength + endLength) {
|
|
return addr;
|
|
}
|
|
return `${addr.slice(0, startLength)}...${addr.slice(-endLength)}`;
|
|
}
|
|
|
|
/**
|
|
* Validates if a string is a valid Solana address
|
|
*/
|
|
export function isValidSolanaAddress(input: string): boolean {
|
|
return isAddress(input);
|
|
}
|