akaunting 3.0 (the last dance)

This commit is contained in:
Burak Civan
2022-06-01 10:15:55 +03:00
parent cead09f6d4
commit d9c0764572
3812 changed files with 126831 additions and 102949 deletions

View File

@ -0,0 +1,30 @@
<?php
namespace App\Http\ViewComposers;
use App\Http\Controllers\Purchases\Vendors;
use App\Http\Controllers\Sales\Customers;
use Illuminate\View\View;
class ContactType
{
/**
* Bind data to the view.
*
* @param View $view
* @return void
*/
public function compose(View $view)
{
$route = request()->route();
if (empty($route)) {
return;
}
/** @var Customers|Vendors $controller */
$controller = $route->getController();
$view->with(['type' => $controller->type ?? '']);
}
}

View File

@ -0,0 +1,50 @@
<?php
namespace App\Http\ViewComposers;
use Illuminate\View\View;
use Illuminate\Support\Str;
class DocumentRecurring
{
/**
* Bind data to the view.
*
* @param View $view
* @return void
*/
public function compose(View $view)
{
$route = request()->route();
if (empty($route)) {
return;
}
/** @var Invoices|Bills|PortalInvoices $controller */
$controller = $route->getController();
$type = $controller->type ?? '';
if (! Str::contains($type, 'recurring')) {
return;
}
$payment_terms = [
'0' => trans('settings.invoice.due_receipt'),
'15' => trans('settings.invoice.due_days', ['days' => 15]),
'30' => trans('settings.invoice.due_days', ['days' => 30]),
'45' => trans('settings.invoice.due_days', ['days' => 45]),
'60' => trans('settings.invoice.due_days', ['days' => 60]),
'90' => trans('settings.invoice.due_days', ['days' => 90]),
];
$view->with([
'type' => $type,
'payment_terms' => $payment_terms,
]);
// Override the whole file
$view->setPath(view('components.documents.form.recurring_metadata', compact('type', 'payment_terms'))->getPath());
}
}

View File

@ -1,104 +0,0 @@
<?php
namespace App\Http\ViewComposers;
use App\Traits\Modules;
use App\Utilities\Versions;
use Illuminate\View\View;
class Header
{
use Modules;
/**
* Bind data to the view.
*
* @param View $view
* @return void
*/
public function compose(View $view)
{
$user = user();
$new_apps = $invoices = $bills = $exports = $imports = [];
$updates = $notifications = 0;
$company = null;
if (!empty($user)) {
// Get customer company
if ($user->isCustomer()) {
$company = (object) [
'company_name' => setting('company.name'),
'company_email' => setting('company.email'),
'company_address' => setting('company.address'),
'company_logo' => setting('company.logo'),
];
}
if ($user->can('read-common-notifications')) {
$unreads = $user->unreadNotifications;
foreach ($unreads as $unread) {
$data = $unread->getAttribute('data');
switch ($unread->getAttribute('type')) {
case 'App\Notifications\Common\ExportCompleted':
$exports['completed'][$data['file_name']] = $data['download_url'];
$notifications++;
break;
case 'App\Notifications\Common\ExportFailed':
$exports['failed'][] = $data['message'];
$notifications++;
break;
case 'App\Notifications\Common\ImportCompleted':
$imports['completed'][] = $data['translation'];
$notifications++;
break;
case 'App\Notifications\Common\ImportFailed':
$imports['failed'][] = '';
$notifications++;
break;
case 'App\Notifications\Purchase\Bill':
$bills[$data['bill_id']] = $data['amount'];
$notifications++;
break;
case 'App\Notifications\Sale\Invoice':
$invoices[$data['invoice_id']] = $data['amount'];
$notifications++;
break;
}
}
$new_apps = $this->getNotifications('new-apps');
foreach ($new_apps as $key => $new_app) {
if (setting('notifications.' . user()->id . '.' . $new_app->alias)) {
unset($new_apps[$key]);
continue;
}
$notifications++;
}
}
if ($user->can('read-install-updates')) {
$updates = count(Versions::getUpdates());
}
$this->loadSuggestions();
}
$view->with([
'user' => $user,
'notifications' => $notifications,
'new_apps' => $new_apps,
'exports' => $exports,
'imports' => $imports,
'bills' => $bills,
'invoices' => $invoices,
'company' => $company,
'updates' => $updates,
]);
}
}

View File

