Επαλήθευση διεύθυνσης

Η αποστολή κεφαλαίων σε λανθασμένη διεύθυνση μπορεί να οδηγήσει σε μόνιμη απώλεια. Η επαλήθευση διεύθυνσης διασφαλίζει ότι στέλνετε μόνο σε διευθύνσεις που μπορούν να λάβουν και να αποκτήσουν πρόσβαση στα κεφάλαια.

Η επικύρωση εξαρτάται από το τι στέλνετε:

  • Τα SPL tokens προστατεύονται εν μέρει από μόνα τους. Το Token Program απορρίπτει μια μεταφορά της οποίας οι λογαριασμοί δεν αντιστοιχούν στο αναμενόμενο mint, οπότε μια λανθασμένα κατευθυνόμενη μεταφορά token αποτυγχάνει χωρίς απώλεια κεφαλαίων. Το μεγαλύτερο μέρος αυτής της σελίδας καλύπτει αποστολές SPL token.
  • Το εγγενές SOL δεν έχει τέτοια προστασία. Μια μεταφορά System Program επιτυγχάνει σε οποιονδήποτε λογαριασμό, οπότε ένας λανθασμένος παραλήπτης κλειδώνει οριστικά το SOL. Δείτε Αποστολή εγγενούς SOL.

Δείτε Πώς Λειτουργούν οι Πληρωμές στο Solana για βασικές έννοιες πληρωμών.

Κατανόηση των Διευθύνσεων Solana

Οι λογαριασμοί Solana έχουν δύο τύπους διευθύνσεων: επί καμπύλης και εκτός καμπύλης.

Διευθύνσεις Επί Καμπύλης

Οι τυπικές διευθύνσεις είναι τα δημόσια κλειδιά από Ed25519 keypairs. Αυτές οι διευθύνσεις:

  • Διαθέτουν αντίστοιχο ιδιωτικό κλειδί που μπορεί να υπογράφει συναλλαγές
  • Χρησιμοποιούνται ως διευθύνσεις πορτοφολιού

Διευθύνσεις Εκτός Καμπύλης (PDAs)

Τα Program Derived Addresses παράγονται ντετερμινιστικά από ένα αναγνωριστικό προγράμματος και seeds. Αυτές οι διευθύνσεις:

  • Δεν διαθέτουν αντίστοιχο ιδιωτικό κλειδί
  • Μπορούν να υπογραφούν μόνο από το πρόγραμμα από το οποίο παράχθηκε η διεύθυνση

Τύποι Λογαριασμών στις Πληρωμές

Χρησιμοποιήστε τη διεύθυνση για να ανακτήσετε έναν λογαριασμό από το δίκτυο, ελέγξτε τον κάτοχο προγράμματος και τον τύπο λογαριασμού για να προσδιορίσετε πώς να χειριστείτε τη διεύθυνση.

Το να γνωρίζετε αν μια διεύθυνση είναι επί καμπύλης ή εκτός καμπύλης δεν σας λέει τι τύπο λογαριασμού είναι, ποιο πρόγραμμα τον κατέχει, ή αν υπάρχει λογαριασμός σε αυτή τη διεύθυνση. Πρέπει να ανακτήσετε τον λογαριασμό από το δίκτυο για να προσδιορίσετε αυτές τις λεπτομέρειες.

Λογαριασμοί System Program (Πορτοφόλια)

Οι λογαριασμοί που ανήκουν στο System Program είναι τυπικά πορτοφόλια. Για να στείλετε SPL tokens σε ένα πορτοφόλι, παράγετε και χρησιμοποιείτε το Associated Token Account (ATA) του.

Αφού παράγετε τη διεύθυνση ATA, ελέγξτε αν το token account υπάρχει στο onchain. Αν το ATA δεν υπάρχει, μπορείτε να συμπεριλάβετε μια εντολή για τη δημιουργία του token account του παραλήπτη στην ίδια συναλλαγή με τη μεταφορά. Ωστόσο, αυτό απαιτεί την πληρωμή rent για το νέο token account. Καθώς ο παραλήπτης κατέχει το ATA, το SOL που καταβλήθηκε για το rent δεν μπορεί να ανακτηθεί από τον αποστολέα.

Χωρίς προστατευτικές δικλείδες, η επιδότηση δημιουργίας ATA μπορεί να εκμεταλλευτεί. Ένας κακόβουλος χρήστης θα μπορούσε να ζητήσει μια μεταφορά, να δημιουργήσει το ATA του με δικά σας έξοδα, να κλείσει το ATA για να ανακτήσει το rent SOL και να επαναλάβει τη διαδικασία.

Token Accounts

Τα token accounts ανήκουν στο Token Program ή Token-2022 Program και αποθηκεύουν υπόλοιπα tokens. Αν η διεύθυνση που λαμβάνετε ανήκει σε ένα token program, θα πρέπει να επαληθεύσετε ότι ο λογαριασμός είναι ένα token account (όχι ένα mint account) και ότι αντιστοιχεί στο αναμενόμενο token mint account πριν αποστείλετε.

