Benutzer mit den meisten Antworten
Value mit New-Item über eine Pipe einlesen

Frage
-
Hallo zusammen.
Ich stehe vor einem "Problem", dessen Ursache ich nicht verstehe.
Ich möchte neue Dateien und Verzeichnisse erstellen und die dazu nötigen Daten aus einer Pipe verwenden. Laut Dokumentation unterstützen die Parameter Path, ItemType und Value Eingaben über eine Pipe als ByPropertyName, also über den Namen der Eigenschaft. Dies funktioniert hervorragend mit Path und ItemType, jedoch nicht mit Value. Das nachfolgende Beispiel zeigt dies.
PS> $data = @" Path:ItemType:Value datei.txt:File:Hallo Welt verzeichnis:Directory: "@ PS> $data | ConvertFrom-Csv -Delimiter : | New-Item -Force
PS> Get-Content .\datei.txt
@{Path=datei.txt; ItemType=File; Value=Hallo Welt}Zur Lösung müsste ich das Kommando ausschreiben:
$data | ConvertFrom-Csv -Delimiter : |% { New-Item -Path $_.Path -ItemType $_.ItemType -Value $_.Value -Force }
Kann mir jemand erklären, wodurch sich die Probleme mit der Pipe im oberen Codeblock ergeben?
Vielen Dank. cc
Antworten
-
> (es wird ja auch hier ein String geliefert).
Und auch der ist ein Objekt... Abgesehen davon hab ich grad auch nicht wirklich ne Ahnung, was da "under the hood" passiert.
Naja, unter die Haube können wir ja einen vorsichtigen Blick riskieren:
Trace-Command -Name ParameterBinding -Expression {$data | ConvertFrom-Csv -Delimiter : | New-Item -Force} -PSHost
und sehen dann
BIND PIPELINE object to parameters: [New-Item] PIPELINE object TYPE = [System.Management.Automation.PSCustomObject] RESTORING pipeline parameter's original values Parameter [Value] PIPELINE INPUT ValueFromPipeline NO COERCION BIND arg [@{Path=datei.txt; ItemType=File; Value=Hallo Welt}] to parameter [Value] BIND arg [@{Path=datei.txt; ItemType=File; Value=Hallo Welt}] to param [Value] SUCCESSFUL Parameter [Credential] PIPELINE INPUT ValueFromPipelineByPropertyName NO COERCION Parameter [ItemType] PIPELINE INPUT ValueFromPipelineByPropertyName NO COERCION BIND arg [File] to parameter [ItemType] BIND arg [File] to param [ItemType] SUCCESSFUL Parameter [Path] PIPELINE INPUT ValueFromPipelineByPropertyName NO COERCION BIND arg [datei.txt] to parameter [Path] Binding collection parameter Path: argument type [String], parameter type [System.String[]], collection type Array, element type [System.String], no coerceElementType Creating array with element type [System.String] and 1 elements Argument type String is not IList, treating this as scalar Adding scalar element of type String to array position 0 BIND arg [System.String[]] to param [Path] SUCCESSFUL Parameter [Credential] PIPELINE INPUT ValueFromPipelineByPropertyName WITH COERCION Parameter [Credential] PIPELINE INPUT ValueFromPipelineByPropertyName WITH COERCION MANDATORY PARAMETER CHECK on cmdlet [New-Item]
Das Blöde ist, wie ich vermute, dass man Value nicht nur nach Namen sondern auch nach Wert binden kann:
Get-Help New-Item -Parameter Value -Value <Object> Erforderlich? false Position? Benannt Pipelineeingaben akzeptieren?true (ByValue, ByPropertyName) Name des Parametersatzes (Alle) Aliase Target Dynamisch? false
Also bindet er da das gesamte übergebene PSCustomObject und ist zufrieden. Im zweiten Beispiel bindest Du explizit nach Namen, daher kommt auch das Gewünschte rein.
Evgenij Smirnov
I work @ msg services ag, Berlin -> http://www.msg-services.de
I blog (in German) @ http://it-pro-berlin.de
my stuff in PSGallery --> https://www.powershellgallery.com/profiles/it-pro-berlin.de/
Exchange User Group, Berlin -> https://exusg.de
Windows Server User Group, Berlin -> http://www.winsvr-berlin.de
Mark Minasi Technical Forum, reloaded -> http://newforum.minasi.com
In theory, there is no difference between theory and practice. In practice, there is.
- Als Antwort markiert cgplc Montag, 10. September 2018 19:50
-
> Ergebnis hier gebloggt <https://it-pro-berlin.de/2018/09/powershell-quirks-values-aus-der-pipeline-object-edition/>
Da hast Du beide Params als [string] definiert. Was passiert denn, wenn einer davon [object] ist?
Ich verrat's Dir gleich :-) Das ist das gleiche wie bei New-Item... Ein [object] krallt sich immer das ganze Objekt, wie es aussieht. Und zwar bevorzugt als ByType statt ByPropertyName
MyOtherParm: MyOtherParmValue Type:string MyInput: MyInput MyOtherParm ForeignParm ------- ----------- ----------- MyInputValue MyOtherParmValue ShouldNotSeeMe Type:System.Management.Automation.PSCustomObject
- Als Antwort vorgeschlagen Evgenij Smirnov Dienstag, 11. September 2018 16:10
- Bearbeitet Martin Binder Dienstag, 11. September 2018 16:13 .....
- Als Antwort markiert Denniver ReiningMVP, Moderator Mittwoch, 19. September 2018 11:33
Alle Antworten
-
Hallo,
Mit:
siehst Du, dass Path und ItemTyp einen String verlangen, den Du ja auch lieferst, Value aber ein Objekt benötigt und daher der Direkt Aufruf in diesem Fall nicht funktioniert (es wird ja auch hier ein String geliefert).get-help new-item
# Output
SYNTAX
New-Item [-Path] <string[]> [-ItemType <string>] [-Value <Object>] [-Force] [-Credential <pscredential>] [-WhatIf] [-Confirm] [-UseTransaction]
[<CommonParameters>]
-
Hallo,
Mit:
siehst Du, dass Path und ItemTyp einen String verlangen, den Du ja auch lieferst, Value aber ein Objekt benötigt und daher der Direkt Aufruf in diesem Fall nicht funktioniert (es wird ja auch hier ein String geliefert).get-help new-item
# Output
SYNTAX
New-Item [-Path] <string[]> [-ItemType <string>] [-Value <Object>] [-Force] [-Credential <pscredential>] [-WhatIf] [-Confirm] [-UseTransaction]
[<CommonParameters>]
Ein String ist ein Object, daher kann ich Deine Erklärung nicht nachvollziehen. Der Typ Object bedeutet lediglich, dass _jeder_ Typ übergeben werden kann, da _alle_ Datentypen von Object abgeleitet sind. Zudem dürfte nach Deiner Erklärung die ausführliche Variante nicht funktionieren, denn auch hier wird ein String übergeben. Die ausführliche Variante funktioniert aber hervorragend.
cc
-
> (es wird ja auch hier ein String geliefert).
Und auch der ist ein Objekt... Abgesehen davon hab ich grad auch nicht wirklich ne Ahnung, was da "under the hood" passiert.
Naja, unter die Haube können wir ja einen vorsichtigen Blick riskieren:
Trace-Command -Name ParameterBinding -Expression {$data | ConvertFrom-Csv -Delimiter : | New-Item -Force} -PSHost
und sehen dann
BIND PIPELINE object to parameters: [New-Item] PIPELINE object TYPE = [System.Management.Automation.PSCustomObject] RESTORING pipeline parameter's original values Parameter [Value] PIPELINE INPUT ValueFromPipeline NO COERCION BIND arg [@{Path=datei.txt; ItemType=File; Value=Hallo Welt}] to parameter [Value] BIND arg [@{Path=datei.txt; ItemType=File; Value=Hallo Welt}] to param [Value] SUCCESSFUL Parameter [Credential] PIPELINE INPUT ValueFromPipelineByPropertyName NO COERCION Parameter [ItemType] PIPELINE INPUT ValueFromPipelineByPropertyName NO COERCION BIND arg [File] to parameter [ItemType] BIND arg [File] to param [ItemType] SUCCESSFUL Parameter [Path] PIPELINE INPUT ValueFromPipelineByPropertyName NO COERCION BIND arg [datei.txt] to parameter [Path] Binding collection parameter Path: argument type [String], parameter type [System.String[]], collection type Array, element type [System.String], no coerceElementType Creating array with element type [System.String] and 1 elements Argument type String is not IList, treating this as scalar Adding scalar element of type String to array position 0 BIND arg [System.String[]] to param [Path] SUCCESSFUL Parameter [Credential] PIPELINE INPUT ValueFromPipelineByPropertyName WITH COERCION Parameter [Credential] PIPELINE INPUT ValueFromPipelineByPropertyName WITH COERCION MANDATORY PARAMETER CHECK on cmdlet [New-Item]
Das Blöde ist, wie ich vermute, dass man Value nicht nur nach Namen sondern auch nach Wert binden kann:
Get-Help New-Item -Parameter Value -Value <Object> Erforderlich? false Position? Benannt Pipelineeingaben akzeptieren?true (ByValue, ByPropertyName) Name des Parametersatzes (Alle) Aliase Target Dynamisch? false
Also bindet er da das gesamte übergebene PSCustomObject und ist zufrieden. Im zweiten Beispiel bindest Du explizit nach Namen, daher kommt auch das Gewünschte rein.
Evgenij Smirnov
I work @ msg services ag, Berlin -> http://www.msg-services.de
I blog (in German) @ http://it-pro-berlin.de
my stuff in PSGallery --> https://www.powershellgallery.com/profiles/it-pro-berlin.de/
Exchange User Group, Berlin -> https://exusg.de
Windows Server User Group, Berlin -> http://www.winsvr-berlin.de
Mark Minasi Technical Forum, reloaded -> http://newforum.minasi.com
In theory, there is no difference between theory and practice. In practice, there is.
- Als Antwort markiert cgplc Montag, 10. September 2018 19:50
-
Parameter [Value] PIPELINE INPUT ValueFromPipeline NO COERCION
Parameter [ItemType] PIPELINE INPUT ValueFromPipelineByPropertyName NO COERCION
Parameter [Path] PIPELINE INPUT ValueFromPipelineByPropertyName NO COERCION
Das Blöde ist, wie ich vermute, dass man Value nicht nur nach Namen sondern auch nach Wert binden kann:
Ich vermute mal, Du vermutest recht ;) Ich musste aber auch zweimal hinschauen, bevor ich die relevante Information gesehen habe. Ich habe die Ausgabe von Trace-Command entsprechend gekürzt.
Dieses Verhalten ist wirklich ärgerlich, denn es bedeutet, dass ganz allgemein die Kombination "ValueFromPipeline" und "ValueFromPipelineByPropertyName" in den Attributen der Parameter keine gute Idee ist, denn das "ValueFromPipelineByPropertyName" kann nur dann funktionieren, wenn diese Eigenschaft auch die einzige Eigenschaft ist.
Vielen Dank, cc
-
Dieses Verhalten ist wirklich ärgerlich, denn es bedeutet, dass ganz allgemein die Kombination "ValueFromPipeline" und "ValueFromPipelineByPropertyName" in den Attributen der Parameter keine gute Idee ist, denn das "ValueFromPipelineByPropertyName" kann nur dann funktionieren, wenn diese Eigenschaft auch die einzige Eigenschaft ist.
Vielen Dank, cc
Evgenij Smirnov
I work @ msg services ag, Berlin -> http://www.msg-services.de
I blog (in German) @ http://it-pro-berlin.de
my stuff in PSGallery --> https://www.powershellgallery.com/profiles/it-pro-berlin.de/
Exchange User Group, Berlin -> https://exusg.de
Windows Server User Group, Berlin -> http://www.winsvr-berlin.de
Mark Minasi Technical Forum, reloaded -> http://newforum.minasi.com
In theory, there is no difference between theory and practice. In practice, there is.
-
> Ergebnis hier gebloggt <https://it-pro-berlin.de/2018/09/powershell-quirks-values-aus-der-pipeline-object-edition/>
Da hast Du beide Params als [string] definiert. Was passiert denn, wenn einer davon [object] ist?
Ich verrat's Dir gleich :-) Das ist das gleiche wie bei New-Item... Ein [object] krallt sich immer das ganze Objekt, wie es aussieht. Und zwar bevorzugt als ByType statt ByPropertyName
MyOtherParm: MyOtherParmValue Type:string MyInput: MyInput MyOtherParm ForeignParm ------- ----------- ----------- MyInputValue MyOtherParmValue ShouldNotSeeMe Type:System.Management.Automation.PSCustomObject
- Als Antwort vorgeschlagen Evgenij Smirnov Dienstag, 11. September 2018 16:10
- Bearbeitet Martin Binder Dienstag, 11. September 2018 16:13 .....
- Als Antwort markiert Denniver ReiningMVP, Moderator Mittwoch, 19. September 2018 11:33
-
Test: Ich antworte jetzt mal mit Quatsch und schau, ob Martins CloudBridge-Antwort gleich auftaucht...
In der Tat... Das Web-Reply scheint im Hintergrund einen Sync anzustoßen, den Bridge-Replys nicht anstoßen... #grützebleibtgrütze :-))
Greetings/Grüße, Martin - https://mvp.microsoft.com/en-us/PublicProfile/5000017 Mal ein gutes Buch über GPOs lesen? - http://www.amazon.de/Windows-Server-2012--8-Gruppenrichtlinien/dp/3866456956 Good or bad GPOs? My blog - http://evilgpo.blogspot.com And if IT bothers me? Coke bottle design refreshment - http://sdrv.ms/14t35cq
-
> Ergebnis hier gebloggt <https://it-pro-berlin.de/2018/09/powershell-quirks-values-aus-der-pipeline-object-edition/>
Da hast Du beide Params als [string] definiert. Was passiert denn, wenn einer davon [object] ist?
Evgenij Smirnov
I work @ msg services ag, Berlin -> http://www.msg-services.de
I blog (in German) @ http://it-pro-berlin.de
my stuff in PSGallery --> https://www.powershellgallery.com/profiles/it-pro-berlin.de/
Exchange User Group, Berlin -> https://exusg.de
Windows Server User Group, Berlin -> http://www.winsvr-berlin.de
Mark Minasi Technical Forum, reloaded -> http://newforum.minasi.com
In theory, there is no difference between theory and practice. In practice, there is.