@ -1,86 +0,0 @@
<?php
namespace App\Http\ViewComposers;
use Akaunting\Module\Module;
use App\Events\Common\BulkActionsAdding;
use Date;
use Illuminate\Support\Str;
use Illuminate\View\View;
class Index
{
/**
* Bind data to the view.
*
* @param View $view
* @return void
*/
public function compose(View $view)
{
$this->addLimits($view);
$this->addBulkActions($view);
}
protected function addLimits(&$view)
{
$limits = ['10' => '10', '25' => '25', '50' => '50', '100' => '100'];
$now = Date::now();
$this_year = $now->year;
$years = [];
$y = $now->addYears(2);
for ($i = 0; $i < 10; $i++) {
$years[$y->year] = $y->year;
$y->subYear();
}
$view->with(['limits' => $limits, 'this_year' => $this_year, 'years' => $years]);
}
protected function addBulkActions(&$view)
{
$class_name = '';
$view_name = str_replace('.index', '', $view->getName());
if (Str::contains($view_name, '::')) {
// my-blog::posts
$names = explode('::', $view_name);
$module = module($names[0]);
if (!$module instanceof Module) {
return;
}
$tmp = explode('.', $names[1]);
$file_name = !empty($tmp[1]) ? Str::studly($tmp[0]) . '\\' . Str::studly($tmp[1]) : Str::studly($tmp[0]);
$class_name = 'Modules\\' . $module->getStudlyName() . '\BulkActions\\' . $file_name;
} else {
// common.items
$tmp = explode('.', $view_name);
$file_name = !empty($tmp[1]) ? Str::studly($tmp[0]) . '\\' . Str::studly($tmp[1]) : Str::studly($tmp[0]);
$class_name = 'App\BulkActions\\' . $file_name;
}
if (class_exists($class_name)) {
event(new BulkActionsAdding(app($class_name)));
$bulk_actions = app($class_name)->actions;
} else {
$b = new \stdClass();
$b->actions = [];
event(new BulkActionsAdding($b));
$bulk_actions = $b->actions;
}
$view->with(['bulk_actions' => $bulk_actions]);
}
}

View File

@ -1,72 +0,0 @@
<?php
namespace App\Http\ViewComposers;
use App\Models\Common\Media;
use File;
use Image;
use Storage;
use Illuminate\View\View;
use Illuminate\Support\Facades\Log;
use Intervention\Image\Exception\NotReadableException;
class Logo
{
/**
* Bind data to the view.
*
* @param View $view
* @return void
*/
public function compose(View $view)
{
$logo = '';
$media = Media::find(setting('company.logo'));
if (!empty($media)) {
$path = $media->getDiskPath();
if (Storage::missing($path)) {
return $logo;
}
} else {
$path = base_path('public/img/company.png');
}
try {
$image = Image::cache(function($image) use ($media, $path) {
$width = setting('invoice.logo_size_width');
$height = setting('invoice.logo_size_height');
if ($media) {
$image->make(Storage::get($path))->resize($width, $height)->encode();
} else {
$image->make($path)->resize($width, $height)->encode();
}
});
} catch (NotReadableException | \Exception $e) {
Log::info('Company ID: ' . company_id() . ' viewcomposer/logo.php exception.');
Log::info($e->getMessage());
$path = base_path('public/img/company.png');
$image = Image::cache(function($image) use ($path) {
$width = setting('invoice.logo_size_width');
$height = setting('invoice.logo_size_height');
$image->make($path)->resize($width, $height)->encode();
});
}
if (empty($image)) {
return $logo;
}
$extension = File::extension($path);
$logo = 'data:image/' . $extension . ';base64,' . base64_encode($image);
$view->with(['logo' => $logo]);
}
}

View File

@ -1,26 +0,0 @@
<?php
namespace App\Http\ViewComposers;
use Illuminate\View\View;
class Menu
{
/**
* Bind data to the view.
*
* @param View $view
* @return void
*/
public function compose(View $view)
{
// Get user companies
if ($user = user()) {
$companies = $user->companies()->enabled()->limit(10)->get()->sortBy('name');
} else {
$companies = [];
}
$view->with(['companies' => $companies]);
}
}

View File

