/** * Builds expression html tree * * @param array $expressionTree output of getExpressionTree() function * @param array $next parameter only for recursive call; should be empty array * @param int $letterNum parameter only for recursive call; should be 0 * @param int $level parameter only for recursive call * @param string $operator parameter only for recursive call * * @return array array containing the trigger expression formula as the first element and an array describing the * expression tree as the second */ function buildExpressionHtmlTree(array $expressionTree, array &$next, &$letterNum, $level = 0, $operator = null) { $treeList = []; $outline = ''; end($expressionTree); $lastKey = key($expressionTree); foreach ($expressionTree as $key => $element) { switch ($element['type']) { case 'operator': $next[$level] = $key != $lastKey; $expr = expressionLevelDraw($next, $level); $expr[] = SPACE; $expr[] = $element['operator'] === 'and' ? _('And') : _('Or'); $levelDetails = ['list' => $expr, 'id' => $element['id'], 'expression' => ['value' => $element['expression']]]; $levelErrors = expressionHighLevelErrors($element['expression']); if (count($levelErrors) > 0) { $levelDetails['expression']['levelErrors'] = $levelErrors; } $treeList[] = $levelDetails; list($subOutline, $subTreeList) = buildExpressionHtmlTree($element['elements'], $next, $letterNum, $level + 1, $element['operator']); $treeList = array_merge($treeList, $subTreeList); $outline .= $level == 0 ? $subOutline : '(' . $subOutline . ')'; if ($operator !== null && $next[$level]) { $outline .= ' ' . $operator . ' '; } break; case 'expression': $next[$level] = $key != $lastKey; $letter = num2letter($letterNum++); $outline .= $letter; if ($operator !== null && $next[$level]) { $outline .= ' ' . $operator . ' '; } if (defined('NO_LINK_IN_TESTING')) { $url = $element['expression']; } else { $expressionId = 'expr_' . $element['id']; $url = (new CSpan($element['expression']))->addClass(ZBX_STYLE_LINK_ACTION)->setId($expressionId)->onClick('javascript: copy_expression("' . $expressionId . '");'); } $expr = expressionLevelDraw($next, $level); $expr[] = SPACE; $expr[] = bold($letter); $expr[] = SPACE; $expr[] = $url; $levelDetails = ['list' => $expr, 'id' => $element['id'], 'expression' => ['value' => $element['expression']]]; $levelErrors = expressionHighLevelErrors($element['expression']); if (count($levelErrors) > 0) { $levelDetails['expression']['levelErrors'] = $levelErrors; } $treeList[] = $levelDetails; break; } } return [$outline, $treeList]; }
/** * Builds expression html tree * * @param array $expressionTree output of getExpressionTree() function * @param array $next parameter only for recursive call; should be empty array * @param int $letterNum parameter only for recursive call; should be 0 * @param int $level parameter only for recursive call * @param string $operand parameter only for recursive call * * @return bool returns true if element is found, false - otherwise */ function buildExpressionHtmlTree(array $expressionTree, array &$next, &$letterNum, $level = 0, $operand = null) { $treeList = array(); $outline = ''; end($expressionTree); $lastKey = key($expressionTree); foreach ($expressionTree as $key => $element) { switch ($element['type']) { case 'operand': $next[$level] = $key != $lastKey; $expr = expressionLevelDraw($next, $level); $expr[] = SPACE; $expr[] = italic($element['operand'] == '&' ? _('AND') : _('OR')); $levelDetails = array('list' => $expr, 'id' => $element['id'], 'expression' => array('value' => $element['expression'])); $levelErrors = expressionHighLevelErrors($element['expression']); if (count($levelErrors) > 0) { $levelDetails['expression']['levelErrors'] = $levelErrors; } $treeList[] = $levelDetails; list($subOutline, $subTreeList) = buildExpressionHtmlTree($element['elements'], $next, $letterNum, $level + 1, $element['operand']); $treeList = array_merge($treeList, $subTreeList); $outline .= $level == 0 ? $subOutline : '(' . $subOutline . ')'; if ($operand !== null && $next[$level]) { $outline .= ' ' . $operand . ' '; } break; case 'expression': $next[$level] = $key != $lastKey; $letter = num2letter($letterNum++); $outline .= $letter; if ($operand !== null && $next[$level]) { $outline .= ' ' . $operand . ' '; } if (defined('NO_LINK_IN_TESTING')) { $url = new CSpan($element['expression']); } else { $expressionId = 'expr_' . $element['id']; $url = new CSpan($element['expression'], 'link'); $url->setAttribute('id', $expressionId); $url->setAttribute('onclick', 'javascript: copy_expression("' . $expressionId . '");'); } $expr = expressionLevelDraw($next, $level); $expr[] = SPACE; $expr[] = bold($letter); $expr[] = SPACE; $expr[] = $url; $levelDetails = array('list' => $expr, 'id' => $element['id'], 'expression' => array('value' => $element['expression'])); $levelErrors = expressionHighLevelErrors($element['expression']); if (count($levelErrors) > 0) { $levelDetails['expression']['levelErrors'] = $levelErrors; } $treeList[] = $levelDetails; break; } } return array($outline, $treeList); }
function build_expression_html_tree($expression, &$treeLevel, $level, &$next, &$nextletter, &$secondLetters = null) { $treeList = array(); $outline = ''; $expr = array(); if ($level > 0) { expressionLevelDraw($next, $level, $expr); } $letterLevel = true; if ($treeLevel['levelType'] == 'independent' || $treeLevel['levelType'] == 'grouping') { $sStart = !isset($treeLevel['openSymbol']) ? $treeLevel['openSymbolNum'] : $treeLevel['openSymbolNum'] + zbx_strlen($treeLevel['openSymbol']); $sEnd = !isset($treeLevel['closeSymbol']) ? $treeLevel['closeSymbolNum'] : $treeLevel['closeSymbolNum'] - zbx_strlen($treeLevel['closeSymbol']); if (isset($treeLevel['parts'])) { $parts =& $treeLevel['parts']; } else { $parts = array(); } $fPart = reset($parts); if (count($parts) == 1 && $sStart == $fPart['openSymbolNum'] && $sEnd == $fPart['closeSymbolNum']) { $next[$level] = false; list($outline, $treeList) = build_expression_html_tree($expression, $fPart, $level, $next, $nextletter, $secondLetters); $outline = (isset($treeLevel['openSymbol']) && $treeLevel['levelType'] == 'grouping' ? $treeLevel['openSymbol'] . ' ' : '') . $outline . (isset($treeLevel['closeSymbol']) && $treeLevel['levelType'] == 'grouping' ? ' ' . $treeLevel['closeSymbol'] : ''); return array($outline, $treeList); } $operand = '|'; reset($parts); $bParts = array(); $opPos = find_next_operand($expression, $sStart, $sEnd, $parts, $bParts, $operand); if (!is_int($opPos) || $opPos >= $sEnd) { $operand = '&'; reset($parts); $bParts = array(); $opPos = find_next_operand($expression, $sStart, $sEnd, $parts, $bParts, $operand); } if (is_int($opPos) && $opPos < $sEnd) { $letterLevel = false; $expValue = trim(zbx_substr($expression, $treeLevel['openSymbolNum'], $treeLevel['closeSymbolNum'] - $treeLevel['openSymbolNum'] + 1)); array_push($expr, SPACE, italic($operand == '&' ? S_AND_BIG : S_OR_BIG)); unset($expDetails); $levelDetails = array('list' => $expr, 'id' => $treeLevel['openSymbolNum'] . '_' . $treeLevel['closeSymbolNum'], 'expression' => array('start' => $treeLevel['openSymbolNum'], 'end' => $treeLevel['closeSymbolNum'], 'oSym' => isset($treeLevel['openSymbol']) ? $treeLevel['openSymbol'] : NULL, 'cSym' => isset($treeLevel['closeSymbol']) ? $treeLevel['closeSymbol'] : NULL, 'value' => $expValue)); $levelErrors = expressionHighLevelErrors($expression, $treeLevel['openSymbolNum'], $treeLevel['closeSymbolNum']); if (count($levelErrors) > 0) { $levelDetails['expression']['levelErrors'] = $levelErrors; } array_push($treeList, $levelDetails); $prev = $sStart; $levelOutline = ''; while (is_int($opPos) && $opPos < $sEnd || $prev < $sEnd) { unset($newTreeLevel); $strStart = $prev + ($prev > $sStart ? zbx_strlen($operand) : 0); $strEnd = is_int($opPos) && $opPos < $sEnd ? $opPos - zbx_strlen($operand) : $sEnd; if (count($bParts) == 1) { $fbPart = reset($bParts); } if (count($bParts) == 1 && zbx_substr($expression, $fbPart['openSymbolNum'], $fbPart['closeSymbolNum'] - $fbPart['openSymbolNum'] + 1) == trim(zbx_substr($expression, $strStart, $strEnd - $strStart + 1))) { $newTreeLevel =& $bParts[key($bParts)]; } else { $newTreeLevel = array('levelType' => 'grouping', 'openSymbolNum' => $strStart, 'closeSymbolNum' => $strEnd); if (is_array($bParts) && count($bParts) > 0) { $newTreeLevel['parts'] =& $bParts; } } // SDI("{$treeLevel['levelType']} parts:".(isset($treeLevel['parts']) ? count($treeLevel['parts']): 0)); unset($bParts); $bParts = array(); $prev = is_int($opPos) && $opPos < $sEnd ? $opPos : $sEnd; $opPos = find_next_operand($expression, $prev + zbx_strlen($operand), $sEnd, $parts, $bParts, $operand); // SDI('>>>>>>>>>>>>>>>>>>>newTreeLevel parts count:'.(isset($newTreeLevel['parts']) ? count($newTreeLevel['parts']) : 0)); $next[$level] = is_int($prev) && $prev < $sEnd ? true : false; list($outln, $treeLst) = build_expression_html_tree($expression, $newTreeLevel, $level + 1, $next, $nextletter, $secondLetters); $treeList = array_merge($treeList, $treeLst); $levelOutline .= trim($outln) . (is_int($prev) && $prev < $sEnd ? ' ' . $operand . ' ' : ''); // SDI("After {$treeLevel['levelType']} parts:".(isset($treeLevel['parts']) ? count($treeLevel['parts']): 0)); } $outline .= zbx_strlen($levelOutline) > 0 ? (isset($treeLevel['openSymbol']) ? $treeLevel['openSymbol'] . ' ' : '') . $levelOutline . (isset($treeLevel['closeSymbol']) ? ' ' . $treeLevel['closeSymbol'] : '') : ''; } } if ($letterLevel) { if (!$nextletter) { $nextletter = 'A'; } if ($nextletter > 'Z') { if (!$secondLetters) { $secondLetters = 'AA'; } if ($secondLetters[1] > 'Z') { $secondLetters[1] = 'A'; $secondLetters[0] = chr(ord($secondLetters[0]) + 1); } if ($secondLetters[0] > 'Z') { $secondLetters[0] = 'A'; } $newch = $secondLetters; } else { $newch = $nextletter; } array_push($expr, SPACE, bold($newch), SPACE); $expValue = trim(zbx_substr($expression, $treeLevel['openSymbolNum'], $treeLevel['closeSymbolNum'] - $treeLevel['openSymbolNum'] + 1)); if (!defined('NO_LINK_IN_TESTING')) { $url = new CSpan($expValue, 'link'); $url->setAttribute('id', 'expr_' . $treeLevel['openSymbolNum'] . '_' . $treeLevel['closeSymbolNum']); $url->setAttribute('onclick', 'javascript: copy_expression("expr_' . $treeLevel['openSymbolNum'] . '_' . $treeLevel['closeSymbolNum'] . '");'); } else { $url = new CSpan($expValue); } $expr[] = $url; $glue = ''; if (isset($secondLetters[1])) { $glue = $secondLetters[1] == 'A' ? " \r\n" : ' '; $secondLetters[1] = chr(ord($secondLetters[1]) + 1); } else { $nextletter = chr(ord($nextletter) + 1); } $outline = $glue . $newch . ' '; $levelDetails = array('start' => $treeLevel['openSymbolNum'], 'end' => $treeLevel['closeSymbolNum'], 'oSym' => isset($treeLevel['openSymbol']) ? $treeLevel['openSymbol'] : NULL, 'cSym' => isset($treeLevel['closeSymbol']) ? $treeLevel['closeSymbol'] : NULL, 'value' => $expValue); $errors = expressionHighLevelErrors($expression, $treeLevel['openSymbolNum'], $treeLevel['closeSymbolNum']); if (count($errors) > 0) { $levelDetails['levelErrors'] = $errors; } array_push($treeList, array('list' => $expr, 'id' => $treeLevel['openSymbolNum'] . '_' . $treeLevel['closeSymbolNum'], 'expression' => $levelDetails)); } return array($outline, $treeList); }