mirror of
				https://github.com/firefly-iii/firefly-iii.git
				synced 2025-10-31 18:54:58 +00:00 
			
		
		
		
	Add new rule engine to API commands.
This commit is contained in:
		| @@ -34,6 +34,7 @@ use FireflyIII\Models\RuleGroup; | ||||
| use FireflyIII\Repositories\Account\AccountRepositoryInterface; | ||||
| use FireflyIII\Repositories\RuleGroup\RuleGroupRepositoryInterface; | ||||
| use FireflyIII\TransactionRules\Engine\RuleEngine; | ||||
| use FireflyIII\TransactionRules\Engine\RuleEngineInterface; | ||||
| use FireflyIII\TransactionRules\TransactionMatcher; | ||||
| use FireflyIII\Transformers\RuleGroupTransformer; | ||||
| use FireflyIII\Transformers\RuleTransformer; | ||||
| @@ -316,32 +317,28 @@ class RuleGroupController extends Controller | ||||
|  | ||||
|         /** @var Collection $collection */ | ||||
|         $collection = $this->ruleGroupRepository->getActiveRules($group); | ||||
|         $rules      = []; | ||||
|         /** @var Rule $item */ | ||||
|         foreach ($collection as $item) { | ||||
|             $rules[] = $item->id; | ||||
|         } | ||||
|  | ||||
|         // start looping. | ||||
|         /** @var RuleEngine $ruleEngine */ | ||||
|         $ruleEngine = app(RuleEngine::class); | ||||
|         $ruleEngine->setUser(auth()->user()); | ||||
|         $ruleEngine->setRulesToApply($rules); | ||||
|         $ruleEngine->setTriggerMode(RuleEngine::TRIGGER_STORE); | ||||
|         $ruleEngine = app(RuleEngineInterface::class); | ||||
|         $ruleEngine->setRules($collection); | ||||
|  | ||||
|         /** @var GroupCollectorInterface $collector */ | ||||
|         $collector = app(GroupCollectorInterface::class); | ||||
|         $collector->setAccounts($parameters['accounts']); | ||||
|         $collector->setRange($parameters['start_date'], $parameters['end_date']); | ||||
|         $journals = $collector->getExtractedJournals(); | ||||
|  | ||||
|         /** @var array $journal */ | ||||
|         foreach ($journals as $journal) { | ||||
|             Log::debug('Start of new journal.'); | ||||
|             $ruleEngine->processJournalArray($journal); | ||||
|             Log::debug('Done with all rules for this group + done with journal.'); | ||||
|         // overrule the rule(s) if necessary. | ||||
|         if (array_key_exists('start', $parameters) && null !== $parameters['start'] ) { | ||||
|             // add a range: | ||||
|             $ruleEngine->addOperator(['type' => 'date_after', 'value' => $parameters['start']->format('Y-m-d')]); | ||||
|         } | ||||
|  | ||||
|         if (array_key_exists('end', $parameters)  && null !== $parameters['end']) { | ||||
|             // add a range: | ||||
|             $ruleEngine->addOperator(['type' => 'date_before', 'value' => $parameters['end']->format('Y-m-d')]); | ||||
|         } | ||||
|         if (array_key_exists('accounts', $parameters) && '' !== $parameters['accounts']) { | ||||
|             $ruleEngine->addOperator(['type' => 'account_id', 'value' => $parameters['accounts']]); | ||||
|         } | ||||
|  | ||||
|         // file the rule(s) | ||||
|         $ruleEngine->fire(); | ||||
|  | ||||
|         return response()->json([], 204); | ||||
|     } | ||||
|  | ||||
|   | ||||
| @@ -40,6 +40,7 @@ use Log; | ||||
| class RuleGroupTriggerRequest extends FormRequest | ||||
| { | ||||
|     use ConvertsDataTypes; | ||||
|  | ||||
|     /** | ||||
|      * Authorize logged in users. | ||||
|      * | ||||
| @@ -57,9 +58,9 @@ class RuleGroupTriggerRequest extends FormRequest | ||||
|     public function getTriggerParameters(): array | ||||
|     { | ||||
|         return [ | ||||
|             'start_date' => $this->getDate('start_date'), | ||||
|             'end_date'   => $this->getDate('end_date'), | ||||
|             'accounts'   => $this->getAccounts(), | ||||
|             'start'    => $this->getDate('start'), | ||||
|             'end'      => $this->getDate('end'), | ||||
|             'accounts' => $this->getAccounts(), | ||||
|         ]; | ||||
|     } | ||||
|  | ||||
| @@ -69,33 +70,17 @@ class RuleGroupTriggerRequest extends FormRequest | ||||
|     public function rules(): array | ||||
|     { | ||||
|         return [ | ||||
|             'start_date' => 'required|date', | ||||
|             'end_date'   => 'required|date|after:start_date', | ||||
|             'start' => 'date', | ||||
|             'end'   => 'date|after:start', | ||||
|         ]; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @return Collection | ||||
|      * @return string | ||||
|      */ | ||||
|     private function getAccounts(): Collection | ||||
|     private function getAccounts(): string | ||||
|     { | ||||
|         $accountList = '' === (string) $this->query('accounts') ? [] : explode(',', $this->query('accounts')); | ||||
|         $accounts    = new Collection; | ||||
|  | ||||
|         /** @var AccountRepositoryInterface $accountRepository */ | ||||
|         $accountRepository = app(AccountRepositoryInterface::class); | ||||
|  | ||||
|         foreach ($accountList as $accountId) { | ||||
|             Log::debug(sprintf('Searching for asset account with id "%s"', $accountId)); | ||||
|             $account = $accountRepository->findNull((int) $accountId); | ||||
|             if ($this->validAccount($account)) { | ||||
|                 /** @noinspection NullPointerExceptionInspection */ | ||||
|                 Log::debug(sprintf('Found account #%d ("%s") and its an asset account', $account->id, $account->name)); | ||||
|                 $accounts->push($account); | ||||
|             } | ||||
|         } | ||||
|  | ||||
|         return $accounts; | ||||
|         return (string) $this->query('accounts'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
| @@ -106,19 +91,7 @@ class RuleGroupTriggerRequest extends FormRequest | ||||
|     private function getDate(string $field): ?Carbon | ||||
|     { | ||||
|         /** @var Carbon $result */ | ||||
|         $result = null === $this->query($field) ? null : Carbon::createFromFormat('Y-m-d', $this->query($field)); | ||||
|  | ||||
|         return $result; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param Account|null $account | ||||
|      * | ||||
|      * @return bool | ||||
|      */ | ||||
|     private function validAccount(?Account $account): bool | ||||
|     { | ||||
|         return null !== $account && AccountType::ASSET === $account->accountType->type; | ||||
|         return null === $this->query($field) ? null : Carbon::createFromFormat('Y-m-d', $this->query($field)); | ||||
|     } | ||||
|  | ||||
| } | ||||
|   | ||||
| @@ -87,10 +87,7 @@ class RuleTriggerRequest extends FormRequest | ||||
|      */ | ||||
|     private function getDate(string $field): ?Carbon | ||||
|     { | ||||
|         /** @var Carbon $result */ | ||||
|         $result = null === $this->query($field) ? null : Carbon::createFromFormat('Y-m-d', $this->query($field)); | ||||
|  | ||||
|         return $result; | ||||
|         return null === $this->query($field) ? null : Carbon::createFromFormat('Y-m-d', $this->query($field)); | ||||
|     } | ||||
|  | ||||
| } | ||||
|   | ||||
| @@ -58,6 +58,7 @@ class ConvertToDeposit implements ActionInterface | ||||
|      * | ||||
|      * @param TransactionJournal $journal | ||||
|      * @deprecated | ||||
|      * @codeCoverageIgnore | ||||
|      * @return bool | ||||
|      * @throws FireflyException | ||||
|      */ | ||||
|   | ||||
| @@ -94,6 +94,7 @@ class SearchRuleEngine implements RuleEngineInterface | ||||
|         foreach ($this->rules as $rule) { | ||||
|             $this->fireRule($rule); | ||||
|         } | ||||
|         Log::debug('SearchRuleEngine:: done processing all rules!'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
| @@ -102,14 +103,17 @@ class SearchRuleEngine implements RuleEngineInterface | ||||
|      */ | ||||
|     private function fireRule(Rule $rule): void | ||||
|     { | ||||
|         Log::debug(sprintf('SearchRuleEngine::fireRule(%d)!', $rule->id)); | ||||
|         $searchArray = []; | ||||
|         /** @var RuleTrigger $ruleTrigger */ | ||||
|         foreach ($rule->ruleTriggers as $ruleTrigger) { | ||||
|             Log::debug(sprintf('SearchRuleEngine:: add a rule trigger: %s:"%s"', $ruleTrigger->trigger_type, $ruleTrigger->trigger_value)); | ||||
|             $searchArray[$ruleTrigger->trigger_type] = sprintf('"%s"', $ruleTrigger->trigger_value); | ||||
|         } | ||||
|  | ||||
|         // add local operators: | ||||
|         foreach ($this->operators as $operator) { | ||||
|             Log::debug(sprintf('SearchRuleEngine:: add local added operator: %s:"%s"', $operator['type'], $operator['value'])); | ||||
|             $searchArray[$operator['type']] = sprintf('"%s"', $operator['value']); | ||||
|         } | ||||
|         $toJoin = []; | ||||
| @@ -118,20 +122,21 @@ class SearchRuleEngine implements RuleEngineInterface | ||||
|         } | ||||
|  | ||||
|         $searchQuery = join(' ', $toJoin); | ||||
|         Log::debug(sprintf('Search query for rule #%d ("%s") = %s', $rule->id, $rule->title, $searchQuery)); | ||||
|         Log::debug(sprintf('SearchRuleEngine:: Search query for rule #%d ("%s") = %s', $rule->id, $rule->title, $searchQuery)); | ||||
|  | ||||
|         // build and run the search engine. | ||||
|         $searchEngine = app(SearchInterface::class); | ||||
|         $searchEngine->setUser($this->user); | ||||
|         $searchEngine->setPage(1); | ||||
|         $searchEngine->setLimit(1337); | ||||
|         $searchEngine->setLimit(31337); | ||||
|         $searchEngine->parseQuery($searchQuery); | ||||
|  | ||||
|         $result     = $searchEngine->searchTransactions(); | ||||
|         $collection = $result->getCollection(); | ||||
|         Log::debug(sprintf('Found %d transactions using search engine.', $collection->count())); | ||||
|         Log::debug(sprintf('SearchRuleEngine:: Found %d transactions using search engine with query "%s".', $collection->count(), $searchQuery)); | ||||
|  | ||||
|         $this->processResults($rule, $collection); | ||||
|         Log::debug(sprintf('SearchRuleEngine:: done processing rule #%d', $rule->id)); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
| @@ -141,7 +146,7 @@ class SearchRuleEngine implements RuleEngineInterface | ||||
|      */ | ||||
|     private function processResults(Rule $rule, Collection $collection): void | ||||
|     { | ||||
|         Log::debug('Going to process results.'); | ||||
|         Log::debug(sprintf('SearchRuleEngine:: Going to process %d results.', $collection->count())); | ||||
|         /** @var array $group */ | ||||
|         foreach ($collection as $group) { | ||||
|             $this->processTransactionGroup($rule, $group); | ||||
| @@ -155,7 +160,7 @@ class SearchRuleEngine implements RuleEngineInterface | ||||
|      */ | ||||
|     private function processTransactionGroup(Rule $rule, array $group): void | ||||
|     { | ||||
|         Log::debug(sprintf('Will now execute actions on transaction group #%d', $group['id'])); | ||||
|         Log::debug(sprintf('SearchRuleEngine:: Will now execute actions on transaction group #%d', $group['id'])); | ||||
|         /** @var array $transaction */ | ||||
|         foreach ($group['transactions'] as $transaction) { | ||||
|             $this->processTransactionJournal($rule, $transaction); | ||||
| @@ -169,7 +174,7 @@ class SearchRuleEngine implements RuleEngineInterface | ||||
|      */ | ||||
|     private function processTransactionJournal(Rule $rule, array $transaction): void | ||||
|     { | ||||
|         Log::debug(sprintf('Will now execute actions on transaction journal #%d', $transaction['transaction_journal_id'])); | ||||
|         Log::debug(sprintf('SearchRuleEngine:: Will now execute actions on transaction journal #%d', $transaction['transaction_journal_id'])); | ||||
|         /** @var RuleAction $ruleAction */ | ||||
|         foreach ($rule->ruleActions as $ruleAction) { | ||||
|             $break = $this->processRuleAction($ruleAction, $transaction); | ||||
|   | ||||
		Reference in New Issue
	
	Block a user