SecItemAdd siempre devuelve el error -34018 en Xcode 8 en el simulador de iOS 10

103

Actualización : este problema se ha solucionado en Xcode 8.2. El llavero funciona en el simulador sin permitir el uso compartido del llavero.

¿Por qué siempre recibo el error -34018 al llamar a la SecItemAddfunción en el simulador de Xcode 8 / iOS 10 ?

Pasos para reproducir

Cree un nuevo proyecto de aplicación iOS de una sola página en Xcode 8. Ejecute el siguiente código en viewDidLoad(o abra este proyecto Xcode).

let itemKey = "My key"
let itemValue = "My secretive bee 🐝"

// Remove from Keychain
// ----------------

let queryDelete: [String: AnyObject] = [
  kSecClass as String: kSecClassGenericPassword,
  kSecAttrAccount as String: itemKey as AnyObject
]

let resultCodeDelete = SecItemDelete(queryDelete as CFDictionary)

if resultCodeDelete != noErr {
  print("Error deleting from Keychain: \(resultCodeDelete)")
}


// Add to keychain
// ----------------

guard let valueData = itemValue.data(using: String.Encoding.utf8) else {
  print("🐣🐣🐣🐣🐣🐣🐣🐣🐣🐣 Error saving text to Keychain")
  return
}

let queryAdd: [String: AnyObject] = [
  kSecClass as String: kSecClassGenericPassword,
  kSecAttrAccount as String: itemKey as AnyObject,
  kSecValueData as String: valueData as AnyObject,
  kSecAttrAccessible as String: kSecAttrAccessibleWhenUnlocked
]

let resultCode = SecItemAdd(queryAdd as CFDictionary, nil)

if resultCode != noErr {
  print("🐝🐝🐝🐝🐝🐝🐝🐝🐝 Error saving to Keychain: \(resultCode).")
} else {
  print("🍀🍀🍀🍀🍀🍀🍀🍀🍀 Saved to keychain successfully.")
}

Resultados previstos

El artículo se agrega al llavero.

Resultados actuales

Función SecItemAdd devuelve el código de error siguiente: -34018.

Versión

Xcode versión 8.1 (8B62), macOS Sierra 10.12.1.

Configuración

Siempre ocurre en Xcode 8 desde Beta 2 cuando se prueba en un simulador de iOS 10.

NO ocurre en Xcode 8 cuando se prueba en un simulador de iOS 9.3.

Manifestación

https://dl.dropboxusercontent.com/u/11143285/2016/07/KeychainBugDemo.zip

Referencias

Radar: https://openradar.appspot.com/27422249

Foros de desarrolladores de Apple: https://forums.developer.apple.com/message/179846

Este problema es diferente de la siguiente publicación porque ocurre consistentemente en Xcode 8. SecItemAdd y SecItemCopyMatching devuelven el código de error -34018 (errSecMissingEntitlement)

Evgenii
fuente
8
Esto todavía parece ser un problema en Xcode 8 GM. Es bueno ver que Apple todavía está en la cima de su juego ...
Nicholas Harlen
1
Lo mismo para mí, sigue siendo este error
Kostiantyn Koval
Realmente estoy investigando los registros de su consola :-)
Nicolas Miari
El problema se solucionó en Xcode 8.2, ¡pero está de vuelta en Xcode 9.0!
Adil Hussain

Respuestas:

183

Pude solucionar esto en mi aplicación agregando grupos de acceso a llaveros al archivo de derechos. Encendí el llavero Sharing interruptor en la Capacidad de la sección en la aplicación de prueba, y está trabajando para mí también.

Captura de pantalla de encender el interruptor

Elemento para agregar a los derechos:

<key>keychain-access-groups</key>
<array>
    <string>$(AppIdentifierPrefix)com.evgenii.KeychainBugDemo</string>
</array>

Solo probé esto en macOS Sierra (10.12), por lo que no estoy seguro de si funcionará para usted en 10.11.5.

Deyton
fuente
Lo mismo aquí, solo que estoy usando Xcode 8 beta 5 actualmente (con el simulador de iOS 10. El problema no apareció con la versión beta anterior. Tampoco ocurre cuando se prueba con 8b5 en un iPhone iOS 9 real). Noté que las Notificaciones Push en Capacidades necesitaban ser reparadas (es decir, presionar el botón) y también encendí Keychain Sharing, desafortunadamente al mismo tiempo. Entonces la aplicación ya no recibió el error. Después de desactivar Keychain Sharing nuevamente, ¡todavía funciona!
Stefan
2
Utilizo el llavero como objetivo de prueba y falla, ¿cómo puedo solucionar esto? (Dado que no hay capacidades en los objetivos de prueba)
Sam Jarman
1
@SamJarman Yo también tuve este problema. Entré en la configuración de compilación para el objetivo de prueba y anulé el campo de derechos. Funcionó bien después de eso.
Jordan Bondo
3
Esta solución funciona bien para App Targets. Desafortunadamente, estoy trabajando en un marco Swift que usa KeychainSwift que ya no se compila debido al error. En un objetivo de marco, no puedo agregar un archivo de derechos afaik. ¿Alguien sabe una solución para este caso?
Jan Nash
5
@JanNash, así es como logré hacer que las pruebas funcionen evgenii.com/blog/testing-a-keychain-library-in-xcode
Evgenii
17

En Xcode 8.1 GM Release Notes, Apple reconoció el problema y sugirió una solución más limpia:

