简体   繁体   English

如何在 android 中以编程方式获取设备的 IMEI/ESN?

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

To identify each devices uniquely I would like to use the IMEI (or ESN number for CDMA devices).为了唯一识别每个设备,我想使用 IMEI(或 CDMA 设备的 ESN 号)。 How to access this programmatically?如何以编程方式访问它?

You want to call android.telephony.TelephonyManager.getDeviceId() .你想调用android.telephony.TelephonyManager.getDeviceId()

This will return whatever string uniquely identifies the device (IMEI on GSM, MEID for CDMA).这将返回唯一标识设备的任何字符串(GSM 上的 IMEI,CDMA 上的 MEID)。

You'll need the following permission in your AndroidManifest.xml :您需要在AndroidManifest.xml获得以下权限:

<uses-permission android:name="android.permission.READ_PHONE_STATE" />

in order to do this.为了做到这一点。

That being said, be careful about doing this.话虽如此,做这件事要小心。 Not only will users wonder why your application is accessing their telephony stack, it might be difficult to migrate data over if the user gets a new device.用户不仅会想知道为什么您的应用程序要访问他们的电话堆栈,而且如果用户获得新设备,可能难以迁移数据。

Update: As mentioned in the comments below, this is not a secure way to authenticate users, and raises privacy concerns.更新:正如在下面的评论中提到的,这不是一种对用户进行身份验证的安全方式,并且会引起隐私问题。 It is not recommended.不推荐。 Instead, look at the Google+ Login API if you want to implement a frictionless login system.相反,如果您想实现无摩擦的登录系统,请查看Google+ 登录 API

The Android Backup API is also available if you just want a lightweight way to persist a bundle of strings for when a user resets their phone (or buys a new device).如果您只想要一种轻量级的方式来在用户重置手机(或购买新设备)时保留一组字符串,也可以使用Android Backup API

In addition to the answer of Trevor Johns, you can use this as follows:除了 Trevor Johns 的回答之外,您还可以按如下方式使用:

TelephonyManager telephonyManager = (TelephonyManager)getSystemService(Context.TELEPHONY_SERVICE);
telephonyManager.getDeviceId();

And you should add the following permission into your Manifest.xml file:您应该将以下权限添加到您的 Manifest.xml 文件中:

<uses-permission android:name="android.permission.READ_PHONE_STATE"/>

In emulator, you'll probably get a like a "00000..." value.在模拟器中,您可能会得到类似“00000...”的值。 getDeviceId() returns NULL if device ID is not available.如果设备 ID 不可用,则 getDeviceId() 返回 NULL。

I use the following code to get the IMEI or use Secure.ANDROID_ID as an alternative, when the device doesn't have phone capabilities:当设备没有电话功能时,我使用以下代码获取 IMEI 或使用 Secure.ANDROID_ID 作为替代:

/**
 * Returns the unique identifier for the device
 *
 * @return unique identifier for the device
 */
public String getDeviceIMEI() {
    String deviceUniqueIdentifier = null;
    TelephonyManager tm = (TelephonyManager) this.getSystemService(Context.TELEPHONY_SERVICE);
    if (null != tm) {
        deviceUniqueIdentifier = tm.getDeviceId();
    }
    if (null == deviceUniqueIdentifier || 0 == deviceUniqueIdentifier.length()) {
        deviceUniqueIdentifier = Settings.Secure.getString(this.getContentResolver(), Settings.Secure.ANDROID_ID);
    }
    return deviceUniqueIdentifier;
}

Or you can use the ANDROID_ID setting from Android.Provider.Settings.System (as described here strazerre.com ).或者您可以使用 Android.Provider.Settings.System 中的 ANDROID_ID 设置(如strazerre.com此处所述)。

This has the advantage that it doesn't require special permissions but can change if another application has write access and changes it (which is apparently unusual but not impossible).这样做的优点是它不需要特殊权限,但可以在另一个应用程序具有写访问权限并更改它时进行更改(这显然不寻常但并非不可能)。

