2010-11-01 5 views
1

Dans le cadre d'un refactoring énorme, j'ai supprimé quelques classes et enums en double. J'ai déplacé les espaces de noms et restructuré tout pour être plus facile à maintenir dans le futur.Comment insérer du texte après une ligne spécifique dans des fichiers utilisant PowerShell?

Tous les changements ont déjà été scriptés à l'exception d'une chose. J'ai besoin d'insérer un espace de noms de contrat de données dans chaque fichier qui utilise un autre espace de noms si l'espace de noms de contrat de données n'a pas encore été inséré.

Le code que j'ai pour le moment ne fonctionne pas mais c'est en quelque sorte ce dont j'ai besoin.

function Insert-Usings{ 
    trap { 
     Write-Host ("ERROR: " + $_) -ForegroundColor Red 
     return $false 
    } 
    (Get-ChildItem $base_dir -Include *.asmx,*.ascx,*.cs,*.aspx -Force -Recurse -ErrorAction:SilentlyContinue) | % { 
    $fileName = $_.FullName 
    (Get-Content $fileName) | 
     Foreach-Object 
     { 
      $_ 
      if ($_ -cmatch "using Company.Shared;") { 
        $_ -creplace "using Company.Shared;", "using Company.Common;" 
      } 
      elseif ($_ -cmatch "using Company") { 
       #Add Lines after the selected pattern 
       "using Company.Services.Contracts;" 
      } 
      else{ 
       $_ 
      } 
     } 
    } | Set-Content $fileName 
} 

Edit: Le code tend à la sortie (remplacer l'ensemble avec- de fichiers) états "à l'aide de Company.Services.Contracts".

+0

Échec? Quel est le message d'erreur? Ou fait-il quelque chose de différent de ce que vous voulez? –

+0

Désolé de ne pas être assez clair dans la question originale. Je vais mettre à jour avec quelques informations supplémentaires. – mhenrixon

Répondre

3

Il n'est pas tout à fait clair ce que vous obtenez exactement, mais je vais essayer de deviner, voir mes commentaires dans le code. Le code original, je pense, contient quelques erreurs, l'un est sérieux: Set-Content est utilisé dans un mauvais pipeline/boucle. Voici le code corrigé.

function Insert-Usings 
{ 
    trap { 
     Write-Host ("ERROR: " + $_) -ForegroundColor Red 
     return $false 
    } 
    (Get-ChildItem $base_dir -Include *.asmx,*.ascx,*.cs,*.aspx -Force -Recurse -ErrorAction:SilentlyContinue) | % { 
     $fileName = $_.FullName 
     (Get-Content $fileName) | % { 
      if ($_ -cmatch "using Company\.Shared;") { 
       # just replace 
       $_ -creplace "using Company\.Shared;", "using Company.Common;" 
      } 
      elseif ($_ -cmatch "using Company") { 
       # write the original line 
       $_ 
       # and add this after 
       "using Company.Services.Contracts;" 
      } 
      else{ 
       # write the original line 
       $_ 
      } 
     } | 
     Set-Content $fileName 
    } 
} 

Par exemple, il remplace ceci:

xxx 

using Company.Shared; 

using Company; 

ttt 

avec ceci:

xxx 

using Company.Common; 

using Company; 
using Company.Services.Contracts; 

ttt 

Note: Je suppose que vous ne devez pas appliquer ce code à des sources plus d'une fois, le code est conçu pour cela.

+0

Fonctionne comme un charme! Pourriez-vous élaborer sur la note de bas de page pour ne pas avoir été conçue pour cela? Tout ce que je peux faire pour le rendre plus sûr? Le code n'est pas destiné à être exécuté plus d'une fois. Ce sera une étape d'une routine de déploiement et seulement une fois par client, mais voyez-vous des façons d'améliorer le code ci-dessus? – mhenrixon

+1

Si vous exécutez ce code une deuxième fois, il ajoutera du code après * chaque * ligne avec 'using Company'. Ce sera faux car cela a déjà été fait lors de la première manche. Ne le faites pas deux fois, je pense que c'est la meilleure solution simple. Si une exécution échoue au milieu, supprimez/tuez toutes les sources partiellement modifiées, prenez l'original, réexécutez après avoir résolu les problèmes. –

+0

J'aimerais pouvoir vous donner plus de points pour les réponses utiles;) – mhenrixon

Questions connexes