Expo ships 100+ first-party native modules that let a React Native app use the camera, send push notifications, read GPS, store secrets, and more — without touching Xcode or Android Studio. But you don't need all 100. In practice a handful of modules show up in almost every app and dominate search traffic and Stack Overflow questions.
Below are the 10 most-searched Expo SDK modules, ranked by how often developers actually reach for them, each with a minimal, copy-paste example. All snippets target SDK 54+ (current stable is SDK 55, React Native 0.83). Install every module the same way:
npx expo install <package-name>
Using expo install (not npm install) picks the version that matches your SDK, which prevents most "it crashed on launch" bugs.
1. Expo Router — file-based navigation
expo-router turns your app/ folder into your navigation. A file becomes a route, a folder becomes a nested stack, and deep linking works automatically. It's the single most-searched Expo topic because every app needs navigation.
// app/_layout.tsx
import { Stack } from "expo-router"
export default function Layout() {
return <Stack />
}
// app/index.tsx
import { Link } from "expo-router"
import { Text, View } from "react-native"
export default function Home() {
return (
<View>
<Text>Home screen</Text>
<Link href="/profile">Go to profile →</Link>
</View>
)
}
app/profile.tsx is now reachable at /profile — no route config, no navigator boilerplate.
2. expo-notifications — local & push notifications
expo-notifications schedules local reminders and receives push notifications with one unified API across iOS and Android. Here's a local notification that fires after 5 seconds:
import * as Notifications from "expo-notifications"
Notifications.setNotificationHandler({
handleNotification: async () => ({
shouldShowBanner: true,
shouldShowList: true,
shouldPlaySound: true,
shouldSetBadge: false,
}),
})
await Notifications.requestPermissionsAsync()
await Notifications.scheduleNotificationAsync({
content: { title: "Don't forget 👋", body: "Your standup starts now." },
trigger: { seconds: 5 },
})
For push notifications you'd also call getExpoPushTokenAsync() and send that token to your server.
3. expo-camera — take photos & scan barcodes
The modern camera API is a single CameraView component plus a useCameraPermissions hook. It handles live preview, photo capture, and barcode scanning.
import { CameraView, useCameraPermissions } from "expo-camera"
import { Button, View } from "react-native"
export default function Scanner() {
const [permission, requestPermission] = useCameraPermissions()
if (!permission?.granted) {
return <Button title="Grant camera access" onPress={requestPermission} />
}
return <CameraView style={{ flex: 1 }} facing="back" />
}
4. expo-image-picker — pick photos & videos
expo-image-picker opens the system UI so users can choose an existing photo or shoot a new one. It's the go-to for avatars, uploads, and attachments.
import * as ImagePicker from "expo-image-picker"
async function pickImage() {
const result = await ImagePicker.launchImageLibraryAsync({
mediaTypes: ["images"],
quality: 1,
})
if (!result.canceled) {
return result.assets[0].uri // use this URI in an <Image />
}
}
5. expo-location — GPS & geolocation
Ask for permission, then read the device's current coordinates. Powers maps, "near me" features, and delivery tracking.
import * as Location from "expo-location"
async function getLocation() {
const { status } = await Location.requestForegroundPermissionsAsync()
if (status !== "granted") return
const { coords } = await Location.getCurrentPositionAsync({})
console.log(coords.latitude, coords.longitude)
}
6. expo-image — the fast image component
expo-image is a drop-in replacement for React Native's <Image> with disk caching, blurhash placeholders, and smooth transitions built in. Faster lists, less flicker.
import { Image } from "expo-image"
<Image
source="https://picsum.photos/400"
style={{ width: 200, height: 200, borderRadius: 12 }}
contentFit="cover"
transition={300}
/>
7. expo-file-system — read & write files
SDK 54 introduced a new synchronous File / Paths API that reads far more like normal file code:
import { File, Paths } from "expo-file-system"
const file = new File(Paths.document, "notes.txt")
file.create()
file.write("Hello from Expo!")
console.log(file.textSync()) // "Hello from Expo!"
Great for caching API responses, saving user-generated content, or handling downloads.
8. expo-secure-store — encrypted key/value storage
Never keep auth tokens in plain AsyncStorage. expo-secure-store encrypts small secrets using the iOS Keychain and Android Keystore.
import * as SecureStore from "expo-secure-store"
await SecureStore.setItemAsync("session_token", "abc123")
const token = await SecureStore.getItemAsync("session_token")
await SecureStore.deleteItemAsync("session_token")
This pairs naturally with auth — see our guide on adding authentication to an Expo app.
9. expo-video & expo-audio — media playback
expo-av is deprecated and removed in SDK 55. Use expo-video for video and expo-audio for sound. Both are hook-based and much simpler than the old API:
import { useVideoPlayer, VideoView } from "expo-video"
import { View } from "react-native"
export default function Player() {
const player = useVideoPlayer(
"https://commondatastorage.googleapis.com/gtv-videos-bucket/sample/BigBuckBunny.mp4",
(p) => {
p.loop = true
p.play()
}
)
return (
<View style={{ flex: 1 }}>
<VideoView style={{ width: "100%", height: 240 }} player={player} allowsFullscreen />
</View>
)
}
Playing a sound with expo-audio is just as short:
import { useAudioPlayer } from "expo-audio"
const player = useAudioPlayer(require("./assets/ping.mp3"))
player.play()
10. expo-sqlite — a real database on-device
For structured, queryable, offline data, expo-sqlite gives you a full SQLite database with an async API.
import * as SQLite from "expo-sqlite"
const db = await SQLite.openDatabaseAsync("app.db")
await db.execAsync(
`CREATE TABLE IF NOT EXISTS todos (id INTEGER PRIMARY KEY NOT NULL, text TEXT);`
)
await db.runAsync("INSERT INTO todos (text) VALUES (?)", "Ship the app")
const todos = await db.getAllAsync("SELECT * FROM todos")
console.log(todos) // [{ id: 1, text: "Ship the app" }]
Wrapping up
These ten modules cover the backbone of almost every Expo app — navigation, notifications, media, storage, and location. Learn their small, focused APIs and you can build most product features without a single line of native code.
A few habits that save time:
- Always install with
npx expo installso versions match your SDK. - Add required permissions/config plugins in
app.json(camera, notifications, and location each need one). - Prefer the modern replacements —
expo-imageover the RNImage, andexpo-video/expo-audioover the retiredexpo-av.
Want a head start instead of wiring these together yourself? Browse our production-ready Expo templates and UI components — they already integrate the modules above.