Hallo Rudi,
aktuell parst du die Def von structure-Devices mit split und einem bestimmten Pattern, das führt dazu, dass z.B.
def structure_dev structure device1 device2
device3
device4
leider zu
$split = 'device1';
$VAR2 = 'device2
device3
';
$VAR3 = 'device4
';
geparst wird. Ich hätte aber eher
# parseParams
$params = [
'device1',
'device2',
'device3',
'device4'
];
erwartet. Siehst du eine Chance das z.B. auf parseParams umzustellen?
Warum ist die "kaputte" def-Version notwendig?
Zitat von: rudolfkoenig am 23 Februar 2021, 15:53:51
Warum ist die "kaputte" def-Version notwendig?
structures mit mehr als eine kleine handvoll kurz benannter Devices werden irgendwann sehr unübersichtlich zu lesen und damit auch zu definieren - mit insbesondere Newlines kann man so eine Def lesbarer machen.
Außerdem haben wir aktuell im Prinzip grob zwei Herangehensweisen, was das Def-Parameter-Parsing angeht: Einmal die auch von dir in structure verwendete Version, die keine Newlines etc. unterstützt und die, die parseParams nehmen, wie es ja auch in DevelopmentModuleAPI beschrieben ist und sogar parameterisierbar für Def, Get und Set eingeschaltet werden kann - was bedeutet, dass sich die Art wie man die Def formatieren darf, je nach Modul unterscheidet und ich hoffe du stimmst mir zu, dass das kein guter Zustand ist.
Ich habe jetzt den ueberkomplizierten split-Regexp vereinfacht, damit sollte dein Eingangsbeispiel auch funktionieren.
parseParams finde ich fuer diese Stelle persoenlich zu abgefahren.
Wenn ich das richtig sehe, erlaubte die alte Variante
my @a = split("[ \t][ \t]*", $def);
mehrere Leerzeichen / Tabs hintereinander als Trenner zwischen zwei Geräten. Die neue Variante
my @a = split(/\s/, $def);
trennt dagegen nach jedem einzelnen Whitespace, was Probleme bereiten könnte, wenn mehr als ein Whitespace zwischen zwei Gerätenamen steht. Oder irre ich mich da? Ich hätte es so geschrieben:
my @a = split(/\s+/, $def);
ZitatOder irre ich mich da?
Ich gehe davon aus.
Ich habe mit den relevanten Code noch einmal angesehen:
125 my @a = split(/\s/, $def);
126 my $devname = shift(@a);
127 my $modname = shift(@a);
128 my $stype = shift(@a);
129
130 my (%list, @list);
131 my $aList = "$stype ${stype}_map structexclude";
132 foreach my $a (@a) {
133 foreach my $d (devspec2array($a)) {
134 next if(!$defs{$d} || $list{$d});
135 $hash->{DEVSPECDEF} = 1 if($a ne $d);
136 $list{$d} = 1;
137 push(@list, $d);
138 next if($c && $c->{$d});
139 addToDevAttrList($d, $aList);
140 structAdd($d, $aList) if($defs{$d} && $defs{$d}{TYPE} eq "structure");
141 }
142 }
Und einmal getestet, was denn split tut:
split(/\s/, "a b");
=> ("a", "", "b")
split(/\s+/, "a b");
=> ("a", "b")
So wie es aussieht, erzeugt split in Zeile 125 tatsächlich leere Elemente, wenn mehr als ein Whitespace als Trennzeichen vorkommt. Aber die werden wohl in Zeile 133 / 134 ausgefiltert, wenn devspec2array keine passenden Devices findet, weshalb sie nicht stören.
Danke fuer den Hinweis.
Ich habe es auf \s+ geaendert, verursacht etwas weniger Last fuer den Prozessor und ist einfacher beim Debuggen.