Objekt-Vererbung in den Template-basierten Konfigurationsdaten


Einleitung

Eine der primären Motivationen den Support für Template-basierte Konfigurationsdaten zu implementieren, war die Fähigkeit es den Objekt-Definitionen zu erlauben verschiedene Eigenschaften von anderen Objekt-Definitionen vererbet zu bekommen. Die Vererbung von Objekt-Eigenschaften wurde dadurch möglich, dass Nagios die Konfigurations-Dateien rekursiv verarbeiten kann.

Dieses Kapitel der Dokumentation versucht diese Rekursion und die Vererbung unter Objekt-Definitionen zu erklären, wenn der Support für Template-basierte Objekt-Konfigurationsdaten in Nagios kompiliert wurde. Es sollte beachtet werden, dass die Rekursions- und Vererbungs-Prinzipien, die hier beschrieben werden, auch auf die Template-basierten erweiterten Informationsdaten gilt.

Falls immernoch Verwirrung über die Funktion der Rekursion und Verarbeitung herrscht, nachdem Sie das gelesen haben, sollte man einen Blick auf die Template-basierten Konfigurationsdateien werfen, die mit dem Quellcode als Beispiel mitgeliefert werden. Falls dies auch nicht hilft, sollte man einfach eine eMail mit einer detailierten Beischreibung des Problems an die nagios-users-Mailinglist.

Grundlagen

Es gibt drei Variablen in allen Objekt-Definitionen, die die Rekursion und Vererbung beeinflussen. Es sind die folgenden...

	define IrgendeinObjektTyp{
		
		objekt-spezifische Variablen ...
		
		name		Template_Name
		use		Name_des_Templates_das_seine_Objekte_diesem_Objekt_vererbt
		register	[0/1]
		}

Die erste Variable ist name. Dies ist nur ein "Template"-Name, der in anderen Objekt-Definitionen als Vererbungs-Referenz genutzt wird, so das dieses Template seine Eigenschaften und Werte vererben kann. Namen von Templates müssen unter den Objekten des gleichen Typs einmalig sein, man kann also z.B. nicht zwei Host-Definitionen den gleichen Template-Namen geben.

Die zweite Variable heisst use. Mit ihr wird das Template-Objekt angegeben, von dem Eigenschaften geerbt werden sollen. Der Name, der unter dieser Variable angegeben wird, muss in einer anderen Objekt-Definition durch die name-Variable als Template-Name angegeben wurde.

Die dritte Variable heisst register. Diese Variable gibt an, ob eine Objekt-Definition in Nagios "registriert" werden soll, oder nicht. Als Standard werden alle Objekt-Definitionen registriert. Falls eine nur teilweise vollständige Objekt-Definition als ein Template zur Verfügung stehen soll, sollte man verhindern können, dass das Objekt registriert wird (ein Beispiel wird später gezeigt).
Die Werte sind: 0 = diese Objekt-Definition NICHT registrieren, 1 = diese Objekt-Definition registrieren (der Standard).

Lokale Variablen vs. vererbte Variablen

Eine wichtige Sache die man bei der Benutzung von vererbten Variablen verstehen muss, ist das "lokale" Variablen immer Vorrang vor vererbten Variablen geniessen. Man werfe einen Blick auf die folgenden Beispiele zweier Host-Definitionen (nicht alle notwendigen Variablen werden hier gezeigt):

	define host{
		host_name		bighost1
		check_command		check-host-alive
		notification_options	d,u,r
		max_check_attempts	5
		name			hosttemplate1
		}

	define host{
		host_name		bighost2
		max_check_attempts	3
		use			hosttemplate1
		}

Man beachte, dass die Definition für Host bighost1 den Wert hosttemplate1 als sein Template-Namen enthält. Die Definition von Host bighost2 benutzt dann die Definition von bighost1 als ihr Template-Objekt. Verarbeitet Nagios die Definitionsdaten, ist die Definition von bighost2 gleich der folgenden Definition:

	define host{
		host_name		bighost2
		check_command		check-host-alive
		notification_options	d,u,r
		max_check_attempts	3
		}

