À retenir — Si le même projet signe correctement dans une session graphique mais échoue en SSH avec errSecInternalComponent, vérifiez d’abord l’utilisateur réellement chargé, l’état du trousseau de connexion et l’accès de codesign à l’identité de signature ; ne recréez pas les certificats avant d’avoir des éléments qui les mettent en cause. Cet ordre convient aux tâches xcodebuild archive lancées depuis une session distante ou un processus non interactif, mais l’erreur seule ne permet pas d’identifier une cause unique.
Cet article s’adresse aux développeurs indépendants qui exécutent un Archive sur un Mac distant par SSH et rencontrent une erreur CodeSign.
Il concerne aussi les petites équipes qui administrent leurs propres tâches de compilation et doivent comparer leur contexte avec une session graphique.
Si l’identité de signature existe déjà, les vérifications ci-dessous permettent de séparer un problème d’accès au trousseau d’un certificat ou d’un profil inadapté.
00Repérer précisément l’étape où la signature échoue
Commencez par conserver le journal complet du build, puis trouvez la première ligne d’échec associée à CodeSign. La dernière erreur affichée n’est pas nécessairement la cause initiale : un problème de signature peut interrompre plusieurs opérations suivantes, tandis qu’un échec de compilation ou d’export peut survenir à une étape différente.
Pour un Archive lancé par SSH, distinguez ces situations :
- La compilation s’arrête avant
CodeSign: examinez d’abord les erreurs de compilation, les dépendances et les réglages du projet. Une modification du trousseau ne répond pas à ce symptôme. - Une ligne
CodeSignéchoue pendant l’Archive : passez aux contrôles de session, de trousseau et d’identité décrits dans cet article. - L’Archive réussit, mais une opération ultérieure échoue : ne qualifiez pas automatiquement le problème d’échec de signature. Vérifiez le message de l’étape d’export ou de téléversement séparément.
- Le terminal SSH affiche une erreur générique : relancez la commande avec une sortie conservée et repérez le premier échec, plutôt que de vous fier à la seule dernière ligne.
Pourquoi SSH peut-il produire errSecInternalComponent alors qu’une session graphique fonctionne ? Parce que le processus peut ne pas disposer du même contexte utilisateur ni du même accès au trousseau que le terminal ouvert dans une session graphique. Apple Developer Technical Support indique que cette erreur peut se présenter dans des environnements de signature non standards, notamment SSH ou CI, et cite un trousseau verrouillé comme cause possible ; elle ne prouve donc pas, à elle seule, que le certificat est invalide. La discussion d’Apple DTS sur les erreurs de signature en SSH et en CI constitue le point de départ pertinent pour ce cas.
Pour comparer les résultats, lancez la même commande, avec le même projet et les mêmes réglages, dans la session graphique puis par SSH. Relevez pour chaque tentative le premier message d’erreur, le nom de l’utilisateur, le chemin du projet et l’étape qui s’interrompt. Si le seul changement est le mode d’exécution, le contexte de session devient une piste prioritaire ; si les deux modes échouent de la même manière, élargissez l’enquête aux réglages et aux ressources de signature.
Les notes de version doivent également être consultées avant d’attribuer un comportement à une version donnée. Les notes de version officielles d’Xcode 27 permettent de vérifier si une modification documentée concerne l’outil utilisé. N’en déduisez pas qu’une mise à jour résout le problème sans reproduire l’Archive dans le contexte concerné.
01Première étape : vérifier l’utilisateur du processus SSH
La présence d’une invite de commande ne prouve pas que le build s’exécute sous le compte attendu. Une commande directe en SSH, une tâche planifiée, un agent ou un service de compilation peuvent être lancés avec des comptes ou des environnements différents. La documentation technique d’Apple sur les daemons et les agents décrit justement pourquoi le contexte d’un processus macOS ne se résume pas au fait qu’il puisse exécuter une commande. La note technique d’Apple sur les contextes d’exécution des daemons et des agents aide à comprendre cette distinction.
Dans la même session que celle qui lance xcodebuild, relevez les informations suivantes :
id -un
printf '%s\n' "$HOME"
pwd
Comparez ces résultats avec le compte qui possède les ressources de signature attendues. Il faut notamment vérifier que le répertoire personnel correspond bien à celui de l’utilisateur prévu et que la tâche n’a pas basculé vers root ou un autre compte. Si le lancement passe par un script ou un service, ajoutez temporairement ces contrôles au script qui exécute réellement le build ; un relevé fait dans une connexion SSH interactive ne décrit pas forcément le processus de la tâche automatisée.
Comment confirmer que le bon compte macOS exécute réellement le build ? Le contrôle utile est celui effectué immédiatement avant xcodebuild, dans le processus qui lancera l’Archive. Si id -un ou $HOME diffère entre la connexion de test et la tâche automatisée, corrigez d’abord le compte ou la configuration de lancement, puis reproduisez l’échec. Ne cherchez pas à « réparer » le compte attendu en important les certificats dans plusieurs trousseaux : cette opération brouille le diagnostic et peut accroître l’exposition des clés privées.
Cochez ces points avant de poursuivre :
- [ ] Le compte relevé correspond au compte prévu pour le build.
- [ ] Le répertoire
$HOMEcorrespond au répertoire personnel de ce compte. - [ ] La tâche automatisée utilise le même compte que celui testé par SSH.
- [ ] Les chemins vers le projet et les ressources de signature sont accessibles à ce compte.
Si un seul de ces contrôles échoue, corrigez le contexte d’exécution puis relancez une Archive de vérification. Les explications générales sur l’accès à un environnement distant peuvent être complétées par l’aide NUKCLOUD sur l’accès et l’utilisation d’un Mac distant, sans confondre les réglages de connexion avec ceux du code signing.
02Deuxième étape : contrôler le trousseau dans la session non interactive
Une session SSH ne peut pas répondre à une fenêtre de dialogue graphique qui demanderait de déverrouiller un trousseau ou d’autoriser un accès. Une compilation qui fonctionne après ouverture de session sur le bureau peut donc échouer en tâche distante, même si le compte utilisateur paraît identique. Apple DTS cite le verrouillage du trousseau parmi les causes possibles d’errSecInternalComponent dans les scénarios SSH ou CI ; cela justifie de vérifier son état avant de modifier les certificats.
Identifiez d’abord le trousseau où se trouve l’identité utilisée par le projet, puis vérifiez qu’il est disponible pour le processus qui lance l’Archive. Les commandes d’inspection doivent être exécutées sous le compte de build et non depuis une session d’administration différente. La documentation d’Apple explique qu’une identité de signature est stockée dans le trousseau et qu’elle associe des éléments nécessaires à la signature ; la description officielle de l’identité conservée dans le trousseau aide à distinguer cette identité d’un simple certificat exporté.
Que faire si le trousseau semble déverrouillé, mais que codesign échoue encore ? Vérifiez que c’est bien le trousseau pertinent qui est disponible pour le compte de build et que l’identité se trouve dans ce trousseau, puis examinez l’autorisation de la clé privée. Un trousseau déverrouillé ne garantit pas automatiquement que le processus peut utiliser chaque clé qu’il contient. Ne concluez donc pas que le mot de passe du trousseau est erroné au seul vu de l’échec de signature.
Si une action de déverrouillage est nécessaire, effectuez-la dans le mécanisme sécurisé prévu pour la tâche, puis testez le build dans ce même contexte. Ne placez jamais le mot de passe du trousseau dans le dépôt, dans une commande conservée dans l’historique, dans une sortie de diagnostic ou dans un script partagé. Évitez également de publier des journaux contenant des chemins privés, des identifiants de certificat ou des variables d’environnement sensibles. Pour une procédure d’accès, les secrets doivent être injectés par un mécanisme de stockage protégé, avec une portée limitée au processus de build.
03Troisième étape : confirmer l’identité et l’accès à la clé privée
Un certificat visible dans une liste n’est pas une preuve suffisante que le processus possède une identité exploitable. Vérifiez que l’identité attendue comprend le certificat et la clé privée correspondante, puis que l’utilisateur de la tâche peut accéder à cette clé. Apple décrit la protection des certificats et les types d’identités dans sa documentation sur les certificats de développement.
Dans le compte concerné, une inspection de la liste des identités de signature peut aider à repérer si l’identité attendue est disponible :
security find-identity -v -p codesigning
Conservez la sortie en lieu sûr et masquez les identifiants avant de la partager. Comparez l’identité affichée avec celle sélectionnée par la configuration de build ; ne copiez pas publiquement son empreinte ni les détails de la clé privée. Si l’identité n’apparaît pas, vérifiez d’abord que le bon trousseau et le bon compte sont utilisés. Si elle apparaît mais que codesign ne peut toujours pas s’en servir, investiguez l’autorisation d’accès à la clé privée et les éventuelles demandes de confirmation impossibles à traiter dans une session SSH.
N’appliquez pas une règle d’autorisation universelle à toutes les installations : les réglages de partage de clé, les politiques locales et la manière dont la tâche est lancée peuvent différer. Une modification trop large de l’accès à la clé peut résoudre le symptôme tout en accordant des droits inutiles. Procédez par preuve : identité absente, identité incomplète, accès refusé ou demande d’autorisation non interactive sont des constats différents et appellent des corrections différentes.
04Distinguer ensuite le certificat du profil de provisionnement
Examinez les certificats et le profil seulement lorsque les indices désignent cette couche : identité absente ou expirée, équipe incorrecte, identifiant d’application incompatible, ou message explicite portant sur le profil. La validité du certificat, l’accès à la clé privée et le déverrouillage du trousseau ne sont pas le même problème ; les traiter comme un seul réglage mène souvent à remplacer des ressources sans rapport avec l’erreur initiale.
Pour isoler un problème de configuration, comparez les valeurs effectivement utilisées par le build, notamment l’identité de signature, PRODUCT_BUNDLE_IDENTIFIER, l’équipe et le profil sélectionné. Vérifiez que le profil correspond à l’identifiant d’application et à l’équipe du projet, puis examinez le journal d’Archive pour voir si le message d’échec désigne précisément cette incompatibilité. Les documents d’Apple sur la modification, le téléchargement et la régénération des profils de provisionnement décrivent les opérations disponibles ; ils ne justifient pas de remplacer un profil sans preuve que celui-ci est en cause.
Comment séparer une panne d’accès au trousseau d’un profil incompatible ? Si l’erreur survient lorsque le processus tente d’utiliser l’identité, et que la même identité signe dans la session graphique, examinez d’abord le compte, le trousseau et l’autorisation de la clé. Si le journal nomme un profil, une équipe ou un identifiant d’application incompatible, comparez ces valeurs au projet et au profil actif. Pour les cas moins évidents, l’index Apple des problèmes de signature iOS aide à classer les symptômes plutôt qu’à appliquer une réparation générique.
La configuration des droits intégrés à l’application est une vérification distincte. Si le message concerne les entitlements, inspectez ceux du produit généré et comparez-les aux capacités attendues, au lieu de modifier le trousseau. Apple décrit cette démarche dans son guide pour diagnostiquer les problèmes liés aux entitlements.
05Choisir la piste selon les indices, puis valider la correction
Utilisez cette liste de décision pour éviter les changements qui ne correspondent pas au symptôme :
- Si l’utilisateur ou
$HOMEdiffère entre la connexion SSH et la tâche réelle, corrigez d’abord le compte ou le lanceur, puis répétez le test. Sinon, passez au contrôle du trousseau. - Si le trousseau utilisé par la tâche est verrouillé ou inaccessible, rétablissez son accès dans le contexte sécurisé prévu pour le build, puis vérifiez l’identité. Ne recréez pas le certificat à ce stade.
- Si le trousseau est disponible mais que l’identité ou sa clé privée manque, corrigez l’importation ou l’accès à cette identité pour le compte concerné, puis relancez la signature.
- Si l’identité est accessible mais qu’un message désigne le certificat, l’équipe, l’identifiant d’application ou le profil, vérifiez ces réglages précis avant de modifier les ressources de signature.
- Si l’Archive réussit mais que l’étape suivante échoue, revenez à l’étape précise du journal : la correction doit viser l’export ou le téléversement concerné, pas la session de signature par défaut.
Une correction n’est pas validée parce qu’une commande isolée retourne un résultat favorable. Relancez un Archive représentatif avec le même compte, le même mode SSH, le même schéma et les mêmes réglages que la tâche de livraison. Par exemple, adaptez les variables ci-dessous aux valeurs locales sans y inscrire de secret :
xcodebuild \
-scheme "$SCHEME" \
-archivePath "$ARCHIVE_PATH" \
archive
Conservez le journal complet et vérifiez que la commande atteint la fin de l’Archive sans erreur CodeSign. Si le produit contient une application intégrée, vérifiez aussi le résultat de signature et les entitlements du produit obtenu, en suivant les indications Apple sur l’inspection des entitlements. Cette vérification ne remplace pas la validation de l’application dans votre processus de livraison ; elle confirme que le problème initial n’a pas simplement été déplacé vers une étape suivante.
Notez, dans un relevé interne qui ne contient aucun secret, la version de macOS et d’Xcode, le compte d’exécution, l’emplacement du trousseau utilisé, la première erreur observée et les conditions de reproduction. Si la panne revient, ces informations permettent de comparer deux exécutions sans exposer les mots de passe, les jetons ou les clés privées. La page NUKCLOUD consacrée aux Macs distants permet de vérifier les possibilités d’accès avant de préparer un environnement de build correspondant à ces contraintes.
06Quand le Mac distant devient préférable à la machine actuelle
Si la signature fonctionne localement mais dépend d’une session graphique ouverte, la configuration actuelle présente des limites concrètes : le build automatisé peut ne pas retrouver le contexte utilisateur attendu ; une machine partagée peut mélanger les trousseaux et les réglages de plusieurs projets ; enfin, les secrets risquent d’être copiés dans des scripts ou journaux pour contourner une demande interactive. Ces problèmes ne sont pas résolus en remplaçant systématiquement les certificats.
Pour un besoin temporaire de compilation distante, un Mac dédié accessible par SSH peut séparer le compte de build, son trousseau et les tâches du projet de l’environnement de travail quotidien. NUKCLOUD propose la location d’un Mac distant accessible par SSH, VNC ou console web ; cette option évite l’achat d’une machine consacrée uniquement aux Archives, tout en laissant à l’équipe la responsabilité de sécuriser ses identifiants et son flux de signature. Si le build tourne en continu et exige un environnement physique ou des périphériques locaux, un Mac possédé et administré sur place peut rester plus adapté. Pour un test ou une capacité de compilation ponctuelle, la location permet d’évaluer ce modèle sans confondre l’accès à une machine avec la configuration correcte du code signing.
Avant de modifier les certificats, établissez donc si la panne appartient à la session, au trousseau, à la clé privée ou au profil : ce classement réduit les changements inutiles et rend l’Archive reproductible. Si l’environnement distant reste la variable déterminante, consultez les options Mac de NUKCLOUD et vérifiez que le mode d’accès proposé correspond à votre processus SSH et à vos exigences de sécurité.