Just for reference here is the code from the blog:仅供参考,这里是博客中的代码:

import android.provider.Settings;
import android.provider.Settings.System;   

String androidID = System.getString(this.getContentResolver(),Secure.ANDROID_ID);

Implementation note : if the ID is critical to the system architecture you need to be aware that in practice some of the very low end Android phones & tablets have been found reusing the same ANDROID_ID (9774d56d682e549c was the value showing up in our logs)实施注意事项如果 ID 对系统架构至关重要,您需要注意在实践中发现一些非常低端的 Android 手机和平板电脑重复使用相同的 ANDROID_ID(9774d56d682e549c 是我们日志中显示的值)

From: http://mytechead.wordpress.com/2011/08/28/how-to-get-imei-number-of-android-device/ :来自: http : //mytechead.wordpress.com/2011/08/28/how-to-get-imei-number-of-android-device/

The following code helps in obtaining IMEI number of android devices :以下代码有助于获取安卓设备的 IMEI 号码:

TelephonyManager tm = (TelephonyManager)getSystemService(Context.TELEPHONY_SERVICE);
String device_id = tm.getDeviceId();

Permissions required in Android Manifest: Android 清单中所需的权限:

android.permission.READ_PHONE_STATE

NOTE: In case of tablets or devices which can't act as Mobile Phone IMEI will be null.注意:如果是平板电脑或不能作为手机的设备,IMEI 将为空。

to get IMEI (international mobile equipment identifier)获取IMEI (国际移动设备标识符)

public String getIMEI(Activity activity) {
    TelephonyManager telephonyManager = (TelephonyManager) activity
            .getSystemService(Context.TELEPHONY_SERVICE);
    return telephonyManager.getDeviceId();
}

to get device unique id获取设备唯一ID

public String getDeviceUniqueID(Activity activity){
    String device_unique_id = Secure.getString(activity.getContentResolver(),
            Secure.ANDROID_ID);
    return device_unique_id;
}

For Android 6.0+ the game has changed so i suggest you use this;对于 Android 6.0+,游戏已经改变,所以我建议你使用它;

The best way to go is during runtime else you get permission errors.最好的方法是在运行时,否则你会遇到权限错误。

   /**
 * A loading screen after AppIntroActivity.
 */
public class LoadingActivity extends BaseActivity {
private static final int MY_PERMISSIONS_REQUEST_READ_PHONE_STATE = 0;
private TextView loading_tv2;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_loading);

    //trigger 'loadIMEI'
    loadIMEI();
    /** Fading Transition Effect */
    overridePendingTransition(android.R.anim.fade_in, android.R.anim.fade_out);
}

/**
 * Called when the 'loadIMEI' function is triggered.
 */
public void loadIMEI() {
    // Check if the READ_PHONE_STATE permission is already available.
    if (ActivityCompat.checkSelfPermission(this, Manifest.permission.READ_PHONE_STATE)
            != PackageManager.PERMISSION_GRANTED) {
        // READ_PHONE_STATE permission has not been granted.
        requestReadPhoneStatePermission();
    } else {
        // READ_PHONE_STATE permission is already been granted.
        doPermissionGrantedStuffs();
    }
}



/**
 * Requests the READ_PHONE_STATE permission.
 * If the permission has been denied previously, a dialog will prompt the user to grant the
 * permission, otherwise it is requested directly.
 */
