コード例 #1
0
ファイル: Where.php プロジェクト: modpreneur/trinity-search
 /**
  * Parse condition;
  *
  * @param $str
  * @return array
  * @throws SyntaxErrorException
  */
 private static function parseCondition($str) : array
 {
     $parts = [];
     // REMOVE TRAILING SPACES
     $str = trim($str);
     // LOOP THROUGH ALL CHARACTERS
     $iMax = strlen($str);
     /** @noinspection ForeachInvariantsInspection */
     for ($i = 0; $i < $iMax; $i++) {
         // IF CHARACTER IS LEFT BRACKET, FIND PAIR BRACKET AND RECURSIVELY FIND CONDITIONS WITHIN THESE BRACKETS
         if ($str[$i] === '(') {
             $pairBracketIndex = self::findPairBracketIndex($str, $i + 1);
             if ($pairBracketIndex > 0) {
                 $part = new WherePart();
                 $part->type = WherePartType::SUBCONDITION;
                 $subCondition = substr($str, $i + 1, $pairBracketIndex - $i - 1);
                 $part->baseExpr = trim($subCondition);
                 $part->subTree = self::parseCondition($subCondition);
                 $parts[] = $part;
                 $i = $pairBracketIndex;
                 continue;
             } else {
                 throw new SyntaxErrorException('Missing pair bracket');
             }
         } else {
             if ($str[$i] === ' ') {
                 if (trim(substr($str, $i, 4)) === Operator::AND) {
                     $part = new WherePart();
                     $part->type = WherePartType::OPERATOR;
                     $part->value = Operator::AND;
                     $parts[] = $part;
                     $i += 3;
                 } else {
                     if (trim(substr($str, $i, 3)) === Operator::OR) {
                         $part = new WherePart();
                         $part->type = WherePartType::OPERATOR;
                         $part->value = Operator::OR;
                         $parts[] = $part;
                         $i += 2;
                     }
                 }
             } else {
                 $match = [];
                 $wasFound = preg_match(self::$regKeyOpValue, substr($str, $i), $match);
                 if ($wasFound) {
                     $part = new WherePart();
                     $part->type = WherePartType::CONDITION;
                     $part->key = Column::parse($match['key']);
                     $value = $match['value'];
                     if (StringUtils::startsWith($value, '"') && StringUtils::endsWith($value, '"')) {
                         $value = StringUtils::substring($value, 1, StringUtils::length($value) - 1);
                     }
                     $part->value = $value;
                     $part->operator = $match['operator'];
                     $parts[] = $part;
                     $i = $i + strlen($match[0]) - 1;
                 } else {
                     $part = new WherePart();
                     $part->type = 'UNKNOWN';
                     $part->value = $str[$i];
                     $parts[] = $part;
                     $context = self::getErrorContext($str, $i);
                     throw new SyntaxErrorException("Unrecognized char sequence at '{$context['subString']}' starting from index {$context['errorAt']}");
                 }
             }
         }
     }
     return $parts;
 }
コード例 #2
0
 /**
  * @param WherePart[] $conditions
  * @param string $columnDefaultAlias
  * @param int $paramCounter
  * @return array
  */
 private function getParametrizedWhere($conditions, $columnDefaultAlias = '', &$paramCounter = 0) : array
 {
     $whereClause = '';
     $whereParams = [];
     foreach ($conditions as $cond) {
         switch ($cond->type) {
             case WherePartType::OPERATOR:
                 $whereClause .= ' ' . $cond->value;
                 break;
             case WherePartType::CONDITION:
                 $whereClause .= ' ' . ($cond->key->getWrappingFunction() === null ? '' : $cond->key->getWrappingFunction() . '(') . (!count($cond->key->getJoinWith()) ? $cond->key->getAlias() ?? $columnDefaultAlias : $cond->key->getJoinWith()[count($cond->key->getJoinWith()) - 1]) . '.' . $cond->key->getName() . ' ' . ($cond->key->getWrappingFunction() === null ? '' : ')') . ($cond->operator === '!=' ? '<>' : $cond->operator) . ' ?' . $paramCounter;
                 if ($cond->operator === Operator::LIKE && !StringUtils::startsWith($cond->value, '%') && !StringUtils::endsWith($cond->value, '%')) {
                     $whereParams[] = '%' . $cond->value . '%';
                 } else {
                     $whereParams[] = $cond->value;
                 }
                 $paramCounter++;
                 break;
             case WherePartType::SUBCONDITION:
                 $parametrizedSubWhere = $this->getParametrizedWhere($cond->subTree, $columnDefaultAlias, $paramCounter);
                 $subWhereClause = $parametrizedSubWhere['clause'];
                 $subWhereParams = $parametrizedSubWhere['params'];
                 $whereClause .= ' (' . $subWhereClause . ')';
                 $whereParams = array_merge($whereParams, $subWhereParams);
                 break;
         }
     }
     return ['clause' => $whereClause, 'params' => $whereParams];
 }