-(require 'apropos)
-(require 'regexp-opt)
+;;
+;; nagios-mode, an Emacs mode for Nagios <http://www.nagios.org/>
+;; configuration files.
+;;
+;; Copyright Michael Orlitzky
+;;
+;; http://michael.orlitzky.com/
+;;
+;; This program is free software: you can redistribute it and/or modify
+;; it under the terms of the GNU General Public License as published by
+;; the Free Software Foundation, either version 3 of the License, or
+;; (at your option) any later version.
+;;
+;; This program is distributed in the hope that it will be useful,
+;; but WITHOUT ANY WARRANTY; without even the implied warranty of
+;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+;; GNU General Public License for more details.
+;;
+;; http://www.fsf.org/licensing/licenses/gpl.html
+;;
+
(require 'font-lock)
+(require 'regexp-opt)
-;;;;;;;;;;;;;;;;;;;;;;
-;; CUSTOM VARIABLES ;;
-;;;;;;;;;;;;;;;;;;;;;;
+;; Custom Variables
(defcustom nagios-indent-level 2
- "*Number of spaces in one indentation (tab)."
+ "Number of spaces in one indentation (tab)."
:type 'integer :group 'nagios
)
-;;;;;;;;;;;;;;;;;;;;;;;;;;;
-;; INDENTATION FUNCTIONS ;;
-;;;;;;;;;;;;;;;;;;;;;;;;;;;
+;; Indentation Voodoo
(defun nagios-indent-line(&optional flag)
"Indents a line, taking nesting into account."
(defun nagios-in-block()
"Determine if the point is inside of a {} block."
+
(setq pos (point))
;; Get the position of the last opening and closing braces, with
-;;;;;;;;;;;;
-;; KEYMAP ;;
-;;;;;;;;;;;;
+;; Keymaps
(defun nagios-insert-right-brace-and-indent()
"Insert a '}' character, and indent the line."
)
-
(defvar nagios-mode-map()
"Keymap used in nagios mode.")
(when (not nagios-mode-map)
(setq nagios-mode-map (make-sparse-keymap))
- (define-key nagios-mode-map (read-kbd-macro "}") 'nagios-insert-right-brace-and-indent)
+ (define-key nagios-mode-map
+ (read-kbd-macro "}")
+ 'nagios-insert-right-brace-and-indent)
)
-;;;;;;;;;;;;;;;;;;;;;;;;;;;;
-;; REGEXP TRANSFORMATIONS ;;
-;;;;;;;;;;;;;;;;;;;;;;;;;;;;
+;; Regular Expression Transformations
(defun regexp-word(regexp)
"Takes a regular expression as an argument, and adds the word boundary condition to the beginning and end of it."
- (concat "\\<\\(" regexp "\\)\\>")
+ ;; I consider neither a hyphen nor an underscore to be a word
+ ;; boundary for the purpose of syntax highlighting.
+ (concat "[^_-]\\<\\(" regexp "\\)\\>[^_-]")
)
-
(defun regexp-alt-raw(element-list)
"Takes a list of elements, and returns the string '\\(element1\\|element2...\\)'"
-
+
+ ;; This is necessary since regexp-opt does not accept regular
+ ;; expressions as arguments. We use regexp-opt when we can, of
+ ;; course.
+
(let ((regexp "\\("))
(mapcar (lambda(elem)
(setq regexp (concat regexp "\\(" elem "\\)" "\\|")))
-;;;;;;;;;;;;;;;;;;;;;
-;; SYNTAX PATTERNS ;;
-;;;;;;;;;;;;;;;;;;;;;
+;; Syntax Highlighting Patterns
(defconst nagios-comments
(eval-when-compile
)
-
(defconst nagios-directives
(eval-when-compile
(regexp-opt
'("active_checks_enabled" "address" "alias" "check_command"
- "check_freshness" "check_period" "checks_enabled" "command_line"
- "command_name" "contact_groups" "contact_name" "contactgroup_name"
- "dependent_host_name" "dependent_service_description"
- "email" "event_handler" "event_handler_enabled"
- "execution_failure_criteria" "first_notification"
- "flap_detection_enabled" "freshness_threshold"
- "friday" "high_flap_threshold" "host_name"
- "host_notification_commands"
- "host_notification_options"
- "host_notification_period" "hostgroup_name"
- "is_volatile" "last_notification"
+ "check_freshness" "check_interval" "check_period" "checks_enabled"
+ "command_line" "command_name" "contact_groups" "contact_name"
+ "contactgroup_name" "dependent_host_name"
+ "dependent_service_description" "email" "event_handler"
+ "event_handler_enabled" "execution_failure_criteria"
+ "failure_prediction_enabled" "first_notification"
+ "flap_detection_enabled" "freshness_threshold" "friday"
+ "high_flap_threshold" "host_name" "host_notification_commands"
+ "host_notification_options" "host_notification_period"
+ "hostgroup_name" "hostgroups" "is_volatile" "last_notification"
"low_flap_threshold" "max_check_attempts"
"members" "monday" "normal_check_interval"
"notification_failure_criteria"
"parents" "passive_checks_enabled"
"process_perf_data" "retain_nonstatus_information"
"retain_status_information" "retry_check_interval"
- "saturday" "service_description"
+ "retry_interval" "saturday" "service_description"
"service_notification_commands"
"service_notification_options"
"service_notification_period" "stalking_options"
- "sunday" "thursday" "timeperiod_name" "tuesday" "wednesday")))
+ "sunday" "thursday" "timeperiod_name" "tuesday" "wednesday") t))
)
-(defvar nagios-macros
+(defconst nagios-macros
(eval-when-compile
(regexp-alt-raw
'("\\$CONTACT\\(NAME\\|ALIAS\\|EMAIL\\|PAGER\\)\\$"
-(defvar nagios-definitions
+(defconst nagios-definitions
(eval-when-compile
(regexp-alt-raw
'("define +\\(host\\|service\\|timeperiod\\|contact\\|command\\)"
-(defvar nagios-special
+(defconst nagios-special
(eval-when-compile
(regexp-opt
- '("name" "register" "use")))
+ '("name" "register" "use") t))
)
-;;;;;;;;;;;;;;;;;;;;;;;;
-;; FONT LOCK VARIABLE ;;
-;;;;;;;;;;;;;;;;;;;;;;;;
+;; The One True Font Locking Variable
(defvar nagios-font-lock-keywords
(list
- (cons nagios-comments font-lock-comment-face)
+
+ ;; This first bit of ugliness allows us to override any
+ ;; other font-locking with the comment font.
+ (cons nagios-comments '(0 font-lock-comment-delimiter-face t))
+
+ ;; The rest just map regular expressions to font faces.
(cons (regexp-word nagios-directives) font-lock-variable-name-face)
- (cons (regexp-word nagios-macros) font-lock-doc-face)
+ (cons (regexp-word nagios-macros) font-lock-constant-face)
(cons (regexp-word nagios-definitions) font-lock-function-name-face)
(cons (regexp-word nagios-special) font-lock-keyword-face))
-;;;;;;;;;;;;;;;;;;;;;;;;
-;; MAIN MODE FUNCTION ;;
-;;;;;;;;;;;;;;;;;;;;;;;;
+;; Main Mode Function
(defun nagios-mode()
"Major mode for editing Nagios configuration files."
(interactive)
- ; Initializing
+ ;; Initializing. This is actually important to cover
+ ;; up some Emacs stupidity. Font locking won't occur
+ ;; without it.
(kill-all-local-variables)
- ; Setting up indentation handling
+ ;; Set up indentation handling using the functions
+ ;; defined earlier.
(make-local-variable 'indent-line-function)
(setq indent-line-function 'nagios-indent-line)
- ; Setting up font-locking
+ ;; Configure font locking. Set the defaults to something
+ ;; sensible, defined earlier.
(make-local-variable 'font-lock-defaults)
- (setq font-lock-defaults '(nagios-font-lock-keywords nil t nil nil))
-
-
- ; Setting up syntax recognition
- (make-local-variable 'comment-start)
- (make-local-variable 'comment-end)
- (make-local-variable 'comment-start-skip)
-
- (setq comment-start "# ")
- (setq comment-end "")
- (setq comment-start-skip nagios-comments)
-
+ (setq font-lock-defaults '(nagios-font-lock-keywords nil t))
;; Keyboard Mapping
(use-local-map nagios-mode-map)
-
-
- ; Setting up syntax table
- (modify-syntax-entry ?* ". 23")
- (modify-syntax-entry ?/ ". 14")
- ; Final stuff, then we're done
+ ;; Rock and roll.
(setq mode-name "nagios"
major-mode 'nagios-mode)
-
+
+ ;; I don't /think/ I need to define this before attempting
+ ;; to run it. Users can define it if they want.
(run-hooks 'nagios-mode-hook)
)