El permiso de Android no funciona incluso si lo he declarado
Estoy intentando escribir código para enviar un SMS desde una aplicación de Android, pero cuando intento enviar el SMS me devuelve el error:
09-17 18:37:29.974 12847-12847/**.**.****E/AndroidRuntime﹕ FATAL EXCEPTION: main
Process: **.**.****, PID: 12847
java.lang.SecurityException: Sending SMS message: uid 10092 does not have android.permission.SEND_SMS.
at android.os.Parcel.readException(Parcel.java:1599)
at android.os.Parcel.readException(Parcel.java:1552)
at com.android.internal.telephony.ISms$Stub$Proxy.sendTextForSubscriber(ISms.java:768)
at android.telephony.SmsManager.sendTextMessageInternal(SmsManager.java:310)
at android.telephony.SmsManager.sendTextMessage(SmsManager.java:293)
at **.**.****.MainActivity$3.onClick(MainActivity.java:70)
at android.view.View.performClick(View.java:5198)
at android.view.View$PerformClick.run(View.java:21147)
at android.os.Handler.handleCallback(Handler.java:739)
at android.os.Handler.dispatchMessage(Handler.java:95)
at android.os.Looper.loop(Looper.java:148)
at android.app.ActivityThread.main(ActivityThread.java:5417)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:726)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:616)
Lo verifiqué pero tengo los permisos en el manifiesto, de la siguiente manera:
<?xml version="1.0" encoding="utf-8"?>
<uses-permission android:name="android.permission.SEND_SMS"/>
<uses-feature android:name="android.hardware.telephony"
android:required="true"/>
<application
android:exported="true"
android:allowBackup="true"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:theme="@style/AppTheme">
<activity
android:name=".MainActivity"
android:label="@string/app_name"
android:screenOrientation="portrait">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
</application>
Busqué en Internet pero todos los errores eran de <uses-permission/>
sintaxis, ¿podrían ayudarme por favor?
(Lo siguiente está extraído de una publicación mía sobre esto )
La gran razón para no obtener su permiso hoy en día es porque su proyecto tiene un valor targetSdkVersion
de 23 o superior y el permiso que solicita es "peligroso". En Android 6.0, esto incluye:
ACCEPT_HANDOVER
ACCESS_BACKGROUND_LOCATION
ACCESS_MEDIA_LOCATION
ACTIVITY_RECOGNITION
ANSWER_PHONE_CALLS
ACCESS_COARSE_LOCATION
ACCESS_FINE_LOCATION
ADD_VOICEMAIL
BODY_SENSORS
CALL_PHONE
CAMERA
GET_ACCOUNTS
PROCESS_OUTGOING_CALLS
READ_CALENDAR
READ_CALL_LOG
READ_CELL_BROADCASTS
READ_CONTACTS
READ_EXTERNAL_STORAGE
READ_PHONE_STATE
READ_SMS
RECEIVE_MMS
RECEIVE_SMS
RECEIVE_WAP_PUSH
RECORD_AUDIO
SEND_SMS
USE_SIP
WRITE_CALENDAR
WRITE_CALL_LOG
WRITE_CONTACTS
WRITE_EXTERNAL_STORAGE
Para estos permisos, su targetSdkVersion
aplicación 23+ no solo necesita tener los <uses-permission>
elementos, sino que también debe solicitar esos permisos en tiempo de ejecución al usuario en dispositivos Android 6.0+, usando métodos como checkSelfPermission()
y
requestPermissions()
.
Como solución temporal, baje targetSdkVersion
de 23 años.
Sin embargo, eventualmente tendrás alguna razón para querer
targetSdkVersion
tener 23 años o más. En ese momento, deberá ajustar su aplicación para utilizar el nuevo sistema de permisos de tiempo de ejecución. La documentación de Android tiene
una página dedicada a este tema .
Por encima del nivel API 23, se le proporcionará programación pragmática como:
private static final int PERMISSION_REQUEST_CODE = 1;
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.M) {
if (checkSelfPermission(Manifest.permission.SEND_SMS)
== PackageManager.PERMISSION_DENIED) {
Log.d("permission", "permission denied to SEND_SMS - requesting it");
String[] permissions = {Manifest.permission.SEND_SMS};
requestPermissions(permissions, PERMISSION_REQUEST_CODE);
}
}
solicitar permiso de forma pragmática (después de API 23)
if (ContextCompat.checkSelfPermission(thisActivity, Manifest.permission.SEND_SMS)
!= PackageManager.PERMISSION_GRANTED) {
// Permission is not granted
// Ask for permision
ActivityCompat.requestPermissions(this,new String[] { Manifest.permission.SEND_SMS}, 1);
}
else {
// Permission has already been granted
}
"Si la aplicación tiene el permiso, el método checkSelfPermission() devuelve PERMISSION_GRANTED y la aplicación puede continuar con la operación.
Si la aplicación no tiene el permiso, el método devuelve PERMISSION_DENIED y la aplicación debe pedir permiso explícitamente al usuario. Debe solicitar ese permiso al usuario, como se muestra en el código anterior. Al llamar a requestPermissions() aparece un cuadro de diálogo estándar de Android, que no se puede personalizar".
Vaya al siguiente enlace, https://developer.android.com/guide/topics/permissions/overview.html
También hay algunos ejemplos disponibles allí para comenzar con los permisos.
Para hacer que Android sea más seguro, ahora los desarrolladores deben mencionar el permiso en el manifiesto y también deben solicitar al usuario en tiempo de ejecución que realice el trabajo. Están clasificados en la sección de permisos peligrosos que se mencionan a continuación.
CALENDARIO
READ_CALENDAR
WRITE_CALENDAR
CÁMARA
CAMERA
CONTACTOS
READ_CONTACTS
WRITE_CONTACTS
GET_ACCOUNTS
UBICACIÓN
ACCESS_FINE_LOCATION
ACCESS_COARSE_LOCATION
MICRÓFONO
RECORD_AUDIO
TELÉFONO
READ_PHONE_STATE
READ_PHONE_NUMBERS
CALL_PHONE
ANSWER_PHONE_CALLS (must request at runtime)
READ_CALL_LOG
WRITE_CALL_LOG
ADD_VOICEMAIL
USE_SIP
PROCESS_OUTGOING_CALLS
ANSWER_PHONE_CALLS
SENSORES
BODY_SENSORS
SMS
SEND_SMS
RECEIVE_SMS
READ_SMS
RECEIVE_WAP_PUSH
RECEIVE_MMS
ALMACENAMIENTO
READ_EXTERNAL_STORAGE
WRITE_EXTERNAL_STORAGE