1
0
mirror of https://github.com/invoiceninja/invoiceninja.git synced 2024-09-21 08:51:34 +02:00

Merge pull request #4711 from turbo124/v5-stable

V 5.0.48
This commit is contained in:
David Bomba 2021-01-19 07:58:41 +11:00 committed by GitHub
commit 9c0ce6b085
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
131 changed files with 111296 additions and 109760 deletions

View File

@ -47,7 +47,7 @@ jobs:
- name: Cleanup Builds
run: |
sudo rm -rf bootstrap/cache/*
sudo rm -rf node_modules
- name: Build project # This would actually build your project, using zip for an example artifact
run: |
zip -r ./invoiceninja.zip ./

View File

@ -1 +1 @@
5.0.47
5.0.48

View File

@ -49,8 +49,7 @@ class DesignUpdate extends Command
public function handle()
{
foreach (Design::whereIsCustom(false)->get() as $design) {
$class = 'App\Services\PdfMaker\Designs\\'.$design->name;
$invoice_design = new $class();
$invoice_design = new \App\Services\PdfMaker\Design(strtolower($design->name));
$invoice_design->document();
$design_object = new stdClass;

View File

@ -52,7 +52,7 @@ class PostUpdate extends Command
nlog("finished migrating");
exec('vendor/bin/composer install --no-dev:');
exec('vendor/bin/composer install --no-dev');
nlog("finished running composer install ");

View File

@ -37,9 +37,12 @@ class FeesAndLimits
public $adjust_fee_percent = false;
public $is_enabled = true;
//public $gateway_type_id = 1;
public static $casts = [
'is_enabled' => 'bool',
'gateway_type_id' => 'int',
'min_limit' => 'float',
'max_limit' => 'float',

View File

@ -31,6 +31,8 @@ class UserWasArchived
*/
public $user;
public $creating_user;
public $company;
public $event_vars;
@ -42,9 +44,10 @@ class UserWasArchived
* @param Company $company
* @param array $event_vars
*/
public function __construct(User $user, Company $company, array $event_vars)
public function __construct(User $user, User $creating_user, Company $company, array $event_vars)
{
$this->user = $user;
$this->creating_user = $creating_user;
$this->company = $company;
$this->event_vars = $event_vars;
}

View File

@ -31,6 +31,8 @@ class UserWasCreated
*/
public $user;
public $creating_user;
public $company;
public $event_vars;
@ -42,9 +44,10 @@ class UserWasCreated
* @param Company $company
* @param array $event_vars
*/
public function __construct(User $user, Company $company, array $event_vars)
public function __construct(User $user, User $creating_user, Company $company, array $event_vars)
{
$this->user = $user;
$this->creating_user = $creating_user;
$this->company = $company;
$this->event_vars = $event_vars;
}

View File

@ -31,6 +31,8 @@ class UserWasDeleted
*/
public $user;
public $creating_user;
public $company;
public $event_vars;
@ -42,9 +44,10 @@ class UserWasDeleted
* @param Company $company
* @param array $event_vars
*/
public function __construct(User $user, Company $company, array $event_vars)
public function __construct(User $user, User $creating_user, Company $company, array $event_vars)
{
$this->user = $user;
$this->creating_user = $creating_user;
$this->company = $company;
$this->event_vars = $event_vars;
}

View File

@ -35,7 +35,7 @@ class UserWasRestored
public $event_vars;
public $fromDeleted;
public $creating_user;
/**
* Create a new event instance.
@ -44,12 +44,12 @@ class UserWasRestored
* @param Company $company
* @param array $event_vars
*/
public function __construct(User $user, bool $fromDeleted, Company $company, array $event_vars)
public function __construct(User $user, User $creating_user, Company $company, array $event_vars)
{
$this->user = $user;
$this->company = $company;
$this->event_vars = $event_vars;
$this->fromDeleted = $fromDeleted;
$this->creating_user = $creating_user;
}
/**

View File

@ -31,6 +31,8 @@ class UserWasUpdated
*/
public $user;
public $creating_user;
public $company;
public $event_vars;
@ -42,9 +44,10 @@ class UserWasUpdated
* @param Company $company
* @param array $event_vars
*/
public function __construct(User $user, Company $company, array $event_vars)
public function __construct(User $user, User $creating_user, Company $company, array $event_vars)
{
$this->user = $user;
$this->creating_user = $creating_user;
$this->company = $company;
$this->event_vars = $event_vars;
}

View File

@ -21,13 +21,18 @@
*/
function nlog($output, $context = []): void
{
if (config('ninja.expanded_logging')) {
if (!config('ninja.expanded_logging'))
return;
if (gettype($output) == 'object') {
$output = print_r($output, 1);
}
$trace = debug_backtrace();
\Illuminate\Support\Facades\Log::channel('invoiceninja')->info(print_r($trace[1]['class'],1), []);
\Illuminate\Support\Facades\Log::channel('invoiceninja')->info($output, $context);
}
}
if (!function_exists('ray')) {

View File

@ -432,10 +432,11 @@ class ClientController extends BaseController
*/
public function destroy(DestroyClientRequest $request, Client $client)
{
//may not need these destroy routes as we are using actions to 'archive/delete'
$client->delete();
return response()->json([], 200);
$this->client_repo->delete($client);
return $this->itemResponse($client->fresh());
}
/**

View File

@ -22,6 +22,7 @@ class DashboardController extends Controller
*/
public function index()
{
return $this->render('dashboard.index');
return redirect()->route('client.invoices.index');
//return $this->render('dashboard.index');
}
}

View File

@ -54,11 +54,11 @@ class InvoiceController extends Controller
'invoice' => $invoice,
];
if ($request->query('mode') === 'fullscreen') {
return $this->render('invoices.show.fullscreen', $data);
if ($request->query('mode') === 'portal') {
return $this->render('invoices.show', $data);
}
return $this->render('invoices.show', $data);
return $this->render('invoices.show.fullscreen', $data);
}
/**
@ -123,7 +123,7 @@ class InvoiceController extends Controller
//format totals
$formatted_total = Number::formatMoney($total, auth()->user()->client);
$payment_methods = auth()->user()->client->getPaymentMethods($total);
$payment_methods = auth()->user()->client->service()->getPaymentMethods($total);
$data = [
'settings' => auth()->user()->client->getMergedSettings(),
@ -135,7 +135,7 @@ class InvoiceController extends Controller
];
// nlog($data);
return $this->render('invoices.payment', $data);
}

View File

@ -175,7 +175,7 @@ class PaymentController extends Controller
foreach($payable_invoices as $payable_invoice)
{
nlog($payable_invoice);
// nlog($payable_invoice);
$payable_invoice['amount'] = Number::parseFloat($payable_invoice['amount']);

View File

@ -43,11 +43,11 @@ class QuoteController extends Controller
'quote' => $quote,
];
if ($request->query('mode') === 'fullscreen') {
return $this->render('quotes.show.fullscreen', $data);
if ($request->query('mode') === 'portal') {
return $this->render('quotes.show', $data);
}
return $this->render('quotes.show', $data);
return $this->render('quotes.show.fullscreen', $data);
}
public function bulk(ProcessQuotesInBulkRequest $request)
@ -111,7 +111,7 @@ class QuoteController extends Controller
foreach ($quotes as $quote) {
$quote->service()->approve(auth()->user())->save();
event(new QuoteWasApproved(auth('contact')->user(), $quote, $quote->company, Ninja::eventVars()));
if (request()->has('signature') && !is_null(request()->signature) && !empty(request()->signature)) {
InjectSignature::dispatch($quote, request()->signature);
}

View File

@ -421,7 +421,7 @@ class CompanyGatewayController extends BaseController
{
$company_gateway->delete();
return response()->json([], 200);
return $this->itemResponse($company_gateway->fresh());
}
/**

View File

@ -420,9 +420,9 @@ class CreditController extends BaseController
*/
public function destroy(DestroyCreditRequest $request, Credit $credit)
{
$credit->delete();
$this->credit_repository->delete($credit);
return response()->json([], 200);
return $this->itemResponse($credit->fresh());
}
/**

View File

@ -415,7 +415,7 @@ class DesignController extends BaseController
$design->delete();
$design->save();
return response()->json([], 200);
return $this->itemResponse($design->fresh());
}
/**

View File

@ -22,6 +22,7 @@ use App\Models\GroupSetting;
use App\Repositories\GroupSettingRepository;
use App\Transformers\GroupSettingTransformer;
use App\Utils\Traits\MakesHash;
use App\Utils\Traits\SavesDocuments;
use App\Utils\Traits\Uploadable;
use Illuminate\Foundation\Bus\DispatchesJobs;
use Illuminate\Http\Request;
@ -32,6 +33,7 @@ class GroupSettingController extends BaseController
use DispatchesJobs;
use Uploadable;
use MakesHash;
use SavesDocuments;
protected $entity_type = GroupSetting::class;
@ -357,6 +359,9 @@ class GroupSettingController extends BaseController
$this->uploadLogo($request->file('company_logo'), $group_setting->company, $group_setting);
if ($request->has('documents'))
$this->saveDocuments($request->input('documents'), $group_setting, false);
return $this->itemResponse($group_setting);
}
@ -414,7 +419,7 @@ class GroupSettingController extends BaseController
{
$group_setting->delete();
return response()->json([], 200);
return $this->itemResponse($group_setting->fresh());
}
/**

View File

@ -451,9 +451,9 @@ class InvoiceController extends BaseController
*/
public function destroy(DestroyInvoiceRequest $request, Invoice $invoice)
{
$invoice->delete();
$this->invoice_repo->delete($invoice);
return response()->json([], 200);
return $this->itemResponse($invoice->fresh());
}
/**

View File

@ -397,7 +397,7 @@ class PaymentTermController extends BaseController
{
$payment_term->delete();
return response()->json([], 200);
return $this->itemResponse($payment_term->fresh());
}
/**

View File

@ -429,7 +429,7 @@ class ProjectController extends BaseController
$project->delete();
$project->save();
return response()->json([], 200);
return $this->itemResponse($project->fresh());
}
/**

View File

@ -441,9 +441,9 @@ class QuoteController extends BaseController
*/
public function destroy(DestroyQuoteRequest $request, Quote $quote)
{
$quote->delete();
$this->quote_repo->delete($quote);
return response()->json([], 200);
return $this->itemResponse($quote->fresh());
}
/**

View File

@ -426,9 +426,65 @@ class RecurringInvoiceController extends BaseController
*/
public function destroy(DestroyRecurringInvoiceRequest $request, RecurringInvoice $recurring_invoice)
{
$recurring_invoice->delete();
$this->recurring_invoice_repo->delete($recurring_invoice);
return response()->json([], 200);
return $this->itemResponse($recurring_invoice->fresh());
}
/**
* @OA\Get(
* path="/api/v1/recurring_invoice/{invitation_key}/download",
* operationId="downloadInvoice",
* tags={"invoices"},
* summary="Download a specific invoice by invitation key",
* description="Downloads a specific invoice",
* @OA\Parameter(ref="#/components/parameters/X-Api-Secret"),
* @OA\Parameter(ref="#/components/parameters/X-Api-Token"),
* @OA\Parameter(ref="#/components/parameters/X-Requested-With"),
* @OA\Parameter(ref="#/components/parameters/include"),
* @OA\Parameter(
* name="invitation_key",
* in="path",
* description="The Recurring Invoice Invitation Key",
* example="D2J234DFA",
* required=true,
* @OA\Schema(
* type="string",
* format="string",
* ),
* ),
* @OA\Response(
* response=200,
* description="Returns the recurring invoice pdf",
* @OA\Header(header="X-MINIMUM-CLIENT-VERSION", ref="#/components/headers/X-MINIMUM-CLIENT-VERSION"),
* @OA\Header(header="X-RateLimit-Remaining", ref="#/components/headers/X-RateLimit-Remaining"),
* @OA\Header(header="X-RateLimit-Limit", ref="#/components/headers/X-RateLimit-Limit"),
* ),
* @OA\Response(
* response=422,
* description="Validation error",
* @OA\JsonContent(ref="#/components/schemas/ValidationError"),
*
* ),
* @OA\Response(
* response="default",
* description="Unexpected Error",
* @OA\JsonContent(ref="#/components/schemas/Error"),
* ),
* )
* @param $invitation_key
* @return \Symfony\Component\HttpFoundation\BinaryFileResponse
*/
public function downloadPdf($invitation_key)
{
$invitation = $this->recurring_invoice_repo->getInvitationByKey($invitation_key);
$contact = $invitation->contact;
$recurring_invoice = $invitation->recurring_invoice;
$file_path = $recurring_invoice->service()->getInvoicePdf($contact);
return response()->download($file_path, basename($file_path));
}
/**

View File

@ -428,9 +428,9 @@ class RecurringQuoteController extends BaseController
*/
public function destroy(DestroyRecurringQuoteRequest $request, RecurringQuote $recurring_quote)
{
$recurring_quote->delete();
$this->recurring_quote_repo->delete($recurring_quote);
return response()->json([], 200);
return $this->itemResponse($recurring_quote->fresh());
}
/**

View File

@ -425,9 +425,9 @@ class TaskController extends BaseController
public function destroy(DestroyTaskRequest $request, Task $task)
{
//may not need these destroy routes as we are using actions to 'archive/delete'
$task->delete();
$this->task_repo->delete($task);
return response()->json([], 200);
return $this->itemResponse($task->fresh());
}
/**

View File

@ -174,7 +174,7 @@ class TaskStatusController extends BaseController
*/
public function store(StoreTaskStatusRequest $request)
{
nlog($request->all());
// nlog($request->all());
$task_status = TaskStatusFactory::create(auth()->user()->company()->id, auth()->user()->id);
$task_status->fill($request->all());
@ -400,7 +400,7 @@ class TaskStatusController extends BaseController
{
$task_status->delete();
return response()->json([], 200);
return $this->itemResponse($task_status->fresh());
}
/**

View File

@ -13,6 +13,8 @@ namespace App\Http\Controllers;
use App\DataMapper\CompanySettings;
use App\Events\User\UserWasCreated;
use App\Events\User\UserWasDeleted;
use App\Events\User\UserWasUpdated;
use App\Factory\UserFactory;
use App\Filters\UserFilters;
use App\Http\Controllers\Traits\VerifiesUserEmail;
@ -202,7 +204,7 @@ class UserController extends BaseController
$ct = CreateCompanyToken::dispatchNow($company, $user, $user_agent);
event(new UserWasCreated($user, $company, Ninja::eventVars()));
event(new UserWasCreated($user, auth()->user(), $company, Ninja::eventVars()));
return $this->itemResponse($user->fresh());
}
@ -376,6 +378,8 @@ class UserController extends BaseController
UserEmailChanged::dispatch($new_email, $old_email, auth()->user()->company());
}
event(new UserWasUpdated($user, auth()->user(), auth()->user()->company, Ninja::eventVars()));
return $this->itemResponse($user);
}
@ -444,6 +448,8 @@ class UserController extends BaseController
/* If the user passes the company user we archive the company user */
$user = $this->user_repo->destroy($request->all(), $user);
event(new UserWasDeleted($user, auth()->user(), auth()->user()->company, Ninja::eventVars()));
return $this->itemResponse($user->fresh());
}

