phacility/phabricator · warning · PhutilSearchQueryCompilerSyntaxException

Query contains a token ("%s") with no search term. Query tok

Error message

Query contains a token ("%s") with no search term. Query tokens specify text to search for.

What it means

After operator resolution a token ended up with an empty value while its operator requires text (require_value). Search tokens must specify something to search for; operators like a bare `+` or `-`, or a function prefix with no term (`title:`), produce a token whose value has zero length, which cannot compile into any meaningful query, so PhutilSearchQueryCompilerSyntaxException is thrown with the display form of the offending token.

Source

Thrown at src/applications/search/compiler/PhutilSearchQueryCompiler.php:346

            } else {
              $require_value = true;
            }
            break;
          case self::OPERATOR_SUBSTRING:
            if ($enable_functions && ($token['function'] !== null)) {
              $operator = self::OPERATOR_PRESENT;
              $value = null;
            } else {
              $require_value = true;
            }
            break;
          default:
            $require_value = true;
            break;
        }

        if ($require_value) {
          throw new PhutilSearchQueryCompilerSyntaxException(
            pht(
              'Query contains a token ("%s") with no search term. Query '.
              'tokens specify text to search for.',
              $this->getDisplayToken($token)));
        }
      }

      $result = array(
        'operator' => $operator,
        'quoted' => $is_quoted,
        'value' => $value,
        'raw' => $this->getDisplayToken($token),
      );

      if ($enable_functions) {
        // If a user provides a query like "title:a b c", we interpret all
        // of the terms to be title terms: the "title:" function sticks
        // until we encounter another function.

View on GitHub (pinned to 5720a38cfe)

Solutions

  1. Remove the dangling operator or add the missing term: `cat -` -> `cat`, `title:` -> `title:ship`.
  2. When generating queries in code, skip emission whenever the term is empty: if ($term === '') continue; before prefixing operators.
  3. Trim the query before submit so accidental trailing operators from deleted words are caught by eye.
  4. Treat the exception as form validation: catch PhutilSearchQueryCompilerSyntaxException and re-show the query form with the message; the token is named in the error.

Example fix

// before: emits operator with empty term when filter empty
$parts[] = ($negate ? '-' : '').$term;

// after: skip empty terms entirely
if ($term !== '') {
  $parts[] = ($negate ? '-' : '').$term;
}
Defensive patterns

Strategy: validation

Validate before calling

// Drop operator-only fragments before submitting
$fragments = preg_split('/\s+/', trim($query));
$fragments = array_filter($fragments, function ($f) { return trim($f, '+-:') !== ''; });
$query = implode(' ', $fragments);

Type guard

function hasNoEmptyTokens($q) { return !preg_match('/(^|\s)[+-]+(:\w+)?(\s|$)/', $q); }

Try / catch

try {
  $compiled = $compiler->compileQuery($field, $query);
} catch (PhutilSearchQueryCompilerSyntaxException $ex) {
  $e_query = $ex->getMessage(); // AphrontFormView error binding pattern
}

Prevention

When it happens

Trigger: Queries like `cat +` or `cat -` (trailing operator with no term), `title:` with nothing after the colon, an empty quoted phrase `""` where functions require a value, or a lone function name with functions enabled but no argument. Hit via UI search boxes, saved-query editing, or Conduit search parameters.

Common situations: Trailing space plus operator at the end of a query left over from deleting a word (`fix -` after removing the excluded term); copy-pasted queries where the term after an operator got dropped; programmatic query builders appending an operator prefix then an empty string term.

Related errors


AI-assisted analysis of phacility/phabricator@5720a38cfe (2026-08-21). Data as JSON: /api/errors/7113ab2ed97c3446. Report an issue: GitHub.