Τα Token Programs επικυρώνουν αυτόματα ότι και τα δύο token accounts σε μια μεταφορά περιέχουν tokens του ίδιου mint. Αν η επικύρωση αποτύχει, η συναλλαγή απορρίπτεται και δεν χάνονται κεφάλαια.

Mint Accounts

Τα mint accounts παρακολουθούν την προσφορά tokens και τα μεταδεδομένα ενός συγκεκριμένου token. Τα mint accounts ανήκουν επίσης στα Token Programs, αλλά δεν αποτελούν έγκυρους παραλήπτες για μεταφορές tokens. Η προσπάθεια αποστολής tokens σε μια διεύθυνση mint οδηγεί σε αποτυχημένη συναλλαγή, αλλά δεν χάνονται κεφάλαια.

Άλλοι Λογαριασμοί

Οι λογαριασμοί που ανήκουν σε άλλα προγράμματα απαιτούν μια πολιτική απόφαση. Ορισμένοι λογαριασμοί (π.χ. πορτοφόλια multisig) μπορεί να είναι έγκυροι κάτοχοι token account, ενώ άλλοι θα πρέπει να απορρίπτονται.

Αποστολή εγγενούς SOL

Η παραπάνω κατηγοριοποίηση καθορίζει πού μπορούν να μεταφερθούν τα SPL tokens. Το εγγενές SOL είναι πιο αυστηρό: ο μόνος ασφαλής παραλήπτης είναι ένα πορτοφόλι System Program (ή μια αχρησιμοποίητη διεύθυνση επί καμπύλης που γίνεται τέτοια).

Μια μεταφορά System Program προσθέτει lamport σε οποιονδήποτε λογαριασμό, συμπεριλαμβανομένων των mints, token accounts, προγραμμάτων και PDAs. Τα lamport μπορούν να μετακινηθούν μόνο από το πρόγραμμα ιδιοκτησίας του λογαριασμού, επομένως η αποστολή SOL σε λανθασμένο παραλήπτη μπορεί να οδηγήσει σε μόνιμη απώλεια κεφαλαίων.

Σε αντίθεση με τη μεταφορά SPL token, η συναλλαγή δεν αποτυγχάνει όταν ο παραλήπτης είναι μια μη αναμενόμενη διεύθυνση.

Κατά την αποστολή εγγενούς SOL, μόνο ένα αποτέλεσμα IS_WALLET είναι αποδεκτό. Το IS_TOKEN_ACCOUNT δεν είναι: ένα token account διατηρεί SPL tokens, και το SOL που αποστέλλεται εκεί βρίσκεται εκτός του ελέγχου του αποστολέα.

Αυτός είναι ένας συνηθισμένος τρόπος με τον οποίο χάνεται SOL: ένας χρήστης επικολλά τη διεύθυνση mint ενός token (ή μια διεύθυνση προγράμματος) σε μια ανάληψη SOL. Η μεταφορά ολοκληρώνεται επιτυχώς και το SOL δεν ανακτάται. Να κατηγοριοποιείτε πάντα τον παραλήπτη πριν υπογράψετε μια μεταφορά SOL.

Ροή Επαλήθευσης

Το παρακάτω διάγραμμα δείχνει ένα δέντρο αποφάσεων αναφοράς για την επικύρωση μιας διεύθυνσης:

Address Verification Flow

Ανάκτηση λογαριασμού

Χρησιμοποιήστε τη διεύθυνση για να ανακτήσετε τα στοιχεία του λογαριασμού από το δίκτυο.

Ο λογαριασμός δεν υπάρχει

Εάν δεν υπάρχει λογαριασμός σε αυτή τη διεύθυνση, ελέγξτε αν η διεύθυνση βρίσκεται επί καμπύλης ή εκτός καμπύλης:

  • Εκτός καμπύλης (PDA): Απορρίψτε συντηρητικά τη διεύθυνση για να αποφύγετε την αποστολή σε ένα ATA που μπορεί να είναι μη προσβάσιμο. Χωρίς έναν υπάρχοντα λογαριασμό, δεν μπορείτε να προσδιορίσετε από τη διεύθυνση μόνη της ποιο πρόγραμμα παρήγαγε αυτό το PDA ή αν η διεύθυνση αφορά ένα ATA. Η παραγωγή ενός ATA για αυτή τη διεύθυνση για αποστολή tokens θα μπορούσε να οδηγήσει σε κλείδωμα κεφαλαίων σε μη προσβάσιμο token account.

  • Στην καμπύλη: Αυτή είναι μια έγκυρη διεύθυνση πορτοφολιού (δημόσιο κλειδί) που δεν έχει χρηματοδοτηθεί ακόμα. Εξαγάγετε το ATA, ελέγξτε αν υπάρχει, και στείλτε tokens σε αυτό. Πρέπει να λάβετε μια απόφαση πολιτικής σχετικά με το αν θα χρηματοδοτήσετε τη δημιουργία του ATA αν δεν υπάρχει.

Ο λογαριασμός υπάρχει