View File

@ -432,7 +432,7 @@ class VendorController extends BaseController
//may not need these destroy routes as we are using actions to 'archive/delete'
$vendor->delete();
return response()->json([], 200);
return $this->itemResponse($vendor->fresh());
}
/**

View File

@ -29,8 +29,8 @@ class General extends Component
public $saved;
protected $rules = [
'first_name' => ['required'],
'last_name' => ['required'],
'first_name' => ['sometimes'],
'last_name' => ['sometimes'],
'email' => ['required', 'email'],
];

View File

@ -15,9 +15,9 @@ class NameWebsiteLogo extends Component
public $saved;
public $rules = [
'name' => ['required', 'min:3'],
'website' => ['required', 'url'],
'phone' => ['required', 'string', 'max:255'],
'name' => ['sometimes', 'min:3'],
'website' => ['sometimes'],
'phone' => ['sometimes', 'string', 'max:255'],
];
public function mount()

View File

@ -20,12 +20,12 @@ class PersonalAddress extends Component
public $saved;
protected $rules = [
'address1' => ['required'],
'address2' => ['required'],
'city' => ['required'],
'state' => ['required'],
'postal_code' => ['required'],
'country_id' => ['required'],
'address1' => ['sometimes'],
'address2' => ['sometimes'],
'city' => ['sometimes'],
'state' => ['sometimes'],
'postal_code' => ['sometimes'],
'country_id' => ['sometimes'],
];
public function mount($countries)

View File

@ -20,12 +20,12 @@ class ShippingAddress extends Component
public $saved;
protected $rules = [
'shipping_address1' => ['required'],
'shipping_address2' => ['required'],
'shipping_city' => ['required'],
'shipping_state' => ['required'],
'shipping_postal_code' => ['required'],
'shipping_country_id' => ['required'],
'shipping_address1' => ['sometimes'],
'shipping_address2' => ['sometimes'],
'shipping_city' => ['sometimes'],
'shipping_state' => ['sometimes'],
'shipping_postal_code' => ['sometimes'],
'shipping_country_id' => ['sometimes'],
];
public function mount($countries)

View File

@ -36,6 +36,7 @@ class QuotesTable extends Component
$query = $query
->where('client_id', auth('contact')->user()->client->id)
->where('status_id', '<>', Quote::STATUS_DRAFT)
->paginate($this->per_page);
return render('components.livewire.quotes-table', [

View File

@ -34,7 +34,6 @@ class UpdateTaskStatusRequest extends Request
$rules = [];
if ($this->input('name')) {
//$rules['name'] = 'unique:task_statuses,name,'.$this->id.',id,company_id,'.$this->task_status->company_id;
$rules['name'] = Rule::unique('task_statuses')->where('company_id', auth()->user()->company()->id)->ignore($this->task_status->id);
}

View File

@ -67,8 +67,9 @@ class PortalComposer
{
$data = [];
if($this->settings->enable_client_portal_dashboard == TRUE)
$data[] = [ 'title' => ctrans('texts.dashboard'), 'url' => 'client.dashboard', 'icon' => 'activity'];
//@todo wire this back in when we are happy with dashboard.
// if($this->settings->enable_client_portal_dashboard == TRUE)
// $data[] = [ 'title' => ctrans('texts.dashboard'), 'url' => 'client.dashboard', 'icon' => 'activity'];
$data[] = ['title' => ctrans('texts.invoices'), 'url' => 'client.invoices.index', 'icon' => 'file-text'];
$data[] = ['title' => ctrans('texts.recurring_invoices'), 'url' => 'client.recurring_invoices.index', 'icon' => 'file'];

View File

@ -60,7 +60,7 @@ class BaseTransformer
if ($code) {
$currency = $this->maps['currencies']->where('code', $code)->first();
if ($currency_id) {
if ($currency) {
return $currency->id;
}
}

View File

@ -19,6 +19,7 @@ use App\Models\Invoice;
use App\Models\InvoiceInvitation;
use App\Models\Quote;
use App\Models\QuoteInvitation;
use App\Models\RecurringInvoice;
use App\Models\RecurringInvoiceInvitation;
use App\Services\PdfMaker\Design as PdfDesignModel;
use App\Services\PdfMaker\Design as PdfMakerDesign;
@ -106,6 +107,9 @@ class CreateEntityPdf implements ShouldQueue
} elseif ($this->entity instanceof Credit) {
$path = $this->entity->client->credit_filepath();
$entity_design_id = 'credit_design_id';
} elseif ($this->entity instanceof RecurringInvoice) {
$path = $this->entity->client->recurring_invoice_filepath();
$entity_design_id = 'invoice_design_id';
}
$file_path = $path.$this->entity->number.'.pdf';

View File

@ -74,6 +74,11 @@ class SendRecurring implements ShouldQueue
}
});
//Admin notification for recurring invoice sent.
if ($invoice->invitations->count() >= 1) {
$invoice->entityEmailEvent($invoice->invitations->first(), 'invoice', 'email_template_invoice');
}
if ($invoice->client->getSetting('auto_bill_date') == 'on_send_date' && $this->recurring_invoice->auto_bill_enabled) {
$invoice->service()->autoBill()->save();
}

View File

@ -78,7 +78,7 @@ class CreateUser
'settings' => null,
]);
event(new UserWasCreated($user, $this->company, Ninja::eventVars()));
event(new UserWasCreated($user, $user, $this->company, Ninja::eventVars()));
return $user;
}

View File

@ -58,7 +58,7 @@ class ReminderJob implements ShouldQueue
Invoice::where('next_send_date', Carbon::today()->format('Y-m-d'))->with('invitations')->cursor()->each(function ($invoice) {
if ($invoice->isPayable()) {
$reminder_template = $invoice->calculateTemplate('invoice');
$invoice->service()->touchReminder($this->reminder_template)->save();
$invoice->service()->touchReminder($reminder_template)->save();
$invoice->invitations->each(function ($invitation) use ($invoice, $reminder_template) {
EmailEntity::dispatch($invitation, $invitation->company, $reminder_template);

View File

@ -108,15 +108,29 @@ class WebhookHandler implements ShouldQueue
$client = new Client(['headers' => array_merge($base_headers, $headers)]);
try {
$response = $client->post($subscription->target_url, [
RequestOptions::JSON => $data, // or 'json' => [...]
]);
if ($response->getStatusCode() == 410 || $response->getStatusCode() == 200) {
$subscription->delete();
}
if ($response->getStatusCode() == 410 || $response->getStatusCode() == 200)
$subscription->delete();
SystemLogger::dispatch(
SystemLogger::dispatch(
$response,
SystemLog::CATEGORY_WEBHOOK,
SystemLog::EVENT_WEBHOOK_RESPONSE,
SystemLog::TYPE_WEBHOOK_RESPONSE,
$this->company->clients->first(),
);
}
catch(\Exception $e){
// nlog($e->getMessage());
SystemLogger::dispatch(
$e->getMessage(),
SystemLog::CATEGORY_WEBHOOK,
SystemLog::EVENT_WEBHOOK_RESPONSE,
@ -124,6 +138,10 @@ class WebhookHandler implements ShouldQueue
$this->company->clients->first(),
);
}
}
public function failed($exception)

View File

@ -43,13 +43,10 @@ class ArchivedUserActivity implements ShouldQueue
$fields = new stdClass;
if (auth()->user()->id) {
$fields->user_id = auth()->user()->id;
} else {
$fields->user_id = $event->user->id;
}
$fields->user_id = $event->user->id;
$fields->notes = $event->creating_user->present()->name . " Archived User";
$fields->company_id = $event->user->company_id;
$fields->company_id = $event->company->id;
$fields->activity_type_id = Activity::ARCHIVE_USER;
$this->activityRepo->save($fields, $event->user, $event->event_vars);

View File

@ -43,13 +43,9 @@ class CreatedUserActivity implements ShouldQueue
$fields = new stdClass;
if (auth()->user()) {
$fields->user_id = auth()->user()->id;
} else {
$fields->user_id = $event->user->id;
}
$fields->company_id = $event->user->company_id;
$fields->user_id = $event->user->id;
$fields->notes = $event->creating_user->present()->name() . " Created the user";
$fields->company_id = $event->company->id;
$fields->activity_type_id = Activity::CREATE_USER;
$this->activityRepo->save($fields, $event->user, $event->event_vars);

View File

@ -48,12 +48,8 @@ class DeletedUserActivity implements ShouldQueue
$fields = new stdClass;
if (auth()->check()) {
$fields->user_id = auth()->user()->id;
} else {
$fields->user_id = $event->user->id;
}
$fields->user_id = $event->user->id;
$fields->notes = $event->creating_user->present()->name . " Deleted User";
$fields->company_id = $event->company->id;
$fields->activity_type_id = Activity::DELETE_USER;

View File

@ -43,13 +43,10 @@ class RestoredUserActivity implements ShouldQueue
$fields = new stdClass;
if (auth()->user()->id) {
$fields->user_id = auth()->user()->id;
} else {
$fields->user_id = $event->user->id;
}
$fields->user_id = $event->user->id;
$fields->notes = $event->creating_user->present()->name() . " Restored user";
$fields->company_id = $event->user->company_id;
$fields->company_id = $event->company->id;
$fields->activity_type_id = Activity::RESTORE_USER;
$this->activityRepo->save($fields, $event->user, $event->event_vars);

View File

@ -42,14 +42,9 @@ class UpdatedUserActivity implements ShouldQueue
MultiDB::setDb($event->company->db);
$fields = new stdClass;
if (auth()->user()->id) {
$fields->user_id = auth()->user()->id;
} else {
$fields->user_id = $event->user->id;
}
$fields->company_id = $event->user->company_id;
$fields->user_id = $event->user->id;
$fields->notes = $event->creating_user->present()->name . " Updated user";
$fields->company_id = $event->company->id;
$fields->activity_type_id = Activity::UPDATE_USER;
$this->activityRepo->save($fields, $event->user, $event->event_vars);

View File

@ -60,7 +60,7 @@ class EntitySentObject
private function setTemplate()
{
nlog($this->template);
// nlog($this->template);
switch ($this->template) {
case 'invoice':

View File

@ -65,11 +65,11 @@ class Activity extends StaticModel
const RESTORE_TASK = 46; //
const UPDATE_EXPENSE = 47;//
const CREATE_USER = 48; // only used in CreateUser::job
const UPDATE_USER = 49; // not needed?
const ARCHIVE_USER = 50; // not needed?
const DELETE_USER = 51; // not needed?
const RESTORE_USER = 52; // not needed?
const CREATE_USER = 48;
const UPDATE_USER = 49;
const ARCHIVE_USER = 50;
const DELETE_USER = 51;
const RESTORE_USER = 52;
const MARK_SENT_INVOICE = 53; // not needed?
const PAID_INVOICE = 54; //
const EMAIL_INVOICE_FAILED = 57;

View File

@ -433,6 +433,7 @@ class Client extends BaseModel implements HasLocalePreference
*
* @param float $amount The amount to be charged
* @return array Array of payment labels and urls
* @deprecated 5.0.38 - see service()->getPaymentMethods($amount);
*/
public function getPaymentMethods($amount) :array
{
@ -605,6 +606,11 @@ class Client extends BaseModel implements HasLocalePreference
return $this->company->company_key.'/'.$this->client_hash.'/credits/';
}
public function recurring_invoice_filepath()
{
return $this->company->company_key.'/'.$this->client_hash.'/recurring_invoices/';
}
public function company_filepath()
{
return $this->company->company_key.'/';

View File

@ -87,6 +87,12 @@ class ClientContact extends Authenticatable implements HasLocalePreference
'client_id',
];
/* Changing the username to id allows us to login() a contact that doesn't have an email address set*/
public function username()
{
return 'id';
}
public function getEntityType()
{
return self::class;

View File

@ -44,6 +44,9 @@ class Document extends BaseModel
'jpeg' => [
'mime' => 'image/jpeg',
],
'jpg' => [
'mime' => 'image/jpeg',
],
'tiff' => [
'mime' => 'image/tiff',
],

View File

@ -51,6 +51,11 @@ class GroupSetting extends StaticModel
return $this->hasMany(Client::class, 'id', 'group_settings_id');
}
public function documents()
{
return $this->morphMany(Document::class, 'documentable');
}
/**
* Retrieve the model for a bound value.
*

View File

@ -70,7 +70,6 @@ class Invoice extends BaseModel
'tax_name3',
'tax_rate3',
'is_amount_discount',
'footer',
'partial',
'partial_due_date',
'project_id',

View File

@ -0,0 +1,31 @@
<?php
/**
* Invoice Ninja (https://invoiceninja.com).
*
* @link https://github.com/invoiceninja/invoiceninja source repository
*
* @copyright Copyright (c) 2021. Invoice Ninja LLC (https://invoiceninja.com)
*
* @license https://opensource.org/licenses/AAL
*/
namespace App\Models\Presenters;
use App\Utils\Number;
use App\Utils\Traits\MakesDates;
use Laracasts\Presenter\PresentableTrait;
/**
* Class InvoicePresenter.
*
* For convenience and to allow users to easiliy
* customise their invoices, we provide all possible
* invoice variables to be available from this presenter.
*
* Shortcuts to other presenters are here to facilitate
* a clean UI / UX
*/
class RecurringInvoicePresenter extends InvoicePresenter
{
}

