Test the devices your users actually hold
You cannot cover every phone and every OS version, and you do not have to. Build a coverage matrix from your own audience, run most of it on virtual devices in seconds, and keep real hardware for what only it can answer.
Virtual for breadth · real devices for the verdict
You can't test every phone. You don't need to.
Every model times every OS version is thousands of combinations. Owning one of each is a budget, not a plan — and most of them never load your app. The combinations that matter are the ones your own users are already on.
Cover the cells that cover your users
Read the models and OS versions in your own analytics, mark the handful that reach most of your audience, and test those. A short list you actually run beats a long list you never get to.
- Android 16
Galaxy S25
Samsung
- Android 15
Pixel 9
Google
- iOS 18
iPhone 15 Pro
Apple
- Android 14
Galaxy A54
Samsung
Run them in parallel. Add real hardware for the ones that need it.
How to size your matrix
Rank every device and OS combination by how many of your users actually hit it. A short head covers most of them; the long tail is where you choose your battles.
- 1
Start from analytics
The models and OS versions your users actually load, not a wishlist.
- 2
Cover the top of the curve
A handful of combinations usually reaches most of your audience.
- 3
Add the risky edges
The oldest OS you support, the smallest screen, one low-end device.
- 4
Re-read it each release
The curve moves every quarter. Refresh the matrix instead of re-buying hardware.
Run most of the matrix virtually. Confirm the rest on hardware.
An Android emulator runs the same Chrome and the same Android a phone runs; an iOS simulator runs real WebKit. Layout, engine and logic are genuine there — so you cover breadth in seconds and keep real devices for what only they can answer.
Virtual, for breadth
Layout, CSS, JavaScript, browser engine, and building automated suites.
Hardware, for the verdict
Camera and sensors, gesture feel, real performance, and every release sign-off.
Which environment for which job
A layout change across screen sizes
Virtual — a breakpoint does not depend on silicon.
A cross-browser web regression
Virtual first — the engine is real in both places.
Writing and debugging an automated suite
Virtual — a failed run costs seconds, not a queued handset.
Camera, microphone or sensor flows
Real device — a synthetic camera only proves the permission dialog.
Gesture feel and animation smoothness
Real device — touch and GPU are the phone's, not the host's.
Release sign-off
Real device — the last pass should run where customers do.
Frequently asked questions
There is no fixed number — build the list from your own analytics rather than a target. In practice a handful of your top device and OS-version combinations usually reaches most of your sessions, and you add the oldest OS you still support, one small screen and one low-end device for the risky edges. Then re-read it each release, because the mix shifts.
It is unreliable for questions that depend on physical hardware — camera, sensors, radio, battery, gesture feel and real performance. It is entirely reliable for layout, CSS, JavaScript, browser engine behaviour and application logic, because those parts are real: an Android emulator runs the same Chrome build and the same Android OS that a phone runs. The mistake is not using an emulator; it is using one to answer a question it cannot see. 'Always unreliable' is a sales position, not a technical one.
No. An emulator imitates the device hardware and runs the real operating system on top of it, which is why an Android emulator can install and run an APK. A simulator reimplements the operating system as a program that runs natively on the host machine, which is why an iOS simulator is fast, renders real WebKit, and cannot run an .ipa built for an iPhone's processor.
Not here, and not anywhere that offers simulators honestly. An .ipa is compiled for an iPhone's processor and will not run on a simulator, which executes native macOS code. Simulator sessions are Safari and mobile web only. Testing an iOS app means testing on a real iPhone or iPad.
Android emulator sessions report the same capability surface as the matching real Android session — the same control rail, the same screenshots, recording, visual comparison, logs and bug reporting. iOS simulator sessions differ in three specific ways: no app install, no audio, and no VPN routing. Timezone can be changed on a simulator; language cannot.
Anything physical. Camera, microphone, sensors, cellular radio, battery and thermal behaviour are synthetic or absent on both platforms. Touch is a mouse, so gesture and scroll feel is not something to trust a virtual session about. And performance numbers describe the host machine the session ran on, not the phone you ship to.
Usually both, at different points. Building and debugging a suite against virtual devices is cheaper and faster, and most failures during that phase are your own selectors rather than the platform. Running the suite against real devices before release is where hardware-specific failures surface. Splitting it this way costs less than doing everything on hardware and finds more than doing everything virtually.
An iOS simulator session. It runs a real WebKit build, so layout and engine behaviour are genuine, and it does not require owning a Mac or an iPhone. What it will not tell you is how the page feels under a finger, how it behaves on a cellular connection, or anything involving the camera or sensors — for those, open a session on a real iPhone.
Build your matrix and open the first cell
Pick the device and OS-version combinations your users are on, and open one — an emulator, a simulator or a real phone — from the same picker, with the same toolbar.