diff --git a/library/Director/IcingaConfig/AssignRenderer.php b/library/Director/IcingaConfig/AssignRenderer.php index e0c58495..454e1f34 100644 --- a/library/Director/IcingaConfig/AssignRenderer.php +++ b/library/Director/IcingaConfig/AssignRenderer.php @@ -85,7 +85,8 @@ class AssignRenderer protected function renderFilterExpression(FilterExpression $filter) { $column = $filter->getColumn(); - $expression = $filter->getExpression(); + $expression = $this->renderExpressionValue(json_decode($filter->getExpression())); + if ($filter instanceof FilterEqual) { return sprintf( '%s == %s', @@ -154,6 +155,11 @@ class AssignRenderer } } + protected function renderExpressionValue($value) + { + return IcingaConfigHelper::renderPhpValue($value); + } + protected function renderFilterChain(FilterChain $filter) { // TODO: brackets if deeper level? diff --git a/library/Director/IcingaConfig/IcingaConfigHelper.php b/library/Director/IcingaConfig/IcingaConfigHelper.php index 807b6776..4ae287be 100644 --- a/library/Director/IcingaConfig/IcingaConfigHelper.php +++ b/library/Director/IcingaConfig/IcingaConfigHelper.php @@ -2,6 +2,7 @@ namespace Icinga\Module\Director\IcingaConfig; +use Icinga\Exception\IcingaException; use Icinga\Exception\ProgrammingError; class IcingaConfigHelper @@ -63,15 +64,36 @@ class IcingaConfigHelper public static function renderBoolean($value) { - if ($value === 'y') { + if ($value === 'y' || $value === true) { return 'true'; - } elseif ($value === 'n') { + } elseif ($value === 'n' || $value === false) { return 'false'; } else { throw new ProgrammingError('%s is not a valid boolean', $value); } } + protected static function renderInteger($value) + { + return (string) $value; + } + + protected static function renderFloat($value) + { + // Render .0000 floats as integers, mainly because of some JSON + // implementations: + if ((string) (int) $value === (string) $value) { + return static::renderInteger((int) $value); + } else { + return sprintf('%F', $value); + } + } + + protected static function renderNull() + { + return 'null'; + } + // TODO: Find out how to allow multiline {{{...}}} strings. // Parameter? Dedicated method? Always if \n is found? public static function renderString($string) @@ -103,6 +125,28 @@ class IcingaConfigHelper return '"' . $string . '"'; } + public static function renderPhpValue($value) + { + if (is_null($value)) { + return static::renderNull(); + } elseif (is_bool($value)) { + return static::renderBoolean($value); + } elseif (is_integer($value)) { + return static::renderInteger($value); + } elseif (is_float($value)) { + return static::renderFloat($value); + // TODO: + // } elseif (is_object($value) || static::isAssocArray($value)) { + // return static::renderHash($value, $prefix); + // } elseif (is_array($value)) { + // return static::renderArray($value, $prefix); + } elseif (is_string($value)) { + return static::renderString($value); + } else { + throw new IcingaException('Unexpected type %s', var_export($value, 1)); + } + } + public static function renderDictionaryKey($key) { if (preg_match('/^[a-z_]+[a-z0-9_]*$/i', $key)) { diff --git a/test/php/library/Director/IcingaConfig/AssignRendererTest.php b/test/php/library/Director/IcingaConfig/AssignRendererTest.php index 70aa45c1..a15b8e42 100644 --- a/test/php/library/Director/IcingaConfig/AssignRendererTest.php +++ b/test/php/library/Director/IcingaConfig/AssignRendererTest.php @@ -42,6 +42,18 @@ class AssignRendererTest extends BaseTestCase ); } + public function testWhetherSlashesAreNotEscaped() + { + $string = 'host.name=' . json_encode('a/b'); + + $expected = 'assign where host.name == "a/b"'; + + $this->assertEquals( + $expected, + $this->renderer($string)->renderAssign() + ); + } + protected function renderer($string) { return AssignRenderer::forFilter(Filter::fromQueryString($string));