Android
IMEI
ESN
Programmatically
AndroidDevelopment

How to get the device's IMEI/ESN programmatically in android?

Interview Questions practice on Codemia

Over 8,000 real interview questions from top companies, searchable by company and role.

Browse interview questions

Introduction

Reading a device IMEI or ESN used to be a common Android pattern, but it is no longer a safe default for application design. Modern Android treats hardware identifiers as sensitive data, so the practical answer is not just about code syntax; it is about whether your app is even allowed to access that identifier.

Know What You Are Asking For

IMEI is a cellular hardware identifier, and ESN is an older identifier associated with legacy mobile networks. Both are much more sensitive than an app-scoped ID because they are stable outside your application and can be used for long-term tracking.

That is why many old examples on the internet are misleading today. They show an API call, but not the platform and policy restrictions around it.

Historically, developers used TelephonyManager.

kotlin
val telephonyManager = getSystemService(TELEPHONY_SERVICE) as TelephonyManager
val maybeImei = telephonyManager.imei
println(maybeImei)

That code demonstrates the API shape, but it does not guarantee that an ordinary third-party app can successfully use it in production.

Why the Old Approach Fails in Real Apps

There are three separate questions here:

  • does the SDK expose a method
  • does the app have the required permission
  • is the app allowed by the platform role and device policy to read the value

Even if the method exists, the result may be unavailable, restricted, or inappropriate for your use case. Many teams only discover this after they have already built a backend that depends on a hardware ID.

For most app flows, that is the wrong dependency. If what you really need is an installation ID, account ID, or device registration ID inside your own system, IMEI is unnecessary.

Prefer a Safer Identifier

For many applications, ANDROID_ID is a better fit. It is still an identifier, but it is intended for app-level usage patterns rather than telecom hardware tracking.

kotlin
1import android.provider.Settings
2
3val androidId = Settings.Secure.getString(
4    contentResolver,
5    Settings.Secure.ANDROID_ID
6)
7println(androidId)

That is usually sufficient for linking a local installation to a server record, correlating device state, or storing app preferences keyed to one install base.

If even that is more persistence than you need, generate your own ID and store it.

kotlin
1import java.util.UUID
2
3val localAppId = UUID.randomUUID().toString()
4println(localAppId)

Persist that value in local storage and treat it as your app's private device token.

Choose the Identifier Based on the Requirement

A lot of confusion comes from mixing up different identity problems.

If you need:

  • user identity, use an account or login ID
  • app installation identity, use a generated UUID or app-managed token
  • device enrollment identity inside a controlled enterprise environment, use the mechanism allowed by that management model

That framing is more important than memorizing one Android API. It prevents you from designing a system around a value that your app should not rely on.

Enterprise and Special-Privilege Cases

There are cases where device identifiers can still matter, especially in tightly managed enterprise deployments, carrier software, or privileged system contexts. Those are not ordinary consumer-app assumptions.

If your app runs in a managed environment, the device owner model and distribution method matter as much as the code. In other words, the question stops being purely an Android programming question and becomes a device-management question.

That is another reason to avoid building general-purpose app logic around IMEI unless you know you control the environment.

ESN Is Usually a Legacy Concern

Many older questions mention ESN alongside IMEI, but ESN is usually not the identifier a new Android application should target. In contemporary app development, the more realistic decision is whether you need any telecom hardware identifier at all.

In most cases, the answer is no.

Common Pitfalls

The most common mistake is copying an old getDeviceId() or imei snippet and assuming it will work across current Android devices and app distribution models.

Another mistake is choosing IMEI because it sounds stable. Stability is exactly why the platform treats it as sensitive.

A third problem is designing the server schema around a hardware identifier before validating platform restrictions. That turns a local coding assumption into a system-wide migration problem later.

Finally, many apps ask for IMEI when they only need a way to recognize one installation of the app. A generated app-specific ID is usually a better design.

Summary

  • IMEI and ESN are sensitive hardware identifiers, not general-purpose app IDs.
  • Older TelephonyManager examples do not reflect current platform reality for ordinary apps.
  • Prefer ANDROID_ID, a server-issued token, or an app-generated UUID for most use cases.
  • Design the identifier strategy around the real requirement: user, install, or managed device.
  • Enterprise and privileged-device scenarios are different from normal Play-style app development.
  • If your app architecture depends on IMEI, challenge that assumption before you write more code.

Related reading
Free course
Beginner
7 lessons
2 hours
Tackling System Design Interview Problems

A short course that equips you with the skills to approach system design interviews methodically.

Start the free course
Track what you have practised

A free account saves your progress, solutions and study plan across every problem on Codemia.

Interview Questions practice on Codemia

Over 8,000 real interview questions from top companies, searchable by company and role.

Browse interview questions

All Rights Reserved.