Man erkennt, dass die check_command- und notification_options-Variablen von dem Template-Objekt - wie in bighost1 definiert - geerbt wurden. Die host_name und max_check_attempts-Variablen wurden nicht vom Template-Objekt geerbt, da sie lokal definiert wurden. Wie bereits erläutert, lokal definierte Variablen überschreiben immer die Variablen, die von einem Template-Objekt geerbt wurden. Ein relativ einfaches Konzept.

Verkettete Vererbungen

Objekte können ihre Eigenschaften und Variablen über verschiedene Stufen von Template-Objekten vererbt bekommen.
Hier ein Beispiel...

	define host{
		host_name		bighost1
		check_command		check-host-alive
		notification_options	d,u,r
		max_check_attempts	5
		name			hosttemplate1
		}

	define host{
		host_name		bighost2
		max_check_attempts	3
		use			hosttemplate1
		name			hosttemplate2
		}

	define host{
		host_name		bighost3
		use			hosttemplate2
		}

Man erkennt dass Host bighost3 seine Variablen aus der Definition von bighost2 vererbt bekommt, welcher wiederum seine Werte aus der Definition von Host bighost1 vererbt bekommt hat. Verarbeitet Nagios die Konfigurationsdaten, entsprechen die eben gemachten Konfigurationen den folgenden Host-Definitionen.

	define host{
		host_name		bighost1
		check_command		check-host-alive
		notification_options	d,u,r
		max_check_attempts	5
		}

	define host{
		host_name		bighost2
		check_command		check-host-alive
		notification_options	d,u,r
		max_check_attempts	3
		}

	define host{
		host_name		bighost3
		check_command		check-host-alive
		notification_options	d,u,r
		max_check_attempts	3
		}

Es gibt keinerlei Beschränkung darin, über wie viele Stufen man Objekt-Eigenschaften vererbt. Man sollte sich selbst eine Beschränkung setzen, um ein späteres Chaos und den fehlenden Überblick über die Konfigurationsdaten zu verhindern.

Unvollständige Objekt-Definitionen als Template nutzen

Es ist möglich unvollständige Objekt-Definitionen anderen Objekt-Definitionen als Template zur Verfügung zu stellen. Mit "unvollständigen" Definitionen meinen wir Definitionen die nicht alle benötigten Variablen für eine Objekt-Überwachung besitzen. Es klingt vielleicht seltsam unvollständige Definitionen als Template zu benutzen, aber wir würden dieses sogar empfehlen. Warum? Sie können vielen anderen Objekt-Definitionen viele Standard-Werte vorgeben und so die Konfiguration um einiges vereinfachen.
Es folgt ein kleines Beispiel:

	define host{
		check_command		check-host-alive
		notification_options	d,u,r
		max_check_attempts	5
		name			generichosttemplate
		register			0
		}

	define host{
		host_name		bighost1
		address			192.168.1.3
		use			generichosthosttemplate
		}

	define host{
		host_name		bighost2
		address			192.168.1.4
		use			generichosthosttemplate
		}

Man muss beachten, dass die erste Host-Definition unvollständig ist, da die benötigte host_name-Variable fehlt. Diese muss allerdings nicht angegeben werden, da diese Definition als generisches Host-Template gelten soll. Um zu verhindern, dass diese Definition von Nagios als normale Host-Definition angesehen wird, muss die register-Variable auf "0" gesetzt werden.

Die Definition von Host bighost1 und bighost2 erben ihre Variablen vom generischen Host-Definition. Die einzige Variable die von einer lokalen Variable in den Host-Definitionen bighost1 und bighost2 überschrieben wird, ist die address-Variable. Das heisst, dass beide Hosts genau die gleichen Eigenschaften besitzen, ausser den host_name- und address-Variablen. Würde Nagios die Konfigurationsdaten aus diesem Beispiel verarbeiten, sehen die resultierenden Host-Definitionen aus wie die folgenden:

	define host{
		host_name		bighost1
		address			192.168.1.3
		check_command		check-host-alive
		notification_options	d,u,r
		max_check_attempts	5
		}

	define host{
		host_name		bighost2
		address			192.168.1.4
		check_command		check-host-alive
		notification_options	d,u,r
		max_check_attempts	5
		}

Vor allem spart man sich mit der Benutzung von Template-basierten Definitionen für Standard-Variablen viel Tiparbeit. Ausserdem erspart es einem viel Kopfschmerzen, wenn man später die Standard-Variablen für eine Vielzahl von Hosts ändern will.