private void requestReadPhoneStatePermission() {
    if (ActivityCompat.shouldShowRequestPermissionRationale(this,
            Manifest.permission.READ_PHONE_STATE)) {
        // Provide an additional rationale to the user if the permission was not granted
        // and the user would benefit from additional context for the use of the permission.
        // For example if the user has previously denied the permission.
        new AlertDialog.Builder(LoadingActivity.this)
                .setTitle("Permission Request")
                .setMessage(getString(R.string.permission_read_phone_state_rationale))
                .setCancelable(false)
                .setPositiveButton(android.R.string.yes, new DialogInterface.OnClickListener() {
                    public void onClick(DialogInterface dialog, int which) {
                        //re-request
                        ActivityCompat.requestPermissions(LoadingActivity.this,
                                new String[]{Manifest.permission.READ_PHONE_STATE},
                                MY_PERMISSIONS_REQUEST_READ_PHONE_STATE);
                    }
                })
                .setIcon(R.drawable.onlinlinew_warning_sign)
                .show();
    } else {
        // READ_PHONE_STATE permission has not been granted yet. Request it directly.
        ActivityCompat.requestPermissions(this, new String[]{Manifest.permission.READ_PHONE_STATE},
                MY_PERMISSIONS_REQUEST_READ_PHONE_STATE);
    }
}

/**
 * Callback received when a permissions request has been completed.
 */
@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions,
                                       @NonNull int[] grantResults) {

    if (requestCode == MY_PERMISSIONS_REQUEST_READ_PHONE_STATE) {
        // Received permission result for READ_PHONE_STATE permission.est.");
        // Check if the only required permission has been granted
        if (grantResults.length == 1 && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
            // READ_PHONE_STATE permission has been granted, proceed with displaying IMEI Number
            //alertAlert(getString(R.string.permision_available_read_phone_state));
            doPermissionGrantedStuffs();
        } else {
            alertAlert(getString(R.string.permissions_not_granted_read_phone_state));
          }
    }
}

private void alertAlert(String msg) {
    new AlertDialog.Builder(LoadingActivity.this)
            .setTitle("Permission Request")
            .setMessage(msg)
            .setCancelable(false)
            .setPositiveButton(android.R.string.yes, new DialogInterface.OnClickListener() {
                public void onClick(DialogInterface dialog, int which) {
                    // do somthing here
                }
            })
            .setIcon(R.drawable.onlinlinew_warning_sign)
            .show();
}


public void doPermissionGrantedStuffs() {
    //Have an  object of TelephonyManager
    TelephonyManager tm =(TelephonyManager)getSystemService(Context.TELEPHONY_SERVICE);
    //Get IMEI Number of Phone  //////////////// for this example i only need the IMEI
    String IMEINumber=tm.getDeviceId();

    /************************************************
     * **********************************************
     * This is just an icing on the cake
     * the following are other children of TELEPHONY_SERVICE
     *
     //Get Subscriber ID
     String subscriberID=tm.getDeviceId();

     //Get SIM Serial Number
     String SIMSerialNumber=tm.getSimSerialNumber();

     //Get Network Country ISO Code
     String networkCountryISO=tm.getNetworkCountryIso();

     //Get SIM Country ISO Code
     String SIMCountryISO=tm.getSimCountryIso();

     //Get the device software version
     String softwareVersion=tm.getDeviceSoftwareVersion()

     //Get the Voice mail number
     String voiceMailNumber=tm.getVoiceMailNumber();


     //Get the Phone Type CDMA/GSM/NONE
     int phoneType=tm.getPhoneType();

     switch (phoneType)
     {
     case (TelephonyManager.PHONE_TYPE_CDMA):
     // your code
     break;
     case (TelephonyManager.PHONE_TYPE_GSM)
     // your code
     break;
     case (TelephonyManager.PHONE_TYPE_NONE):
     // your code
     break;
     }

     //Find whether the Phone is in Roaming, returns true if in roaming
     boolean isRoaming=tm.isNetworkRoaming();
     if(isRoaming)
     phoneDetails+="\nIs In Roaming : "+"YES";
     else
     phoneDetails+="\nIs In Roaming : "+"NO";


     //Get the SIM state
     int SIMState=tm.getSimState();
     switch(SIMState)
     {
     case TelephonyManager.SIM_STATE_ABSENT :
     // your code
     break;
     case TelephonyManager.SIM_STATE_NETWORK_LOCKED :
     // your code
     break;
     case TelephonyManager.SIM_STATE_PIN_REQUIRED :
     // your code
     break;
     case TelephonyManager.SIM_STATE_PUK_REQUIRED :
     // your code
     break;
     case TelephonyManager.SIM_STATE_READY :
     // your code
     break;
     case TelephonyManager.SIM_STATE_UNKNOWN :
     // your code
     break;

     }
     */
    // Now read the desired content to a textview.
    loading_tv2 = (TextView) findViewById(R.id.loading_tv2);
    loading_tv2.setText(IMEINumber);
}
}

