1<?php 2/* Icinga Web 2 | (c) 2016 Icinga Development Team | GPLv2+ */ 3 4namespace Icinga\Module\Monitoring\Command\Renderer; 5 6use Icinga\Module\Monitoring\Command\IcingaApiCommand; 7use Icinga\Module\Monitoring\Command\Instance\ToggleInstanceFeatureCommand; 8use Icinga\Module\Monitoring\Command\Object\AcknowledgeProblemCommand; 9use Icinga\Module\Monitoring\Command\Object\AddCommentCommand; 10use Icinga\Module\Monitoring\Command\Object\DeleteCommentCommand; 11use Icinga\Module\Monitoring\Command\Object\DeleteDowntimeCommand; 12use Icinga\Module\Monitoring\Command\Object\ProcessCheckResultCommand; 13use Icinga\Module\Monitoring\Command\Object\PropagateHostDowntimeCommand; 14use Icinga\Module\Monitoring\Command\Object\RemoveAcknowledgementCommand; 15use Icinga\Module\Monitoring\Command\Object\ScheduleHostDowntimeCommand; 16use Icinga\Module\Monitoring\Command\Object\ScheduleServiceCheckCommand; 17use Icinga\Module\Monitoring\Command\Object\ScheduleServiceDowntimeCommand; 18use Icinga\Module\Monitoring\Command\Object\SendCustomNotificationCommand; 19use Icinga\Module\Monitoring\Command\Object\ToggleObjectFeatureCommand; 20use Icinga\Module\Monitoring\Command\IcingaCommand; 21use Icinga\Module\Monitoring\Object\MonitoredObject; 22use InvalidArgumentException; 23 24/** 25 * Icinga command renderer for the Icinga command file 26 */ 27class IcingaApiCommandRenderer implements IcingaCommandRendererInterface 28{ 29 /** 30 * Name of the Icinga application object 31 * 32 * @var string 33 */ 34 protected $app = 'app'; 35 36 /** 37 * Get the name of the Icinga application object 38 * 39 * @return string 40 */ 41 public function getApp() 42 { 43 return $this->app; 44 } 45 46 /** 47 * Set the name of the Icinga application object 48 * 49 * @param string $app 50 * 51 * @return $this 52 */ 53 public function setApp($app) 54 { 55 $this->app = $app; 56 57 return $this; 58 } 59 60 /** 61 * Apply filter to query data 62 * 63 * @param array $data 64 * @param MonitoredObject $object 65 * 66 * @return array 67 */ 68 protected function applyFilter(array &$data, MonitoredObject $object) 69 { 70 if ($object->getType() === $object::TYPE_HOST) { 71 /** @var \Icinga\Module\Monitoring\Object\Host $object */ 72 $data['host'] = $object->getName(); 73 } else { 74 /** @var \Icinga\Module\Monitoring\Object\Service $object */ 75 $data['service'] = sprintf('%s!%s', $object->getHost()->getName(), $object->getName()); 76 } 77 } 78 79 /** 80 * Render a command 81 * 82 * @param IcingaCommand $command 83 * 84 * @return IcingaApiCommand 85 */ 86 public function render(IcingaCommand $command) 87 { 88 $renderMethod = 'render' . $command->getName(); 89 if (! method_exists($this, $renderMethod)) { 90 die($renderMethod); 91 } 92 return $this->$renderMethod($command); 93 } 94 95 public function renderAddComment(AddCommentCommand $command) 96 { 97 $endpoint = 'actions/add-comment'; 98 $data = array( 99 'author' => $command->getAuthor(), 100 'comment' => $command->getComment() 101 ); 102 $this->applyFilter($data, $command->getObject()); 103 return IcingaApiCommand::create($endpoint, $data); 104 } 105 106 public function renderSendCustomNotification(SendCustomNotificationCommand $command) 107 { 108 $endpoint = 'actions/send-custom-notification'; 109 $data = array( 110 'author' => $command->getAuthor(), 111 'comment' => $command->getComment(), 112 'force' => $command->getForced() 113 ); 114 $this->applyFilter($data, $command->getObject()); 115 return IcingaApiCommand::create($endpoint, $data); 116 } 117 118 public function renderProcessCheckResult(ProcessCheckResultCommand $command) 119 { 120 $endpoint = 'actions/process-check-result'; 121 $data = array( 122 'exit_status' => $command->getStatus(), 123 'plugin_output' => $command->getOutput(), 124 'performance_data' => $command->getPerformanceData() 125 ); 126 $this->applyFilter($data, $command->getObject()); 127 return IcingaApiCommand::create($endpoint, $data); 128 } 129 130 public function renderScheduleCheck(ScheduleServiceCheckCommand $command) 131 { 132 $endpoint = 'actions/reschedule-check'; 133 $data = array( 134 'next_check' => $command->getCheckTime(), 135 'force' => $command->getForced() 136 ); 137 $this->applyFilter($data, $command->getObject()); 138 return IcingaApiCommand::create($endpoint, $data); 139 } 140 141 public function renderScheduleDowntime(ScheduleServiceDowntimeCommand $command) 142 { 143 $endpoint = 'actions/schedule-downtime'; 144 $data = array( 145 'author' => $command->getAuthor(), 146 'comment' => $command->getComment(), 147 'start_time' => $command->getStart(), 148 'end_time' => $command->getEnd(), 149 'duration' => $command->getDuration(), 150 'fixed' => $command->getFixed(), 151 'trigger_name' => $command->getTriggerId() 152 ); 153 $commandData = $data; 154 if ($command instanceof PropagateHostDowntimeCommand) { 155 /** @var \Icinga\Module\Monitoring\Command\Object\PropagateHostDowntimeCommand $command */ 156 $commandData['child_options'] = $command->getTriggered() ? 1 : 2; 157 } 158 $this->applyFilter($commandData, $command->getObject()); 159 $apiCommand = IcingaApiCommand::create($endpoint, $commandData); 160 if ($command instanceof ScheduleHostDowntimeCommand 161 /** @var \Icinga\Module\Monitoring\Command\Object\ScheduleHostDowntimeCommand $command */ 162 && $command->getForAllServices() 163 ) { 164 $commandData = $data + array( 165 'type' => 'Service', 166 'filter' => 'host.name == host_name', 167 'filter_vars' => array( 168 'host_name' => $command->getObject()->getName() 169 ) 170 ); 171 $apiCommand->setNext(IcingaApiCommand::create($endpoint, $commandData)); 172 } 173 return $apiCommand; 174 } 175 176 public function renderAcknowledgeProblem(AcknowledgeProblemCommand $command) 177 { 178 $endpoint = 'actions/acknowledge-problem'; 179 $data = array( 180 'author' => $command->getAuthor(), 181 'comment' => $command->getComment(), 182 'sticky' => $command->getSticky(), 183 'notify' => $command->getNotify(), 184 'persistent' => $command->getPersistent() 185 ); 186 if ($command->getExpireTime() !== null) { 187 $data['expiry'] = $command->getExpireTime(); 188 } 189 $this->applyFilter($data, $command->getObject()); 190 return IcingaApiCommand::create($endpoint, $data); 191 } 192 193 public function renderToggleObjectFeature(ToggleObjectFeatureCommand $command) 194 { 195 if ($command->getEnabled() === true) { 196 $enabled = true; 197 } else { 198 $enabled = false; 199 } 200 switch ($command->getFeature()) { 201 case ToggleObjectFeatureCommand::FEATURE_ACTIVE_CHECKS: 202 $attr = 'enable_active_checks'; 203 break; 204 case ToggleObjectFeatureCommand::FEATURE_PASSIVE_CHECKS: 205 $attr = 'enable_passive_checks'; 206 break; 207 case ToggleObjectFeatureCommand::FEATURE_NOTIFICATIONS: 208 $attr = 'enable_notifications'; 209 break; 210 case ToggleObjectFeatureCommand::FEATURE_EVENT_HANDLER: 211 $attr = 'enable_event_handler'; 212 break; 213 case ToggleObjectFeatureCommand::FEATURE_FLAP_DETECTION: 214 $attr = 'enable_flapping'; 215 break; 216 default: 217 throw new InvalidArgumentException($command->getFeature()); 218 } 219 $endpoint = 'objects/'; 220 $object = $command->getObject(); 221 if ($object->getType() === ToggleObjectFeatureCommand::TYPE_HOST) { 222 /** @var \Icinga\Module\Monitoring\Object\Host $object */ 223 $endpoint .= 'hosts'; 224 } else { 225 /** @var \Icinga\Module\Monitoring\Object\Service $object */ 226 $endpoint .= 'services'; 227 } 228 $data = array( 229 'attrs' => array( 230 $attr => $enabled 231 ) 232 ); 233 $this->applyFilter($data, $object); 234 return IcingaApiCommand::create($endpoint, $data); 235 } 236 237 public function renderDeleteComment(DeleteCommentCommand $command) 238 { 239 $endpoint = 'actions/remove-comment'; 240 $data = [ 241 'author' => $command->getAuthor(), 242 'comment' => $command->getCommentName() 243 ]; 244 return IcingaApiCommand::create($endpoint, $data); 245 } 246 247 public function renderDeleteDowntime(DeleteDowntimeCommand $command) 248 { 249 $endpoint = 'actions/remove-downtime'; 250 $data = [ 251 'author' => $command->getAuthor(), 252 'downtime' => $command->getDowntimeName() 253 ]; 254 return IcingaApiCommand::create($endpoint, $data); 255 } 256 257 public function renderRemoveAcknowledgement(RemoveAcknowledgementCommand $command) 258 { 259 $endpoint = 'actions/remove-acknowledgement'; 260 $data = ['author' => $command->getAuthor()]; 261 $this->applyFilter($data, $command->getObject()); 262 return IcingaApiCommand::create($endpoint, $data); 263 } 264 265 public function renderToggleInstanceFeature(ToggleInstanceFeatureCommand $command) 266 { 267 $endpoint = 'objects/icingaapplications/' . $this->getApp(); 268 if ($command->getEnabled() === true) { 269 $enabled = true; 270 } else { 271 $enabled = false; 272 } 273 switch ($command->getFeature()) { 274 case ToggleInstanceFeatureCommand::FEATURE_ACTIVE_HOST_CHECKS: 275 $attr = 'enable_host_checks'; 276 break; 277 case ToggleInstanceFeatureCommand::FEATURE_ACTIVE_SERVICE_CHECKS: 278 $attr = 'enable_service_checks'; 279 break; 280 case ToggleInstanceFeatureCommand::FEATURE_EVENT_HANDLERS: 281 $attr = 'enable_event_handlers'; 282 break; 283 case ToggleInstanceFeatureCommand::FEATURE_FLAP_DETECTION: 284 $attr = 'enable_flapping'; 285 break; 286 case ToggleInstanceFeatureCommand::FEATURE_NOTIFICATIONS: 287 $attr = 'enable_notifications'; 288 break; 289 case ToggleInstanceFeatureCommand::FEATURE_PERFORMANCE_DATA: 290 $attr = 'enable_perfdata'; 291 break; 292 default: 293 throw new InvalidArgumentException($command->getFeature()); 294 } 295 $data = array( 296 'attrs' => array( 297 $attr => $enabled 298 ) 299 ); 300 return IcingaApiCommand::create($endpoint, $data); 301 } 302} 303