View File

@ -59,7 +59,6 @@ class Quote extends BaseModel
'tax_name3',
'tax_rate3',
'is_amount_discount',
'footer',
'partial',
'partial_due_date',
'custom_value1',
@ -226,6 +225,9 @@ class Quote extends BaseModel
case self::STATUS_EXPIRED:
return '<h5><span class="badge badge-danger">'.ctrans('texts.expired').'</span></h5>';
break;
case self::STATUS_CONVERTED:
return '<h5><span class="badge badge-light">'.ctrans('texts.converted').'</span></h5>';
break;
default:
// code...
break;

View File

@ -13,12 +13,14 @@ namespace App\Models;
use App\Helpers\Invoice\InvoiceSum;
use App\Helpers\Invoice\InvoiceSumInclusive;
use App\Models\Presenters\RecurringInvoicePresenter;
use App\Services\Recurring\RecurringService;
use App\Utils\Traits\MakesDates;
use App\Utils\Traits\MakesHash;
use App\Utils\Traits\Recurring\HasRecurrence;
use Illuminate\Database\Eloquent\SoftDeletes;
use Illuminate\Support\Carbon;
use Laracasts\Presenter\PresentableTrait;
/**
* Class for Recurring Invoices.
@ -30,6 +32,9 @@ class RecurringInvoice extends BaseModel
use Filterable;
use MakesDates;
use HasRecurrence;
use PresentableTrait;
protected $presenter = RecurringInvoicePresenter::class;
/**
* Invoice Statuses.

View File

@ -34,7 +34,8 @@ class SystemLog extends Model
const CATEGORY_GATEWAY_RESPONSE = 1;
const CATEGORY_MAIL = 2;
const CATEGORY_WEBHOOK = 3;
const CATEGORY_PDF = 3;
const CATEGORY_PDF = 4;
const CATEGORY_SECURITY = 5;
/* Event IDs*/
const EVENT_PAYMENT_RECONCILIATION_FAILURE = 10;
@ -50,6 +51,9 @@ class SystemLog extends Model
const EVENT_WEBHOOK_RESPONSE = 40;
const EVENT_PDF_RESPONSE = 50;
const EVENT_AUTHENTICATION_FAILURE = 60;
const EVENT_USER = 61;
/*Type IDs*/
const TYPE_PAYPAL = 300;
const TYPE_STRIPE = 301;
@ -62,9 +66,13 @@ class SystemLog extends Model
const TYPE_UPSTREAM_FAILURE = 401;
const TYPE_WEBHOOK_RESPONSE = 500;
const TYPE_PDF_FAILURE = 600;
const TYPE_PDF_SUCCESS = 601;
const TYPE_MODIFIED = 701;
const TYPE_DELETED = 702;
protected $fillable = [
'client_id',
'company_id',

View File

@ -98,29 +98,8 @@ class AuthorizeCreditCard
/*Refactor and push to BaseDriver*/
if ($data['response'] != null && $data['response']->getMessages()->getResultCode() == 'Ok') {
// $response = $data['response'];
// $payment_record = [];
// $payment_record['amount'] = $amount;
// $payment_record['payment_type'] = PaymentType::CREDIT_CARD_OTHER;;
// $payment_record['transaction_reference'] = $response->getTransactionResponse()->getTransId();
// $this->authorize->createPayment($payment_record);
$this->storePayment($payment_hash, $data);
// $payment = $this->createPaymentRecord($data, $amount);
// $payment->meta = $cgt->meta;
// $payment->save();
// $payment_hash->payment_id = $payment->id;
// $payment_hash->save();
// $this->authorize->attachInvoices($payment, $payment_hash);
// $payment->service()->updateInvoicePayment($payment_hash);
// event(new PaymentWasCreated($payment, $payment->company, Ninja::eventVars()));
$vars = [
'hashed_ids' => $invoice->hashed_id,
'amount' => $amount,
@ -212,8 +191,7 @@ class AuthorizeCreditCard
private function processFailedResponse($data, $request)
{
//dd($data);
// nlog(print_r($data, 1));
throw new \Exception(ctrans('texts.error_title'));
}
private function formatGatewayResponse($data, $vars)

View File

@ -228,6 +228,9 @@ class BaseDriver extends AbstractPaymentDriver
$payment->service()->updateInvoicePayment($this->payment_hash);
if ($this->client->getSetting('client_online_payment_notification'))
$payment->service()->sendEmail();
event(new PaymentWasCreated($payment, $payment->company, Ninja::eventVars()));
return $payment->service()->applyNumber()->save();

View File

@ -72,8 +72,11 @@ use App\Events\Task\TaskWasDeleted;
use App\Events\Task\TaskWasRestored;
use App\Events\Task\TaskWasUpdated;
use App\Events\User\UserLoggedIn;
use App\Events\User\UserWasArchived;
use App\Events\User\UserWasCreated;
use App\Events\User\UserWasDeleted;
use App\Events\User\UserWasRestored;
use App\Events\User\UserWasUpdated;
use App\Events\Vendor\VendorWasArchived;
use App\Events\Vendor\VendorWasCreated;
use App\Events\Vendor\VendorWasDeleted;
@ -123,8 +126,8 @@ use App\Listeners\Invoice\InvoiceArchivedActivity;
use App\Listeners\Invoice\InvoiceCancelledActivity;
use App\Listeners\Invoice\InvoiceDeletedActivity;
use App\Listeners\Invoice\InvoiceEmailActivity;
use App\Listeners\Invoice\InvoiceEmailedNotification;
use App\Listeners\Invoice\InvoiceEmailFailedActivity;
use App\Listeners\Invoice\InvoiceEmailedNotification;
use App\Listeners\Invoice\InvoicePaidActivity;
use App\Listeners\Invoice\InvoiceReminderEmailActivity;
use App\Listeners\Invoice\InvoiceRestoredActivity;
@ -132,8 +135,8 @@ use App\Listeners\Invoice\InvoiceReversedActivity;
use App\Listeners\Invoice\InvoiceViewedActivity;
use App\Listeners\Invoice\UpdateInvoiceActivity;
use App\Listeners\Misc\InvitationViewedListener;
use App\Listeners\Payment\PaymentEmailedActivity;
use App\Listeners\Payment\PaymentEmailFailureActivity;
use App\Listeners\Payment\PaymentEmailedActivity;
use App\Listeners\Payment\PaymentNotification;
use App\Listeners\Payment\PaymentRestoredActivity;
use App\Listeners\Quote\QuoteApprovedActivity;
@ -145,8 +148,12 @@ use App\Listeners\Quote\QuoteRestoredActivity;
use App\Listeners\Quote\QuoteViewedActivity;
use App\Listeners\Quote\ReachWorkflowSettings;
use App\Listeners\SendVerificationNotification;
use App\Listeners\User\ArchivedUserActivity;
use App\Listeners\User\CreatedUserActivity;
use App\Listeners\User\DeletedUserActivity;
use App\Listeners\User\RestoredUserActivity;
use App\Listeners\User\UpdateUserLastLogin;
use App\Listeners\User\UpdatedUserActivity;
use Illuminate\Foundation\Support\Providers\EventServiceProvider as ServiceProvider;
class EventServiceProvider extends ServiceProvider
@ -158,14 +165,24 @@ class EventServiceProvider extends ServiceProvider
*/
protected $listen = [
UserWasCreated::class => [
CreatedUserActivity::class,
SendVerificationNotification::class,
],
UserWasDeleted::class => [
DeletedUserActivity::class,
],
UserWasArchived::class => [
ArchivedUserActivity::class,
],
UserLoggedIn::class => [
UpdateUserLastLogin::class,
],
UserWasUpdated::class => [
UpdatedUserActivity::class,
],
UserWasRestored::class => [
RestoredUserActivity::class,
],
ContactLoggedIn::class => [
UpdateContactLastLogin::class,
],

View File

@ -19,6 +19,7 @@ use App\Models\Design;
use App\Models\Invoice;
use App\Models\Quote;
use App\Models\RecurringInvoice;
use App\Models\User;
use App\Services\PdfMaker\Design as PdfDesignModel;
use App\Services\PdfMaker\Design as PdfMakerDesign;
use App\Services\PdfMaker\PdfMaker as PdfMakerService;
@ -69,7 +70,11 @@ class ActivityRepository extends BaseRepository
*/
public function createBackup($entity, $activity)
{
if ($entity->company->is_disabled) {
if($entity instanceof User){
}
else if ($entity->company->is_disabled) {
return;
}

View File

@ -18,6 +18,7 @@ use App\Models\Company;
use App\Models\Credit;
use App\Models\Invoice;
use App\Models\Quote;
use App\Models\RecurringInvoice;
use App\Utils\Ninja;
use App\Utils\Traits\MakesHash;
use App\Utils\Traits\SavesDocuments;
@ -129,13 +130,12 @@ class BaseRepository
return count($entities);
}
/* Returns an invoice if defined as a key in the $resource array*/
public function getInvitation($invitation, $resource)
{
if (is_array($invitation) && ! array_key_exists('key', $invitation)) {
if (is_array($invitation) && ! array_key_exists('key', $invitation))
return false;
}
$invitation_class = sprintf('App\\Models\\%sInvitation', $resource);
$invitation = $invitation_class::whereRaw('BINARY `key`= ?', [$invitation['key']])->first();
@ -143,8 +143,24 @@ class BaseRepository
return $invitation;
}
/* Clean return of a key rather than butchering the model*/
private function resolveEntityKey($model)
{
switch ($model) {
case ($model instanceof RecurringInvoice):
return 'recurring_invoice_id';
case ($model instanceof Invoice):
return 'invoice_id';
case ($model instanceof Quote):
return 'quote_id';
case ($model instanceof Credit):
return 'credit_id';
}
}
/**
* Alternative save used for Invoices, Quotes & Credits.
* Alternative save used for Invoices, Recurring Invoices, Quotes & Credits.
*
* @param $data
* @param $model
* @return mixed
@ -152,17 +168,17 @@ class BaseRepository
*/
protected function alternativeSave($data, $model)
{
$class = new ReflectionClass($model);
if (array_key_exists('client_id', $data)) {
$client = Client::where('id', $data['client_id'])->withTrashed()->first();
} else {
$client = Client::where('id', $model->client_id)->withTrashed()->first();
}
if (array_key_exists('client_id', $data)) //forces the client_id if it doesn't exist
$model->client_id = $data['client_id'];
$client = Client::where('id', $model->client_id)->withTrashed()->first();
$state = [];
$resource = explode('\\', $class->name)[2]; /** This will extract 'Invoice' from App\Models\Invoice */
$lcfirst_resource_id = lcfirst($resource).'_id';
$resource = class_basename($model); //ie Invoice
$lcfirst_resource_id = $this->resolveEntityKey($model); //ie invoice_id
$state['starting_amount'] = $model->amount;
@ -172,26 +188,25 @@ class BaseRepository
$data = array_merge($company_defaults, $data);
}
$tmp_data = $data;
$tmp_data = $data; //preserves the $data arrayss
/* We need to unset some variable as we sometimes unguard the model */
if (isset($tmp_data['invitations'])) {
if (isset($tmp_data['invitations']))
unset($tmp_data['invitations']);
}
if (isset($tmp_data['client_contacts'])) {
if (isset($tmp_data['client_contacts']))
unset($tmp_data['client_contacts']);
}
$model->fill($tmp_data);
$model->save();
if (array_key_exists('documents', $data)) {
/* Model now persisted, now lets do some child tasks */
/* Save any documents */
if (array_key_exists('documents', $data))
$this->saveDocuments($data['documents'], $model);
}
$invitation_factory_class = sprintf('App\\Factory\\%sInvitationFactory', $resource);
/* Marks whether the client contact should receive emails based on the send_email property */
if (isset($data['client_contacts'])) {
foreach ($data['client_contacts'] as $contact) {
if ($contact['send_email'] == 1 && is_string($contact['id'])) {
@ -202,6 +217,7 @@ class BaseRepository
}
}
/* If invitations are present we need to filter existing invitations with the new ones */
if (isset($data['invitations'])) {
$invitations = collect($data['invitations']);
@ -210,23 +226,24 @@ class BaseRepository
$invitation_class = sprintf('App\\Models\\%sInvitation', $resource);
$invitation = $invitation_class::whereRaw('BINARY `key`= ?', [$invitation])->first();
if ($invitation) {
if ($invitation)
$invitation->delete();
}
});
foreach ($data['invitations'] as $invitation) {
//if no invitations are present - create one.
if (! $this->getInvitation($invitation, $resource)) {
if (isset($invitation['id'])) {
if (isset($invitation['id']))
unset($invitation['id']);
}
//make sure we are creating an invite for a contact who belongs to the client only!
$contact = ClientContact::find($invitation['client_contact_id']);
if ($contact && $model->client_id == $contact->client_id) {
$invitation_class = sprintf('App\\Models\\%sInvitation', $resource);
$new_invitation = $invitation_class::withTrashed()
@ -235,12 +252,17 @@ class BaseRepository
->first();
if ($new_invitation && $new_invitation->trashed()) {
$new_invitation->restore();
} else {
$invitation_factory_class = sprintf('App\\Factory\\%sInvitationFactory', $resource);
$new_invitation = $invitation_factory_class::create($model->company_id, $model->user_id);
$new_invitation->{$lcfirst_resource_id} = $model->id;
$new_invitation->client_contact_id = $contact->id;
$new_invitation->save();
}
}
}
@ -250,46 +272,61 @@ class BaseRepository
$model->load('invitations');
/* If no invitations have been created, this is our fail safe to maintain state*/
if ($model->invitations->count() == 0) {
if ($model->invitations->count() == 0)
$model->service()->createInvitations();
}
/* Recalculate invoice amounts */
$model = $model->calc()->getInvoice();
/* We use this to compare to our starting amount */
$state['finished_amount'] = $model->amount;
/* Apply entity number */
$model = $model->service()->applyNumber()->save();
if ($model->company->update_products !== false) {
/* Update product details if necessary */
if ($model->company->update_products !== false)
UpdateOrCreateProduct::dispatch($model->line_items, $model, $model->company);
}
if ($class->name == Invoice::class) {
/* Perform model specific tasks */
if ($model instanceof Invoice) {
if (($state['finished_amount'] != $state['starting_amount']) && ($model->status_id != Invoice::STATUS_DRAFT)) {
$model->ledger()->updateInvoiceBalance(($state['finished_amount'] - $state['starting_amount']));
$model->client->service()->updateBalance(($state['finished_amount'] - $state['starting_amount']))->save();
}
if (! $model->design_id) {
if (! $model->design_id)
$model->design_id = $this->decodePrimaryKey($client->getSetting('invoice_design_id'));
}
//links tasks and expenses back to the invoice.
$model->service()->linkEntities()->save();
}
if ($class->name == Credit::class) {
if ($model instanceof Credit) {
$model = $model->calc()->getCredit();
$model->ledger()->updateCreditBalance(($state['finished_amount'] - $state['starting_amount']));
if (! $model->design_id) {
if (! $model->design_id)
$model->design_id = $this->decodePrimaryKey($client->getSetting('credit_design_id'));
}
}
if ($class->name == Quote::class) {
if ($model instanceof Quote) {
$model = $model->calc()->getQuote();
}
if ($model instanceof RecurringInvoice) {
$model = $model->calc()->getRecurringInvoice();
}
$model->save();

View File

@ -76,6 +76,7 @@ class ClientContactRepository extends BaseRepository
$new_contact->client_id = $client->id;
$new_contact->contact_key = Str::random(40);
$new_contact->is_primary = true;
$new_contact->confirmed = true;
$new_contact->save();
}
}

View File

@ -13,6 +13,7 @@ namespace App\Repositories;
use App\Helpers\Invoice\InvoiceSum;
use App\Models\RecurringInvoice;
use App\Models\RecurringInvoiceInvitation;
/**
* RecurringInvoiceRepository.
@ -21,19 +22,26 @@ class RecurringInvoiceRepository extends BaseRepository
{
public function save($data, RecurringInvoice $invoice) : ?RecurringInvoice
{
$invoice->fill($data);
$invoice->save();
$invoice = $this->alternativeSave($data, $invoice);
// $invoice->fill($data);
$invoice_calc = new InvoiceSum($invoice);
// $invoice->save();
$invoice->service()
->applyNumber()
->createInvitations()
->save();
// $invoice_calc = new InvoiceSum($invoice);
// $invoice->service()
// ->applyNumber()
// ->createInvitations()
// ->save();
$invoice = $invoice_calc->build()->getRecurringInvoice();
// $invoice = $invoice_calc->build()->getRecurringInvoice();
return $invoice;
}
public function getInvitationByKey($key) :?RecurringInvoiceInvitation
{
return RecurringInvoiceInvitation::whereRaw('BINARY `key`= ?', [$key])->first();
}
}

View File

@ -12,7 +12,9 @@
namespace App\Repositories;
use App\DataMapper\CompanySettings;
use App\Events\User\UserWasArchived;
use App\Events\User\UserWasDeleted;
use App\Events\User\UserWasRestored;
use App\Models\CompanyUser;
use App\Models\User;
use App\Utils\Ninja;
@ -137,7 +139,7 @@ class UserRepository extends BaseRepository
$cu->delete();
}
event(new UserWasDeleted($user, $company, Ninja::eventVars()));
event(new UserWasDeleted($user, auth()->user(), $company, Ninja::eventVars()));
$user->is_deleted = true;
$user->save();
@ -146,4 +148,31 @@ class UserRepository extends BaseRepository
return $user->fresh();
}
public function archive($user)
{
if ($user->trashed()) {
return;
}
$user->delete();
event(new UserWasArchived($user, auth()->user(), auth()->user()->company, Ninja::eventVars()));
}
/**
* @param $entity
*/
public function restore($user)
{
if (! $user->trashed()) {
return;
}
$user->restore();
event(new UserWasRestored($user, auth()->user(), auth()->user()->company, Ninja::eventVars()));
}
}

View File

@ -12,6 +12,7 @@
namespace App\Services\Client;
use App\Models\Client;
use App\Services\Client\PaymentMethod;
use App\Utils\Number;
use Illuminate\Database\Eloquent\Collection;
@ -63,6 +64,10 @@ class ClientService
->sortBy('created_at');
}
public function getPaymentMethods(float $amount)
{
return (new PaymentMethod($this->client, $amount))->run();
}
public function save() :Client
{

View File

@ -0,0 +1,241 @@
<?php
/**
* Invoice Ninja (https://invoiceninja.com).
*
* @link https://github.com/invoiceninja/invoiceninja source repository
*
* @copyright Copyright (c) 2021. Invoice Ninja LLC (https://invoiceninja.com)
*
* @license https://opensource.org/licenses/AAL
*/
namespace App\Services\Client;
use App\Models\Client;
use App\Models\CompanyGateway;
use App\Models\GatewayType;
use App\Models\Invoice;
use App\Models\Payment;
use App\Utils\Ninja;
use App\Utils\Traits\MakesHash;
class PaymentMethod
{
use MakesHash;
private $client;
private $amount;
private $gateways;
private $payment_methods;
private $payment_urls = [];
public function __construct(Client $client, float $amount)
{
$this->client = $client;
$this->amount = $amount;
}
public function run()
{
$this->getGateways()
->getMethods()
->buildUrls();
return $this->getPaymentUrls();
}
public function getPaymentUrls()
{
return $this->payment_urls;
}
public function getPaymentMethods()
{
return $this->payment_methods;
}
private function getGateways()
{
$company_gateways = $this->client->getSetting('company_gateway_ids');
//we need to check for "0" here as we disable a payment gateway for a client with the number "0"
if ($company_gateways || $company_gateways == '0') {
$transformed_ids = $this->transformKeys(explode(',', $company_gateways));
$this->gateways = $this->client
->company
->company_gateways
->whereIn('id', $transformed_ids)
->where('gateway_key', '!=', '54faab2ab6e3223dbe848b1686490baa')
->sortby(function ($model) use ($transformed_ids) { //company gateways are sorted in order of priority
return array_search($model->id, $transformed_ids);// this closure sorts for us
});
} else {
$this->gateways = $this->client
->company
->company_gateways
->where('gateway_key', '!=', '54faab2ab6e3223dbe848b1686490baa')
->where('is_deleted', false);
}
return $this;
}
private function getCustomGateways()
{
$company_gateways = $this->client->getSetting('company_gateway_ids');
//we need to check for "0" here as we disable a payment gateway for a client with the number "0"
if ($company_gateways || $company_gateways == '0') {
$transformed_ids = $this->transformKeys(explode(',', $company_gateways));
$this->gateways = $this->client
->company
->company_gateways
->whereIn('id', $transformed_ids)
->where('gateway_key', '=', '54faab2ab6e3223dbe848b1686490baa')
->sortby(function ($model) use ($transformed_ids) { //company gateways are sorted in order of priority
return array_search($model->id, $transformed_ids);// this closure sorts for us
});
} else {
$this->gateways = $this->client
->company
->company_gateways
->where('gateway_key', '=', '54faab2ab6e3223dbe848b1686490baa')
->where('is_deleted', false);
}
return $this;
}
private function getMethods()
{
// we should prefilter $gateway->driver($this)->gatewayTypes()
// and only include the enabled payment methods on the gateway
$this->payment_methods = [];
foreach ($this->gateways as $gateway) {
foreach ($gateway->driver($this->client)->gatewayTypes() as $type) {
if (isset($gateway->fees_and_limits) && property_exists($gateway->fees_and_limits, $type)) {
if ($this->validGatewayForAmount($gateway->fees_and_limits->{$type}, $this->amount)) {
$this->payment_methods[] = [$gateway->id => $type];
}
} else {
$this->payment_methods[] = [$gateway->id => $type];
}
}
}
//transform from Array to Collection
$payment_methods_collections = collect($this->payment_methods);
//** Plucks the remaining keys into its own collection
$this->payment_methods = $payment_methods_collections->intersectByKeys($payment_methods_collections->flatten(1)->unique());
/* Loop through custom gateways if any exist and append them to the methods collection*/
$this->getCustomGateways();
//note we have to use GatewayType::CREDIT_CARD as alias for CUSTOM
foreach ($this->gateways as $gateway) {
foreach ($gateway->driver($this->client)->gatewayTypes() as $type) {
if (isset($gateway->fees_and_limits) && property_exists($gateway->fees_and_limits, $type)) {
if ($this->validGatewayForAmount($gateway->fees_and_limits->{GatewayType::CREDIT_CARD}, $this->amount)) {
$this->payment_methods->push([$gateway->id => $type]);
}
} else {
$this->payment_methods->push([$gateway->id => NULL]);
}
}
}
return $this;
}
private function buildUrls()
{
foreach ($this->payment_methods as $key => $child_array) {
foreach ($child_array as $gateway_id => $gateway_type_id) {
$gateway = CompanyGateway::find($gateway_id);
$fee_label = $gateway->calcGatewayFeeLabel($this->amount, $this->client);
if(!$gateway_type_id){
$this->payment_urls[] = [
'label' => $gateway->getConfigField('name') . $fee_label,
'company_gateway_id' => $gateway_id,
'gateway_type_id' => GatewayType::CREDIT_CARD,
];
}
else
{
$this->payment_urls[] = [
'label' => $gateway->getTypeAlias($gateway_type_id) . $fee_label,
'company_gateway_id' => $gateway_id,
'gateway_type_id' => $gateway_type_id,
];
}
}
}
if (($this->client->getSetting('use_credits_payment') == 'option' || $this->client->getSetting('use_credits_payment') == 'always') && $this->client->service()->getCreditBalance() > 0) {
// Show credits as only payment option if both statements are true.
if (
$this->client->service()->getCreditBalance() > $this->amount
&& $this->client->getSetting('use_credits_payment') == 'always') {
$payment_urls = [];
}
$payment_urls[] = [
'label' => ctrans('texts.apply_credit'),
'company_gateway_id' => CompanyGateway::GATEWAY_CREDIT,
'gateway_type_id' => GatewayType::CREDIT,
];
}
return $this;
}
private function validGatewayForAmount($fees_and_limits_for_payment_type, $amount) :bool
{
if (isset($fees_and_limits_for_payment_type)) {
$fees_and_limits = $fees_and_limits_for_payment_type;
} else {
return true;
}
if ((property_exists($fees_and_limits, 'min_limit')) && $fees_and_limits->min_limit !== null && $fees_and_limits->min_limit != -1 && $this->amount < $fees_and_limits->min_limit) {
return false;
}
if ((property_exists($fees_and_limits, 'max_limit')) && $fees_and_limits->max_limit !== null && $fees_and_limits->max_limit != -1 && $this->amount > $fees_and_limits->max_limit) {
return false;
}
return true;
}
}

View File

@ -102,17 +102,21 @@ class CreditService
{
$settings = $this->credit->client->getMergedSettings();
if (! $this->credit->design_id) {
if (! $this->credit->design_id)
$this->credit->design_id = $this->decodePrimaryKey($settings->credit_design_id);
}
if (!isset($this->credit->footer)) {
if (!isset($this->credit->footer))
$this->credit->footer = $settings->credit_footer;
}
if (!isset($this->credit->terms)) {
if (!isset($this->credit->terms))
$this->credit->terms = $settings->credit_terms;
}
/* If client currency differs from the company default currency, then insert the client exchange rate on the model.*/
if(!isset($this->credit->exchange_rate) && $this->credit->client->currency()->id != (int) $this->credit->company->settings->currency_id)
$this->credit->exchange_rate = $this->credit->client->currency()->exchange_rate;
if (!isset($this->credit->public_notes))
$this->credit->public_notes = $this->credit->client->public_notes;
return $this;

View File

@ -43,16 +43,17 @@ class AddGatewayFee extends AbstractService
{
$gateway_fee = round($this->company_gateway->calcGatewayFee($this->amount, $this->gateway_type_id, $this->invoice->uses_inclusive_taxes), $this->invoice->client->currency()->precision);
if ((int)$gateway_fee == 0) {
if ((int)$gateway_fee == 0)
return $this->invoice;
}
// Removes existing stale gateway fees
$this->cleanPendingGatewayFees();
if ($gateway_fee > 0) {
// If a gateway fee is > 0 insert the line item
if ($gateway_fee > 0)
return $this->processGatewayFee($gateway_fee);
}
// If we have reached this far, then we are apply a gateway discount
return $this->processGatewayDiscount($gateway_fee);
}

View File

@ -88,7 +88,7 @@ class AutoBillInvoice extends AbstractService
/* Build payment hash */
$payment_hash = PaymentHash::create([
'hash' => Str::random(128),
'data' => [['invoice_id' => $this->invoice->hashed_id, 'amount' => $amount]],
'data' => ['invoices' => [['invoice_id' => $this->invoice->hashed_id, 'amount' => $amount]]],
'fee_total' => $fee,
'fee_invoice_id' => $this->invoice->id,
]);
@ -252,17 +252,51 @@ class AutoBillInvoice extends AbstractService
* @param float $amount The amount to charge
* @return ClientGatewayToken The client gateway token
*/
private function getGateway($amount)
{
$gateway_tokens = $this->client->gateway_tokens()->orderBy('is_default', 'DESC')->get();
// private function
// {
// $gateway_tokens = $this->client->gateway_tokens()->orderBy('is_default', 'DESC')->get();
foreach ($gateway_tokens as $gateway_token) {
if ($this->validGatewayLimits($gateway_token, $amount)) {
return $gateway_token;
// foreach ($gateway_tokens as $gateway_token) {
// if ($this->validGatewayLimits($gateway_token, $amount)) {
// return $gateway_token;
// }
// }
// }
public function getGateway($amount)
{
//get all client gateway tokens and set the is_default one to the first record
//$gateway_tokens = $this->client->gateway_tokens()->orderBy('is_default', 'DESC');
$gateway_tokens = $this->client->gateway_tokens;
$filtered_gateways = $gateway_tokens->filter(function ($gateway_token) use($amount) {
$company_gateway = $gateway_token->gateway;
//check if fees and limits are set
if (isset($company_gateway->fees_and_limits) && property_exists($company_gateway->fees_and_limits, $gateway_token->gateway_type_id))
{
//if valid we keep this gateway_token
if ($this->invoice->client->validGatewayForAmount($company_gateway->fees_and_limits->{$gateway_token->gateway_type_id}, $amount))
return true;
else
return false;
}
}
return true; //if no fees_and_limits set then we automatically must add this gateway
});
if($filtered_gateways->count() >= 1)
return $filtered_gateways->first();
return false;
}
/**
* Adds a gateway fee to the invoice.
*
@ -332,33 +366,33 @@ class AutoBillInvoice extends AbstractService
// return $this;
// }
/**
* Checks whether a given gateway token is able
* to process the payment after passing through the
* fees and limits check.
*
* @param CompanyGateway $cg The CompanyGateway instance
* @param float $amount The amount to be paid
* @return bool
*/
public function validGatewayLimits($cg, $amount) : bool
{
if (isset($cg->fees_and_limits)) {
$fees_and_limits = $cg->fees_and_limits->{'1'};
} else {
return true;
}
// /**
// * Checks whether a given gateway token is able
// * to process the payment after passing through the
// * fees and limits check.
// *
// * @param CompanyGateway $cg The CompanyGateway instance
// * @param float $amount The amount to be paid
// * @return bool
// */
// public function validGatewayLimits($cg, $amount) : bool
// {
// if (isset($cg->fees_and_limits)) {
// $fees_and_limits = $cg->fees_and_limits->{'1'};
// } else {
// return true;
// }
if ((property_exists($fees_and_limits, 'min_limit')) && $fees_and_limits->min_limit !== null && $amount < $fees_and_limits->min_limit) {
info("amount {$amount} less than ".$fees_and_limits->min_limit);
$passes = false;
} elseif ((property_exists($fees_and_limits, 'max_limit')) && $fees_and_limits->max_limit !== null && $amount > $fees_and_limits->max_limit) {
info("amount {$amount} greater than ".$fees_and_limits->max_limit);
$passes = false;
} else {
$passes = true;
}
// if ((property_exists($fees_and_limits, 'min_limit')) && $fees_and_limits->min_limit !== null && $amount < $fees_and_limits->min_limit) {
// info("amount {$amount} less than ".$fees_and_limits->min_limit);
// $passes = false;
// } elseif ((property_exists($fees_and_limits, 'max_limit')) && $fees_and_limits->max_limit !== null && $amount > $fees_and_limits->max_limit) {
// info("amount {$amount} greater than ".$fees_and_limits->max_limit);
// $passes = false;
// } else {
// $passes = true;
// }
return $passes;
}
// return $passes;
// }
}

View File

@ -364,19 +364,22 @@ class InvoiceService
{
$settings = $this->invoice->client->getMergedSettings();
if (! $this->invoice->design_id) {
if (! $this->invoice->design_id)
$this->invoice->design_id = $this->decodePrimaryKey($settings->invoice_design_id);
}
if (!isset($this->invoice->footer)) {
$this->invoice->footer = $settings->invoice_footer;
}
if (!isset($this->invoice->terms)) {
$this->invoice->terms = $settings->invoice_terms;
}
if (!isset($this->invoice->footer))
$this->invoice->footer = $settings->invoice_footer;
if (!isset($this->invoice->terms))
$this->invoice->terms = $settings->invoice_terms;
if (!isset($this->invoice->public_notes))
$this->invoice->public_notes = $this->invoice->client->public_notes;
/* If client currency differs from the company default currency, then insert the client exchange rate on the model.*/
if(!isset($this->invoice->exchange_rate) && $this->invoice->client->currency()->id != (int) $this->invoice->company->settings->currency_id)
$this->invoice->exchange_rate = $this->invoice->client->currency()->exchange_rate;
return $this;
}

View File

@ -74,9 +74,8 @@ class MarkPaid extends AbstractService
->applyNumber()
->save();
if ($this->invoice->client->getSetting('client_manual_payment_notification')) {
EmailPayment::dispatch($payment, $payment->company, $payment->client->primary_contact()->first());
}
if ($this->invoice->client->getSetting('client_manual_payment_notification'))
$payment->service()->sendEmail();
/* Update Invoice balance */
event(new PaymentWasCreated($payment, $payment->company, Ninja::eventVars()));

View File

@ -415,8 +415,12 @@ class Design extends BaseDesign
$variables = $this->context['pdf_variables']['total_columns'];
$elements = [
['element' => 'div', 'elements' => [
['element' => 'span', 'content' => '$entity.public_notes', 'properties' => ['data-ref' => 'total_table-public_notes-label', 'style' => 'text-align: left;']],
['element' => 'div', 'properties' => ['style' => 'display: flex; flex-direction: column;'], 'elements' => [
['element' => 'p', 'content' => '$entity.public_notes', 'properties' => ['data-ref' => 'total_table-public_notes', 'style' => 'text-align: left;']],
['element' => 'p', 'content' => '', 'properties' => ['style' => 'text-align: left; display: flex; flex-direction: column;'], 'elements' => [
['element' => 'span', 'content' => '$entity.terms_label: ', 'properties' => ['hidden' => $this->entityVariableCheck('$entity.terms'), 'data-ref' => 'total_table-terms-label', 'style' => 'font-weight: bold; text-align: left;']],
['element' => 'span', 'content' => '$entity.terms', 'properties' => ['data-ref' => 'total_table-terms', 'style' => 'text-align: left;']],
]],
]],
];
@ -444,11 +448,11 @@ class Design extends BaseDesign
continue;
}
foreach ($taxes as $tax) {
foreach ($taxes as $i => $tax) {
$elements[] = ['element' => 'div', 'elements' => [
['element' => 'span', 'content' => 'This is placeholder for the 3rd fraction of element.', 'properties' => ['style' => 'opacity: 0%']], // Placeholder for fraction of element (3fr)
['element' => 'span', 'content', 'content' => $tax['name']],
['element' => 'span', 'content', 'content' => Number::formatMoney($tax['total'], $this->context['client'])],
['element' => 'span', 'content', 'content' => $tax['name'], 'properties' => ['data-ref' => 'totals-table-total_tax_' . $i . '-label']],
['element' => 'span', 'content', 'content' => Number::formatMoney($tax['total'], $this->context['client']), 'properties' => ['data-ref' => 'totals-table-total_tax_' . $i]],
]];
}
} elseif ($variable == '$line_taxes') {
@ -458,22 +462,30 @@ class Design extends BaseDesign
continue;
}
foreach ($taxes as $tax) {
foreach ($taxes as $i => $tax) {
$elements[] = ['element' => 'div', 'elements' => [
['element' => 'span', 'content' => 'This is placeholder for the 3rd fraction of element.', 'properties' => ['style' => 'opacity: 0%']], // Placeholder for fraction of element (3fr)
['element' => 'span', 'content', 'content' => $tax['name']],
['element' => 'span', 'content', 'content' => Number::formatMoney($tax['total'], $this->context['client'])],
['element' => 'span', 'content', 'content' => $tax['name'], 'properties' => ['data-ref' => 'totals-table-line_tax_' . $i . '-label']],
['element' => 'span', 'content', 'content' => Number::formatMoney($tax['total'], $this->context['client']), 'properties' => ['data-ref' => 'totals-table-line_tax_' . $i]],
]];
}
} else {
$elements[] = ['element' => 'div', 'elements' => [
['element' => 'span', 'content' => 'This is placeholder for the 3rd fraction of element.', 'properties' => ['style' => 'opacity: 0%']], // Placeholder for fraction of element (3fr)
['element' => 'span', 'content' => $variable . '_label', 'properties' => ['data-ref' => 'totals_table-' . substr($variable, 1)]],
['element' => 'span', 'content' => $variable],
['element' => 'span', 'content' => $variable . '_label', 'properties' => ['data-ref' => 'totals_table-' . substr($variable, 1) . '-label']],
['element' => 'span', 'content' => $variable, 'properties' => ['data-ref' => 'totals_table-' . substr($variable, 1)]],
]];
}
}
if (!is_null($this->entity->partial) && $this->entity->partial > 0) {
$elements[] = ['element' => 'div', 'elements' => [
['element' => 'span', 'content' => 'This is placeholder for the 3rd fraction of element.', 'properties' => ['style' => 'opacity: 0%']], // Placeholder for fraction of element (3fr)
['element' => 'span', 'content' => '$partial_due_label', 'properties' => ['data-ref' => 'totals_table-partial_due-label']],
['element' => 'span', 'content' => '$partial_due'],
]];
}
return $elements;
}
}

View File

@ -159,18 +159,21 @@ class QuoteService
{
$settings = $this->quote->client->getMergedSettings();
if (! $this->quote->design_id) {
if (! $this->quote->design_id)
$this->quote->design_id = $this->decodePrimaryKey($settings->quote_design_id);
}
if (!isset($this->quote->footer)) {
if (!isset($this->quote->footer))
$this->quote->footer = $settings->quote_footer;
}
if (!isset($this->quote->terms)) {
if (!isset($this->quote->terms))
$this->quote->terms = $settings->quote_terms;
}
/* If client currency differs from the company default currency, then insert the client exchange rate on the model.*/
if(!isset($this->quote->exchange_rate) && $this->quote->client->currency()->id != (int) $this->quote->company->settings->currency_id)
$this->quote->exchange_rate = $this->quote->client->currency()->exchange_rate;
if (!isset($this->quote->public_notes))
$this->quote->public_notes = $this->quote->client->public_notes;
return $this;
}

View File

@ -0,0 +1,60 @@
<?php
/**
* Invoice Ninja (https://invoiceninja.com).
*
* @link https://github.com/invoiceninja/invoiceninja source repository
*
* @copyright Copyright (c) 2021. Invoice Ninja LLC (https://invoiceninja.com)
*
* @license https://opensource.org/licenses/AAL
*/
namespace App\Services\Recurring;
use App\Jobs\Entity\CreateEntityPdf;
use App\Models\ClientContact;
use App\Models\Invoice;
use App\Services\AbstractService;
use App\Utils\TempFile;
use Illuminate\Support\Facades\Storage;
class GetInvoicePdf extends AbstractService
{
public $entity;
public function __construct($entity, ClientContact $contact = null)
{
$this->entity = $entity;
$this->contact = $contact;
}
public function run()
{
if (! $this->contact) {
$this->contact = $this->entity->client->primary_contact()->first();
}
$invitation = $this->entity->invitations->where('client_contact_id', $this->contact->id)->first();
$path = $this->entity->client->recurring_invoice_filepath();
$file_path = $path.$this->entity->hashed_id.'.pdf';
$disk = config('filesystems.default');
$file = Storage::disk($disk)->exists($file_path);
if (! $file) {
$file_path = CreateEntityPdf::dispatchNow($invitation);
}
/* Copy from remote disk to local when using cloud file storage. */
if(config('filesystems.default') == 's3')
return TempFile::path(Storage::disk($disk)->url($file_path));
// return Storage::disk($disk)->url($file_path);
return Storage::disk($disk)->path($file_path);
}
}

View File

@ -12,6 +12,7 @@
namespace App\Services\Recurring;
use App\Models\RecurringInvoice;
use App\Services\Recurring\GetInvoicePdf;
use Illuminate\Support\Carbon;
class RecurringService
@ -77,6 +78,11 @@ class RecurringService
return $this;
}
public function getInvoicePdf($contact = null)
{
return (new GetInvoicePdf($this->recurring_entity, $contact))->run();
}
public function save()
{
$this->recurring_entity->save();

View File

@ -75,6 +75,7 @@ class AccountTransformer extends EntityTransformer
'archived_at' => (int) $account->deleted_at,
'report_errors' => (bool) $account->report_errors,
'debug_enabled' => (bool) config('ninja.debug_enabled'),
'is_docker' => (bool) config('ninja.is_docker'),
];
}

View File

@ -59,7 +59,7 @@ class TaskTransformer extends EntityTransformer
'project_id' => $this->encodePrimaryKey($task->project_id) ?: '',
'is_deleted' => (bool) $task->is_deleted,
'time_log' => $task->time_log ?: '',
'is_running' => (bool) $task->is_running,
'is_running' => (bool) $task->is_running, //@deprecate
'custom_value1' => $task->custom_value1 ?: '',
'custom_value2' => $task->custom_value2 ?: '',
'custom_value3' => $task->custom_value3 ?: '',

View File

@ -96,7 +96,7 @@ class HtmlEngine
}
$data = [];
$data['$global_margin'] = ['value' => '0cm', 'label' => ''];
$data['$global_margin'] = ['value' => '6.35mm', 'label' => ''];
$data['$tax'] = ['value' => '', 'label' => ctrans('texts.tax')];
$data['$app_url'] = ['value' => $this->generateAppUrl(), 'label' => ''];
$data['$from'] = ['value' => '', 'label' => ctrans('texts.from')];
@ -106,7 +106,7 @@ class HtmlEngine
$data['$line_tax_labels'] = ['value' => $this->lineTaxLabels(), 'label' => ctrans('texts.taxes')];
$data['$line_tax_values'] = ['value' => $this->lineTaxValues(), 'label' => ctrans('texts.taxes')];
$data['$date'] = ['value' => $this->formatDate($this->entity->date, $this->entity->client->date_format()) ?: '&nbsp;', 'label' => ctrans('texts.date')];
//$data['$invoice_date'] = ['value' => $this->date ?: '&nbsp;', 'label' => ctrans('texts.invoice_date')];
$data['$invoice.date'] = &$data['$date'];
$data['$due_date'] = ['value' => $this->formatDate($this->entity->due_date, $this->entity->client->date_format()) ?: '&nbsp;', 'label' => ctrans('texts.'.$this->entity_string.'_due_date')];
$data['$payment_due'] = ['value' => $this->formatDate($this->entity->due_date, $this->entity->client->date_format()) ?: '&nbsp;', 'label' => ctrans('texts.payment_due')];
@ -118,13 +118,7 @@ class HtmlEngine
$data['$quote.datetime'] = &$data['$entity.datetime'];
$data['$credit.datetime'] = &$data['$entity.datetime'];
// $data['$line_taxes'] = ['value' => $this->makeLineTaxes() ?: '&nbsp;', 'label' => ctrans('texts.taxes')];
// $data['$invoice.line_taxes'] = &$data['$line_taxes'];
// $data['$total_taxes'] = ['value' => $this->makeTotalTaxes() ?: '&nbsp;', 'label' => ctrans('texts.taxes')];
// $data['$invoice.total_taxes'] = &$data['$total_taxes'];
if ($this->entity_string == 'invoice') {
if ($this->entity_string == 'invoice' || $this->entity_string == 'recurring_invoice') {
$data['$entity'] = ['value' => '', 'label' => ctrans('texts.invoice')];
$data['$number'] = ['value' => $this->entity->number ?: '&nbsp;', 'label' => ctrans('texts.invoice_number')];
$data['$entity.terms'] = ['value' => $this->entity->terms ?: '&nbsp;', 'label' => ctrans('texts.invoice_terms')];
@ -159,14 +153,14 @@ class HtmlEngine
$data['$invoice.subtotal'] = &$data['$subtotal'];
if ($this->entity->partial > 0) {
$data['$balance_due'] = ['value' => Number::formatMoney($this->entity->partial, $this->client) ?: '&nbsp;', 'label' => ctrans('texts.balance_due')];
$data['$balance_due'] = ['value' => Number::formatMoney($this->entity->partial, $this->client) ?: '&nbsp;', 'label' => ctrans('texts.partial_due')];
} else {
$data['$balance_due'] = ['value' => Number::formatMoney($this->entity->balance, $this->client) ?: '&nbsp;', 'label' => ctrans('texts.balance_due')];
}
$data['$quote.balance_due'] = $data['$balance_due'];
$data['$invoice.balance_due'] = $data['$balance_due'];
$data['$balance_due'] = $data['$balance_due'];
// $data['$balance_due'] = $data['$balance_due'];
$data['$outstanding'] = $data['$balance_due'];
$data['$partial_due'] = ['value' => Number::formatMoney($this->entity->partial, $this->client) ?: '&nbsp;', 'label' => ctrans('texts.partial_due')];
$data['$total'] = ['value' => Number::formatMoney($this->entity_calc->getTotal(), $this->client) ?: '&nbsp;', 'label' => ctrans('texts.total')];
@ -212,15 +206,6 @@ class HtmlEngine
$data['$credit_no'] = &$data['$number'];
$data['$credit.credit_no'] = &$data['$number'];
// $data['$invoice_issued_to'] = ;
// $data['$quote_issued_to'] = ;
// $data['$rate'] = ;
// $data['$hours'] = ;
// $data['$from'] = ;
// $data['$to'] = ;
// $data['$invoice_to'] = ;
// $data['$quote_to'] = ;
// $data['$details'] = ;
$data['$invoice_no'] = &$data['$number'];
$data['$invoice.invoice_no'] = &$data['$number'];
$data['$client1'] = ['value' => $this->helpers->formatCustomFieldValue($this->company->custom_fields, 'client1', $this->client->custom_value1, $this->client) ?: '&nbsp;', 'label' => $this->helpers->makeCustomField($this->company->custom_fields, 'client1')];
@ -362,44 +347,6 @@ class HtmlEngine
$data['$entity_footer'] = ['value' => $this->client->getSetting("{$this->entity_string}_footer"), 'label' => ''];
// $data['custom_label1'] = ['value' => '', 'label' => ctrans('texts.')];
// $data['custom_label2'] = ['value' => '', 'label' => ctrans('texts.')];
// $data['custom_label3'] = ['value' => '', 'label' => ctrans('texts.')];
// $data['custom_label4'] = ['value' => '', 'label' => ctrans('texts.')];
//$data['$blank'] = ;
//$data['$surcharge'] = ;
/*
$data['$tax_invoice'] =
$data['$tax_quote'] =
$data['$statement'] = ;
$data['$statement_date'] = ;
$data['$your_statement'] = ;
$data['$statement_issued_to'] = ;
$data['$statement_to'] = ;
$data['$credit_note'] = ;
$data['$credit_date'] = ;
$data['$credit_issued_to'] = ;
$data['$credit_to'] = ;
$data['$your_credit'] = ;
$data['$phone'] = ;
$data['$outstanding'] = ;
$data['$invoice_due_date'] = ;
$data['$quote_due_date'] = ;
$data['$service'] = ;
$data['$product_key'] = ;
$data['$unit_cost'] = ;
$data['$custom_value1'] = ;
$data['$custom_value2'] = ;
$data['$delivery_note'] = ;
$data['$date'] = ;
$data['$method'] = ;
$data['$payment_date'] = ;
$data['$reference'] = ;
$data['$amount'] = ;
$data['$amount_paid'] =;
*/
$arrKeysLength = array_map('strlen', array_keys($data));
array_multisort($arrKeysLength, SORT_DESC, $data);

View File

@ -13,7 +13,7 @@ return [
'require_https' => env('REQUIRE_HTTPS', true),
'app_url' => rtrim(env('APP_URL', ''), '/'),
'app_domain' => env('APP_DOMAIN', ''),
'app_version' => '5.0.47',
'app_version' => '5.0.48',
'minimum_client_version' => '5.0.16',
'terms_version' => '1.0.1',
'api_secret' => env('API_SECRET', false),
@ -33,7 +33,7 @@ return [
'phantomjs_secret' => env('PHANTOMJS_SECRET', false),
'phantomjs_pdf_generation' => env('PHANTOMJS_PDF_GENERATION', true),
'trusted_proxies' => env('TRUSTED_PROXIES', false),
'is_docker' => env('IS_DOCKER', false),
'sentry_dsn' => env('SENTRY_LARAVEL_DSN', 'https://9b4e15e575214354a7d666489783904a@sentry.invoicing.co/6'),
'environment' => env('NINJA_ENVIRONMENT', 'selfhost'), // 'hosted', 'development', 'selfhost', 'reseller'

View File

@ -0,0 +1,28 @@
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
class UpdateDesigns extends Migration
{
/**
* Run the migrations.
*
* @return void
*/
public function up()
{
\Illuminate\Support\Facades\Artisan::call('ninja:design-update');
}
/**
* Reverse the migrations.
*
* @return void
*/
public function down()
{
//
}
}

View File

@ -0,0 +1,57 @@
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
class ChangeCustomSurchargeColumnType extends Migration
{
/**
* Run the migrations.
*
* @return void
*/
public function up()
{
Schema::table('invoices', function (Blueprint $table) {
$table->decimal('custom_surcharge1', 20,6)->change();
$table->decimal('custom_surcharge2', 20,6)->change();
$table->decimal('custom_surcharge3', 20,6)->change();
$table->decimal('custom_surcharge4', 20,6)->change();
});
Schema::table('recurring_invoices', function (Blueprint $table) {
$table->decimal('custom_surcharge1', 20,6)->change();
$table->decimal('custom_surcharge2', 20,6)->change();
$table->decimal('custom_surcharge3', 20,6)->change();
$table->decimal('custom_surcharge4', 20,6)->change();
});
Schema::table('quotes', function (Blueprint $table) {
$table->decimal('custom_surcharge1', 20,6)->change();
$table->decimal('custom_surcharge2', 20,6)->change();
$table->decimal('custom_surcharge3', 20,6)->change();
$table->decimal('custom_surcharge4', 20,6)->change();
});
Schema::table('credits', function (Blueprint $table) {
$table->decimal('custom_surcharge1', 20,6)->change();
$table->decimal('custom_surcharge2', 20,6)->change();
$table->decimal('custom_surcharge3', 20,6)->change();
$table->decimal('custom_surcharge4', 20,6)->change();
});
}
/**
* Reverse the migrations.
*
* @return void
*/
public function down()
{
//
}
}

View File

@ -497,6 +497,38 @@ See the License for the specific language governing permissions and
limitations under the License.
--------------------------------------------------------------------------------
abseil-cpp
accessibility
skia
Copyright 2020 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
abseil-cpp
angle
boringssl
etc1
@ -708,10 +740,419 @@ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
--------------------------------------------------------------------------------
abseil-cpp
accessibility
Copyright (c) 2009 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
accessibility
Copyright (c) 2017 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
accessibility
Copyright (c) 2018 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
accessibility
Copyright (c) 2019 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
accessibility
angle
Copyright (c) 2013 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
accessibility
base
Copyright 2013 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
accessibility
base
fuchsia_sdk
skia
zlib
Copyright 2018 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
accessibility
base
icu
zlib
Copyright 2014 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
accessibility
base
zlib
Copyright (c) 2011 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
accessibility
fuchsia_sdk
skia
zlib
Copyright 2019 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
accessibility
icu
skia
Copyright 2020 The Chromium Authors. All rights reserved.
Copyright 2015 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
accessibility
icu
skia
Copyright 2016 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
accessibility
zlib
Copyright (c) 2012 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
accessibility
zlib
Copyright 2017 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
@ -894,36 +1335,6 @@ SOFTWARE.
--------------------------------------------------------------------------------
angle
Copyright (c) 2013 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
angle
Copyright (c) 2019 The ANGLE Project Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
@ -1484,9 +1895,6 @@ notice, this list of conditions and the following disclaimer.
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google LLC. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
@ -1788,132 +2196,6 @@ THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
base
Copyright 2013 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
base
fuchsia_sdk
skia
zlib
Copyright 2018 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
base
icu
zlib
Copyright 2014 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
base
zlib
Copyright (c) 2011 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
boolean_selector
build
@ -7713,36 +7995,6 @@ Legal Terms
--------------------------------------------------------------------------------
fuchsia_sdk
Copyright 2013 The Fuchsia Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google LLC. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
fuchsia_sdk
Copyright 2014 The Fuchsia Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
@ -7755,9 +8007,6 @@ notice, this list of conditions and the following disclaimer.
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google LLC. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
@ -7785,9 +8034,6 @@ notice, this list of conditions and the following disclaimer.
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google LLC. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
@ -7815,9 +8061,6 @@ notice, this list of conditions and the following disclaimer.
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google LLC. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
@ -7846,9 +8089,6 @@ notice, this list of conditions and the following disclaimer.
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google LLC. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
@ -7876,9 +8116,6 @@ notice, this list of conditions and the following disclaimer.
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google LLC. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
@ -7906,9 +8143,33 @@ notice, this list of conditions and the following disclaimer.
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google LLC. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
fuchsia_sdk
Copyright 2019 The Fuchsia Authors.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
@ -7936,9 +8197,6 @@ notice, this list of conditions and the following disclaimer.
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google LLC. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
@ -8301,38 +8559,6 @@ The above copyright notice and this permission notice shall be included in all c
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
--------------------------------------------------------------------------------
fuchsia_sdk
skia
zlib
Copyright 2019 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
glfw
Copyright (c) 2002-2006 Marcus Geelnard
@ -11449,68 +11675,6 @@ shall not be used in advertising or otherwise to promote the sale,
use or other dealings in these Data Files or Software without prior
written authorization of the copyright holder.
--------------------------------------------------------------------------------
icu
skia
Copyright 2015 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
icu
skia
Copyright 2016 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
image
Copyright 2013 Brendan Duncan
@ -17963,66 +18127,6 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
zlib
Copyright (c) 2012 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
zlib
Copyright 2017 The Chromium Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
--------------------------------------------------------------------------------
zlib
version 1.2.11, January 15th, 2017
Copyright (C) 1995-2017 Jean-loup Gailly and Mark Adler

2
public/css/app.css vendored

File diff suppressed because one or more lines are too long

View File

@ -3,36 +3,36 @@ const MANIFEST = 'flutter-app-manifest';
const TEMP = 'flutter-temp-cache';
const CACHE_NAME = 'flutter-app-cache';
const RESOURCES = {
"icons/Icon-512.png": "0f9aff01367f0a0c69773d25ca16ef35",
"icons/Icon-192.png": "bb1cf5f6982006952211c7c8404ffbed",
"favicon.ico": "51636d3a390451561744c42188ccd628",
"manifest.json": "77215c1737c7639764e64a192be2f7b8",
"assets/packages/material_design_icons_flutter/lib/fonts/materialdesignicons-webfont.ttf": "c1242726c7eac4eb5e843d826f78fb1b",
"assets/NOTICES": "78d34f6f5f2ada51f119a89da5b00dfe",
"assets/assets/images/logo.png": "090f69e23311a4b6d851b3880ae52541",
"assets/assets/images/payment_types/mastercard.png": "6f6cdc29ee2e22e06b1ac029cb52ef71",
"assets/assets/images/payment_types/amex.png": "c49a4247984b3732a4af50a3390aa978",
"assets/assets/images/payment_types/unionpay.png": "7002f52004e0ab8cc0b7450b0208ccb2",
"assets/assets/images/payment_types/switch.png": "4fa11c45327f5fdc20205821b2cfd9cc",
"assets/assets/images/payment_types/paypal.png": "8e06c094c1871376dfea1da8088c29d1",
"assets/assets/images/payment_types/visa.png": "3ddc4a4d25c946e8ad7e6998f30fd4e3",
"assets/assets/images/payment_types/laser.png": "b4e6e93dd35517ac429301119ff05868",
"assets/assets/images/payment_types/other.png": "d936e11fa3884b8c9f1bd5c914be8629",
"assets/assets/images/payment_types/dinerscard.png": "06d85186ba858c18ab7c9caa42c92024",
"assets/assets/images/payment_types/carteblanche.png": "d936e11fa3884b8c9f1bd5c914be8629",
"assets/assets/images/payment_types/paypal.png": "8e06c094c1871376dfea1da8088c29d1",
"assets/assets/images/payment_types/ach.png": "7433f0aff779dc98a649b7a2daf777cf",
"assets/assets/images/payment_types/switch.png": "4fa11c45327f5fdc20205821b2cfd9cc",
"assets/assets/images/payment_types/amex.png": "c49a4247984b3732a4af50a3390aa978",
"assets/assets/images/payment_types/dinerscard.png": "06d85186ba858c18ab7c9caa42c92024",
"assets/assets/images/payment_types/solo.png": "2030c3ccaccf5d5e87916a62f5b084d6",
"assets/assets/images/payment_types/discover.png": "6c0a386a00307f87db7bea366cca35f5",
"assets/assets/images/payment_types/maestro.png": "e533b92bfb50339fdbfa79e3dfe81f08",
"assets/assets/images/payment_types/unionpay.png": "7002f52004e0ab8cc0b7450b0208ccb2",
"assets/assets/images/payment_types/other.png": "d936e11fa3884b8c9f1bd5c914be8629",
"assets/assets/images/payment_types/jcb.png": "07e0942d16c5592118b72e74f2f7198c",
"assets/assets/images/payment_types/maestro.png": "e533b92bfb50339fdbfa79e3dfe81f08",
"assets/assets/images/payment_types/mastercard.png": "6f6cdc29ee2e22e06b1ac029cb52ef71",
"assets/assets/images/payment_types/discover.png": "6c0a386a00307f87db7bea366cca35f5",
"assets/assets/images/payment_types/visa.png": "3ddc4a4d25c946e8ad7e6998f30fd4e3",
"assets/assets/images/payment_types/carteblanche.png": "d936e11fa3884b8c9f1bd5c914be8629",
"assets/assets/images/payment_types/laser.png": "b4e6e93dd35517ac429301119ff05868",
"assets/assets/images/logo.png": "090f69e23311a4b6d851b3880ae52541",
"assets/assets/images/google-icon.png": "0f118259ce403274f407f5e982e681c3",
"assets/AssetManifest.json": "659dcf9d1baf3aed3ab1b9c42112bf8f",
"assets/packages/material_design_icons_flutter/lib/fonts/materialdesignicons-webfont.ttf": "c1242726c7eac4eb5e843d826f78fb1b",
"assets/FontManifest.json": "cf3c681641169319e61b61bd0277378f",
"assets/fonts/MaterialIcons-Regular.otf": "1288c9e28052e028aba623321f7826ac",
"/": "23224b5e03519aaa87594403d54412cf",
"assets/NOTICES": "1965e076d9705b3500fedcfad4bebcdf",
"assets/AssetManifest.json": "659dcf9d1baf3aed3ab1b9c42112bf8f",
"version.json": "6b7a4ad416a3730ae32b64e007cef7f3",
"main.dart.js": "ef2ed4cc194dd16d85ab85db7f0e155f",
"favicon.png": "dca91c54388f52eded692718d5a98b8b"
"favicon.png": "dca91c54388f52eded692718d5a98b8b",
"main.dart.js": "1e4432ea8822b383364c591ad3798039",
"manifest.json": "77215c1737c7639764e64a192be2f7b8",
"/": "23224b5e03519aaa87594403d54412cf",
"icons/Icon-512.png": "0f9aff01367f0a0c69773d25ca16ef35",
"icons/Icon-192.png": "bb1cf5f6982006952211c7c8404ffbed",
"favicon.ico": "51636d3a390451561744c42188ccd628"
};
// The application shell files that are downloaded before a service worker can

View File

@ -3,7 +3,7 @@
*
* @link https://github.com/invoiceninja/invoiceninja source repository
*
* @copyright Copyright (c) 2020. Invoice Ninja LLC (https://invoiceninja.com)
* @copyright Copyright (c) 2021. Invoice Ninja LLC (https://invoiceninja.com)
*
* @license https://opensource.org/licenses/AAL
*/

View File

@ -3,7 +3,7 @@
*
* @link https://github.com/invoiceninja/invoiceninja source repository
*
* @copyright Copyright (c) 2020. Invoice Ninja LLC (https://invoiceninja.com)
* @copyright Copyright (c) 2021. Invoice Ninja LLC (https://invoiceninja.com)
*
* @license https://opensource.org/licenses/AAL
*/

View File

@ -3,7 +3,7 @@
*
* @link https://github.com/invoiceninja/invoiceninja source repository
*
* @copyright Copyright (c) 2020. Invoice Ninja LLC (https://invoiceninja.com)
* @copyright Copyright (c) 2021. Invoice Ninja LLC (https://invoiceninja.com)
*
* @license https://opensource.org/licenses/AAL
*/

View File

@ -3,7 +3,7 @@
*
* @link https://github.com/invoiceninja/invoiceninja source repository
*
* @copyright Copyright (c) 2020. Invoice Ninja LLC (https://invoiceninja.com)
* @copyright Copyright (c) 2021. Invoice Ninja LLC (https://invoiceninja.com)
*
* @license https://opensource.org/licenses/AAL
*/

View File

@ -3,7 +3,7 @@
*
* @link https://github.com/invoiceninja/invoiceninja source repository
*
* @copyright Copyright (c) 2020. Invoice Ninja LLC (https://invoiceninja.com)
* @copyright Copyright (c) 2021. Invoice Ninja LLC (https://invoiceninja.com)
*
* @license https://opensource.org/licenses/AAL
*/

View File

@ -3,7 +3,7 @@
*
* @link https://github.com/invoiceninja/invoiceninja source repository
*
* @copyright Copyright (c) 2020. Invoice Ninja LLC (https://invoiceninja.com)
* @copyright Copyright (c) 2021. Invoice Ninja LLC (https://invoiceninja.com)
*
* @license https://opensource.org/licenses/AAL
*/

View File

@ -3,7 +3,7 @@
*
* @link https://github.com/invoiceninja/invoiceninja source repository
*
* @copyright Copyright (c) 2020. Invoice Ninja LLC (https://invoiceninja.com)
* @copyright Copyright (c) 2021. Invoice Ninja LLC (https://invoiceninja.com)
*
* @license https://opensource.org/licenses/AAL
*/

View File

@ -3,7 +3,7 @@
*
* @link https://github.com/invoiceninja/invoiceninja source repository
*
* @copyright Copyright (c) 2020. Invoice Ninja LLC (https://invoiceninja.com)
* @copyright Copyright (c) 2021. Invoice Ninja LLC (https://invoiceninja.com)
*
* @license https://opensource.org/licenses/AAL
*/

View File

@ -3,7 +3,7 @@
*
* @link https://github.com/invoiceninja/invoiceninja source repository
*
* @copyright Copyright (c) 2020. Invoice Ninja LLC (https://invoiceninja.com)
* @copyright Copyright (c) 2021. Invoice Ninja LLC (https://invoiceninja.com)
*
* @license https://opensource.org/licenses/AAL
*/

View File

@ -3,7 +3,7 @@
*
* @link https://github.com/invoiceninja/invoiceninja source repository
*
* @copyright Copyright (c) 2020. Invoice Ninja LLC (https://invoiceninja.com)
* @copyright Copyright (c) 2021. Invoice Ninja LLC (https://invoiceninja.com)
*
* @license https://opensource.org/licenses/AAL
*/

View File

@ -3,7 +3,7 @@
*
* @link https://github.com/invoiceninja/invoiceninja source repository
*
* @copyright Copyright (c) 2020. Invoice Ninja LLC (https://invoiceninja.com)
* @copyright Copyright (c) 2021. Invoice Ninja LLC (https://invoiceninja.com)
*
* @license https://opensource.org/licenses/AAL
*/

View File

@ -3,7 +3,7 @@
*
* @link https://github.com/invoiceninja/invoiceninja source repository
*
* @copyright Copyright (c) 2020. Invoice Ninja LLC (https://invoiceninja.com)
* @copyright Copyright (c) 2021. Invoice Ninja LLC (https://invoiceninja.com)
*
* @license https://opensource.org/licenses/AAL
*/

View File

@ -3,7 +3,7 @@
*
* @link https://github.com/invoiceninja/invoiceninja source repository
*
* @copyright Copyright (c) 2020. Invoice Ninja LLC (https://invoiceninja.com)
* @copyright Copyright (c) 2021. Invoice Ninja LLC (https://invoiceninja.com)
*
* @license https://opensource.org/licenses/AAL
*/

Some files were not shown because too many files have changed in this diff Show More