Guest User

Untitled

a guest
Jul 22nd, 2018
146
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 9.30 KB | None | 0 0
  1. #!/usr/bin/php
  2. <?php
  3.  
  4. $progname = "check_mssql";
  5. $version = "0.6.6";
  6.  
  7. // Parse the command line options
  8. for ($i = 1; $i < $_SERVER['argc']; $i++) {
  9. $arg = $_SERVER["argv"][$i];
  10. switch($arg) {
  11. case '-h':
  12. case '--help':
  13. help();
  14. break;
  15.  
  16. case '-V':
  17. case '--version':
  18. version();
  19. break;
  20.  
  21. case '-H':
  22. case '--hostname':
  23. $db_host = check_command_line_option($_SERVER["argv"][$i], $i);
  24. break;
  25.  
  26. case '-u':
  27. case '-U':
  28. case '--username':
  29. $db_user = check_command_line_option($_SERVER["argv"][$i], $i);
  30. break;
  31.  
  32. case '-P':
  33. case '--password':
  34. $db_pass = check_command_line_option($_SERVER["argv"][$i], $i);
  35. break;
  36.  
  37. case '-p':
  38. case '--port':
  39. $db_port = check_command_line_option($_SERVER["argv"][$i], $i);
  40. break;
  41.  
  42. case '-d':
  43. case '--database':
  44. $db_name = check_command_line_option($_SERVER["argv"][$i], $i);
  45. break;
  46.  
  47. case '-q':
  48. case '--query':
  49. $query = check_command_line_option($_SERVER["argv"][$i], $i);
  50. $querytype = "query";
  51. break;
  52.  
  53. case '-s':
  54. case '--storedproc':
  55. $storedproc = check_command_line_option($_SERVER["argv"][$i], $i);
  56. $querytype = "stored procedure";
  57. break;
  58.  
  59. case '-r':
  60. case '--result':
  61. $expected_result = check_command_line_option($_SERVER["argv"][$i], $i);
  62. break;
  63.  
  64. case '-w':
  65. case '--warning':
  66. $warning = check_command_line_option($_SERVER["argv"][$i], $i);
  67. break;
  68.  
  69. case '-c':
  70. case '--critical':
  71. $critical = check_command_line_option($_SERVER["argv"][$i], $i);
  72. break;
  73. }
  74. }
  75.  
  76. // Error out if mssql support is not present.
  77. if (!function_exists('mssql_connect')) {
  78. print "UNKNOWN: MSSQL support is not installed on this server.\n";
  79. exit(3);
  80. }
  81.  
  82. // If no options are set, display the help
  83. if ($_SERVER['argc'] == 1) {
  84. print "$progname: Could not parse arguments\n";
  85. usage();
  86. exit;
  87. }
  88.  
  89. // Determine if the query is a SQL file or a text query
  90. if (isset($query)) {
  91. if (file_exists($query)) {
  92. $query = file_get_contents($query);
  93. }
  94. }
  95.  
  96. // Add "exec" to the beginning of the stored proc if it doesnt exist.
  97. if (isset($storedproc)) {
  98. if (substr($storedproc, 0, 5) != "exec ") {
  99. $storedproc = "exec $storedproc";
  100. }
  101. }
  102.  
  103. // Do not allow both -q and -s
  104. if (isset($query) && isset($storedproc)) {
  105. print "UNKNOWN: The -q and -s switches are mutually exclusive. You may not select both.\n";
  106. exit(3);
  107. }
  108.  
  109. // -r demands -q and -q demands -r
  110. if (isset($expected_result) && !isset($query)) {
  111. print "UNKNOWN: The -r switch requires the -q switch. Please specify a query.\n";
  112. exit(3);
  113. }
  114.  
  115. // Validate the hostname
  116. if (isset($db_host)) {
  117. if (!preg_match("/^([a-zA-Z0-9-]+[\.])+([a-zA-Z0-9]+)$/", $db_host)) {
  118. print "UNKNOWN: Invalid characters in the hostname.\n";
  119. exit(3);
  120. }
  121. } else {
  122. print "UNKNOWN: The required hostname field is missing.\n";
  123. exit(3);
  124. }
  125.  
  126. // Validate the port
  127. if (isset($db_port)) {
  128. if (!preg_match("/^([0-9]{4,5})$/", $db_port)) {
  129. print "UNKNOWN: The port field should be numeric and in the range 1000-65535.\n";
  130. exit(3);
  131. }
  132. } else {
  133. $db_port = 1433;
  134. }
  135.  
  136. // Validate the username
  137. if (isset($db_user)) {
  138. if (!preg_match("/^[a-zA-Z0-9-]{2,32}$/", $db_user)) {
  139. print "UNKNOWN: Invalid characters in the username.\n";
  140. exit(3);
  141. }
  142. } else {
  143. print "UNKNOWN: You must specify a username for this DB connection.\n";
  144. exit(3);
  145. }
  146.  
  147. // Validate the password
  148. if (empty($db_pass)) {
  149. print "UNKNOWN: You must specify a password for this DB connection.\n";
  150. exit(3);
  151. }
  152.  
  153. // Validate the warning threshold
  154. if (isset($warning)) {
  155. if (!preg_match("/^([0-9]+){1,3}$/", $warning)) {
  156. print "UNKNOWN: Invalid warning threshold.\n";
  157. exit(3);
  158. }
  159. } else {
  160. $warning = 2;
  161. }
  162.  
  163. // Validate the critical threshold
  164. if (isset($critical)) {
  165. if (!preg_match("/^([0-9]+){1,3}$/", $critical)) {
  166. print "UNKNOWN: Invalid critical threshold.\n";
  167. exit(3);
  168. }
  169. } else {
  170. $critical = 5;
  171. }
  172.  
  173. // Is warning greater than critical?
  174. if ($warning > $critical) {
  175. $exit_code = 3;
  176. $output_msg = "UNKNOWN: warning value should be lower than critical value.\n";
  177. display_output($exit_code, $output_msg);
  178. }
  179.  
  180. // Attempt to connect to the server
  181. $time_start = microtime(true);
  182. if (!$connection = @mssql_connect("$db_host:$db_port", $db_user, $db_pass)) {
  183. $exit_code = 2;
  184. $output_msg = "CRITICAL: Could not connect to $db_host as $db_user.";
  185. display_output($exit_code, $output_msg);
  186. } else {
  187. $time_end = microtime(true);
  188. $query_duration = round(($time_end - $time_start), 6);
  189. // Exit now if no query or stored procedure is specified
  190. if (empty($storedproc) && empty($query)) {
  191. $output_msg = "Connect time=$query_duration seconds.\n";
  192. process_results($query_duration, $warning, $critical, $output_msg);
  193. }
  194. }
  195.  
  196. if (empty($db_name)) {
  197. $exit_code = 3;
  198. $output_msg = "UNKNOWN: You must specify a database with the -q or -s switches.\n";
  199. display_output($exit_code, $output_msg);
  200. }
  201.  
  202. // Attempt to select the database
  203. if(!@mssql_select_db($db_name, $connection)) {
  204. $exit_code = 2;
  205. $output_msg = "CRITICAL: Could not connect to $db_name on $db_host.\n";
  206. display_output($exit_code, $output_msg);
  207. }
  208.  
  209. // Attempt to execute the query/stored procedure
  210. $time_start = microtime(true);
  211. if (!$query_data = @mssql_query("$query")) {
  212. $exit_code = 2;
  213. $output_msg = "CRITICAL: Could not execute the $querytype.\n";
  214. display_output($exit_code, $output_msg);
  215. } else {
  216. $time_end = microtime(true);
  217. $query_duration = round(($time_end - $time_start), 6);
  218. $output_msg = "Query duration=$query_duration seconds.\n";
  219. }
  220.  
  221. if ($querytype == "query" && !empty($expected_result)) {
  222. if (mssql_num_rows($query_data) > 0 ) {
  223. while ($row = mssql_fetch_row($query_data)) {
  224. $query_result = $row[0];
  225. }
  226. }
  227. if ($query_result == $expected_result) {
  228. $output_msg = "Query results matched, query duration=$query_duration seconds.\n";
  229. } else {
  230. $exit_code = 2;
  231. $output_msg = "CRITICAL: Query expected \"$expected_result\" but got \"$query_result\".\n";
  232. display_output($exit_code, $output_msg);
  233. }
  234. }
  235. process_results($query_duration, $warning, $critical, $output_msg);
  236.  
  237. //-----------//
  238. // Functions //
  239. //-----------//
  240.  
  241. // Function to validate a command line option
  242. function check_command_line_option($option, $i) {
  243. // If the option requires an argument but one isn't sent, bail out
  244. $next_offset = $i + 1;
  245. if (!isset($_SERVER['argv'][$next_offset]) || substr($_SERVER['argv'][$next_offset], 0, 1) == "-") {
  246. print "UNKNOWN: The \"$option\" option requires a value.\n";
  247. exit(3);
  248. } else {
  249. ${$option} = $_SERVER['argv'][++$i];
  250. return ${$option};
  251. }
  252. }
  253.  
  254. // Function to process the results
  255. function process_results($query_duration, $warning, $critical, $output_msg) {
  256. if ($query_duration > $critical) {
  257. $state = "CRITICAL";
  258. $exit_code = 2;
  259. } elseif ($query_duration > $warning) {
  260. $state = "WARNING";
  261. $exit_code = 1;
  262. } else {
  263. $state = "OK";
  264. $exit_code = 0;
  265. }
  266. $output_msg = "$state: $output_msg";
  267. display_output($exit_code, $output_msg);
  268. }
  269.  
  270. // Function to display the output
  271. function display_output($exit_code, $output_msg) {
  272. print $output_msg;
  273. exit($exit_code);
  274. }
  275.  
  276. // Function to display usage information
  277. function usage() {
  278. global $progname, $version;
  279. print <<<EOF
  280. Usage: $progname -H <hostname> --username <username> --password <password>
  281. [--port <port>] [--database <database>] [--query <"text">|filename]
  282. [--storeproc <"text">] [--result <text>] [--warning <warn time>]
  283. [--critical <critical time>] [--help] [--version]
  284.  
  285. EOF;
  286. }
  287.  
  288. // Function to display copyright information
  289. function copyright() {
  290. global $progname, $version;
  291. print <<<EOF
  292. Copyright (c) 2008 Gary Danko (gdanko@gmail.com)
  293.  
  294. This plugin checks various aspect of an MSSQL server. It will also
  295. execute queries or stored procedures and return results based on
  296. query execution times and expected query results.
  297.  
  298. EOF;
  299. }
  300.  
  301. // Function to display detailed help
  302. function help() {
  303. global $progname, $version;
  304. print "$progname, $version\n";
  305. copyright();
  306. print <<<EOF
  307.  
  308. Options:
  309. -h, --help
  310. Print detailed help screen.
  311. -V, --version
  312. Print version information.
  313. -H, --hostname
  314. Hostname of the MSSQL server.
  315. -U, --username
  316. Username to use when logging into the MSSQL server.
  317. -P, --password
  318. Password to use when logging into the MSSQL server.
  319. -p, --port
  320. Optional MSSQL server port. (Default is 1433).
  321. -d, --database
  322. Optional DB name to connect to.
  323. -q, --query
  324. Optional query or SQL file to execute against the MSSQL server.
  325. -s, --storedproc
  326. Optional stored procedure to execute against the MSSQL server.
  327. -r, --result
  328. Expected result from the specified query, requires -q. The query
  329. pulls only the first row for comparison, so you should limit
  330. yourself to small, simple queries.
  331. -w, --warning
  332. Warning threshold in seconds on duration of check (Default is 2).
  333. -c, --critical
  334. Critical threshold in seconds on duration of check (Default is 5).
  335.  
  336. Example: $progname -H myserver -U myuser -P mypass -q /tmp/query.sql -w 2 -c 5
  337. Example: $progname -H myserver -U myuser -P mypass -q "select count(*) from mytable" -r "632" -w 2 -c 5
  338. Send any questions regarding this utility to gdanko@gmail.com.
  339.  
  340. EOF;
  341. exit(0);
  342. }
  343.  
  344. // Function to display version information
  345. function version() {
  346. global $version;
  347. print <<<EOF
  348. $version
  349.  
  350. EOF;
  351. exit(0);
  352. }
  353. ?>
Add Comment
Please, Sign In to add comment