@ -1,35 +0,0 @@
<?php
namespace App\Http\ViewComposers;
use App\Traits\Modules as RemoteModules;
use Cache;
use Date;
use Illuminate\View\View;
class Modules
{
use RemoteModules;
/**
* Bind data to the view.
*
* @param View $view
* @return void
*/
public function compose(View $view)
{
if (setting('apps.api_key')) {
$categories = Cache::remember('modules.categories.' . language()->getShortCode(), Date::now()->addHour(6), function () {
return collect($this->getCategoriesOfModules())->pluck('name', 'slug')
->prepend(trans('general.all_type', ['type' => trans_choice('general.categories', 2)]), '*');
});
} else {
$categories = collect([
'*' => trans('general.all_type', ['type' => trans_choice('general.categories', 2)]),
]);
}
$view->with(['categories' => $categories]);
}
}

View File

@ -1,50 +0,0 @@
<?php
namespace App\Http\ViewComposers;
use App\Traits\Modules;
use Illuminate\Support\Facades\Route;
use Illuminate\View\View;
class Notifications
{
use Modules;
/**
* Bind data to the view.
*
* @param View $view
* @return void
*/
public function compose(View $view)
{
// No need to add suggestions in console
if (app()->runningInConsole() || !config('app.installed') || !user()) {
return;
}
if (!$path = Route::current()->uri()) {
return;
}
$path = str_replace('{company_id}/', '', $path);
$notifications = $this->getNotifications($path);
// Push to a stack
foreach ($notifications as $notification) {
$path = str_replace('/', '#', $notification->path);
$message = str_replace('#path#', $path, $notification->message);
$message = str_replace('#token#', csrf_token(), $message);
$message = str_replace('#url#', route('dashboard'), $message);
$message = str_replace('#company_id#', company_id(), $message);
if (!setting('notifications.' . $notification->path . '.' . $notification->id . '.status', 1)) {
continue;
}
$view->getFactory()->startPush('content_content_start', $message);
}
}
}

View File

@ -12,6 +12,12 @@ class ReadOnlyNotification
return;
}
$view->getFactory()->startPush('content_content_start', view('partials.read-only'));
$notifications = $view->getData()['notifications'];
$notifications[] = view('components.read-only');
$view->with([
'notifications' => $notifications,
]);
}
}

View File

@ -1,36 +0,0 @@
<?php
namespace App\Http\ViewComposers;
use Illuminate\View\View;
class Recurring
{
/**
* Bind data to the view.
*
* @param View $view
* @return void
*/
public function compose(View $view)
{
$recurring_frequencies = [
'no' => trans('general.no'),
'daily' => trans('recurring.daily'),
'weekly' => trans('recurring.weekly'),
'monthly' => trans('recurring.monthly'),
'yearly' => trans('recurring.yearly'),
'custom' => trans('recurring.custom'),
];
$recurring_custom_frequencies = [
'daily' => trans('recurring.days'),
'weekly' => trans('recurring.weeks'),
'monthly' => trans('recurring.months'),
'yearly' => trans('recurring.years'),
];
$view->with(['recurring_frequencies' => $recurring_frequencies, 'recurring_custom_frequencies' => $recurring_custom_frequencies]);
}
}

View File

@ -1,33 +0,0 @@
<?php
namespace App\Http\ViewComposers;
use Date;
use Illuminate\View\View;
class Show
{
/**
* Bind data to the view.
*
* @param View $view
* @return void
*/
public function compose(View $view)
{
$limits = ['10' => '10', '25' => '25', '50' => '50', '100' => '100'];
$now = Date::now();
$this_year = $now->year;
$years = [];
$y = $now->addYears(2);
for ($i = 0; $i < 10; $i++) {
$years[$y->year] = $y->year;
$y->subYear();
}
$view->with(['limits' => $limits, 'this_year' => $this_year, 'years' => $years]);
}
}

View File

@ -1,58 +0,0 @@
<?php
namespace App\Http\ViewComposers;
use App\Traits\Modules;
use Illuminate\View\View;
use Route;
class Suggestions
{
use Modules;
/**
* Bind data to the view.
*
* @param View $view
* @return void
*/
public function compose(View $view)
{
// No need to add suggestions in console
if (app()->runningInConsole() || !config('app.installed')) {
return;
}
if ((!$user = user()) || $user->cannot('read-modules-home')) {
return;
}
if (!$path = Route::current()->uri()) {
return;
}
$path = str_replace('{company_id}/', '', $path);
if (!$suggestions = $this->getSuggestions($path)) {
return;
}
$modules = [];
foreach ($suggestions->modules as $s_module) {
if ($this->moduleIsEnabled($s_module->alias)) {
continue;
}
$s_module->action_url = company_id() . '/' . $s_module->action_url;
$modules[] = $s_module;
}
if (empty($modules)) {
return;
}
$view->getFactory()->startPush('header_button_end', view('partials.admin.suggestions', compact('modules')));
}
}