Hope this helps you or someone.希望这对您或某人有帮助。

New Update:新更新:

For Android Version 6 And Above, WLAN MAC Address has been deprecated , follow Trevor Johns answer对于 Android 6 及以上版本,WLAN MAC 地址已被弃用,请参考 Trevor Johns 的回答

Update:更新:

For uniquely Identification of devices, You can Use Secure.ANDROID_ID .对于设备的唯一标识,您可以使用Secure.ANDROID_ID

Old Answer:旧答案:

Disadvantages of using IMEI as Unique Device ID:使用 IMEI 作为唯一设备 ID 的缺点:

  • IMEI is dependent on the Simcard slot of the device, so it is not possible to get the IMEI for the devices that do not use Simcard. IMEI 依赖于设备的 Simcard 插槽,因此不使用 Simcard 的设备无法获取 IMEI。 In Dual sim devices, we get 2 different IMEIs for the same device as it has 2 slots for simcard.在双卡设备中,我们为同一设备获得 2 个不同的 IMEI,因为它有 2 个卡槽。

You can Use The WLAN MAC Address string (Not Recommended For Marshmallow and Marshmallow+ as WLAN MAC Address has been deprecated on Marshmallow forward. So you'll get a bogus value)您可以使用 WLAN MAC 地址字符串(不推荐用于 Marshmallow 和 Marshmallow+,因为 WLAN MAC 地址已在 Marshmallow forward 上弃用。因此您会得到一个虚假值)

We can get the Unique ID for android phones using the WLAN MAC address also.我们也可以使用 WLAN MAC 地址获取安卓手机的唯一 ID。 The MAC address is unique for all devices and it works for all kinds of devices. MAC 地址对所有设备都是唯一的,它适用于所有类型的设备。

Advantages of using WLAN MAC address as Device ID:使用 WLAN MAC 地址作为 Device ID 的优点:

  • It is unique identifier for all type of devices (smart phones and tablets).它是所有类型设备(智能手机和平板电脑)的唯一标识符。

  • It remains unique if the application is reinstalled如果重新安装应用程序,它仍然是唯一的

Disadvantages of using WLAN MAC address as Device ID:使用 WLAN MAC 地址作为 Device ID 的缺点:

  • Give You a Bogus Value from Marshmallow and above.给你一个来自棉花糖及以上的虚假价值。

  • If device doesn't have wifi hardware then you get null MAC address, but generally it is seen that most of the Android devices have wifi hardware and there are hardly few devices in the market with no wifi hardware.如果设备没有wifi硬件,那么你会得到空的MAC地址,但通常可以看到大多数Android设备都有wifi硬件,市场上几乎没有没有wifi硬件的设备。

SOURCE : technetexperts.com来源: technetexperts.com

As in API 26 getDeviceId() is depreciated so you can use following code to cater API 26 and earlier versions由于在 API 26 中getDeviceId()已折旧,因此您可以使用以下代码来满足 API 26 和更早版本

TelephonyManager telephonyManager = (TelephonyManager)getSystemService(Context.TELEPHONY_SERVICE);
String imei="";
if (android.os.Build.VERSION.SDK_INT >= 26) {
  imei=telephonyManager.getImei();
}
else
{
  imei=telephonyManager.getDeviceId();
}

Don't forget to add permission requests for READ_PHONE_STATE to use the above code.不要忘记为READ_PHONE_STATE添加权限请求以使用上述代码。

UPDATE: From Android 10 its is restricted for user apps to get non-resettable hardware identifiers like IMEI.更新:从 Android 10 开始,用户应用程序无法获取不可重置的硬件标识符(如 IMEI)。

The method getDeviceId() of TelephonyManager returns the unique device ID, for example, the IMEI for GSM and the MEID or ESN for CDMA phones. TelephonyManager 的 getDeviceId() 方法返回唯一的设备 ID,例如,GSM 的 IMEI 和 CDMA 电话的 MEID 或 ESN。 Return null if device ID is not available.如果设备 ID 不可用,则返回 null。

Java Code Java代码

package com.AndroidTelephonyManager;

import android.app.Activity;
import android.content.Context;
import android.os.Bundle;
import android.telephony.TelephonyManager;
import android.widget.TextView;

public class AndroidTelephonyManager extends Activity {
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.main);
    TextView textDeviceID = (TextView)findViewById(R.id.deviceid);

    //retrieve a reference to an instance of TelephonyManager
    TelephonyManager telephonyManager = (TelephonyManager)getSystemService(Context.TELEPHONY_SERVICE);

    textDeviceID.setText(getDeviceID(telephonyManager));

}

