Device Token یک شناسه منحصربهفرد است که APNS به هر دستگاه iOS برای مسیریابی اعلانهای فشاری اختصاص میدهد. توکن توسط سیستم هنگام ثبت درخواست برنامه برای دریافت اعلانها تولید میشود و باید به سرور ارسال شود تا اعلان فشاری دقیقاً به این دستگاه ارسال گردد. طبق Apple Developer Documentation, 2026، Device Token ممکن است با نصب مجدد برنامه، بازیابی دستگاه از پشتیبان یا بهروزرسانی iOS تغییر کند، بنابراین سرور باید به طور منظم توکنها را بهروزرسانی کند تا تحویل تضمین شود.
نکات اصلی
Device Token (توکن دستگاه) یک شناسه منحصربهفرد به شکل رشته hex است که APNS (سرویس اعلان فشاری اپل) برای هر برنامه روی دستگاه iOS تولید میکند. توکن کلیدی است که سرور از طریق آن اعلانهای فشاری را به دستگاه خاصی ارسال میکند. بدون Device Token صحیح، سرور نمیتواند اعلان فشاری را تحویل دهد — APNS درخواست را با خطای 400 BadRequest رد میکند.
Device Token توسط سیستم iOS در اولین تماس برنامه با APNS پس از نصب ایجاد میشود. فرآیند تولید شامل پیوند رمزنگاری به شناسه برنامه (bundle ID) و شناسه منحصربهفرد دستگاه (UID) است، پس از آن APNS یک توکن 32 بایتی را در قالب hex (64 کاراکتر) به برنامه برمیگرداند. توکن ثابت نیست — سیستم ممکن است در شرایط خاصی توکن جدیدی تولید کند.
وقتی سرور اعلان فشاری ارسال میکند، Device Token را در درخواست HTTP/2 به APNS قرار میدهد. APNS اعتبار توکن را بررسی میکند: اگر توکن متعلق به محیط دیگری (sandbox به جای production) باشد، منقضی شده یا لغو شده باشد، سرور اپل خطای 410 Gone یا 400 BadRequest برمیگرداند. فقط پس از تأیید اعتبار توکن، APNS تحویل اعلان به دستگاه را آغاز میکند.
Device Token را نباید با IDFA (شناسه تبلیغکنندگان)، IDFV (شناسه فروشنده) یا UID (شناسه یکتای دستگاه) اشتباه گرفت. IDFA و IDFV برای تبلیغات و تحلیل استفاده میشوند، UID شماره سریال سختافزاری است. Device Token صرفاً برای اعلانهای فشاری وجود دارد و اطلاعاتی درباره کاربر یا دستگاه خارج از APNS فاش نمیکند.
| شناسه | کاربرد | ثبات |
|---|---|---|
| Device Token | مسیریابی اعلانهای فشاری APNS | ممکن است تغییر کند |
| IDFA | تبلیغات و ردیابی | توسط کاربر بازنشانی میشود |
| IDFV | شناسایی فروشنده (تحلیل) | برای برنامههای یک توسعهدهنده ثابت است |
| Bundle ID | شناسه یکتای برنامه | ثابت |
فرآیند دریافت Device Token شامل چند مرحله اجباری است، از درخواست مجوز از کاربر تا ارسال توکن به سرور. هر مرحله حیاتی است — حذف هر یک از آنها منجر به عدم امکان ارسال اعلانهای فشاری به دستگاه میشود.
اولین قدم، برنامه از کاربر مجوز ارسال اعلانها را از طریق UNUserNotificationCenter.current().requestAuthorization درخواست میکند. کاربر میتواند موافقت کند، رد کند یا گزینههای اختیاری (alert، badge، sound) را انتخاب نماید. بدون رضایت صریح کاربر، سیستم Device Token را صادر نمیکند، حتی اگر برنامه registerForRemoteNotifications را فراخوانی کند. پس از دریافت مجوز، برنامه UIApplication.shared.registerForRemoteNotifications() را فراخوانی میکند که فرآیند ثبت در APNS را آغاز میکند.
پس از ثبت، APNS توکن را از طریق نماینده AppDelegate برمیگرداند: application(_:didRegisterForRemoteNotificationsWithDeviceToken:). فراخوانی موفق شامل یک شیء Data حاوی توکن است که باید برای ارسال به سرور به رشته hex تبدیل شود. در صورت خطا، سیستم application(_:didFailToRegisterForRemoteNotificationsWithError:) را با شرح مشکل فراخوانی میکند: تنظیم نادرست گواهیها، عدم وجود شبکه یا پیکربندی نادرست پروژه.
پس از دریافت توکن، برنامه باید بلافاصله آن را به سرور خود برای ذخیره در پایگاه داده ارسال کند. درخواست API شامل توکن، شناسه دستگاه (برای تطبیق)، محیط (sandbox/production) و به صورت اختیاری دادههای اضافی: نسخه سیستمعامل، مدل دستگاه، زبان است. توصیه میشود ارسال توکن را در هر راهاندازی برنامه تکرار کنید تا سرور همیشه توکن بهروزی داشته باشد.
// درخواست مجوز و ثبتنام در APNS
func registerForPushNotifications() {
UNUserNotificationCenter.current()
.requestAuthorization(options: [.alert, .sound, .badge]) {
[weak self] granted, error in
guard granted else {
print("مجوز دریافت نشد")
return
}
DispatchQueue.main.async {
UIApplication.shared
.registerForRemoteNotifications()
}
}
}
// دریافت Device Token از APNS
func application(
_ application: UIApplication,
didRegisterForRemoteNotificationsWithDeviceToken deviceToken: Data
) {
let tokenString = deviceToken
.map { String(format: "%02.2hhx", $0) }
.joined()
print("Device Token: \(tokenString)")
// ارسال توکن به سرور
PushTokenService.shared
.sendTokenToServer(tokenString) { success in
if success {
UserDefaults.standard.set(tokenString,
forKey: "lastDeviceToken")
}
}
}
بخش سرور سیستم اعلان فشاری باید Device Token را در پایگاه داده و مرتبط با کاربر و محیط ذخیره کند. هنگام ارسال اعلان، سرور درخواستی به APNS تشکیل میدهد که شامل توکن در URL و توکن JWT (یا گواهی) برای احراز هویت است. مدیریت صحیح توکنها به شدت بر نرخ تحویل اعلانهای فشاری تأثیر میگذارد.
جدول توکنها در سرور باید حداقل شامل موارد زیر باشد: Device Token (یکتا)، شناسه کاربر، محیط (sandbox/production)، تاریخ آخرین بهروزرسانی و وضعیت (فعال/غیرفعال). توصیه میشود ایندکس روی توکن برای جستجوی سریع هنگام ارسال و روی کاربر برای دریافت لیست تمام دستگاههای کاربر اضافه شود. بسیاری از برنامهها به یک کاربر اجازه داشتن چندین دستگاه میدهند — هر کدام با توکن خود.
برای ارسال اعلان فشاری، سرور باید درخواست را به دو روش به APNS احراز هویت کند. مبتنی بر گواهی (Certificate-based) از گواهی SSL تولید شده در Apple Developer Console استفاده میکند. روش مبتنی بر توکن (Token-based) از JWT با کلید .p8 استفاده میکند که تا ۳۰ روز بدون نیاز به بهروزرسانی گواهی معتبر است. احراز هویت مبتنی بر توکن مدرنتر محسوب میشود و اپل آن را برای پروژههای جدید توصیه میکند.
درخواست به APNS شامل متد POST HTTP/2، URL با مسیر /3/device/{device_token}، هدرهای احراز هویت و بدنه JSON با payload است. هدر apns-topic الزاماً شامل bundle ID برنامه است. apns-priority اولویت تحویل را مشخص میکند (۵ — فوری، ۱۰ — با صرفهجویی در باتری). apns-expiration زمان را بر حسب ثانیه از epoch تعیین میکند که تا آن زمان APNS تلاش خواهد کرد اعلان را تحویل دهد.
// نمونه ارسال اعلان فشاری در Node.js از طریق APNS HTTP/2
const http2 = require('http2');
const client = http2.connect('https://api.push.apple.com');
const deviceToken = 'abcdef0123456789...';
const payload = JSON.stringify({
"aps": { "alert": "Hello!", "sound": "default" }
});
const req = client.request({
':method': 'POST',
':path': `/3/device/${deviceToken}`,
'apns-topic': 'com.example.app',
'apns-priority': '10',
'apns-expiration': '0',
'authorization': `bearer ${jwtToken}`
});
req.write(payload);
req.end();
req.on('response', (headers) => {
if (headers[':status'] === '200') {
console.log('Push sent successfully');
}
});
هنگام ارسال اعلانهای فشاری به تعداد زیادی دستگاه، از ارسال دستهای با کنترل سرعت استفاده کنید. APNS توصیه میکند از ۱۵۰۰ درخواست در ثانیه در هر اتصال تجاوز نکنید. در صورت تجاوز از محدودیت، سرور اپل خطای 429 Too Many Requests برمیگرداند. برای ارسالهای مقیاس بزرگ از چندین اتصال استفاده کنید و بار را به طور یکنواخت بین دستگاهها توزیع کنید.
Device Token ثابت نیست و ممکن است در چند سناریو تغییر کند که نیاز به مکانیزم بهروزرسانی در سرور دارد. اگر سرور همچنان به ارسال اعلان به توکن قدیمی ادامه دهد، APNS خطای 410 Gone را برمیگرداند که نشان میدهد توکن دیگر برای آن محیط معتبر نیست.
اپل چند سناریو را مستند کرده است که در آنها Device Token تغییر میکند: کاربر برنامه را دوباره نصب میکند، دستگاه را از پشتیبان iCloud بازیابی میکند، نسخه جدید iOS را نصب میکند و همچنین هنگام بازنشانی تنظیمات شبکه یا حریم خصوصی. در هر مورد برنامه در راهاندازی بعدی توکن جدیدی از APNS دریافت میکند. سرور باید توکن را در پایگاه داده بهروزرسانی کند، توکن قدیمی را حذف و جدید را ذخیره نماید.
وقتی سرور اعلانی به توکن قدیمی ارسال میکند، APNS HTTP 410 را با هدر apns-unless-timestamp برمیگرداند. این هدر زمانی را نشان میدهد که پس از آن توکن نامعتبر شده است. سرور باید بلافاصله این توکن را در پایگاه داده حذف یا غیرفعال کند تا دوباره به آن ارسال نکند. نادیده گرفتن خطای 410 منجر به هدر رفتن منابع و کاهش نرخ تحویل میشود.
برای حفظ بهروز بودن پایگاه داده توکنها، توصیه میشود پاکسازی دورهای انجام شود. اسکریپت پاکسازی لاگهای APNS را برای N روز اخیر تحلیل میکند، تمام توکنهایی که خطای 410 برای آنها دریافت شده را پیدا کرده و در پایگاه داده غیرفعال میکند. همچنین میتوان توکنهایی را که بیش از ۹۰ روز فعالیت کاربر نداشتهاند حذف کرد — اینها رکوردهای بیفایدهای هستند که فقط حجم پایگاه داده را افزایش میدهند.
قبل از ارسال انبوه اعلانهای فشاری (خبرنامه، کمپین تبلیغاتی)، توصیه میشود ابتدا اعتبار توکنها را بررسی کنید. APNS API مستقیمی برای اعتبارسنجی دستهای توکنها ارائه نمیدهد، بنابراین از استراتژی ارسال اعلان آزمایشی با اولویت پایین و تحلیل خطاها استفاده میشود. توکنهایی که خطای 410 برگرداندهاند از ارسال اصلی حذف میشوند.
بیایید چرخه کامل دریافت Device Token در Swift، شامل مدیریت خطا و ارسال به سرور را بررسی کنیم. کد شامل درخواست مجوز، ثبت در APNS، تبدیل Data به رشته hex، مدیریت خطا و ارسال توکن به سرور خود با تلاش مجدد در صورت شکست است.
import UIKit
import UserNotifications
final class PushNotificationManager: NSObject {
static let shared = PushNotificationManager()
private let apiClient = APIClient()
private var currentToken: String?
func register() {
UNUserNotificationCenter.current()
.requestAuthorization(
options: [.alert, .badge, .sound]) {
[weak self] granted, error in
guard granted else {
Analytics.log(
"Push permission denied")
return
}
DispatchQueue.main.async {
UIApplication.shared
.registerForRemoteNotifications()
}
}
}
func handleDeviceToken(_ tokenData: Data) {
let token = tokenData
.map { String(format: "%02.2hhx", $0) }
.joined()
guard token != currentToken else { return }
currentToken = token
sendTokenToServer(token)
}
func handleRegistrationError(_ error: Error) {
Analytics.log(
"Push registration failed: \(error)")
// تلاش مجدد پس از تأخیر در خطاهای شبکه
if let urlError = error as? URLError,
urlError.code == .notConnectedToInternet {
DispatchQueue.main.asyncAfter(
deadline: .now() + 10) { [weak self] in
self?.register()
}
}
}
private func sendTokenToServer(_ token: String) {
let body = PushTokenRequest(
token: token,
environment: Environment.current == .debug
? "sandbox" : "production",
osVersion: UIDevice.current.systemVersion,
locale: Locale.current.identifier
)
apiClient.sendToken(body) { [weak self] result in
if case .success = result {
self?.currentToken = token
}
}
}
}
خطاهای ثبت در APNS میتوانند به دلایل مختلفی ایجاد شوند. شایعترین — عدم وجود شبکه، پیکربندی نادرست گواهیها در Xcode (مثلاً غیرفعال بودن قابلیت Push Notifications)، استفاده از شبیهساز (که از اعلان فشاری پشتیبانی نمیکند) یا پروفایل provisioning نادرست. در تولید، ثبت خطاها و در صورت امکان تکرار ثبت در راهاندازی بعدی برنامه مهم است.
شبیهساز iOS از دریافت Device Token واقعی پشتیبانی نمیکند. برای تست ثبت در شبیهساز از بررسیهای معماری i386 استفاده کنید: در نسخه debug میتوان دریافت توکن را شبیهسازی کرد یا از تستهای UI با اشیاء mock استفاده نمود. تست واقعی اعلانهای فشاری همیشه روی دستگاه فیزیکی متصل به Xcode انجام میشود.
سوالات متداول
بله، Device Token ممکن است با نصب مجدد برنامه، بازیابی دستگاه از پشتیبان یا بهروزرسانی iOS تغییر کند. سرور باید بهروزرسانی توکنها را مدیریت کند: هنگام دریافت توکن جدید از یک دستگاه شناخته شده — توکن قدیمی را جایگزین کند، هنگام خطای ۴۱۰ — توکن را از پایگاه داده حذف کند.
Device Token یک رشته hex ۳۲ بایتی از ۶۴ کاراکتر با حروف کوچک (۰–۹, a–f) است. مثال: «a1b2c3d4e5f6a1b2c3d4e5f6a1b2c3d4e5f6a1b2c3d4e5f6a1b2c3d4e5f6a1b2». توکن به صورت Data از APNS دریافت و در سمت برنامه به رشته تبدیل میشود.
توکن sandbox برای برنامههایی که با پروفایل provisioning توسعه ساخته شدهاند صادر میشود و فقط با api.sandbox.push.apple.com کار میکند. توکن production — برای App Store و TestFlight، با api.push.apple.com کار میکند. سرور باید محیطها را تشخیص داده و اعلان را به endpoint APNS مربوطه ارسال کند.
خطای 410 Gone به این معنی است که Device Token معتبر نیست. سرور باید بلافاصله این توکن را از پایگاه داده حذف کند و تلاش برای ارسال به آن را متوقف کند. هدر apns-unless-timestamp در پاسخ نشان میدهد از چه زمانی توکن از کار افتاده است.
فراخوانی نماینده application(_:didRegisterForRemoteNotificationsWithDeviceToken:) را در AppDelegate بررسی کنید. اگر متد فراخوانی شود — توکن دریافت شده است. از لاگهای debugging یا OSLog برای نمایش توکن در کنسول Xcode استفاده کنید. روی دستگاه فیزیکی بررسی کنید که توکن از طریق Network Link Conditioner به سرور ارسال میشود.
خلاصه
ما یک اپلیکیشن موبایل به صورت کلید در دست توسعه خواهیم داد
IT Sectr از سال 2017 برنامههای iOS و Android را برای استارتاپها و کسبوکارها ایجاد میکند. ما به شما مشاوره میدهیم و بهترین راهحل را پیشنهاد خواهیم کرد.
همچنین بخوانید