bommi1961
Goto Top

Mit Powershell den Inhalt einer Excel mit einer Text Datei abgleichen

Hallo zusammen,

ich muss den Inhalt einer Excel Datei (Mappe1) mit dem Daten einer Text Datei abgleichen. Die Daten die in der Text Datei sind, aber nicht in der Excel Datei müssen in eine neun .TXT ausgegeben werden.

Hier haben ich etwas ähnliches gefunden:
Powershell Datei einlesen, Datensätze mit anderer Datei vergleichen und ändern

komme aber leider nicht weiter.

für Tipps wäre ich sehr dankbar.

VG

Content-ID: 372179

Url: https://administrator.de/forum/mit-powershell-den-inhalt-einer-excel-mit-einer-text-datei-abgleichen-372179.html

Ausgedruckt am: 22.12.2024 um 21:12 Uhr

136037
136037 25.04.2018 aktualisiert um 11:04:48 Uhr
Goto Top
Viel zu wenig Infos face-sad.
Wie sieht die Textdatei aus? wie sieht die Mappe aus, wie sind die Daten dort verteilt und was soll dort ausgelesen werden? Oder ist es gar eine CSV??
Wie soll mit der Textdatei verglichen werden? Format, Komma getrennt, oder in Zeilen verteilt?

Fragen über Fragen!

p.s. So ich fahr jetzt mal mit meinem Sofa zu Arbeit irgendwie wird das ja funktionieren, wenn nicht frag ich mal ins Forum :-P ...
Pjordorf
Pjordorf 25.04.2018 um 11:02:51 Uhr
Goto Top
Hallo,

Zitat von @Bommi1961:
komme aber leider nicht weiter.
Und? Sollen wir jetzt rate mal Rosenthal spielen um dein nicht weiter kommen zu Analysieren? Wo kommst du nicht weiter bzw. wodran happert es?

für Tipps wäre ich sehr dankbar.
Morgens immer Duschen.

Gruß,
Peter
136037
136037 25.04.2018 aktualisiert um 11:21:59 Uhr
Goto Top
Zitat von @Pjordorf:
Morgens immer Duschen.
Und das Shampoo bloß nicht vergessen ... face-smile
Bommi1961
Bommi1961 25.04.2018 um 11:29:30 Uhr
Goto Top
Der Inhalt der Text Datei das Ergebnis dieses Befehls "dir /A /B" ausgeführt auf mehrer Verzeichnis. In der Auflistung stehen Verzeichnisnamen.

Die Excel Datei ist eine .xlsm in der ersten Mappe Spalte "A" stehen die Verzeichnisnamen aus der Text Datei oder auch nicht. Und genau darum geht es, wenn neue Verzeichnis dazu gekommen sind müssen diese in die Excel Datei eingetragen werden. Ich würde hier den Umweg über eine 2. Text Datei machen und dann die Verzeichnisnamen in die Excel Liste übertragen.
Es ist nichts mit Komar getrennt.

Beispiel der Text Daten:

. 05-Abnahme

Igor-Pavlov_7-zip_x64_16.04_v2.0
Oracle_Java8_x86_1.5.2_v1.0
Adobe_Flashplayer_x64_27.0.0_v1.0

Die Excel Datei

A B
I-----------
Verzeichnis Name I Test2
I ---------
Igor-Pavlov_7-zip_x64_16.04_v2.0 I
Adobe_Flashplayer_x64_27.0.0_v1.0 I


Also müsste hier jetzt Oracle_Java8_x86_1.5.2_v1.0 ausgegeben werden.
colinardo
colinardo 25.04.2018 aktualisiert um 21:08:03 Uhr
Goto Top
Servus Bommi1961,
irgendwie ziemlich umständlich die Vorgehensweise mit den ganzen Textdateien face-smile.
Das lässt sich alles direkt ohne Umweg über Textdateien abfackeln. Powershell wäre dafür eigentlich auch nicht nötig (VBS/VBA würden reichen) da es aber im Titel steht hier diese Variante:
(Variablen im Kopf anpassen, alle Zeilen im Code kommentiert)

