Expand rule/search combination.

This commit is contained in:
James Cole
2020-08-27 20:22:52 +02:00
parent 2393344978
commit 8c97754b64
6 changed files with 142 additions and 8 deletions

View File

@@ -32,11 +32,15 @@ use FireflyIII\Models\TransactionJournal;
use FireflyIII\Repositories\Rule\RuleRepositoryInterface;
use FireflyIII\Support\Http\Controllers\ModelInformation;
use FireflyIII\Support\Http\Controllers\RuleManagement;
use FireflyIII\Support\Search\OperatorQuerySearch;
use FireflyIII\Support\Search\SearchInterface;
use Illuminate\Contracts\View\Factory;
use Illuminate\Http\RedirectResponse;
use Illuminate\Http\Request;
use Illuminate\Routing\Redirector;
use Illuminate\View\View;
use Log;
use Throwable;
/**
* Class CreateController
@@ -44,6 +48,7 @@ use Illuminate\View\View;
class CreateController extends Controller
{
use RuleManagement, ModelInformation;
/** @var RuleRepositoryInterface Rule repository */
private $ruleRepos;
@@ -86,6 +91,20 @@ class CreateController extends Controller
$oldTriggers = [];
$oldActions = [];
// build triggers from query, if present.
$query = (string) $request->get('from_query');
if ('' !== $query) {
$search = app(SearchInterface::class);
$search->parseQuery($query);
$words = $search->getWordsAsString();
$operators = $search->getOperators()->toArray();
if ('' !== $words) {
session()->flash('warning', trans('firefly.rule_from_search_words', ['string' => $words]));
array_push($operators, ['type' => 'description_contains', 'value' => $words]);
}
$oldTriggers = $this->parseFromOperators($operators);
}
// restore actions and triggers from old input:
if ($request->old()) {
$oldTriggers = $this->getPreviousTriggers($request);
@@ -183,8 +202,8 @@ class CreateController extends Controller
$subTitle = (string) trans('firefly.make_new_rule_no_group');
// get triggers and actions for journal.
$oldTriggers = $this->getTriggersForJournal($journal);
$oldActions = [];
$oldTriggers = $this->getTriggersForJournal($journal);
$oldActions = [];
$this->createDefaultRuleGroup();
$this->createDefaultRule();
@@ -271,4 +290,45 @@ class CreateController extends Controller
return $redirect;
}
/**
* @param array $submittedOperators
* @return array
*/
private function parseFromOperators(array $submittedOperators): array
{
// TODO duplicated code.
$operators = config('firefly.search.operators');
$renderedEntries = [];
$triggers = [];
foreach ($operators as $key => $operator) {
if ('user_action' !== $key && false === $operator['alias']) {
$triggers[$key] = (string) trans(sprintf('firefly.rule_trigger_%s_choice', $key));
}
}
asort($triggers);
$index = 0;
foreach ($submittedOperators as $operator) {
try {
$renderedEntries[] = view(
'rules.partials.trigger',
[
'oldTrigger' => OperatorQuerySearch::getRootOperator($operator['type']),
'oldValue' => $operator['value'],
'oldChecked' => 1 === (int) ($oldTrigger['stop_processing'] ?? '0'),
'count' => $index + 1,
'triggers' => $triggers,
]
)->render();
} catch (Throwable $e) {
Log::debug(sprintf('Throwable was thrown in getPreviousTriggers(): %s', $e->getMessage()));
Log::error($e->getTraceAsString());
}
$index++;
}
return $renderedEntries;
}
}

View File

@@ -30,6 +30,8 @@ use FireflyIII\Models\Rule;
use FireflyIII\Repositories\Rule\RuleRepositoryInterface;
use FireflyIII\Support\Http\Controllers\RenderPartialViews;
use FireflyIII\Support\Http\Controllers\RuleManagement;
use FireflyIII\Support\Search\OperatorQuerySearch;
use FireflyIII\Support\Search\SearchInterface;
use Illuminate\Contracts\View\Factory;
use Illuminate\Http\RedirectResponse;
use Illuminate\Http\Request;
@@ -81,15 +83,31 @@ class EditController extends Controller
$actionCount = 0;
$oldActions = [];
$oldTriggers = [];
// build triggers from query, if present.
$query = (string) $request->get('from_query');
if ('' !== $query) {
$search = app(SearchInterface::class);
$search->parseQuery($query);
$words = $search->getWordsAsString();
$operators = $search->getOperators()->toArray();
if ('' !== $words) {
session()->flash('warning', trans('firefly.rule_from_search_words', ['string' => $words]));
array_push($operators, ['type' => 'description_contains', 'value' => $words]);
}
$oldTriggers = $this->parseFromOperators($operators);
}
// has old input?
if (count($request->old()) > 0) {
$oldTriggers = $this->getPreviousTriggers($request);
$triggerCount = count($oldTriggers);
$oldActions = $this->getPreviousActions($request);
$actionCount = count($oldActions);
}
$triggerCount = count($oldTriggers);
$actionCount = count($oldActions);
// overrule old input when it has no rule data:
// overrule old input and query data when it has no rule data:
if (0 === $triggerCount && 0 === $actionCount) {
$oldTriggers = $this->getCurrentTriggers($rule);
$triggerCount = count($oldTriggers);
@@ -146,4 +164,45 @@ class EditController extends Controller
return $redirect;
}
/**
* @param array $submittedOperators
* @return array
*/
private function parseFromOperators(array $submittedOperators): array
{
// TODO duplicated code.
$operators = config('firefly.search.operators');
$renderedEntries = [];
$triggers = [];
foreach ($operators as $key => $operator) {
if ('user_action' !== $key && false === $operator['alias']) {
$triggers[$key] = (string) trans(sprintf('firefly.rule_trigger_%s_choice', $key));
}
}
asort($triggers);
$index = 0;
foreach ($submittedOperators as $operator) {
try {
$renderedEntries[] = view(
'rules.partials.trigger',
[
'oldTrigger' => OperatorQuerySearch::getRootOperator($operator['type']),
'oldValue' => $operator['value'],
'oldChecked' => 1 === (int) ($oldTrigger['stop_processing'] ?? '0'),
'count' => $index + 1,
'triggers' => $triggers,
]
)->render();
} catch (Throwable $e) {
Log::debug(sprintf('Throwable was thrown in getPreviousTriggers(): %s', $e->getMessage()));
Log::error($e->getTraceAsString());
}
$index++;
}
return $renderedEntries;
}
}

View File

@@ -26,6 +26,7 @@ use Carbon\Carbon;
use FireflyIII\Models\Account;
use FireflyIII\Repositories\Account\AccountRepositoryInterface;
use FireflyIII\Repositories\User\UserRepositoryInterface;
use FireflyIII\Support\Search\OperatorQuerySearch;
use League\CommonMark\CommonMarkConverter;
use Route;
use Twig\Extension\AbstractExtension;
@@ -64,9 +65,20 @@ class General extends AbstractExtension
$this->formatDate(),
$this->getMetaField(),
$this->hasRole(),
$this->getRootSearchOperator(),
];
}
protected function getRootSearchOperator(): TwigFunction
{
return new TwigFunction(
'getRootSearchOperator',
static function (string $operator): string {
return OperatorQuerySearch::getRootOperator($operator);
}
);
}
/**
* Will return "active" when a part of the route matches the argument.
* ie. "accounts" will match "accounts.index".