mirror of
https://github.com/firefly-iii/firefly-iii.git
synced 2025-01-27 16:56:46 -06:00
Code for #3052
This commit is contained in:
parent
0c13ac2e93
commit
ac931698d3
@ -25,7 +25,9 @@ namespace FireflyIII\Http\Controllers\Transaction;
|
||||
|
||||
|
||||
use FireflyIII\Http\Controllers\Controller;
|
||||
use FireflyIII\Models\TransactionGroup;
|
||||
use FireflyIII\Repositories\Account\AccountRepositoryInterface;
|
||||
use FireflyIII\Services\Internal\Update\GroupCloneService;
|
||||
|
||||
/**
|
||||
* Class CreateController
|
||||
@ -34,6 +36,7 @@ class CreateController extends Controller
|
||||
{
|
||||
/**
|
||||
* CreateController constructor.
|
||||
*
|
||||
* @codeCoverageIgnore
|
||||
*/
|
||||
public function __construct()
|
||||
@ -55,6 +58,21 @@ class CreateController extends Controller
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param TransactionGroup $group
|
||||
*
|
||||
* @return \Illuminate\Http\RedirectResponse|\Illuminate\Routing\Redirector
|
||||
*/
|
||||
public function cloneGroup(TransactionGroup $group)
|
||||
{
|
||||
|
||||
/** @var GroupCloneService $service */
|
||||
$service = app(GroupCloneService::class);
|
||||
$newGroup = $service->cloneGroup($group);
|
||||
|
||||
return redirect(route('transactions.show', [$newGroup->id]));
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a new transaction group.
|
||||
*
|
||||
|
146
app/Services/Internal/Update/GroupCloneService.php
Normal file
146
app/Services/Internal/Update/GroupCloneService.php
Normal file
@ -0,0 +1,146 @@
|
||||
<?php
|
||||
/**
|
||||
* GroupCloneService.php
|
||||
* Copyright (c) 2019 thegrumpydictator@gmail.com
|
||||
*
|
||||
* This file is part of Firefly III (https://github.com/firefly-iii).
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace FireflyIII\Services\Internal\Update;
|
||||
|
||||
use Carbon\Carbon;
|
||||
use FireflyIII\Models\Budget;
|
||||
use FireflyIII\Models\Category;
|
||||
use FireflyIII\Models\Note;
|
||||
use FireflyIII\Models\Tag;
|
||||
use FireflyIII\Models\Transaction;
|
||||
use FireflyIII\Models\TransactionGroup;
|
||||
use FireflyIII\Models\TransactionJournal;
|
||||
use FireflyIII\Models\TransactionJournalMeta;
|
||||
|
||||
/**
|
||||
* Class GroupCloneService
|
||||
* TODO test.
|
||||
*/
|
||||
class GroupCloneService
|
||||
{
|
||||
/**
|
||||
* @param TransactionGroup $group
|
||||
*
|
||||
* @return TransactionGroup
|
||||
*/
|
||||
public function cloneGroup(TransactionGroup $group): TransactionGroup
|
||||
{
|
||||
$newGroup = $group->replicate();
|
||||
$newGroup->save();
|
||||
foreach ($group->transactionJournals as $journal) {
|
||||
$this->cloneJournal($journal, $newGroup, (int)$group->id);
|
||||
}
|
||||
|
||||
|
||||
return $newGroup;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param TransactionJournal $journal
|
||||
* @param TransactionGroup $newGroup
|
||||
* @param int $originalGroup
|
||||
*/
|
||||
private function cloneJournal(TransactionJournal $journal, TransactionGroup $newGroup, int $originalGroup): void
|
||||
{
|
||||
$newJournal = $journal->replicate();
|
||||
$newJournal->transaction_group_id = $newGroup->id;
|
||||
$newJournal->date = Carbon::now();
|
||||
$newJournal->save();
|
||||
|
||||
foreach ($journal->transactions as $transaction) {
|
||||
$this->cloneTransaction($transaction, $newJournal);
|
||||
}
|
||||
|
||||
// clone notes
|
||||
/** @var Note $note */
|
||||
foreach ($journal->notes as $note) {
|
||||
$this->cloneNote($note, $newJournal, $originalGroup);
|
||||
}
|
||||
// clone location (not yet available)
|
||||
|
||||
// clone meta
|
||||
/** @var TransactionJournalMeta $meta */
|
||||
foreach ($journal->transactionJournalMeta as $meta) {
|
||||
$this->cloneMeta($meta, $newJournal);
|
||||
}
|
||||
// clone category
|
||||
/** @var Category $category */
|
||||
foreach ($journal->categories as $category) {
|
||||
$newJournal->categories()->save($category);
|
||||
}
|
||||
|
||||
// clone budget
|
||||
/** @var Budget $budget */
|
||||
foreach ($journal->budgets as $budget) {
|
||||
$newJournal->budgets()->save($budget);
|
||||
}
|
||||
// clone links (ongoing).
|
||||
|
||||
// clone tags
|
||||
/** @var Tag $tag */
|
||||
foreach ($journal->tags as $tag) {
|
||||
$newJournal->tags()->save($tag);
|
||||
}
|
||||
// add note saying "cloned".
|
||||
|
||||
// add relation.
|
||||
}
|
||||
|
||||
/**
|
||||
* @param TransactionJournalMeta $meta
|
||||
* @param TransactionJournal $newJournal
|
||||
*/
|
||||
private function cloneMeta(TransactionJournalMeta $meta, TransactionJournal $newJournal): void
|
||||
{
|
||||
$newMeta = $meta->replicate();
|
||||
$newMeta->transaction_journal_id = $newJournal->id;
|
||||
if ('recurrence_id' !== $newMeta->name) {
|
||||
$newMeta->save();
|
||||
}
|
||||
}
|
||||
|
||||
private function cloneNote(Note $note, TransactionJournal $newJournal, int $oldGroupId): void
|
||||
{
|
||||
$newNote = $note->replicate();
|
||||
$newNote->text .= sprintf(
|
||||
"\n\n%s", trans('firefly.clones_journal_x', ['description' => $newJournal->description, 'id' => $oldGroupId])
|
||||
);
|
||||
$newNote->noteable_id = $newJournal->id;
|
||||
$newNote->save();
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* @param Transaction $transaction
|
||||
* @param TransactionJournal $newJournal
|
||||
*/
|
||||
private function cloneTransaction(Transaction $transaction, TransactionJournal $newJournal): void
|
||||
{
|
||||
$newTransaction = $transaction->replicate();
|
||||
$newTransaction->transaction_journal_id = $newJournal->id;
|
||||
$newTransaction->save();
|
||||
}
|
||||
|
||||
|
||||
}
|
@ -27,8 +27,14 @@ $(function () {
|
||||
makeAutoComplete();
|
||||
})
|
||||
$('[data-toggle="tooltip"]').tooltip();
|
||||
|
||||
$('#clone_button').click(cloneNewFunction);
|
||||
});
|
||||
|
||||
function cloneNewFunction() {
|
||||
return confirm(newCloneInstructions);
|
||||
}
|
||||
|
||||
function getLinkModal(e) {
|
||||
var button = $(e.currentTarget);
|
||||
var journalId = parseInt(button.data('journal'));
|
||||
|
@ -58,7 +58,8 @@ return [
|
||||
'no_rules_for_bill' => 'This bill has no rules associated to it.',
|
||||
'go_to_asset_accounts' => 'View your asset accounts',
|
||||
'go_to_budgets' => 'Go to your budgets',
|
||||
'clone_instructions' => 'To clone a transaction, search for the "store as new" checkbox in the edit screen',
|
||||
'new_clone_instructions' => 'This button will automatically clone the transaction and set the date to today. Are you sure?',
|
||||
'clones_journal_x' => 'This transaction is a clone of ":description" (#:id)',
|
||||
'go_to_categories' => 'Go to your categories',
|
||||
'go_to_bills' => 'Go to your bills',
|
||||
'go_to_expense_accounts' => 'See your expense accounts',
|
||||
|
@ -61,9 +61,8 @@
|
||||
|
||||
|
||||
{% if groupArray.transactions[0].type != 'opening balance' and groupArray.transactions[0].type != 'reconciliation' %}
|
||||
<!--CLONE-->
|
||||
<a href="#" class="btn btn-default" style="white-space: nowrap;" onclick="return false;" data-toggle="tooltip" data-placement="top" title="{{ 'clone_instructions' |_|escape}}">Clone</a>
|
||||
{#<a href="{{ route('transactions.clone', [transactionGroup.id]) }}" class="btn btn-default"><i class="fa fa-copy"></i> {{ 'clone'|_ }}</a>#}
|
||||
<!-- since 5.1.0 -->
|
||||
<a href="{{ route('transactions.clone', [transactionGroup.id]) }}" id="clone_button" class="btn btn-default"><i class="fa fa-copy"></i> {{ 'clone'|_ }}</a>
|
||||
{% endif %}
|
||||
{#
|
||||
<a href="{{ route('transactions.delete', [transactionGroup.id]) }}" class="btn btn-danger"><i class="fa fa-trash"></i> {{ 'delete'|_ }}</a>
|
||||
@ -415,6 +414,7 @@
|
||||
var modalDialogURI = '{{ route('transactions.link.modal', ['%JOURNAL%']) }}';
|
||||
var acURI = '{{ route('json.autocomplete.all-journals-with-id') }}';
|
||||
var groupURI = '{{ route('transactions.show',['%GROUP%']) }}';
|
||||
var newCloneInstructions = '{{ 'new_clone_instructions'|_|escape('js') }}';
|
||||
</script>
|
||||
<script type="text/javascript" src="v1/js/lib/typeahead/typeahead.bundle.min.js?v={{ FF_VERSION }}" nonce="{{ JS_NONCE }}"></script>
|
||||
<script type="text/javascript" src="v1/js/ff/transactions/show.js?v={{ FF_VERSION }}" nonce="{{ JS_NONCE }}"></script>
|
||||
|
@ -963,6 +963,9 @@ Route::group(
|
||||
Route::get('create/{objectType}', ['uses' => 'Transaction\CreateController@create', 'as' => 'create']);
|
||||
Route::post('store', ['uses' => 'Transaction\CreateController@store', 'as' => 'store']);
|
||||
|
||||
// clone group
|
||||
Route::get('clone/{transactionGroup}', ['uses' => 'Transaction\CreateController@cloneGroup', 'as' => 'clone']);
|
||||
|
||||
// edit group
|
||||
Route::get('edit/{transactionGroup}', ['uses' => 'Transaction\EditController@edit', 'as' => 'edit']);
|
||||
Route::post('update', ['uses' => 'Transaction\EditController@update', 'as' => 'update']);
|
||||
@ -971,17 +974,6 @@ Route::group(
|
||||
Route::get('delete/{transactionGroup}', ['uses' => 'Transaction\DeleteController@delete', 'as' => 'delete']);
|
||||
Route::post('destroy/{transactionGroup}', ['uses' => 'Transaction\DeleteController@destroy', 'as' => 'destroy']);
|
||||
|
||||
// clone group:
|
||||
//Route::get('clone/{transactionGroup}', ['uses' => 'Transaction\CloneController@clone', 'as' => 'clone']);
|
||||
|
||||
//Route::get('debug/{tj}', ['uses' => 'Transaction\SingleController@debugShow', 'as' => 'debug']);
|
||||
//Route::get('debug/{tj}', ['uses' => 'Transaction\SingleController@debugShow', 'as' => 'debug']);
|
||||
|
||||
//Route::post('reorder', ['uses' => 'TransactionController@reorder', 'as' => 'reorder']);
|
||||
//Route::post('reconcile', ['uses' => 'TransactionController@reconcile', 'as' => 'reconcile']);
|
||||
// TODO end of improvement.
|
||||
|
||||
|
||||
Route::get('show/{transactionGroup}', ['uses' => 'Transaction\ShowController@show', 'as' => 'show']);
|
||||
}
|
||||
);
|
||||
|
Loading…
Reference in New Issue
Block a user