Das Skript liest die Ordnernamen eines Verzeichnises ein und Vergleicht diese mit der Spalte A der Excel Datei und fügt nur neue Namen direkt in die Excel-Datei unten an.
# ====== VARIABLEN ============
# Quelldatei Excel
$quelleExcel = 'D:\test_daten.xlsm'  
# Quellordner dessen Ordnernamen ausgelesen werden
$directory = 'D:\Root'  
# =============================
if ($PSVersionTable.PSVersion.Major -lt 3){write-host "ERROR: Minimum Powershell Version 3.0 is required!" -F Yellow; return}    
# Excel Objekt
$objExcel = New-Object -Com Excel.Application
# Mappe readonly öffnen
$wb = $objExcel.Workbooks.Open($quelleExcel)
# Excel anzeigen wenn gewünscht
# $objExcel.Visible = $true
# Meldungen unterdrücken
$objExcel.DisplayAlerts = $false
# Worksheet Variablen zuweisen
$ws = $wb.Sheets.Item(1)
# letzte belegte Zelle in Spalte A ermitteln
$rnglast = $ws.Cells($ws.Rows.Count,1).End(-4162)
# Daten aller belegten Zeilen in Spalte A holen
$data = $ws.Range("A1:A" + $rnglast.Row).Value()  
# Daten aus Excel-Datei mit den Namen der Ordner vergleichen und nur "singles" ausfiltern 
$newdata = compare @($data) @((gci $directory -Directory -Name)) -PassThru | ?{$_.SideIndicator -eq '=>'}  
if ($newdata.Count -gt 0 ){
    write-host "Füge folgende Zeilen zur Exceldatei hinzu:" -F Green  
    $newdata
    # 2-dim Array erstellen und Daten zuweisen
    $arrData = New-Object 'object[,]' $newdata.Count,1  
    0..($newdata.count-1) | %{
        $arrData[$_,0] = $newdata[$_]
    }
    # neue Daten am Ende von Spalte A ergänzen
    $rngNew = $rnglast.Offset(1,0).Resize($newdata.Count,1)
    $rngNew.NumberFormat = '@'  
    $rngNew.Value() = $arrData
}
# Dokument speichern und schließen
$wb.Save() | out-null
$wb.Close($true) | out-null
# Meldungen wieder einschalten
$objExcel.DisplayAlerts = $true
# Excel schließen
$objExcel.Quit() | out-null
# Ressourcen freigeben
[System.Runtime.InteropServices.Marshal]::ReleaseComObject($objExcel) | out-null
Damit solltest du nun zurecht kommen.

Grüße Uwe
Bommi1961
Bommi1961 25.04.2018 um 12:13:30 Uhr
Goto Top
Hallo Uwe,

bekomme diesen Fehler:
Compare-Object : Cannot bind argument to parameter 'ReferenceObject' because it is null.
At E:\Powershell-Skripe_neu\PS1\Paket_Auswertung.ps1:51 char:20

back-to-top$newdata = compare $data (gci $directory -Directory -Name) -PassThru ...

back-to-top~~~~~

