¿Cómo puedo obtener programáticamente el número de teléfono del dispositivo que ejecuta mi aplicación de Android?
¿Cómo puedo obtener programáticamente el número de teléfono del dispositivo que ejecuta mi aplicación de Android?
Respuestas:
Código:
TelephonyManager tMgr = (TelephonyManager)mAppContext.getSystemService(Context.TELEPHONY_SERVICE);
String mPhoneNumber = tMgr.getLine1Number();
Permiso requerido:
<uses-permission android:name="android.permission.READ_PHONE_STATE"/>
De acuerdo con los comentarios altamente votados, hay algunas advertencias a tener en cuenta. Esto puede devolver null
o ""
incluso "???????"
, y puede devolver un número de teléfono obsoleto que ya no es válido. Si desea algo que identifique de forma exclusiva el dispositivo, debe usarlo getDeviceId()
en su lugar.
null
. Dicho esto, no estoy al tanto de una mejor respuesta.
No hay una solución garantizada para este problema porque el número de teléfono no se almacena físicamente en todas las tarjetas SIM, ni se transmite desde la red al teléfono. Esto es especialmente cierto en algunos países que requieren la verificación de la dirección física, con la asignación de números solo después. La asignación del número de teléfono ocurre en la red, y se puede cambiar sin cambiar la tarjeta SIM o el dispositivo (por ejemplo, así es como se admite la transferencia).
Sé que es doloroso, pero lo más probable es que la mejor solución sea pedirle al usuario que ingrese su número de teléfono una vez y lo almacene.
En realidad, es posible que desee considerar una solución alternativa si no puede obtenerla a través del servicio de telefonía.
A partir de hoy, puede confiar en otra gran aplicación Whatsapp, utilizando AccountManager
. Millones de dispositivos tienen instalada esta aplicación y, si no puede obtener el número de teléfono, puede intentarlo TelephonyManager
.
Permiso:
<uses-permission android:name="android.permission.GET_ACCOUNTS" />
Código:
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);
}
Verifique la actype
cuenta de WhatsApp
if(actype.equals("com.whatsapp")){
String phoneNumber = ac.name;
}
Por supuesto, es posible que no lo obtenga si el usuario no instaló WhatsApp, pero vale la pena intentarlo de todos modos. Y recuerde que siempre debe pedirle confirmación al usuario.
Como publicado en mi respuesta anterior
Use el siguiente código:
TelephonyManager tMgr = (TelephonyManager)mAppContext.getSystemService(Context.TELEPHONY_SERVICE);
String mPhoneNumber = tMgr.getLine1Number();
En AndroidManifest.xml, otorgue el siguiente permiso:
<uses-permission android:name="android.permission.READ_PHONE_STATE"/>
Pero recuerde, este código no siempre funciona, ya que el número de teléfono celular depende de la tarjeta SIM y del operador de red / operador de telefonía celular.
Además, intente verificar en Teléfono -> Configuración -> Acerca de -> Identidad del teléfono , si puede ver el Número allí, la probabilidad de obtener el número de teléfono del código anterior es mayor. Si no puede ver el número de teléfono en la configuración, ¡no podrá obtenerlo a través de este código!
Solución sugerida:
Realice los 4 pasos anteriores como actividad única durante el primer inicio de la aplicación. Más adelante, cuando se requiera un número de teléfono, use el valor disponible en preferencia compartida.
Así es como solicitas un número de teléfono a través de la API de Play Services sin el permiso y los hacks. Fuente y ejemplo completo .
En su build.gradle (se requiere la versión 10.2.xy superior):
compile "com.google.android.gms:play-services-auth:$gms_version"
En su actividad (el código está simplificado):
@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;
}
}
Esto generará un diálogo como este:
private String getMyPhoneNumber(){
TelephonyManager mTelephonyMgr;
mTelephonyMgr = (TelephonyManager)
getSystemService(Context.TELEPHONY_SERVICE);
return mTelephonyMgr.getLine1Number();
}
private String getMy10DigitPhoneNumber(){
String s = getMyPhoneNumber();
return s != null && s.length() > 2 ? s.substring(2) : null;
}
Código tomado de http://www.androidsnippets.com/get-my-phone-number
Hay una nueva API de Android que permite al usuario seleccionar su número de teléfono sin la necesidad de un permiso. Echa un vistazo a: https://android-developers.googleblog.com/2017/10/effective-phone-number-verification.html
// Construct a request for phone numbers and show the picker
private void requestHint() {
HintRequest hintRequest = new HintRequest.Builder()
.setPhoneNumberIdentifierSupported(true)
.build();
PendingIntent intent = Auth.CredentialsApi.getHintPickerIntent(
apiClient, hintRequest);
startIntentSenderForResult(intent.getIntentSender(),
RESOLVE_HINT, null, 0, 0, 0);
}
Solo quiero agregar un poco aquí a las explicaciones anteriores en las respuestas anteriores. Lo que también ahorrará tiempo para los demás.
En mi caso, este método no devolvió ningún número de móvil, se devolvió una cadena vacía. Fue debido al caso de que había portado mi número en el nuevo sim. Entonces, si entro en Configuración> Acerca del teléfono> Estado> Mi número de teléfono, me muestra "Desconocido".
A veces, debajo del código devuelve null
o cadena en blanco.
TelephonyManager tMgr = (TelephonyManager)mAppContext.getSystemService(Context.TELEPHONY_SERVICE);
String mPhoneNumber = tMgr.getLine1Number();
Con el siguiente permiso
<uses-permission android:name="android.permission.READ_PHONE_STATE"/>
Hay otra manera de que pueda obtener su número de teléfono, no lo he probado en varios dispositivos, pero el código anterior no funciona todo el tiempo.
Pruebe el siguiente código:
String main_data[] = {"data1", "is_primary", "data3", "data2", "data1", "is_primary", "photo_uri", "mimetype"};
Object object = getContentResolver().query(Uri.withAppendedPath(android.provider.ContactsContract.Profile.CONTENT_URI, "data"),
main_data, "mimetype=?",
new String[]{"vnd.android.cursor.item/phone_v2"},
"is_primary DESC");
if (object != null) {
do {
if (!((Cursor) (object)).moveToNext())
break;
// This is the phoneNumber
String s1 = ((Cursor) (object)).getString(4);
} while (true);
((Cursor) (object)).close();
}
Deberá agregar estos dos permisos.
<uses-permission android:name="android.permission.READ_CONTACTS" />
<uses-permission android:name="android.permission.READ_PROFILE" />
Espero que esto ayude, ¡Gracias!
String s1
será el número de teléfono.
En primer lugar, obtener el número de teléfono móvil de los usuarios va en contra de la política ética, antes era posible, pero ahora, según mi investigación, no hay una solución sólida disponible para esto. Al usar algún código, es posible obtener el número de teléfono móvil, pero no hay garantía de que funcione. solo en pocos dispositivos. Después de mucha investigación, encontré solo tres soluciones, pero no funcionan en todos los dispositivos.
Hay la siguiente razón por la que no estamos recibiendo.
1.El dispositivo Android y la nueva tarjeta Sim no almacenan el número de teléfono móvil si el número de teléfono móvil no está disponible en el dispositivo y en la tarjeta SIM, entonces, ¿cómo es posible obtener el número? sabio devolverá el "nulo" o "" o "??????"
<uses-permission android:name="android.permission.READ_PHONE_STATE"/>
TelephonyManager tel= (TelephonyManager)this.getSystemService(Context.
TELEPHONY_SERVICE);
String PhoneNumber = tel.getLine1Number();
Nota: He probado esta solución en el siguiente dispositivo Moto x, Samsung Tab 4, Samsung S4, Nexus 5 y Redmi 2 prime, pero no funciona cada vez que devuelve una cadena vacía, por lo que la conclusión es inútil.
Nota: - Esta tampoco es la solución garantizada y eficiente, he probado esta solución en muchos dispositivos, pero funcionó solo en Redmi 2 prime, que es un dispositivo dual sim, me da dos números móviles, el primero es correcto pero el segundo no. pertenece a mi segundo sim, pertenece a mi antigua tarjeta sim que no estoy usando.
String main_data[] = {"data1", "is_primary", "data3", "data2", "data1",
"is_primary", "photo_uri", "mimetype"};
Object object = getContentResolver().
query(Uri.withAppendedPath(android.provider.ContactsContract.Profile.CONTENT_URI, "data"),
main_data, "mimetype=?",
new String[]{"vnd.android.cursor.item/phone_v2"},
"is_primary DESC");
String s1="";
if (object != null) {
do {
if (!((Cursor) (object)).moveToNext())
break;
// This is the phoneNumber
s1 =s1+"---"+ ((Cursor) (object)).getString(4);
} while (true);
((Cursor) (object)).close();
}
Conclusión : - Android no tiene ninguna solución garantizada para obtener el número de teléfono móvil del usuario mediante programación.
Sugerencia : - 1. Si desea verificar el número de teléfono móvil del usuario, solicite al usuario que proporcione su número, utilizando otp puede verificarlo.
- Si desea identificar el dispositivo del usuario, para esto puede obtener fácilmente el número IMEI del dispositivo.
TelephonyManager
no es la solución correcta, porque en algunos casos el número no se almacena en la SIM. Le sugiero que use la preferencia compartida para almacenar el número de teléfono del usuario por primera vez que la aplicación esté abierta y el número se usará cuando lo necesite.
Aquí hay una combinación de las soluciones que he encontrado (proyecto de muestra aquí , si desea verificar también el autocompletado):
manifiesto
<uses-permission android:name="android.permission.READ_PHONE_STATE" />
build.gradle
implementation "com.google.android.gms:play-services-auth:17.0.0"
MainActivity.kt
class MainActivity : AppCompatActivity() {
private lateinit var googleApiClient: GoogleApiClient
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
tryGetCurrentUserPhoneNumber(this)
googleApiClient = GoogleApiClient.Builder(this).addApi(Auth.CREDENTIALS_API).build()
if (phoneNumber.isEmpty()) {
val hintRequest = HintRequest.Builder().setPhoneNumberIdentifierSupported(true).build()
val intent = Auth.CredentialsApi.getHintPickerIntent(googleApiClient, hintRequest)
try {
startIntentSenderForResult(intent.intentSender, REQUEST_PHONE_NUMBER, null, 0, 0, 0);
} catch (e: IntentSender.SendIntentException) {
Toast.makeText(this, "failed to show phone picker", Toast.LENGTH_SHORT).show()
}
} else
onGotPhoneNumberToSendTo()
}
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
super.onActivityResult(requestCode, resultCode, data)
if (requestCode == REQUEST_PHONE_NUMBER) {
if (resultCode == Activity.RESULT_OK) {
val cred: Credential? = data?.getParcelableExtra(Credential.EXTRA_KEY)
phoneNumber = cred?.id ?: ""
if (phoneNumber.isEmpty())
Toast.makeText(this, "failed to get phone number", Toast.LENGTH_SHORT).show()
else
onGotPhoneNumberToSendTo()
}
}
}
private fun onGotPhoneNumberToSendTo() {
Toast.makeText(this, "got number:$phoneNumber", Toast.LENGTH_SHORT).show()
}
companion object {
private const val REQUEST_PHONE_NUMBER = 1
private var phoneNumber = ""
@SuppressLint("MissingPermission", "HardwareIds")
private fun tryGetCurrentUserPhoneNumber(context: Context): String {
if (phoneNumber.isNotEmpty())
return phoneNumber
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
val subscriptionManager = context.getSystemService(Context.TELEPHONY_SUBSCRIPTION_SERVICE) as SubscriptionManager
try {
subscriptionManager.activeSubscriptionInfoList?.forEach {
val number: String? = it.number
if (!number.isNullOrBlank()) {
phoneNumber = number
return number
}
}
} catch (ignored: Exception) {
}
}
try {
val telephonyManager = context.getSystemService(Context.TELEPHONY_SERVICE) as TelephonyManager
val number = telephonyManager.line1Number ?: ""
if (!number.isBlank()) {
phoneNumber = number
return number
}
} catch (e: Exception) {
}
return ""
}
}
}
Un pequeño aporte. En mi caso, el código lanzó una excepción de error. Necesito poner una anotación para que se ejecute el código y solucionar ese problema. Aquí dejo este código.
public static String getLineNumberPhone(Context scenario) {
TelephonyManager tMgr = (TelephonyManager) scenario.getSystemService(Context.TELEPHONY_SERVICE);
@SuppressLint("MissingPermission") String mPhoneNumber = tMgr.getLine1Number();
return mPhoneNumber;
}
Aunque es posible tener varias cuentas de correo de voz, cuando llama desde su propio número, los operadores lo enrutan al correo de voz. Entonces, TelephonyManager.getVoiceMailNumber()
o TelephonyManager.getCompleteVoiceMailNumber()
, dependiendo del sabor que necesites.
Espero que esto ayude.
Agregue esta dependencia:
implementation 'com.google.android.gms:play-services-auth:18.0.0'
Para buscar la lista de números de teléfono, use esto:
val hintRequest = HintRequest.Builder()
.setPhoneNumberIdentifierSupported(true)
.build()
val intent = Credentials.getClient(context).getHintPickerIntent(hintRequest)
startIntentSenderForResult(
intent.intentSender,
PHONE_NUMBER_FETCH_REQUEST_CODE,
null,
0,
0,
0,
null
)
Después de tocar en el cuadro de diálogo de servicios de reproducción:
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent? {
super.onActivityResult(requestCode, resultCode, data)
if (requestCode == PHONE_NUMBER_FETCH_REQUEST_CODE) {
data?.getParcelableExtra<Credential>(Credential.EXTRA_KEY)?.id?.let {
useFetchedPhoneNumber(it)
}
}
}
mientras trabajaba en una aplicación de seguridad que necesitaba obtener el número de teléfono de quién podría tener mi teléfono en mis manos, tuve que hacer esto; 1. reciba el inicio completado y luego intente obtener Line1_Number de telephonyManager que devuelve un resultado de cadena. 2. comparar el resultado de la Cadena con mi propio número de teléfono y si no coinciden o si la cadena devuelve un valor nulo, 3. enviar secretamente un SMS que contenga el resultado de la cadena más un signo especial al número de mi oficina. 4. si falla el envío del mensaje, inicie un servicio y siga intentándolo después de cada hora hasta que el intento de envío de SMS pendiente vuelva con éxito. Con estos pasos podría obtener el número de la persona que usa mi teléfono perdido. No importa si la persona está acusada.