Αν ένας λογαριασμός υπάρχει, ελέγξτε ποιο πρόγραμμα τον κατέχει:

  • System Program: Αυτό είναι ένα τυπικό πορτοφόλι. Εξαγάγετε το ATA, ελέγξτε αν υπάρχει, και στείλτε tokens σε αυτό. Πρέπει να λάβετε μια απόφαση πολιτικής σχετικά με το αν θα χρηματοδοτήσετε τη δημιουργία του ATA αν δεν υπάρχει.

  • Token Program / Token-2022: Επαληθεύστε ότι ο λογαριασμός είναι token account (όχι mint account) και ότι διατηρεί το token (mint) που σκοπεύετε να στείλετε. Αν είναι έγκυρο, στείλτε tokens απευθείας σε αυτή τη διεύθυνση. Αν είναι mint account ή token account για διαφορετικό mint, απορρίψτε τη διεύθυνση.

  • Άλλο Πρόγραμμα: Αυτό απαιτεί απόφαση πολιτικής. Ορισμένα προγράμματα όπως τα πορτοφόλια multisig μπορεί να είναι αποδεκτοί κάτοχοι token accounts. Αν η πολιτική σας το επιτρέπει, εξαγάγετε το ATA και στείλτε. Διαφορετικά, απορρίψτε τη διεύθυνση.

Demo

Το παρακάτω παράδειγμα εμφανίζει μόνο τη λογική επαλήθευσης διευθύνσεων. Αυτός είναι κώδικας αναφοράς για λόγους επεξήγησης.

Το demo δεν δείχνει πώς να εξαχθεί ένα ATA ή να δημιουργηθεί μια συναλλαγή για αποστολή tokens. Ανατρέξτε στην τεκμηρίωση για το token account και τη μεταφορά token για παραδείγματα κώδικα.

Το demo παρακάτω χρησιμοποιεί τρία πιθανά αποτελέσματα:

ΑποτέλεσμαΣημασίαΕνέργεια
IS_WALLETΈγκυρη διεύθυνση πορτοφολιούΕξαγωγή και αποστολή στο associated token account
IS_TOKEN_ACCOUNTΈγκυρο token accountΑποστολή tokens απευθείας σε αυτή τη διεύθυνση
REJECTΜη έγκυρη διεύθυνσηΜην αποστείλετε

Στη συνέχεια αντιστοιχεί κάθε αποτέλεσμα στην αποδεκτότητα ανά στοιχείο με canReceiveNativeSol (μόνο πορτοφόλια) και canReceiveSplToken (πορτοφόλια ή token accounts). Ένα token account επιστρέφει IS_TOKEN_ACCOUNT, άρα μπορεί να λαμβάνει SPL tokens αλλά όχι εγγενές SOL — η διάκριση που αποτρέπει το κλείδωμα του SOL.

Demo
/**
* Validates an input address and classifies it as a wallet, token account, or invalid.
*
* @param inputAddress - The address to validate
* @param rpc - Optional RPC client (defaults to mainnet)
* @returns Classification result:
* - IS_WALLET: Valid wallet address
* - IS_TOKEN_ACCOUNT: Valid token account
* - REJECT: Invalid address for transfers
*/
export async function validateAddress(
inputAddress: Address,
rpc: Rpc<GetAccountInfoApi> = defaultRpc
): Promise<ValidationResult> {
const account = await fetchJsonParsedAccount(rpc, inputAddress);
// Log the account data for demo
console.log("\nAccount:", account);
// Account doesn't exist onchain
if (!account.exists) {
// Off-curve = PDA that doesn't exist as an account
// Reject conservatively to avoid sending to an address that may be inaccessible.
if (isOffCurveAddress(inputAddress)) {
return { type: "REJECT", reason: "PDA doesn't exist as an account" };
}
// On-curve = valid keypair address, treat as unfunded wallet
return { type: "IS_WALLET" };
}
// Account exists, check program owner
const owner = account.programAddress;
// System Program = wallet
if (owner === SYSTEM_PROGRAM) {
return { type: "IS_WALLET" };
}
// Token Program or Token-2022, check if token account
if (owner === TOKEN_PROGRAM || owner === TOKEN_2022_PROGRAM) {
const accountType = (
account.data as { parsedAccountMeta?: { type?: string } }
).parsedAccountMeta?.type;
if (accountType === "account") {
return { type: "IS_TOKEN_ACCOUNT" };
}
// Reject if not a token account (mint account)
return {
type: "REJECT",
reason: "Not a token account"
};
}
// Unknown program owner
return { type: "REJECT", reason: "Unknown program owner" };
}
/**
* Native SOL is only safe to send to a wallet. Any other account locks it.
*/
function canReceiveNativeSol(result: ValidationResult): boolean {
return result.type === "IS_WALLET";
}
/**
* SPL tokens can go to a wallet (via its ATA) or directly to a token account.
*/
function canReceiveSplToken(result: ValidationResult): boolean {
return result.type === "IS_WALLET" || result.type === "IS_TOKEN_ACCOUNT";
}
// =============================================================================
// Examples
// =============================================================================
Console
Click to execute the code.

Is this page helpful?

© 2026 Ίδρυμα Solana. Με επιφύλαξη παντός δικαιώματος.