+ CategoryInfo : InvalidData: (face-smile [Compare-Object], ParameterBindingValidationException
+ FullyQualifiedErrorId : ParameterArgumentValidationErrorNullNotAllowed,Microsoft.PowerShell.Commands.Compa
reObjectCommand

hab nach geschaut, in $data sind Daten drin.
colinardo
colinardo 25.04.2018 aktualisiert um 12:15:45 Uhr
Goto Top
Du hast eine ältere Variante kopiert, ich hatte den Parameter aktualisiert, nochmal kopieren. Wurde hier einwandfrei getestet.
Bommi1961
Bommi1961 25.04.2018 um 12:33:29 Uhr
Goto Top
Leider bleibt der Fehler:
Compare-Object : Cannot bind argument to parameter 'ReferenceObject' because it is null.
At E:\Powershell-Skripe_neu\PS1\Paket_Auswertung.ps1:33 char:20

back-to-top$newdata = compare @($data) @((gci $directory -Directory -Name)) -Pas ...

back-to-top~~~~~~~~

+ CategoryInfo : InvalidData: (face-smile [Compare-Object], ParameterBindingValidationException
+ FullyQualifiedErrorId : ParameterArgumentValidationErrorNullNotAllowed,Microsoft.PowerShell.Commands.Compa
reObjectCommand

Zeile 33 sieht so aus:
$newdata = compare @($data) @((gci $directory -Directory -Name)) -PassThru | ?{$_.SideIndicator -eq '=>'}
colinardo
colinardo 25.04.2018 aktualisiert um 12:38:54 Uhr
Goto Top
Welche Excel Version verwendest du? Ich schätze eine ältere die die Value2 Property nicht kennt...
Dann ändere Zeile 21 zum Daten auslesen ab in
$data = $ws.Range("A1:A" + $rnglast.Row).Value()
Funktioniert hier soweit alles einwandfrei in allen möglichen Konstellationen.

Der Fehler muss bei dir oder deiner Beschreibung liegen.
Bommi1961
Bommi1961 25.04.2018 um 12:41:46 Uhr
Goto Top
ich habe Excel 365 Version 1708 Build 8431.2110

der Fehler bleibt leider auch nach dem ändern
colinardo
colinardo 25.04.2018 aktualisiert um 12:47:07 Uhr
Goto Top
Nöp auch mit dieser Version einwandfrei, dein Powershell muss ne Macke haben.

Teamviewer-Support gibt's gern gegen Cash.
Bommi1961
Bommi1961 25.04.2018 um 12:46:25 Uhr
Goto Top
In $data stehen Daten drin.

Ich bekomme eine Meldung "Namenskonflikt" siehe Foto, hier gebe ich einen anderen Excel Dateinamen ein, richtig?
namenskonflikt
colinardo
colinardo 25.04.2018 aktualisiert um 12:49:02 Uhr
Goto Top
OK dann liegts an der Formatierung deiner Zellen und das du spezielle Ordnernamen hast, du solltest sie alle als Text festlegen, oder ich mach dir das im Code.
Bommi1961
Bommi1961 25.04.2018 um 12:50:07 Uhr
Goto Top
wenn ich es mir aussuchen kann, würde ich deinen Code nehmen. face-smile
colinardo
colinardo 25.04.2018 um 12:54:35 Uhr
Goto Top
Ist angepasst.
Bommi1961
Bommi1961 25.04.2018 um 12:59:24 Uhr
Goto Top
ich habe den Quellentext von oben noch mal kopiert. Richtig?

Wenn ja, beide Fehler bleiben.

"Namenskonflikt" und
Compare-Object : Das Argument kann nicht an den Parameter "ReferenceObject"
gebunden werden, da es NULL ist.
In Zeile:36 Zeichen:20

back-to-top$newdata = compare @($data) @((gci $directory -Directory -Name)) -Pas ...

back-to-top~~~~~~~~

+ CategoryInfo : InvalidData: (face-smile [Compare-Object], ParameterBind
ingValidationException
+ FullyQualifiedErrorId : ParameterArgumentValidationErrorNullNotAllowed,M
icrosoft.PowerShell.Commands.CompareObjectCommand
colinardo
colinardo 25.04.2018 aktualisiert um 13:20:38 Uhr
Goto Top
Das liegt an deinem System bzw. deiner Excel-Datei, sorry. S.o. Teamviewer Hinweis. Ich bin raus.
136037
136037 25.04.2018 aktualisiert um 13:04:52 Uhr
Goto Top
Boa bist du ein Brocken, zur Info hier lüppt sein Skript auch Fehlerfrei!
Bommi1961
Bommi1961 25.04.2018 um 13:14:03 Uhr
Goto Top
Danke schon mal für Deine Mühe, ich werde es jetzt noch mal auf anderen System versuchen.

Du hattest ganz am Anfang geschrieben das man nicht ungedient mit Powershell machen muss, was gibt es denn da für eine Alterative?
colinardo
Lösung colinardo 25.04.2018 aktualisiert um 13:24:08 Uhr
Goto Top
Zitat von @Bommi1961:

Danke schon mal für Deine Mühe, ich werde es jetzt noch mal auf anderen System versuchen.
Ich denke es liegt am Aufbau deiner Excel-Datei, die kann ich hier leider nicht prüfen.
Du hattest ganz am Anfang geschrieben das man nicht ungedient mit Powershell machen muss, was gibt es denn da für eine Alterative?
Steht oben, das ganze geht auch per VBA direkt in der Excel-Datei oder per VBS extern aber ohne den genauen Aufbau deiner Excel-Datei bringt dir das auch nichts, das wird dann auch nicht klappen.

Lade die Datei doch mal anonymisiert irgendwo hoch oder wenn dir das nicht zusagt schicke sie mir per Mail (PN Anfrage).
Bommi1961
Bommi1961 25.04.2018 um 15:41:49 Uhr
Goto Top
Ich hab es hin bekommen, hab die Excel Datei einfach noch mal neu erstellt. Läuft klasse, vielen Dank noch mal.

VG Bommi