Considérer:
Invoke-WebRequest $sumoApiURL -Headers @{"Content-Type"= "application/json"} -Credential $cred -WebSession $webRequestSession -Method post -Body $sumojson -ErrorAction Stop
Cela lève l'exception suivante:
Comment puis-je l'attraper complètement ou au moins filtrer "Une ressource portant le même nom existe déjà."?
En utilisant $_.Exception.GetType().FullName
System.Net.WebException
et $_.Exception.Message
donne
Le serveur distant a renvoyé une erreur: (400) requête incorrecte.
Les erreurs et les exceptions dans PowerShell sont des objets structurés. Le message d'erreur que vous voyez imprimé sur la console est en fait un message formaté contenant des informations provenant de plusieurs éléments de l'objet error/exception. Vous pouvez (re) construire vous-même comme ceci:
$formatstring = "{0} : {1}`n{2}`n" +
" + CategoryInfo : {3}`n" +
" + FullyQualifiedErrorId : {4}`n"
$fields = $_.InvocationInfo.MyCommand.Name,
$_.ErrorDetails.Message,
$_.InvocationInfo.PositionMessage,
$_.CategoryInfo.ToString(),
$_.FullyQualifiedErrorId
$formatstring -f $fields
Si vous souhaitez simplement que le message d'erreur soit affiché dans votre bloc catch
, vous pouvez simplement faire écho à la variable d'objet en cours (qui contient l'erreur à cet endroit):
try {
...
} catch {
$_
}
Si vous avez besoin d'une sortie en couleur, utilisez Write-Host
avec une chaîne formatée comme décrit ci-dessus:
try {
...
} catch {
...
Write-Host -Foreground Red -Background Black ($formatstring -f $fields)
}
Cela dit, vous ne voulez généralement pas afficher le message d'erreur tel quel dans un gestionnaire d'exceptions (sinon, le -ErrorAction Stop
ne servirait à rien). Les objets d'erreur/exception structurés vous fournissent des informations supplémentaires que vous pouvez utiliser pour un meilleur contrôle des erreurs. Par exemple, vous avez $_.Exception.HResult
avec le numéro d'erreur actuel. $_.ScriptStackTrace
et $_.Exception.StackTrace
, vous pouvez donc afficher les traces de pile lors du débogage. $_.Exception.InnerException
vous donne accès aux exceptions imbriquées contenant souvent des informations supplémentaires sur l'erreur (les erreurs de niveau supérieur PowerShell peuvent être quelque peu génériques). Vous pouvez dérouler ces exceptions imbriquées avec quelque chose comme ceci:
$e = $_.Exception
$msg = $e.Message
while ($e.InnerException) {
$e = $e.InnerException
$msg += "`n" + $e.Message
}
$msg
Dans votre cas, les informations que vous souhaitez extraire semblent se trouver dans $_.ErrorDetails.Message
. Je ne sais pas très bien si vous avez un objet ou une chaîne JSON ici, mais vous devriez pouvoir obtenir des informations sur les types et les valeurs des membres de $_.ErrorDetails
en exécutant
$_.ErrorDetails | Get-Member
$_.ErrorDetails | Format-List *
Si $_.ErrorDetails.Message
est un objet, vous devriez pouvoir obtenir la chaîne de message comme ceci:
$_.ErrorDetails.Message.message
sinon, vous devez d'abord convertir la chaîne JSON en objet:
$_.ErrorDetails.Message | ConvertFrom-Json | Select-Object -Expand message
Selon le type d'erreur que vous gérez, les exceptions de types particuliers peuvent également inclure des informations plus spécifiques sur le problème rencontré. Dans votre cas, par exemple, vous avez un WebException
qui, en plus du message d'erreur ($_.Exception.Message
), contient la réponse réelle du serveur:
PS C: \> $ e.Exception | Get-membre TypeName: System.Net.WebException Nom MemberType Définition ---- ---------- - --------- Méthode Equals bool Equals (Objets obj), bool _Exception.E ... Méthode GetBaseException System.Exception Get.BaseException (), System.Excep. .. Méthode GetHashCode int GetHashCode (), int _Exception.GetHashCode () Méthode GetObjectData void GetObjectData (System.Runtime.Serialization.S ... GetType Type de méthode GetType ( ), tapez _Exception.GetType () ToString Méthode string ToString (), string _Exception.ToString () Propriété de données System.Collections.IDictionary Données {get;} Propriété HelpLink, propriété string HelpLink {get; set;} Propriété HResult int HResult {get;} InnerException Propriété System.Exception InnerException {get;} Message Propriété string Message {get;} Réponse, propriété System.Net.WebResponse Response {get;} Propriété source string Source {get; set;} StackTrace Propriété string StackTrace {get;} Status Propriété System.Net.WebExceptionStatus Status {get;} Propriété TargetSite System.Reflection.MethodBase TargetSite {get;}
qui vous fournit des informations comme celle-ci:
PS C: \> $ e.Exception.Response IsMutuallyAuthenticated: False Cookies: {} En-têtes: {Keep-Alive, Connexion, Longueur du contenu, Contenu-T ...} SupportsHeaders: True ContentLength: 198 ContentEncoding: ContentType: text/html; charset = iso-8859-1 CharacterSet: iso-8859-1 Serveur: Apache/2.4.10 Dernière modification: 17.07.2016 14:39:29 StatusCode: NotFound StatusDescription: non trouvé ProtocolVersion: 1.1 ResponseUri: http://www.example.com/ Method: POST IsFromCache: False
Étant donné que toutes les exceptions ne possèdent pas exactement le même ensemble de propriétés, vous pouvez utiliser des gestionnaires spécifiques pour des exceptions particulières:
try {
...
} catch [System.ArgumentException] {
# handle argument exceptions
} catch [System.Net.WebException] {
# handle web exceptions
} catch {
# handle all other exceptions
}
Si des opérations doivent être effectuées, qu'une erreur soit survenue ou non (tâches de nettoyage telles que la fermeture d'un socket ou une connexion à une base de données), vous pouvez les placer dans un bloc finally
après la gestion des exceptions:
try {
...
} catch {
...
} finally {
# cleanup operations go here
}
Je l'ai trouvé!
Imprimez simplement $Error[0]
pour le dernier message d'erreur.
Vous pouvez ajouter:
-ErrorVariable errvar
Et puis regardez dans $errvar
.
Ce qui suit a bien fonctionné pour moi
try {
asdf
} catch {
$string_err = $_ | Out-String
}
write-Host $string_err
Le résultat de ceci est le suivant en tant que chaîne au lieu d'un objet ErrorRecord
asdf : The term 'asdf' is not recognized as the name of a cmdlet, function, script file, or operable program. Check the spelling of the name, or if a path was included, verify that the path is correct and try again.
At C:\Users\TASaif\Desktop\tmp\catch_exceptions.ps1:2 char:5
+ asdf
+ ~~~~
+ CategoryInfo : ObjectNotFound: (asdf:String) [], CommandNotFoundException
+ FullyQualifiedErrorId : CommandNotFoundException
Je reviens sans cesse à ces questions pour essayer de déterminer où se trouvent exactement les données qui m'intéressent dans ce qui est vraiment une structure monolithique ErrorRecord. Presque toutes les réponses donnent des instructions fragmentaires sur la manière d'extraire certaines données.
Mais j’ai trouvé extrêmement utile de vider tout l’objet avec ConvertTo-Json
afin de pouvoir visualiser visuellement LITTÉRALEMENT TOUT dans une mise en page compréhensible.
try {
Invoke-WebRequest...
}
catch {
Write-Host ($_ | ConvertTo-Json)
}
Utilisez le paramètre ConvertTo-Json
de -Depth
pour développer des valeurs plus profondes, mais faites extrêmement attention en dépassant le rayon par défaut de 2
: P.
https://docs.Microsoft.com/en-us/powershell/module/Microsoft.powershell.utility/convertto-json