String getDeviceID(TelephonyManager phonyManager){

 String id = phonyManager.getDeviceId();
 if (id == null){
  id = "not available";
 }

 int phoneType = phonyManager.getPhoneType();
 switch(phoneType){
 case TelephonyManager.PHONE_TYPE_NONE:
  return "NONE: " + id;

 case TelephonyManager.PHONE_TYPE_GSM:
  return "GSM: IMEI=" + id;

 case TelephonyManager.PHONE_TYPE_CDMA:
  return "CDMA: MEID/ESN=" + id;

 /*
  *  for API Level 11 or above
  *  case TelephonyManager.PHONE_TYPE_SIP:
  *   return "SIP";
  */

 default:
  return "UNKNOWN: ID=" + id;
 }

}
}

XML XML

<linearlayout android:layout_height="fill_parent" android:layout_width="fill_parent" android:orientation="vertical" xmlns:android="http://schemas.android.com/apk/res/android">
<textview android:layout_height="wrap_content" android:layout_width="fill_parent" android:text="@string/hello">
<textview android:id="@+id/deviceid" android:layout_height="wrap_content" android:layout_width="fill_parent">
</textview></textview></linearlayout> 

Permission Required READ_PHONE_STATE in manifest file.清单文件中需要READ_PHONE_STATE权限

You can use this TelephonyManager TELEPHONY_SERVICE function to get unique device ID , Requires Permission: READ_PHONE_STATE您可以使用此 TelephonyManager TELEPHONY_SERVICE函数来获取唯一的设备 ID ,需要权限:READ_PHONE_STATE

<uses-permission android:name="android.permission.READ_PHONE_STATE" />

Example, the IMEI for GSM and the MEID or ESN for CDMA phones.例如, GSMIMEICDMA手机的MEID 或 ESN

/**
 * Gets the device unique id called IMEI. Sometimes, this returns 00000000000000000 for the
 * rooted devices.
 **/
public static String getDeviceImei(Context ctx) {
    TelephonyManager telephonyManager = (TelephonyManager) ctx.getSystemService(Context.TELEPHONY_SERVICE);
    return telephonyManager.getDeviceId();
}

Return null if device ID is not available .如果设备 ID 不可用,返回 null

Try this(need to get first IMEI always)试试这个(总是需要先获得 IMEI)

TelephonyManager mTelephony = (TelephonyManager) getSystemService(Context.TELEPHONY_SERVICE);
        if (ActivityCompat.checkSelfPermission(LoginActivity.this,Manifest.permission.READ_PHONE_STATE)!= PackageManager.PERMISSION_GRANTED) {

         return;
}

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
                if (mTelephony.getPhoneCount() == 2) {
                    IME = mTelephony.getImei(0);
                }else{
                    IME = mTelephony.getImei();
                }
            }else{
                if (mTelephony.getPhoneCount() == 2) {
                    IME = mTelephony.getDeviceId(0);
                } else {
                    IME = mTelephony.getDeviceId();
                }
            }
        } else {
            IME = mTelephony.getDeviceId();
        }