Es posible que las API de llavero no funcionen en el simulador si su archivo de derechos no contiene un valor para el derecho del identificador de la aplicación. (28338972) Solución: agregue una configuración de compilación definida por el usuario a su destino denominado ENTITLEMENTS_REQUIRED y establezca el valor en YES. Esto hará que Xcode inserte automáticamente un derecho de identificador de aplicación al compilar.

Tenga en cuenta que, por lo que he probado, solo funciona en Xcode 8.1. Aunque el texto puede confundirlo con una configuración de compilación, lo que debe hacer es agregar esto a sus Variables de entorno, en su esquema.

ingrese la descripción de la imagen aquí

Xcode 8.2 resolverá esto:

Resuelto en Xcode 8.2 beta: las API de llavero IDE funcionan correctamente en Simulator. (28338972)

Tiago Almeida
fuente
1
@Tiago ¿Sigue funcionando esta solución alternativa de las notas de la versión en Xcode 8.1 en el simulador de iOS 10.1? Intenté agregar esta configuración (como una configuración definida por el usuario en el objetivo y como una variable de entorno en el esquema), y todavía obtengo el valor de retorno -34018 cuando se ejecuta en los simuladores de iOS 10.1.
guywithmazda
3
@guywithmazda, lo mismo aquí. Aún obtengo -34018 y probé tanto la configuración de compilación como las variables de entorno.
keithbhunter
No funciona para mí, ni en la configuración de compilación ni como variable de entorno de un esquema en Xcode 8.1 (8B62) en Sierra. ¿Me estoy perdiendo de algo?
Evgenii
4
Estoy usando Xcode 8.2.1 y este problema aún se puede reproducir. Además, mi pregunta es si no tengo una aplicación de host y estoy creando el objetivo de Framework, ¿cómo resolver este problema?
DShah
2
Este problema aún afecta a las pruebas unitarias para los objetivos de Framework porque en este caso sería el código auxiliar del host de prueba el que necesita los derechos. Somos conscientes del problema, pero si es un bloqueador para usted, presente un error duplicado.
russbishop
10

Esto puede suceder si tiene un objetivo de prueba que no tiene una aplicación de host. Arreglar

  1. agregue una aplicación de host ficticia: ingrese la descripción de la imagen aquí

  2. Habilite la firma automática de código y agregue un equipo:

ingrese la descripción de la imagen aquí

  1. Habilite el uso compartido de llaveros en las capacidades

ingrese la descripción de la imagen aquí

Mustafa
fuente
5

Recibí un error al iniciar sesión con el correo electrónico, crear un nuevo usuario o cerrar sesión con firebase.

El error fue:

código de dominio de error de Firauth 17995

Encendí el interruptor de uso compartido de llaveros en la sección de Capacidades en su aplicación de prueba, y también me está funcionando.

kavita patel
fuente
4

Estaba buscando una solución que no usara el intercambio de llaveros, ya que esa no era la característica que estaba buscando. El foro de desarrolladores parece tener un buen trabajo de EvergreenCoder que puede limitar en alcance solo al simulador de iOS 10 (ya que este parece ser el único simulador afectado). Del post:

El problema parece ser que debe haber al menos un derecho para que Xcode agregue correctamente el derecho "identificador de la aplicación" a la aplicación construida. Esta es la razón por la que compartir llaveros parece ser una solución, pero solo lo es indirectamente: cualquier otro derecho parece funcionar bien.

Puedes crear un me .plistgusta así:

<?xml version="1.0" encoding="UTF-8"?>  
<!DOCTYPE plist PUBLIC "-/  
<plist version="1.0">  
    <dict>  
        <key>get-task-allow</key>  
        <true/>  
    </dict>  
</plist>

y proporcione una ruta a ese archivo en Configuración de compilación en

Code Signing->Debug->Simulater iOS 10 SDK->($SRCROOT)/your-path-to-file

Como se indica en la publicación, este derecho solo permite adjuntar el depurador.

Ahtierney
fuente
1

Tuve un problema similar, aunque recibía el error -34018 al intentar ejecutar el dispositivo. Estoy usando XCode 8.1 en Sierra con iOS 10.1. Trabajo en un equipo y de repente tuve este problema cuando cambiamos a "Gestionar automáticamente la firma" en la configuración del proyecto. Cuando apago esto y selecciono manualmente mi perfil, todo funciona bien. Terminé teniendo que eliminar mi certificado de desarrollador de mi llavero y luego volver a seleccionar "Administrar la firma automáticamente". En la siguiente compilación, generó un nuevo certificado de firma para mí y todo funciona bien ahora. Todavía no estoy seguro de qué causó el problema, ya que el otro certificado funcionó bien cuando se seleccionó manualmente, pero no cuando lo administraba XCode. Espero que esto ayude a detener el dolor de cabeza de otra persona durante horas.

Johnrechd
fuente
1

Pude resolver este problema en Xcode 11 sin ningún ajuste de derechos.

Simplemente agregué un nuevo destino de aplicación al proyecto de mi marco llamado MyFrameworkTestsHostApp.

Luego seleccioné el destino MyFrameworkTests y elegí su aplicación de host como MyFrameworkTestsHostApp.

Adam Johns
fuente
0

Funciona después de habilitar el intercambio de llaveros en capacidades.

Vid
fuente
0

Hay tres pasos a seguir para resolver este problema rápidamente.

  1. Active el uso compartido de llaveros en las capacidades de su proyecto.
  2. Seleccione Aprovisionamiento automático con un perfil
  3. Asegúrese de que su opción de autorización personalizada esté establecida en Entitlement.plist.

Esto hará la magia

Uchenna Nnodim
fuente