In einigen Kundenumgebungen stand ich schon oft vor dem Problem, das beim setzen einer Abhängigkeit in den Eigenschaften eines Softwarepaketes die folgende Meldung auftrat:
Das Speichern dieses Paketes ist aufgrund eines Zirkelbezuges nicht möglich.
Diese Fehlermeldung hat nichts mit dem eigentlichen Paket zu tun, das man gerade bearbeitet, sondern wird aufgrund fehlerhafter Abhängigkeitseinträge aus anderen Paketen hervorgerufen. Das Problem ist, das in Paketen mehr als eine Abhängigkeit hinterlegt ist, und zwischen den Abhängigkeiten der Operator fehlt. Durch was diese fehlerhaften Einträge erzeugt werden, kann ich nicht beurteilen, soll aber in der Vergangenheit auch in älteren Versionen schon vorgekommen sein.
Bild 1 (Hier fehlt in dem Bild der Operator (AND | OR) zwischen den Paketen)
Um das Problem jetzt zu beheben, soll man die fehlerhaften Abhängigkeiten löschen, damit man generell wieder Abhängigkeiten setzen kann. Leider erscheint beim Versuch die fehlerhaften Abhängigkeiten über die Empirum Konsole zu löschen die gleiche Fehlermeldung :-).
Also muss man entweder das komplette Paket löschen und wieder neu einbinden, was natürlich nicht immer sehr einfach ist, wenn es in der Administration mehrfach zugewiesen ist, oder man muss direkt in der Empirum Datenbank die fehlerhaften Abhängigkeiten korrigieren.
Bevor wir aber soweit sind, muss man erst mal das, oder die Pakete ermitteln, die fehlerhafte Abhängigkeiten besitzen. In Umgebungen, die nur wenige Pakete verwenden, kann man dies noch über die Empirum Konsole bewältigen und jedes Paket prüfen. In Umgebungen mit mehreren hundert Paketen, wäre dieser Aufwand aber zu groß.
Hierfür habe ich ein PowerShell Skript geschrieben, welches die DDS Datei im User Verzeichnis auf dem Empirum Server prüft und fehlerhafte Requirements mit entsprechenden Paketinformationen in eine Log Datei schreibt.
Powershell Skript: [ddownload id=188]
[php]# Setzen diverser Variablen
$cc_EmpUserPath = "\\$Env:empirumserver\configurator$\User"
$cc_ddsFile = "$cc_EmpUserPath\swdepot.dds"
$cc_ddsOutPut = "$Env:TEMP\swdepot_requirements.log"
$a = [char]34
$cc_output = ""
# Löscht die Ausgabedatei, falls diese schon vorhanden ist
If (test-path $cc_ddsOutPut) {Remove-Item $cc_ddsOutPut}
# Einlesen der DDS in eine Variable
$cc_input_dds = Get-Content $cc_ddsFile
# Anzahl der Zeilen in der DDS
$cc_NumberOfLines = Get-Content $cc_ddsFile | Measure-Object
$cc_NumberOfLinesCount = $cc_NumberOfLines.Count
# Einlesen jeder DDS Zeile. Es wird auf den Eintrag Requirements=* geprüft, ist dieser vorhanden und nicht nur Requirements=, wird die Zeile in die Ausgabedatei geschrieben
# Zähler für die Anzahl der abgearbeiteten Zeilen
$cc_counter = 0
foreach ($cc_line in $cc_input_dds) {
# Errechnung in Prozent der abgearbeiteten Zeilen
$cc_percent = $cc_counter / $cc_NumberOfLinesCount * 100
$cc_percent_int = [int]$cc_percent
# Ersetze " durch § und [ durch ~, damit diese als Vergleichgswert in den IF Abfragen angewendet werden können
$cc_lineReplaced_1 = $cc_line.replace("$a","§")
$cc_lineReplaced = $cc_lineReplaced_1.replace("[","~")
# Zwischenspeichern des Paketnamens
If ($cc_lineReplaced -like "~*"){
$cc_package_name = $cc_line
}
# Zwischenspeichern der Paket ID
If ($cc_lineReplaced -like "SoftwareID=*"){
$cc_package_id = $cc_line
}
# Abfrage welche Zeile Requirements=* beinhaltet
If ($cc_lineReplaced -like "Requirements=*"){
# Grafische Ausgabe
cls
write-host "—————————————————————————————-"
write-host "—– Requirements Check —–"
write-host "—————————————————————————————-"
write-host " "
write-host "$cc_percent_int % von 100% ausgewertet"
write-host " "
write-host " "
write-host "Fehlerhafte Requirements"
write-host " "
write-host $cc_output
# Abfrage welche Zeile nicht nur Requirements= beinhaltet
If ($cc_lineReplaced -ne "Requirements="){
# Abfrage welche Requirements fehlerhafte Einträge haben
If ($cc_lineReplaced -like "*§§*" -OR $cc_lineReplaced -like "*§! §*"){
# Ersetze " durch § und [ durch ~
$cc_lineReplaced_1 = $cc_line.replace("§","$a")
$cc_lineReplaced = $cc_lineReplaced_1.replace("~","[")
# Ausgabe und schreiben der fehlerhaften Pakete in die Ausgabedatei
$cc_output = $cc_output + "$cc_package_name`r`n$cc_package_id`r`n$cc_lineReplaced`r`n`r`n"
}
}
}
$cc_output | out-file -Encoding Ascii $cc_ddsOutPut
$cc_counter++
}[/php]
Geprüft werden zwei Arten von fehlerhaften Requirement Einträgen in der DDS. Zum einen Pakete ohne Operator zwischen zwei Abhängigkeiten, und zum anderen Pakete ohne Operator zwischen zwei Abhängigkeiten, die mit NOT (NOT = ! in der DDS) markiert sind.
Requirement Packages mit einem fehlenden Operator dazwischen
Requirements=“Test\Anwendung\1.0„“Test\Anwendung\2.0″
Requirement Packages mit einem NOT Flag (in der DDS ist NOT = !) und einem fehlenden Operator dazwischen
Requirements=! „Test\Anwendung\1.0„! „Test\Anwendung\2.0″
In dem PowerShell Skript werden die rot markierten Zeichenfolgen in den Requirements Einträgen der DDS geprüft, und das Ergebnis im %TEMP% Verzeichnis des Anwenders der das PowerShell Skript ausführt in die Datei swdepot_requirements.log geschrieben. Ebenfalls wird die SoftwareID des Paketes, die man im weiteren Verlauf noch braucht, ausgelesen und in die Log Datei geschrieben.
Beispiel Log Datei:
[Test\Anwendung\3.0] SoftwareID=DCD0C921-A2CE-493B-9243-111111111111 Requirements=! “ Test\Anwendung\1.0″! „Test\Anwendung\2.0“
Die folgenden Schritte nur nach Rücksprache mit dem MX42 Support durchführen!
Um die Abhängigkeit jetzt korrigieren, und einen Operator zwischen zwei Pakete einfügen zu können, sucht man in der Empirum Datenbank in der Tabelle SwDependencies alle Einträge anhand der SoftwareID (Spalte 2) heraus, die zu dem Paket gehören, das die fehlerhaften Abhängigkeiten beinhaltet.
Die erste Zeile bezieht sich auf den ersten Paketeintrag unter Abhängigkeiten und die zweite Zeile auf den zweiten Paketeintrag unter Abhängigkeiten (Siehe Bild 1). Die Abhängigen Pakete sollte man sicherheitshalber über die DepSoftwareID gegenprüfen (kann man über die DDS abgleichen).
In der ANDOR Spalte der ersten Zeile ist, wie auch im Bild 1 zu sehen, kein Operator für die Abhängigkeit gesetzt. Hier kann man jetzt die Datenbank manipulieren und einen Operator einfügen 1 = AND und 2 = OR.
Dies muss man für alle Pakete, die fehlerhafte Abhängigkeiten besitzen durchführen.
Super Eintrag, hat mir geholfen das Problem zu lösen!
Vielen Dank!