Use below code gives you IMEI number:使用以下代码为您提供 IMEI 号码:

TelephonyManager telephonyManager = (TelephonyManager) getSystemService(Context.TELEPHONY_SERVICE);
System.out.println("IMEI::" + telephonyManager.getDeviceId());

The method getDeviceId() is deprecated.不推荐使用getDeviceId()方法。 There a new method for this getImei(int)这个getImei(int)有一个新方法

Check here 在这里查看

for API Level 11 or above:对于 API 级别 11 或更高级别:

case TelephonyManager.PHONE_TYPE_SIP: 
return "SIP";

TelephonyManager tm= (TelephonyManager)getSystemService(Context.TELEPHONY_SERVICE);
textDeviceID.setText(getDeviceID(tm));

Kotlin Code for getting DeviceId ( IMEI ) with handling permission & comparability check for all android versions :用于获取 DeviceId (IMEI) 的 Kotlin 代码以及所有 android 版本的处理权限和可比性检查:

 val  telephonyManager = getSystemService(Context.TELEPHONY_SERVICE) as TelephonyManager
    if (ContextCompat.checkSelfPermission(this, Manifest.permission.READ_PHONE_STATE)
        == PackageManager.PERMISSION_GRANTED) {
        // Permission is  granted
        val imei : String? = if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O)  telephonyManager.imei
        // older OS  versions
        else  telephonyManager.deviceId

        imei?.let {
            Log.i("Log", "DeviceId=$it" )
        }

    } else {  // Permission is not granted

    }

Also add this permission to AndroidManifest.xml :还要将此权限添加到 AndroidManifest.xml :

<uses-permission android:name="android.permission.READ_PHONE_STATE"/> <!-- IMEI-->

You'll need the following permission in your AndroidManifest.xml:您需要在 AndroidManifest.xml 中获得以下权限:

<uses-permission android:name="android.permission.READ_PHONE_STATE" />

To get IMEI (international mobile equipment identifier) and if It is above API level 26 then we get telephonyManager.getImei() as null so for that, we use ANDROID_ID as a Unique Identifier.要获取IMEI (国际移动设备标识符),如果它高于 API 级别 26,那么我们将telephonyManager.getImei()获取为 null,为此,我们使用ANDROID_ID作为唯一标识符。

 public static String getIMEINumber(@NonNull final Context context)
            throws SecurityException, NullPointerException {
        TelephonyManager tm = (TelephonyManager) context.getSystemService(Context.TELEPHONY_SERVICE);
        String imei;
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
            assert tm != null;
            imei = tm.getImei();
            //this change is for Android 10 as per security concern it will not provide the imei number.
            if (imei == null) {
                imei = Settings.Secure.getString(context.getContentResolver(), Settings.Secure.ANDROID_ID);
            }
        } else {
            assert tm != null;
            if (tm.getDeviceId() != null && !tm.getDeviceId().equals("000000000000000")) {
                imei = tm.getDeviceId();
            } else {
                imei = Settings.Secure.getString(context.getContentResolver(), Settings.Secure.ANDROID_ID);
            }
        }

        return imei;
    }

use below code:使用以下代码:

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
        String[] permissions = {Manifest.permission.READ_PHONE_STATE};
        if (ActivityCompat.checkSelfPermission(this,
                Manifest.permission.READ_PHONE_STATE) != PackageManager.PERMISSION_GRANTED) {
            requestPermissions(permissions, READ_PHONE_STATE);
        }
    } else {
        try {
            TelephonyManager telephonyManager = (TelephonyManager) getSystemService(Context.TELEPHONY_SERVICE);
            if (ActivityCompat.checkSelfPermission(this, Manifest.permission.READ_PHONE_STATE) != PackageManager.PERMISSION_GRANTED) {
                return;
            }
            String imei = telephonyManager.getDeviceId();

        } catch (Exception e) {
            e.printStackTrace();
        }
    }

