การขอสิทธิ์และรับโทเค็นพุช
ใช้ expo-notifications เพื่อขอสิทธิ์การแจ้งเตือน รับโทเค็นพุชของ Expo และส่งโทเค็นไปยังเซิร์ฟเวอร์แบ็กเอนด์เพื่อจัดเก็บ
การขอสิทธิ์และรับโทเค็นพุช เป็นบทเรียน React Native Academy ฟรีบน CoddyKit นี่คือบทเรียนที่ 1 จากทั้งหมด 4 บทเรียน คุณสามารถอ่านบทเรียนทั้งหมดด้านล่างฟรี — จากนั้นลองปฏิบัติด้วยตัวคุณเองในเบราว์เซอร์พร้อมตัวแก้ไขโค้ดในตัวและติวเตอร์ AI ตลอด 24/7 บทเรียนนี้เป็นส่วนหนึ่งของเส้นทางการเรียน React Native Academy และความก้าวหน้าของคุณจะซิงค์ข้ามเว็บและแอป CoddyKit คอร์ส React Native Academy มีบทเรียนทั้งหมด 4 บทเรียน
บางส่วนของบทเรียนนี้ยังไม่ได้รับการแปล และแสดงเป็นภาษาอังกฤษ
What Are Push Notifications?
Push notifications are messages sent from your server to a user's device even when the app is closed. They appear in the device's notification center, show on the lock screen, and can trigger a badge count on the app icon. On mobile they are one of the most powerful re-engagement tools available.
The flow for push notifications involves three parties: your app (registers the device), your server (decides when to send), and a push gateway (Apple APNs for iOS, Google FCM for Android). Expo wraps both gateways with a unified push service.
Installing expo-notifications
The expo-notifications package provides a unified API for push notifications on both iOS and Android. Install it with the Expo CLI, which handles installing the correct native version for your Expo SDK.
Push notifications require a development build (not Expo Go) because they need APNs entitlements embedded in the iOS app binary. Android push works in Expo Go but iOS does not. For production, EAS Build handles the certificate configuration automatically.
// Install:
// npx expo install expo-notifications
// In app.json, configure notification appearance:
{
'expo': {
'notification': {
'icon': './assets/notification-icon.png',
'color': '#ffffff',
'androidMode': 'default',
'androidCollapsedTitle': '#{unread_notifications} new updates'
}
}
}Requesting Notification Permission
Before sending or receiving notifications, you must request permission from the user. On iOS this shows the system permission dialog the first time. On Android 13+ (API 33+) you must also explicitly request permission; on older Android versions it's granted automatically.
Use Notifications.requestPermissionsAsync() and check the returned status. The status is 'granted', 'denied', or 'undetermined'. If denied, the user must manually re-enable in Settings — you cannot show the dialog again.
import * as Notifications from 'expo-notifications';
async function requestPushPermission() {
const { status: existingStatus } = await Notifications.getPermissionsAsync();
let finalStatus = existingStatus;
if (existingStatus !== 'granted') {
const { status } = await Notifications.requestPermissionsAsync();
finalStatus = status;
}
if (finalStatus !== 'granted') {
console.log('Push permission denied');
return false;
}
return true;
}Getting the Expo Push Token
An Expo Push Token is a unique identifier for the app+device+user combination. It looks like ExponentPushToken[xxxxxxxxxxxxxxxxxxxxxx]. You pass this token to your server so it can send notifications to this specific device later.
Use Notifications.getExpoPushTokenAsync() to retrieve the token. This must be called after permission is granted. For production (non-Expo) builds you also need to provide the projectId from your Expo project.
import * as Notifications from 'expo-notifications';
import Constants from 'expo-constants';
async function getExpoPushToken() {
const token = await Notifications.getExpoPushTokenAsync({
projectId: Constants.expoConfig.extra.eas.projectId,
});
console.log('Push token:', token.data);
// 'ExponentPushToken[AbCdEfGhIjKl...]'
return token.data;
}Storing the Token on Your Server
The push token is only useful if your server has it. After retrieving the token, send it to your backend via an API call and store it associated with the user account. A user might use multiple devices — store one token per device per user.
Tokens can change — when a user reinstalls the app or resets their device. Build your server to handle token updates: either overwrite the old token for the same user, or store multiple tokens per user and handle invalid token responses from the push gateway by removing stale tokens.
async function registerForPushNotifications(userId) {
const hasPermission = await requestPushPermission();
if (!hasPermission) return;
const token = await getExpoPushToken();
// Send to your backend:
await fetch('https://api.myapp.com/users/' + userId + '/push-token', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ token }),
});
}Calling Registration at the Right Time
Call the registration function at an appropriate moment in the user journey — typically right after the user logs in or completes onboarding. Requesting push permission too early (on app first launch) before the user understands the app's value reduces acceptance rates.
Use a useEffect in your authenticated root component to trigger registration once when the user is authenticated. Persist the registration status in AsyncStorage to avoid requesting permission on every launch.
import { useEffect } from 'react';
import AsyncStorage from '@react-native-async-storage/async-storage';
function usePostLoginPushRegistration(userId) {
useEffect(() => {
if (!userId) return;
AsyncStorage.getItem('pushRegistered').then((registered) => {
if (!registered) {
registerForPushNotifications(userId).then(() => {
AsyncStorage.setItem('pushRegistered', 'true');
});
}
});
}, [userId]);
}Android-Specific: Notification Channels
Android 8+ requires notification channels — logical groupings that give users fine-grained control over which types of notifications they receive. Create channels with Notifications.setNotificationChannelAsync() before sending any notifications. On iOS this is not needed.
Use descriptive channel IDs and names that mean something to users in the Settings notification page. For example, messages, promotions, and system. Assign appropriate importance levels — HIGH for urgent notifications, DEFAULT for standard ones.
import * as Notifications from 'expo-notifications';
import { Platform } from 'react-native';
async function setupNotificationChannels() {
if (Platform.OS === 'android') {
await Notifications.setNotificationChannelAsync('messages', {
name: 'Messages',
importance: Notifications.AndroidImportance.HIGH,
vibrationPattern: [0, 250, 250, 250],
lightColor: '#FF231F7C',
});
await Notifications.setNotificationChannelAsync('promotions', {
name: 'Promotions',
importance: Notifications.AndroidImportance.DEFAULT,
});
}
}Configuring Notification Presentation
By default, expo-notifications does not show notifications when the app is in the foreground. Configure the default notification handler with Notifications.setNotificationHandler to control this behavior. Set at the top level of your app, before any components mount.
The handler function receives each notification and returns a config object specifying whether to play a sound, show an alert, and set the badge count. Set up this handler once in your app entry file (App.js or index.js).
import * as Notifications from 'expo-notifications';
// At app root level (outside components):
Notifications.setNotificationHandler({
handleNotification: async () => ({
shouldShowAlert: true,
shouldPlaySound: true,
shouldSetBadge: true,
}),
});
export default function App() {
return <NavigationContainer>...</NavigationContainer>;
}Getting a Native Device Token
For production apps not using Expo's push service (e.g., integrating directly with APNs or FCM), use Notifications.getDevicePushTokenAsync() instead of the Expo push token. This returns the raw APNs or FCM device token that you can pass directly to those services.
The native token is a hexadecimal string (iOS) or registration token (Android). Handle both cases on your server. When using native tokens you must also handle the certificate/key setup for APNs and the google-services.json for FCM separately.
// For direct APNs/FCM integration (not Expo push service):
const nativeToken = await Notifications.getDevicePushTokenAsync();
console.log('Native token type:', nativeToken.type); // 'ios' or 'android'
console.log('Native token data:', nativeToken.data); // raw APNs/FCM token
// Send to your server for direct gateway integration:Handling Token Refresh
Push tokens can be invalidated and refreshed by the OS — for example when the user restores from a backup, reinstalls the app, or resets their device. Listen for token changes with Notifications.addPushTokenListener and update your server with the new token when this fires.
A robust push notification system always handles token refresh. Unregistered tokens cause silent delivery failures on your server. Clean up stale tokens from your database when the push gateway returns a DeviceNotRegistered error.
useEffect(() => {
const tokenSubscription = Notifications.addPushTokenListener(
async ({ data: newToken }) => {
console.log('Push token refreshed:', newToken);
// Update server with new token
await fetch('/api/push-token/refresh', {
method: 'PUT',
body: JSON.stringify({ token: newToken }),
});
}
);
return () => tokenSubscription.remove();
}, []);Privacy and Best Practices
Push token management best practices:
- Never log tokens in production — they are credentials that identify specific devices.
- Encrypt tokens at rest on your server — a leaked token database can enable notification spam.
- Associate tokens with users — delete tokens when users delete their account or opt out of notifications.
- Batch token updates — don't call the server on every app launch, only when the token changes or at first registration.
- Respect user preferences — provide in-app notification settings and honor them on your server.
Quick Check
Test your understanding of React Native Mobile Development concepts from this lesson.
Lesson Recap
In this lesson you learned: Notifications.requestPermissionsAsync() requests OS permission and must be granted before getting a push token, Notifications.getExpoPushTokenAsync() returns a token like ExponentPushToken[...] that identifies the device to your backend, and tokens must be stored on your server and updated when they change to maintain reliable delivery. Next up we send push notifications to devices using the Expo Push API from a server.
คำถามที่พบบ่อย
บทเรียน “การขอสิทธิ์และรับโทเค็นพุช” ฟรีหรือไม่
ใช่ — ข้อความเต็มของ “การขอสิทธิ์และรับโทเค็นพุช” ฟรีให้อ่านที่นี่บนเว็บ เพื่อปฏิบัติแบบโต้ตอบ (ตัวแก้ไขโค้ดในตัวและติวเตอร์ AI ตลอด 24/7) และปลดล็อคส่วนที่เหลือของคอร์ส React Native Academy ให้อัปเกรดเป็น CoddyKit PRO คอร์ส React Native Academy มีบทเรียนทั้งหมด 4 บทเรียน
คุณจะเรียนรู้อะไรในบทเรียน “การขอสิทธิ์และรับโทเค็นพุช”
ใช้ expo-notifications เพื่อขอสิทธิ์การแจ้งเตือน รับโทเค็นพุชของ Expo และส่งโทเค็นไปยังเซิร์ฟเวอร์แบ็กเอนด์เพื่อจัดเก็บ คุณปฏิบัติ React Native Academy ด้วยโค้ดที่ใช้งานได้จริงที่คุณเรียกใช้โดยตรงในเบราว์เซอร์ และติวเตอร์ AI ตลอด 24/7 ตอบคำถามของคุณขณะที่คุณไปผ่านบทเรียน
คุณต้องมีประสบการณ์ก่อนที่จะเริ่มเรียน React Native Academy หรือไม่
ไม่จำเป็นต้องมีประสบการณ์มาก่อน React Native Academy บน CoddyKit ออกแบบมาสำหรับผู้เริ่มต้นไปจนถึงผู้เรียนขั้นสูง คุณสามารถเริ่มต้นที่นี่หรือเริ่มจากตัวแรกและเรียนด้วยความเร็วของคุณเอง นี่คือบทเรียนที่ 1 จากทั้งหมด 4 บทเรียน
บทเรียน “การขอสิทธิ์และรับโทเค็นพุช” ใช้เวลานานแค่ไหน
บทเรียน CoddyKit ส่วนใหญ่ใช้เวลาประมาณ 5–10 นาที แต่ละบทเรียนจึงสั้นและเป็นแบบโต้ตอบ คุณสามารถก้าวหน้าอย่างต่อเนื่องและกลับมาเรียนต่อจากตรงที่เพิ่งหยุดบนเว็บและแอปได้เลย
ฉันเขียนและรันโค้ดในบทเรียน React Native Academy นี้ได้ไหม
ได้ บทเรียน React Native Academy ทุกบทมีตัวแก้ไขโค้ดในตัว คุณจึงเขียนและรันโค้ดจริงได้เลยในเบราว์เซอร์ และได้รับข้อเสนอแนะจาก AI ในทันที — ไม่ต้องติดตั้งในเครื่องของคุณ
บทเรียนทั้งหมดในหลักสูตรนี้
- การขอสิทธิ์และรับโทเค็นพุช
- การส่งการแจ้งเตือนผ่าน Expo Push API
- การจัดการการแจ้งเตือนขณะอยู่เบื้องหน้าและเบื้องหลัง
- ช่องการแจ้งเตือนและเนื้อหาแบบหลากหลาย