View File

@ -1,172 +0,0 @@
<?php
namespace App\Http\ViewComposers;
use Akaunting\Money\Currency as MoneyCurrency;
use App\Models\Common\Media;
use App\Models\Setting\Currency;
use App\Models\Setting\Tax;
use App\Traits\Modules;
use App\Models\Common\Company;
use Illuminate\View\View;
class Wizard
{
use Modules;
/**
* Bind data to the view.
*
* @param View $view
* @return void
*/
public function compose(View $view)
{
$translations = $this->getTransalations();
$currencies = $this->getCurrencies();
// Prepare codes
$codes = $this->getCurrencyCodes();
$taxes = $this->getTaxes();
$modules = $this->getFeaturedModules([
'query' => [
'limit' => 4
]
]);
$company = $this->getCompany();
$view->with([
'translations' => $translations,
'company' => $company,
'currencies' => $currencies,
'currency_codes' => $codes,
'taxes' => $taxes,
'modules' => $modules,
]);
}
/* Wizard page transactions */
protected function getTransalations()
{
return [
'company' => [
'title' => trans_choice('general.companies', 1),
'api_key' => trans('modules.api_key'),
'form_enter' => trans('general.form.enter'),
'get_api_key' => trans('modules.get_api_key'),
'tax_number' => trans('general.tax_number'),
'financial_start' => trans('settings.localisation.financial_start'),
'address' => trans('settings.company.address'),
'logo' => trans('settings.company.logo'),
'skip' => trans('general.skip'),
'save' => trans('general.save'),
'country' => trans_choice('general.countries', 1),
],
'currencies' => [
'title' => trans_choice('general.currencies', 2),
'add_new' => trans('general.add_new'),
'name' => trans('general.name'),
'code' => trans('currencies.code'),
'rate' => trans('currencies.rate'),
'enabled' => trans('general.enabled'),
'actions' => trans('general.actions') ,
'yes' => trans('general.yes'),
'no' => trans('general.no'),
'edit' => trans('general.edit'),
'delete' => trans('general.delete'),
'save' => trans('general.save'),
'precision' => trans('currencies.precision'),
'symbol' => trans('currencies.symbol.symbol'),
'position' => trans('currencies.symbol.position'),
'decimal_mark' => trans('currencies.decimal_mark'),
'thousands_separator' => trans('currencies.thousands_separator'),
'previous' => trans('pagination.previous'),
'next' => trans('pagination.next'),
'delete_confirm' => trans('general.delete_confirm'),
'cancel' => trans('general.cancel'),
],
'taxes' => [
'title' => trans_choice('general.taxes', 2),
'add_new' => trans('general.add_new'),
'name' => trans('general.name'),
'rate_percent' => trans('taxes.rate_percent'),
'enabled' => trans('general.enabled'),
'actions' => trans('general.actions'),
'yes' => trans('general.yes'),
'no' => trans('general.no'),
'edit' => trans('general.edit'),
'delete' => trans('general.delete'),
'name' => trans('general.name'),
'rate' => trans('currencies.rate'),
'enabled' => trans('general.enabled'),
'save' => trans('general.save'),
'previous' => trans('pagination.previous'),
'next' => trans('pagination.next'),
'cancel' => trans('general.cancel'),
],
'finish' => [
'title' => trans_choice('general.finish', 1),
'recommended_apps' => trans('modules.recommended_apps'),
'no_apps' => trans('modules.no_apps'),
'developer' => trans('modules.developer'),
'previous' => trans('pagination.previous'),
'go_to_dashboard' => trans('general.go_to_dashboard'),
'error_message' => trans('errors.title.500'),
]
];
}
protected function getCurrencies()
{
return Currency::all();
}
protected function getCurrencyCodes()
{
$codes = [];
$money_currencies = MoneyCurrency::getCurrencies();
foreach ($money_currencies as $key => $item) {
$codes[$key] = $key;
}
return $codes;
}
protected function getTaxes()
{
return Tax::all();
}
protected function getCompany()
{
$company = company();
$company->api_key = setting('apps.api_key');
$company->financial_start = setting('localisation.financial_start');
$logo_id = setting('company.logo');
$logo = false;
if ($logo_id) {
$logo = Media::find($logo_id);
if ($logo) {
$logo->path = route('uploads.get', $logo->id);
}
}
$company->logo = $logo;
return $company;
}
}