And call onRequestPermissionsResult method following code:并调用 onRequestPermissionsResult 方法以下代码:

@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
    switch (requestCode) {
        case READ_PHONE_STATE:
            if (grantResults.length > 0
                    && grantResults[0] == PackageManager.PERMISSION_GRANTED)
                try {
                    TelephonyManager telephonyManager = (TelephonyManager) getSystemService(Context.TELEPHONY_SERVICE);
                    if (ActivityCompat.checkSelfPermission(this, Manifest.permission.READ_PHONE_STATE) != PackageManager.PERMISSION_GRANTED) {
                        return;
                    }
                    String imei = telephonyManager.getDeviceId();

                } catch (Exception e) {
                    e.printStackTrace();
                }
    }
}

Add following permission in your AndroidManifest.xml:在您的 AndroidManifest.xml 中添加以下权限:

<uses-permission android:name="android.permission.READ_PHONE_STATE" />

There is no Way you can get imei number from andorid 10+ or 29+ mobiles here is the alternative function that will be used for creating imei number for devices.您无法从安卓 10+ 或 29+ 手机中获取 imei 号码,这里是用于为设备创建 imei 号码的替代功能。

public  static String getDeviceID(){
    String devIDShort = "35" + //we make this look like a valid IMEI
            Build.BOARD.length()%10+ Build.BRAND.length()%10 +
            Build.CPU_ABI.length()%10 + Build.DEVICE.length()%10 +
            Build.DISPLAY.length()%10 + Build.HOST.length()%10 +
            Build.ID.length()%10 + Build.MANUFACTURER.length()%10 +
            Build.MODEL.length()%10 + Build.PRODUCT.length()%10 +
            Build.TAGS.length()%10 + Build.TYPE.length()%10 +
            Build.USER.length()%10 ; //13 digits

    return  devIDShort;
}

For those looking for a Kotlin version, you can use something like this;对于那些寻找 Kotlin 版本的人,你可以使用这样的东西;

private fun telephonyService() {
    val telephonyManager = getSystemService(TELEPHONY_SERVICE) as TelephonyManager
    val imei = if (android.os.Build.VERSION.SDK_INT >= 26) {
        Timber.i("Phone >= 26 IMEI")
        telephonyManager.imei
    } else {
        Timber.i("Phone IMEI < 26")
        telephonyManager.deviceId
    }

    Timber.i("Phone IMEI $imei")
}

NOTE: You must wrap telephonyService() above with a permission check using checkSelfPermission or whatever method you use.注意:您必须使用checkSelfPermission或您使用的任何方法通过权限检查将上面的telephonyService()包装起来。

Also add this permission in the manifest file;还要在清单文件中添加此权限;

<uses-permission android:name="android.permission.READ_PHONE_STATE"/>

For Android 10 Following code is working for me.对于 Android 10 以下代码对我有用。

val uid: String = Settings.Secure.getString(ctx.applicationContext.contentResolver, Settings.Secure.ANDROID_ID)
if (ContextCompat.checkSelfPermission(ctx, Manifest.permission.READ_PHONE_STATE) == PackageManager.PERMISSION_GRANTED) {
            imei = when {
                Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q -> {
                    uid
                }
                Build.VERSION.SDK_INT >= Build.VERSION_CODES.O -> {
                    telephonyManager.imei
                }
                else -> {
                    telephonyManager.deviceId
                }
            }
        }

Restriction on non-resettable device identifiers对不可重置设备标识符的限制

Starting in Android 10, apps must have the READ_PRIVILEGED_PHONE_STATE privileged permission in order to access the device's non-resettable identifiers, which include both IMEI and serial number.从 Android 10 开始,应用必须具有READ_PRIVILEGED_PHONE_STATE特权才能访问设备的不可重置标识符,包括 IMEI 和序列号。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM