我如何通过编程方式获得正在运行我的android应用程序的设备的电话号码?


当前回答

如果我从voiceMailNumer得到数字,那么它工作得很好-

val telephonyManager = getSystemService(TELEPHONY_SERVICE) as TelephonyManager
    if (ActivityCompat.checkSelfPermission(this,
                    Manifest.permission.READ_PHONE_STATE) == PackageManager.PERMISSION_GRANTED
    ) {
        Log.d("number", telephonyManager.voiceMailNumber.toString())
    }

其他回答

代码:

TelephonyManager tMgr = (TelephonyManager)mAppContext.getSystemService(Context.TELEPHONY_SERVICE);
String mPhoneNumber = tMgr.getLine1Number();

需要许可:

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

警告:

根据得到高度好评的评论,有一些注意事项需要注意。这可以返回null或“”甚至“???????”,它可以返回一个过时的电话号码,不再有效。如果您想要唯一地标识设备,则应该使用getDeviceId()。

更新:这个答案不再可用,因为Whatsapp已经停止将电话号码作为帐户名,请忽略这个答案。

实际上,如果你不能通过电话服务获得它,你可以考虑另一种解决方案。

到今天为止,你可以依靠另一个大型应用程序Whatsapp,使用AccountManager。数以百万计的设备安装了这个应用程序,如果你不能通过TelephonyManager获得电话号码,你可以试试这个。

许可:

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

代码:

AccountManager am = AccountManager.get(this);
Account[] accounts = am.getAccounts();

for (Account ac : accounts) {
    String acname = ac.name;
    String actype = ac.type;
    // Take your time to look at all available accounts
    System.out.println("Accounts : " + acname + ", " + actype);
}

检查WhatsApp帐户的actype

if(actype.equals("com.whatsapp")){
    String phoneNumber = ac.name;
}

当然,如果用户没有安装WhatsApp,你可能不会得到它,但无论如何都值得一试。 记住,你应该总是询问用户的确认。

所以这就是你如何通过Play服务API请求一个电话号码,而没有许可和黑客。源代码和完整的示例。

在你的构建中。Gradle(版本10.2。X及以上要求):

compile "com.google.android.gms:play-services-auth:$gms_version"

在你的活动中(代码被简化了):

@Override
protected void onCreate(Bundle savedInstanceState) {
    // ...
    googleApiClient = new GoogleApiClient.Builder(this)
            .addApi(Auth.CREDENTIALS_API)
            .build();
    requestPhoneNumber(result -> {
        phoneET.setText(result);
    });
}

public void requestPhoneNumber(SimpleCallback<String> callback) {
    phoneNumberCallback = callback;
    HintRequest hintRequest = new HintRequest.Builder()
            .setPhoneNumberIdentifierSupported(true)
            .build();

    PendingIntent intent = Auth.CredentialsApi.getHintPickerIntent(googleApiClient, hintRequest);
    try {
        startIntentSenderForResult(intent.getIntentSender(), PHONE_NUMBER_RC, null, 0, 0, 0);
    } catch (IntentSender.SendIntentException e) {
        Logs.e(TAG, "Could not start hint picker Intent", e);
    }
}

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    super.onActivityResult(requestCode, resultCode, data);
    if (requestCode == PHONE_NUMBER_RC) {
        if (resultCode == RESULT_OK) {
            Credential cred = data.getParcelableExtra(Credential.EXTRA_KEY);
            if (phoneNumberCallback != null){
                phoneNumberCallback.onSuccess(cred.getId());
            }
        }
        phoneNumberCallback = null;
    }
}

这会生成一个这样的对话框:

我注意到有几个回复都发了同样的东西。首先,从2021年开始,onActivityResult已弃用。下面是不弃用的解决方案。

private fun requestHint() {

    val hintRequest = HintRequest.Builder()
        .setPhoneNumberIdentifierSupported(true)
        .build()

    val intent = Credentials.getClient(this).getHintPickerIntent(hintRequest)
    val intentSender = IntentSenderRequest.Builder(intent.intentSender).build()

    val resultLauncher = registerForActivityResult(
        ActivityResultContracts.StartIntentSenderForResult()
    ) { result ->
        if (result.resultCode == Activity.RESULT_OK) {
            val credential: Credential? = result.data?.getParcelableExtra(Credential.EXTRA_KEY)
            // Phone number with country code
            Log.i("mTag", "Selected phone No: ${credential?.id}")
        }
    }
    resultLauncher.launch(intentSender)
}

注意:虽然很多人认为这可以让你检索用户的手机号码。通常情况并非如此。谷歌播放服务缓存了几个电话号码,有时对话框显示电话号码,其中不属于用户。

一个重要的导入。com.google.android.gms.auth.api.credentials.Credential

参考文档提供了详细信息,但代码有些不推荐。

正如我之前回答的那样

使用以下代码:

TelephonyManager tMgr = (TelephonyManager)mAppContext.getSystemService(Context.TELEPHONY_SERVICE);
String mPhoneNumber = tMgr.getLine1Number();

在AndroidManifest.xml中,赋予以下权限:

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

但请记住,这个代码并不总是有效,因为手机号码取决于SIM卡和网络运营商/手机运营商。

另外,试着在电话->设置->关于->电话身份,如果你能在那里看到号码,从上面的代码获得电话号码的概率更高。如果您不能在设置中查看电话号码,那么您将无法通过此代码获得!

建议解决方案:

获取用户的电话号码作为用户的手动输入。 通过短信将代码发送到用户的手机号码。 请用户输入确认电话号码的代码。 保存在sharedpreference中。

在应用首次发布时一次性执行上述4个步骤。稍后,当需要电话号码时,使用共享首选项中可用的值。