Skip to content
This repository has been archived by the owner on Apr 1, 2024. It is now read-only.

Commit

Permalink
preparations for v2
Browse files Browse the repository at this point in the history
  • Loading branch information
mattkingshott committed Nov 22, 2021
1 parent 61d5003 commit 8c20653
Show file tree
Hide file tree
Showing 19 changed files with 119 additions and 136 deletions.
44 changes: 0 additions & 44 deletions .github/.php-cs-fixer.php

This file was deleted.

2 changes: 1 addition & 1 deletion .github/workflows/style.yml
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ jobs:
- name: Run PHP CS Fixer
uses: docker://oskarstark/php-cs-fixer-ga
with:
args: --config=.github/.php_cs --allow-risky=yes
args: --config=tools/.php-cs-fixer.php --allow-risky=yes

- name: Extract branch name
shell: bash
Expand Down
4 changes: 2 additions & 2 deletions resources/version.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
1 change: 0 additions & 1 deletion src/Macros/OrderByFuzzy.php
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,6 @@

class OrderByFuzzy
{

/**
* Construct a fuzzy search expression.
*
Expand Down
75 changes: 43 additions & 32 deletions src/Macros/WhereFuzzy.php
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,12 @@

namespace Quest\Macros;

use Illuminate\Database\Query\Builder;
use Quest\Matchers\ExactMatcher;
use Illuminate\Support\Facades\DB;
use Quest\Matchers\AcronymMatcher;
use Quest\Matchers\InStringMatcher;
use Quest\Matchers\StudlyCaseMatcher;
use Illuminate\Database\Query\Builder;
use Quest\Matchers\StartOfWordsMatcher;
use Quest\Matchers\StartOfStringMatcher;
use Quest\Matchers\TimesInStringMatcher;
Expand All @@ -16,20 +16,19 @@

class WhereFuzzy
{

/**
* The weights for the pattern matching classes.
*
**/
protected static array $matchers = [
ExactMatcher::class => 100,
StartOfStringMatcher::class => 50,
AcronymMatcher::class => 42,
ExactMatcher::class => 100,
StartOfStringMatcher::class => 50,
AcronymMatcher::class => 42,
ConsecutiveCharactersMatcher::class => 40,
StartOfWordsMatcher::class => 35,
StudlyCaseMatcher::class => 32,
InStringMatcher::class => 30,
TimesInStringMatcher::class => 8,
StartOfWordsMatcher::class => 35,
StudlyCaseMatcher::class => 32,
InStringMatcher::class => 30,
TimesInStringMatcher::class => 8,
];

/**
Expand All @@ -38,33 +37,35 @@ class WhereFuzzy
**/
public static function make(Builder $builder, $field, $value): Builder
{
$value = static::escapeValue($value);
$value = static::escapeValue($value);
$nativeField = '`' . str_replace('.', '`.`', trim($field, '` ')) . '`';

if (!is_array($builder->columns) || empty($builder->columns)) {
if (! is_array($builder->columns) || empty($builder->columns)) {
$builder->columns = ['*'];
}

$builder
->addSelect([static::pipeline($field, $nativeField, $value)])
->having('fuzzy_relevance_' . str_replace('.', '_', $field), '>', 0);

static::calculateTotalRelevanceColumn($builder);

return $builder;
}

/**
* Construct a fuzzy search expression.
* Construct a fuzzy OR search expression.
*
**/
public static function makeOr(Builder $builder, $field, $value): Builder
{

$value = static::escapeValue($value);
$value = static::escapeValue($value);
$nativeField = '`' . str_replace('.', '`.`', trim($field, '` ')) . '`';

if (!is_array($builder->columns) || empty($builder->columns)) {
if (! is_array($builder->columns) || empty($builder->columns)) {
$builder->columns = ['*'];
}

$builder
->addSelect([static::pipeline($field, $nativeField, $value)])
->orHaving('fuzzy_relevance_' . str_replace('.', '_', $field), '>', 0);
Expand All @@ -75,74 +76,84 @@ public static function makeOr(Builder $builder, $field, $value): Builder
}

/**
* Manage relevance columns SUM for total relevance ORDER
* Searches all relevance columns and parses the relevance expressions to create the total relevance column
* and creates the order statement for it
* @param $builder
* @return bool
* Manage relevance columns SUM for total relevance ORDER.
*
* Searches all relevance columns and parses the relevance
* expressions to create the total relevance column
* and creates the order statement for it.
*
*/
protected static function calculateTotalRelevanceColumn($builder): bool
{
if (!empty($builder->columns)) {
if (! empty($builder->columns)) {
$existingRelevanceColumns = [];
$sumColumnIdx = null;
$sumColumnIdx = null;

// search for fuzzy_relevance_* columns and _fuzzy_relevance_ position
foreach ($builder->columns as $as => $column) {
if ($column instanceof Expression) {
if (stripos($column->getValue(), 'AS fuzzy_relevance_')) {
$matches = [];

preg_match('/AS (fuzzy_relevance_.*)$/', $column->getValue(), $matches);
if (!empty($matches[1])) {

if (! empty($matches[1])) {
$existingRelevanceColumns[$as] = $matches[1];
}
} elseif (stripos($column->getValue(), 'AS _fuzzy_relevance_')) {
$sumColumnIdx = $as;
}
}
}

// glue together all relevance expresions under _fuzzy_relevance_ column
$relevanceTotalColumn = '';

foreach ($existingRelevanceColumns as $as => $column) {
$relevanceTotalColumn .= (!empty($relevanceTotalColumn) ? ' + ' : '')
$relevanceTotalColumn .= (! empty($relevanceTotalColumn) ? ' + ' : '')
. '('
. str_ireplace(' AS ' . $column, '', $builder->columns[$as]->getValue())
. ')';
}

$relevanceTotalColumn .= ' AS _fuzzy_relevance_';

if (is_null($sumColumnIdx)) {
// no sum column yet, just add this one
$builder
->addSelect([new Expression($relevanceTotalColumn)]);
$builder->addSelect([new Expression($relevanceTotalColumn)]);
} else {
// update the existing one
$builder->columns[$sumColumnIdx] = new Expression($relevanceTotalColumn);
}

// only add the _fuzzy_relevance_ ORDER once
if (
!$builder->orders
|| ($builder->orders
&& array_search('_fuzzy_relevance_',
! $builder->orders
|| (
$builder->orders
&& array_search(
'_fuzzy_relevance_',
array_column($builder->orders, 'column')
) === false
)
) {
$builder->orderBy('_fuzzy_relevance_', 'desc');
}

return true;
}

return false;
}

/**
* Escape value input for fuzzy search
* @param $value
* @return false|string
* Escape value input for fuzzy search.
*/
protected static function escapeValue($value)
{
$value = str_replace(['"', "'", '`'], '', $value);
$value = substr(DB::connection()->getPdo()->quote($value), 1, -1);

return $value;
}

Expand Down
3 changes: 0 additions & 3 deletions src/Matchers/AcronymMatcher.php
Original file line number Diff line number Diff line change
Expand Up @@ -4,15 +4,12 @@

class AcronymMatcher extends BaseMatcher
{

/**
* The operator to use for the WHERE clause.
*
**/
protected string $operator = 'LIKE';



/**
* Format the given search term.
*
Expand Down
5 changes: 0 additions & 5 deletions src/Matchers/BaseMatcher.php
Original file line number Diff line number Diff line change
Expand Up @@ -4,15 +4,12 @@

abstract class BaseMatcher
{

/**
* The weight to apply to the match.
*
**/
protected int $multiplier;



/**
* Constructor.
*
Expand All @@ -22,8 +19,6 @@ public function __construct(int $multiplier)
$this->multiplier = $multiplier;
}



/**
* The default process for building the query string.
*
Expand Down
5 changes: 0 additions & 5 deletions src/Matchers/ConsecutiveCharactersMatcher.php
Original file line number Diff line number Diff line change
Expand Up @@ -4,15 +4,12 @@

class ConsecutiveCharactersMatcher extends BaseMatcher
{

/**
* The operator to use for the WHERE clause.
*
**/
protected string $operator = 'LIKE';



/**
* The process for building the query string.
*
Expand All @@ -25,8 +22,6 @@ public function buildQueryString(string $field, string $value) : string
"(CHAR_LENGTH('$value') / CHAR_LENGTH(REPLACE($field, ' ', '')))), 0)";
}



/**
* Format the given search term.
*
Expand Down
1 change: 0 additions & 1 deletion src/Matchers/ExactMatcher.php
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@

class ExactMatcher extends BaseMatcher
{

/**
* The operator to use for the WHERE clause.
*
Expand Down
3 changes: 0 additions & 3 deletions src/Matchers/InStringMatcher.php
Original file line number Diff line number Diff line change
Expand Up @@ -4,15 +4,12 @@

class InStringMatcher extends BaseMatcher
{

/**
* The operator to use for the WHERE clause.
*
**/
protected string $operator = 'LIKE';



/**
* Format the given search term.
*
Expand Down
3 changes: 0 additions & 3 deletions src/Matchers/StartOfStringMatcher.php
Original file line number Diff line number Diff line change
Expand Up @@ -4,15 +4,12 @@

class StartOfStringMatcher extends BaseMatcher
{

/**
* The operator to use for the WHERE clause.
*
**/
protected string $operator = 'LIKE';



/**
* Format the given search term.
*
Expand Down
3 changes: 0 additions & 3 deletions src/Matchers/StartOfWordsMatcher.php
Original file line number Diff line number Diff line change
Expand Up @@ -4,15 +4,12 @@

class StartOfWordsMatcher extends BaseMatcher
{

/**
* The operator to use for the WHERE clause.
*
**/
protected string $operator = 'LIKE';



/**
* Format the given search term.
*
Expand Down
Loading

0 comments on commit 8c20653

Please sign in to comment.