Hoe recursief bestanden met een specifieke extensie in PowerShell op te halen?

Voor een specifieke map moet ik alle bestanden met de extensie .jsweergeven, zelfs als ze op elk niveau in submappen zijn genest.

Het resultaat voor de uitvoerconsole zou een lijst met bestandsnamen moeten zijn zonder extensie regel voor regel, zodat deze gemakkelijk kan worden gekopieerd en geplakt in een andere toepassing.

Op dit moment probeer ik dit, maar in de output console krijg ik verschillende meta-informatie en geen simpele lijst.

Get-ChildItem -Path C:\xx\x-Recurse -File | sort length –Descending

Kun je me wat hints geven?


Antwoord 1, autoriteit 100%

Als sorteren op lengte niet nodig is, kunt u de parameter -Namegebruiken om Get-ChildItemalleen de naam te laten retourneren, en vervolgens [System.IO.Path]::GetFileNameWithoutExtension()om het pad en de extensie te verwijderen:

Get-ChildItem -Path .\ -Filter *.js -Recurse -File -Name| ForEach-Object {
    [System.IO.Path]::GetFileNameWithoutExtension($_)
}

Als sorteren op lengte gewenst is, laat u de parameter -Namevallen en voert u de eigenschap BaseNameuit van elk FileInfo-object. U kunt de uitvoer (in beide voorbeelden) doorsluizen naar clip, om deze naar het klembord te kopiëren:

Get-ChildItem -Path .\ -Filter *.js -Recurse -File| Sort-Object Length -Descending | ForEach-Object {
    $_.BaseName
} | clip

Als je het volledige pad wilt, maar zonder de extensie, vervang dan $_.BaseNamedoor:

$_.FullName.Remove($_.FullName.Length - $_.Extension.Length)

Antwoord 2, autoriteit 13%

De eenvoudige optie is om de eigenschap .Namevan het item FileInfoin de pijplijn te gebruiken en vervolgens de extensie te verwijderen:

Get-ChildItem -Path "C:\code\" -Filter *.js -r | % { $_.Name.Replace( ".js","") }

Antwoord 3, autoriteit 7%

Er zijn twee methoden om bestanden te filteren: globbingmet een jokerteken, of met behulp van een reguliere expressie (Regex).

Waarschuwing:De globbing-methode heeft het nadeel dat deze ook overeenkomt met bestanden die niet moeten worden gevonden, zoals *.jsx.

# globbing with Wildcard filter 
# the error action prevents the output of errors
# (ie. directory requires admin rights and is inaccessible)
Get-ChildItem -Recurse -Filter '*.js' -ErrorAction 'SilentlyContinue' 
# filter by Regex
Where-Object { $_.Name -Match '.*\.js$' }

U kunt vervolgens naar behoefte sorteren op naam of bestandsgrootte:

# sort the output 
Sort-Object -PropertyName 'Length'

Maak het een eenvoudige lijst met pad en bestandsnaam:

# format output
Format-List -Property ('Path','Name')

Om de bestandsextensie te verwijderen, kunt u een select gebruiken om het resultaat toe te wijzen:

Select-Item { $_.Name.Replace( ".js", "")

Alles bij elkaar, er is ook een zeer korte versie, die u niet in scripts moet gebruiken, omdat deze nauwelijks leesbaar is:

ls -r | ? { $_.Name -matches '.*\.js' } | sort Length | % { $_.Name.Replace( ".js", "") | fl

Antwoord 4, autoriteit 4%

Als u van beknoptheid houdt, kunt u het ForEach-Object en de aanhalingstekens verwijderen. -Pathis standaard de huidige map, dus u kunt deze weglaten

(Get-ChildItem -Filter *.js -Recurse).BaseName | Sort length -Descending

Antwoord 5

De bovenstaande antwoorden werken prima. In WIndows is er echter een alias genaamd ls hetzelfde als op linux, dus een andere kortere opdracht die ook werkt, is ls -Filter *.exe


Antwoord 6

Gebruik BaseNamevoor de bestandsnaam zonder de bestandsextensie.

Get-ChildItem -Path ".\*.js" | Sort-Object Length -Descending | ForEach-Object {
    $_.BaseName  
}

Other episodes