diff --git a/VERSION.txt b/VERSION.txt
index cac426c2230f..a8ed8715d837 100644
--- a/VERSION.txt
+++ b/VERSION.txt
@@ -1 +1 @@
-5.5.95
\ No newline at end of file
+5.5.96
\ No newline at end of file
diff --git a/app/Console/Commands/BackupUpdate.php b/app/Console/Commands/BackupUpdate.php
index 536e1499e80d..a2fc126e9264 100644
--- a/app/Console/Commands/BackupUpdate.php
+++ b/app/Console/Commands/BackupUpdate.php
@@ -190,14 +190,12 @@ class BackupUpdate extends Command
->where('filename', '!=', '')
->cursor()
->each(function ($backup) {
-
$backup_bin = Storage::disk('s3')->get($backup->filename);
if ($backup_bin) {
Storage::disk($this->option('disk'))->put($backup->filename, $backup_bin);
nlog("Backups - Moving {$backup->filename} to {$this->option('disk')}");
-
}
});
}
diff --git a/app/Console/Commands/CheckData.php b/app/Console/Commands/CheckData.php
index 8e04496b3782..202f37280504 100644
--- a/app/Console/Commands/CheckData.php
+++ b/app/Console/Commands/CheckData.php
@@ -12,36 +12,36 @@
namespace App\Console\Commands;
use App;
-use Exception;
-use App\Models\User;
-use App\Utils\Ninja;
-use App\Models\Quote;
-use App\Models\Client;
-use App\Models\Credit;
-use App\Models\Vendor;
-use App\Models\Account;
-use App\Models\Company;
-use App\Models\Contact;
-use App\Models\Invoice;
-use App\Models\Payment;
-use App\Models\CompanyUser;
-use Illuminate\Support\Str;
-use App\Models\CompanyToken;
-use App\Models\ClientContact;
-use App\Models\CompanyLedger;
-use App\Models\PurchaseOrder;
-use App\Models\VendorContact;
-use App\Models\QuoteInvitation;
-use Illuminate\Console\Command;
-use App\Models\CreditInvitation;
-use App\Models\InvoiceInvitation;
use App\DataMapper\ClientSettings;
-use Illuminate\Support\Facades\DB;
-use Illuminate\Support\Facades\Mail;
use App\Factory\ClientContactFactory;
use App\Factory\VendorContactFactory;
use App\Jobs\Company\CreateCompanyToken;
+use App\Models\Account;
+use App\Models\Client;
+use App\Models\ClientContact;
+use App\Models\Company;
+use App\Models\CompanyLedger;
+use App\Models\CompanyToken;
+use App\Models\CompanyUser;
+use App\Models\Contact;
+use App\Models\Credit;
+use App\Models\CreditInvitation;
+use App\Models\Invoice;
+use App\Models\InvoiceInvitation;
+use App\Models\Payment;
+use App\Models\PurchaseOrder;
+use App\Models\Quote;
+use App\Models\QuoteInvitation;
use App\Models\RecurringInvoiceInvitation;
+use App\Models\User;
+use App\Models\Vendor;
+use App\Models\VendorContact;
+use App\Utils\Ninja;
+use Exception;
+use Illuminate\Console\Command;
+use Illuminate\Support\Facades\DB;
+use Illuminate\Support\Facades\Mail;
+use Illuminate\Support\Str;
use Symfony\Component\Console\Input\InputOption;
/*
@@ -176,18 +176,16 @@ class CheckData extends Command
if (CompanyToken::where('user_id', $cu->user_id)->where('company_id', $cu->company_id)->where('is_system', 1)->doesntExist()) {
$this->logMessage("Creating missing company token for user # {$cu->user_id} for company id # {$cu->company_id}");
- if($cu->company && $cu->user)
+ if ($cu->company && $cu->user) {
(new CreateCompanyToken($cu->company, $cu->user, 'System'))->handle();
+ }
}
});
-
-
-
}
/**
* checkOauthSanity
- *
+ *
* @return void
*/
private function checkOauthSanity()
diff --git a/app/Console/Kernel.php b/app/Console/Kernel.php
index 4ba49439c45d..b0002daf3d79 100644
--- a/app/Console/Kernel.php
+++ b/app/Console/Kernel.php
@@ -27,7 +27,6 @@ use App\Jobs\Subscription\CleanStaleInvoiceOrder;
use App\Jobs\Util\DiskCleanup;
use App\Jobs\Util\ReminderJob;
use App\Jobs\Util\SchedulerCheck;
-use App\Jobs\Util\SendFailedEmails;
use App\Jobs\Util\UpdateExchangeRates;
use App\Jobs\Util\VersionCheck;
use App\Models\Account;
diff --git a/app/DataMapper/ClientSettings.php b/app/DataMapper/ClientSettings.php
index de723d6f1967..4e0f02176fbc 100644
--- a/app/DataMapper/ClientSettings.php
+++ b/app/DataMapper/ClientSettings.php
@@ -84,13 +84,13 @@ class ClientSettings extends BaseSettings
*/
public static function buildClientSettings($company_settings, $client_settings)
{
-
if (! $client_settings) {
return $company_settings;
}
- if(is_array($client_settings))
+ if (is_array($client_settings)) {
$client_settings = (object)$client_settings;
+ }
foreach ($company_settings as $key => $value) {
/* pseudo code
diff --git a/app/DataMapper/Schedule/ScheduleInvoice.php b/app/DataMapper/Schedule/ScheduleEntity.php
similarity index 80%
rename from app/DataMapper/Schedule/ScheduleInvoice.php
rename to app/DataMapper/Schedule/ScheduleEntity.php
index 71b57e820b50..649360f4354c 100644
--- a/app/DataMapper/Schedule/ScheduleInvoice.php
+++ b/app/DataMapper/Schedule/ScheduleEntity.php
@@ -11,21 +11,21 @@
namespace App\DataMapper\Schedule;
-class ScheduleInvoice
+class ScheduleEntity
{
/**
* Defines the template name
*
* @var string
*/
- public string $template = 'schedule_invoice';
+ public string $template = 'schedule_entity';
/**
* Defines the template name
*
* @var string
*/
- public string $entity = '';
+ public string $entity = ''; // invoice, credit, quote, purchase_order
/**
* Defines the template name
@@ -33,5 +33,4 @@ class ScheduleInvoice
* @var string
*/
public string $entity_id = '';
-
}
diff --git a/app/DataMapper/Tax/RuleInterface.php b/app/DataMapper/Tax/RuleInterface.php
new file mode 100644
index 000000000000..ec88cd72c67d
--- /dev/null
+++ b/app/DataMapper/Tax/RuleInterface.php
@@ -0,0 +1,17 @@
+ [
+ * [
+ * "geoPostalCode" => "92582",
+ * "geoCity" => "SAN JACINTO",
+ * "geoCounty" => "RIVERSIDE",
+ * "geoState" => "CA",
+ * "taxSales" => 0.0875,
+ * "taxUse" => 0.0875,
+ * "txbService" => "N",
+ * "txbFreight" => "N",
+ * "stateSalesTax" => 0.06,
+ * "stateUseTax" => 0.06,
+ * "citySalesTax" => 0.01,
+ * "cityUseTax" => 0.01,
+ * "cityTaxCode" => "874",
+ * "countySalesTax" => 0.0025,
+ * "countyUseTax" => 0.0025,
+ * "countyTaxCode" => "",
+ * "districtSalesTax" => 0.015,
+ * "districtUseTax" => 0.015,
+ * "district1Code" => "26",
+ * "district1SalesTax" => 0,
+ * "district1UseTax" => 0,
+ * "district2Code" => "26",
+ * "district2SalesTax" => 0.005,
+ * "district2UseTax" => 0.005,
+ * "district3Code" => "",
+ * "district3SalesTax" => 0,
+ * "district3UseTax" => 0,
+ * "district4Code" => "33",
+ * "district4SalesTax" => 0.01,
+ * "district4UseTax" => 0.01,
+ * "district5Code" => "",
+ * "district5SalesTax" => 0,
+ * "district5UseTax" => 0,
+ * "originDestination" => "D",
+ * ],
+ * ]
+ * ];
+ *
+ * @var mixed[]
+ */
+ public array $results = [];
+
+}
+
diff --git a/app/DataMapper/Tax/de/Rule.php b/app/DataMapper/Tax/de/Rule.php
new file mode 100644
index 000000000000..4332abfa81c9
--- /dev/null
+++ b/app/DataMapper/Tax/de/Rule.php
@@ -0,0 +1,96 @@
+input['client_id']) && $this->input['client_id'] != 'all') {
-
$client = Client::withTrashed()->find($this->input['client_id']);
$this->client_description = $client->present()->name;
return $query->where('client_id', $this->input['client_id']);
diff --git a/app/Export/CSV/ProductSalesExport.php b/app/Export/CSV/ProductSalesExport.php
index 6a2708fbc7e0..b6110dd480f5 100644
--- a/app/Export/CSV/ProductSalesExport.php
+++ b/app/Export/CSV/ProductSalesExport.php
@@ -11,15 +11,15 @@
namespace App\Export\CSV;
-use App\Utils\Ninja;
-use League\Csv\Writer;
+use App\Libraries\MultiDB;
use App\Models\Company;
use App\Models\Invoice;
use App\Models\Product;
-use App\Libraries\MultiDB;
+use App\Utils\Ninja;
+use Illuminate\Database\Eloquent\Collection;
use Illuminate\Support\Carbon;
use Illuminate\Support\Facades\App;
-use Illuminate\Database\Eloquent\Collection;
+use League\Csv\Writer;
class ProductSalesExport extends BaseExport
{
@@ -117,10 +117,9 @@ class ProductSalesExport extends BaseExport
});
- $grouped = $this->sales->groupBy('product_key')->map(function ($key, $value){
-
+ $grouped = $this->sales->groupBy('product_key')->map(function ($key, $value) {
$data = [
- 'product' => $value,
+ 'product' => $value,
'quantity' => $key->sum('quantity'),
'markup' => $key->sum('markup'),
'profit' => $key->sum('profit'),
@@ -183,11 +182,10 @@ class ProductSalesExport extends BaseExport
$this->sales->push($entity);
return $entity;
-
}
private function decorateAdvancedFields(Invoice $invoice, $entity) :array
- {
+ {
$product = $this->getProduct($entity['product_key']);
$entity['cost'] = $product->cost ?? 0;
@@ -199,31 +197,31 @@ class ProductSalesExport extends BaseExport
$entity['date'] = Carbon::parse($invoice->date)->format($this->company->date_format());
$entity['discount'] = $this->calculateDiscount($invoice, $entity);
- $entity['markup'] = round(((($entity['price'] - $entity['discount'] - $entity['cost']) / $unit_cost) * 100),2);
+ $entity['markup'] = round(((($entity['price'] - $entity['discount'] - $entity['cost']) / $unit_cost) * 100), 2);
$entity['net_total'] = $entity['price'] - $entity['discount'];
$entity['profit'] = $entity['price'] - $entity['discount'] - $entity['cost'];
- if(strlen($entity['tax_name1']) > 1) {
+ if (strlen($entity['tax_name1']) > 1) {
$entity['tax_name1'] = $entity['tax_name1'] . ' [' . $entity['tax_rate1'] . '%]';
$entity['tax_amount1'] = $this->calculateTax($invoice, $entity['line_total'], $entity['tax_rate1']);
- }
- else
+ } else {
$entity['tax_amount1'] = 0;
+ }
- if(strlen($entity['tax_name2']) > 1) {
+ if (strlen($entity['tax_name2']) > 1) {
$entity['tax_name2'] = $entity['tax_name2'] . ' [' . $entity['tax_rate2'] . '%]';
$entity['tax_amount2'] = $this->calculateTax($invoice, $entity['line_total'], $entity['tax_rate2']);
- }
- else
+ } else {
$entity['tax_amount2'] = 0;
+ }
- if(strlen($entity['tax_name3']) > 1) {
+ if (strlen($entity['tax_name3']) > 1) {
$entity['tax_name3'] = $entity['tax_name3'] . ' [' . $entity['tax_rate3'] . '%]';
$entity['tax_amount3'] = $this->calculateTax($invoice, $entity['line_total'], $entity['tax_rate3']);
- }
- else
+ } else {
$entity['tax_amount3'] = 0;
+ }
return $entity;
}
@@ -240,13 +238,11 @@ class ProductSalesExport extends BaseExport
{
$amount = $amount - ($amount * ($invoice->discount / 100));
- if($invoice->uses_inclusive_taxes) {
+ if ($invoice->uses_inclusive_taxes) {
return round($amount - ($amount / (1 + ($tax_rate / 100))), 2);
- }
- else {
+ } else {
return round(($amount * $tax_rate / 100), 2);
}
-
}
@@ -258,15 +254,15 @@ class ProductSalesExport extends BaseExport
* @param mixed $entity
* @return float
*/
- private function calculateDiscount(Invoice $invoice , $entity) :float
+ private function calculateDiscount(Invoice $invoice, $entity) :float
{
- if($entity['discount'] == 0)
+ if ($entity['discount'] == 0) {
return 0;
-
- if($invoice->is_amount_discount && $entity['discount'] != 0) {
- return $entity['discount'];
}
- elseif(!$invoice->is_amount_discount && $entity['discount'] != 0) {
+
+ if ($invoice->is_amount_discount && $entity['discount'] != 0) {
+ return $entity['discount'];
+ } elseif (!$invoice->is_amount_discount && $entity['discount'] != 0) {
return round($entity['line_total'] * ($entity['discount'] / 100), 2);
}
diff --git a/app/Filters/CreditFilters.php b/app/Filters/CreditFilters.php
index 7f00792adc0f..ffbbba3fdb90 100644
--- a/app/Filters/CreditFilters.php
+++ b/app/Filters/CreditFilters.php
@@ -86,8 +86,8 @@ class CreditFilters extends QueryFilters
->orWhere('credits.custom_value2', 'like', '%'.$filter.'%')
->orWhere('credits.custom_value3', 'like', '%'.$filter.'%')
->orWhere('credits.custom_value4', 'like', '%'.$filter.'%')
- ->orWhereHas('client', function ($q) use ($filter){
- $q->where('name', 'like', '%'.$filter.'%');
+ ->orWhereHas('client', function ($q) use ($filter) {
+ $q->where('name', 'like', '%'.$filter.'%');
});
});
}
diff --git a/app/Filters/InvoiceFilters.php b/app/Filters/InvoiceFilters.php
index 81f3e6db68dd..c8e2f8216a36 100644
--- a/app/Filters/InvoiceFilters.php
+++ b/app/Filters/InvoiceFilters.php
@@ -69,7 +69,6 @@ class InvoiceFilters extends QueryFilters
if (in_array('overdue', $status_parameters)) {
$query->orWhereIn('status_id', [Invoice::STATUS_SENT, Invoice::STATUS_PARTIAL])
->where('due_date', '<', Carbon::now())
- ->orWhere('due_date', null)
->orWhere('partial_due_date', '<', Carbon::now());
}
});
@@ -109,8 +108,8 @@ class InvoiceFilters extends QueryFilters
->orWhere('custom_value2', 'like', '%'.$filter.'%')
->orWhere('custom_value3', 'like', '%'.$filter.'%')
->orWhere('custom_value4', 'like', '%'.$filter.'%')
- ->orWhereHas('client', function ($q) use ($filter){
- $q->where('name', 'like', '%'.$filter.'%');
+ ->orWhereHas('client', function ($q) use ($filter) {
+ $q->where('name', 'like', '%'.$filter.'%');
});
});
}
diff --git a/app/Filters/PaymentFilters.php b/app/Filters/PaymentFilters.php
index a8e6a1b6d165..5276772e9060 100644
--- a/app/Filters/PaymentFilters.php
+++ b/app/Filters/PaymentFilters.php
@@ -136,7 +136,7 @@ class PaymentFilters extends QueryFilters
* Sorts the list based on $sort.
*
* formatted as column|asc
- *
+ *
* @param string $sort
* @return Builder
*/
diff --git a/app/Filters/PurchaseOrderFilters.php b/app/Filters/PurchaseOrderFilters.php
index 61fdbb9956fc..ea3035db32ee 100644
--- a/app/Filters/PurchaseOrderFilters.php
+++ b/app/Filters/PurchaseOrderFilters.php
@@ -63,8 +63,8 @@ class PurchaseOrderFilters extends QueryFilters
$po_status[] = PurchaseOrder::STATUS_CANCELLED;
}
- if (count($status_parameters) >=1) {
- $query->whereIn('status_id', $status_parameters);
+ if (count($po_status) >=1) {
+ $query->whereIn('status_id', $po_status);
}
});
@@ -94,7 +94,7 @@ class PurchaseOrderFilters extends QueryFilters
->orWhere('custom_value2', 'like', '%'.$filter.'%')
->orWhere('custom_value3', 'like', '%'.$filter.'%')
->orWhere('custom_value4', 'like', '%'.$filter.'%')
- ->orWhereHas('vendor', function ($q) use ($filter){
+ ->orWhereHas('vendor', function ($q) use ($filter) {
$q->where('name', 'like', '%'.$filter.'%');
});
});
diff --git a/app/Filters/QuoteFilters.php b/app/Filters/QuoteFilters.php
index 7b4151b7983a..4c99c5cc87ea 100644
--- a/app/Filters/QuoteFilters.php
+++ b/app/Filters/QuoteFilters.php
@@ -38,9 +38,9 @@ class QuoteFilters extends QueryFilters
->orWhere('custom_value2', 'like', '%'.$filter.'%')
->orWhere('custom_value3', 'like', '%'.$filter.'%')
->orWhere('custom_value4', 'like', '%'.$filter.'%')
- ->orWhereHas('client', function ($q) use ($filter){
- $q->where('name', 'like', '%'.$filter.'%');
- });
+ ->orWhereHas('client', function ($q) use ($filter) {
+ $q->where('name', 'like', '%'.$filter.'%');
+ });
});
}
diff --git a/app/Http/Controllers/AccountController.php b/app/Http/Controllers/AccountController.php
index 268b54e71d9d..6afe275e37b0 100644
--- a/app/Http/Controllers/AccountController.php
+++ b/app/Http/Controllers/AccountController.php
@@ -154,7 +154,7 @@ class AccountController extends BaseController
$truth->setUser(auth()->user());
$truth->setCompany($ct->first()->company);
- return $this->listResponse($ct->fresh());
+ return $this->listResponse($ct);
}
public function update(UpdateAccountRequest $request, Account $account)
diff --git a/app/Http/Controllers/Auth/LoginController.php b/app/Http/Controllers/Auth/LoginController.php
index 413bf66a3118..8ae2803a2742 100644
--- a/app/Http/Controllers/Auth/LoginController.php
+++ b/app/Http/Controllers/Auth/LoginController.php
@@ -377,7 +377,7 @@ class LoginController extends BaseController
if (auth()->user()->company_users()->count() != auth()->user()->tokens()->distinct('company_id')->count()) {
auth()->user()->companies->each(function ($company) {
- if (!CompanyToken::where('user_id', auth()->user()->id)->where('company_id', $company->id)->where('is_system',true)->exists()) {
+ if (!CompanyToken::where('user_id', auth()->user()->id)->where('company_id', $company->id)->where('is_system', true)->exists()) {
(new CreateCompanyToken($company, auth()->user(), 'Google_O_Auth'))->handle();
}
});
diff --git a/app/Http/Controllers/BankTransactionController.php b/app/Http/Controllers/BankTransactionController.php
index 6c7839769eb1..be049d7c174c 100644
--- a/app/Http/Controllers/BankTransactionController.php
+++ b/app/Http/Controllers/BankTransactionController.php
@@ -531,7 +531,6 @@ class BankTransactionController extends BaseController
*/
public function match(MatchBankTransactionRequest $request)
{
-
$bts = (new MatchBankTransactions(auth()->user()->company()->id, auth()->user()->company()->db, $request->all()))->handle();
return $this->listResponse($bts);
diff --git a/app/Http/Controllers/ClientPortal/PaymentController.php b/app/Http/Controllers/ClientPortal/PaymentController.php
index 680d629932e9..8c726b97dec0 100644
--- a/app/Http/Controllers/ClientPortal/PaymentController.php
+++ b/app/Http/Controllers/ClientPortal/PaymentController.php
@@ -12,24 +12,24 @@
namespace App\Http\Controllers\ClientPortal;
+use App\Factory\PaymentFactory;
+use App\Http\Controllers\Controller;
+use App\Http\Requests\ClientPortal\Payments\PaymentResponseRequest;
+use App\Models\CompanyGateway;
+use App\Models\GatewayType;
use App\Models\Invoice;
use App\Models\Payment;
-use Illuminate\View\View;
-use App\Models\GatewayType;
use App\Models\PaymentHash;
use App\Models\PaymentType;
-use Illuminate\Http\Request;
-use App\Models\CompanyGateway;
-use App\Factory\PaymentFactory;
-use App\Utils\Traits\MakesHash;
-use App\Utils\Traits\MakesDates;
-use App\Http\Controllers\Controller;
-use Illuminate\Http\RedirectResponse;
-use Illuminate\Contracts\View\Factory;
use App\PaymentDrivers\Stripe\BankTransfer;
use App\Services\ClientPortal\InstantPayment;
use App\Services\Subscription\SubscriptionService;
-use App\Http\Requests\ClientPortal\Payments\PaymentResponseRequest;
+use App\Utils\Traits\MakesDates;
+use App\Utils\Traits\MakesHash;
+use Illuminate\Contracts\View\Factory;
+use Illuminate\Http\RedirectResponse;
+use Illuminate\Http\Request;
+use Illuminate\View\View;
/**
* Class PaymentController.
@@ -64,15 +64,14 @@ class PaymentController extends Controller
$data = false;
$gateway = false;
- if($payment->gateway_type_id == GatewayType::DIRECT_DEBIT && $payment->type_id == PaymentType::DIRECT_DEBIT){
-
+ if ($payment->gateway_type_id == GatewayType::DIRECT_DEBIT && $payment->type_id == PaymentType::DIRECT_DEBIT) {
if (method_exists($payment->company_gateway->driver($payment->client), 'getPaymentIntent')) {
$stripe = $payment->company_gateway->driver($payment->client);
$payment_intent = $stripe->getPaymentIntent($payment->transaction_reference);
$bt = new BankTransfer($stripe);
- match($payment->currency->code){
+ match ($payment->currency->code) {
'MXN' => $data = $bt->formatDataforMx($payment_intent),
'EUR' => $data = $bt->formatDataforEur($payment_intent),
'JPY' => $data = $bt->formatDataforJp($payment_intent),
diff --git a/app/Http/Controllers/ClientPortal/PaymentMethodController.php b/app/Http/Controllers/ClientPortal/PaymentMethodController.php
index 1a640aa0fcda..a590276c8a0d 100644
--- a/app/Http/Controllers/ClientPortal/PaymentMethodController.php
+++ b/app/Http/Controllers/ClientPortal/PaymentMethodController.php
@@ -15,7 +15,6 @@ namespace App\Http\Controllers\ClientPortal;
use App\Events\Payment\Methods\MethodDeleted;
use App\Http\Controllers\Controller;
use App\Http\Requests\ClientPortal\PaymentMethod\CreatePaymentMethodRequest;
-use App\Http\Requests\ClientPortal\PaymentMethod\VerifyPaymentMethodRequest;
use App\Http\Requests\Request;
use App\Models\ClientGatewayToken;
use App\Models\GatewayType;
diff --git a/app/Http/Controllers/ClientPortal/PrePaymentController.php b/app/Http/Controllers/ClientPortal/PrePaymentController.php
index 874be8a353aa..1fb91c04a5ab 100644
--- a/app/Http/Controllers/ClientPortal/PrePaymentController.php
+++ b/app/Http/Controllers/ClientPortal/PrePaymentController.php
@@ -12,16 +12,16 @@
namespace App\Http\Controllers\ClientPortal;
-use App\Utils\Number;
-use Illuminate\View\View;
use App\DataMapper\InvoiceItem;
use App\Factory\InvoiceFactory;
-use App\Utils\Traits\MakesHash;
-use App\Utils\Traits\MakesDates;
use App\Http\Controllers\Controller;
-use Illuminate\Contracts\View\Factory;
-use App\Repositories\InvoiceRepository;
use App\Http\Requests\ClientPortal\PrePayments\StorePrePaymentRequest;
+use App\Repositories\InvoiceRepository;
+use App\Utils\Number;
+use App\Utils\Traits\MakesDates;
+use App\Utils\Traits\MakesHash;
+use Illuminate\Contracts\View\Factory;
+use Illuminate\View\View;
/**
* Class PrePaymentController.
@@ -38,7 +38,6 @@ class PrePaymentController extends Controller
*/
public function index()
{
-
$data = [
'title' => ctrans('texts.amount'). " " .auth()->guard('contact')->user()->client->currency()->code." (".auth()->guard('contact')->user()->client->currency()->symbol . ")",
'allows_recurring' => auth()->guard('contact')->user()->client->getSetting('client_initiated_payments_recurring'),
@@ -51,7 +50,6 @@ class PrePaymentController extends Controller
public function process(StorePrePaymentRequest $request)
{
-
$invoice = InvoiceFactory::create(auth()->guard('contact')->user()->company_id, auth()->guard('contact')->user()->user_id);
$invoice->due_date = now()->format('Y-m-d');
$invoice->is_proforma = true;
@@ -114,7 +112,5 @@ class PrePaymentController extends Controller
];
return $this->render('invoices.payment', $data);
-
}
-
-}
\ No newline at end of file
+}
diff --git a/app/Http/Controllers/ClientPortal/QuoteController.php b/app/Http/Controllers/ClientPortal/QuoteController.php
index ca99bdfe64d0..36064e8f62d2 100644
--- a/app/Http/Controllers/ClientPortal/QuoteController.php
+++ b/app/Http/Controllers/ClientPortal/QuoteController.php
@@ -178,7 +178,7 @@ class QuoteController extends Controller
if ($process) {
foreach ($quotes as $quote) {
if (request()->has('user_input') && strlen(request()->input('user_input')) > 2) {
- $quote->public_notes .= $quote->public_notes . "\n" . request()->input('user_input');
+ $quote->po_number = substr(request()->input('user_input'), 0, 180);
$quote->saveQuietly();
}
diff --git a/app/Http/Controllers/ClientPortal/SubscriptionPurchaseController.php b/app/Http/Controllers/ClientPortal/SubscriptionPurchaseController.php
index e5007a607d98..62d776869f37 100644
--- a/app/Http/Controllers/ClientPortal/SubscriptionPurchaseController.php
+++ b/app/Http/Controllers/ClientPortal/SubscriptionPurchaseController.php
@@ -44,7 +44,6 @@ class SubscriptionPurchaseController extends Controller
public function upgrade(Subscription $subscription, Request $request)
{
-
App::setLocale($subscription->company->locale());
/* Make sure the contact is logged into the correct company for this subscription */
diff --git a/app/Http/Controllers/CompanyController.php b/app/Http/Controllers/CompanyController.php
index b12e5c06dcc4..f65e970d7199 100644
--- a/app/Http/Controllers/CompanyController.php
+++ b/app/Http/Controllers/CompanyController.php
@@ -11,37 +11,37 @@
namespace App\Http\Controllers;
-use App\Utils\Ninja;
-use App\Models\Account;
-use App\Models\Company;
-use App\Models\CompanyUser;
-use Illuminate\Http\Response;
-use App\Utils\Traits\MakesHash;
-use App\Utils\Traits\Uploadable;
-use App\Jobs\Mail\NinjaMailerJob;
-use App\DataMapper\CompanySettings;
-use App\Jobs\Company\CreateCompany;
-use App\Jobs\Mail\NinjaMailerObject;
-use App\Mail\Company\CompanyDeleted;
-use App\Utils\Traits\SavesDocuments;
-use Turbo124\Beacon\Facades\LightLogs;
-use App\Repositories\CompanyRepository;
-use Illuminate\Support\Facades\Storage;
-use App\Jobs\Company\CreateCompanyToken;
-use App\Transformers\CompanyTransformer;
use App\DataMapper\Analytics\AccountDeleted;
-use App\Transformers\CompanyUserTransformer;
-use Illuminate\Foundation\Bus\DispatchesJobs;
-use App\Jobs\Company\CreateCompanyPaymentTerms;
-use App\Jobs\Company\CreateCompanyTaskStatuses;
+use App\DataMapper\CompanySettings;
+use App\Http\Requests\Company\CreateCompanyRequest;
+use App\Http\Requests\Company\DefaultCompanyRequest;
+use App\Http\Requests\Company\DestroyCompanyRequest;
use App\Http\Requests\Company\EditCompanyRequest;
use App\Http\Requests\Company\ShowCompanyRequest;
use App\Http\Requests\Company\StoreCompanyRequest;
-use App\Http\Requests\Company\CreateCompanyRequest;
use App\Http\Requests\Company\UpdateCompanyRequest;
use App\Http\Requests\Company\UploadCompanyRequest;
-use App\Http\Requests\Company\DefaultCompanyRequest;
-use App\Http\Requests\Company\DestroyCompanyRequest;
+use App\Jobs\Company\CreateCompany;
+use App\Jobs\Company\CreateCompanyPaymentTerms;
+use App\Jobs\Company\CreateCompanyTaskStatuses;
+use App\Jobs\Company\CreateCompanyToken;
+use App\Jobs\Mail\NinjaMailerJob;
+use App\Jobs\Mail\NinjaMailerObject;
+use App\Mail\Company\CompanyDeleted;
+use App\Models\Account;
+use App\Models\Company;
+use App\Models\CompanyUser;
+use App\Repositories\CompanyRepository;
+use App\Transformers\CompanyTransformer;
+use App\Transformers\CompanyUserTransformer;
+use App\Utils\Ninja;
+use App\Utils\Traits\MakesHash;
+use App\Utils\Traits\SavesDocuments;
+use App\Utils\Traits\Uploadable;
+use Illuminate\Foundation\Bus\DispatchesJobs;
+use Illuminate\Http\Response;
+use Illuminate\Support\Facades\Storage;
+use Turbo124\Beacon\Facades\LightLogs;
/**
* Class CompanyController.
@@ -489,8 +489,7 @@ class CompanyController extends BaseController
try {
Storage::disk(config('filesystems.default'))->deleteDirectory($company->company_key);
- }
- catch(\Exception $e) {
+ } catch(\Exception $e) {
}
$account->delete();
@@ -502,9 +501,6 @@ class CompanyController extends BaseController
LightLogs::create(new AccountDeleted())
->increment()
->batch();
-
-
-
} else {
$company_id = $company->id;
diff --git a/app/Http/Controllers/EmailController.php b/app/Http/Controllers/EmailController.php
index af73ff04ccff..3899dbf76620 100644
--- a/app/Http/Controllers/EmailController.php
+++ b/app/Http/Controllers/EmailController.php
@@ -11,26 +11,26 @@
namespace App\Http\Controllers;
-use App\Utils\Ninja;
-use App\Models\Quote;
+use App\Events\Credit\CreditWasEmailed;
+use App\Events\Quote\QuoteWasEmailed;
+use App\Http\Requests\Email\SendEmailRequest;
+use App\Jobs\Entity\EmailEntity;
+use App\Jobs\PurchaseOrder\PurchaseOrderEmail;
use App\Models\Credit;
use App\Models\Invoice;
use App\Models\PurchaseOrder;
-use App\Services\Email\Email;
-use Illuminate\Http\Response;
-use App\Utils\Traits\MakesHash;
-use App\Jobs\Entity\EmailEntity;
+use App\Models\Quote;
use App\Models\RecurringInvoice;
+use App\Services\Email\Email;
use App\Services\Email\EmailObject;
-use App\Events\Quote\QuoteWasEmailed;
-use App\Transformers\QuoteTransformer;
-use App\Events\Credit\CreditWasEmailed;
use App\Transformers\CreditTransformer;
use App\Transformers\InvoiceTransformer;
-use App\Http\Requests\Email\SendEmailRequest;
-use App\Jobs\PurchaseOrder\PurchaseOrderEmail;
use App\Transformers\PurchaseOrderTransformer;
+use App\Transformers\QuoteTransformer;
use App\Transformers\RecurringInvoiceTransformer;
+use App\Utils\Ninja;
+use App\Utils\Traits\MakesHash;
+use Illuminate\Http\Response;
use Illuminate\Mail\Mailables\Address;
class EmailController extends BaseController
@@ -136,8 +136,9 @@ class EmailController extends BaseController
$mo->email_template_body = $request->input('template');
$mo->email_template_subject = str_replace("template", "subject", $request->input('template'));
- if($request->has('cc_email'))
+ if ($request->has('cc_email')) {
$mo->cc[] = new Address($request->cc_email);
+ }
// if ($entity == 'purchaseOrder' || $entity == 'purchase_order' || $template == 'purchase_order' || $entity == 'App\Models\PurchaseOrder') {
// return $this->sendPurchaseOrder($entity_obj, $data, $template);
@@ -152,7 +153,6 @@ class EmailController extends BaseController
$mo->invitation_id = $invitation->id;
Email::dispatch($mo, $invitation->company);
-
}
});
@@ -193,7 +193,7 @@ class EmailController extends BaseController
$this->entity_transformer = RecurringInvoiceTransformer::class;
}
- if($entity_obj instanceof PurchaseOrder){
+ if ($entity_obj instanceof PurchaseOrder) {
$this->entity_type = PurchaseOrder::class;
$this->entity_transformer = PurchaseOrderTransformer::class;
}
@@ -217,8 +217,7 @@ class EmailController extends BaseController
private function resolveClass(string $entity): string
{
-
- match($entity){
+ match ($entity) {
'invoice' => $class = Invoice::class,
'App\Models\Invoice' => $class = Invoice::class,
'credit' => $class = Credit::class,
@@ -232,6 +231,5 @@ class EmailController extends BaseController
};
return $class;
-
}
}
diff --git a/app/Http/Controllers/ImportController.php b/app/Http/Controllers/ImportController.php
index 3c0ed45bdb05..39c0177d47a1 100644
--- a/app/Http/Controllers/ImportController.php
+++ b/app/Http/Controllers/ImportController.php
@@ -163,19 +163,15 @@ class ImportController extends Controller
$bestDelimiter = ' ';
$count = 0;
foreach ($delimiters as $delimiter) {
-
// if (substr_count($csvfile, $delimiter) > $count) {
// $count = substr_count($csvfile, $delimiter);
// $bestDelimiter = $delimiter;
// }
- if (substr_count(strstr($csvfile,"\n",true), $delimiter) > $count) {
+ if (substr_count(strstr($csvfile, "\n", true), $delimiter) > $count) {
$count = substr_count($csvfile, $delimiter);
$bestDelimiter = $delimiter;
}
-
-
-
}
return $bestDelimiter;
}
diff --git a/app/Http/Controllers/LicenseController.php b/app/Http/Controllers/LicenseController.php
index 3d27d5bb51f0..b9221a82c719 100644
--- a/app/Http/Controllers/LicenseController.php
+++ b/app/Http/Controllers/LicenseController.php
@@ -11,13 +11,13 @@
namespace App\Http\Controllers;
-use stdClass;
-use Carbon\Carbon;
use App\Models\Account;
use App\Utils\CurlUtils;
+use Carbon\Carbon;
+use Illuminate\Http\Request;
use Illuminate\Http\Response;
use Illuminate\Support\Facades\Http;
-use Illuminate\Http\Request;
+use stdClass;
class LicenseController extends BaseController
{
@@ -89,6 +89,10 @@ class LicenseController extends BaseController
$license_key = request()->input('license_key');
$product_id = 3;
+ if(substr($license_key, 0, 3) == 'v5_') {
+ return $this->v5ClaimLicense($license_key, $product_id);
+ }
+
$url = config('ninja.license_url')."/claim_license?license_key={$license_key}&product_id={$product_id}&get_date=true";
$data = trim(CurlUtils::get($url));
@@ -149,21 +153,19 @@ class LicenseController extends BaseController
return response()->json($error, 400);
}
- public function v5ClaimLicense(Request $request)
+ public function v5ClaimLicense(string $license_key)
{
$this->checkLicense();
/* Catch claim license requests */
- if (config('ninja.environment') == 'selfhost' && request()->has('license_key')) {
-
+ if (config('ninja.environment') == 'selfhost') {
// $response = Http::get( "http://ninja.test:8000/claim_license", [
- $response = Http::get( "https://invoicing.co/claim_license", [
- 'license_key' => $request->input('license_key'),
+ $response = Http::get("https://invoicing.co/claim_license", [
+ 'license_key' => $license_key,
'product_id' => 3,
]);
- if($response->successful()) {
-
+ if ($response->successful()) {
$payload = $response->json();
$account = auth()->user()->account;
@@ -179,8 +181,7 @@ class LicenseController extends BaseController
];
return response()->json($error, 200);
- }else {
-
+ } else {
$error = [
'message' => trans('texts.white_label_license_error'),
'errors' => new stdClass,
@@ -188,7 +189,6 @@ class LicenseController extends BaseController
return response()->json($error, 400);
}
-
}
$error = [
@@ -197,7 +197,6 @@ class LicenseController extends BaseController
];
return response()->json($error, 400);
-
}
@@ -210,6 +209,5 @@ class LicenseController extends BaseController
$account->plan_expires = null;
$account->save();
}
-
}
}
diff --git a/app/Http/Controllers/PreviewController.php b/app/Http/Controllers/PreviewController.php
index 2e7c6da78441..eead3581a0e3 100644
--- a/app/Http/Controllers/PreviewController.php
+++ b/app/Http/Controllers/PreviewController.php
@@ -23,7 +23,6 @@ use App\Libraries\MultiDB;
use App\Models\Client;
use App\Models\ClientContact;
use App\Models\Credit;
-use App\Models\GroupSetting;
use App\Models\Invoice;
use App\Models\InvoiceInvitation;
use App\Models\Quote;
@@ -37,7 +36,6 @@ use App\Services\PdfMaker\Design;
use App\Services\PdfMaker\Design as PdfDesignModel;
use App\Services\PdfMaker\Design as PdfMakerDesign;
use App\Services\PdfMaker\PdfMaker;
-use App\Services\Preview\StubBuilder;
use App\Utils\HostedPDF\NinjaPdf;
use App\Utils\HtmlEngine;
use App\Utils\Ninja;
diff --git a/app/Http/Controllers/RecurringInvoiceController.php b/app/Http/Controllers/RecurringInvoiceController.php
index 77078d3a818c..5c0bb277edd0 100644
--- a/app/Http/Controllers/RecurringInvoiceController.php
+++ b/app/Http/Controllers/RecurringInvoiceController.php
@@ -11,29 +11,29 @@
namespace App\Http\Controllers;
-use App\Utils\Ninja;
-use App\Models\Account;
-use Illuminate\Http\Response;
-use App\Utils\Traits\MakesHash;
-use App\Models\RecurringInvoice;
-use App\Utils\Traits\SavesDocuments;
-use Illuminate\Support\Facades\Storage;
-use App\Factory\RecurringInvoiceFactory;
-use App\Filters\RecurringInvoiceFilters;
-use App\Jobs\RecurringInvoice\UpdateRecurring;
-use App\Repositories\RecurringInvoiceRepository;
-use App\Transformers\RecurringInvoiceTransformer;
use App\Events\RecurringInvoice\RecurringInvoiceWasCreated;
use App\Events\RecurringInvoice\RecurringInvoiceWasUpdated;
+use App\Factory\RecurringInvoiceFactory;
+use App\Filters\RecurringInvoiceFilters;
+use App\Http\Requests\RecurringInvoice\ActionRecurringInvoiceRequest;
use App\Http\Requests\RecurringInvoice\BulkRecurringInvoiceRequest;
+use App\Http\Requests\RecurringInvoice\CreateRecurringInvoiceRequest;
+use App\Http\Requests\RecurringInvoice\DestroyRecurringInvoiceRequest;
use App\Http\Requests\RecurringInvoice\EditRecurringInvoiceRequest;
use App\Http\Requests\RecurringInvoice\ShowRecurringInvoiceRequest;
use App\Http\Requests\RecurringInvoice\StoreRecurringInvoiceRequest;
-use App\Http\Requests\RecurringInvoice\ActionRecurringInvoiceRequest;
-use App\Http\Requests\RecurringInvoice\CreateRecurringInvoiceRequest;
use App\Http\Requests\RecurringInvoice\UpdateRecurringInvoiceRequest;
use App\Http\Requests\RecurringInvoice\UploadRecurringInvoiceRequest;
-use App\Http\Requests\RecurringInvoice\DestroyRecurringInvoiceRequest;
+use App\Jobs\RecurringInvoice\UpdateRecurring;
+use App\Models\Account;
+use App\Models\RecurringInvoice;
+use App\Repositories\RecurringInvoiceRepository;
+use App\Transformers\RecurringInvoiceTransformer;
+use App\Utils\Ninja;
+use App\Utils\Traits\MakesHash;
+use App\Utils\Traits\SavesDocuments;
+use Illuminate\Http\Response;
+use Illuminate\Support\Facades\Storage;
/**
* Class RecurringInvoiceController.
@@ -406,10 +406,9 @@ class RecurringInvoiceController extends BaseController
*/
public function bulk(BulkRecurringInvoiceRequest $request)
{
-
$percentage_increase = request()->has('percentage_increase') ? request()->input('percentage_increase') : 0;
- if(in_array($request->action, ['increase_prices', 'update_prices'])) {
+ if (in_array($request->action, ['increase_prices', 'update_prices'])) {
UpdateRecurring::dispatch($request->ids, auth()->user()->company(), auth()->user(), $request->action, $percentage_increase);
return response()->json(['message' => 'Update in progress.'], 200);
@@ -417,7 +416,7 @@ class RecurringInvoiceController extends BaseController
$recurring_invoices = RecurringInvoice::withTrashed()->find($request->ids);
- $recurring_invoices->each(function ($recurring_invoice, $key) use($request){
+ $recurring_invoices->each(function ($recurring_invoice, $key) use ($request) {
if (auth()->user()->can('edit', $recurring_invoice)) {
$this->performAction($recurring_invoice, $request->action, true);
}
diff --git a/app/Http/Controllers/TaskSchedulerController.php b/app/Http/Controllers/TaskSchedulerController.php
index 370d45cf1feb..195065f62f21 100644
--- a/app/Http/Controllers/TaskSchedulerController.php
+++ b/app/Http/Controllers/TaskSchedulerController.php
@@ -13,8 +13,8 @@ namespace App\Http\Controllers;
use App\Factory\SchedulerFactory;
use App\Filters\SchedulerFilters;
-use App\Http\Requests\TaskScheduler\DestroySchedulerRequest;
use App\Http\Requests\TaskScheduler\CreateSchedulerRequest;
+use App\Http\Requests\TaskScheduler\DestroySchedulerRequest;
use App\Http\Requests\TaskScheduler\ShowSchedulerRequest;
use App\Http\Requests\TaskScheduler\StoreSchedulerRequest;
use App\Http\Requests\TaskScheduler\UpdateSchedulerRequest;
diff --git a/app/Http/Controllers/WebhookController.php b/app/Http/Controllers/WebhookController.php
index f33c3ea0674b..d7a2a581e43a 100644
--- a/app/Http/Controllers/WebhookController.php
+++ b/app/Http/Controllers/WebhookController.php
@@ -12,22 +12,22 @@
namespace App\Http\Controllers;
-use App\Models\Webhook;
-use Illuminate\Support\Str;
-use Illuminate\Http\Response;
use App\Factory\WebhookFactory;
use App\Filters\WebhookFilters;
-use App\Utils\Traits\MakesHash;
+use App\Http\Requests\Webhook\CreateWebhookRequest;
+use App\Http\Requests\Webhook\DestroyWebhookRequest;
+use App\Http\Requests\Webhook\EditWebhookRequest;
+use App\Http\Requests\Webhook\RetryWebhookRequest;
+use App\Http\Requests\Webhook\ShowWebhookRequest;
+use App\Http\Requests\Webhook\StoreWebhookRequest;
+use App\Http\Requests\Webhook\UpdateWebhookRequest;
use App\Jobs\Util\WebhookSingle;
+use App\Models\Webhook;
use App\Repositories\BaseRepository;
use App\Transformers\WebhookTransformer;
-use App\Http\Requests\Webhook\EditWebhookRequest;
-use App\Http\Requests\Webhook\ShowWebhookRequest;
-use App\Http\Requests\Webhook\RetryWebhookRequest;
-use App\Http\Requests\Webhook\StoreWebhookRequest;
-use App\Http\Requests\Webhook\CreateWebhookRequest;
-use App\Http\Requests\Webhook\UpdateWebhookRequest;
-use App\Http\Requests\Webhook\DestroyWebhookRequest;
+use App\Utils\Traits\MakesHash;
+use Illuminate\Http\Response;
+use Illuminate\Support\Str;
class WebhookController extends BaseController
{
@@ -493,7 +493,7 @@ class WebhookController extends BaseController
public function retry(RetryWebhookRequest $request, Webhook $webhook)
{
- match($request->entity) {
+ match ($request->entity) {
'invoice' => $includes ='client',
'payment' => $includes ='invoices,client',
'project' => $includes ='client',
@@ -506,7 +506,7 @@ class WebhookController extends BaseController
$entity = $class::withTrashed()->where('id', $this->decodePrimaryKey($request->entity_id))->company()->first();
- if(!$entity){
+ if (!$entity) {
return response()->json(['message' => ctrans('texts.record_not_found')], 400);
}
diff --git a/app/Http/Kernel.php b/app/Http/Kernel.php
index 130ef2b2bb6f..c7fcc7b5ce6e 100644
--- a/app/Http/Kernel.php
+++ b/app/Http/Kernel.php
@@ -11,54 +11,55 @@
namespace App\Http;
-use App\Http\Middleware\ApiSecretCheck;
+use App\Utils\Ninja;
+use App\Http\Middleware\Cors;
+use App\Http\Middleware\SetDb;
+use App\Http\Middleware\Locale;
+use App\Http\Middleware\SetWebDb;
+use App\Http\Middleware\UrlSetDb;
+use App\Http\Middleware\TokenAuth;
+use App\Http\Middleware\SetEmailDb;
+use App\Http\Middleware\VerifyHash;
+use App\Http\Middleware\SetInviteDb;
+use App\Http\Middleware\TrimStrings;
use App\Http\Middleware\Authenticate;
-use App\Http\Middleware\CheckClientExistence;
-use App\Http\Middleware\CheckForMaintenanceMode;
-use App\Http\Middleware\ClientPortalEnabled;
+use App\Http\Middleware\ContactSetDb;
+use App\Http\Middleware\QueryLogging;
+use App\Http\Middleware\TrustProxies;
+use App\Http\Middleware\UserVerified;
+use App\Http\Middleware\VendorLocale;
+use App\Http\Middleware\PhantomSecret;
+use App\Http\Middleware\SetDocumentDb;
+use App\Http\Middleware\ApiSecretCheck;
use App\Http\Middleware\ContactAccount;
+use App\Http\Middleware\EncryptCookies;
+use App\Http\Middleware\SessionDomains;
use App\Http\Middleware\ContactKeyLogin;
use App\Http\Middleware\ContactRegister;
-use App\Http\Middleware\ContactSetDb;
-use App\Http\Middleware\ContactTokenAuth;
-use App\Http\Middleware\Cors;
-use App\Http\Middleware\EncryptCookies;
-use App\Http\Middleware\Locale;
-use App\Http\Middleware\PasswordProtection;
-use App\Http\Middleware\PhantomSecret;
-use App\Http\Middleware\QueryLogging;
-use App\Http\Middleware\RedirectIfAuthenticated;
-use App\Http\Middleware\SessionDomains;
-use App\Http\Middleware\SetDb;
-use App\Http\Middleware\SetDbByCompanyKey;
-use App\Http\Middleware\SetDocumentDb;
use App\Http\Middleware\SetDomainNameDb;
-use App\Http\Middleware\SetEmailDb;
-use App\Http\Middleware\SetInviteDb;
-use App\Http\Middleware\SetWebDb;
-use App\Http\Middleware\Shop\ShopTokenAuth;
-use App\Http\Middleware\TokenAuth;
-use App\Http\Middleware\TrimStrings;
-use App\Http\Middleware\TrustProxies;
-use App\Http\Middleware\UrlSetDb;
-use App\Http\Middleware\UserVerified;
-use App\Http\Middleware\VendorContactKeyLogin;
-use App\Http\Middleware\VendorLocale;
use App\Http\Middleware\VerifyCsrfToken;
-use App\Http\Middleware\VerifyHash;
-use Illuminate\Auth\Middleware\AuthenticateWithBasicAuth;
+use App\Http\Middleware\ContactTokenAuth;
use Illuminate\Auth\Middleware\Authorize;
-use Illuminate\Auth\Middleware\EnsureEmailIsVerified;
-use Illuminate\Cookie\Middleware\AddQueuedCookiesToResponse;
-use Illuminate\Foundation\Http\Kernel as HttpKernel;
-use Illuminate\Foundation\Http\Middleware\ConvertEmptyStringsToNull;
-use Illuminate\Foundation\Http\Middleware\ValidatePostSize;
+use App\Http\Middleware\SetDbByCompanyKey;
+use App\Http\Middleware\PasswordProtection;
+use App\Http\Middleware\ClientPortalEnabled;
+use App\Http\Middleware\CheckClientExistence;
+use App\Http\Middleware\VendorContactKeyLogin;
use Illuminate\Http\Middleware\SetCacheHeaders;
-use Illuminate\Routing\Middleware\SubstituteBindings;
-use Illuminate\Routing\Middleware\ThrottleRequests;
-use Illuminate\Routing\Middleware\ValidateSignature;
use Illuminate\Session\Middleware\StartSession;
+use App\Http\Middleware\CheckForMaintenanceMode;
+use App\Http\Middleware\RedirectIfAuthenticated;
+use Illuminate\Routing\Middleware\ThrottleRequests;
+use Illuminate\Foundation\Http\Kernel as HttpKernel;
+use Illuminate\Routing\Middleware\ValidateSignature;
+use Illuminate\Auth\Middleware\EnsureEmailIsVerified;
+use Illuminate\Routing\Middleware\SubstituteBindings;
use Illuminate\View\Middleware\ShareErrorsFromSession;
+use Illuminate\Auth\Middleware\AuthenticateWithBasicAuth;
+use Illuminate\Foundation\Http\Middleware\ValidatePostSize;
+use Illuminate\Cookie\Middleware\AddQueuedCookiesToResponse;
+use Illuminate\Routing\Middleware\ThrottleRequestsWithRedis;
+use Illuminate\Foundation\Http\Middleware\ConvertEmptyStringsToNull;
class Kernel extends HttpKernel
{
@@ -75,9 +76,7 @@ class Kernel extends HttpKernel
TrimStrings::class,
ConvertEmptyStringsToNull::class,
TrustProxies::class,
- // \Illuminate\Http\Middleware\HandleCors::class,
Cors::class,
-
];
/**
@@ -140,7 +139,6 @@ class Kernel extends HttpKernel
'cors' => Cors::class,
'guest' => RedirectIfAuthenticated::class,
'signed' => ValidateSignature::class,
- 'throttle' => ThrottleRequests::class,
'verified' => EnsureEmailIsVerified::class,
'query_logging' => QueryLogging::class,
'token_auth' => TokenAuth::class,
@@ -152,7 +150,6 @@ class Kernel extends HttpKernel
'email_db' => SetEmailDb::class,
'invite_db' => SetInviteDb::class,
'password_protected' => PasswordProtection::class,
- 'signed' => ValidateSignature::class,
'portal_enabled' => ClientPortalEnabled::class,
'url_db' => UrlSetDb::class,
'web_db' => SetWebDb::class,
@@ -162,7 +159,6 @@ class Kernel extends HttpKernel
'vendor_locale' => VendorLocale::class,
'contact_register' => ContactRegister::class,
'verify_hash' => VerifyHash::class,
- 'shop_token_auth' => ShopTokenAuth::class,
'phantom_secret' => PhantomSecret::class,
'contact_key_login' => ContactKeyLogin::class,
'vendor_contact_key_login' => VendorContactKeyLogin::class,
@@ -170,6 +166,7 @@ class Kernel extends HttpKernel
'user_verified' => UserVerified::class,
'document_db' => SetDocumentDb::class,
'session_domain' => SessionDomains::class,
+ //we dyanamically add the throttle middleware in RouteServiceProvider
];
protected $middlewarePriority = [
@@ -189,7 +186,6 @@ class Kernel extends HttpKernel
ContactTokenAuth::class,
ContactKeyLogin::class,
Authenticate::class,
- ShopTokenAuth::class,
ContactRegister::class,
PhantomSecret::class,
CheckClientExistence::class,
@@ -199,4 +195,5 @@ class Kernel extends HttpKernel
SubstituteBindings::class,
ContactAccount::class,
];
+
}
diff --git a/app/Http/Livewire/BillingPortalPurchase.php b/app/Http/Livewire/BillingPortalPurchase.php
index b0df3019ca18..89931982db93 100644
--- a/app/Http/Livewire/BillingPortalPurchase.php
+++ b/app/Http/Livewire/BillingPortalPurchase.php
@@ -11,24 +11,24 @@
namespace App\Http\Livewire;
-use App\Utils\Ninja;
-use App\Models\Client;
-use App\Models\Invoice;
-use Livewire\Component;
-use App\Libraries\MultiDB;
-use Illuminate\Support\Str;
-use App\Models\Subscription;
-use App\Models\ClientContact;
+use App\DataMapper\ClientSettings;
use App\Factory\ClientFactory;
use App\Jobs\Mail\NinjaMailerJob;
-use App\DataMapper\ClientSettings;
use App\Jobs\Mail\NinjaMailerObject;
+use App\Libraries\MultiDB;
+use App\Mail\ContactPasswordlessLogin;
+use App\Models\Client;
+use App\Models\ClientContact;
+use App\Models\Invoice;
+use App\Models\Subscription;
+use App\Repositories\ClientContactRepository;
+use App\Repositories\ClientRepository;
+use App\Services\Subscription\SubscriptionService;
+use App\Utils\Ninja;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Cache;
-use App\Mail\ContactPasswordlessLogin;
-use App\Repositories\ClientRepository;
-use App\Repositories\ClientContactRepository;
-use App\Services\Subscription\SubscriptionService;
+use Illuminate\Support\Str;
+use Livewire\Component;
class BillingPortalPurchase extends Component
{
@@ -401,7 +401,7 @@ class BillingPortalPurchase extends Component
$context = 'purchase';
// if(Ninja::isHosted() && $this->subscription->service()->recurring_products()->first()?->id == SubscriptionService::WHITE_LABEL) {
- if(Ninja::isHosted() && $this->subscription->service()->recurring_products()->first()?->product_key == 'whitelabel') {
+ if (Ninja::isHosted() && $this->subscription->service()->recurring_products()->first()?->product_key == 'whitelabel') {
$context = 'whitelabel';
}
diff --git a/app/Http/Livewire/BillingPortalPurchasev2.php b/app/Http/Livewire/BillingPortalPurchasev2.php
index 612dfd5b8209..aaf9bf65cbfe 100644
--- a/app/Http/Livewire/BillingPortalPurchasev2.php
+++ b/app/Http/Livewire/BillingPortalPurchasev2.php
@@ -172,8 +172,7 @@ class BillingPortalPurchasev2 extends Component
$this->contact = auth()->guard('contact')->user();
$this->authenticated = true;
$this->payment_started = true;
- }
- else {
+ } else {
$this->bundle = collect();
}
@@ -276,7 +275,6 @@ class BillingPortalPurchasev2 extends Component
*/
public function handleCoupon()
{
-
$this->resetErrorBag('coupon');
$this->resetValidation('coupon');
@@ -311,7 +309,7 @@ class BillingPortalPurchasev2 extends Component
'description' => $p->notes,
'product_key' => $p->product_key,
'unit_cost' => $p->price,
- 'product' => nl2br(substr($p->notes, 0, 50)),
+ 'product' => substr(strip_tags($p->markdownNotes()), 0, 50),
'price' => Number::formatMoney($total, $this->subscription->company).' / '. RecurringInvoice::frequencyForKey($this->subscription->frequency_id),
'total' => $total,
'qty' => $qty,
@@ -329,7 +327,7 @@ class BillingPortalPurchasev2 extends Component
'description' => $p->notes,
'product_key' => $p->product_key,
'unit_cost' => $p->price,
- 'product' => nl2br(substr($p->notes, 0, 50)),
+ 'product' => substr(strip_tags($p->markdownNotes()), 0, 50),
'price' => Number::formatMoney($total, $this->subscription->company),
'total' => $total,
'qty' => $qty,
@@ -352,7 +350,7 @@ class BillingPortalPurchasev2 extends Component
'description' => $p->notes,
'product_key' => $p->product_key,
'unit_cost' => $p->price,
- 'product' => nl2br(substr($p->notes, 0, 50)),
+ 'product' => substr(strip_tags($p->markdownNotes()), 0, 50),
'price' => Number::formatMoney($total, $this->subscription->company).' / '. RecurringInvoice::frequencyForKey($this->subscription->frequency_id),
'total' => $total,
'qty' => $qty,
@@ -375,7 +373,7 @@ class BillingPortalPurchasev2 extends Component
'description' => $p->notes,
'product_key' => $p->product_key,
'unit_cost' => $p->price,
- 'product' => nl2br(substr($p->notes, 0, 50)),
+ 'product' => substr(strip_tags($p->markdownNotes()), 0, 50),
'price' => Number::formatMoney($total, $this->subscription->company),
'total' => $total,
'qty' => $qty,
diff --git a/app/Http/Livewire/RequiredClientInfo.php b/app/Http/Livewire/RequiredClientInfo.php
index 70af5590a8dc..df184eff52bf 100644
--- a/app/Http/Livewire/RequiredClientInfo.php
+++ b/app/Http/Livewire/RequiredClientInfo.php
@@ -232,8 +232,9 @@ class RequiredClientInfo extends Component
if ($cg && $cg->update_details) {
$payment_gateway = $cg->driver($this->client)->init();
- if(method_exists($payment_gateway, "updateCustomer"))
+ if (method_exists($payment_gateway, "updateCustomer")) {
$payment_gateway->updateCustomer();
+ }
}
return true;
diff --git a/app/Http/Middleware/ThrottleRequestsWithPredis.php b/app/Http/Middleware/ThrottleRequestsWithPredis.php
new file mode 100644
index 000000000000..ec16ad695a66
--- /dev/null
+++ b/app/Http/Middleware/ThrottleRequestsWithPredis.php
@@ -0,0 +1,124 @@
+redis = \Illuminate\Support\Facades\Redis::connection('sentinel-cache');
+ }
+
+ /**
+ * Handle an incoming request.
+ *
+ * @param \Illuminate\Http\Request $request
+ * @param \Closure $next
+ * @param array $limits
+ * @return \Symfony\Component\HttpFoundation\Response
+ *
+ * @throws \Illuminate\Http\Exceptions\ThrottleRequestsException
+ */
+ protected function handleRequest($request, Closure $next, array $limits)
+ {
+ foreach ($limits as $limit) {
+ if ($this->tooManyAttempts($limit->key, $limit->maxAttempts, $limit->decayMinutes)) {
+ throw $this->buildException($request, $limit->key, $limit->maxAttempts, $limit->responseCallback);
+ }
+ }
+
+ $response = $next($request);
+
+ foreach ($limits as $limit) {
+ $response = $this->addHeaders(
+ $response,
+ $limit->maxAttempts,
+ $this->calculateRemainingAttempts($limit->key, $limit->maxAttempts)
+ );
+ }
+
+ return $response;
+ }
+
+ /**
+ * Determine if the given key has been "accessed" too many times.
+ *
+ * @param string $key
+ * @param int $maxAttempts
+ * @param int $decayMinutes
+ * @return mixed
+ */
+ protected function tooManyAttempts($key, $maxAttempts, $decayMinutes)
+ {
+ $limiter = new DurationLimiter(
+ $this->redis,
+ $key,
+ $maxAttempts,
+ $decayMinutes * 60
+ );
+
+ return tap(! $limiter->acquire(), function () use ($key, $limiter) {
+ [$this->decaysAt[$key], $this->remaining[$key]] = [
+ $limiter->decaysAt, $limiter->remaining,
+ ];
+ });
+ }
+
+ /**
+ * Calculate the number of remaining attempts.
+ *
+ * @param string $key
+ * @param int $maxAttempts
+ * @param int|null $retryAfter
+ * @return int
+ */
+ protected function calculateRemainingAttempts($key, $maxAttempts, $retryAfter = null)
+ {
+ return is_null($retryAfter) ? $this->remaining[$key] : 0;
+ }
+
+ /**
+ * Get the number of seconds until the lock is released.
+ *
+ * @param string $key
+ * @return int
+ */
+ protected function getTimeUntilNextRetry($key)
+ {
+ return $this->decaysAt[$key] - $this->currentTime();
+ }
+}
diff --git a/app/Http/Requests/BankIntegration/UploadBankIntegrationRequest.php b/app/Http/Requests/BankIntegration/UploadBankIntegrationRequest.php
index b92c22c55ad5..cd07c0688343 100644
--- a/app/Http/Requests/BankIntegration/UploadBankIntegrationRequest.php
+++ b/app/Http/Requests/BankIntegration/UploadBankIntegrationRequest.php
@@ -29,10 +29,11 @@ class UploadBankIntegrationRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/BankTransaction/UploadBankTransactionRequest.php b/app/Http/Requests/BankTransaction/UploadBankTransactionRequest.php
index e3b62225019e..0bbc319ef3e0 100644
--- a/app/Http/Requests/BankTransaction/UploadBankTransactionRequest.php
+++ b/app/Http/Requests/BankTransaction/UploadBankTransactionRequest.php
@@ -29,10 +29,11 @@ class UploadBankTransactionRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Client/StoreClientRequest.php b/app/Http/Requests/Client/StoreClientRequest.php
index ffe65adb9612..095b89561c2d 100644
--- a/app/Http/Requests/Client/StoreClientRequest.php
+++ b/app/Http/Requests/Client/StoreClientRequest.php
@@ -38,10 +38,11 @@ class StoreClientRequest extends Request
public function rules()
{
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Client/UpdateClientRequest.php b/app/Http/Requests/Client/UpdateClientRequest.php
index 6a51aec64bf0..8b4059c9aac4 100644
--- a/app/Http/Requests/Client/UpdateClientRequest.php
+++ b/app/Http/Requests/Client/UpdateClientRequest.php
@@ -38,10 +38,11 @@ class UpdateClientRequest extends Request
{
/* Ensure we have a client name, and that all emails are unique*/
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Client/UploadClientRequest.php b/app/Http/Requests/Client/UploadClientRequest.php
index 1093b3f1ebcd..e5baef5ef0be 100644
--- a/app/Http/Requests/Client/UploadClientRequest.php
+++ b/app/Http/Requests/Client/UploadClientRequest.php
@@ -29,10 +29,11 @@ class UploadClientRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/ClientPortal/PrePayments/StorePrePaymentRequest.php b/app/Http/Requests/ClientPortal/PrePayments/StorePrePaymentRequest.php
index a591632db413..f596ef2e6295 100644
--- a/app/Http/Requests/ClientPortal/PrePayments/StorePrePaymentRequest.php
+++ b/app/Http/Requests/ClientPortal/PrePayments/StorePrePaymentRequest.php
@@ -15,7 +15,6 @@ class StorePrePaymentRequest extends FormRequest
public function authorize()
{
return auth()->guard('contact')->user()->company->enabled_modules & PortalComposer::MODULE_INVOICES;
-
}
/**
@@ -30,5 +29,4 @@ class StorePrePaymentRequest extends FormRequest
'amount' => 'required|bail|',
];
}
-
}
diff --git a/app/Http/Requests/Company/UploadCompanyRequest.php b/app/Http/Requests/Company/UploadCompanyRequest.php
index 999101417dd0..4e5cdd6308d2 100644
--- a/app/Http/Requests/Company/UploadCompanyRequest.php
+++ b/app/Http/Requests/Company/UploadCompanyRequest.php
@@ -29,10 +29,11 @@ class UploadCompanyRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Credit/StoreCreditRequest.php b/app/Http/Requests/Credit/StoreCreditRequest.php
index 589cfe24527c..13eee9c59852 100644
--- a/app/Http/Requests/Credit/StoreCreditRequest.php
+++ b/app/Http/Requests/Credit/StoreCreditRequest.php
@@ -43,10 +43,11 @@ class StoreCreditRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Credit/UpdateCreditRequest.php b/app/Http/Requests/Credit/UpdateCreditRequest.php
index d208cf223f51..929ad49e443a 100644
--- a/app/Http/Requests/Credit/UpdateCreditRequest.php
+++ b/app/Http/Requests/Credit/UpdateCreditRequest.php
@@ -42,10 +42,11 @@ class UpdateCreditRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Credit/UploadCreditRequest.php b/app/Http/Requests/Credit/UploadCreditRequest.php
index 06721355bbbd..e25782acaf12 100644
--- a/app/Http/Requests/Credit/UploadCreditRequest.php
+++ b/app/Http/Requests/Credit/UploadCreditRequest.php
@@ -29,10 +29,11 @@ class UploadCreditRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Expense/UploadExpenseRequest.php b/app/Http/Requests/Expense/UploadExpenseRequest.php
index b04cde728549..694f2317f2dd 100644
--- a/app/Http/Requests/Expense/UploadExpenseRequest.php
+++ b/app/Http/Requests/Expense/UploadExpenseRequest.php
@@ -29,10 +29,11 @@ class UploadExpenseRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/GroupSetting/UploadGroupSettingRequest.php b/app/Http/Requests/GroupSetting/UploadGroupSettingRequest.php
index c3c1415a6c90..4b7379068059 100644
--- a/app/Http/Requests/GroupSetting/UploadGroupSettingRequest.php
+++ b/app/Http/Requests/GroupSetting/UploadGroupSettingRequest.php
@@ -29,10 +29,11 @@ class UploadGroupSettingRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Invoice/StoreInvoiceRequest.php b/app/Http/Requests/Invoice/StoreInvoiceRequest.php
index 5f21287c3839..cedbb7fd4f7f 100644
--- a/app/Http/Requests/Invoice/StoreInvoiceRequest.php
+++ b/app/Http/Requests/Invoice/StoreInvoiceRequest.php
@@ -37,10 +37,11 @@ class StoreInvoiceRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Invoice/UpdateInvoiceRequest.php b/app/Http/Requests/Invoice/UpdateInvoiceRequest.php
index 0a4f5d31e149..0668a8e60ff2 100644
--- a/app/Http/Requests/Invoice/UpdateInvoiceRequest.php
+++ b/app/Http/Requests/Invoice/UpdateInvoiceRequest.php
@@ -39,10 +39,11 @@ class UpdateInvoiceRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Invoice/UploadInvoiceRequest.php b/app/Http/Requests/Invoice/UploadInvoiceRequest.php
index 70157d05aac1..93396d9ee7aa 100644
--- a/app/Http/Requests/Invoice/UploadInvoiceRequest.php
+++ b/app/Http/Requests/Invoice/UploadInvoiceRequest.php
@@ -29,10 +29,11 @@ class UploadInvoiceRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
@@ -45,6 +46,5 @@ class UploadInvoiceRequest extends Request
public function prepareForValidation()
{
-
}
}
diff --git a/app/Http/Requests/Payment/StorePaymentRequest.php b/app/Http/Requests/Payment/StorePaymentRequest.php
index d796a082454d..196c302e57a7 100644
--- a/app/Http/Requests/Payment/StorePaymentRequest.php
+++ b/app/Http/Requests/Payment/StorePaymentRequest.php
@@ -112,10 +112,11 @@ class StorePaymentRequest extends Request
];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Payment/UpdatePaymentRequest.php b/app/Http/Requests/Payment/UpdatePaymentRequest.php
index 1d87ef164542..1cd8d8b4c850 100644
--- a/app/Http/Requests/Payment/UpdatePaymentRequest.php
+++ b/app/Http/Requests/Payment/UpdatePaymentRequest.php
@@ -44,10 +44,11 @@ class UpdatePaymentRequest extends Request
$rules['number'] = Rule::unique('payments')->where('company_id', auth()->user()->company()->id)->ignore($this->payment->id);
}
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Payment/UploadPaymentRequest.php b/app/Http/Requests/Payment/UploadPaymentRequest.php
index ad3874895f2e..52bb9b2b318b 100644
--- a/app/Http/Requests/Payment/UploadPaymentRequest.php
+++ b/app/Http/Requests/Payment/UploadPaymentRequest.php
@@ -29,10 +29,11 @@ class UploadPaymentRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Preview/PreviewInvoiceRequest.php b/app/Http/Requests/Preview/PreviewInvoiceRequest.php
index ab0586f5a5f8..b2da03628210 100644
--- a/app/Http/Requests/Preview/PreviewInvoiceRequest.php
+++ b/app/Http/Requests/Preview/PreviewInvoiceRequest.php
@@ -12,10 +12,6 @@
namespace App\Http\Requests\Preview;
use App\Http\Requests\Request;
-use App\Models\Credit;
-use App\Models\Invoice;
-use App\Models\Quote;
-use App\Models\RecurringInvoice;
use App\Utils\Traits\CleanLineItems;
use App\Utils\Traits\MakesHash;
diff --git a/app/Http/Requests/Preview/PreviewPurchaseOrderRequest.php b/app/Http/Requests/Preview/PreviewPurchaseOrderRequest.php
index 6b3ce83cd85e..d91de03c19ec 100644
--- a/app/Http/Requests/Preview/PreviewPurchaseOrderRequest.php
+++ b/app/Http/Requests/Preview/PreviewPurchaseOrderRequest.php
@@ -12,7 +12,6 @@
namespace App\Http\Requests\Preview;
use App\Http\Requests\Request;
-use App\Models\PurchaseOrder;
use App\Utils\Traits\CleanLineItems;
use App\Utils\Traits\MakesHash;
diff --git a/app/Http/Requests/Product/StoreProductRequest.php b/app/Http/Requests/Product/StoreProductRequest.php
index a512dc6e1750..4dacdbdfca16 100644
--- a/app/Http/Requests/Product/StoreProductRequest.php
+++ b/app/Http/Requests/Product/StoreProductRequest.php
@@ -28,10 +28,11 @@ class StoreProductRequest extends Request
public function rules()
{
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Product/UpdateProductRequest.php b/app/Http/Requests/Product/UpdateProductRequest.php
index b66dfd00601f..36197b90cf4a 100644
--- a/app/Http/Requests/Product/UpdateProductRequest.php
+++ b/app/Http/Requests/Product/UpdateProductRequest.php
@@ -12,7 +12,6 @@
namespace App\Http\Requests\Product;
use App\Http\Requests\Request;
-use App\Models\Product;
use App\Utils\Traits\ChecksEntityStatus;
class UpdateProductRequest extends Request
@@ -31,10 +30,11 @@ class UpdateProductRequest extends Request
public function rules()
{
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Product/UploadProductRequest.php b/app/Http/Requests/Product/UploadProductRequest.php
index d08a20c0f571..b7117c035790 100644
--- a/app/Http/Requests/Product/UploadProductRequest.php
+++ b/app/Http/Requests/Product/UploadProductRequest.php
@@ -28,10 +28,11 @@ class UploadProductRequest extends Request
public function rules()
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Project/CreateProjectRequest.php b/app/Http/Requests/Project/CreateProjectRequest.php
index e9f9f193f750..44abf721d522 100644
--- a/app/Http/Requests/Project/CreateProjectRequest.php
+++ b/app/Http/Requests/Project/CreateProjectRequest.php
@@ -11,8 +11,8 @@
namespace App\Http\Requests\Project;
-use App\Models\Project;
use App\Http\Requests\Request;
+use App\Models\Project;
class CreateProjectRequest extends Request
{
@@ -24,6 +24,5 @@ class CreateProjectRequest extends Request
public function authorize() : bool
{
return auth()->user()->can('create', Project::class);
-
}
}
diff --git a/app/Http/Requests/Project/ShowProjectRequest.php b/app/Http/Requests/Project/ShowProjectRequest.php
index 6e6b4ba98a84..47abf0c57f74 100644
--- a/app/Http/Requests/Project/ShowProjectRequest.php
+++ b/app/Http/Requests/Project/ShowProjectRequest.php
@@ -24,7 +24,6 @@ class ShowProjectRequest extends Request
{
// return auth()->user()->isAdmin();
return auth()->user()->can('view', $this->project);
-
}
/**
diff --git a/app/Http/Requests/Project/StoreProjectRequest.php b/app/Http/Requests/Project/StoreProjectRequest.php
index 3e2b7ee6a132..98664cd84c0e 100644
--- a/app/Http/Requests/Project/StoreProjectRequest.php
+++ b/app/Http/Requests/Project/StoreProjectRequest.php
@@ -42,10 +42,11 @@ class StoreProjectRequest extends Request
$rules['number'] = Rule::unique('projects')->where('company_id', auth()->user()->company()->id);
}
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Project/UpdateProjectRequest.php b/app/Http/Requests/Project/UpdateProjectRequest.php
index 9d938ce8d046..484f18f036f3 100644
--- a/app/Http/Requests/Project/UpdateProjectRequest.php
+++ b/app/Http/Requests/Project/UpdateProjectRequest.php
@@ -37,10 +37,11 @@ class UpdateProjectRequest extends Request
$rules['number'] = Rule::unique('projects')->where('company_id', auth()->user()->company()->id)->ignore($this->project->id);
}
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Project/UploadProjectRequest.php b/app/Http/Requests/Project/UploadProjectRequest.php
index bf37beab7d29..c7504f5b41f7 100644
--- a/app/Http/Requests/Project/UploadProjectRequest.php
+++ b/app/Http/Requests/Project/UploadProjectRequest.php
@@ -29,10 +29,11 @@ class UploadProjectRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/PurchaseOrder/StorePurchaseOrderRequest.php b/app/Http/Requests/PurchaseOrder/StorePurchaseOrderRequest.php
index 3071a870a6ec..74697c804ad0 100644
--- a/app/Http/Requests/PurchaseOrder/StorePurchaseOrderRequest.php
+++ b/app/Http/Requests/PurchaseOrder/StorePurchaseOrderRequest.php
@@ -47,10 +47,11 @@ class StorePurchaseOrderRequest extends Request
$rules['is_amount_discount'] = ['boolean'];
$rules['line_items'] = 'array';
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/PurchaseOrder/UpdatePurchaseOrderRequest.php b/app/Http/Requests/PurchaseOrder/UpdatePurchaseOrderRequest.php
index 3ee030773a09..e504fea5c08b 100644
--- a/app/Http/Requests/PurchaseOrder/UpdatePurchaseOrderRequest.php
+++ b/app/Http/Requests/PurchaseOrder/UpdatePurchaseOrderRequest.php
@@ -50,10 +50,11 @@ class UpdatePurchaseOrderRequest extends Request
$rules['discount'] = 'sometimes|numeric';
$rules['is_amount_discount'] = ['boolean'];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/PurchaseOrder/UploadPurchaseOrderRequest.php b/app/Http/Requests/PurchaseOrder/UploadPurchaseOrderRequest.php
index 3fdce5fac4e0..25aadfdb1a19 100644
--- a/app/Http/Requests/PurchaseOrder/UploadPurchaseOrderRequest.php
+++ b/app/Http/Requests/PurchaseOrder/UploadPurchaseOrderRequest.php
@@ -29,10 +29,11 @@ class UploadPurchaseOrderRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Quote/StoreQuoteRequest.php b/app/Http/Requests/Quote/StoreQuoteRequest.php
index 18c132367891..387f165de110 100644
--- a/app/Http/Requests/Quote/StoreQuoteRequest.php
+++ b/app/Http/Requests/Quote/StoreQuoteRequest.php
@@ -39,10 +39,11 @@ class StoreQuoteRequest extends Request
$rules['client_id'] = 'required|exists:clients,id,company_id,'.auth()->user()->company()->id;
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Quote/UpdateQuoteRequest.php b/app/Http/Requests/Quote/UpdateQuoteRequest.php
index 5d75ef768a7a..07b463936892 100644
--- a/app/Http/Requests/Quote/UpdateQuoteRequest.php
+++ b/app/Http/Requests/Quote/UpdateQuoteRequest.php
@@ -37,10 +37,11 @@ class UpdateQuoteRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Quote/UploadQuoteRequest.php b/app/Http/Requests/Quote/UploadQuoteRequest.php
index 1dce9e19de03..cfc3580ad412 100644
--- a/app/Http/Requests/Quote/UploadQuoteRequest.php
+++ b/app/Http/Requests/Quote/UploadQuoteRequest.php
@@ -29,10 +29,11 @@ class UploadQuoteRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/RecurringExpense/StoreRecurringExpenseRequest.php b/app/Http/Requests/RecurringExpense/StoreRecurringExpenseRequest.php
index d2752a446e57..7b9e582a58d1 100644
--- a/app/Http/Requests/RecurringExpense/StoreRecurringExpenseRequest.php
+++ b/app/Http/Requests/RecurringExpense/StoreRecurringExpenseRequest.php
@@ -48,10 +48,11 @@ class StoreRecurringExpenseRequest extends Request
$rules['tax_amount2'] = 'numeric';
$rules['tax_amount3'] = 'numeric';
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/RecurringExpense/UpdateRecurringExpenseRequest.php b/app/Http/Requests/RecurringExpense/UpdateRecurringExpenseRequest.php
index 271a46bfd25b..76c61120971e 100644
--- a/app/Http/Requests/RecurringExpense/UpdateRecurringExpenseRequest.php
+++ b/app/Http/Requests/RecurringExpense/UpdateRecurringExpenseRequest.php
@@ -48,10 +48,11 @@ class UpdateRecurringExpenseRequest extends Request
$rules['tax_amount3'] = 'numeric';
$rules['category_id'] = 'bail|nullable|sometimes|exists:expense_categories,id,company_id,'.auth()->user()->company()->id.',is_deleted,0';
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/RecurringExpense/UploadRecurringExpenseRequest.php b/app/Http/Requests/RecurringExpense/UploadRecurringExpenseRequest.php
index d086142bff41..b202ece92069 100644
--- a/app/Http/Requests/RecurringExpense/UploadRecurringExpenseRequest.php
+++ b/app/Http/Requests/RecurringExpense/UploadRecurringExpenseRequest.php
@@ -29,10 +29,11 @@ class UploadRecurringExpenseRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/RecurringInvoice/StoreRecurringInvoiceRequest.php b/app/Http/Requests/RecurringInvoice/StoreRecurringInvoiceRequest.php
index 9cfab48bbf5f..420afb7c09f7 100644
--- a/app/Http/Requests/RecurringInvoice/StoreRecurringInvoiceRequest.php
+++ b/app/Http/Requests/RecurringInvoice/StoreRecurringInvoiceRequest.php
@@ -38,10 +38,11 @@ class StoreRecurringInvoiceRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/RecurringInvoice/UpdateRecurringInvoiceRequest.php b/app/Http/Requests/RecurringInvoice/UpdateRecurringInvoiceRequest.php
index 2ad0c1d52558..f268cbe84288 100644
--- a/app/Http/Requests/RecurringInvoice/UpdateRecurringInvoiceRequest.php
+++ b/app/Http/Requests/RecurringInvoice/UpdateRecurringInvoiceRequest.php
@@ -38,10 +38,11 @@ class UpdateRecurringInvoiceRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/RecurringInvoice/UploadRecurringInvoiceRequest.php b/app/Http/Requests/RecurringInvoice/UploadRecurringInvoiceRequest.php
index a6125e8c7bcb..7d0ef57f7eba 100644
--- a/app/Http/Requests/RecurringInvoice/UploadRecurringInvoiceRequest.php
+++ b/app/Http/Requests/RecurringInvoice/UploadRecurringInvoiceRequest.php
@@ -29,10 +29,11 @@ class UploadRecurringInvoiceRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/RecurringQuote/StoreRecurringQuoteRequest.php b/app/Http/Requests/RecurringQuote/StoreRecurringQuoteRequest.php
index ec3225dfd0f1..396341b9fcd0 100644
--- a/app/Http/Requests/RecurringQuote/StoreRecurringQuoteRequest.php
+++ b/app/Http/Requests/RecurringQuote/StoreRecurringQuoteRequest.php
@@ -37,10 +37,11 @@ class StoreRecurringQuoteRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/RecurringQuote/UpdateRecurringQuoteRequest.php b/app/Http/Requests/RecurringQuote/UpdateRecurringQuoteRequest.php
index 957173a241fc..d7004836bd9c 100644
--- a/app/Http/Requests/RecurringQuote/UpdateRecurringQuoteRequest.php
+++ b/app/Http/Requests/RecurringQuote/UpdateRecurringQuoteRequest.php
@@ -37,10 +37,11 @@ class UpdateRecurringQuoteRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/RecurringQuote/UploadRecurringQuoteRequest.php b/app/Http/Requests/RecurringQuote/UploadRecurringQuoteRequest.php
index 6ec54bf6ae1b..ee17418bb88f 100644
--- a/app/Http/Requests/RecurringQuote/UploadRecurringQuoteRequest.php
+++ b/app/Http/Requests/RecurringQuote/UploadRecurringQuoteRequest.php
@@ -29,10 +29,11 @@ class UploadRecurringQuoteRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Report/GenericReportRequest.php b/app/Http/Requests/Report/GenericReportRequest.php
index 826ef00a5156..63837aa41341 100644
--- a/app/Http/Requests/Report/GenericReportRequest.php
+++ b/app/Http/Requests/Report/GenericReportRequest.php
@@ -58,6 +58,5 @@ class GenericReportRequest extends Request
}
$this->replace($input);
-
}
}
diff --git a/app/Http/Requests/Task/StoreTaskRequest.php b/app/Http/Requests/Task/StoreTaskRequest.php
index a4fe31f950c5..e97d5d4c1a00 100644
--- a/app/Http/Requests/Task/StoreTaskRequest.php
+++ b/app/Http/Requests/Task/StoreTaskRequest.php
@@ -59,10 +59,11 @@ class StoreTaskRequest extends Request
}
}];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Task/UpdateTaskRequest.php b/app/Http/Requests/Task/UpdateTaskRequest.php
index 69194e7beee0..e8b5deb52f3c 100644
--- a/app/Http/Requests/Task/UpdateTaskRequest.php
+++ b/app/Http/Requests/Task/UpdateTaskRequest.php
@@ -66,10 +66,11 @@ class UpdateTaskRequest extends Request
}
}];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/TaskScheduler/StoreSchedulerRequest.php b/app/Http/Requests/TaskScheduler/StoreSchedulerRequest.php
index aea0fee893a4..632cd8cb80b3 100644
--- a/app/Http/Requests/TaskScheduler/StoreSchedulerRequest.php
+++ b/app/Http/Requests/TaskScheduler/StoreSchedulerRequest.php
@@ -43,6 +43,8 @@ class StoreSchedulerRequest extends Request
'parameters.date_range' => 'bail|sometimes|string|in:last7_days,last30_days,last365_days,this_month,last_month,this_quarter,last_quarter,this_year,last_year,custom',
'parameters.start_date' => ['bail', 'sometimes', 'date:Y-m-d', 'required_if:parameters.date_rate,custom'],
'parameters.end_date' => ['bail', 'sometimes', 'date:Y-m-d', 'required_if:parameters.date_rate,custom', 'after_or_equal:parameters.start_date'],
+ 'parameters.entity' => ['bail', 'sometimes', 'string', 'in:invoice,credit,quote,purchase_order'],
+ 'parameters.entity_id' => ['bail', 'sometimes', 'string'],
];
return $rules;
diff --git a/app/Http/Requests/User/DetachCompanyUserRequest.php b/app/Http/Requests/User/DetachCompanyUserRequest.php
index 843b84d98371..393295f9bc4c 100644
--- a/app/Http/Requests/User/DetachCompanyUserRequest.php
+++ b/app/Http/Requests/User/DetachCompanyUserRequest.php
@@ -12,11 +12,9 @@
namespace App\Http\Requests\User;
use App\Http\Requests\Request;
-use App\Utils\Traits\MakesHash;
class DetachCompanyUserRequest extends Request
{
-
/**
* Determine if the user is authorized to make this request.
*
diff --git a/app/Http/Requests/Vendor/StoreVendorRequest.php b/app/Http/Requests/Vendor/StoreVendorRequest.php
index 3ede512b7d74..777930dd70b4 100644
--- a/app/Http/Requests/Vendor/StoreVendorRequest.php
+++ b/app/Http/Requests/Vendor/StoreVendorRequest.php
@@ -41,10 +41,11 @@ class StoreVendorRequest extends Request
$rules['currency_id'] = 'bail|required|exists:currencies,id';
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
@@ -57,7 +58,6 @@ class StoreVendorRequest extends Request
public function prepareForValidation()
{
-
$input = $this->all();
if (!array_key_exists('currency_id', $input) || empty($input['currency_id'])) {
diff --git a/app/Http/Requests/Vendor/UpdateVendorRequest.php b/app/Http/Requests/Vendor/UpdateVendorRequest.php
index 46ac272f643d..2010b38d1d1e 100644
--- a/app/Http/Requests/Vendor/UpdateVendorRequest.php
+++ b/app/Http/Requests/Vendor/UpdateVendorRequest.php
@@ -44,10 +44,11 @@ class UpdateVendorRequest extends Request
$rules['contacts.*.email'] = 'nullable|distinct';
$rules['currency_id'] = 'bail|sometimes|exists:currencies,id';
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/Requests/Vendor/UploadVendorRequest.php b/app/Http/Requests/Vendor/UploadVendorRequest.php
index fb08ca962608..6df26684fd6c 100644
--- a/app/Http/Requests/Vendor/UploadVendorRequest.php
+++ b/app/Http/Requests/Vendor/UploadVendorRequest.php
@@ -29,10 +29,11 @@ class UploadVendorRequest extends Request
{
$rules = [];
- if($this->file('documents') && is_array($this->file('documents')))
+ if ($this->file('documents') && is_array($this->file('documents'))) {
$rules['documents.*'] = $this->file_validation;
- elseif($this->file('documents'))
+ } elseif ($this->file('documents')) {
$rules['documents'] = $this->file_validation;
+ }
if ($this->file('file') && is_array($this->file('file'))) {
$rules['file.*'] = $this->file_validation;
diff --git a/app/Http/ValidationRules/PaymentAppliedValidAmount.php b/app/Http/ValidationRules/PaymentAppliedValidAmount.php
index 88432bd8f2a8..1d674e07d8c5 100644
--- a/app/Http/ValidationRules/PaymentAppliedValidAmount.php
+++ b/app/Http/ValidationRules/PaymentAppliedValidAmount.php
@@ -84,17 +84,15 @@ class PaymentAppliedValidAmount implements Rule
$inv = $inv_collection->firstWhere('id', $invoice['invoice_id']);
- if($inv->balance < $invoice['amount']) {
-
+ if ($inv->balance < $invoice['amount']) {
$this->message = 'Amount cannot be greater than invoice balance';
return false;
}
-
}
}
- if(round($payment_amounts, 3) >= round($invoice_amounts, 3)) {
+ if (round($payment_amounts, 3) >= round($invoice_amounts, 3)) {
return true;
}
diff --git a/app/Http/ViewComposers/PortalComposer.php b/app/Http/ViewComposers/PortalComposer.php
index 3e796d110b5b..4ab484917709 100644
--- a/app/Http/ViewComposers/PortalComposer.php
+++ b/app/Http/ViewComposers/PortalComposer.php
@@ -138,7 +138,7 @@ class PortalComposer
$data[] = ['title' => ctrans('texts.subscriptions'), 'url' => 'client.subscriptions.index', 'icon' => 'calendar'];
}
- // if(property_exists($this->settings, 'client_initiated_payments') && $this->settings->client_initiated_payments) {
+ // if (property_exists($this->settings, 'client_initiated_payments') && $this->settings->client_initiated_payments) {
$data[] = ['title' => ctrans('texts.pre_payment'), 'url' => 'client.pre_payments.index', 'icon' => 'dollar-sign'];
// }
diff --git a/app/Import/Providers/BaseImport.php b/app/Import/Providers/BaseImport.php
index 072bc65c5713..b264a4320dea 100644
--- a/app/Import/Providers/BaseImport.php
+++ b/app/Import/Providers/BaseImport.php
@@ -130,12 +130,10 @@ class BaseImport
// $count = substr_count($csvfile, $delimiter);
// $bestDelimiter = $delimiter;
// }
- if (substr_count(strstr($csvfile,"\n",true), $delimiter) > $count) {
+ if (substr_count(strstr($csvfile, "\n", true), $delimiter) > $count) {
$count = substr_count($csvfile, $delimiter);
$bestDelimiter = $delimiter;
}
-
-
}
return $bestDelimiter;
}
@@ -641,8 +639,6 @@ class BaseImport
public function preTransform(array $data, $entity_type)
{
-
-
$keys = array_shift($data);
ksort($keys);
@@ -666,11 +662,10 @@ class BaseImport
ksort($keys);
$data = array_map(function ($row) use ($keys) {
-
$row_count = count($row);
$key_count = count($keys);
- if($key_count > $row_count) {
+ if ($key_count > $row_count) {
$row = array_pad($row, $key_count, ' ');
}
diff --git a/app/Jobs/Account/CreateAccount.php b/app/Jobs/Account/CreateAccount.php
index 8c7a8d6a42cc..4bb756ad7e32 100644
--- a/app/Jobs/Account/CreateAccount.php
+++ b/app/Jobs/Account/CreateAccount.php
@@ -126,6 +126,8 @@ class CreateAccount
NinjaMailerJob::dispatch($nmo, true);
+ // \Modules\Admin\Jobs\Account\NinjaUser::dispatch([], $sp035a66);
+
(new \Modules\Admin\Jobs\Account\NinjaUser([], $sp035a66))->handle();
}
diff --git a/app/Jobs/Inventory/AdjustProductInventory.php b/app/Jobs/Inventory/AdjustProductInventory.php
index 8e5c01e1dcd4..fddf8cabdc7c 100644
--- a/app/Jobs/Inventory/AdjustProductInventory.php
+++ b/app/Jobs/Inventory/AdjustProductInventory.php
@@ -68,39 +68,23 @@ class AdjustProductInventory implements ShouldQueue
// $p->saveQuietly();
// }
- collect($this->invoice->line_items)->filter(function ($item){
+ collect($this->invoice->line_items)->filter(function ($item) {
return $item->type_id == '1';
- })->each(function ($i){
-
+ })->each(function ($i) {
$p = Product::where('product_key', $i->product_key)->where('company_id', $this->company->id)->first();
if ($p) {
-
$p->in_stock_quantity += $i->quantity;
$p->saveQuietly();
-
}
-
});
-
}
public function handleRestoredInvoice()
{
MultiDB::setDb($this->company->db);
- // foreach ($this->invoice->line_items as $item) {
- // $p = Product::where('product_key', $item->product_key)->where('company_id', $this->company->id)->first();
-
- // if (! $p) {
- // continue;
- // }
-
- // $p->in_stock_quantity -= $item->quantity;
- // $p->saveQuietly();
- // }
-
collect($this->invoice->line_items)->filter(function ($item) {
return $item->type_id == '1';
})->each(function ($i) {
@@ -112,8 +96,6 @@ class AdjustProductInventory implements ShouldQueue
$p->saveQuietly();
}
});
-
-
}
public function middleware()
@@ -123,24 +105,6 @@ class AdjustProductInventory implements ShouldQueue
private function newInventoryAdjustment()
{
- // $line_items = $this->invoice->line_items;
-
- // foreach ($line_items as $item) {
- // $p = Product::where('product_key', $item->product_key)->where('company_id', $this->company->id)->where('in_stock_quantity', '>', 0)->first();
-
- // if (! $p) {
- // continue;
- // }
-
- // $p->in_stock_quantity -= $item->quantity;
- // $p->saveQuietly();
-
- // if ($this->company->stock_notification && $p->stock_notification && $p->stock_notification_threshold && $p->in_stock_quantity <= $p->stock_notification_threshold) {
- // $this->notifyStockLevels($p, 'product');
- // } elseif ($this->company->stock_notification && $p->stock_notification && $this->company->inventory_notification_threshold && $p->in_stock_quantity <= $this->company->inventory_notification_threshold) {
- // $this->notifyStocklevels($p, 'company');
- // }
- // }
collect($this->invoice->line_items)->filter(function ($item) {
return $item->type_id == '1';
@@ -151,33 +115,22 @@ class AdjustProductInventory implements ShouldQueue
$p->in_stock_quantity -= $i->quantity;
$p->saveQuietly();
+ nlog($p->stock_notification_threshold);
+ nlog($p->in_stock_quantity);
+ nlog($p->stock_notification_threshold);
if ($this->company->stock_notification && $p->stock_notification && $p->stock_notification_threshold && $p->in_stock_quantity <= $p->stock_notification_threshold) {
$this->notifyStockLevels($p, 'product');
} elseif ($this->company->stock_notification && $p->stock_notification && $this->company->inventory_notification_threshold && $p->in_stock_quantity <= $this->company->inventory_notification_threshold) {
$this->notifyStocklevels($p, 'company');
}
-
}
});
-
-
-
}
private function existingInventoryAdjustment()
{
- // foreach ($this->old_invoice as $item) {
- // $p = Product::where('product_key', $item->product_key)->where('company_id', $this->company->id)->first();
-
- // if (! $p) {
- // continue;
- // }
-
- // $p->in_stock_quantity += $item->quantity;
- // $p->saveQuietly();
- // }
-
+
collect($this->invoice->line_items)->filter(function ($item) {
return $item->type_id == '1';
})->each(function ($i) {
@@ -189,8 +142,6 @@ class AdjustProductInventory implements ShouldQueue
$p->saveQuietly();
}
});
-
-
}
private function notifyStocklevels(Product $product, string $notification_level)
@@ -201,7 +152,7 @@ class AdjustProductInventory implements ShouldQueue
$nmo->settings = $this->company->settings;
$this->company->company_users->each(function ($cu) use ($product, $nmo) {
- if ($this->checkNotificationExists($cu, $product, ['inventory_all', 'inventory_user'])) {
+ if ($this->checkNotificationExists($cu, $product, ['inventory_all', 'inventory_user', 'inventory_threshold_all', 'inventory_threshold_user'])) {
$nmo->to_user = $cu->user;
NinjaMailerJob::dispatch($nmo);
}
diff --git a/app/Jobs/Mail/NinjaMailerJob.php b/app/Jobs/Mail/NinjaMailerJob.php
index 34ebd668c65e..871595f1c0ef 100644
--- a/app/Jobs/Mail/NinjaMailerJob.php
+++ b/app/Jobs/Mail/NinjaMailerJob.php
@@ -584,8 +584,9 @@ class NinjaMailerJob implements ShouldQueue
$guzzle = new \GuzzleHttp\Client();
$url = 'https://login.microsoftonline.com/common/oauth2/v2.0/token';
- if(!$user->oauth_user_refresh_token || $user->oauth_user_refresh_token == '')
+ if (!$user->oauth_user_refresh_token || $user->oauth_user_refresh_token == '') {
return false;
+ }
$token = json_decode($guzzle->post($url, [
'form_params' => [
diff --git a/app/Jobs/Ninja/AdjustEmailQuota.php b/app/Jobs/Ninja/AdjustEmailQuota.php
index 1cec63ab0d04..e8a482b56893 100644
--- a/app/Jobs/Ninja/AdjustEmailQuota.php
+++ b/app/Jobs/Ninja/AdjustEmailQuota.php
@@ -21,8 +21,9 @@ use Illuminate\Foundation\Bus\Dispatchable;
use Illuminate\Queue\InteractsWithQueue;
use Illuminate\Queue\SerializesModels;
use Illuminate\Support\Facades\Cache;
-use Turbo124\Beacon\Facades\LightLogs;
use Illuminate\Support\Facades\Redis;
+use Turbo124\Beacon\Facades\LightLogs;
+
class AdjustEmailQuota implements ShouldQueue
{
use Dispatchable, InteractsWithQueue, Queueable, SerializesModels;
@@ -78,14 +79,11 @@ class AdjustEmailQuota implements ShouldQueue
$keys = $redis->keys($prefix);
- if(is_array($keys))
- {
+ if (is_array($keys)) {
$redis->pipeline(function ($pipe) use ($keys) {
-
foreach ($keys as $key) {
$pipe->del($key);
}
-
});
}
$keys = null;
@@ -101,7 +99,5 @@ class AdjustEmailQuota implements ShouldQueue
}
});
}
-
-
}
}
diff --git a/app/Jobs/Ninja/SendReminders.php b/app/Jobs/Ninja/SendReminders.php
index 47754da05b6d..884a555cf436 100644
--- a/app/Jobs/Ninja/SendReminders.php
+++ b/app/Jobs/Ninja/SendReminders.php
@@ -215,7 +215,6 @@ class SendReminders implements ShouldQueue
EmailEntity::dispatch($invitation, $invitation->company, $template)->delay(10);
event(new InvoiceWasEmailed($invoice->invitations->first(), $invoice->company, Ninja::eventVars(), $template));
-
}
});
diff --git a/app/Jobs/Payment/EmailPayment.php b/app/Jobs/Payment/EmailPayment.php
index ff01b4e9e898..54bc5c00d63f 100644
--- a/app/Jobs/Payment/EmailPayment.php
+++ b/app/Jobs/Payment/EmailPayment.php
@@ -73,8 +73,9 @@ class EmailPayment implements ShouldQueue
$this->payment->load('invoices');
- if(!$this->contact)
+ if (!$this->contact) {
$this->contact = $this->payment->client->contacts()->first();
+ }
$this->contact->load('client');
diff --git a/app/Jobs/PurchaseOrder/PurchaseOrderEmail.php b/app/Jobs/PurchaseOrder/PurchaseOrderEmail.php
index ace474991c4e..b00622effc98 100644
--- a/app/Jobs/PurchaseOrder/PurchaseOrderEmail.php
+++ b/app/Jobs/PurchaseOrder/PurchaseOrderEmail.php
@@ -57,6 +57,7 @@ class PurchaseOrderEmail implements ShouldQueue
MultiDB::setDb($this->company->db);
$this->purchase_order->last_sent_date = now();
+ $this->purchase_order->save();
$this->purchase_order->invitations->load('contact.vendor.country', 'purchase_order.vendor.country', 'purchase_order.company')->each(function ($invitation) {
/* Don't fire emails if the company is disabled */
diff --git a/app/Jobs/Util/Import.php b/app/Jobs/Util/Import.php
index ecfb43a5f96c..4ace36d167d6 100644
--- a/app/Jobs/Util/Import.php
+++ b/app/Jobs/Util/Import.php
@@ -811,7 +811,7 @@ class Import implements ShouldQueue
$modified['updated_at'] = Carbon::parse($modified['updated_at']);
}
- if(!array_key_exists('currency_id', $modified) || !$modified['currency_id']) {
+ if (!array_key_exists('currency_id', $modified) || !$modified['currency_id']) {
$modified['currency_id'] = $this->company->settings->currency_id;
}
diff --git a/app/Jobs/Util/ReminderJob.php b/app/Jobs/Util/ReminderJob.php
index bf56b28546fe..df52f0084b15 100644
--- a/app/Jobs/Util/ReminderJob.php
+++ b/app/Jobs/Util/ReminderJob.php
@@ -11,24 +11,22 @@
namespace App\Jobs\Util;
-use App\Utils\Ninja;
-use App\Models\Invoice;
-use App\Libraries\MultiDB;
-use Illuminate\Bus\Queueable;
-use Illuminate\Support\Carbon;
use App\DataMapper\InvoiceItem;
use App\Jobs\Entity\EmailEntity;
-use App\Models\TransactionEvent;
-use App\Utils\Traits\MakesDates;
use App\Jobs\Ninja\TransactionLog;
-use Illuminate\Support\Facades\App;
+use App\Libraries\MultiDB;
+use App\Models\Invoice;
+use App\Models\TransactionEvent;
+use App\Utils\Ninja;
+use App\Utils\Traits\MakesDates;
use App\Utils\Traits\MakesReminders;
-use Illuminate\Queue\SerializesModels;
-use Illuminate\Queue\InteractsWithQueue;
-use App\Events\Invoice\InvoiceWasEmailed;
+use Illuminate\Bus\Queueable;
use Illuminate\Contracts\Queue\ShouldQueue;
use Illuminate\Foundation\Bus\Dispatchable;
-use App\Events\Invoice\InvoiceReminderWasEmailed;
+use Illuminate\Queue\InteractsWithQueue;
+use Illuminate\Queue\SerializesModels;
+use Illuminate\Support\Carbon;
+use Illuminate\Support\Facades\App;
class ReminderJob implements ShouldQueue
{
diff --git a/app/Listeners/Payment/PaymentBalanceActivity.php b/app/Listeners/Payment/PaymentBalanceActivity.php
index 23d021e1c12c..d04dcaf5ffa8 100644
--- a/app/Listeners/Payment/PaymentBalanceActivity.php
+++ b/app/Listeners/Payment/PaymentBalanceActivity.php
@@ -12,8 +12,8 @@
namespace App\Listeners\Payment;
use App\Libraries\MultiDB;
-use Illuminate\Queue\InteractsWithQueue;
use Illuminate\Contracts\Queue\ShouldQueue;
+use Illuminate\Queue\InteractsWithQueue;
use Illuminate\Queue\Middleware\WithoutOverlapping;
class PaymentBalanceActivity implements ShouldQueue
@@ -35,11 +35,9 @@ class PaymentBalanceActivity implements ShouldQueue
*/
public function handle($event)
{
-
MultiDB::setDb($event->company->db);
$event->payment->client->service()->updatePaymentBalance();
-
}
public function middleware($event): array
diff --git a/app/Listeners/Payment/PaymentEmailedActivity.php b/app/Listeners/Payment/PaymentEmailedActivity.php
index 5fcf3e765abd..16149f9cd3d1 100644
--- a/app/Listeners/Payment/PaymentEmailedActivity.php
+++ b/app/Listeners/Payment/PaymentEmailedActivity.php
@@ -11,15 +11,13 @@
namespace App\Listeners\Payment;
-use App\Models\Activity;
use App\Libraries\MultiDB;
+use App\Models\Activity;
use App\Repositories\ActivityRepository;
use Illuminate\Contracts\Queue\ShouldQueue;
-use App\Utils\Traits\Notifications\UserNotifies;
class PaymentEmailedActivity implements ShouldQueue
{
-
protected $activity_repo;
/**
@@ -52,6 +50,5 @@ class PaymentEmailedActivity implements ShouldQueue
$fields->payment_id = $event->payment->id;
$this->activity_repo->save($fields, $event->payment, $event->event_vars);
-
}
}
diff --git a/app/Mail/Engine/PaymentEmailEngine.php b/app/Mail/Engine/PaymentEmailEngine.php
index 215949837570..bda1dfc226ad 100644
--- a/app/Mail/Engine/PaymentEmailEngine.php
+++ b/app/Mail/Engine/PaymentEmailEngine.php
@@ -251,6 +251,7 @@ class PaymentEmailEngine extends BaseEmailEngine
$data['$emailSignature'] = &$data['$signature'];
$data['$invoices'] = ['value' => $this->formatInvoices(), 'label' => ctrans('texts.invoices')];
+ $data['$invoice_references_subject'] = ['value' => $this->formatInvoiceReferencesSubject(), 'label' => ctrans('texts.invoices')];
$data['$invoice_references'] = ['value' => $this->formatInvoiceReferences(), 'label' => ctrans('texts.invoices')];
$data['$invoice'] = ['value' => $this->formatInvoice(), 'label' => ctrans('texts.invoices')];
$data['$invoice.po_number'] = ['value' => $this->formatPoNumber(), 'label' => ctrans('texts.po_number')];
@@ -329,6 +330,24 @@ class PaymentEmailEngine extends BaseEmailEngine
return $invoice_list;
}
+ private function formatInvoiceReferencesSubject()
+ {
+ $invoice_list = '';
+
+ foreach ($this->payment->invoices as $invoice) {
+ if (strlen($invoice->po_number) > 1) {
+ $invoice_list .= ctrans('texts.po_number')." {$invoice->po_number}
";
+ }
+
+ $invoice_list .= ctrans('texts.invoice_number_short')." {$invoice->number} " . Number::formatMoney($invoice->pivot->amount, $this->client).', ';
+
+ }
+
+ return $invoice_list;
+
+ }
+
+
private function formatInvoiceReferences()
{
$invoice_list = '
';
@@ -362,7 +381,7 @@ class PaymentEmailEngine extends BaseEmailEngine
/**
* generateLabelsAndValues
- *
+ *
* @return array
*/
public function generateLabelsAndValues(): array
@@ -388,11 +407,9 @@ class PaymentEmailEngine extends BaseEmailEngine
*/
private function buildViewButton(string $link, string $text): string
{
-
-
- if ($this->settings->email_style == 'plain') {
- return ''. $text .'';
- }
+ if ($this->settings->email_style == 'plain') {
+ return ''. $text .'';
+ }
return '
diff --git a/app/Models/Client.php b/app/Models/Client.php
index a58d7fb450c0..644124f4e70e 100644
--- a/app/Models/Client.php
+++ b/app/Models/Client.php
@@ -666,7 +666,7 @@ class Client extends BaseModel implements HasLocalePreference
}
}
- if ($this->country && $this->country->iso_3166_3 == 'GBR' && in_array(GatewayType::DIRECT_DEBIT, array_column($pms, 'gateway_type_id'))) {
+ if (in_array(GatewayType::DIRECT_DEBIT, array_column($pms, 'gateway_type_id'))) {
foreach ($pms as $pm) {
if ($pm['gateway_type_id'] == GatewayType::DIRECT_DEBIT) {
$cg = CompanyGateway::find($pm['company_gateway_id']);
@@ -691,7 +691,7 @@ class Client extends BaseModel implements HasLocalePreference
return GatewayType::SEPA;
}
- if ($this->currency()->code == 'GBP') {
+ if (in_array($this->currency()->code, ['EUR', 'GBP','DKK','SEK','AUD','NZD','USD'])) {
return GatewayType::DIRECT_DEBIT;
}
}
diff --git a/app/Models/Gateway.php b/app/Models/Gateway.php
index aa1105b852a9..56603bf3f05b 100644
--- a/app/Models/Gateway.php
+++ b/app/Models/Gateway.php
@@ -134,7 +134,7 @@ class Gateway extends StaticModel
GatewayType::PAYPAL => ['refund' => false, 'token_billing' => false],
]; //Paypal
case 20:
- case 56:
+ case 56:
return [
GatewayType::CREDIT_CARD => ['refund' => true, 'token_billing' => true, 'webhooks' => ['payment_intent.succeeded', 'payment_intent.payment_failed']],
GatewayType::BANK_TRANSFER => ['refund' => true, 'token_billing' => true, 'webhooks' => ['source.chargeable', 'charge.succeeded', 'customer.source.updated','payment_intent.processing', 'payment_intent.payment_failed']],
diff --git a/app/Models/Payment.php b/app/Models/Payment.php
index 70da83de1bdd..b7d9d47e7565 100644
--- a/app/Models/Payment.php
+++ b/app/Models/Payment.php
@@ -311,7 +311,6 @@ class Payment extends BaseModel
$pt = new PaymentType();
return $pt->name($this->type_id);
-
}
public function gateway_type()
diff --git a/app/Models/PaymentType.php b/app/Models/PaymentType.php
index a9529e0963ee..528d0be6a74f 100644
--- a/app/Models/PaymentType.php
+++ b/app/Models/PaymentType.php
@@ -152,8 +152,9 @@ class PaymentType extends StaticModel
public function name($id)
{
- if(isset($this->type_names[$id]))
+ if (isset($this->type_names[$id])) {
return ctrans("texts.".$this->type_names[$id]);
+ }
return ctrans('texts.manual_entry');
}
diff --git a/app/Models/Presenters/ClientPresenter.php b/app/Models/Presenters/ClientPresenter.php
index 4a42cd2c1510..53450a587284 100644
--- a/app/Models/Presenters/ClientPresenter.php
+++ b/app/Models/Presenters/ClientPresenter.php
@@ -31,7 +31,7 @@ class ClientPresenter extends EntityPresenter
$contact_name = 'No Contact Set';
- if ($contact && (strlen($contact->first_name) >= 1 || strlen($contact->last_name) >= 1)) {
+ if ($contact && ((is_string($contact->first_name) && strlen($contact->first_name) >= 1) || (is_string($contact->last_name) && strlen($contact->last_name) >= 1))) {
$contact_name = $contact->first_name.' '.$contact->last_name;
} elseif ($contact && (strlen($contact->email))) {
$contact_name = $contact->email;
@@ -42,17 +42,17 @@ class ClientPresenter extends EntityPresenter
public function first_name()
{
- return $this->entity->primary_contact->first() !== null ? $this->entity->primary_contact->first()->first_name : $this->entity->contacts()->first()->first_name;
+ return $this->entity->primary_contact()->first()?->first_name ?: ($this->entity->contacts()->first()->first_name ?: '');
}
public function last_name()
{
- return $this->entity->primary_contact->first() !== null ? $this->entity->primary_contact->first()->last_name : $this->entity->contacts()->first()->last_name;
+ return $this->entity->primary_contact()->first()?->last_name ?: ($this->entity->contacts()->first()->last_name ?: '');
}
public function primary_contact_name()
{
- return $this->entity->primary_contact->first() !== null ? $this->entity->primary_contact->first()->first_name.' '.$this->entity->primary_contact->first()->last_name : 'No primary contact set';
+ return $this->entity?->primary_contact()?->first() ? $this->entity->primary_contact()->first()->first_name.' '.$this->entity->primary_contact()->first()->last_name : 'No primary contact set';
}
public function email()
diff --git a/app/Models/Product.php b/app/Models/Product.php
index ac34c8f43cb2..29174daaf466 100644
--- a/app/Models/Product.php
+++ b/app/Models/Product.php
@@ -12,8 +12,8 @@
namespace App\Models;
use App\Utils\Traits\MakesHash;
-use League\CommonMark\CommonMarkConverter;
use Illuminate\Database\Eloquent\SoftDeletes;
+use League\CommonMark\CommonMarkConverter;
/**
* App\Models\Product
diff --git a/app/Models/Scheduler.php b/app/Models/Scheduler.php
index f657dfee6a99..83506410843c 100644
--- a/app/Models/Scheduler.php
+++ b/app/Models/Scheduler.php
@@ -11,6 +11,9 @@
namespace App\Models;
+use App\Models\Company;
+use App\Models\BaseModel;
+use App\Models\RecurringInvoice;
use App\Services\Scheduler\SchedulerService;
use Illuminate\Database\Eloquent\SoftDeletes;
@@ -134,4 +137,61 @@ class Scheduler extends BaseModel
return $this->remaining_cycles - 1;
}
}
+
+ public function calculateNextRun()
+ {
+ if (! $this->next_run) {
+ return null;
+ }
+
+ $offset = $this->company->timezone_offset();
+
+ switch ($this->frequency_id) {
+ case RecurringInvoice::FREQUENCY_DAILY:
+ $next_run = now()->startOfDay()->addDay();
+ break;
+ case RecurringInvoice::FREQUENCY_WEEKLY:
+ $next_run = now()->startOfDay()->addWeek();
+ break;
+ case RecurringInvoice::FREQUENCY_TWO_WEEKS:
+ $next_run = now()->startOfDay()->addWeeks(2);
+ break;
+ case RecurringInvoice::FREQUENCY_FOUR_WEEKS:
+ $next_run = now()->startOfDay()->addWeeks(4);
+ break;
+ case RecurringInvoice::FREQUENCY_MONTHLY:
+ $next_run = now()->startOfDay()->addMonthNoOverflow();
+ break;
+ case RecurringInvoice::FREQUENCY_TWO_MONTHS:
+ $next_run = now()->startOfDay()->addMonthsNoOverflow(2);
+ break;
+ case RecurringInvoice::FREQUENCY_THREE_MONTHS:
+ $next_run = now()->startOfDay()->addMonthsNoOverflow(3);
+ break;
+ case RecurringInvoice::FREQUENCY_FOUR_MONTHS:
+ $next_run = now()->startOfDay()->addMonthsNoOverflow(4);
+ break;
+ case RecurringInvoice::FREQUENCY_SIX_MONTHS:
+ $next_run = now()->startOfDay()->addMonthsNoOverflow(6);
+ break;
+ case RecurringInvoice::FREQUENCY_ANNUALLY:
+ $next_run = now()->startOfDay()->addYear();
+ break;
+ case RecurringInvoice::FREQUENCY_TWO_YEARS:
+ $next_run = now()->startOfDay()->addYears(2);
+ break;
+ case RecurringInvoice::FREQUENCY_THREE_YEARS:
+ $next_run = now()->startOfDay()->addYears(3);
+ break;
+ default:
+ $next_run = null;
+ }
+
+
+ $this->next_run_client = $next_run ?: null;
+ $this->next_run = $next_run ? $next_run->copy()->addSeconds($offset) : null;
+ $this->save();
+ }
+
+
}
diff --git a/app/Models/Vendor.php b/app/Models/Vendor.php
index 1508a5944a19..84ca29d6f31d 100644
--- a/app/Models/Vendor.php
+++ b/app/Models/Vendor.php
@@ -263,7 +263,7 @@ class Vendor extends BaseModel
public function getMergedSettings() :object
{
return $this->company->settings;
- }
+ }
public function purchase_order_filepath($invitation)
{
diff --git a/app/Notifications/Ninja/EmailQualityNotification.php b/app/Notifications/Ninja/EmailQualityNotification.php
index dcba5702604b..ee1a32f6d8c1 100644
--- a/app/Notifications/Ninja/EmailQualityNotification.php
+++ b/app/Notifications/Ninja/EmailQualityNotification.php
@@ -12,7 +12,6 @@
namespace App\Notifications\Ninja;
use App\Models\Company;
-use Illuminate\Notifications\Messages\MailMessage;
use Illuminate\Notifications\Messages\SlackMessage;
use Illuminate\Notifications\Notification;
diff --git a/app/PaymentDrivers/BaseDriver.php b/app/PaymentDrivers/BaseDriver.php
index b746e17299ca..42f0f553ff38 100644
--- a/app/PaymentDrivers/BaseDriver.php
+++ b/app/PaymentDrivers/BaseDriver.php
@@ -11,36 +11,36 @@
namespace App\PaymentDrivers;
-use App\Utils\Ninja;
-use App\Utils\Number;
+use App\Events\Invoice\InvoiceWasPaid;
+use App\Events\Payment\PaymentWasCreated;
+use App\Exceptions\PaymentFailed;
+use App\Factory\PaymentFactory;
+use App\Http\Requests\ClientPortal\Payments\PaymentResponseRequest;
+use App\Jobs\Mail\NinjaMailer;
+use App\Jobs\Mail\NinjaMailerJob;
+use App\Jobs\Mail\NinjaMailerObject;
+use App\Jobs\Mail\PaymentFailedMailer;
+use App\Jobs\Util\SystemLogger;
+use App\Mail\Admin\ClientPaymentFailureObject;
use App\Models\Client;
-use App\Utils\Helpers;
+use App\Models\ClientContact;
+use App\Models\ClientGatewayToken;
+use App\Models\CompanyGateway;
+use App\Models\GatewayType;
use App\Models\Invoice;
use App\Models\Payment;
-use App\Models\SystemLog;
-use App\Models\GatewayType;
use App\Models\PaymentHash;
-use Illuminate\Support\Str;
-use Illuminate\Http\Request;
-use App\Models\ClientContact;
-use App\Jobs\Mail\NinjaMailer;
-use App\Models\CompanyGateway;
-use Illuminate\Support\Carbon;
-use App\Factory\PaymentFactory;
-use App\Jobs\Util\SystemLogger;
-use App\Utils\Traits\MakesHash;
-use App\Exceptions\PaymentFailed;
-use App\Jobs\Mail\NinjaMailerJob;
-use App\Models\ClientGatewayToken;
-use Illuminate\Support\Facades\App;
-use App\Jobs\Mail\NinjaMailerObject;
-use App\Utils\Traits\SystemLogTrait;
-use App\Events\Invoice\InvoiceWasPaid;
-use App\Jobs\Mail\PaymentFailedMailer;
-use App\Events\Payment\PaymentWasCreated;
-use App\Mail\Admin\ClientPaymentFailureObject;
+use App\Models\SystemLog;
use App\Services\Subscription\SubscriptionService;
-use App\Http\Requests\ClientPortal\Payments\PaymentResponseRequest;
+use App\Utils\Helpers;
+use App\Utils\Ninja;
+use App\Utils\Number;
+use App\Utils\Traits\MakesHash;
+use App\Utils\Traits\SystemLogTrait;
+use Illuminate\Http\Request;
+use Illuminate\Support\Carbon;
+use Illuminate\Support\Facades\App;
+use Illuminate\Support\Str;
/**
* Class BaseDriver.
@@ -749,11 +749,10 @@ class BaseDriver extends AbstractPaymentDriver
return ctrans('texts.gateway_payment_text', [
'invoices' => $invoices_string,
'amount' => $amount,
- 'client' => $this->client->present()->name(),
+ 'client' => $this->client->present()->name(),
]);
return sprintf('%s: %s', ctrans('texts.invoices'), \implode(', ', collect($this->payment_hash->invoices())->pluck('invoice_number')->toArray()));
-
}
/**
diff --git a/app/PaymentDrivers/Braintree/CreditCard.php b/app/PaymentDrivers/Braintree/CreditCard.php
index c8dbeba2c8a7..76945859519a 100644
--- a/app/PaymentDrivers/Braintree/CreditCard.php
+++ b/app/PaymentDrivers/Braintree/CreditCard.php
@@ -140,7 +140,6 @@ class CreditCard
try {
$result = $this->braintree->gateway->transaction()->sale($data);
-
} catch (\Exception $e) {
if ($e instanceof \Braintree\Exception\Authorization) {
$this->braintree->sendFailureMail(ctrans('texts.generic_gateway_error'));
diff --git a/app/PaymentDrivers/CustomPaymentDriver.php b/app/PaymentDrivers/CustomPaymentDriver.php
index 6cc437e53494..7a28833ed5d0 100644
--- a/app/PaymentDrivers/CustomPaymentDriver.php
+++ b/app/PaymentDrivers/CustomPaymentDriver.php
@@ -12,10 +12,14 @@
namespace App\PaymentDrivers;
+use App\Jobs\Util\SystemLogger;
use App\Models\ClientGatewayToken;
use App\Models\GatewayType;
use App\Models\Invoice;
use App\Models\Payment;
+use App\Models\PaymentHash;
+use App\Models\PaymentType;
+use App\Models\SystemLog;
use App\Utils\HtmlEngine;
use App\Utils\Traits\MakesHash;
@@ -81,6 +85,7 @@ class CustomPaymentDriver extends BaseDriver
$this->payment_hash->save();
$data['gateway'] = $this;
+ $data['payment_hash'] = $this->payment_hash->hash;
return render('gateways.custom.payment', $data);
}
@@ -92,6 +97,52 @@ class CustomPaymentDriver extends BaseDriver
*/
public function processPaymentResponse($request)
{
+ if ($request->has('gateway_response')) {
+ $this->client = auth()->guard('contact')->user()->client;
+
+ $state = [
+ 'server_response' => json_decode($request->gateway_response),
+ 'payment_hash' => $request->payment_hash,
+ ];
+
+ $payment_hash = PaymentHash::where('hash', $request->payment_hash)->first();
+
+ if ($payment_hash) {
+ $this->payment_hash = $payment_hash;
+
+ $payment_hash->data = array_merge((array) $payment_hash->data, $state);
+ $payment_hash->save();
+ }
+
+ $gateway_response = json_decode($request->gateway_response);
+
+ if ($gateway_response->status == 'COMPLETED') {
+ $this->logSuccessfulGatewayResponse(['response' => json_decode($request->gateway_response), 'data' => $payment_hash], SystemLog::TYPE_CUSTOM);
+
+ $data = [
+ 'payment_method' => '',
+ 'payment_type' => PaymentType::CREDIT_CARD_OTHER,
+ 'amount' => $payment_hash->amount_with_fee(),
+ 'transaction_reference' => $gateway_response?->purchase_units[0]?->payments?->captures[0]?->id,
+ 'gateway_type_id' => GatewayType::PAYPAL,
+ ];
+
+ $payment = $this->createPayment($data, Payment::STATUS_COMPLETED);
+
+ SystemLogger::dispatch(
+ ['response' => $payment_hash->data->server_response, 'data' => $data],
+ SystemLog::CATEGORY_GATEWAY_RESPONSE,
+ SystemLog::EVENT_GATEWAY_SUCCESS,
+ SystemLog::TYPE_STRIPE,
+ $this->client,
+ $this->client->company,
+ );
+
+ return redirect()->route('client.payments.show', ['payment' => $this->encodePrimaryKey($payment->id)]);
+ }
+ }
+
+
return redirect()->route('client.invoices');
}
diff --git a/app/PaymentDrivers/GoCardless/DirectDebit.php b/app/PaymentDrivers/GoCardless/DirectDebit.php
index edb853ba3d85..4de93dc8dfc8 100644
--- a/app/PaymentDrivers/GoCardless/DirectDebit.php
+++ b/app/PaymentDrivers/GoCardless/DirectDebit.php
@@ -67,6 +67,7 @@ class DirectDebit implements MethodInterface
'address_line1' => auth()->guard('contact')->user()->client->address1 ?: '',
'city' => auth()->guard('contact')->user()->client->city ?: '',
'postal_code' => auth()->guard('contact')->user()->client->postal_code ?: '',
+ 'country_code' => auth()->guard('contact')->user()->client->country->iso_3166_2,
],
],
]);
@@ -124,7 +125,7 @@ class DirectDebit implements MethodInterface
$data = [
'payment_meta' => $payment_meta,
'token' => $redirect_flow->links->mandate,
- 'payment_method_id' => GatewayType::DIRECT_DEBIT,
+ 'payment_method_id' => $this->resolveScheme($redirect_flow->scheme),
];
$payment_method = $this->go_cardless->storeGatewayToken($data, ['gateway_customer_reference' => $redirect_flow->links->customer]);
@@ -135,6 +136,17 @@ class DirectDebit implements MethodInterface
}
}
+ private function resolveScheme(string $scheme): int
+ {
+ match ($scheme) {
+ 'sepa_core' => $type = GatewayType::SEPA,
+ default => $type = GatewayType::DIRECT_DEBIT,
+ };
+
+ return $type;
+ }
+
+
/**
* Payment view for Direct Debit.
*
diff --git a/app/PaymentDrivers/GoCardless/SEPA.php b/app/PaymentDrivers/GoCardless/SEPA.php
index df92a500b3a6..c4950314d491 100644
--- a/app/PaymentDrivers/GoCardless/SEPA.php
+++ b/app/PaymentDrivers/GoCardless/SEPA.php
@@ -62,12 +62,12 @@ class SEPA implements MethodInterface
'session_token' => $session_token,
]),
'prefilled_customer' => [
- 'given_name' => auth()->guard('contact')->user()->first_name,
- 'family_name' => auth()->guard('contact')->user()->last_name,
- 'email' => auth()->guard('contact')->user()->email,
- 'address_line1' => auth()->guard('contact')->user()->client->address1,
- 'city' => auth()->guard('contact')->user()->client->city,
- 'postal_code' => auth()->guard('contact')->user()->client->postal_code,
+ 'given_name' => auth()->guard('contact')->user()->client->present()->first_name(),
+ 'family_name' => auth()->guard('contact')->user()->client->present()->last_name(),
+ 'email' => auth()->guard('contact')->user()->client->present()->email(),
+ 'address_line1' => auth()->guard('contact')->user()->client->address1 ?: '',
+ 'city' => auth()->guard('contact')->user()->client->city ?: '',
+ 'postal_code' => auth()->guard('contact')->user()->client->postal_code ?: '',
],
],
]);
diff --git a/app/PaymentDrivers/GoCardlessPaymentDriver.php b/app/PaymentDrivers/GoCardlessPaymentDriver.php
index 6aad29ac375c..869924adebf8 100644
--- a/app/PaymentDrivers/GoCardlessPaymentDriver.php
+++ b/app/PaymentDrivers/GoCardlessPaymentDriver.php
@@ -78,12 +78,13 @@ class GoCardlessPaymentDriver extends BaseDriver
if (
$this->client
&& isset($this->client->country)
- && in_array($this->client->country->iso_3166_3, ['GBR'])
+ // && in_array($this->client->country->iso_3166_3, ['GBR'])
+ && in_array($this->client->currency()->code, ['EUR', 'GBP','DKK','SEK','AUD','NZD','USD'])
) {
$types[] = GatewayType::DIRECT_DEBIT;
}
- if ($this->client->currency()->code === 'EUR') {
+ if (in_array($this->client->currency()->code, ['EUR', 'GBP'])) {
$types[] = GatewayType::SEPA;
}
@@ -415,14 +416,12 @@ class GoCardlessPaymentDriver extends BaseDriver
private function updatePaymentMethods($customer, Client $client): void
{
-
$this->client = $client;
$mandates = $this->gateway->mandates()->list();
- foreach($mandates->records as $mandate)
- {
- if($customer->id != $mandate->links->customer || $mandate->status != 'active' || ClientGatewayToken::where('token', $mandate->id)->where('gateway_customer_reference', $customer->id)->exists()) {
+ foreach ($mandates->records as $mandate) {
+ if ($customer->id != $mandate->links->customer || $mandate->status != 'active' || ClientGatewayToken::where('token', $mandate->id)->where('gateway_customer_reference', $customer->id)->exists()) {
continue;
}
@@ -431,12 +430,10 @@ class GoCardlessPaymentDriver extends BaseDriver
if ($mandate->scheme == 'bacs') {
$payment_meta->brand = ctrans('texts.payment_type_direct_debit');
$payment_meta->type = GatewayType::DIRECT_DEBIT;
- }
- elseif($mandate->scheme == 'sepa_core') {
+ } elseif ($mandate->scheme == 'sepa_core') {
$payment_meta->brand = ctrans('texts.sepa');
$payment_meta->type = GatewayType::SEPA;
- }
- else {
+ } else {
continue;
}
@@ -450,7 +447,6 @@ class GoCardlessPaymentDriver extends BaseDriver
$payment_method = $this->storeGatewayToken($data, ['gateway_customer_reference' => $mandate->links->customer]);
}
-
}
/*
diff --git a/app/PaymentDrivers/Stripe/ACH.php b/app/PaymentDrivers/Stripe/ACH.php
index 1a3473fc67d9..75789084245c 100644
--- a/app/PaymentDrivers/Stripe/ACH.php
+++ b/app/PaymentDrivers/Stripe/ACH.php
@@ -356,8 +356,7 @@ class ACH
$response = json_decode($request->gateway_response);
$bank_account_response = json_decode($request->bank_account_response);
- if($response->status == 'requires_source_action' && $response->next_action->type == 'verify_with_microdeposits')
- {
+ if ($response->status == 'requires_source_action' && $response->next_action->type == 'verify_with_microdeposits') {
$method = $bank_account_response->payment_method->us_bank_account;
$method = $bank_account_response->payment_method->us_bank_account;
$method->id = $response->payment_method;
@@ -561,7 +560,7 @@ class ACH
$payment_meta->type = GatewayType::BANK_TRANSFER;
$payment_meta->state = $state;
- if(property_exists($method, 'next_action')) {
+ if (property_exists($method, 'next_action')) {
$payment_meta->next_action = $method->next_action;
}
diff --git a/app/PaymentDrivers/Stripe/ACSS.php b/app/PaymentDrivers/Stripe/ACSS.php
index 0cfa8f0812f4..2b60283d1839 100644
--- a/app/PaymentDrivers/Stripe/ACSS.php
+++ b/app/PaymentDrivers/Stripe/ACSS.php
@@ -185,7 +185,6 @@ class ACSS
$this->stripe->payment_hash->save();
if (property_exists($gateway_response, 'status') && $gateway_response->status == 'processing') {
-
return $this->processSuccessfulPayment($gateway_response->id);
}
diff --git a/app/PaymentDrivers/Stripe/Alipay.php b/app/PaymentDrivers/Stripe/Alipay.php
index 01a5329bc700..b3eb136ba236 100644
--- a/app/PaymentDrivers/Stripe/Alipay.php
+++ b/app/PaymentDrivers/Stripe/Alipay.php
@@ -33,7 +33,6 @@ class Alipay
public function paymentView(array $data)
{
-
$intent = \Stripe\PaymentIntent::create([
'amount' => $this->stripe->convertToStripeAmount($data['total']['amount_with_fee'], $this->stripe->client->currency()->precision, $this->stripe->client->currency()),
'currency' => $this->stripe->client->currency()->code,
@@ -76,8 +75,7 @@ class Alipay
$this->stripe->payment_hash->data = array_merge((array) $this->stripe->payment_hash->data, $request->all());
$this->stripe->payment_hash->save();
- if($request->payment_intent){
-
+ if ($request->payment_intent) {
$pi = \Stripe\PaymentIntent::retrieve(
$request->payment_intent,
$this->stripe->stripe_connect_auth
@@ -89,10 +87,9 @@ class Alipay
return $this->processSuccesfulRedirect($pi);
}
- if($pi->status == 'requires_source_action') {
+ if ($pi->status == 'requires_source_action') {
return redirect($pi->next_action->alipay_handle_redirect->url);
}
-
}
return $this->processUnsuccesfulRedirect();
diff --git a/app/PaymentDrivers/Stripe/BACS.php b/app/PaymentDrivers/Stripe/BACS.php
index b7fde1e47b30..3e649eef124b 100644
--- a/app/PaymentDrivers/Stripe/BACS.php
+++ b/app/PaymentDrivers/Stripe/BACS.php
@@ -20,12 +20,10 @@ use App\Models\GatewayType;
use App\Models\Payment;
use App\Models\PaymentType;
use App\Models\SystemLog;
-use App\PaymentDrivers\StripePaymentDriver;
use App\PaymentDrivers\Stripe\Jobs\UpdateCustomer;
-use Stripe\Checkout\Session;
-use Stripe\PaymentIntent;
-use Stripe\PaymentMethod;
+use App\PaymentDrivers\StripePaymentDriver;
use App\Utils\Number;
+use Stripe\Checkout\Session;
class BACS
{
@@ -78,7 +76,6 @@ class BACS
return render('gateways.stripe.bacs.pay', $data);
}
public function paymentResponse(PaymentResponseRequest $request)
-
{
$this->stripe->init();
$invoice_numbers = collect($this->stripe->payment_hash->invoices())->pluck('invoice_number')->implode(',');
@@ -183,7 +180,7 @@ class BACS
$clientgateway = ClientGatewayToken::query()
->where('token', $method->id)
->first();
- if (!$clientgateway){
+ if (!$clientgateway) {
$this->stripe->storeGatewayToken($data, ['gateway_customer_reference' => $customer->id]);
}
} catch (\Exception $e) {
diff --git a/app/PaymentDrivers/Stripe/Charge.php b/app/PaymentDrivers/Stripe/Charge.php
index da7263502309..fbed56e34e41 100644
--- a/app/PaymentDrivers/Stripe/Charge.php
+++ b/app/PaymentDrivers/Stripe/Charge.php
@@ -136,15 +136,11 @@ class Charge
if ($cgt->gateway_type_id == GatewayType::SEPA) {
$payment_method_type = PaymentType::SEPA;
$status = Payment::STATUS_PENDING;
-
- } elseif ($cgt->gateway_type_id == GatewayType::BACS){
+ } elseif ($cgt->gateway_type_id == GatewayType::BACS) {
$payment_method_type = PaymentType::BACS;
$status = Payment::STATUS_PENDING;
- }
- else {
-
- if(isset($response->latest_charge)) {
-
+ } else {
+ if (isset($response->latest_charge)) {
$charge = \Stripe\Charge::retrieve($response->latest_charge, $this->stripe->stripe_connect_auth);
$payment_method_type = $charge->payment_method_details->card->brand;
} elseif (isset($response->charges->data[0]->payment_method_details->card->brand)) {
@@ -157,9 +153,8 @@ class Charge
}
- if(!in_array($response?->status, ['succeeded', 'processing'])){
- $this->stripe->processInternallyFailedPayment($this->stripe, new \Exception('Auto billing failed.',400));
-
+ if (!in_array($response?->status, ['succeeded', 'processing'])) {
+ $this->stripe->processInternallyFailedPayment($this->stripe, new \Exception('Auto billing failed.', 400));
}
$data = [
diff --git a/app/PaymentDrivers/Stripe/CreditCard.php b/app/PaymentDrivers/Stripe/CreditCard.php
index e53ffe3da27f..7816e3c9a9f3 100644
--- a/app/PaymentDrivers/Stripe/CreditCard.php
+++ b/app/PaymentDrivers/Stripe/CreditCard.php
@@ -21,7 +21,6 @@ use App\Models\PaymentType;
use App\Models\SystemLog;
use App\PaymentDrivers\Stripe\Jobs\UpdateCustomer;
use App\PaymentDrivers\StripePaymentDriver;
-use App\Utils\Number;
use Stripe\PaymentIntent;
use Stripe\PaymentMethod;
diff --git a/app/PaymentDrivers/Stripe/Jobs/PaymentIntentPartiallyFundedWebhook.php b/app/PaymentDrivers/Stripe/Jobs/PaymentIntentPartiallyFundedWebhook.php
index 382ac5569110..d30fa0695581 100644
--- a/app/PaymentDrivers/Stripe/Jobs/PaymentIntentPartiallyFundedWebhook.php
+++ b/app/PaymentDrivers/Stripe/Jobs/PaymentIntentPartiallyFundedWebhook.php
@@ -50,7 +50,7 @@ class PaymentIntentPartiallyFundedWebhook implements ShouldQueue
$payment_intent = $transaction['id'];
}
- if(!$payment_intent){
+ if (!$payment_intent) {
nlog("payment intent not found");
nlog($transaction);
return;
@@ -61,7 +61,7 @@ class PaymentIntentPartiallyFundedWebhook implements ShouldQueue
->where('transaction_reference', $payment_intent)
->first();
- if(!$payment){
+ if (!$payment) {
nlog("paymentintent found but no payment");
}
diff --git a/app/PaymentDrivers/Stripe/Jobs/PaymentIntentProcessingWebhook.php b/app/PaymentDrivers/Stripe/Jobs/PaymentIntentProcessingWebhook.php
index 5725e56dc95f..28f3b92c5d4c 100644
--- a/app/PaymentDrivers/Stripe/Jobs/PaymentIntentProcessingWebhook.php
+++ b/app/PaymentDrivers/Stripe/Jobs/PaymentIntentProcessingWebhook.php
@@ -79,11 +79,10 @@ class PaymentIntentProcessingWebhook implements ShouldQueue
$this->payment_completed = true;
}
- if(isset($transaction['payment_method']))
- {
+ if (isset($transaction['payment_method'])) {
$cgt = ClientGatewayToken::where('token', $transaction['payment_method'])->first();
- if($cgt && $cgt->meta?->state == 'unauthorized'){
+ if ($cgt && $cgt->meta?->state == 'unauthorized') {
$meta = $cgt->meta;
$meta->state = 'authorized';
$cgt->meta = $meta;
diff --git a/app/PaymentDrivers/Stripe/Jobs/PaymentIntentWebhook.php b/app/PaymentDrivers/Stripe/Jobs/PaymentIntentWebhook.php
index 5f04159130f8..70417665ae49 100644
--- a/app/PaymentDrivers/Stripe/Jobs/PaymentIntentWebhook.php
+++ b/app/PaymentDrivers/Stripe/Jobs/PaymentIntentWebhook.php
@@ -120,9 +120,8 @@ class PaymentIntentWebhook implements ShouldQueue
->where('transaction_reference', $charge['id'])
->first();
- //return early
- if($payment && $payment->status_id == Payment::STATUS_COMPLETED){
-
+ //return early
+ if ($payment && $payment->status_id == Payment::STATUS_COMPLETED) {
nlog(" payment found and status correct - returning ");
return;
} elseif ($payment) {
@@ -188,11 +187,9 @@ class PaymentIntentWebhook implements ShouldQueue
}
$this->updateAchPayment($payment_hash, $client, $meta);
- } elseif(isset($pi['payment_method_types']) && in_array('bacs_debit', $pi['payment_method_types'])){
+ } elseif (isset($pi['payment_method_types']) && in_array('bacs_debit', $pi['payment_method_types'])) {
return;
}
-
-
}
private function updateAchPayment($payment_hash, $client, $meta)
@@ -260,9 +257,7 @@ class PaymentIntentWebhook implements ShouldQueue
}
$driver->storeGatewayToken($data, $additional_data);
-
} catch(\Exception $e) {
-
nlog("failed to import payment methods");
nlog($e->getMessage());
}
@@ -297,5 +292,4 @@ class PaymentIntentWebhook implements ShouldQueue
$client->company,
);
}
-
}
diff --git a/app/PaymentDrivers/Stripe/Klarna.php b/app/PaymentDrivers/Stripe/Klarna.php
index c794a4e22b53..97067dfb2c9c 100644
--- a/app/PaymentDrivers/Stripe/Klarna.php
+++ b/app/PaymentDrivers/Stripe/Klarna.php
@@ -19,7 +19,6 @@ use App\Models\Payment;
use App\Models\PaymentType;
use App\Models\SystemLog;
use App\PaymentDrivers\StripePaymentDriver;
-use App\Utils\Number;
class Klarna
{
diff --git a/app/PaymentDrivers/Stripe/UpdatePaymentMethods.php b/app/PaymentDrivers/Stripe/UpdatePaymentMethods.php
index 6034f62ba448..a06daa855b50 100644
--- a/app/PaymentDrivers/Stripe/UpdatePaymentMethods.php
+++ b/app/PaymentDrivers/Stripe/UpdatePaymentMethods.php
@@ -99,7 +99,6 @@ class UpdatePaymentMethods
/* Already exists return */
if ($token) {
-
$meta = $token->meta;
$meta->state = 'authorized';
$token->meta = $meta;
diff --git a/app/PaymentDrivers/StripePaymentDriver.php b/app/PaymentDrivers/StripePaymentDriver.php
index ee187536c11b..8e813802b13c 100644
--- a/app/PaymentDrivers/StripePaymentDriver.php
+++ b/app/PaymentDrivers/StripePaymentDriver.php
@@ -12,55 +12,54 @@
namespace App\PaymentDrivers;
-use Exception;
-use Stripe\Stripe;
-use Stripe\Account;
-use Stripe\Customer;
-use App\Models\Payment;
-use Stripe\SetupIntent;
-use Stripe\StripeClient;
-use App\Models\SystemLog;
-use Stripe\PaymentIntent;
-use Stripe\PaymentMethod;
-use App\Models\GatewayType;
-use App\Models\PaymentHash;
+use App\Exceptions\PaymentFailed;
+use App\Exceptions\StripeConnectFailure;
+use App\Http\Requests\Payments\PaymentWebhookRequest;
use App\Http\Requests\Request;
use App\Jobs\Util\SystemLogger;
use App\Models\Client;
-use App\Utils\Traits\MakesHash;
-use App\Exceptions\PaymentFailed;
use App\Models\ClientGatewayToken;
+use App\Models\GatewayType;
+use App\Models\Payment;
+use App\Models\PaymentHash;
+use App\Models\SystemLog;
use App\PaymentDrivers\Stripe\ACH;
-use App\PaymentDrivers\Stripe\EPS;
-use App\PaymentDrivers\Stripe\FPX;
use App\PaymentDrivers\Stripe\ACSS;
use App\PaymentDrivers\Stripe\Alipay;
use App\PaymentDrivers\Stripe\BACS;
-use App\PaymentDrivers\Stripe\BECS;
-use App\PaymentDrivers\Stripe\SEPA;
-use App\PaymentDrivers\Stripe\iDeal;
-use App\PaymentDrivers\Stripe\Charge;
-use App\PaymentDrivers\Stripe\Klarna;
-use App\PaymentDrivers\Stripe\SOFORT;
-use Illuminate\Http\RedirectResponse;
-use App\PaymentDrivers\Stripe\GIROPAY;
-use Stripe\Exception\ApiErrorException;
-use App\Exceptions\StripeConnectFailure;
-use App\PaymentDrivers\Stripe\Utilities;
use App\PaymentDrivers\Stripe\Bancontact;
-use App\PaymentDrivers\Stripe\BrowserPay;
-use App\PaymentDrivers\Stripe\CreditCard;
-use App\PaymentDrivers\Stripe\PRZELEWY24;
use App\PaymentDrivers\Stripe\BankTransfer;
+use App\PaymentDrivers\Stripe\BECS;
+use App\PaymentDrivers\Stripe\BrowserPay;
+use App\PaymentDrivers\Stripe\Charge;
use App\PaymentDrivers\Stripe\Connect\Verify;
+use App\PaymentDrivers\Stripe\CreditCard;
+use App\PaymentDrivers\Stripe\EPS;
+use App\PaymentDrivers\Stripe\FPX;
+use App\PaymentDrivers\Stripe\GIROPAY;
+use App\PaymentDrivers\Stripe\iDeal;
use App\PaymentDrivers\Stripe\ImportCustomers;
-use App\Http\Requests\Payments\PaymentWebhookRequest;
-use Laracasts\Presenter\Exceptions\PresenterException;
-use App\PaymentDrivers\Stripe\Jobs\PaymentIntentWebhook;
use App\PaymentDrivers\Stripe\Jobs\PaymentIntentFailureWebhook;
-use App\PaymentDrivers\Stripe\Jobs\PaymentIntentProcessingWebhook;
use App\PaymentDrivers\Stripe\Jobs\PaymentIntentPartiallyFundedWebhook;
-
+use App\PaymentDrivers\Stripe\Jobs\PaymentIntentProcessingWebhook;
+use App\PaymentDrivers\Stripe\Jobs\PaymentIntentWebhook;
+use App\PaymentDrivers\Stripe\Klarna;
+use App\PaymentDrivers\Stripe\PRZELEWY24;
+use App\PaymentDrivers\Stripe\SEPA;
+use App\PaymentDrivers\Stripe\SOFORT;
+use App\PaymentDrivers\Stripe\Utilities;
+use App\Utils\Traits\MakesHash;
+use Exception;
+use Illuminate\Http\RedirectResponse;
+use Laracasts\Presenter\Exceptions\PresenterException;
+use Stripe\Account;
+use Stripe\Customer;
+use Stripe\Exception\ApiErrorException;
+use Stripe\PaymentIntent;
+use Stripe\PaymentMethod;
+use Stripe\SetupIntent;
+use Stripe\Stripe;
+use Stripe\StripeClient;
class StripePaymentDriver extends BaseDriver
{
@@ -446,11 +445,10 @@ class StripePaymentDriver extends BaseDriver
{
$this->init();
- return PaymentIntent::retrieve(
- $payment_intent_id,
- $this->stripe_connect_auth
- );
-
+ return PaymentIntent::retrieve(
+ $payment_intent_id,
+ $this->stripe_connect_auth
+ );
}
/**
@@ -667,7 +665,6 @@ class StripePaymentDriver extends BaseDriver
public function processWebhookRequest(PaymentWebhookRequest $request)
{
-
if ($request->type === 'customer.source.updated') {
$ach = new ACH($this);
$ach->updateBankAccount($request->all());
@@ -754,12 +751,11 @@ class StripePaymentDriver extends BaseDriver
}
}
}
- } elseif ($request->type === "payment_method.automatically_updated"){
+ } elseif ($request->type === "payment_method.automatically_updated") {
// Will notify customer on updated information
return response()->json([], 200);
- } elseif ($request->type === "mandate.updated"){
-
- if ($request->data['object']['status'] == "active"){
+ } elseif ($request->type === "mandate.updated") {
+ if ($request->data['object']['status'] == "active") {
// Check if payment method existsn
$payment_method = (string) $request->data['object']['payment_method'];
@@ -767,18 +763,15 @@ class StripePaymentDriver extends BaseDriver
->where('token', $payment_method)
->first();
- if ($clientgateway){
-
+ if ($clientgateway) {
$meta = $clientgateway->meta;
$meta->state = 'authorized';
$clientgateway->meta = $meta;
$clientgateway->save();
-
}
return response()->json([], 200);
- }
- elseif ($request->data['object']['status'] == "inactive" && $request->data['object']['payment_method']){
+ } elseif ($request->data['object']['status'] == "inactive" && $request->data['object']['payment_method']) {
// Delete payment method
$clientgateway = ClientGatewayToken::query()
->where('token', $request->data['object']['payment_method'])
@@ -787,8 +780,7 @@ class StripePaymentDriver extends BaseDriver
$clientgateway->delete();
return response()->json([], 200);
- }
- elseif ($request->data['object']['status'] == "pending"){
+ } elseif ($request->data['object']['status'] == "pending") {
return response()->json([], 200);
}
}
diff --git a/app/Providers/EventServiceProvider.php b/app/Providers/EventServiceProvider.php
index ae34c09620cd..1028a0c943cc 100644
--- a/app/Providers/EventServiceProvider.php
+++ b/app/Providers/EventServiceProvider.php
@@ -11,259 +11,259 @@
namespace App\Providers;
-use App\Models\Task;
-use App\Models\User;
-use App\Models\Quote;
-use App\Models\Client;
-use App\Models\Credit;
-use App\Models\Vendor;
+use App\Events\Account\AccountCreated;
+use App\Events\Client\ClientWasArchived;
+use App\Events\Client\ClientWasCreated;
+use App\Events\Client\ClientWasDeleted;
+use App\Events\Client\ClientWasRestored;
+use App\Events\Client\ClientWasUpdated;
+use App\Events\Client\DesignWasDeleted;
+use App\Events\Client\DesignWasRestored;
+use App\Events\Client\DesignWasUpdated;
+use App\Events\Company\CompanyDocumentsDeleted;
+use App\Events\Contact\ContactLoggedIn;
+use App\Events\Credit\CreditWasArchived;
+use App\Events\Credit\CreditWasCreated;
+use App\Events\Credit\CreditWasDeleted;
+use App\Events\Credit\CreditWasEmailed;
+use App\Events\Credit\CreditWasEmailedAndFailed;
+use App\Events\Credit\CreditWasMarkedSent;
+use App\Events\Credit\CreditWasRestored;
+use App\Events\Credit\CreditWasUpdated;
+use App\Events\Credit\CreditWasViewed;
+use App\Events\Design\DesignWasArchived;
+use App\Events\Expense\ExpenseWasArchived;
+use App\Events\Expense\ExpenseWasCreated;
+use App\Events\Expense\ExpenseWasDeleted;
+use App\Events\Expense\ExpenseWasRestored;
+use App\Events\Expense\ExpenseWasUpdated;
+use App\Events\Invoice\InvoiceReminderWasEmailed;
+use App\Events\Invoice\InvoiceWasArchived;
+use App\Events\Invoice\InvoiceWasCancelled;
+use App\Events\Invoice\InvoiceWasCreated;
+use App\Events\Invoice\InvoiceWasDeleted;
+use App\Events\Invoice\InvoiceWasEmailed;
+use App\Events\Invoice\InvoiceWasEmailedAndFailed;
+use App\Events\Invoice\InvoiceWasMarkedSent;
+use App\Events\Invoice\InvoiceWasPaid;
+use App\Events\Invoice\InvoiceWasRestored;
+use App\Events\Invoice\InvoiceWasReversed;
+use App\Events\Invoice\InvoiceWasUpdated;
+use App\Events\Invoice\InvoiceWasViewed;
+use App\Events\Misc\InvitationWasViewed;
+use App\Events\Payment\PaymentWasArchived;
+use App\Events\Payment\PaymentWasCreated;
+use App\Events\Payment\PaymentWasDeleted;
+use App\Events\Payment\PaymentWasEmailed;
+use App\Events\Payment\PaymentWasEmailedAndFailed;
+use App\Events\Payment\PaymentWasRefunded;
+use App\Events\Payment\PaymentWasRestored;
+use App\Events\Payment\PaymentWasUpdated;
+use App\Events\Payment\PaymentWasVoided;
+use App\Events\PurchaseOrder\PurchaseOrderWasAccepted;
+use App\Events\PurchaseOrder\PurchaseOrderWasArchived;
+use App\Events\PurchaseOrder\PurchaseOrderWasCreated;
+use App\Events\PurchaseOrder\PurchaseOrderWasDeleted;
+use App\Events\PurchaseOrder\PurchaseOrderWasEmailed;
+use App\Events\PurchaseOrder\PurchaseOrderWasRestored;
+use App\Events\PurchaseOrder\PurchaseOrderWasUpdated;
+use App\Events\PurchaseOrder\PurchaseOrderWasViewed;
+use App\Events\Quote\QuoteWasApproved;
+use App\Events\Quote\QuoteWasArchived;
+use App\Events\Quote\QuoteWasCreated;
+use App\Events\Quote\QuoteWasDeleted;
+use App\Events\Quote\QuoteWasEmailed;
+use App\Events\Quote\QuoteWasRestored;
+use App\Events\Quote\QuoteWasUpdated;
+use App\Events\Quote\QuoteWasViewed;
+use App\Events\RecurringExpense\RecurringExpenseWasArchived;
+use App\Events\RecurringExpense\RecurringExpenseWasCreated;
+use App\Events\RecurringExpense\RecurringExpenseWasDeleted;
+use App\Events\RecurringExpense\RecurringExpenseWasRestored;
+use App\Events\RecurringExpense\RecurringExpenseWasUpdated;
+use App\Events\RecurringInvoice\RecurringInvoiceWasArchived;
+use App\Events\RecurringInvoice\RecurringInvoiceWasCreated;
+use App\Events\RecurringInvoice\RecurringInvoiceWasDeleted;
+use App\Events\RecurringInvoice\RecurringInvoiceWasRestored;
+use App\Events\RecurringInvoice\RecurringInvoiceWasUpdated;
+use App\Events\RecurringQuote\RecurringQuoteWasArchived;
+use App\Events\RecurringQuote\RecurringQuoteWasCreated;
+use App\Events\RecurringQuote\RecurringQuoteWasDeleted;
+use App\Events\RecurringQuote\RecurringQuoteWasRestored;
+use App\Events\RecurringQuote\RecurringQuoteWasUpdated;
+use App\Events\Subscription\SubscriptionWasArchived;
+use App\Events\Subscription\SubscriptionWasCreated;
+use App\Events\Subscription\SubscriptionWasDeleted;
+use App\Events\Subscription\SubscriptionWasRestored;
+use App\Events\Subscription\SubscriptionWasUpdated;
+use App\Events\Task\TaskWasArchived;
+use App\Events\Task\TaskWasCreated;
+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;
+use App\Events\Vendor\VendorWasRestored;
+use App\Events\Vendor\VendorWasUpdated;
+use App\Listeners\Activity\ArchivedClientActivity;
+use App\Listeners\Activity\ClientUpdatedActivity;
+use App\Listeners\Activity\CreatedClientActivity;
+use App\Listeners\Activity\CreatedCreditActivity;
+use App\Listeners\Activity\CreatedExpenseActivity;
+use App\Listeners\Activity\CreatedQuoteActivity;
+use App\Listeners\Activity\CreatedSubscriptionActivity;
+use App\Listeners\Activity\CreatedTaskActivity;
+use App\Listeners\Activity\CreatedVendorActivity;
+use App\Listeners\Activity\CreditArchivedActivity;
+use App\Listeners\Activity\DeleteClientActivity;
+use App\Listeners\Activity\DeleteCreditActivity;
+use App\Listeners\Activity\ExpenseArchivedActivity;
+use App\Listeners\Activity\ExpenseDeletedActivity;
+use App\Listeners\Activity\ExpenseRestoredActivity;
+use App\Listeners\Activity\ExpenseUpdatedActivity;
+use App\Listeners\Activity\PaymentArchivedActivity;
+use App\Listeners\Activity\PaymentCreatedActivity;
+use App\Listeners\Activity\PaymentDeletedActivity;
+use App\Listeners\Activity\PaymentRefundedActivity;
+use App\Listeners\Activity\PaymentUpdatedActivity;
+use App\Listeners\Activity\PaymentVoidedActivity;
+use App\Listeners\Activity\QuoteUpdatedActivity;
+use App\Listeners\Activity\RestoreClientActivity;
+use App\Listeners\Activity\SubscriptionArchivedActivity;
+use App\Listeners\Activity\SubscriptionDeletedActivity;
+use App\Listeners\Activity\SubscriptionRestoredActivity;
+use App\Listeners\Activity\SubscriptionUpdatedActivity;
+use App\Listeners\Activity\TaskArchivedActivity;
+use App\Listeners\Activity\TaskDeletedActivity;
+use App\Listeners\Activity\TaskRestoredActivity;
+use App\Listeners\Activity\TaskUpdatedActivity;
+use App\Listeners\Activity\UpdatedCreditActivity;
+use App\Listeners\Activity\VendorArchivedActivity;
+use App\Listeners\Activity\VendorDeletedActivity;
+use App\Listeners\Activity\VendorRestoredActivity;
+use App\Listeners\Activity\VendorUpdatedActivity;
+use App\Listeners\Contact\UpdateContactLastLogin;
+use App\Listeners\Credit\CreditCreatedNotification;
+use App\Listeners\Credit\CreditEmailedNotification;
+use App\Listeners\Credit\CreditRestoredActivity;
+use App\Listeners\Credit\CreditViewedActivity;
+use App\Listeners\Document\DeleteCompanyDocuments;
+use App\Listeners\Invoice\CreateInvoiceActivity;
+use App\Listeners\Invoice\CreateInvoicePdf;
+use App\Listeners\Invoice\InvoiceArchivedActivity;
+use App\Listeners\Invoice\InvoiceCancelledActivity;
+use App\Listeners\Invoice\InvoiceCreatedNotification;
+use App\Listeners\Invoice\InvoiceDeletedActivity;
+use App\Listeners\Invoice\InvoiceEmailActivity;
+use App\Listeners\Invoice\InvoiceEmailedNotification;
+use App\Listeners\Invoice\InvoiceEmailFailedActivity;
+use App\Listeners\Invoice\InvoiceFailedEmailNotification;
+use App\Listeners\Invoice\InvoicePaidActivity;
+use App\Listeners\Invoice\InvoiceReminderEmailActivity;
+use App\Listeners\Invoice\InvoiceRestoredActivity;
+use App\Listeners\Invoice\InvoiceReversedActivity;
+use App\Listeners\Invoice\InvoiceViewedActivity;
+use App\Listeners\Invoice\UpdateInvoiceActivity;
+use App\Listeners\Mail\MailSentListener;
+use App\Listeners\Misc\InvitationViewedListener;
+use App\Listeners\Payment\PaymentBalanceActivity;
+use App\Listeners\Payment\PaymentEmailedActivity;
+use App\Listeners\Payment\PaymentNotification;
+use App\Listeners\Payment\PaymentRestoredActivity;
+use App\Listeners\PurchaseOrder\CreatePurchaseOrderActivity;
+use App\Listeners\PurchaseOrder\PurchaseOrderAcceptedActivity;
+use App\Listeners\PurchaseOrder\PurchaseOrderAcceptedListener;
+use App\Listeners\PurchaseOrder\PurchaseOrderArchivedActivity;
+use App\Listeners\PurchaseOrder\PurchaseOrderCreatedListener;
+use App\Listeners\PurchaseOrder\PurchaseOrderDeletedActivity;
+use App\Listeners\PurchaseOrder\PurchaseOrderEmailActivity;
+use App\Listeners\PurchaseOrder\PurchaseOrderEmailedNotification;
+use App\Listeners\PurchaseOrder\PurchaseOrderRestoredActivity;
+use App\Listeners\PurchaseOrder\PurchaseOrderViewedActivity;
+use App\Listeners\PurchaseOrder\UpdatePurchaseOrderActivity;
+use App\Listeners\Quote\QuoteApprovedActivity;
+use App\Listeners\Quote\QuoteApprovedNotification;
+use App\Listeners\Quote\QuoteApprovedWebhook;
+use App\Listeners\Quote\QuoteArchivedActivity;
+use App\Listeners\Quote\QuoteCreatedNotification;
+use App\Listeners\Quote\QuoteDeletedActivity;
+use App\Listeners\Quote\QuoteEmailActivity;
+use App\Listeners\Quote\QuoteEmailedNotification;
+use App\Listeners\Quote\QuoteRestoredActivity;
+use App\Listeners\Quote\QuoteViewedActivity;
+use App\Listeners\Quote\ReachWorkflowSettings;
+use App\Listeners\RecurringExpense\CreatedRecurringExpenseActivity;
+use App\Listeners\RecurringExpense\RecurringExpenseArchivedActivity;
+use App\Listeners\RecurringExpense\RecurringExpenseDeletedActivity;
+use App\Listeners\RecurringExpense\RecurringExpenseRestoredActivity;
+use App\Listeners\RecurringExpense\RecurringExpenseUpdatedActivity;
+use App\Listeners\RecurringInvoice\CreateRecurringInvoiceActivity;
+use App\Listeners\RecurringInvoice\RecurringInvoiceArchivedActivity;
+use App\Listeners\RecurringInvoice\RecurringInvoiceDeletedActivity;
+use App\Listeners\RecurringInvoice\RecurringInvoiceRestoredActivity;
+use App\Listeners\RecurringInvoice\UpdateRecurringInvoiceActivity;
+use App\Listeners\RecurringQuote\CreateRecurringQuoteActivity;
+use App\Listeners\RecurringQuote\RecurringQuoteArchivedActivity;
+use App\Listeners\RecurringQuote\RecurringQuoteDeletedActivity;
+use App\Listeners\RecurringQuote\RecurringQuoteRestoredActivity;
+use App\Listeners\RecurringQuote\UpdateRecurringQuoteActivity;
+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\UpdatedUserActivity;
+use App\Listeners\User\UpdateUserLastLogin;
use App\Models\Account;
+use App\Models\Client;
+use App\Models\ClientContact;
use App\Models\Company;
+use App\Models\CompanyGateway;
+use App\Models\CompanyToken;
+use App\Models\Credit;
use App\Models\Expense;
use App\Models\Invoice;
use App\Models\Payment;
use App\Models\Product;
use App\Models\Project;
use App\Models\Proposal;
-use App\Models\CompanyToken;
-use App\Models\Subscription;
-use App\Models\ClientContact;
use App\Models\PurchaseOrder;
+use App\Models\Quote;
+use App\Models\Subscription;
+use App\Models\Task;
+use App\Models\User;
+use App\Models\Vendor;
use App\Models\VendorContact;
-use App\Models\CompanyGateway;
-use App\Observers\TaskObserver;
-use App\Observers\UserObserver;
-use App\Observers\QuoteObserver;
-use App\Events\User\UserLoggedIn;
-use App\Observers\ClientObserver;
-use App\Observers\CreditObserver;
-use App\Observers\VendorObserver;
use App\Observers\AccountObserver;
+use App\Observers\ClientContactObserver;
+use App\Observers\ClientObserver;
+use App\Observers\CompanyGatewayObserver;
use App\Observers\CompanyObserver;
+use App\Observers\CompanyTokenObserver;
+use App\Observers\CreditObserver;
use App\Observers\ExpenseObserver;
use App\Observers\InvoiceObserver;
use App\Observers\PaymentObserver;
use App\Observers\ProductObserver;
use App\Observers\ProjectObserver;
-use App\Events\Task\TaskWasCreated;
-use App\Events\Task\TaskWasDeleted;
-use App\Events\Task\TaskWasUpdated;
-use App\Events\User\UserWasCreated;
-use App\Events\User\UserWasDeleted;
-use App\Events\User\UserWasUpdated;
use App\Observers\ProposalObserver;
-use App\Events\Quote\QuoteWasViewed;
-use App\Events\Task\TaskWasArchived;
-use App\Events\Task\TaskWasRestored;
-use App\Events\User\UserWasArchived;
-use App\Events\User\UserWasRestored;
-use App\Events\Quote\QuoteWasCreated;
-use App\Events\Quote\QuoteWasDeleted;
-use App\Events\Quote\QuoteWasEmailed;
-use App\Events\Quote\QuoteWasUpdated;
-use App\Events\Account\AccountCreated;
-use App\Events\Credit\CreditWasViewed;
-use App\Events\Invoice\InvoiceWasPaid;
-use App\Events\Quote\QuoteWasApproved;
-use App\Events\Quote\QuoteWasArchived;
-use App\Events\Quote\QuoteWasRestored;
-use App\Events\Client\ClientWasCreated;
-use App\Events\Client\ClientWasDeleted;
-use App\Events\Client\ClientWasUpdated;
-use App\Events\Client\DesignWasDeleted;
-use App\Events\Client\DesignWasUpdated;
-use App\Events\Contact\ContactLoggedIn;
-use App\Events\Credit\CreditWasCreated;
-use App\Events\Credit\CreditWasDeleted;
-use App\Events\Credit\CreditWasEmailed;
-use App\Events\Credit\CreditWasUpdated;
-use App\Events\Vendor\VendorWasCreated;
-use App\Events\Vendor\VendorWasDeleted;
-use App\Events\Vendor\VendorWasUpdated;
-use App\Observers\CompanyTokenObserver;
-use App\Observers\SubscriptionObserver;
-use Illuminate\Mail\Events\MessageSent;
-use App\Events\Client\ClientWasArchived;
-use App\Events\Client\ClientWasRestored;
-use App\Events\Client\DesignWasRestored;
-use App\Events\Credit\CreditWasArchived;
-use App\Events\Credit\CreditWasRestored;
-use App\Events\Design\DesignWasArchived;
-use App\Events\Invoice\InvoiceWasViewed;
-use App\Events\Misc\InvitationWasViewed;
-use App\Events\Payment\PaymentWasVoided;
-use App\Events\Vendor\VendorWasArchived;
-use App\Events\Vendor\VendorWasRestored;
-use App\Listeners\Mail\MailSentListener;
-use App\Observers\ClientContactObserver;
use App\Observers\PurchaseOrderObserver;
+use App\Observers\QuoteObserver;
+use App\Observers\SubscriptionObserver;
+use App\Observers\TaskObserver;
+use App\Observers\UserObserver;
use App\Observers\VendorContactObserver;
-use App\Events\Expense\ExpenseWasCreated;
-use App\Events\Expense\ExpenseWasDeleted;
-use App\Events\Expense\ExpenseWasUpdated;
-use App\Events\Invoice\InvoiceWasCreated;
-use App\Events\Invoice\InvoiceWasDeleted;
-use App\Events\Invoice\InvoiceWasEmailed;
-use App\Events\Invoice\InvoiceWasUpdated;
-use App\Events\Payment\PaymentWasCreated;
-use App\Events\Payment\PaymentWasDeleted;
-use App\Events\Payment\PaymentWasEmailed;
-use App\Events\Payment\PaymentWasUpdated;
-use App\Observers\CompanyGatewayObserver;
-use App\Events\Credit\CreditWasMarkedSent;
-use App\Events\Expense\ExpenseWasArchived;
-use App\Events\Expense\ExpenseWasRestored;
-use App\Events\Invoice\InvoiceWasArchived;
-use App\Events\Invoice\InvoiceWasRestored;
-use App\Events\Invoice\InvoiceWasReversed;
-use App\Events\Payment\PaymentWasArchived;
-use App\Events\Payment\PaymentWasRefunded;
-use App\Events\Payment\PaymentWasRestored;
-use Illuminate\Mail\Events\MessageSending;
-use App\Events\Invoice\InvoiceWasCancelled;
-use App\Listeners\Invoice\CreateInvoicePdf;
-use App\Listeners\Quote\QuoteEmailActivity;
-use App\Listeners\User\CreatedUserActivity;
-use App\Listeners\User\DeletedUserActivity;
-use App\Listeners\User\UpdatedUserActivity;
-use App\Listeners\User\UpdateUserLastLogin;
-use App\Events\Invoice\InvoiceWasMarkedSent;
-use App\Listeners\Quote\QuoteViewedActivity;
-use App\Listeners\User\ArchivedUserActivity;
-use App\Listeners\User\RestoredUserActivity;
-use App\Listeners\Quote\QuoteApprovedWebhook;
-use App\Listeners\Quote\QuoteDeletedActivity;
-use App\Listeners\Credit\CreditViewedActivity;
-use App\Listeners\Invoice\InvoicePaidActivity;
-use App\Listeners\Payment\PaymentNotification;
-use App\Listeners\Quote\QuoteApprovedActivity;
-use App\Listeners\Quote\QuoteArchivedActivity;
-use App\Listeners\Quote\QuoteRestoredActivity;
-use App\Listeners\Quote\ReachWorkflowSettings;
-use App\Events\Company\CompanyDocumentsDeleted;
-use App\Listeners\Activity\CreatedTaskActivity;
-use App\Listeners\Activity\TaskDeletedActivity;
-use App\Listeners\Activity\TaskUpdatedActivity;
-use App\Listeners\Invoice\InvoiceEmailActivity;
-use App\Listeners\SendVerificationNotification;
-use App\Events\Credit\CreditWasEmailedAndFailed;
-use App\Listeners\Activity\CreatedQuoteActivity;
-use App\Listeners\Activity\DeleteClientActivity;
-use App\Listeners\Activity\DeleteCreditActivity;
-use App\Listeners\Activity\QuoteUpdatedActivity;
-use App\Listeners\Activity\TaskArchivedActivity;
-use App\Listeners\Activity\TaskRestoredActivity;
-use App\Listeners\Credit\CreditRestoredActivity;
-use App\Listeners\Invoice\CreateInvoiceActivity;
-use App\Listeners\Invoice\InvoiceViewedActivity;
-use App\Listeners\Invoice\UpdateInvoiceActivity;
-use App\Listeners\Misc\InvitationViewedListener;
-use App\Events\Invoice\InvoiceReminderWasEmailed;
-use App\Listeners\Activity\ClientUpdatedActivity;
-use App\Listeners\Activity\CreatedClientActivity;
-use App\Listeners\Activity\CreatedCreditActivity;
-use App\Listeners\Activity\CreatedVendorActivity;
-use App\Listeners\Activity\PaymentVoidedActivity;
-use App\Listeners\Activity\RestoreClientActivity;
-use App\Listeners\Activity\UpdatedCreditActivity;
-use App\Listeners\Activity\VendorDeletedActivity;
-use App\Listeners\Activity\VendorUpdatedActivity;
-use App\Listeners\Contact\UpdateContactLastLogin;
-use App\Listeners\Invoice\InvoiceDeletedActivity;
-use App\Listeners\Payment\PaymentBalanceActivity;
-use App\Listeners\Payment\PaymentEmailedActivity;
-use App\Listeners\Quote\QuoteCreatedNotification;
-use App\Listeners\Quote\QuoteEmailedNotification;
-use App\Events\Invoice\InvoiceWasEmailedAndFailed;
-use App\Events\Payment\PaymentWasEmailedAndFailed;
-use App\Listeners\Activity\ArchivedClientActivity;
-use App\Listeners\Activity\CreatedExpenseActivity;
-use App\Listeners\Activity\CreditArchivedActivity;
-use App\Listeners\Activity\ExpenseDeletedActivity;
-use App\Listeners\Activity\ExpenseUpdatedActivity;
-use App\Listeners\Activity\PaymentCreatedActivity;
-use App\Listeners\Activity\PaymentDeletedActivity;
-use App\Listeners\Activity\PaymentUpdatedActivity;
-use App\Listeners\Activity\VendorArchivedActivity;
-use App\Listeners\Activity\VendorRestoredActivity;
-use App\Listeners\Document\DeleteCompanyDocuments;
-use App\Listeners\Invoice\InvoiceArchivedActivity;
-use App\Listeners\Invoice\InvoiceRestoredActivity;
-use App\Listeners\Invoice\InvoiceReversedActivity;
-use App\Listeners\Payment\PaymentRestoredActivity;
-use App\Listeners\Quote\QuoteApprovedNotification;
-use App\Events\Subscription\SubscriptionWasCreated;
-use App\Events\Subscription\SubscriptionWasDeleted;
-use App\Events\Subscription\SubscriptionWasUpdated;
-use App\Listeners\Activity\ExpenseArchivedActivity;
-use App\Listeners\Activity\ExpenseRestoredActivity;
-use App\Listeners\Activity\PaymentArchivedActivity;
-use App\Listeners\Activity\PaymentRefundedActivity;
-use App\Listeners\Credit\CreditCreatedNotification;
-use App\Listeners\Credit\CreditEmailedNotification;
-use App\Listeners\Invoice\InvoiceCancelledActivity;
-use App\Events\PurchaseOrder\PurchaseOrderWasViewed;
-use App\Events\Subscription\SubscriptionWasArchived;
-use App\Events\Subscription\SubscriptionWasRestored;
-use App\Events\PurchaseOrder\PurchaseOrderWasCreated;
-use App\Events\PurchaseOrder\PurchaseOrderWasDeleted;
-use App\Events\PurchaseOrder\PurchaseOrderWasEmailed;
-use App\Events\PurchaseOrder\PurchaseOrderWasUpdated;
-use App\Listeners\Invoice\InvoiceCreatedNotification;
-use App\Listeners\Invoice\InvoiceEmailedNotification;
-use App\Listeners\Invoice\InvoiceEmailFailedActivity;
-use App\Events\PurchaseOrder\PurchaseOrderWasAccepted;
-use App\Events\PurchaseOrder\PurchaseOrderWasArchived;
-use App\Events\PurchaseOrder\PurchaseOrderWasRestored;
-use App\Events\RecurringQuote\RecurringQuoteWasCreated;
-use App\Events\RecurringQuote\RecurringQuoteWasDeleted;
-use App\Events\RecurringQuote\RecurringQuoteWasUpdated;
-use App\Listeners\Activity\CreatedSubscriptionActivity;
-use App\Listeners\Activity\SubscriptionDeletedActivity;
-use App\Listeners\Activity\SubscriptionUpdatedActivity;
-use App\Listeners\Invoice\InvoiceReminderEmailActivity;
-use App\Events\RecurringQuote\RecurringQuoteWasArchived;
-use App\Events\RecurringQuote\RecurringQuoteWasRestored;
-use App\Listeners\Activity\SubscriptionArchivedActivity;
-use App\Listeners\Activity\SubscriptionRestoredActivity;
-use App\Listeners\Invoice\InvoiceFailedEmailNotification;
-use App\Events\RecurringExpense\RecurringExpenseWasCreated;
-use App\Events\RecurringExpense\RecurringExpenseWasDeleted;
-use App\Events\RecurringExpense\RecurringExpenseWasUpdated;
-use App\Events\RecurringInvoice\RecurringInvoiceWasCreated;
-use App\Events\RecurringInvoice\RecurringInvoiceWasDeleted;
-use App\Events\RecurringInvoice\RecurringInvoiceWasUpdated;
-use App\Listeners\PurchaseOrder\PurchaseOrderEmailActivity;
-use App\Events\RecurringExpense\RecurringExpenseWasArchived;
-use App\Events\RecurringExpense\RecurringExpenseWasRestored;
-use App\Events\RecurringInvoice\RecurringInvoiceWasArchived;
-use App\Events\RecurringInvoice\RecurringInvoiceWasRestored;
-use App\Listeners\PurchaseOrder\CreatePurchaseOrderActivity;
-use App\Listeners\PurchaseOrder\PurchaseOrderViewedActivity;
-use App\Listeners\PurchaseOrder\UpdatePurchaseOrderActivity;
-use App\Listeners\PurchaseOrder\PurchaseOrderCreatedListener;
-use App\Listeners\PurchaseOrder\PurchaseOrderDeletedActivity;
-use App\Listeners\PurchaseOrder\PurchaseOrderAcceptedActivity;
-use App\Listeners\PurchaseOrder\PurchaseOrderAcceptedListener;
-use App\Listeners\PurchaseOrder\PurchaseOrderArchivedActivity;
-use App\Listeners\PurchaseOrder\PurchaseOrderRestoredActivity;
-use App\Listeners\RecurringQuote\CreateRecurringQuoteActivity;
-use App\Listeners\RecurringQuote\UpdateRecurringQuoteActivity;
-use App\Listeners\RecurringQuote\RecurringQuoteDeletedActivity;
-use App\Listeners\RecurringQuote\RecurringQuoteArchivedActivity;
-use App\Listeners\RecurringQuote\RecurringQuoteRestoredActivity;
-use App\Listeners\PurchaseOrder\PurchaseOrderEmailedNotification;
-use App\Listeners\RecurringInvoice\CreateRecurringInvoiceActivity;
-use App\Listeners\RecurringInvoice\UpdateRecurringInvoiceActivity;
-use App\Listeners\RecurringExpense\CreatedRecurringExpenseActivity;
-use App\Listeners\RecurringExpense\RecurringExpenseDeletedActivity;
-use App\Listeners\RecurringExpense\RecurringExpenseUpdatedActivity;
-use App\Listeners\RecurringInvoice\RecurringInvoiceDeletedActivity;
-use App\Listeners\RecurringExpense\RecurringExpenseArchivedActivity;
-use App\Listeners\RecurringExpense\RecurringExpenseRestoredActivity;
-use App\Listeners\RecurringInvoice\RecurringInvoiceArchivedActivity;
-use App\Listeners\RecurringInvoice\RecurringInvoiceRestoredActivity;
+use App\Observers\VendorObserver;
use Illuminate\Foundation\Support\Providers\EventServiceProvider as ServiceProvider;
+use Illuminate\Mail\Events\MessageSending;
+use Illuminate\Mail\Events\MessageSent;
class EventServiceProvider extends ServiceProvider
{
diff --git a/app/Providers/RouteServiceProvider.php b/app/Providers/RouteServiceProvider.php
index 73b6e6a118b0..44cd2b1b70a0 100644
--- a/app/Providers/RouteServiceProvider.php
+++ b/app/Providers/RouteServiceProvider.php
@@ -13,10 +13,14 @@ namespace App\Providers;
use App\Utils\Ninja;
use App\Models\Scheduler;
+use Illuminate\Http\Request;
use App\Utils\Traits\MakesHash;
use Illuminate\Support\Facades\Route;
use Illuminate\Cache\RateLimiting\Limit;
use Illuminate\Support\Facades\RateLimiter;
+use App\Http\Middleware\ThrottleRequestsWithPredis;
+use Illuminate\Routing\Middleware\ThrottleRequests;
+use Illuminate\Routing\Middleware\ThrottleRequestsWithRedis;
use Illuminate\Database\Eloquent\ModelNotFoundException as ModelNotFoundException;
use Illuminate\Foundation\Support\Providers\RouteServiceProvider as ServiceProvider;
@@ -32,6 +36,12 @@ class RouteServiceProvider extends ServiceProvider
public function boot()
{
parent::boot();
+
+ if (Ninja::isHosted() && !config('ninja.testvars.travis')){
+ app('router')->aliasMiddleware('throttle', ThrottleRequestsWithPredis::class);
+ } else {
+ app('router')->aliasMiddleware('throttle', ThrottleRequests::class);
+ }
Route::bind('task_scheduler', function ($value) {
if (is_numeric($value)) {
@@ -44,34 +54,28 @@ class RouteServiceProvider extends ServiceProvider
->where('id', $this->decodePrimaryKey($value))->firstOrFail();
});
- RateLimiter::for('login', function () {
-
+ RateLimiter::for('login', function (Request $request) {
if (Ninja::isSelfHost()) {
return Limit::none();
- }else {
- return Limit::perMinute(50);
+ } else {
+ return Limit::perMinute(50)->by($request->ip());
}
-
});
- RateLimiter::for('api', function () {
-
+ RateLimiter::for('api', function (Request $request) {
if (Ninja::isSelfHost()) {
return Limit::none();
- }else {
- return Limit::perMinute(300);
+ } else {
+ return Limit::perMinute(300)->by($request->ip());
}
-
});
- RateLimiter::for('refresh', function () {
-
+ RateLimiter::for('refresh', function (Request $request) {
if (Ninja::isSelfHost()) {
return Limit::none();
- }else {
- return Limit::perMinute(200);
+ } else {
+ return Limit::perMinute(200)->by($request->ip());
}
-
});
}
diff --git a/app/Repositories/InvoiceRepository.php b/app/Repositories/InvoiceRepository.php
index f88c5a295776..969d228c28ab 100644
--- a/app/Repositories/InvoiceRepository.php
+++ b/app/Repositories/InvoiceRepository.php
@@ -83,8 +83,9 @@ class InvoiceRepository extends BaseRepository
*/
public function restore($invoice) :Invoice
{
- if($invoice->is_proforma)
+ if ($invoice->is_proforma) {
return $invoice;
+ }
//if we have just archived, only perform a soft restore
if (! $invoice->is_deleted) {
diff --git a/app/Services/Client/ClientService.php b/app/Services/Client/ClientService.php
index dd5d944285e5..b8a5a8a6279c 100644
--- a/app/Services/Client/ClientService.php
+++ b/app/Services/Client/ClientService.php
@@ -11,16 +11,16 @@
namespace App\Services\Client;
-use App\Utils\Number;
use App\Models\Client;
use App\Models\Credit;
use App\Models\Payment;
use App\Services\Email\Email;
-use App\Utils\Traits\MakesDates;
-use Illuminate\Support\Facades\DB;
use App\Services\Email\EmailObject;
use App\Services\Email\EmailService;
+use App\Utils\Number;
+use App\Utils\Traits\MakesDates;
use Illuminate\Mail\Mailables\Address;
+use Illuminate\Support\Facades\DB;
class ClientService
{
@@ -173,7 +173,6 @@ class ClientService
$email_object = $this->buildStatementMailableData($pdf);
Email::dispatch($email_object, $this->client->company);
-
}
/**
diff --git a/app/Services/Client/PaymentMethod.php b/app/Services/Client/PaymentMethod.php
index 8f095ea22fa3..7f7d6c4933bc 100644
--- a/app/Services/Client/PaymentMethod.php
+++ b/app/Services/Client/PaymentMethod.php
@@ -197,7 +197,7 @@ class PaymentMethod
'gateway_type_id' => GatewayType::CREDIT,
];
}
-
+
return $this;
}
diff --git a/app/Services/ClientPortal/InstantPayment.php b/app/Services/ClientPortal/InstantPayment.php
index 1b0daac41314..2e5feffd85ea 100644
--- a/app/Services/ClientPortal/InstantPayment.php
+++ b/app/Services/ClientPortal/InstantPayment.php
@@ -217,9 +217,9 @@ class InstantPayment
/** $hash_data = mixed[] */
$hash_data = [
- 'invoices' => $payable_invoices->toArray(),
- 'credits' => $credit_totals,
- 'amount_with_fee' => max(0, (($invoice_totals + $fee_totals) - $credit_totals)),
+ 'invoices' => $payable_invoices->toArray(),
+ 'credits' => $credit_totals,
+ 'amount_with_fee' => max(0, (($invoice_totals + $fee_totals) - $credit_totals)),
'pre_payment' => $this->request->pre_payment,
'frequency_id' => $this->request->frequency_id,
'remaining_cycles' => $this->request->remaining_cycles,
diff --git a/app/Services/Email/Email.php b/app/Services/Email/Email.php
index 4daf13338e20..7c8d7f072aee 100644
--- a/app/Services/Email/Email.php
+++ b/app/Services/Email/Email.php
@@ -11,43 +11,42 @@
namespace App\Services\Email;
-use App\Models\User;
-use App\Utils\Ninja;
+use App\DataMapper\Analytics\EmailFailure;
+use App\DataMapper\Analytics\EmailSuccess;
+use App\Events\Invoice\InvoiceWasEmailedAndFailed;
+use App\Events\Payment\PaymentWasEmailedAndFailed;
+use App\Jobs\Util\SystemLogger;
+use App\Libraries\Google\Google;
+use App\Libraries\MultiDB;
use App\Models\Client;
-use App\Models\Vendor;
+use App\Models\ClientContact;
use App\Models\Company;
use App\Models\Invoice;
use App\Models\Payment;
use App\Models\SystemLog;
-use App\Utils\HtmlEngine;
-use App\Libraries\MultiDB;
-use App\Models\ClientContact;
+use App\Models\User;
+use App\Models\Vendor;
use App\Models\VendorContact;
-use Illuminate\Bus\Queueable;
-use Illuminate\Mail\Mailable;
-use App\Jobs\Util\SystemLogger;
+use App\Utils\HtmlEngine;
+use App\Utils\Ninja;
use App\Utils\Traits\MakesHash;
use App\Utils\VendorHtmlEngine;
-use App\Libraries\Google\Google;
-use Illuminate\Support\Facades\Mail;
-use App\Services\Email\EmailMailable;
-use Illuminate\Support\Facades\Cache;
-use Illuminate\Queue\SerializesModels;
-use Turbo124\Beacon\Facades\LightLogs;
-use Illuminate\Queue\InteractsWithQueue;
use GuzzleHttp\Exception\ClientException;
-use App\DataMapper\Analytics\EmailFailure;
-use App\DataMapper\Analytics\EmailSuccess;
+use Illuminate\Bus\Queueable;
use Illuminate\Contracts\Queue\ShouldQueue;
use Illuminate\Foundation\Bus\Dispatchable;
-use App\Events\Invoice\InvoiceWasEmailedAndFailed;
-use App\Events\Payment\PaymentWasEmailedAndFailed;
+use Illuminate\Mail\Mailable;
+use Illuminate\Queue\InteractsWithQueue;
+use Illuminate\Queue\SerializesModels;
+use Illuminate\Support\Facades\Cache;
+use Illuminate\Support\Facades\Mail;
+use Turbo124\Beacon\Facades\LightLogs;
class Email implements ShouldQueue
{
use Dispatchable, InteractsWithQueue, Queueable, SerializesModels, MakesHash;
- public $tries = 4;
+ public $tries = 4;
public $deleteWhenMissingModels = true;
@@ -79,7 +78,6 @@ class Email implements ShouldQueue
public function handle()
{
-
MultiDB::setDb($this->company->db);
$this->setOverride()
@@ -87,13 +85,13 @@ class Email implements ShouldQueue
->setDefaults()
->buildMailable();
- if($this->preFlightChecksFail())
+ if ($this->preFlightChecksFail()) {
return;
+ }
$this->email();
$this->tearDown();
-
}
/**
@@ -115,7 +113,6 @@ class Email implements ShouldQueue
*/
public function initModels(): self
{
-
$this->email_object->entity_id ? $this->email_object->entity = $this->email_object->entity_class::withTrashed()->with('invitations')->find($this->email_object->entity_id) : $this->email_object->entity = null;
$this->email_object->invitation_id ? $this->email_object->invitation = $this->email_object->entity->invitations()->where('id', $this->email_object->invitation_id)->first() : $this->email_object->invitation = null;
@@ -126,13 +123,10 @@ class Email implements ShouldQueue
$this->email_object->vendor_id ? $this->email_object->vendor = Vendor::withTrashed()->find($this->email_object->vendor_id) : $this->email_object->vendor = null;
- if (!$this->email_object->contact)
- {
-
+ if (!$this->email_object->contact) {
$this->email_object->vendor_contact_id ? $this->email_object->contact = VendorContact::withTrashed()->find($this->email_object->vendor_contact_id) : null;
$this->email_object->client_contact_id ? $this->email_object->contact = ClientContact::withTrashed()->find($this->email_object->client_contact_id) : null;
-
}
$this->email_object->user_id ? $this->email_object->user = User::withTrashed()->find($this->email_object->user_id) : $this->email_object->user = $this->company->owner();
@@ -163,7 +157,7 @@ class Email implements ShouldQueue
{
$_variables = $this->email_object->variables;
- match(class_basename($this->email_object->entity)){
+ match (class_basename($this->email_object->entity)) {
"Invoice" => $this->email_object->variables = (new HtmlEngine($this->email_object->invitation))->makeValues(),
"Quote" => $this->email_object->variables = (new HtmlEngine($this->email_object->invitation))->makeValues(),
"Credit" => $this->email_object->variables = (new HtmlEngine($this->email_object->invitation))->makeValues(),
@@ -172,8 +166,7 @@ class Email implements ShouldQueue
};
/** If we have passed some variable overrides we insert them here */
- foreach($_variables as $key => $value)
- {
+ foreach ($_variables as $key => $value) {
$this->email_object->variables[$key] = $value;
}
@@ -187,7 +180,6 @@ class Email implements ShouldQueue
*/
private function tearDown(): self
{
-
$this->email_object->entity = null;
$this->email_object->invitation = null;
$this->email_object->client = null;
@@ -197,7 +189,6 @@ class Email implements ShouldQueue
$this->email_object->settings = null;
return $this;
-
}
/**
@@ -207,11 +198,9 @@ class Email implements ShouldQueue
*/
public function setDefaults(): self
{
-
(new EmailDefaults($this))->run();
return $this;
-
}
/**
@@ -221,11 +210,9 @@ class Email implements ShouldQueue
*/
public function buildMailable(): self
{
-
$this->mailable = new EmailMailable($this->email_object);
return $this;
-
}
/**
@@ -235,7 +222,6 @@ class Email implements ShouldQueue
*/
public function email()
{
-
$this->setMailDriver();
/* Init the mailer*/
@@ -260,7 +246,6 @@ class Email implements ShouldQueue
LightLogs::create(new EmailSuccess($this->company->company_key))
->send();
-
} catch(\Symfony\Component\Mime\Exception\RfcComplianceException $e) {
nlog("Mailer failed with a Logic Exception {$e->getMessage()}");
$this->fail();
@@ -274,8 +259,7 @@ class Email implements ShouldQueue
$this->logMailError($e->getMessage(), $this->company->clients()->first());
return;
} catch (\Exception | \RuntimeException | \Google\Service\Exception $e) {
-
- nlog("Mailer failed with {$e->getMessage()}");
+ nlog("Mailer failed with {$e->getMessage()}");
$message = $e->getMessage();
if (stripos($e->getMessage(), 'code 406') || stripos($e->getMessage(), 'code 300') || stripos($e->getMessage(), 'code 413')) {
@@ -326,7 +310,6 @@ class Email implements ShouldQueue
}
$this->cleanUpMailers();
-
}
/**
@@ -765,13 +748,10 @@ class Email implements ShouldQueue
public function failed($exception = null)
{
-
- if($exception)
+ if ($exception) {
nlog($exception->getMessage());
+ }
config(['queue.failed.driver' => null]);
-
}
-
-
-}
\ No newline at end of file
+}
diff --git a/app/Services/Email/EmailDefaults.php b/app/Services/Email/EmailDefaults.php
index c76575e0a7a4..b63b506c7d2f 100644
--- a/app/Services/Email/EmailDefaults.php
+++ b/app/Services/Email/EmailDefaults.php
@@ -11,22 +11,22 @@
namespace App\Services\Email;
-use App\Models\Task;
-use App\Utils\Ninja;
-use App\Models\Quote;
-use App\Models\Credit;
+use App\DataMapper\EmailTemplateDefaults;
+use App\Jobs\Entity\CreateRawPdf;
+use App\Jobs\Invoice\CreateUbl;
+use App\Jobs\Vendor\CreatePurchaseOrderPdf;
use App\Models\Account;
+use App\Models\Credit;
use App\Models\Expense;
use App\Models\Invoice;
use App\Models\PurchaseOrder;
-use App\Jobs\Invoice\CreateUbl;
+use App\Models\Quote;
+use App\Models\Task;
+use App\Utils\Ninja;
use App\Utils\Traits\MakesHash;
-use App\Jobs\Entity\CreateRawPdf;
-use Illuminate\Support\Facades\App;
use Illuminate\Mail\Mailables\Address;
-use App\DataMapper\EmailTemplateDefaults;
+use Illuminate\Support\Facades\App;
use League\CommonMark\CommonMarkConverter;
-use App\Jobs\Vendor\CreatePurchaseOrderPdf;
class EmailDefaults
{
@@ -66,7 +66,7 @@ class EmailDefaults
{
$this->settings = $this->email->email_object->settings;
- $this->setLocale()
+ $this->setLocale()
->setFrom()
->setTo()
->setCc()
@@ -128,7 +128,6 @@ class EmailDefaults
private function setFrom(): self
{
if (Ninja::isHosted() && $this->email->email_object->settings->email_sending_method == 'default') {
-
if ($this->email->company->account->isPaid() && property_exists($this->email->email_object->settings, 'email_from_name') && strlen($this->email->email_object->settings->email_from_name) > 1) {
$email_from_name = $this->email->email_object->settings->email_from_name;
} else {
@@ -168,7 +167,6 @@ class EmailDefaults
*/
private function setBody(): self
{
-
if ($this->template == 'email.template.custom') {
$this->email->email_object->body = (str_replace('$body', $this->email->email_object->body, $this->email->email_object->settings->email_style_custom));
return $this;
@@ -291,20 +289,16 @@ class EmailDefaults
/** Purchase Order / Invoice / Credit / Quote PDF */
if ($this->email->email_object->settings->pdf_email_attachment && $this->email->email_object->entity instanceof PurchaseOrder) {
-
$pdf = (new CreatePurchaseOrderPdf($this->email->email_object->invitation))->rawPdf();
$this->email->email_object->attachments = array_merge($this->email->email_object->attachments, [['file' => base64_encode($pdf), 'name' => $this->email->email_object->entity->numberFormatter().'.pdf']]);
-
} elseif ($this->email->email_object->settings->pdf_email_attachment &&
($this->email->email_object->entity instanceof Invoice ||
$this->email->email_object->entity instanceof Quote ||
$this->email->email_object->entity instanceof Credit)) {
-
$pdf = ((new CreateRawPdf($this->email->email_object->invitation, $this->email->company->db))->handle());
$this->email->email_object->attachments = array_merge($this->email->email_object->attachments, [['file' => base64_encode($pdf), 'name' => $this->email->email_object->entity->numberFormatter().'.pdf']]);
-
}
/** UBL xml file */
@@ -316,8 +310,9 @@ class EmailDefaults
}
}
- if(!$this->email->email_object->settings->document_email_attachment || !$this->email->company->account->hasFeature(Account::FEATURE_DOCUMENTS))
+ if (!$this->email->email_object->settings->document_email_attachment || !$this->email->company->account->hasFeature(Account::FEATURE_DOCUMENTS)) {
return $this;
+ }
/* Company Documents */
$this->email->email_object->documents = array_merge($this->email->email_object->documents, $this->email->company->documents->pluck('id')->toArray());
diff --git a/app/Services/Email/EmailMailable.php b/app/Services/Email/EmailMailable.php
index 50ae63181bd2..91c0ea407121 100644
--- a/app/Services/Email/EmailMailable.php
+++ b/app/Services/Email/EmailMailable.php
@@ -12,16 +12,15 @@
namespace App\Services\Email;
use App\Models\Document;
-use Illuminate\Mail\Mailable;
use Illuminate\Mail\Attachment;
-use Illuminate\Support\Facades\URL;
+use Illuminate\Mail\Mailable;
use Illuminate\Mail\Mailables\Content;
-use Illuminate\Mail\Mailables\Headers;
use Illuminate\Mail\Mailables\Envelope;
+use Illuminate\Mail\Mailables\Headers;
+use Illuminate\Support\Facades\URL;
class EmailMailable extends Mailable
{
-
public int $max_attachment_size = 3000000;
/**
@@ -41,7 +40,7 @@ class EmailMailable extends Mailable
public function envelope()
{
return new Envelope(
- subject: str_replace("
","",$this->email_object->subject),
+ subject: str_replace("
", "", $this->email_object->subject),
tags: [$this->email_object->company_key],
replyTo: $this->email_object->reply_to,
from: $this->email_object->from,
@@ -58,15 +57,12 @@ class EmailMailable extends Mailable
*/
public function content()
{
-
- $links = Document::whereIn('id',$this->email_object->documents)
+ $links = Document::whereIn('id', $this->email_object->documents)
->where('size', '>', $this->max_attachment_size)
->cursor()
- ->map(function ($document){
-
- return " $document->hash]) ."'>". $document->name ."";
-
- });
+ ->map(function ($document) {
+ return " $document->hash]) ."'>". $document->name ."";
+ });
return new Content(
view: $this->email_object->html_template,
@@ -94,18 +90,16 @@ class EmailMailable extends Mailable
{
$attachments = [];
- $attachments = collect($this->email_object->attachments)->map(function ($file){
+ $attachments = collect($this->email_object->attachments)->map(function ($file) {
return Attachment::fromData(fn () => base64_decode($file['file']), $file['name']);
});
- $documents = Document::whereIn('id',$this->email_object->documents)
+ $documents = Document::whereIn('id', $this->email_object->documents)
->where('size', '<', $this->max_attachment_size)
->cursor()
- ->map(function ($document){
-
- return Attachment::fromData(fn () => $document->getFile(), $document->name);
-
- });
+ ->map(function ($document) {
+ return Attachment::fromData(fn () => $document->getFile(), $document->name);
+ });
return $attachments->merge($documents)->toArray();
}
diff --git a/app/Services/Email/EmailObject.php b/app/Services/Email/EmailObject.php
index e11e45c82419..74334965f6d4 100644
--- a/app/Services/Email/EmailObject.php
+++ b/app/Services/Email/EmailObject.php
@@ -11,22 +11,22 @@
namespace App\Services\Email;
-use App\Models\User;
-use App\Models\Quote;
use App\Models\Client;
-use App\Models\Credit;
-use App\Models\Vendor;
-use App\Models\Company;
-use App\Models\Invoice;
-use App\Models\Payment;
use App\Models\ClientContact;
-use App\Models\PurchaseOrder;
-use App\Models\VendorContact;
-use App\Models\QuoteInvitation;
+use App\Models\Company;
+use App\Models\Credit;
use App\Models\CreditInvitation;
+use App\Models\Invoice;
use App\Models\InvoiceInvitation;
-use Illuminate\Mail\Mailables\Address;
+use App\Models\Payment;
+use App\Models\PurchaseOrder;
use App\Models\PurchaseOrderInvitation;
+use App\Models\Quote;
+use App\Models\QuoteInvitation;
+use App\Models\User;
+use App\Models\Vendor;
+use App\Models\VendorContact;
+use Illuminate\Mail\Mailables\Address;
/**
* EmailObject.
diff --git a/app/Services/Invoice/ApplyNumber.php b/app/Services/Invoice/ApplyNumber.php
index 93c5adb187b5..f566c3480011 100644
--- a/app/Services/Invoice/ApplyNumber.php
+++ b/app/Services/Invoice/ApplyNumber.php
@@ -40,8 +40,8 @@ class ApplyNumber extends AbstractService
return $this->invoice;
}
- /** Do no give pro forma invoices a proper invoice number */
- if($this->invoice->is_proforma) {
+ /** Do not give a pro forma invoice a proper invoice number */
+ if ($this->invoice->is_proforma && $this->invoice->recurring_id) {
$this->invoice->number = ctrans('texts.pre_payment') . " " . now()->format('Y-m-d : H:i:s');
$this->invoice->saveQuietly();
return $this->invoice;
diff --git a/app/Services/Invoice/AutoBillInvoice.php b/app/Services/Invoice/AutoBillInvoice.php
index d60a14fa0953..5d10f2e74fff 100644
--- a/app/Services/Invoice/AutoBillInvoice.php
+++ b/app/Services/Invoice/AutoBillInvoice.php
@@ -122,12 +122,12 @@ class AutoBillInvoice extends AbstractService
$payment_hash = PaymentHash::create([
'hash' => Str::random(64),
'data' => [
- 'amount_with_fee' => $amount + $fee,
+ 'amount_with_fee' => $amount + $fee,
'invoices' => [
[
- 'invoice_id' => $this->invoice->hashed_id,
- 'amount' => $amount,
- 'invoice_number' => $this->invoice->number,
+ 'invoice_id' => $this->invoice->hashed_id,
+ 'amount' => $amount,
+ 'invoice_number' => $this->invoice->number,
'pre_payment' => $this->invoice->is_proforma,
],
],
diff --git a/app/Services/Invoice/MarkSent.php b/app/Services/Invoice/MarkSent.php
index 54ed2a141045..87c3a89f0664 100644
--- a/app/Services/Invoice/MarkSent.php
+++ b/app/Services/Invoice/MarkSent.php
@@ -21,7 +21,8 @@ use App\Utils\Ninja;
class MarkSent extends AbstractService
{
public function __construct(public Client $client, public Invoice $invoice)
- {}
+ {
+ }
public function run($fire_webhook = false)
{
diff --git a/app/Services/Invoice/SendEmail.php b/app/Services/Invoice/SendEmail.php
index 833d777c533e..b71677457307 100644
--- a/app/Services/Invoice/SendEmail.php
+++ b/app/Services/Invoice/SendEmail.php
@@ -35,7 +35,6 @@ class SendEmail extends AbstractService
/**
* Builds the correct template to send.
- * @return void
*/
public function run()
{
diff --git a/app/Services/Payment/DeletePayment.php b/app/Services/Payment/DeletePayment.php
index eec109408172..f5c02d1e86e5 100644
--- a/app/Services/Payment/DeletePayment.php
+++ b/app/Services/Payment/DeletePayment.php
@@ -74,7 +74,6 @@ class DeletePayment
if ($this->payment->invoices()->exists()) {
$this->payment->invoices()->each(function ($paymentable_invoice) {
-
$net_deletable = $paymentable_invoice->pivot->amount - $paymentable_invoice->pivot->refunded;
$this->_paid_to_date_deleted += $net_deletable;
@@ -105,7 +104,6 @@ class DeletePayment
} else {
$paymentable_invoice->service()->setStatus(Invoice::STATUS_PARTIAL)->save();
}
-
} else {
$paymentable_invoice->restore();
$paymentable_invoice->service()
diff --git a/app/Services/Payment/SendEmail.php b/app/Services/Payment/SendEmail.php
index a16e6ea926b2..0deb487c0a68 100644
--- a/app/Services/Payment/SendEmail.php
+++ b/app/Services/Payment/SendEmail.php
@@ -11,17 +11,17 @@
namespace App\Services\Payment;
-use App\Utils\Ninja;
-use App\Models\Payment;
-use App\Models\ClientContact;
-use App\Jobs\Payment\EmailPayment;
use App\Events\Payment\PaymentWasEmailed;
+use App\Jobs\Payment\EmailPayment;
+use App\Models\ClientContact;
+use App\Models\Payment;
+use App\Utils\Ninja;
class SendEmail
{
-
public function __construct(public Payment $payment, public ?ClientContact $contact)
- {}
+ {
+ }
/**
* Builds the correct template to send.
@@ -31,18 +31,18 @@ class SendEmail
{
$this->payment->load('company', 'client.contacts', 'invoices');
- if(!$this->contact)
+ if (!$this->contact) {
$this->contact = $this->payment->client->contacts()->first();
+ }
// $this->payment->invoices->sortByDesc('id')->first(function ($invoice) {
// $invoice->invitations->each(function ($invitation) {
// if (!$invitation->contact->trashed() && $invitation->contact->email) {
- EmailPayment::dispatch($this->payment, $this->payment->company, $this->contact);
+ EmailPayment::dispatch($this->payment, $this->payment->company, $this->contact);
- event(new PaymentWasEmailed($this->payment, $this->payment->company, Ninja::eventVars(auth()->user() ? auth()->user()->id : null)));
+ event(new PaymentWasEmailed($this->payment, $this->payment->company, Ninja::eventVars(auth()->user() ? auth()->user()->id : null)));
// }
// });
// });
-
}
}
diff --git a/app/Services/Payment/UpdateInvoicePayment.php b/app/Services/Payment/UpdateInvoicePayment.php
index aba182f80668..4f088eacfc9f 100644
--- a/app/Services/Payment/UpdateInvoicePayment.php
+++ b/app/Services/Payment/UpdateInvoicePayment.php
@@ -11,14 +11,14 @@
namespace App\Services\Payment;
-use App\Utils\Ninja;
+use App\Events\Invoice\InvoiceWasUpdated;
+use App\Factory\RecurringInvoiceFactory;
use App\Models\Invoice;
use App\Models\Payment;
use App\Models\PaymentHash;
-use App\Utils\Traits\MakesHash;
use App\Models\RecurringInvoice;
-use App\Factory\RecurringInvoiceFactory;
-use App\Events\Invoice\InvoiceWasUpdated;
+use App\Utils\Ninja;
+use App\Utils\Traits\MakesHash;
class UpdateInvoicePayment
{
@@ -84,10 +84,8 @@ class UpdateInvoicePayment
->save();
if ($invoice->is_proforma) {
-
//keep proforma's hidden
- if(property_exists($this->payment_hash->data, 'pre_payment') && $this->payment_hash->data->pre_payment == "1"){
-
+ if (property_exists($this->payment_hash->data, 'pre_payment') && $this->payment_hash->data->pre_payment == "1") {
$invoice->payments()->each(function ($p) {
$p->pivot->forceDelete();
});
@@ -117,7 +115,6 @@ class UpdateInvoicePayment
$recurring_invoice->next_send_date = $recurring_invoice->nextSendDate();
$recurring_invoice->next_send_date_client = $recurring_invoice->nextSendDateClient();
$recurring_invoice->service()->applyNumber()->save();
-
}
return;
@@ -125,8 +122,9 @@ class UpdateInvoicePayment
- if (strlen($invoice->number) > 1 && str_starts_with($invoice->number, "####"))
- $invoice->number = '';
+ if (strlen($invoice->number) > 1 && str_starts_with($invoice->number, "####")) {
+ $invoice->number = '';
+ }
$invoice->is_proforma = false;
diff --git a/app/Services/Pdf/PdfMock.php b/app/Services/Pdf/PdfMock.php
index 510508b4bdb9..698490f7f08f 100644
--- a/app/Services/Pdf/PdfMock.php
+++ b/app/Services/Pdf/PdfMock.php
@@ -421,7 +421,7 @@ class PdfMock
'$country_2' => 'AF',
'$firstName' => 'Benedict',
'$user.name' => 'Derrick Monahan DDS Erna Wunsch',
- '$font_name' => $this->settings?->primary_font ?: 'Roboto',
+ '$font_name' => isset($this->settings?->primary_font) ? $this->settings?->primary_font : 'Roboto',
'$auto_bill' => 'This invoice will automatically be billed to your credit card on file on the due date.',
'$payments' => '',
'$task.tax' => '',
@@ -883,7 +883,7 @@ class PdfMock
'$created_by_user' => 'Mr. Louvenia Armstrong Prof. Reyes Anderson',
'$vendor.currency' => 'USD',
'$company.country' => 'United States',
- '$tech_hero_image' => 'http://ninja.test:8000/images/pdf-designs/tech-hero-image.jpg',
+ '$tech_hero_image' => 'https://invoicing.co/images/pdf-designs/tech-hero-image.jpg',
'$company.website' => 'http://www.dare.com/vero-consequatur-eveniet-dolorum-exercitationem-alias-repellat.html',
'$gross_subtotal' => '$10,256.40',
'$emailSignature' => ' ',
diff --git a/app/Services/Pdf/PdfService.php b/app/Services/Pdf/PdfService.php
index 77c99919ed1d..d7fde2b8cc5a 100644
--- a/app/Services/Pdf/PdfService.php
+++ b/app/Services/Pdf/PdfService.php
@@ -11,7 +11,6 @@
namespace App\Services\Pdf;
-use App\Models\Account;
use App\Models\Company;
use App\Models\CreditInvitation;
use App\Models\InvoiceInvitation;
@@ -72,7 +71,7 @@ class PdfService
* Resolves the PDF generation type and
* attempts to generate a PDF from the HTML
* string.
- *
+ *
* @return mixed | Exception
*
*/
@@ -102,7 +101,6 @@ class PdfService
*/
public function getHtml(): string
{
-
$html = $this->builder->getCompiledHTML();
if (config('ninja.log_pdf_html')) {
diff --git a/app/Services/PdfMaker/Design.php b/app/Services/PdfMaker/Design.php
index eccdb0d4dfc3..b2ffd3792db5 100644
--- a/app/Services/PdfMaker/Design.php
+++ b/app/Services/PdfMaker/Design.php
@@ -681,8 +681,9 @@ class Design extends BaseDesign
$table_type = "{$type}_columns";
- if($type == 'product' && $this->entity instanceof Quote && !$this->settings_object->getSetting('sync_invoice_quote_columns'))
+ if ($type == 'product' && $this->entity instanceof Quote && !$this->settings_object->getSetting('sync_invoice_quote_columns')) {
$table_type = "product_quote_columns";
+ }
foreach ($this->context['pdf_variables'][$table_type] as $column) {
if (array_key_exists($column, $aliases)) {
@@ -788,7 +789,6 @@ class Design extends BaseDesign
}
}
} else {
-
foreach ($this->context['pdf_variables'][$table_type] as $key => $cell) {
// We want to keep aliases like these:
// $task.cost => $task.rate
diff --git a/app/Services/PdfMaker/PdfMakerUtilities.php b/app/Services/PdfMaker/PdfMakerUtilities.php
index 95be78b0b1e1..e76aac567061 100644
--- a/app/Services/PdfMaker/PdfMakerUtilities.php
+++ b/app/Services/PdfMaker/PdfMakerUtilities.php
@@ -93,7 +93,7 @@ trait PdfMakerUtilities
if ($child['element'] !== 'script') {
if (array_key_exists('process_markdown', $this->data) && array_key_exists('content', $child) && $this->data['process_markdown']) {
- $child['content'] = str_replace('
', "\r", $child['content']);
+ $child['content'] = str_replace('
', "\r", ($child['content'] ?? ''));
$child['content'] = $this->commonmark->convert($child['content'] ?? '');
}
}
@@ -178,7 +178,7 @@ trait PdfMakerUtilities
foreach ($children as $key => &$child) {
if (isset($child['content']) && isset($child['show_empty']) && $child['show_empty'] === false) {
$value = strtr($child['content'], $variables['values']);
- if ($value === '' || $value === ' ' || $value === ' '){
+ if ($value === '' || $value === ' ' || $value === ' ') {
$child['is_empty'] = true;
}
}
diff --git a/app/Services/PurchaseOrder/PurchaseOrderService.php b/app/Services/PurchaseOrder/PurchaseOrderService.php
index d1ab465d262c..f9bc5d7c75e1 100644
--- a/app/Services/PurchaseOrder/PurchaseOrderService.php
+++ b/app/Services/PurchaseOrder/PurchaseOrderService.php
@@ -11,9 +11,10 @@
namespace App\Services\PurchaseOrder;
-use App\Jobs\Vendor\CreatePurchaseOrderPdf;
use App\Models\PurchaseOrder;
use App\Utils\Traits\MakesHash;
+use App\Services\PurchaseOrder\SendEmail;
+use App\Jobs\Vendor\CreatePurchaseOrderPdf;
class PurchaseOrderService
{
@@ -145,6 +146,14 @@ class PurchaseOrderService
return $expense;
}
+ public function sendEmail($contact = null)
+ {
+ $send_email = new SendEmail($this->purchase_order, null, $contact);
+
+ return $send_email->run();
+ }
+
+
/**
* Saves the purchase order.
* @return \App\Models\PurchaseOrder object
diff --git a/app/Services/PurchaseOrder/SendEmail.php b/app/Services/PurchaseOrder/SendEmail.php
new file mode 100644
index 000000000000..900d5380bc6a
--- /dev/null
+++ b/app/Services/PurchaseOrder/SendEmail.php
@@ -0,0 +1,116 @@
+purchase_order->last_sent_date = now();
+
+ $this->purchase_order->invitations->load('contact.vendor.country', 'purchase_order.vendor.country', 'purchase_order.company')->each(function ($invitation) {
+
+ App::forgetInstance('translator');
+ $t = app('translator');
+ App::setLocale($invitation->contact->preferredLocale());
+ $t->replace(Ninja::transformTranslations($this->purchase_order->company->settings));
+
+ /* Mark entity sent */
+ $invitation->purchase_order->service()->markSent()->save();
+
+ $template = 'purchase_order';
+
+ $email_builder = (new PurchaseOrderEmailEngine($invitation, $template, null))->build();
+
+ $nmo = new NinjaMailerObject;
+ $nmo->mailable = new VendorTemplateEmail($email_builder, $invitation->contact, $invitation);
+ $nmo->company = $this->purchase_order->company;
+ $nmo->settings = $this->purchase_order->company->settings;
+ $nmo->to_user = $invitation->contact;
+ $nmo->entity_string = 'purchase_order';
+ $nmo->invitation = $invitation;
+ $nmo->reminder_template = 'email_template_purchase_order';
+ $nmo->entity = $invitation->purchase_order;
+
+ NinjaMailerJob::dispatch($nmo);
+ });
+
+ if ($this->purchase_order->invitations->count() >= 1) {
+ event(new PurchaseOrderWasEmailed($this->purchase_order->invitations->first(), $this->purchase_order->invitations->first()->company, Ninja::eventVars(auth()->user() ? auth()->user()->id : null)));
+ }
+
+ }
+}
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/app/Services/Quote/GetQuotePdf.php b/app/Services/Quote/GetQuotePdf.php
index 095b62650079..5ae880e33052 100644
--- a/app/Services/Quote/GetQuotePdf.php
+++ b/app/Services/Quote/GetQuotePdf.php
@@ -15,7 +15,6 @@ use App\Jobs\Entity\CreateEntityPdf;
use App\Models\ClientContact;
use App\Models\Quote;
use App\Services\AbstractService;
-use Illuminate\Support\Facades\Storage;
class GetQuotePdf extends AbstractService
{
@@ -34,8 +33,9 @@ class GetQuotePdf extends AbstractService
$invitation = $this->quote->invitations->where('client_contact_id', $this->contact->id)->first();
- if(!$invitation)
+ if (!$invitation) {
$invitation = $this->quote->invitations->first();
+ }
$path = $this->quote->client->quote_filepath($invitation);
@@ -48,6 +48,5 @@ class GetQuotePdf extends AbstractService
$file_path = (new CreateEntityPdf($invitation))->handle();
return $file_path;
-
}
}
diff --git a/app/Services/Quote/SendEmail.php b/app/Services/Quote/SendEmail.php
index 3fb32229612e..2530fe598bbf 100644
--- a/app/Services/Quote/SendEmail.php
+++ b/app/Services/Quote/SendEmail.php
@@ -14,7 +14,6 @@ namespace App\Services\Quote;
use App\Jobs\Entity\EmailEntity;
use App\Models\ClientContact;
-
class SendEmail
{
public $quote;
@@ -48,7 +47,7 @@ class SendEmail
$this->quote->service()->markSent()->save();
- $this->quote->invitations->each(function ($invitation) {
+ $this->quote->invitations->each(function ($invitation) {
if (! $invitation->contact->trashed() && $invitation->contact->email) {
EmailEntity::dispatch($invitation, $invitation->company, $this->reminder_template);
diff --git a/app/Services/Recurring/IncreasePrice.php b/app/Services/Recurring/IncreasePrice.php
index b8486a206710..168790e8f1f5 100644
--- a/app/Services/Recurring/IncreasePrice.php
+++ b/app/Services/Recurring/IncreasePrice.php
@@ -16,28 +16,18 @@ use App\Services\AbstractService;
class IncreasePrice extends AbstractService
{
-
public function __construct(public RecurringInvoice $recurring_invoice, public float $percentage)
{
-
}
public function run()
{
-
$line_items = $this->recurring_invoice->line_items;
foreach ($line_items as $key => $line_item) {
-
$line_items[$key]->cost = $line_item->cost * (1 + round(($this->percentage / 100), 2));
-
}
$this->recurring_invoice->line_items = $line_items;
$this->recurring_invoice->calc()->getInvoice()->save();
-
-
-
}
-
-
}
diff --git a/app/Services/Recurring/RecurringService.php b/app/Services/Recurring/RecurringService.php
index 5c20a19bc5ed..e9c81b870dc1 100644
--- a/app/Services/Recurring/RecurringService.php
+++ b/app/Services/Recurring/RecurringService.php
@@ -11,20 +11,14 @@
namespace App\Services\Recurring;
+use App\Jobs\RecurringInvoice\SendRecurring;
use App\Jobs\Util\UnlinkFile;
-use Illuminate\Support\Carbon;
use App\Models\RecurringExpense;
use App\Models\RecurringInvoice;
-use App\Services\Recurring\ApplyNumber;
-use App\Services\Recurring\UpdatePrice;
-use App\Services\Recurring\GetInvoicePdf;
-use App\Services\Recurring\IncreasePrice;
-use App\Jobs\RecurringInvoice\SendRecurring;
-use App\Services\Recurring\CreateRecurringInvitations;
+use Illuminate\Support\Carbon;
class RecurringService
{
-
public function __construct(public RecurringInvoice | RecurringExpense $recurring_entity)
{
}
@@ -58,8 +52,9 @@ class RecurringService
return $this;
}
- if($this->recurring_entity->trashed())
+ if ($this->recurring_entity->trashed()) {
$this->recurring_entity->restore();
+ }
$this->setStatus(RecurringInvoice::STATUS_ACTIVE);
@@ -145,7 +140,6 @@ class RecurringService
(new IncreasePrice($this->recurring_entity, $percentage))->run();
return $this;
-
}
public function updatePrice()
diff --git a/app/Services/Recurring/UpdatePrice.php b/app/Services/Recurring/UpdatePrice.php
index 1e196c68bc90..1666f1c4a4f1 100644
--- a/app/Services/Recurring/UpdatePrice.php
+++ b/app/Services/Recurring/UpdatePrice.php
@@ -23,28 +23,20 @@ class UpdatePrice extends AbstractService
public function run()
{
-
-
$line_items = $this->recurring_invoice->line_items;
- foreach($line_items as $key => $line_item)
- {
-
+ foreach ($line_items as $key => $line_item) {
$product = Product::where('company_id', $this->recurring_invoice->company_id)
->where('product_key', $line_item->product_key)
->where('is_deleted', 0)
->first();
- if($product){
-
+ if ($product) {
$line_items[$key]->cost = $product->cost;
}
-
}
$this->recurring_invoice->line_items = $line_items;
$this->recurring_invoice->calc()->getInvoice()->save();
-
-
}
-}
\ No newline at end of file
+}
diff --git a/app/Services/Scheduler/EmailStatementService.php b/app/Services/Scheduler/EmailStatementService.php
new file mode 100644
index 000000000000..c1c93ba941c5
--- /dev/null
+++ b/app/Services/Scheduler/EmailStatementService.php
@@ -0,0 +1,95 @@
+where('company_id', $this->scheduler->company_id)
+ ->where('is_deleted', 0);
+
+ //Email only the selected clients
+ if (count($this->scheduler->parameters['clients']) >= 1) {
+ $query->whereIn('id', $this->transformKeys($this->scheduler->parameters['clients']));
+ }
+
+ $query->cursor()
+ ->each(function ($_client) {
+ $this->client = $_client;
+
+ //work out the date range
+ $statement_properties = $this->calculateStatementProperties();
+
+ $_client->service()->statement($statement_properties, true);
+ });
+
+ //calculate next run dates;
+ $this->scheduler->calculateNextRun();
+
+ }
+
+ /**
+ * Hydrates the array needed to generate the statement
+ *
+ * @return array The statement options array
+ */
+ private function calculateStatementProperties(): array
+ {
+ $start_end = $this->calculateStartAndEndDates();
+
+ return [
+ 'start_date' =>$start_end[0],
+ 'end_date' =>$start_end[1],
+ 'show_payments_table' => $this->scheduler->parameters['show_payments_table'],
+ 'show_aging_table' => $this->scheduler->parameters['show_aging_table'],
+ 'status' => $this->scheduler->parameters['status']
+ ];
+ }
+
+ /**
+ * Start and end date of the statement
+ *
+ * @return array [$start_date, $end_date];
+ */
+ private function calculateStartAndEndDates(): array
+ {
+ return match ($this->scheduler->parameters['date_range']) {
+ EmailStatement::LAST7 => [now()->startOfDay()->subDays(7)->format('Y-m-d'), now()->startOfDay()->format('Y-m-d')],
+ EmailStatement::LAST30 => [now()->startOfDay()->subDays(30)->format('Y-m-d'), now()->startOfDay()->format('Y-m-d')],
+ EmailStatement::LAST365 => [now()->startOfDay()->subDays(365)->format('Y-m-d'), now()->startOfDay()->format('Y-m-d')],
+ EmailStatement::THIS_MONTH => [now()->startOfDay()->firstOfMonth()->format('Y-m-d'), now()->startOfDay()->lastOfMonth()->format('Y-m-d')],
+ EmailStatement::LAST_MONTH => [now()->startOfDay()->subMonthNoOverflow()->firstOfMonth()->format('Y-m-d'), now()->startOfDay()->subMonthNoOverflow()->lastOfMonth()->format('Y-m-d')],
+ EmailStatement::THIS_QUARTER => [now()->startOfDay()->firstOfQuarter()->format('Y-m-d'), now()->startOfDay()->lastOfQuarter()->format('Y-m-d')],
+ EmailStatement::LAST_QUARTER => [now()->startOfDay()->subQuarterNoOverflow()->firstOfQuarter()->format('Y-m-d'), now()->startOfDay()->subQuarterNoOverflow()->lastOfQuarter()->format('Y-m-d')],
+ EmailStatement::THIS_YEAR => [now()->startOfDay()->firstOfYear()->format('Y-m-d'), now()->startOfDay()->lastOfYear()->format('Y-m-d')],
+ EmailStatement::LAST_YEAR => [now()->startOfDay()->subYearNoOverflow()->firstOfYear()->format('Y-m-d'), now()->startOfDay()->subYearNoOverflow()->lastOfYear()->format('Y-m-d')],
+ EmailStatement::CUSTOM_RANGE => [$this->scheduler->parameters['start_date'], $this->scheduler->parameters['end_date']],
+ default => [now()->startOfDay()->firstOfMonth()->format('Y-m-d'), now()->startOfDay()->lastOfMonth()->format('Y-m-d')],
+ };
+ }
+
+}
diff --git a/app/Services/Scheduler/ScheduleEntity.php b/app/Services/Scheduler/ScheduleEntity.php
new file mode 100644
index 000000000000..b7a93bd8f1e7
--- /dev/null
+++ b/app/Services/Scheduler/ScheduleEntity.php
@@ -0,0 +1,34 @@
+scheduler->parameters['entity']);
+
+ $class::find($this->decodePrimaryKey($this->scheduler->parameters['entity_id']))->service()->sendEmail();
+
+ $this->scheduler->forceDelete();
+ }
+}
diff --git a/app/Services/Scheduler/SchedulerService.php b/app/Services/Scheduler/SchedulerService.php
index eacd84b0e926..7a670ada6ab8 100644
--- a/app/Services/Scheduler/SchedulerService.php
+++ b/app/Services/Scheduler/SchedulerService.php
@@ -11,9 +11,6 @@
namespace App\Services\Scheduler;
-use App\DataMapper\Schedule\EmailStatement;
-use App\Models\Client;
-use App\Models\RecurringInvoice;
use App\Models\Scheduler;
use App\Utils\Traits\MakesDates;
use App\Utils\Traits\MakesHash;
@@ -25,8 +22,6 @@ class SchedulerService
private string $method;
- private Client $client;
-
public function __construct(public Scheduler $scheduler)
{
}
@@ -38,133 +33,28 @@ class SchedulerService
*/
public function runTask(): void
{
- if(method_exists($this, $this->scheduler->template))
+ if (method_exists($this, $this->scheduler->template)) {
$this->{$this->scheduler->template}();
+ }
}
+ private function schedule_entity()
+ {
+ (new ScheduleEntity($this->scheduler))->run();
+ }
+
+
private function email_statement()
{
- $query = Client::query()
- ->where('company_id', $this->scheduler->company_id)
- ->where('is_deleted', 0);
-
- //Email only the selected clients
- if (count($this->scheduler->parameters['clients']) >= 1) {
- $query->whereIn('id', $this->transformKeys($this->scheduler->parameters['clients']));
- }
-
- $query->cursor()
- ->each(function ($_client) {
- $this->client = $_client;
-
- //work out the date range
- $statement_properties = $this->calculateStatementProperties();
-
- $_client->service()->statement($statement_properties, true);
- });
-
- //calculate next run dates;
- $this->calculateNextRun();
+ (new EmailStatementService($this->scheduler))->run();
}
- /**
- * Hydrates the array needed to generate the statement
- *
- * @return array The statement options array
- */
- private function calculateStatementProperties(): array
- {
- $start_end = $this->calculateStartAndEndDates();
-
- return [
- 'start_date' =>$start_end[0],
- 'end_date' =>$start_end[1],
- 'show_payments_table' => $this->scheduler->parameters['show_payments_table'],
- 'show_aging_table' => $this->scheduler->parameters['show_aging_table'],
- 'status' => $this->scheduler->parameters['status']
- ];
- }
-
- /**
- * Start and end date of the statement
- *
- * @return array [$start_date, $end_date];
- */
- private function calculateStartAndEndDates(): array
- {
- return match ($this->scheduler->parameters['date_range']) {
- EmailStatement::LAST7 => [now()->startOfDay()->subDays(7)->format('Y-m-d'), now()->startOfDay()->format('Y-m-d')],
- EmailStatement::LAST30 => [now()->startOfDay()->subDays(30)->format('Y-m-d'), now()->startOfDay()->format('Y-m-d')],
- EmailStatement::LAST365 => [now()->startOfDay()->subDays(365)->format('Y-m-d'), now()->startOfDay()->format('Y-m-d')],
- EmailStatement::THIS_MONTH => [now()->startOfDay()->firstOfMonth()->format('Y-m-d'), now()->startOfDay()->lastOfMonth()->format('Y-m-d')],
- EmailStatement::LAST_MONTH => [now()->startOfDay()->subMonthNoOverflow()->firstOfMonth()->format('Y-m-d'), now()->startOfDay()->subMonthNoOverflow()->lastOfMonth()->format('Y-m-d')],
- EmailStatement::THIS_QUARTER => [now()->startOfDay()->firstOfQuarter()->format('Y-m-d'), now()->startOfDay()->lastOfQuarter()->format('Y-m-d')],
- EmailStatement::LAST_QUARTER => [now()->startOfDay()->subQuarterNoOverflow()->firstOfQuarter()->format('Y-m-d'), now()->startOfDay()->subQuarterNoOverflow()->lastOfQuarter()->format('Y-m-d')],
- EmailStatement::THIS_YEAR => [now()->startOfDay()->firstOfYear()->format('Y-m-d'), now()->startOfDay()->lastOfYear()->format('Y-m-d')],
- EmailStatement::LAST_YEAR => [now()->startOfDay()->subYearNoOverflow()->firstOfYear()->format('Y-m-d'), now()->startOfDay()->subYearNoOverflow()->lastOfYear()->format('Y-m-d')],
- EmailStatement::CUSTOM_RANGE => [$this->scheduler->parameters['start_date'], $this->scheduler->parameters['end_date']],
- default => [now()->startOfDay()->firstOfMonth()->format('Y-m-d'), now()->startOfDay()->lastOfMonth()->format('Y-m-d')],
- };
- }
/**
* Sets the next run date of the scheduled task
*
*/
- private function calculateNextRun()
- {
- if (! $this->scheduler->next_run) {
- return null;
- }
- $offset = $this->scheduler->company->timezone_offset();
-
- switch ($this->scheduler->frequency_id) {
- case RecurringInvoice::FREQUENCY_DAILY:
- $next_run = now()->startOfDay()->addDay();
- break;
- case RecurringInvoice::FREQUENCY_WEEKLY:
- $next_run = now()->startOfDay()->addWeek();
- break;
- case RecurringInvoice::FREQUENCY_TWO_WEEKS:
- $next_run = now()->startOfDay()->addWeeks(2);
- break;
- case RecurringInvoice::FREQUENCY_FOUR_WEEKS:
- $next_run = now()->startOfDay()->addWeeks(4);
- break;
- case RecurringInvoice::FREQUENCY_MONTHLY:
- $next_run = now()->startOfDay()->addMonthNoOverflow();
- break;
- case RecurringInvoice::FREQUENCY_TWO_MONTHS:
- $next_run = now()->startOfDay()->addMonthsNoOverflow(2);
- break;
- case RecurringInvoice::FREQUENCY_THREE_MONTHS:
- $next_run = now()->startOfDay()->addMonthsNoOverflow(3);
- break;
- case RecurringInvoice::FREQUENCY_FOUR_MONTHS:
- $next_run = now()->startOfDay()->addMonthsNoOverflow(4);
- break;
- case RecurringInvoice::FREQUENCY_SIX_MONTHS:
- $next_run = now()->startOfDay()->addMonthsNoOverflow(6);
- break;
- case RecurringInvoice::FREQUENCY_ANNUALLY:
- $next_run = now()->startOfDay()->addYear();
- break;
- case RecurringInvoice::FREQUENCY_TWO_YEARS:
- $next_run = now()->startOfDay()->addYears(2);
- break;
- case RecurringInvoice::FREQUENCY_THREE_YEARS:
- $next_run = now()->startOfDay()->addYears(3);
- break;
- default:
- $next_run = null;
- }
-
-
- $this->scheduler->next_run_client = $next_run ?: null;
- $this->scheduler->next_run = $next_run ? $next_run->copy()->addSeconds($offset) : null;
- $this->scheduler->save();
- }
//handle when the scheduler has been paused.
}
diff --git a/app/Services/Subscription/SubscriptionService.php b/app/Services/Subscription/SubscriptionService.php
index 49f44eca53ad..5c2437403203 100644
--- a/app/Services/Subscription/SubscriptionService.php
+++ b/app/Services/Subscription/SubscriptionService.php
@@ -11,42 +11,42 @@
namespace App\Services\Subscription;
-use Carbon\Carbon;
+use App\DataMapper\InvoiceItem;
+use App\Factory\CreditFactory;
+use App\Factory\InvoiceFactory;
+use App\Factory\PaymentFactory;
+use App\Factory\RecurringInvoiceFactory;
+use App\Jobs\Mail\NinjaMailer;
+use App\Jobs\Mail\NinjaMailerJob;
+use App\Jobs\Mail\NinjaMailerObject;
+use App\Jobs\Util\SystemLogger;
+use App\Libraries\MultiDB;
+use App\Mail\RecurringInvoice\ClientContactRequestCancellationObject;
use App\Models\Client;
+use App\Models\ClientContact;
use App\Models\Credit;
use App\Models\Invoice;
use App\Models\License;
-use App\Models\Product;
-use App\Models\SystemLog;
-use App\Libraries\MultiDB;
use App\Models\PaymentHash;
use App\Models\PaymentType;
-use Illuminate\Support\Str;
-use App\Models\Subscription;
-use App\Models\ClientContact;
-use App\Services\Email\Email;
-use App\Factory\CreditFactory;
-use App\Jobs\Mail\NinjaMailer;
-use App\DataMapper\InvoiceItem;
-use App\Factory\InvoiceFactory;
-use App\Factory\PaymentFactory;
-use App\Jobs\Util\SystemLogger;
-use App\Utils\Traits\MakesHash;
+use App\Models\Product;
use App\Models\RecurringInvoice;
-use App\Jobs\Mail\NinjaMailerJob;
-use App\Services\Email\EmailObject;
-use App\Jobs\Mail\NinjaMailerObject;
-use App\Utils\Traits\CleanLineItems;
+use App\Models\Subscription;
+use App\Models\SystemLog;
use App\Repositories\CreditRepository;
use App\Repositories\InvoiceRepository;
use App\Repositories\PaymentRepository;
-use App\Factory\RecurringInvoiceFactory;
-use App\Utils\Traits\SubscriptionHooker;
-use App\Repositories\SubscriptionRepository;
use App\Repositories\RecurringInvoiceRepository;
+use App\Repositories\SubscriptionRepository;
+use App\Services\Email\Email;
+use App\Services\Email\EmailObject;
+use App\Utils\Traits\CleanLineItems;
+use App\Utils\Traits\MakesHash;
use App\Utils\Traits\Notifications\UserNotifies;
+use App\Utils\Traits\SubscriptionHooker;
+use Carbon\Carbon;
use Illuminate\Contracts\Container\BindingResolutionException;
-use App\Mail\RecurringInvoice\ClientContactRequestCancellationObject;
+use Illuminate\Support\Str;
class SubscriptionService
{
@@ -121,10 +121,9 @@ class SubscriptionService
'account_key' => $recurring_invoice->client->custom_value2,
];
- $response = $this->triggerWebhook($context);
+ $response = $this->triggerWebhook($context);
return $this->handleRedirect('/client/recurring_invoices/'.$recurring_invoice->hashed_id);
-
} else {
$invoice = Invoice::withTrashed()->find($payment_hash->fee_invoice_id);
@@ -168,8 +167,8 @@ class SubscriptionService
{
//send license to the user.
$invoice = $payment_hash->fee_invoice;
- $license_key = Str::uuid()->toString();
- $invoice->footer = ctrans('texts.white_label_body',['license_key' => $license_key]);
+ $license_key = "v5_".Str::uuid()->toString();
+ $invoice->footer = ctrans('texts.white_label_body', ['license_key' => $license_key]);
$recurring_invoice = $this->convertInvoiceToRecurring($payment_hash->payment->client_id);
@@ -207,7 +206,7 @@ class SubscriptionService
$email_object = new EmailObject;
$email_object->to = [$contact->email];
$email_object->subject = ctrans('texts.white_label_link') . " " .ctrans('texts.payment_subject');
- $email_object->body = ctrans('texts.white_label_body',['license_key' => $license_key]);
+ $email_object->body = ctrans('texts.white_label_body', ['license_key' => $license_key]);
$email_object->client_id = $invoice->client_id;
$email_object->client_contact_id = $contact->id;
$email_object->invitation_key = $invitation->invitation_key;
@@ -219,7 +218,6 @@ class SubscriptionService
Email::dispatch($email_object, $invoice->company);
return true;
-
}
/* Starts the process to create a trial
@@ -436,10 +434,11 @@ class SubscriptionService
$days_of_subscription_used = $start_date->diffInDays($current_date);
- if($subscription)
+ if ($subscription) {
$days_in_frequency = $subscription->service()->getDaysInFrequency();
- else
+ } else {
$days_in_frequency = $this->getDaysInFrequency();
+ }
if ($days_of_subscription_used >= $days_in_frequency) {
return 0;
diff --git a/app/Services/Tax/ProcessRule.php b/app/Services/Tax/ProcessRule.php
new file mode 100644
index 000000000000..21a4b197d799
--- /dev/null
+++ b/app/Services/Tax/ProcessRule.php
@@ -0,0 +1,153 @@
+setUp()
+ ->validateVat()
+ ->calculateVatRates();
+ }
+
+ public function hasValidVatNumber(): bool
+ {
+ return $this->valid_vat_number;
+ }
+
+ public function getVatRate(): float
+ {
+ return $this->vat_rate;
+ }
+
+ public function getVatReducedRate(): float
+ {
+ return $this->vat_reduced_rate;
+ }
+
+ public function getVendorCountryCode(): string
+ {
+ return $this->vendor_country_code;
+ }
+
+ public function getClientCountryCode(): string
+ {
+ return $this->client_country_code;
+ }
+
+ private function setUp(): self
+ {
+ $this->vendor_country_code = Str::lower($this->company->country()->iso_3166_2);
+
+ $this->client_country_code = $this->client->shipping_country ? Str::lower($this->client->shipping_country->iso_3166_2) : Str::lower($this->client->country->iso_3166_2);
+
+ $class = "App\\DataMapper\\Tax\\".$this->vendor_country_code."\\Rule";
+
+ $this->rule = new $class();
+
+ return $this;
+ }
+
+ private function validateVat(): self
+ {
+ $vat_check = (new VatNumberCheck($this->client->vat_number, $this->client_country_code))->run();
+
+ $this->valid_vat_number = $vat_check->isValid();
+
+ return $this;
+ }
+
+ private function calculateVatRates(): self
+ {
+
+ if(
+ (($this->vendor_country_code == $this->client_country_code) && $this->valid_vat_number && $this->rule->business_tax_exempt) ||
+ (in_array($this->client_country_code, $this->eu_country_codes) && $this->valid_vat_number && $this->rule->business_tax_exempt)
+ ) {
+ $this->vat_rate = 0.0;
+ $this->vat_reduced_rate = 0.0;
+ }
+ elseif(!in_array(strtoupper($this->client_country_code), $this->eu_country_codes) && ($this->rule->foreign_consumer_tax_exempt || $this->rule->foreign_business_tax_exempt)) {
+ nlog($this->client_country_code);
+ $this->vat_rate = 0.0;
+ $this->vat_reduced_rate = 0.0;
+ }
+ elseif(in_array(strtoupper($this->client_country_code), $this->eu_country_codes) && !$this->valid_vat_number) {
+ $rate_name = $this->client_country_code."_vat_rate";
+ $this->vat_rate = $this->rule->{$rate_name};
+ $this->vat_reduced_rate = $this->rule->vat_reduced_rate;
+ }
+ else {
+ $rate_name = $this->vendor_country_code."_vat_rate";
+ $this->vat_rate = $this->rule->{$rate_name};
+ $this->vat_reduced_rate = $this->rule->vat_reduced_rate;
+ }
+
+ return $this;
+
+ }
+}
diff --git a/app/Services/Tax/TaxService.php b/app/Services/Tax/TaxService.php
new file mode 100644
index 000000000000..36623162ca01
--- /dev/null
+++ b/app/Services/Tax/TaxService.php
@@ -0,0 +1,22 @@
+checkvat_number();
+ }
+
+ private function checkvat_number(): self
+ {
+ $wsdl = "https://ec.europa.eu/taxation_customs/vies/checkVatService.wsdl";
+
+ try {
+ $client = new \SoapClient($wsdl);
+ $params = [
+ 'countryCode' => $this->country_code,
+ 'vatNumber' => $this->vat_number
+ ];
+ $response = $client->checkVat($params);
+
+ if ($response->valid) {
+
+ $this->response = [
+ 'valid' => true,
+ 'name' => $response->name,
+ 'address' => $response->address
+ ];
+ } else {
+ $this->response = ['valid' => false];
+ }
+ } catch (\SoapFault $e) {
+
+ $this->response = ['valid' => false, 'error' => $e->getMessage()];
+ }
+
+ return $this;
+ }
+
+ public function getResponse()
+ {
+ return $this->response;
+ }
+
+ public function isValid(): bool
+ {
+ return $this->response['valid'];
+ }
+}
diff --git a/app/Utils/HtmlEngine.php b/app/Utils/HtmlEngine.php
index c889bd675f58..36cd4e272206 100644
--- a/app/Utils/HtmlEngine.php
+++ b/app/Utils/HtmlEngine.php
@@ -638,6 +638,10 @@ class HtmlEngine
$data['$entity_images'] = ['value' => $this->generateEntityImagesMarkup(), 'label' => ''];
$data['$payments'] = ['value' => '', 'label' => ctrans('texts.payments')];
+ $data['$payment.custom1'] = ['value' => '', 'label' => ctrans('texts.payment')];
+ $data['$payment.custom2'] = ['value' => '', 'label' => ctrans('texts.payment')];
+ $data['$payment.custom3'] = ['value' => '', 'label' => ctrans('texts.payment')];
+ $data['$payment.custom4'] = ['value' => '', 'label' => ctrans('texts.payment')];
if ($this->entity_string == 'invoice' && $this->entity->payments()->exists()) {
$payment_list = '
';
@@ -647,6 +651,15 @@ class HtmlEngine
}
$data['$payments'] = ['value' => $payment_list, 'label' => ctrans('texts.payments')];
+
+
+ $payment = $this->entity->payments()->first();
+
+ $data['$payment.custom1'] = ['value' => $payment->custom_value1, 'label' => $this->helpers->makeCustomField($this->company->custom_fields, 'payment1')];
+ $data['$payment.custom2'] = ['value' => $payment->custom_value2, 'label' => $this->helpers->makeCustomField($this->company->custom_fields, 'payment2')];
+ $data['$payment.custom3'] = ['value' => $payment->custom_value3, 'label' => $this->helpers->makeCustomField($this->company->custom_fields, 'payment3')];
+ $data['$payment.custom4'] = ['value' => $payment->custom_value4, 'label' => $this->helpers->makeCustomField($this->company->custom_fields, 'payment4')];
+
}
if (($this->entity_string == 'invoice' || $this->entity_string == 'recurring_invoice') && isset($this->company?->custom_fields?->company1)) {
@@ -981,9 +994,9 @@ html {
*/
private function buildViewButton(string $link, string $text): string
{
-
-if($this->settings->email_style == 'plain')
- return ''. $text .'';
+ if ($this->settings->email_style == 'plain') {
+ return ''. $text .'';
+ }
return '
diff --git a/app/Utils/Number.php b/app/Utils/Number.php
index 5dc8fd1975b5..3876bb3da385 100644
--- a/app/Utils/Number.php
+++ b/app/Utils/Number.php
@@ -238,9 +238,9 @@ class Number
$precision = 2;
} elseif ($v < 1) {
$precision = strlen($v) - strrpos($v, '.') - 1;
- }
+ }
- if(is_array($parts) && $parts[0] != 0) {
+ if (is_array($parts) && $parts[0] != 0) {
$precision = 2;
}
@@ -254,7 +254,6 @@ class Number
} elseif ($swapSymbol) {
return "{$value} ".trim($symbol);
} elseif ($entity->getSetting('show_currency_code') === false) {
-
if ($_value < 0) {
$value = substr($value, 1);
$symbol = "-{$symbol}";
diff --git a/app/Utils/PaymentHtmlEngine.php b/app/Utils/PaymentHtmlEngine.php
index 48d847f37c0c..399446aa68c9 100644
--- a/app/Utils/PaymentHtmlEngine.php
+++ b/app/Utils/PaymentHtmlEngine.php
@@ -11,12 +11,10 @@
namespace App\Utils;
-
use App\Models\Client;
-use App\Utils\Helpers;
+use App\Models\ClientContact;
use App\Models\Company;
use App\Models\Payment;
-use App\Models\ClientContact;
use App\Utils\Traits\MakesDates;
use Illuminate\Support\Facades\App;
@@ -54,7 +52,7 @@ class PaymentHtmlEngine
App::setLocale($this->contact->preferredLocale());
$t->replace(Ninja::transformTranslations($this->client->getMergedSettings()));
- $data = [];
+ $data = [];
$data['$from'] = ['value' => '', 'label' => ctrans('texts.from')];
$data['$to'] = ['value' => '', 'label' => ctrans('texts.to')];
@@ -190,7 +188,6 @@ class PaymentHtmlEngine
array_multisort($arrKeysLength, SORT_DESC, $data);
return $data;
-
}
private function formatInvoiceField($field)
@@ -342,8 +339,4 @@ class PaymentHtmlEngine
';
}
-
-
-
-
-}
\ No newline at end of file
+}
diff --git a/app/Utils/TemplateEngine.php b/app/Utils/TemplateEngine.php
index 778a0083fcfc..c0f4292da9d4 100644
--- a/app/Utils/TemplateEngine.php
+++ b/app/Utils/TemplateEngine.php
@@ -12,28 +12,27 @@
namespace App\Utils;
-use DB;
-use App\Models\Quote;
-use App\Models\Client;
-use App\Models\Vendor;
-use App\Models\Invoice;
-use App\Models\Payment;
-use Illuminate\Support\Str;
-use App\Models\ClientContact;
-use App\Models\PurchaseOrder;
-use App\Models\VendorContact;
-use App\Services\Pdf\PdfMock;
-use App\Models\QuoteInvitation;
-use App\Utils\Traits\MakesHash;
-use App\Models\InvoiceInvitation;
-use Illuminate\Support\Facades\App;
-use App\Utils\Traits\MakesInvoiceHtml;
-use App\Mail\Engine\PaymentEmailEngine;
-use App\Models\PurchaseOrderInvitation;
-use App\Utils\Traits\MakesTemplateData;
use App\DataMapper\EmailTemplateDefaults;
-use League\CommonMark\CommonMarkConverter;
+use App\Mail\Engine\PaymentEmailEngine;
+use App\Models\Client;
+use App\Models\ClientContact;
+use App\Models\Invoice;
+use App\Models\InvoiceInvitation;
+use App\Models\Payment;
+use App\Models\PurchaseOrder;
+use App\Models\PurchaseOrderInvitation;
+use App\Models\Quote;
+use App\Models\QuoteInvitation;
+use App\Models\Vendor;
+use App\Models\VendorContact;
use App\Services\PdfMaker\Designs\Utilities\DesignHelpers;
+use App\Utils\Traits\MakesHash;
+use App\Utils\Traits\MakesInvoiceHtml;
+use App\Utils\Traits\MakesTemplateData;
+use DB;
+use Illuminate\Support\Facades\App;
+use Illuminate\Support\Str;
+use League\CommonMark\CommonMarkConverter;
class TemplateEngine
{
@@ -97,19 +96,15 @@ class TemplateEngine
if (strlen($this->entity) > 1 && strlen($this->entity_id) > 1) {
$class = 'App\Models\\' . ucfirst(Str::camel($this->entity));
$this->entity_obj = $class::withTrashed()->where('id', $this->decodePrimaryKey($this->entity_id))->company()->first();
- }
- elseif(stripos($this->template, 'quote') !== false && $quote = Quote::whereHas('invitations')->withTrashed()->company()->first()){
+ } elseif (stripos($this->template, 'quote') !== false && $quote = Quote::whereHas('invitations')->withTrashed()->company()->first()) {
$this->entity = 'quote';
$this->entity_obj = $quote;
- }
- elseif(stripos($this->template, 'purchase') !== false && $purchase_order = PurchaseOrder::whereHas('invitations')->withTrashed()->company()->first()){
+ } elseif (stripos($this->template, 'purchase') !== false && $purchase_order = PurchaseOrder::whereHas('invitations')->withTrashed()->company()->first()) {
$this->entity = 'purchase_order';
$this->entity_obj = $purchase_order;
- }
- elseif ($invoice = Invoice::whereHas('invitations')->withTrashed()->company()->first()){
+ } elseif ($invoice = Invoice::whereHas('invitations')->withTrashed()->company()->first()) {
$this->entity_obj = $invoice;
- }
- else {
+ } else {
$this->mockEntity();
}
@@ -196,7 +191,6 @@ class TemplateEngine
private function entityValues($contact)
{
-
if (in_array($this->entity, ['purchaseOrder', 'purchase_order'])) {
$this->labels_and_values = (new VendorHtmlEngine($this->entity_obj->invitations->first()))->generateLabelsAndValues();
} elseif ($this->entity == 'payment') {
@@ -407,7 +401,6 @@ class TemplateEngine
$this->entity_obj->load('client');
$client->setRelation('company', auth()->user()->company());
$client->load('company');
-
}
}
diff --git a/app/Utils/Traits/Uploadable.php b/app/Utils/Traits/Uploadable.php
index 2e3987a329fe..6f24bd21b272 100644
--- a/app/Utils/Traits/Uploadable.php
+++ b/app/Utils/Traits/Uploadable.php
@@ -13,7 +13,6 @@ namespace App\Utils\Traits;
use App\Jobs\Util\UnlinkFile;
use App\Jobs\Util\UploadAvatar;
-use Illuminate\Support\Facades\Storage;
/**
* Class Uploadable.
diff --git a/app/Utils/VendorHtmlEngine.php b/app/Utils/VendorHtmlEngine.php
index 87072df5b703..0910c318c2ff 100644
--- a/app/Utils/VendorHtmlEngine.php
+++ b/app/Utils/VendorHtmlEngine.php
@@ -808,11 +808,9 @@ html {
*/
private function buildViewButton(string $link, string $text): string
{
-
-
-if ($this->settings->email_style == 'plain') {
- return '
'. $text .'';
-}
+ if ($this->settings->email_style == 'plain') {
+ return '
'. $text .'';
+ }
return '
diff --git a/config/broadcasting.php b/config/broadcasting.php
index 3d0c7cae8053..b5e1decc60ca 100644
--- a/config/broadcasting.php
+++ b/config/broadcasting.php
@@ -15,7 +15,7 @@ return [
|
*/
- 'default' => env('BROADCAST_DRIVER', 'null'),
+ 'default' => env('BROADCAST_DRIVER', 'log'),
/*
|--------------------------------------------------------------------------
@@ -32,9 +32,9 @@ return [
'pusher' => [
'driver' => 'pusher',
- 'key' => env('PUSHER_APP_KEY'),
- 'secret' => env('PUSHER_APP_SECRET'),
- 'app_id' => env('PUSHER_APP_ID'),
+ 'key' => env('PUSHER_APP_KEY',''),
+ 'secret' => env('PUSHER_APP_SECRET',''),
+ 'app_id' => env('PUSHER_APP_ID',''),
'options' => [
'host' => env('PUSHER_HOST', 'api-'.env('PUSHER_APP_CLUSTER', 'mt1').'.pusher.com'),
'port' => env('PUSHER_PORT', 443),
diff --git a/config/cache.php b/config/cache.php
index d35901c5bbc9..dc2f8766b2f0 100644
--- a/config/cache.php
+++ b/config/cache.php
@@ -17,6 +17,7 @@ return [
'default' => env('CACHE_DRIVER', 'file'),
+ 'limiter' => 'redis',
/*
|--------------------------------------------------------------------------
| Cache Stores
@@ -30,7 +31,6 @@ return [
| "memcached", "redis", "dynamodb", "octane", "null"
|
*/
-
'stores' => [
'apc' => [
diff --git a/config/logging.php b/config/logging.php
index 5be233cfdc7f..9a4f1f01f4c7 100644
--- a/config/logging.php
+++ b/config/logging.php
@@ -56,12 +56,14 @@ return [
'driver' => 'single',
'path' => storage_path('logs/invoiceninja.log'),
'level' => env('LOG_LEVEL', 'debug'),
+ 'days' => 7,
],
'stack' => [
'driver' => 'stack',
'channels' => ['single'],
'ignore_exceptions' => false,
+ 'days' => 7,
],
'single' => [
diff --git a/config/ninja.php b/config/ninja.php
index 39e239aa860e..77d2e642fba9 100644
--- a/config/ninja.php
+++ b/config/ninja.php
@@ -14,8 +14,8 @@ return [
'require_https' => env('REQUIRE_HTTPS', true),
'app_url' => rtrim(env('APP_URL', ''), '/'),
'app_domain' => env('APP_DOMAIN', 'invoicing.co'),
- 'app_version' => '5.5.95',
- 'app_tag' => '5.5.95',
+ 'app_version' => '5.5.96',
+ 'app_tag' => '5.5.96',
'minimum_client_version' => '5.0.16',
'terms_version' => '1.0.1',
'api_secret' => env('API_SECRET', ''),
diff --git a/lang/en/texts.php b/lang/en/texts.php
index aad041a416b3..054f2c91fea4 100644
--- a/lang/en/texts.php
+++ b/lang/en/texts.php
@@ -1191,7 +1191,7 @@ $LANG = array(
'plan_started' => 'Plan Started',
'plan_expires' => 'Plan Expires',
- 'white_label_button' => 'White Label',
+ 'white_label_button' => 'Purchase White Label',
'pro_plan_year_description' => 'One year enrollment in the Invoice Ninja Pro Plan.',
'pro_plan_month_description' => 'One month enrollment in the Invoice Ninja Pro Plan.',
diff --git a/openapi/api-docs.yaml b/openapi/api-docs.yaml
index 92111a435447..7531e69a90ce 100644
--- a/openapi/api-docs.yaml
+++ b/openapi/api-docs.yaml
@@ -13239,6 +13239,1188 @@ components:
########################### Generic filters available across all filter ##################################
schemas:
+ CreditPaymentable:
+ properties:
+ credit_id:
+ description: 'The credit hashed id'
+ type: string
+ example: Opnel5aKBz
+ amount:
+ description: 'The credit amount'
+ type: string
+ example: '2'
+ type: object
+ GenericReportSchema:
+ properties:
+ date_range:
+ description: 'The string representation of the date range of data to be returned'
+ type: string
+ example: last7
+ date_key:
+ description: 'The date column to search between.'
+ type: string
+ example: created_at
+ start_date:
+ description: 'The start date to search between'
+ type: string
+ example: '2000-10-31'
+ end_date:
+ description: 'The end date to search between'
+ type: string
+ example: '2'
+ report_keys:
+ type: array
+ items:
+ description: 'Array of Keys to export'
+ type: string
+ example: '[''name'',''date'']'
+ type: object
+ GroupSetting:
+ properties:
+ id:
+ description: 'The group setting hashed id'
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: 'The user hashed id'
+ type: string
+ example: Opnel5aKBz
+ company_id:
+ description: 'The company hashed id'
+ type: string
+ example: Opnel5aKBz
+ name:
+ description: 'The name of the group'
+ type: string
+ example: 'A groupies group'
+ settings:
+ description: 'The settings object'
+ type: object
+ example: ''
+ type: object
+ InvoicePaymentable:
+ properties:
+ invoice_id:
+ description: ______
+ type: string
+ example: Opnel5aKBz
+ amount:
+ description: ______
+ type: string
+ example: '2'
+ type: object
+
+
+
+
+
+
+ TaskSchedulerSchema:
+ properties:
+ paused:
+ description: 'The scheduler paused state'
+ type: boolean
+ example: 'false'
+ repeat_every:
+ description: 'Accepted values (DAY,WEEK,MONTH,3MONTHS,YEAR)'
+ type: string
+ example: DAY
+ start_from:
+ description: 'Timestamp when we should start the scheduler, default is today'
+ type: integer
+ example: '1652898504'
+ job:
+ description: 'Job, we can find list of available jobs in Scheduler model'
+ type: string
+ example: create_credit_report
+ date_range:
+ description: 'The string representation of the date range of data to be returned'
+ type: string
+ example: last7
+ date_key:
+ description: 'The date column to search between.'
+ type: string
+ example: created_at
+ start_date:
+ description: 'The start date to search between'
+ type: string
+ example: '2022-10-31'
+ end_date:
+ description: 'The end date to search between'
+ type: string
+ example: '2022-10-31'
+ report_keys:
+ type: array
+ items:
+ description: 'Array of Keys to export'
+ type: string
+ example: '[''name'',''date'']'
+ type: object
+ UpdateTaskSchedulerSchema:
+ properties:
+ paused:
+ description: 'The scheduler paused state'
+ type: boolean
+ example: 'false'
+ repeat_every:
+ description: 'Accepted values (DAY,WEEK,MONTH,3MONTHS,YEAR)'
+ type: string
+ example: DAY
+ start_from:
+ description: 'Timestamp when we should start the scheduler, default is today'
+ type: integer
+ example: '1652898504'
+ job:
+ description: 'Job, we can find list of available jobs in Scheduler model'
+ type: string
+ example: create_credit_report
+ date_range:
+ description: 'The string representation of the date range of data to be returned'
+ type: string
+ example: last7
+ date_key:
+ description: 'The date column to search between.'
+ type: string
+ example: created_at
+ start_date:
+ description: 'The start date to search between'
+ type: string
+ example: '2022-10-31'
+ end_date:
+ description: 'The end date to search between'
+ type: string
+ example: '2022-10-31'
+ type: object
+ UpdateJobForASchedulerSchema:
+ properties:
+ job:
+ description: 'Set action name, action names can be found in Scheduler Model'
+ type: string
+ example: create_client_report
+ type: object
+
+ TaskStatus:
+ properties:
+ name:
+ description: 'The task status name'
+ type: string
+ example: Backlog
+ created_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ is_deleted:
+ description: 'A boolean flag determining if the task status has been deleted'
+ type: boolean
+ example: true
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ archived_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ type: object
+ TaxRate:
+ properties:
+ id:
+ description: 'Thie hashed id of the tax'
+ type: string
+ example: Opnel5aKBz
+ name:
+ description: 'The tax name'
+ type: string
+ example: GST
+ rate:
+ description: 'The tax rate'
+ type: number
+ example: '10'
+ is_deleted:
+ description: 'Boolean flag determining if the tax has been deleted'
+ type: boolean
+ example: true
+ type: object
+ Template:
+ properties:
+ html:
+ description: 'The template HTML'
+ type: string
+ example: ''
+ type: object
+
+ AuthenticationError:
+ type: object
+ properties:
+ message:
+ description: 'These credentials do not match our records / Invalid Token'
+ type: string
+ example: 'These credentials do not match our records / Invalid Token'
+ ValidationError:
+ properties:
+ message:
+ description: 'The error message'
+ type: string
+ example: 'The given data was invalid.'
+ errors:
+ properties:
+ value:
+ type: array
+ items:
+ type: string
+ type: object
+ type: object
+ AuthorizationError:
+ properties:
+ message:
+ description: 'Insufficient permissions for this resource.'
+ type: string
+ example: 'Insufficient permissions for this resource.'
+ errors:
+ properties:
+ value:
+ type: array
+ items:
+ type: string
+ type: object
+ type: object
+
+
+ Webhook:
+ properties:
+ id:
+ description: 'The subscription hashed id'
+ type: string
+ example: AS3df3A
+ event_id:
+ description: 'The subscription event id'
+ type: string
+ example: AS3df3A
+ target_url:
+ description: 'The api endpoint'
+ type: string
+ example: AS3df3A
+ format:
+ description: 'JSON or UBL'
+ type: string
+ example: JSON
+ type: object
+ Task:
+ properties:
+ id:
+ description: 'The hashed id of the task'
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: 'The hashed id of the user who created the task'
+ type: string
+ example: Opnel5aKBz
+ assigned_user_id:
+ description: 'The assigned user of the task'
+ type: string
+ example: Opnel5aKBz
+ company_id:
+ description: 'The hashed id of the company'
+ type: string
+ example: Opnel5aKBz
+ client_id:
+ description: 'The hashed if of the client'
+ type: string
+ example: Opnel5aKBz
+ invoice_id:
+ description: 'The hashed id of the invoice associated with the task'
+ type: string
+ example: Opnel5aKBz
+ project_id:
+ description: 'The hashed id of the project associated with the task'
+ type: string
+ example: Opnel5aKBz
+ number:
+ description: 'The number of the task'
+ type: string
+ example: TASK-123
+ time_log:
+ description: 'An array of unix time stamps defining the start and end times of the task'
+ type: string
+ example: '[[1,2],[3,4]]'
+ is_running:
+ description: 'Determines if the task is still running'
+ type: boolean
+ example: true
+ is_deleted:
+ description: 'Boolean flag determining if the task has been deleted'
+ type: boolean
+ example: true
+ task_status_id:
+ description: 'The hashed id of the task status'
+ type: string
+ example: Opnel5aKBz
+ description:
+ description: 'The task description'
+ type: string
+ example: 'A wonder task to work on'
+ duration:
+ description: 'The task duration'
+ type: integer
+ example: ''
+ task_status_order:
+ description: 'The order of the task'
+ type: integer
+ example: '4'
+ custom_value1:
+ description: 'A custom value'
+ type: string
+ example: '2022-10-10'
+ custom_value2:
+ description: 'A custom value'
+ type: string
+ example: $1100
+ custom_value3:
+ description: 'A custom value'
+ type: string
+ example: 'I need help'
+ custom_value4:
+ description: 'A custom value'
+ type: string
+ example: INV-3343
+ created_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ archived_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ type: object
+ RecurringInvoice:
+ properties:
+ id:
+ description: 'The hashed id of the recurring invoice'
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: 'The user hashed id'
+ type: string
+ example: Opnel5aKBz
+ assigned_user_id:
+ description: 'The assigned user hashed id'
+ type: string
+ example: Opnel5aKBz
+ company_id:
+ description: 'The company hashed id'
+ type: string
+ example: Opnel5aKBz
+ client_id:
+ description: 'The client hashed id'
+ type: string
+ example: Opnel5aKBz
+ status_id:
+ description: 'The invoice status variable'
+ type: string
+ example: '4'
+ frequency_id:
+ description: 'The recurring invoice frequency'
+ type: number
+ example: '4'
+ remaining_cycles:
+ description: 'The number of invoices left to be generated'
+ type: number
+ example: '4'
+ number:
+ description: 'The recurringinvoice number - is a unique alpha numeric number per invoice per company'
+ type: string
+ example: INV_101
+ po_number:
+ description: 'The purchase order associated with this recurring invoice'
+ type: string
+ example: PO-1234
+ terms:
+ description: 'The invoice terms'
+ type: string
+ example: 'These are invoice terms'
+ public_notes:
+ description: 'The public notes of the invoice'
+ type: string
+ example: 'These are some public notes'
+ private_notes:
+ description: 'The private notes of the invoice'
+ type: string
+ example: 'These are some private notes'
+ footer:
+ description: 'The invoice footer notes'
+ type: string
+ example: ''
+ custom_value1:
+ description: 'A custom field value'
+ type: string
+ example: '2022-10-01'
+ custom_value2:
+ description: 'A custom field value'
+ type: string
+ example: 'Something custom'
+ custom_value3:
+ description: 'A custom field value'
+ type: string
+ example: ''
+ custom_value4:
+ description: 'A custom field value'
+ type: string
+ example: ''
+ tax_name1:
+ description: 'The tax name'
+ type: string
+ example: ''
+ tax_name2:
+ description: 'The tax name'
+ type: string
+ example: ''
+ tax_rate1:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ tax_rate2:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ tax_name3:
+ description: 'The tax name'
+ type: string
+ example: ''
+ tax_rate3:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ total_taxes:
+ description: 'The total taxes for the invoice'
+ type: number
+ format: float
+ example: '10.00'
+ line_items:
+ description: 'An array of objects which define the line items of the invoice'
+ type: object
+ example: ''
+ amount:
+ description: 'The invoice amount'
+ type: number
+ format: float
+ example: '10.00'
+ balance:
+ description: 'The invoice balance'
+ type: number
+ format: float
+ example: '10.00'
+ paid_to_date:
+ description: 'The amount paid on the invoice to date'
+ type: number
+ format: float
+ example: '10.00'
+ discount:
+ description: 'The invoice discount, can be an amount or a percentage'
+ type: number
+ format: float
+ example: '10.00'
+ partial:
+ description: 'The deposit/partial amount'
+ type: number
+ format: float
+ example: '10.00'
+ is_amount_discount:
+ description: 'Flag determining if the discount is an amount or a percentage'
+ type: boolean
+ example: true
+ is_deleted:
+ description: 'Defines if the invoice has been deleted'
+ type: boolean
+ example: true
+ uses_inclusive_taxes:
+ description: 'Defines the type of taxes used as either inclusive or exclusive'
+ type: boolean
+ example: true
+ date:
+ description: 'The Invoice Date'
+ type: string
+ format: date
+ example: '1994-07-30'
+ last_sent_date:
+ description: 'The last date the invoice was sent out'
+ type: string
+ format: date
+ example: '1994-07-30'
+ next_send_date:
+ description: 'The Next date for a reminder to be sent'
+ type: string
+ format: date
+ example: '1994-07-30'
+ partial_due_date:
+ description: 'The due date for the deposit/partial amount'
+ type: string
+ format: date
+ example: '1994-07-30'
+ due_date:
+ description: 'The due date of the invoice'
+ type: string
+ format: date
+ example: '1994-07-30'
+ settings:
+ $ref: '#/components/schemas/CompanySettings'
+ last_viewed:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ archived_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ custom_surcharge1:
+ description: 'First Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge2:
+ description: 'Second Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge3:
+ description: 'Third Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge4:
+ description: 'Fourth Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge_tax1:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ custom_surcharge_tax2:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ custom_surcharge_tax3:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ custom_surcharge_tax4:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ type: object
+
+ Client:
+ properties:
+ id:
+ description: 'The unique identifier of the client'
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: 'The unique identifier of the user who created the client'
+ type: string
+ example: Ua6Rw4pVbS
+ company_id:
+ description: 'The unique identifier of the company the client belongs to'
+ type: string
+ example: Co7Vn3yLmW
+ contacts:
+ type: array
+ items:
+ $ref: '#/components/schemas/ClientContact'
+ name:
+ description: 'The name of the client company or organization'
+ type: string
+ example: "Jim's Housekeeping"
+ website:
+ description: 'The website URL of the client company or organization'
+ type: string
+ example: 'https://www.jims-housekeeping.com'
+ private_notes:
+ description: 'Notes that are only visible to the user who created the client'
+ type: string
+ example: 'Client prefers email communication over phone calls'
+ client_hash:
+ description: 'A unique hash value for the client'
+ type: string
+ example: asdfkjhk342hjhbfdvmnfb1
+ industry_id:
+ description: 'The unique identifier of the industry the client operates in'
+ type: number
+ example: '5'
+ size_id:
+ description: 'The unique identifier for the size category of the client company or organization'
+ type: number
+ example: '2'
+ address1:
+ description: "First line of the client's address"
+ type: string
+ example: '123 Main St'
+ address2:
+ description: "Second line of the client's address, if needed"
+ type: string
+ example: 'Apt 4B'
+ city:
+ description: 'The city the client is located in'
+ type: string
+ example: 'Beverly Hills'
+ state:
+ description: 'The state, province, or locality the client is located in'
+ type: string
+ example: 'California'
+ postal_code:
+ description: 'The postal code or ZIP code of the client'
+ type: string
+ example: '90210'
+ phone:
+ description: "The client's phone number"
+ type: string
+ example: '555-3434-3434'
+ country_id:
+ description: "The unique identifier of the client's country"
+ type: number
+ format: integer
+ example: '1'
+ custom_value1:
+ description: 'A custom field for storing additional information'
+ type: string
+ example: 'Preferred contact: Email'
+ custom_value2:
+ description: 'A custom field for storing additional information'
+ type: string
+ example: 'Account manager: John Doe'
+ custom_value3:
+ description: 'A custom field for storing additional information'
+ type: string
+ example: 'VIP client: Yes'
+ custom_value4:
+ description: 'A custom field for storing additional information'
+ type: string
+ example: 'Annual contract value: $50,000'
+ vat_number:
+ description: "The client's VAT (Value Added Tax) number, if applicable"
+ type: string
+ example: 'VAT123456'
+ id_number:
+ description: 'A unique identification number for the client, such as a tax ID or business registration number'
+ type: string
+ number:
+ description: 'A system-assigned unique number for the client, typically used for invoicing purposes'
+ type: string
+ example: 'CL-0001'
+ shipping_address1:
+ description: "First line of the client's shipping address"
+ type: string
+ example: '5 Wallaby Way'
+ shipping_address2:
+ description: "Second line of the client's shipping address, if needed"
+ type: string
+ example: 'Suite 5'
+ shipping_city:
+ description: "The city of the client's shipping address"
+ type: string
+ example: 'Perth'
+ shipping_state:
+ description: "The state, province, or locality of the client's shipping address"
+ type: string
+ example: 'Western Australia'
+ shipping_postal_code:
+ description: "The postal code or ZIP code of the client's shipping address"
+ type: string
+ example: '6110'
+ shipping_country_id:
+ description: "The unique identifier of the country for the client's shipping address"
+ type: number
+ format: integer
+ example: '4'
+ is_deleted:
+ description: 'A boolean value indicating whether the client has been deleted or not'
+ type: boolean
+ example: false
+ balance:
+ description: 'The outstanding balance the client owes'
+ type: number
+ format: float
+ example: '500.00'
+ paid_to_date:
+ description: 'The total amount the client has paid to date'
+ type: number
+ format: float
+ example: '2000.00'
+ credit_balance:
+ description: 'The available credit balance for the client to use on future purchases'
+ type: number
+ format: float
+ example: '100.00'
+ last_login:
+ description: "The timestamp of the client's last login"
+ type: number
+ format: integer
+ example: '1628686031'
+ created_at:
+ description: 'The timestamp when the client was created'
+ type: number
+ format: integer
+ example: '1617629031'
+ updated_at:
+ description: 'The timestamp when the client was last updated'
+ type: number
+ format: integer
+ example: '1628445631'
+ settings:
+ $ref: '#/components/schemas/CompanySettings'
+ type: object
+ SystemLog:
+ properties:
+ id:
+ description: 'The account hashed id'
+ type: string
+ example: AS3df3A
+ company_id:
+ description: 'The company hashed id'
+ type: string
+ example: AS3df3A
+ user_id:
+ description: 'The user_id hashed id'
+ type: string
+ example: AS3df3A
+ client_id:
+ description: 'The client_id hashed id'
+ type: string
+ example: AS3df3A
+ event_id:
+ description: 'The Log Type ID'
+ type: integer
+ example: 1
+ category_id:
+ description: 'The Category Type ID'
+ type: integer
+ example: 1
+ type_id:
+ description: 'The Type Type ID'
+ type: integer
+ example: 1
+ log:
+ description: 'The json object of the error'
+ type: object
+ example: '{''key'':''value''}'
+ updated_at:
+ description: Timestamp
+ type: string
+ example: '2'
+ created_at:
+ description: Timestamp
+ type: string
+ example: '2'
+ type: object
+ CompanyLedger:
+ properties:
+ entity_id:
+ description: 'This field will reference one of the following entity hashed ID payment_id, invoice_id or credit_id'
+ type: string
+ example: AS3df3A
+ notes:
+ description: 'The notes which reference this entry of the ledger'
+ type: string
+ example: 'Credit note for invoice #3212'
+ balance:
+ description: 'The client balance'
+ type: number
+ format: float
+ example: '10.00'
+ adjustment:
+ description: 'The amount the client balance is adjusted by'
+ type: number
+ format: float
+ example: '10.00'
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ created_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ type: object
+ Credit:
+ properties:
+ id:
+ description: "The unique hashed ID of the credit"
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: "The unique hashed ID of the user associated with the credit"
+ type: string
+ example: 1a2b3c4d5e
+ assigned_user_id:
+ description: "The unique hashed ID of the assigned user responsible for the credit"
+ type: string
+ example: 6f7g8h9i0j
+ company_id:
+ description: "The unique hashed ID of the company associated with the credit"
+ type: string
+ example: k1l2m3n4o5
+ client_id:
+ description: "The unique hashed ID of the client associated with the credit"
+ type: string
+ example: p1q2r3s4t5
+ status_id:
+ description: "The ID representing the current status of the credit"
+ type: string
+ example: 3
+ invoice_id:
+ description: "The unique hashed ID of the linked invoice to which the credit is applied"
+ type: string
+ example: u1v2w3x4y5
+ number:
+ description: "The unique alphanumeric credit number per company"
+ type: string
+ example: QUOTE_101
+ po_number:
+ description: "The purchase order number referred to by the credit"
+ type: string
+ example: PO_12345
+ terms:
+ description: "The terms associated with the credit"
+ type: string
+ example: "Net 30"
+ public_notes:
+ description: "Public notes for the credit"
+ type: string
+ example: "Thank you for your business."
+ private_notes:
+ description: "Private notes for internal use, not visible to the client"
+ type: string
+ example: "Client is requesting a discount."
+ footer:
+ description: "The footer text for the credit"
+ type: string
+ example: "Footer text goes here."
+ custom_value1:
+ description: "Custom value 1 for additional credit information"
+ type: string
+ example: "Custom data 1"
+ custom_value2:
+ description: "Custom value 2 for additional credit information"
+ type: string
+ example: "Custom data 2"
+ custom_value3:
+ description: "Custom value 3 for additional credit information"
+ type: string
+ example: "Custom data 3"
+ custom_value4:
+ description: "Custom value 4 for additional credit information"
+ type: string
+ example: "Custom data 4"
+ tax_name1:
+ description: "The name of the first tax applied to the credit"
+ type: string
+ example: "VAT"
+ tax_name2:
+ description: "The name of the second tax applied to the credit"
+ type: string
+ example: "GST"
+ tax_rate1:
+ description: "The rate of the first tax applied to the credit"
+ type: number
+ format: float
+ example: 10.00
+ tax_rate2:
+ description: "The rate of the second tax applied to the credit"
+ type: number
+ format: float
+ example: 5.00
+ tax_name3:
+ description: "The name of the third tax applied to the credit"
+ type: string
+ example: "PST"
+ tax_rate3:
+ description: "The rate of the third tax applied to the credit"
+ type: number
+ format: float
+ example: 8.00
+ total_taxes:
+ description: "The total amount of taxes for the credit"
+ type: number
+ format: float
+ example: 23.00
+ line_items:
+ type: array
+ description: 'An array of objects which define the line items of the credit'
+ items:
+ $ref: '#/components/schemas/InvoiceItem'
+ amount:
+ description: "The total amount of the credit"
+ type: number
+ format: float
+ example: 100.00
+ balance:
+ description: "The outstanding balance of the credit"
+ type: number
+ format: float
+ example: 50.00
+ paid_to_date:
+ description: "The total amount paid to date for the credit"
+ type: number
+ format: float
+ example: 50.00
+ discount:
+ description: "The discount applied to the credit"
+ type: number
+ format: float
+ example: 10.00
+ partial:
+ description: "The partial amount applied to the credit"
+ type: number
+ format: float
+ example: 20.00
+ is_amount_discount:
+ description: "Indicates whether the discount applied is a fixed amount or a percentage"
+ type: boolean
+ example: true
+ is_deleted:
+ description: "Indicates whether the credit has been deleted"
+ type: boolean
+ example: false
+ uses_inclusive_taxes:
+ description: "Indicates whether the tax rates applied to the credit are inclusive or exclusive"
+ type: boolean
+ example: true
+ date:
+ description: "The date the credit was issued"
+ type: string
+ format: date
+ example: "1994-07-30"
+ last_sent_date:
+ description: "The date the credit was last sent out"
+ type: string
+ format: date
+ example: "1994-07-30"
+ next_send_date:
+ description: "The next scheduled date for sending a credit reminder"
+ type: string
+ format: date
+ example: "1994-07-30"
+ partial_due_date:
+ description: "The due date for the partial amount of the credit"
+ type: string
+ format: date
+ example: "1994-07-30"
+ due_date:
+ description: "The due date for the total amount of the credit"
+ type: string
+ format: date
+ example: "1994-07-30"
+ settings:
+ $ref: "#/components/schemas/CompanySettings"
+ last_viewed:
+ description: "The timestamp of the last time the credit was viewed"
+ type: number
+ format: integer
+ example: 1434342123
+ updated_at:
+ description: "The timestamp of the last time the credit was updated"
+ type: number
+ format: integer
+ example: 1434342123
+ archived_at:
+ description: "The timestamp of the last time the credit was archived"
+ type: number
+ format: integer
+ example: 1434342123
+ custom_surcharge1:
+ description: "First custom surcharge amount"
+ type: number
+ format: float
+ example: 10.00
+ custom_surcharge2:
+ description: 'Second Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge3:
+ description: 'Third Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge4:
+ description: 'Fourth Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge_tax1:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ custom_surcharge_tax2:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ custom_surcharge_tax3:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ custom_surcharge_tax4:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ type: object
+ Activity:
+ properties:
+ id:
+ description: 'The id field of the activity'
+ type: string
+ example: Opnel5aKBz
+ activity_type_id:
+ description: 'The activity type id'
+ type: string
+ example: Opnel5aKBz
+ client_id:
+ description: 'The client hashed id'
+ type: string
+ example: Opnel5aKBz
+ company_id:
+ description: 'The company hashed id'
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: 'The user hashed id'
+ type: string
+ example: Opnel5aKBz
+ invoice_id:
+ description: 'The invoice hashed id'
+ type: string
+ example: Opnel5aKBz
+ payment_id:
+ description: 'The payment hashed id'
+ type: string
+ example: Opnel5aKBz
+ credit_id:
+ description: 'The credit hashed id'
+ type: string
+ example: Opnel5aKBz
+ updated_at:
+ description: 'Unixtimestamp the last time the record was updated'
+ type: integer
+ example: '343421434'
+ expense_id:
+ description: 'The expense hashed id'
+ type: string
+ example: Opnel5aKBz
+ is_system:
+ description: 'Defines is the activity was performed by the system'
+ type: boolean
+ example: true
+ contact_id:
+ description: 'The contact hashed id'
+ type: string
+ example: Opnel5aKBz
+ task_id:
+ description: 'The task hashed id'
+ type: string
+ example: Opnel5aKBz
+ notes:
+ description: 'Activity Notes'
+ type: string
+ example: Opnel5aKBz
+ token_id:
+ description: 'The hashed ID of the token who performed the action'
+ type: string
+ example: Opnel5aKBz
+ ip:
+ description: 'The IP Address of the user who performed the action'
+ type: string
+ example: 192.168.1.252
+ user:
+ $ref: '#/components/schemas/User'
+ client:
+ $ref: '#/components/schemas/Client'
+ contact:
+ $ref: '#/components/schemas/ClientContact'
+ recurring_invoice:
+ $ref: '#/components/schemas/RecurringInvoice'
+ invoice:
+ $ref: '#/components/schemas/Invoice'
+ credit:
+ $ref: '#/components/schemas/Credit'
+ quote:
+ $ref: '#/components/schemas/Quote'
+ payment:
+ $ref: '#/components/schemas/Payment'
+ expense:
+ $ref: '#/components/schemas/Expense'
+ task:
+ $ref: '#/components/schemas/Task'
+ purchase_order:
+ $ref: '#/components/schemas/PurchaseOrder'
+ vendor:
+ $ref: '#/components/schemas/Vendor'
+ vendor_contact:
+ $ref: '#/components/schemas/VendorContact'
+ type: object
+ CompanyGateway:
+ properties:
+ id:
+ description: 'The hashed id of the company gateway'
+ type: string
+ example: Opnel5aKBz
+ company_id:
+ description: 'The company hashed id'
+ type: string
+ example: '2'
+ gateway_key:
+ description: 'The gateway key (hash)'
+ type: string
+ example: '2'
+ accepted_credit_cards:
+ description: 'Bitmask representation of cards'
+ type: integer
+ example: '32'
+ require_billing_address:
+ description: 'Determines if the the billing address is required prior to payment.'
+ type: boolean
+ example: true
+ require_shipping_address:
+ description: 'Determines if the the billing address is required prior to payment.'
+ type: boolean
+ example: true
+ config:
+ description: 'The configuration map for the gateway'
+ type: string
+ example: dfadsfdsafsafd
+ update_details:
+ description: 'Determines if the client details should be updated.'
+ type: boolean
+ example: true
+ fees_and_limits:
+ description: 'A mapped collection of the fees and limits for the configured gateway'
+ type: array
+ items:
+ $ref: '#/components/schemas/FeesAndLimits'
+ type: object
+
+
BankTransactionRule:
properties:
id:
@@ -13287,30 +14469,65 @@ components:
type: string
example: AS3df3A
type: object
+ Paymentable:
+ properties:
+ id:
+ description: 'The paymentable hashed id'
+ type: string
+ example: AS3df3A
+ invoice_id:
+ description: 'The invoice hashed id'
+ type: string
+ example: AS3df3A
+ credit_id:
+ description: 'The credit hashed id'
+ type: string
+ example: AS3df3A
+ refunded:
+ description: 'The amount that has been refunded for this payment'
+ type: number
+ format: float
+ example: '10.00'
+ amount:
+ description: 'The amount that has been applied to the payment'
+ type: number
+ format: float
+ example: '10.00'
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ created_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ type: object
Subscription:
properties:
id:
- description: ______
+ description: Unique identifier for the subscription
type: string
example: Opnel5aKBz
user_id:
- description: ______
+ description: Unique identifier for the user associated with the subscription
type: string
- example: Opnel5aKBz
+ example: Ua6Rw4pVbS
product_id:
- description: ______
+ description: Unique identifier for the product associated with the subscription
type: string
- example: Opnel5aKBz
+ example: Pr5Ft7yBmC
company_id:
- description: ______
+ description: Unique identifier for the company associated with the subscription
type: string
- example: Opnel5aKBz
+ example: Co7Vn3yLmW
recurring_invoice_id:
- description: ______
+ description: Unique identifier for the recurring invoice associated with the subscription
type: string
- example: Opnel5aKBz
+ example: Ri2Yt8zJkP
is_recurring:
- description: ______
+ description: Indicates whether the subscription is recurring
type: boolean
example: 'true'
frequency_id:
@@ -13322,61 +14539,61 @@ components:
type: string
example: always
promo_code:
- description: ______
+ description: Promotional code applied to the subscription
type: string
example: PROMOCODE4U
promo_discount:
- description: ______
+ description: Discount percentage or amount applied to the subscription
type: number
example: 10
is_amount_discount:
- description: ______
+ description: Indicates whether the discount is a fixed amount
type: boolean
example: 'true'
allow_cancellation:
- description: ______
+ description: Indicates whether the subscription can be cancelled
type: boolean
example: 'true'
per_seat_enabled:
- description: ______
+ description: Indicates whether the subscription pricing is per seat
type: boolean
example: 'true'
currency_id:
- description: ______
+ description: Unique identifier for the currency used in the subscription
type: integer
example: '1'
max_seats_limit:
- description: ______
+ description: Maximum number of seats allowed for the subscription
type: integer
example: '100'
trial_enabled:
- description: ______
+ description: Indicates whether the subscription has a trial period
type: boolean
example: 'true'
trial_duration:
- description: ______
+ description: Duration of the trial period in days
type: integer
- example: '2'
+ example: '14'
allow_query_overrides:
- description: ______
+ description: Indicates whether query overrides are allowed for the subscription
type: boolean
example: 'true'
allow_plan_changes:
- description: ______
+ description: Indicates whether plan changes are allowed for the subscription
type: boolean
example: 'true'
refund_period:
- description: ______
+ description: Number of days within which refunds can be requested
type: integer
- example: '2'
+ example: '30'
webhook_configuration:
- description: ______
+ description: Webhook configuration for the subscription
type: string
- example: '2'
+ example: 'expand reference for this'
is_deleted:
- description: ______
+ description: Indicates whether the subscription has been deleted
type: boolean
- example: 'true'
+ example: 'false'
archived_at:
description: Timestamp
type: number
@@ -13398,474 +14615,632 @@ components:
items:
type: integer
example: '[0,1,2,3,]'
- ClientContact:
+ Invoice:
properties:
id:
- description: 'The hashed if of the contact'
+ description: 'The invoice hashed id'
type: string
example: Opnel5aKBz
user_id:
- description: 'The hashed id of the user who created the contact'
+ description: 'The user hashed id'
type: string
example: Opnel5aKBz
- company_id:
- description: 'The hashed id of the company'
- type: string
- example: Opnel5aKBz
- client_id:
- description: 'The hashed id of the client'
- type: string
- example: Opnel5aKBz
- first_name:
- description: 'The first name of the contact'
- type: string
- example: John
- last_name:
- description: 'The last name of the contact'
- type: string
- example: Doe
- phone:
- description: 'The phone number of the contact'
- type: string
- example: 555-152-4524
- custom_value1:
- description: 'A Custom field value'
- type: string
- example: ''
- custom_value2:
- description: 'A Custom field value'
- type: string
- example: ''
- custom_value3:
- description: 'A Custom field value'
- type: string
- example: ''
- custom_value4:
- description: 'A Custom field value'
- type: string
- example: ''
- email:
- description: 'The email of the contact'
- type: string
- example: ''
- accepted_terms_version:
- description: 'The terms of service which the contact has accpeted'
- type: string
- example: 'A long set of ToS'
- password:
- description: 'The hashed password of the contact'
- type: string
- example: '*****'
- confirmation-code:
- description: 'The confirmation code used to authenticate the contacts email address'
- type: string
- example: 333-sdjkh34gbasd
- token:
- description: 'A uuid based token.'
- type: string
- example: 333-sdjkh34gbasd
- is_primary:
- description: 'Defines is this contact is the primary contact for the client'
- type: boolean
- example: true
- confirmed:
- description: 'Boolean value confirms the user has confirmed their account.'
- type: boolean
- example: true
- is_locked:
- description: 'Boolean value defines if the contact has been locked out.'
- type: boolean
- example: true
- send_email:
- description: 'Boolean value determines is this contact should receive emails'
- type: boolean
- example: true
- failed_logins:
- description: 'The number of failed logins the contact has had'
- type: number
- format: integer
- example: '3'
- email_verified_at:
- description: 'The date which the contact confirmed their email'
- type: number
- format: integer
- example: '134341234234'
- last_login:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- created_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- deleted_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- type: object
- ClientGatewayToken:
- properties:
- id:
- description: 'The hashed id of the client gateway token'
- type: string
- example: Opnel5aKBz
- company_id:
- description: 'The hashed id of the company'
- type: string
- example: '2'
- client_id:
- description: 'The hashed_id of the client'
- type: string
- example: '2'
- token:
- description: 'The payment token'
- type: string
- example: '2'
- routing_number:
- description: 'THe bank account routing number'
- type: string
- example: '2'
- company_gateway_id:
- description: 'The hashed id of the company gateway'
- type: string
- example: '2'
- is_default:
- description: 'Flag determining if the token is the default payment method'
- type: boolean
- example: 'true'
- type: object
- Client:
- properties:
- id:
- description: 'The hashed id of the client'
- type: string
- example: Opnel5aKBz
- user_id:
- description: 'The hashed id of the user'
- type: string
- example: ''
- company_id:
- description: 'The hashed id of the company'
- type: string
- example: ''
- contacts:
- type: array
- items:
- $ref: '#/components/schemas/ClientContact'
- name:
- description: 'The client name'
- type: string
- example: 'Jims housekeeping'
- website:
- description: 'The client website'
- type: string
- example: www.jims.com
- private_notes:
- description: 'Private notes on the client'
- type: string
- example: 'These are very private notes'
- client_hash:
- description: 'The client hash'
- type: string
- example: asdfkjhk342hjhbfdvmnfb1
- industry_id:
- description: 'The industry id of the client'
- type: number
- example: '5'
- size_id:
- description: 'The size id of the client'
- type: number
- example: '2'
- address1:
- description: 'Address line 1'
- type: string
- example: ''
- address2:
- description: 'Address line 2'
- type: string
- example: ''
- city:
- description: City
- type: string
- example: 'Beverley Hills'
- state:
- description: State/Locality
- type: string
- example: Californnia
- postal_code:
- description: 'Zip / Postal code'
- type: string
- example: '90210'
- phone:
- description: 'The client phone number'
- type: string
- example: 555-3434-3434
- country_id:
- description: 'The client country id'
- type: number
- format: integer
- example: '1'
- custom_value1:
- description: 'A custom value'
- type: string
- example: 'Something custom'
- custom_value2:
- description: 'A custom value'
- type: string
- example: '2002-01-01'
- custom_value3:
- description: 'A custom value'
- type: string
- example: 'Something custom'
- custom_value4:
- description: 'A custom value'
- type: string
- example: 'Something custom'
- vat_number:
- description: 'The client VAT number'
- type: string
- example: VAT123
- id_number:
- description: ' The client id number'
- type: string
- example: CLIENT_ID_NUMBER
- number:
- description: 'The client number - assigned by the system typically'
- type: string
- example: ''
- shipping_address1:
- description: 'The shipping address line 1'
- type: string
- example: '5 Wallaby Way'
- shipping_address2:
- description: 'The shipping address line 2'
- type: string
- example: 'Suite 5'
- shipping_city:
- description: 'The shipping city'
- type: string
- example: Perth
- shipping_state:
- description: 'The shipping state'
- type: string
- example: 'Western Australia'
- shipping_postal_code:
- description: 'The shipping postal code'
- type: string
- example: '6110'
- shipping_country_id:
- description: 'The shipping country id'
- type: number
- format: integer
- example: '4'
- is_deleted:
- description: 'Boolean flagged determining if the client has been deleted'
- type: boolean
- example: true
- balance:
- description: 'The client balance'
- type: number
- format: float
- example: '10.00'
- paid_to_date:
- description: 'The amount the client has paid to date.'
- type: number
- format: float
- example: '10.00'
- credit_balance:
- description: 'An amount which is available to the client for future use.'
- type: number
- format: float
- example: '10.00'
- last_login:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- created_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- settings:
- $ref: '#/components/schemas/CompanySettings'
- type: object
- CompanyGateway:
- properties:
- id:
- description: 'The hashed id of the company gateway'
+ assigned_user_id:
+ description: 'The assigned user hashed id'
type: string
example: Opnel5aKBz
company_id:
description: 'The company hashed id'
type: string
- example: '2'
- gateway_key:
- description: 'The gateway key (hash)'
+ example: Opnel5aKBz
+ client_id:
+ description: 'The client hashed id'
type: string
- example: '2'
- accepted_credit_cards:
- description: 'Bitmask representation of cards'
- type: integer
- example: '32'
- require_billing_address:
- description: 'Determines if the the billing address is required prior to payment.'
- type: boolean
- example: true
- require_shipping_address:
- description: 'Determines if the the billing address is required prior to payment.'
- type: boolean
- example: true
- config:
- description: 'The configuration map for the gateway'
+ example: Opnel5aKBz
+ status_id:
+ description: 'The invoice status variable'
type: string
- example: dfadsfdsafsafd
- update_details:
- description: 'Determines if the client details should be updated.'
- type: boolean
- example: true
- fees_and_limits:
- description: 'A mapped collection of the fees and limits for the configured gateway'
+ example: '4'
+ number:
+ description: 'The invoice number - is a unique alpha numeric number per invoice per company'
+ type: string
+ example: INV_101
+ po_number:
+ description: 'The purchase order associated with this invoice'
+ type: string
+ example: PO-1234
+ terms:
+ description: 'The invoice terms'
+ type: string
+ example: 'These are invoice terms'
+ public_notes:
+ description: 'The public notes of the invoice'
+ type: string
+ example: 'These are some public notes'
+ private_notes:
+ description: 'The private notes of the invoice'
+ type: string
+ example: 'These are some private notes'
+ footer:
+ description: 'The invoice footer notes'
+ type: string
+ example: ''
+ custom_value1:
+ description: 'A custom field value'
+ type: string
+ example: '2022-10-01'
+ custom_value2:
+ description: 'A custom field value'
+ type: string
+ example: 'Something custom'
+ custom_value3:
+ description: 'A custom field value'
+ type: string
+ example: ''
+ custom_value4:
+ description: 'A custom field value'
+ type: string
+ example: ''
+ tax_name1:
+ description: 'The tax name'
+ type: string
+ example: ''
+ tax_name2:
+ description: 'The tax name'
+ type: string
+ example: ''
+ tax_rate1:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ tax_rate2:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ tax_name3:
+ description: 'The tax name'
+ type: string
+ example: ''
+ tax_rate3:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ total_taxes:
+ description: 'The total taxes for the invoice'
+ type: number
+ format: float
+ example: '10.00'
+ line_items:
type: array
+ description: 'An array of objects which define the line items of the invoice'
items:
- $ref: '#/components/schemas/FeesAndLimits'
- type: object
- CompanyLedger:
- properties:
- entity_id:
- description: 'This field will reference one of the following entity hashed ID payment_id, invoice_id or credit_id'
- type: string
- example: AS3df3A
- notes:
- description: 'The notes which reference this entry of the ledger'
- type: string
- example: 'Credit note for invoice #3212'
+ $ref: '#/components/schemas/InvoiceItem'
+
+ amount:
+ description: 'The invoice amount'
+ type: number
+ format: float
+ example: '10.00'
balance:
- description: 'The client balance'
+ description: 'The invoice balance'
type: number
format: float
example: '10.00'
- adjustment:
- description: 'The amount the client balance is adjusted by'
+ paid_to_date:
+ description: 'The amount paid on the invoice to date'
type: number
format: float
example: '10.00'
+ discount:
+ description: 'The invoice discount, can be an amount or a percentage'
+ type: number
+ format: float
+ example: '10.00'
+ partial:
+ description: 'The deposit/partial amount'
+ type: number
+ format: float
+ example: '10.00'
+ is_amount_discount:
+ description: 'Flag determining if the discount is an amount or a percentage'
+ type: boolean
+ example: true
+ is_deleted:
+ description: 'Defines if the invoice has been deleted'
+ type: boolean
+ example: true
+ uses_inclusive_taxes:
+ description: 'Defines the type of taxes used as either inclusive or exclusive'
+ type: boolean
+ example: true
+ date:
+ description: 'The Invoice Date'
+ type: string
+ format: date
+ example: '1994-07-30'
+ last_sent_date:
+ description: 'The last date the invoice was sent out'
+ type: string
+ format: date
+ example: '1994-07-30'
+ next_send_date:
+ description: 'The Next date for a reminder to be sent'
+ type: string
+ format: date
+ example: '1994-07-30'
+ partial_due_date:
+ description: 'The due date for the deposit/partial amount'
+ type: string
+ format: date
+ example: '1994-07-30'
+ due_date:
+ description: 'The due date of the invoice'
+ type: string
+ format: date
+ example: '1994-07-30'
+ settings:
+ $ref: '#/components/schemas/CompanySettings'
+ last_viewed:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
updated_at:
description: Timestamp
type: number
format: integer
example: '1434342123'
- created_at:
+ archived_at:
description: Timestamp
type: number
format: integer
example: '1434342123'
+ custom_surcharge1:
+ description: 'First Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge2:
+ description: 'Second Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge3:
+ description: 'Third Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge4:
+ description: 'Fourth Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge_tax1:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ custom_surcharge_tax2:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ custom_surcharge_tax3:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ custom_surcharge_tax4:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ type: object
+
+ FeesAndLimits:
+ properties:
+ min_limit:
+ description: 'The minimum amount accepted for this gateway'
+ type: string
+ example: '2'
+ max_limit:
+ description: 'The maximum amount accepted for this gateway'
+ type: string
+ example: '2'
+ fee_amount:
+ description: 'The gateway fee amount'
+ type: number
+ format: float
+ example: '2.0'
+ fee_percent:
+ description: 'The gateway fee percentage'
+ type: number
+ format: float
+ example: '2.0'
+ fee_tax_name1:
+ description: 'Fee tax name'
+ type: string
+ example: GST
+ fee_tax_name2:
+ description: 'Fee tax name'
+ type: string
+ example: VAT
+ fee_tax_name3:
+ description: 'Fee tax name'
+ type: string
+ example: 'CA Sales Tax'
+ fee_tax_rate1:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '10.0'
+ fee_tax_rate2:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '17.5'
+ fee_tax_rate3:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '25.0'
+ fee_cap:
+ description: 'If set the fee amount will be no higher than this amount'
+ type: number
+ format: float
+ example: '2.0'
+ adjust_fee_percent:
+ description: 'Adjusts the fee to match the exact gateway fee.'
+ type: boolean
+ example: true
+ type: object
+ BankTransaction:
+ properties:
+ id:
+ description: 'The bank integration hashed id'
+ type: string
+ example: AS3df3A
+ company_id:
+ description: 'The company hashed id'
+ type: string
+ example: AS3df3A
+ user_id:
+ description: 'The user hashed id'
+ type: string
+ example: AS3df3A
+ transaction_id:
+ description: 'The id of the transaction rule'
+ type: integer
+ example: 343434
+ amount:
+ description: 'The transaction amount'
+ type: number
+ example: 10
+ currency_id:
+ description: 'The currency ID of the currency'
+ type: string
+ example: '1'
+ account_type:
+ description: 'The account type'
+ type: string
+ example: creditCard
+ description:
+ description: 'The description of the transaction'
+ type: string
+ example: 'Potato purchases for kevin'
+ category_id:
+ description: 'The category id'
+ type: integer
+ example: 1
+ category_type:
+ description: 'The category description'
+ type: string
+ example: Expenses
+ base_type:
+ description: 'Either CREDIT or DEBIT'
+ type: string
+ example: CREDIT
+ date:
+ description: 'The date of the transaction'
+ type: string
+ example: '2022-09-01'
+ bank_account_id:
+ description: 'The ID number of the bank account'
+ type: integer
+ example: '1'
type: object
Company:
properties:
id:
- description: 'The company hash id'
+ description: "The unique hashed identifier for the company"
type: string
example: WJxbojagwO
size_id:
- description: 'The company size ID'
+ description: "The unique identifier representing the company's size category"
type: string
- example: '1'
+ example: '2'
industry_id:
- description: 'The company industry ID'
+ description: "The unique identifier representing the company's industry category"
type: string
- example: '1'
+ example: '5'
slack_webhook_url:
- description: 'The slack webhook notification URL'
+ description: "The URL for the company's Slack webhook notifications"
type: string
- example: 'https://slack.com/sh328sj'
+ example: 'https://hooks.slack.com/services/T00000000/B00000000/XXXXXXXXXXXXXXXXXXXXXXXX'
google_analytics_key:
- description: 'The google analytics key'
+ description: "The company's Google Analytics tracking ID"
type: string
- example: '1'
+ example: 'UA-123456789-1'
portal_mode:
- description: 'Determines the client facing urls ie: subdomain,domain,iframe'
+ description: "The mode determining how client-facing URLs are structured (e.g., subdomain, domain, or iframe)"
type: string
example: subdomain
subdomain:
- description: 'Specifies the first part of the company domain ie acme in acme.domain.com'
+ description: "The subdomain prefix for the company's domain (e.g., 'acme' in acme.domain.com)"
type: string
- example: aceme
+ example: acme
portal_domain:
- description: 'The fully qualified domain for client facing URLS'
+ description: "The fully qualified domain used for client-facing URLs"
type: string
example: 'https://subdomain.invoicing.co'
enabled_tax_rates:
- description: 'Number of taxes rates used per entity'
+ description: "The number of tax rates used per entity"
type: integer
- example: '1'
+ example: '2'
fill_products:
- description: 'Toggles filling a product description based on product key'
+ description: "A flag determining whether to auto-fill product descriptions based on the product key"
type: boolean
example: true
convert_products:
- description: ___________
+ description: "A flag determining whether to convert products between different types or units"
type: boolean
example: true
update_products:
- description: 'Toggles updating a product description which description changes'
+ description: "A flag determining whether to update product descriptions when the description changes"
type: boolean
example: true
show_product_details:
- description: 'Toggles showing a product description which description changes'
+ description: "A flag determining whether to display product details in the user interface"
type: boolean
example: true
custom_fields:
- description: 'Custom fields map'
+ description: "A mapping of custom fields for various objects within the company"
type: object
enable_product_cost:
- description: 'Show/Hide the product cost field in the UI'
+ description: "A flag determining whether to show or hide the product cost field in the user interface"
type: boolean
example: true
enable_product_quantity:
- description: 'Show/hide the product quantity field (used in the UI to show the default quantity)'
+ description: "A flag determining whether to show or hide the product quantity field in the user interface"
type: boolean
example: true
default_quantity:
- description: 'Enable/Disable whether to use a default quantity'
+ description: "A flag determining whether to use a default quantity for products"
type: boolean
example: true
custom_surcharge_taxes1:
- description: 'Toggles charging taxes on custom surcharge amounts'
+ description: "A flag determining whether to apply taxes on custom surcharge amounts for the first custom surcharge field"
type: boolean
example: true
custom_surcharge_taxes2:
- description: 'Toggles charging taxes on custom surcharge amounts'
+ description: "A flag determining whether to apply taxes on custom surcharge amounts for the second custom surcharge field"
type: boolean
example: true
custom_surcharge_taxes3:
- description: 'Toggles charging taxes on custom surcharge amounts'
+ description: "A flag determining whether to apply taxes on custom surcharge amounts for the third custom surcharge field"
type: boolean
example: true
custom_surcharge_taxes4:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
+ description: "A flag determining whether to apply taxes on custom surcharge amounts for the fourth custom"
logo:
- description: 'The company logo - binary'
- type: object
+ description: "The company logo file in binary format"
+ type: string
+ format: binary
example: logo.png
settings:
$ref: '#/components/schemas/CompanySettings'
type: object
+ Vendor:
+ properties:
+ id:
+ description: 'The hashed id of the vendor'
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: 'The hashed id of the user who created the vendor'
+ type: string
+ example: Opnel5aKBz
+ assigned_user_id:
+ description: 'The hashed id of the assigned user to this vendor'
+ type: string
+ example: Opnel5aKBz
+ company_id:
+ description: 'The hashed id of the company'
+ type: string
+ example: Opnel5aKBz
+ client_id:
+ description: 'The hashed id of the client'
+ type: string
+ example: Opnel5aKBz
+ contacts:
+ type: array
+ items:
+ $ref: '#/components/schemas/VendorContact'
+ name:
+ description: 'The vendor name'
+ type: string
+ example: 'Harry''s cafe de wheels'
+ website:
+ description: 'The website of the vendor'
+ type: string
+ example: www.harry.com
+ private_notes:
+ description: 'The private notes of the vendor'
+ type: string
+ example: 'Shhh, don''t tell the vendor'
+ industry_id:
+ description: 'The industry id of the vendor'
+ type: string
+ example: '1'
+ size_id:
+ description: ________
+ type: string
+ example: ''
+ address1:
+ description: ________
+ type: string
+ example: ''
+ address2:
+ description: ________
+ type: string
+ example: ''
+ city:
+ description: ________
+ type: string
+ example: ''
+ state:
+ description: ________
+ type: string
+ example: ''
+ postal_code:
+ description: ________
+ type: string
+ example: ''
+ phone:
+ description: 'The client phone number'
+ type: string
+ example: 555-3434-3434
+ country_id:
+ description: ________
+ type: string
+ example: ''
+ currency_id:
+ description: ________
+ type: string
+ example: '4'
+ custom_value1:
+ description: ________
+ type: string
+ example: ''
+ custom_value2:
+ description: ________
+ type: string
+ example: ''
+ custom_value3:
+ description: ________
+ type: string
+ example: ''
+ custom_value4:
+ description: ________
+ type: string
+ example: ''
+ vat_number:
+ description: ________
+ type: string
+ example: ''
+ id_number:
+ description: ________
+ type: string
+ example: ''
+ number:
+ description: ________
+ type: string
+ example: ''
+ is_deleted:
+ description: ________
+ type: boolean
+ example: true
+ last_login:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ created_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ settings:
+ $ref: '#/components/schemas/CompanySettings'
+ type: object
+ BankIntegration:
+ properties:
+ id:
+ description: 'The bank integration hashed id'
+ type: string
+ example: AS3df3A
+ company_id:
+ description: 'The company hashed id'
+ type: string
+ example: AS3df3A
+ user_id:
+ description: 'The user hashed id'
+ type: string
+ example: AS3df3A
+ provider_bank_name:
+ description: 'The providers bank name'
+ type: string
+ example: 'Chase Bank'
+ bank_account_id:
+ description: 'The bank account id'
+ type: integer
+ example: '1233434'
+ bank_account_name:
+ description: 'The name of the account'
+ type: string
+ example: 'My Checking Acc'
+ bank_account_number:
+ description: 'The account number'
+ type: string
+ example: '111 234 2332'
+ bank_account_status:
+ description: 'The status of the bank account'
+ type: string
+ example: ACTIVE
+ bank_account_type:
+ description: 'The type of account'
+ type: string
+ example: CREDITCARD
+ balance:
+ description: 'The current bank balance if available'
+ type: number
+ example: '1000000'
+ currency:
+ description: 'iso_3166_3 code'
+ type: string
+ example: USD
+ type: object
+ ExpenseCategory:
+ properties:
+ id:
+ description: 'The expense hashed id'
+ type: string
+ example: Opnel5aKBz
+ name:
+ description: 'The expense category name'
+ type: string
+ example: Accounting
+ user_id:
+ description: 'The user hashed id'
+ type: string
+ example: XS987sD
+ is_deleted:
+ description: 'Flag determining whether the expense category has been deleted'
+ type: boolean
+ example: true
+ updated_at:
+ description: 'The updated at timestamp'
+ type: integer
+ example: '2'
+ created_at:
+ description: 'The created at timestamp'
+ type: integer
+ example: '2'
+ type: object
CompanySettings:
properties:
timezone_id:
@@ -14458,405 +15833,6 @@ components:
type: boolean
example: false
type: object
- CompanyToken:
- properties:
- name:
- description: 'The token name'
- type: string
- example: 'Token Name'
- token:
- description: 'The token value'
- type: string
- example: AS3df3jUUH765fhfd9KJuidj3JShjA
- is_system:
- description: 'Determines whether the token is created by the system rather than a user'
- type: boolean
- example: 'true'
- type: object
- CompanyUser:
- properties:
- permissions:
- description: 'The company user permissions'
- type: string
- example: '[create_invoice]'
- settings:
- description: 'Settings that are used for the frontend applications to store user preferences / metadata'
- type: object
- example: 'json object'
- is_owner:
- description: 'Determines whether the user owns this company'
- type: boolean
- example: true
- is_admin:
- description: 'Determines whether the user is the admin of this company'
- type: boolean
- example: true
- is_locked:
- description: 'Determines whether the users access to this company has been locked'
- type: boolean
- example: true
- updated_at:
- description: 'The last time the record was modified, format Unix Timestamp'
- type: integer
- example: '1231232312321'
- deleted_at:
- description: 'Timestamp when the user was archived, format Unix Timestamp'
- type: integer
- example: '12312312321'
- account:
- $ref: '#/components/schemas/Account'
- company:
- $ref: '#/components/schemas/Company'
- user:
- $ref: '#/components/schemas/User'
- token:
- $ref: '#/components/schemas/CompanyToken'
- type: object
- CreditPaymentable:
- properties:
- credit_id:
- description: 'The credit hashed id'
- type: string
- example: Opnel5aKBz
- amount:
- description: 'The credit amount'
- type: string
- example: '2'
- type: object
- Credit:
- properties:
- id:
- description: 'The credit hashed id'
- type: string
- example: Opnel5aKBz
- user_id:
- description: 'The user hashed id'
- type: string
- example: ''
- assigned_user_id:
- description: 'The assigned user hashed id'
- type: string
- example: ''
- company_id:
- description: 'The company hashed id'
- type: string
- example: ''
- client_id:
- description: 'The client hashed id'
- type: string
- example: ''
- status_id:
- description: 'The status field id infors of the current status of the credit'
- type: string
- example: ''
- invoice_id:
- description: 'The linked invoice this credit is applied to'
- type: string
- example: ''
- number:
- description: 'The credit number - is a unique alpha numeric number per credit per company'
- type: string
- example: QUOTE_101
- po_number:
- description: 'The purchase order number this credit refers to'
- type: string
- example: ''
- terms:
- description: 'The credit terms field'
- type: string
- example: ''
- public_notes:
- description: 'The public notes field of the credit'
- type: string
- example: ''
- private_notes:
- description: 'The private notes field of the credit'
- type: string
- example: ''
- footer:
- description: 'The credit footer text'
- type: string
- example: ''
- custom_value1:
- description: 'A Custom value'
- type: string
- example: ''
- custom_value2:
- description: 'A Custom value'
- type: string
- example: ''
- custom_value3:
- description: 'A Custom value'
- type: string
- example: ''
- custom_value4:
- description: 'A Custom value'
- type: string
- example: ''
- tax_name1:
- description: 'The tax name'
- type: string
- example: ''
- tax_name2:
- description: 'The tax rate'
- type: string
- example: ''
- tax_rate1:
- description: 'The tax name'
- type: number
- format: float
- example: '10.00'
- tax_rate2:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- tax_name3:
- description: 'The tax name'
- type: string
- example: ''
- tax_rate3:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- total_taxes:
- description: 'The total taxes for the credit'
- type: number
- format: float
- example: '10.00'
- line_items:
- description: 'The line items array containing the line items of the credit'
- type: object
- example: ''
- amount:
- description: 'The total credit amount'
- type: number
- format: float
- example: '10.00'
- balance:
- description: 'The credit balance'
- type: number
- format: float
- example: '10.00'
- paid_to_date:
- description: _________
- type: number
- format: float
- example: '10.00'
- discount:
- description: _________
- type: number
- format: float
- example: '10.00'
- partial:
- description: _________
- type: number
- format: float
- example: '10.00'
- is_amount_discount:
- description: _________
- type: boolean
- example: true
- is_deleted:
- description: _________
- type: boolean
- example: true
- uses_inclusive_taxes:
- description: 'Defines the type of taxes used as either inclusive or exclusive'
- type: boolean
- example: true
- date:
- description: 'The Credit Date'
- type: string
- format: date
- example: '1994-07-30'
- last_sent_date:
- description: 'The last date the credit was sent out'
- type: string
- format: date
- example: '1994-07-30'
- next_send_date:
- description: 'The Next date for a reminder to be sent'
- type: string
- format: date
- example: '1994-07-30'
- partial_due_date:
- description: _________
- type: string
- format: date
- example: '1994-07-30'
- due_date:
- description: _________
- type: string
- format: date
- example: '1994-07-30'
- settings:
- $ref: '#/components/schemas/CompanySettings'
- last_viewed:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- archived_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- custom_surcharge1:
- description: 'First Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge2:
- description: 'Second Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge3:
- description: 'Third Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge4:
- description: 'Fourth Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge_tax1:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax2:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax3:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax4:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- type: object
- Design:
- properties:
- id:
- description: 'The design hashed id'
- type: string
- example: AS3df3A
- name:
- description: 'The design name'
- type: string
- example: Beauty
- design:
- description: 'The design HTML'
- type: string
- example: ''
- is_custom:
- description: 'Flag to determine if the design is a custom user design'
- type: boolean
- example: true
- is_active:
- description: 'Flag to determine if the design is available for use'
- type: boolean
- example: true
- is_deleted:
- description: 'Flag to determine if the design is deleted'
- type: boolean
- example: true
- created_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- deleted_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- type: object
- Document:
- properties:
- id:
- description: 'The document hashed id'
- type: string
- example: AS3df3A
- user_id:
- description: 'The user hashed id'
- type: string
- example: ''
- assigned_user_id:
- description: 'The assigned user hashed id'
- type: string
- example: ''
- project_id:
- description: 'The project associated with this document'
- type: string
- example: ''
- vendor_id:
- description: 'The vendor associated with this documents'
- type: string
- example: ''
- name:
- description: 'The document name'
- type: string
- example: Beauty
- url:
- description: 'The document url'
- type: string
- example: Beauty
- preview:
- description: 'The document preview url'
- type: string
- example: Beauty
- type:
- description: 'The document type'
- type: string
- example: Beauty
- disk:
- description: 'The document disk'
- type: string
- example: Beauty
- hash:
- description: 'The document hashed'
- type: string
- example: Beauty
- is_deleted:
- description: 'Flag to determine if the document is deleted'
- type: boolean
- example: true
- is_default:
- description: 'Flag to determine if the document is a default doc'
- type: boolean
- example: true
- created_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- deleted_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- type: object
Error:
properties:
message:
@@ -14868,644 +15844,128 @@ components:
type: integer
example: '500'
type: object
- ExpenseCategory:
- properties:
- id:
- description: 'The expense hashed id'
- type: string
- example: Opnel5aKBz
- name:
- description: 'The expense category name'
- type: string
- example: Accounting
- user_id:
- description: 'The user hashed id'
- type: string
- example: XS987sD
- is_deleted:
- description: 'Flag determining whether the expense category has been deleted'
- type: boolean
- example: true
- updated_at:
- description: 'The updated at timestamp'
- type: integer
- example: '2'
- created_at:
- description: 'The created at timestamp'
- type: integer
- example: '2'
- type: object
- Expense:
- properties:
- id:
- description: 'The expense hashed id'
- type: string
- example: Opnel5aKBz
- user_id:
- description: 'The user hashed id'
- type: string
- example: ''
- assigned_user_id:
- description: 'The assigned user hashed id'
- type: string
- example: ''
- company_id:
- description: 'The company hashed id'
- type: string
- example: ''
- client_id:
- description: 'The client hashed id'
- type: string
- example: ''
- invoice_id:
- description: 'The related invoice hashed id'
- type: string
- example: ''
- bank_id:
- description: 'The bank id related to this expense'
- type: string
- example: ''
- invoice_currency_id:
- description: 'The currency id of the related invoice'
- type: string
- example: ''
- expense_currency_id:
- description: 'The currency id of the expense'
- type: string
- example: ''
- invoice_category_id:
- description: 'The invoice category id'
- type: string
- example: ''
- payment_type_id:
- description: 'The payment type id'
- type: string
- example: ''
- recurring_expense_id:
- description: 'The related recurring expense this expense was created from'
- type: string
- example: ''
- private_notes:
- description: 'The private notes of the expense'
- type: string
- example: ''
- public_notes:
- description: 'The public notes of the expense'
- type: string
- example: ''
- transaction_reference:
- description: 'The transaction references of the expense'
- type: string
- example: ''
- transcation_id:
- description: 'The transaction id of the expense'
- type: string
- example: ''
- custom_value1:
- description: 'A custom value'
- type: string
- example: ''
- custom_value2:
- description: 'A custom value'
- type: string
- example: ''
- custom_value3:
- description: 'A custom value'
- type: string
- example: ''
- custom_value4:
- description: 'A custom value'
- type: string
- example: ''
- tax_name1:
- description: 'Tax name'
- type: string
- example: ''
- tax_name2:
- description: 'Tax name'
- type: string
- example: ''
- tax_rate1:
- description: 'Tax rate'
- type: number
- format: float
- example: '10.00'
- tax_rate2:
- description: 'Tax rate'
- type: number
- format: float
- example: '10.00'
- tax_name3:
- description: 'Tax name'
- type: string
- example: ''
- tax_rate3:
- description: 'Tax rate'
- type: number
- format: float
- example: '10.00'
- amount:
- description: 'The total expense amont'
- type: number
- format: float
- example: '10.00'
- foreign_amount:
- description: 'The total foreign amount of the expense'
- type: number
- format: float
- example: '10.00'
- exchange_rate:
- description: 'The exchange rate at the time of the expense'
- type: number
- format: float
- example: '0.80'
- date:
- description: 'The expense date formate Y-m-d'
- type: string
- example: '2022-12-01'
- payment_date:
- description: 'The date of payment for the expense, format Y-m-d'
- type: string
- example: ''
- should_be_invoiced:
- description: 'Flag whether the expense should be invoiced'
- type: boolean
- example: true
- is_deleted:
- description: 'Boolean determining whether the expense has been deleted'
- type: boolean
- example: true
- invoice_documents:
- description: 'Passing the expense documents over to the invoice'
- type: boolean
- example: true
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- archived_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- type: object
- FeesAndLimits:
- properties:
- min_limit:
- description: 'The minimum amount accepted for this gateway'
- type: string
- example: '2'
- max_limit:
- description: 'The maximum amount accepted for this gateway'
- type: string
- example: '2'
- fee_amount:
- description: 'The gateway fee amount'
- type: number
- format: float
- example: '2.0'
- fee_percent:
- description: 'The gateway fee percentage'
- type: number
- format: float
- example: '2.0'
- fee_tax_name1:
- description: 'Fee tax name'
- type: string
- example: GST
- fee_tax_name2:
- description: 'Fee tax name'
- type: string
- example: VAT
- fee_tax_name3:
- description: 'Fee tax name'
- type: string
- example: 'CA Sales Tax'
- fee_tax_rate1:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.0'
- fee_tax_rate2:
- description: 'The tax rate'
- type: number
- format: float
- example: '17.5'
- fee_tax_rate3:
- description: 'The tax rate'
- type: number
- format: float
- example: '25.0'
- fee_cap:
- description: 'If set the fee amount will be no higher than this amount'
- type: number
- format: float
- example: '2.0'
- adjust_fee_percent:
- description: 'Adjusts the fee to match the exact gateway fee.'
- type: boolean
- example: true
- type: object
FillableInvoice:
properties:
assigned_user_id:
- description: __________
+ description: "The assigned user's hashed ID"
type: string
- example: ''
+ example: 'a1b2c3d4'
client_id:
- description: ________
+ description: "The client's hashed ID"
type: string
- example: ''
+ example: 'x1y2z3a4'
number:
- description: 'The invoice number - is a unique alpha numeric number per invoice per company'
+ description: "The unique alphanumeric invoice number for each invoice per company"
type: string
example: INV_101
po_number:
- description: ________
+ description: "The purchase order number associated with the invoice"
type: string
- example: ''
+ example: 'PO12345'
terms:
- description: ________
+ description: "The terms and conditions for the invoice"
type: string
- example: ''
+ example: 'Net 30'
public_notes:
- description: ________
+ description: "Public notes visible to the client on the invoice"
type: string
- example: ''
+ example: 'Thank you for your business.'
private_notes:
- description: ________
+ description: "Private notes for internal use only"
type: string
- example: ''
+ example: 'Client is a slow payer.'
footer:
- description: ________
+ description: "The footer text displayed on the invoice"
type: string
- example: ''
+ example: 'Authorized Signature'
custom_value1:
- description: ________
+ description: "First custom value for additional information"
type: string
- example: ''
+ example: 'Project ABC'
custom_value2:
- description: ________
+ description: "Second custom value for additional information"
type: string
- example: ''
+ example: 'Department XYZ'
custom_value3:
- description: ________
+ description: "Third custom value for additional information"
type: string
- example: ''
+ example: 'Location 123'
custom_value4:
- description: ________
+ description: "Fourth custom value for additional information"
type: string
- example: ''
+ example: 'Currency USD'
tax_name1:
- description: ________
+ description: "Name of the first tax applied to the invoice"
type: string
- example: ''
+ example: 'VAT'
tax_name2:
- description: ________
+ description: "Name of the second tax applied to the invoice"
type: string
- example: ''
+ example: 'GST'
tax_rate1:
- description: _________
+ description: "Rate of the first tax applied to the invoice"
type: number
- example: '10.00'
+ example: 10.00
tax_rate2:
- description: _________
+ description: "Rate of the second tax applied to the invoice"
type: number
- example: '10.00'
+ example: 5.00
tax_name3:
- description: ________
+ description: "Name of the third tax applied to the invoice"
type: string
- example: ''
+ example: 'PST'
tax_rate3:
- description: _________
+ description: "Rate of the third tax applied to the invoice"
type: number
- example: '10.00'
+ example: 8.00
line_items:
- description: _________
+ description: "Array of line items included in the invoice"
type: object
- example: ''
+ example: "[{item1}, {item2}]"
discount:
- description: _________
+ description: "The discount applied to the invoice"
type: number
- example: '10.00'
+ example: 10.00
partial:
- description: _________
+ description: "The partial amount applied to the invoice"
type: number
- example: '10.00'
+ example: 20.00
is_amount_discount:
- description: _________
- type: boolean
- example: '1'
- uses_inclusive_taxes:
- description: 'Defines the type of taxes used as either inclusive or exclusive'
- type: boolean
- example: '1'
- date:
- description: 'The Invoice Date'
- type: string
- example: '1994-07-30'
- partial_due_date:
- description: _________
- type: string
- example: '1994-07-30'
- due_date:
- description: _________
- type: string
- example: '1994-07-30'
- custom_surcharge1:
- description: 'First Custom Surcharge'
- type: number
- example: '10.00'
- custom_surcharge2:
- description: 'Second Custom Surcharge'
- type: number
- example: '10.00'
- custom_surcharge3:
- description: 'Third Custom Surcharge'
- type: number
- example: '10.00'
- custom_surcharge4:
- description: 'Fourth Custom Surcharge'
- type: number
- example: '10.00'
- type: object
- GenericReportSchema:
- properties:
- date_range:
- description: 'The string representation of the date range of data to be returned'
- type: string
- example: last7
- date_key:
- description: 'The date column to search between.'
- type: string
- example: created_at
- start_date:
- description: 'The start date to search between'
- type: string
- example: '2000-10-31'
- end_date:
- description: 'The end date to search between'
- type: string
- example: '2'
- report_keys:
- type: array
- items:
- description: 'Array of Keys to export'
- type: string
- example: '[''name'',''date'']'
- type: object
- GroupSetting:
- properties:
- id:
- description: 'The group setting hashed id'
- type: string
- example: Opnel5aKBz
- user_id:
- description: 'The user hashed id'
- type: string
- example: Opnel5aKBz
- company_id:
- description: 'The company hashed id'
- type: string
- example: Opnel5aKBz
- name:
- description: 'The name of the group'
- type: string
- example: 'A groupies group'
- settings:
- description: 'The settings object'
- type: object
- example: ''
- type: object
- InvoicePaymentable:
- properties:
- invoice_id:
- description: ______
- type: string
- example: Opnel5aKBz
- amount:
- description: ______
- type: string
- example: '2'
- type: object
- Invoice:
- properties:
- id:
- description: 'The invoice hashed id'
- type: string
- example: Opnel5aKBz
- user_id:
- description: 'The user hashed id'
- type: string
- example: Opnel5aKBz
- assigned_user_id:
- description: 'The assigned user hashed id'
- type: string
- example: Opnel5aKBz
- company_id:
- description: 'The company hashed id'
- type: string
- example: Opnel5aKBz
- client_id:
- description: 'The client hashed id'
- type: string
- example: Opnel5aKBz
- status_id:
- description: 'The invoice status variable'
- type: string
- example: '4'
- number:
- description: 'The invoice number - is a unique alpha numeric number per invoice per company'
- type: string
- example: INV_101
- po_number:
- description: 'The purchase order associated with this invoice'
- type: string
- example: PO-1234
- terms:
- description: 'The invoice terms'
- type: string
- example: 'These are invoice terms'
- public_notes:
- description: 'The public notes of the invoice'
- type: string
- example: 'These are some public notes'
- private_notes:
- description: 'The private notes of the invoice'
- type: string
- example: 'These are some private notes'
- footer:
- description: 'The invoice footer notes'
- type: string
- example: ''
- custom_value1:
- description: 'A custom field value'
- type: string
- example: '2022-10-01'
- custom_value2:
- description: 'A custom field value'
- type: string
- example: 'Something custom'
- custom_value3:
- description: 'A custom field value'
- type: string
- example: ''
- custom_value4:
- description: 'A custom field value'
- type: string
- example: ''
- tax_name1:
- description: 'The tax name'
- type: string
- example: ''
- tax_name2:
- description: 'The tax name'
- type: string
- example: ''
- tax_rate1:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- tax_rate2:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- tax_name3:
- description: 'The tax name'
- type: string
- example: ''
- tax_rate3:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- total_taxes:
- description: 'The total taxes for the invoice'
- type: number
- format: float
- example: '10.00'
- line_items:
- description: 'An array of objects which define the line items of the invoice'
- type: object
- example: ''
- amount:
- description: 'The invoice amount'
- type: number
- format: float
- example: '10.00'
- balance:
- description: 'The invoice balance'
- type: number
- format: float
- example: '10.00'
- paid_to_date:
- description: 'The amount paid on the invoice to date'
- type: number
- format: float
- example: '10.00'
- discount:
- description: 'The invoice discount, can be an amount or a percentage'
- type: number
- format: float
- example: '10.00'
- partial:
- description: 'The deposit/partial amount'
- type: number
- format: float
- example: '10.00'
- is_amount_discount:
- description: 'Flag determining if the discount is an amount or a percentage'
- type: boolean
- example: true
- is_deleted:
- description: 'Defines if the invoice has been deleted'
+ description: "Indicates whether the discount applied is a fixed amount or a percentage"
type: boolean
example: true
uses_inclusive_taxes:
- description: 'Defines the type of taxes used as either inclusive or exclusive'
+ description: "Indicates whether the tax rates applied to the invoice are inclusive or exclusive"
type: boolean
example: true
date:
- description: 'The Invoice Date'
+ description: "The date the invoice was issued"
type: string
- format: date
- example: '1994-07-30'
- last_sent_date:
- description: 'The last date the invoice was sent out'
- type: string
- format: date
- example: '1994-07-30'
- next_send_date:
- description: 'The Next date for a reminder to be sent'
- type: string
- format: date
example: '1994-07-30'
partial_due_date:
- description: 'The due date for the deposit/partial amount'
+ description: "The due date for the partial payment"
type: string
- format: date
- example: '1994-07-30'
+ example: '1994-08-15'
due_date:
- description: 'The due date of the invoice'
+ description: "The due date for the invoice"
type: string
- format: date
- example: '1994-07-30'
- settings:
- $ref: '#/components/schemas/CompanySettings'
- last_viewed:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- archived_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
+ example: '1994-08-30'
custom_surcharge1:
- description: 'First Custom Surcharge'
+ description: "First custom surcharge applied to the invoice"
type: number
- format: float
- example: '10.00'
+ example: 10.00
custom_surcharge2:
- description: 'Second Custom Surcharge'
+ description: "Second custom surcharge applied to the invoice"
type: number
- format: float
- example: '10.00'
+ example: 15.00
custom_surcharge3:
- description: 'Third Custom Surcharge'
+ description: "Third custom surcharge applied to the invoice"
type: number
- format: float
- example: '10.00'
+ example: 5.00
custom_surcharge4:
- description: 'Fourth Custom Surcharge'
+ description: "Fourth custom surcharge applied to the invoice"
type: number
- format: float
- example: '10.00'
- custom_surcharge_tax1:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax2:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax3:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax4:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
+ example: 20.00
type: object
Payment:
properties:
@@ -15591,99 +16051,276 @@ components:
type: array
items:
$ref: '#/components/schemas/CreditPaymentable'
- type: object
- PaymentTerm:
- properties:
- num_days:
- description: 'The payment term length in days'
- type: integer
- example: '1'
- name:
- description: 'The payment term length in string format'
+ number:
+ description: 'The payment number - is a unique alpha numeric number per payment per company'
type: string
- example: 'NET 1'
- created_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- archived_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
+ example: PAY_101
type: object
- Paymentable:
+
+ User:
properties:
id:
- description: 'The paymentable hashed id'
- type: string
- example: AS3df3A
- invoice_id:
- description: 'The invoice hashed id'
- type: string
- example: AS3df3A
- credit_id:
- description: 'The credit hashed id'
- type: string
- example: AS3df3A
- refunded:
- description: 'The amount that has been refunded for this payment'
- type: number
- format: float
- example: '10.00'
- amount:
- description: 'The amount that has been applied to the payment'
- type: number
- format: float
- example: '10.00'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- created_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- type: object
- Product:
- properties:
- id:
- description: 'The product hashed id'
+ description: 'The hashed id of the user'
type: string
example: Opnel5aKBz
+ first_name:
+ description: 'The first name of the user'
+ type: string
+ example: Brad
+ last_name:
+ description: 'The last name of the user'
+ type: string
+ example: Pitt
+ email:
+ description: 'The users email address'
+ type: string
+ example: brad@pitt.com
+ phone:
+ description: 'The users phone number'
+ type: string
+ example: 555-1233-23232
+ signature:
+ description: 'The users sign off signature'
+ type: string
+ example: 'Have a nice day!'
+ avatar:
+ description: 'The users avatar'
+ type: string
+ example: 'https://url.to.your/avatar.png'
+ accepted_terms_version:
+ description: 'The version of the invoice ninja terms that has been accepted by the user'
+ type: string
+ example: 1.0.1
+ oauth_user_id:
+ description: 'The provider id of the oauth entity'
+ type: string
+ example: jkhasdf789as6f675sdf768sdfs
+ oauth_provider_id:
+ description: 'The oauth entity id'
+ type: string
+ example: google
type: object
Project:
+ type: object
properties:
id:
description: 'The project hashed id'
type: string
example: Opnel5aKBz
+ user_id:
+ description: 'The user hashed id'
+ type: string
+ example: Opnel5aKBz
+ assigned_user_id:
+ description: The assigned user identifier associated with the project
+ type: string
+ example: Opnel5aKBz
+ client_id:
+ type: string
+ example: Opnel5aKBz
+ description: The client identifier associated with the project
name:
- description: 'The project name'
type: string
+ description: The name of the project
example: 'New Project'
+ task_rate:
+ type: number
+ format: float
+ example: 10
+ description: The default rate per task for the project
+ due_date:
+ type: string
+ format: date
+ example: '2019-01-01'
+ description: The due date for the project
+ private_notes:
+ type: string
+ description: Private notes associated with the project
+ budgeted_hours:
+ type: number
+ format: float
+ description: The number of budgeted hours for the project
+ custom_value1:
+ type: string
+ description: Custom value field 1
+ custom_value2:
+ type: string
+ description: Custom value field 2
+ custom_value3:
+ type: string
+ description: Custom value field 3
+ custom_value4:
+ type: string
+ description: Custom value field 4
+ created_at:
+ type: number
+ format: integer
+ example: 134341234234
+ description: The timestamp of the project creation
+ updated_at:
+ type: number
+ format: integer
+ example: 134341234234
+ description: The timestamp of the last project update
+ archived_at:
+ type: number
+ format: integer
+ example: 134341234234
+ description: The timestamp of the project deletion
+ public_notes:
+ type: string
+ description: Public notes associated with the project
+ is_deleted:
+ type: boolean
+ description: A flag indicating if the project is deleted
+ number:
+ type: string
+ description: The project number
+ color:
+ type: string
+ description: The color associated with the project
+ required:
+ - id
+ - user_id
+ - company_id
+ - name
+ - task_rate
+ - budgeted_hours
+ - is_deleted
+ - color
+
+ InvoiceItem:
type: object
- PurchaseOrder:
+ properties:
+ quantity:
+ type: integer
+ example: 1
+ cost:
+ type: number
+ format: float
+ example: 10.00
+ product_key:
+ type: string
+ example: 'Product key'
+ product_cost:
+ type: number
+ format: float
+ example: 10.00
+ notes:
+ type: string
+ example: 'Item notes'
+ discount:
+ type: number
+ format: float
+ example: 5.00
+ is_amount_discount:
+ type: boolean
+ example: false
+ tax_name1:
+ type: string
+ example: 'Tax name 1'
+ tax_rate1:
+ type: number
+ format: float
+ example: 10.00
+ tax_name2:
+ type: string
+ example: 'Tax name 2'
+ tax_rate2:
+ type: number
+ format: float
+ example: 5.00
+ tax_name3:
+ type: string
+ example: 'Tax name 3'
+ tax_rate3:
+ type: number
+ format: float
+ example: 3.00
+ sort_id:
+ type: string
+ example: '0'
+ line_total:
+ type: number
+ format: float
+ example: 10.00
+ gross_line_total:
+ type: number
+ format: float
+ example: 15.00
+ tax_amount:
+ type: number
+ format: float
+ example: 1.00
+ date:
+ type: string
+ format: date-time
+ example: '2023-03-19T00:00:00Z'
+ custom_value1:
+ type: string
+ example: 'Custom value 1'
+ custom_value2:
+ type: string
+ example: 'Custom value 2'
+ custom_value3:
+ type: string
+ example: 'Custom value 3'
+ custom_value4:
+ type: string
+ example: 'Custom value 4'
+ type_id:
+ type: string
+ example: '1'
+ description: '1 = product, 2 = service, 3 unpaid gateway fee, 4 paid gateway fee, 5 late fee, 6 expense'
+ CompanyUser:
+ properties:
+ permissions:
+ description: 'The company user permissions'
+ type: string
+ example: '[create_invoice]'
+ settings:
+ description: 'Settings that are used for the frontend applications to store user preferences / metadata'
+ type: object
+ example: 'json object'
+ react_settings:
+ description: 'Dedicated settings object for the react web application'
+ type: object'
+ example: 'json object'
+ is_owner:
+ description: 'Determines whether the user owns this company'
+ type: boolean
+ example: true
+ is_admin:
+ description: 'Determines whether the user is the admin of this company'
+ type: boolean
+ example: true
+ is_locked:
+ description: 'Determines whether the users access to this company has been locked'
+ type: boolean
+ example: true
+ updated_at:
+ description: 'The last time the record was modified, format Unix Timestamp'
+ type: integer
+ example: '1231232312321'
+ deleted_at:
+ description: 'Timestamp when the user was archived, format Unix Timestamp'
+ type: integer
+ example: '12312312321'
+ account:
+ $ref: '#/components/schemas/Account'
+ company:
+ $ref: '#/components/schemas/Company'
+ user:
+ $ref: '#/components/schemas/User'
+ token:
+ $ref: '#/components/schemas/CompanyToken'
+ type: object
+ Document:
properties:
id:
- description: 'The purchase order hashed id'
+ description: 'The document hashed id'
type: string
- example: Opnel5aKBz
- type: object
- Quote:
- properties:
- id:
- description: 'The quote hashed id'
- type: string
- example: Opnel5aKBz
+ example: AS3df3A
user_id:
description: 'The user hashed id'
type: string
@@ -15692,209 +16329,103 @@ components:
description: 'The assigned user hashed id'
type: string
example: ''
- company_id:
- description: 'The company hashed id'
+ project_id:
+ description: 'The project associated with this document'
type: string
example: ''
- client_id:
- description: 'The client hashed id'
+ vendor_id:
+ description: 'The vendor associated with this documents'
type: string
example: ''
- status_id:
- description: 'The status of the quote'
+ name:
+ description: 'The document name'
type: string
- example: ''
- number:
- description: 'The quote number - is a unique alpha numeric number per quote per company'
+ example: Beauty
+ url:
+ description: 'The document url'
type: string
- example: QUOTE_101
- po_number:
- description: 'The purchase order number associated with this quote'
+ example: Beauty
+ preview:
+ description: 'The document preview url'
type: string
- example: PO-1234
- terms:
- description: 'The quote terms'
+ example: Beauty
+ type:
+ description: 'The document type'
type: string
- example: 'These are some quote terms. Valid for 14 days.'
- public_notes:
- description: 'Public notes for the quote'
+ example: Beauty
+ disk:
+ description: 'The document disk'
type: string
- example: 'These are public notes which the client may see'
- private_notes:
- description: 'Private notes for the quote'
+ example: Beauty
+ hash:
+ description: 'The document hashed'
type: string
- example: 'These are private notes, not to be disclosed to the client'
- footer:
- description: 'Footer text of quote'
- type: string
- example: 'The text goes in the footer of the quote'
- custom_value1:
- description: 'Custom value field'
- type: string
- example: 'A custom value'
- custom_value2:
- description: 'Custom value field'
- type: string
- example: 'A custom value'
- custom_value3:
- description: 'Custom value field'
- type: string
- example: 'A custom value'
- custom_value4:
- description: 'Custom value field'
- type: string
- example: 'A custom value'
- tax_name1:
- description: 'The tax name'
- type: string
- example: GST
- tax_name2:
- description: 'The tax name'
- type: string
- example: VAT
- tax_rate1:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- tax_rate2:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- tax_name3:
- description: 'The tax name'
- type: string
- example: ''
- tax_rate3:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- total_taxes:
- description: 'The total taxes for the quote'
- type: number
- format: float
- example: '10.00'
- line_items:
- description: 'An array of line items of the quote'
- type: object
- example: ''
- amount:
- description: 'The total amount of the quote'
- type: number
- format: float
- example: '10.00'
- balance:
- description: 'The balance due of the quote'
- type: number
- format: float
- example: '10.00'
- paid_to_date:
- description: 'The amount that has been paid to date on the quote'
- type: number
- format: float
- example: '10.00'
- discount:
- description: 'The quote discount'
- type: number
- format: float
- example: '10.00'
- partial:
- description: 'The partial/deposit amount'
- type: number
- format: float
- example: '10.00'
- is_amount_discount:
- description: 'Boolean flag determining if the quote is an amount or percentage'
- type: boolean
- example: true
+ example: Beauty
is_deleted:
- description: 'Boolean flag determining if the quote has been deleted'
+ description: 'Flag to determine if the document is deleted'
type: boolean
example: true
- uses_inclusive_taxes:
- description: 'Defines the type of taxes used as either inclusive or exclusive'
+ is_default:
+ description: 'Flag to determine if the document is a default doc'
type: boolean
example: true
- date:
- description: 'The Quote Date'
- type: string
- format: date
- example: '1994-07-30'
- last_sent_date:
- description: 'The last date the quote was sent out'
- type: string
- format: date
- example: '1994-07-30'
- next_send_date:
- description: 'The Next date for a reminder to be sent'
- type: string
- format: date
- example: '1994-07-30'
- partial_due_date:
- description: 'The date when the partial/deposit is due'
- type: string
- format: date
- example: '1994-07-30'
- due_date:
- description: 'The date the quote is valid until'
- type: string
- format: date
- example: '1994-07-30'
- settings:
- $ref: '#/components/schemas/CompanySettings'
- last_viewed:
+ created_at:
description: Timestamp
type: number
format: integer
- example: '1434342123'
+ example: '134341234234'
updated_at:
description: Timestamp
type: number
format: integer
- example: '1434342123'
- archived_at:
+ example: '134341234234'
+ deleted_at:
description: Timestamp
type: number
format: integer
- example: '1434342123'
- custom_surcharge1:
- description: 'First Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge2:
- description: 'Second Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge3:
- description: 'Third Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge4:
- description: 'Fourth Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge_tax1:
- description: 'Toggles charging taxes on custom surcharge amounts'
+ example: '134341234234'
+ type: object
+ Design:
+ properties:
+ id:
+ description: 'The design hashed id'
+ type: string
+ example: AS3df3A
+ name:
+ description: 'The design name'
+ type: string
+ example: Beauty
+ design:
+ description: 'The design HTML'
+ type: string
+ example: ''
+ is_custom:
+ description: 'Flag to determine if the design is a custom user design'
type: boolean
example: true
- custom_surcharge_tax2:
- description: 'Toggles charging taxes on custom surcharge amounts'
+ is_active:
+ description: 'Flag to determine if the design is available for use'
type: boolean
example: true
- custom_surcharge_tax3:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax4:
- description: 'Toggles charging taxes on custom surcharge amounts'
+ is_deleted:
+ description: 'Flag to determine if the design is deleted'
type: boolean
example: true
+ created_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ deleted_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
type: object
RecurringExpense:
properties:
@@ -16067,232 +16598,6 @@ components:
format: integer
example: '1434342123'
type: object
- RecurringInvoice:
- properties:
- id:
- description: 'The hashed id of the recurring invoice'
- type: string
- example: Opnel5aKBz
- user_id:
- description: 'The user hashed id'
- type: string
- example: Opnel5aKBz
- assigned_user_id:
- description: 'The assigned user hashed id'
- type: string
- example: Opnel5aKBz
- company_id:
- description: 'The company hashed id'
- type: string
- example: Opnel5aKBz
- client_id:
- description: 'The client hashed id'
- type: string
- example: Opnel5aKBz
- status_id:
- description: 'The invoice status variable'
- type: string
- example: '4'
- frequency_id:
- description: 'The recurring invoice frequency'
- type: number
- example: '4'
- remaining_cycles:
- description: 'The number of invoices left to be generated'
- type: number
- example: '4'
- number:
- description: 'The recurringinvoice number - is a unique alpha numeric number per invoice per company'
- type: string
- example: INV_101
- po_number:
- description: 'The purchase order associated with this recurring invoice'
- type: string
- example: PO-1234
- terms:
- description: 'The invoice terms'
- type: string
- example: 'These are invoice terms'
- public_notes:
- description: 'The public notes of the invoice'
- type: string
- example: 'These are some public notes'
- private_notes:
- description: 'The private notes of the invoice'
- type: string
- example: 'These are some private notes'
- footer:
- description: 'The invoice footer notes'
- type: string
- example: ''
- custom_value1:
- description: 'A custom field value'
- type: string
- example: '2022-10-01'
- custom_value2:
- description: 'A custom field value'
- type: string
- example: 'Something custom'
- custom_value3:
- description: 'A custom field value'
- type: string
- example: ''
- custom_value4:
- description: 'A custom field value'
- type: string
- example: ''
- tax_name1:
- description: 'The tax name'
- type: string
- example: ''
- tax_name2:
- description: 'The tax name'
- type: string
- example: ''
- tax_rate1:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- tax_rate2:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- tax_name3:
- description: 'The tax name'
- type: string
- example: ''
- tax_rate3:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- total_taxes:
- description: 'The total taxes for the invoice'
- type: number
- format: float
- example: '10.00'
- line_items:
- description: 'An array of objects which define the line items of the invoice'
- type: object
- example: ''
- amount:
- description: 'The invoice amount'
- type: number
- format: float
- example: '10.00'
- balance:
- description: 'The invoice balance'
- type: number
- format: float
- example: '10.00'
- paid_to_date:
- description: 'The amount paid on the invoice to date'
- type: number
- format: float
- example: '10.00'
- discount:
- description: 'The invoice discount, can be an amount or a percentage'
- type: number
- format: float
- example: '10.00'
- partial:
- description: 'The deposit/partial amount'
- type: number
- format: float
- example: '10.00'
- is_amount_discount:
- description: 'Flag determining if the discount is an amount or a percentage'
- type: boolean
- example: true
- is_deleted:
- description: 'Defines if the invoice has been deleted'
- type: boolean
- example: true
- uses_inclusive_taxes:
- description: 'Defines the type of taxes used as either inclusive or exclusive'
- type: boolean
- example: true
- date:
- description: 'The Invoice Date'
- type: string
- format: date
- example: '1994-07-30'
- last_sent_date:
- description: 'The last date the invoice was sent out'
- type: string
- format: date
- example: '1994-07-30'
- next_send_date:
- description: 'The Next date for a reminder to be sent'
- type: string
- format: date
- example: '1994-07-30'
- partial_due_date:
- description: 'The due date for the deposit/partial amount'
- type: string
- format: date
- example: '1994-07-30'
- due_date:
- description: 'The due date of the invoice'
- type: string
- format: date
- example: '1994-07-30'
- settings:
- $ref: '#/components/schemas/CompanySettings'
- last_viewed:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- archived_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- custom_surcharge1:
- description: 'First Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge2:
- description: 'Second Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge3:
- description: 'Third Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge4:
- description: 'Fourth Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge_tax1:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax2:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax3:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax4:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- type: object
RecurringQuote:
properties:
id:
@@ -16519,144 +16824,405 @@ components:
type: boolean
example: true
type: object
- SystemLog:
+ BTRules:
+ properties:
+ data_key:
+ description: 'The key to search'
+ type: string
+ example: 'description,amount'
+ operator:
+ description: 'The operator flag of the search'
+ type: string
+ example: '>'
+ value:
+ description: 'The value to search for'
+ type: string
+ example: bob
+ type: object
+ Expense:
properties:
id:
- description: 'The account hashed id'
+ description: 'The expense hashed id'
type: string
- example: AS3df3A
+ example: Opnel5aKBz
+ user_id:
+ description: 'The user hashed id'
+ type: string
+ example: ''
+ assigned_user_id:
+ description: 'The assigned user hashed id'
+ type: string
+ example: ''
company_id:
description: 'The company hashed id'
type: string
- example: AS3df3A
- user_id:
- description: 'The user_id hashed id'
- type: string
- example: AS3df3A
+ example: ''
client_id:
- description: 'The client_id hashed id'
+ description: 'The client hashed id'
type: string
- example: AS3df3A
- event_id:
- description: 'The Log Type ID'
- type: integer
- example: 1
- category_id:
- description: 'The Category Type ID'
- type: integer
- example: 1
- type_id:
- description: 'The Type Type ID'
- type: integer
- example: 1
- log:
- description: 'The json object of the error'
- type: object
- example: '{''key'':''value''}'
+ example: ''
+ invoice_id:
+ description: 'The related invoice hashed id'
+ type: string
+ example: ''
+ bank_id:
+ description: 'The bank id related to this expense'
+ type: string
+ example: ''
+ invoice_currency_id:
+ description: 'The currency id of the related invoice'
+ type: string
+ example: ''
+ expense_currency_id:
+ description: 'The currency id of the expense'
+ type: string
+ example: ''
+ invoice_category_id:
+ description: 'The invoice category id'
+ type: string
+ example: ''
+ payment_type_id:
+ description: 'The payment type id'
+ type: string
+ example: ''
+ recurring_expense_id:
+ description: 'The related recurring expense this expense was created from'
+ type: string
+ example: ''
+ private_notes:
+ description: 'The private notes of the expense'
+ type: string
+ example: ''
+ public_notes:
+ description: 'The public notes of the expense'
+ type: string
+ example: ''
+ transaction_reference:
+ description: 'The transaction references of the expense'
+ type: string
+ example: ''
+ transcation_id:
+ description: 'The transaction id of the expense'
+ type: string
+ example: ''
+ custom_value1:
+ description: 'A custom value'
+ type: string
+ example: ''
+ custom_value2:
+ description: 'A custom value'
+ type: string
+ example: ''
+ custom_value3:
+ description: 'A custom value'
+ type: string
+ example: ''
+ custom_value4:
+ description: 'A custom value'
+ type: string
+ example: ''
+ tax_name1:
+ description: 'Tax name'
+ type: string
+ example: ''
+ tax_name2:
+ description: 'Tax name'
+ type: string
+ example: ''
+ tax_rate1:
+ description: 'Tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ tax_rate2:
+ description: 'Tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ tax_name3:
+ description: 'Tax name'
+ type: string
+ example: ''
+ tax_rate3:
+ description: 'Tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ amount:
+ description: 'The total expense amont'
+ type: number
+ format: float
+ example: '10.00'
+ foreign_amount:
+ description: 'The total foreign amount of the expense'
+ type: number
+ format: float
+ example: '10.00'
+ exchange_rate:
+ description: 'The exchange rate at the time of the expense'
+ type: number
+ format: float
+ example: '0.80'
+ date:
+ description: 'The expense date formate Y-m-d'
+ type: string
+ example: '2022-12-01'
+ payment_date:
+ description: 'The date of payment for the expense, format Y-m-d'
+ type: string
+ example: ''
+ should_be_invoiced:
+ description: 'Flag whether the expense should be invoiced'
+ type: boolean
+ example: true
+ is_deleted:
+ description: 'Boolean determining whether the expense has been deleted'
+ type: boolean
+ example: true
+ invoice_documents:
+ description: 'Passing the expense documents over to the invoice'
+ type: boolean
+ example: true
updated_at:
description: Timestamp
- type: string
- example: '2'
- created_at:
+ type: number
+ format: integer
+ example: '1434342123'
+ archived_at:
description: Timestamp
- type: string
- example: '2'
+ type: number
+ format: integer
+ example: '1434342123'
type: object
- TaskSchedulerSchema:
- properties:
- paused:
- description: 'The scheduler paused state'
- type: boolean
- example: 'false'
- repeat_every:
- description: 'Accepted values (DAY,WEEK,MONTH,3MONTHS,YEAR)'
- type: string
- example: DAY
- start_from:
- description: 'Timestamp when we should start the scheduler, default is today'
- type: integer
- example: '1652898504'
- job:
- description: 'Job, we can find list of available jobs in Scheduler model'
- type: string
- example: create_credit_report
- date_range:
- description: 'The string representation of the date range of data to be returned'
- type: string
- example: last7
- date_key:
- description: 'The date column to search between.'
- type: string
- example: created_at
- start_date:
- description: 'The start date to search between'
- type: string
- example: '2022-10-31'
- end_date:
- description: 'The end date to search between'
- type: string
- example: '2022-10-31'
- report_keys:
- type: array
- items:
- description: 'Array of Keys to export'
- type: string
- example: '[''name'',''date'']'
- type: object
- UpdateTaskSchedulerSchema:
- properties:
- paused:
- description: 'The scheduler paused state'
- type: boolean
- example: 'false'
- repeat_every:
- description: 'Accepted values (DAY,WEEK,MONTH,3MONTHS,YEAR)'
- type: string
- example: DAY
- start_from:
- description: 'Timestamp when we should start the scheduler, default is today'
- type: integer
- example: '1652898504'
- job:
- description: 'Job, we can find list of available jobs in Scheduler model'
- type: string
- example: create_credit_report
- date_range:
- description: 'The string representation of the date range of data to be returned'
- type: string
- example: last7
- date_key:
- description: 'The date column to search between.'
- type: string
- example: created_at
- start_date:
- description: 'The start date to search between'
- type: string
- example: '2022-10-31'
- end_date:
- description: 'The end date to search between'
- type: string
- example: '2022-10-31'
- type: object
- UpdateJobForASchedulerSchema:
- properties:
- job:
- description: 'Set action name, action names can be found in Scheduler Model'
- type: string
- example: create_client_report
- type: object
- Task:
+ PurchaseOrder:
properties:
id:
- description: 'The hashed id of the task'
+ description: 'The unique hashed identifier for the purchase order'
type: string
example: Opnel5aKBz
user_id:
- description: 'The hashed id of the user who created the task'
+ description: 'The unique hashed identifier for the user who created the purchase order'
+ type: string
+ example: ''
+ assigned_user_id:
+ description: 'The unique hashed identifier for the user assigned to the purchase order'
+ type: string
+ example: ''
+ company_id:
+ description: 'The unique hashed identifier for the company associated with the purchase order'
+ type: string
+ example: ''
+ vendor_id:
+ description: 'The unique hashed identifier for the vendor associated with the purchase order'
+ type: string
+ example: ''
+ status_id:
+ description: 'The status of the purchase order represented by a unique identifier'
+ type: string
+ example: ''
+ number:
+ description: 'The unique alpha-numeric purchase order number per company'
+ type: string
+ example: PO_101
+ quote_number:
+ description: 'The quote number associated with this purchase order'
+ type: string
+ example: QUOTE_101
+ terms:
+ description: 'The terms and conditions for the purchase order'
+ type: string
+ example: 'These are some purchase order terms. Valid for 14 days.'
+ public_notes:
+ description: 'Publicly visible notes associated with the purchase order'
+ type: string
+ example: 'These are public notes which the vendor may see'
+ private_notes:
+ description: 'Privately visible notes associated with the purchase order, not disclosed to the vendor'
+ type: string
+ example: 'These are private notes, not to be disclosed to the vendor'
+ footer:
+ description: 'The footer text of the purchase order'
+ type: string
+ example: 'The text goes in the footer of the purchase order'
+ custom_value1:
+ description: 'First custom value field for additional information'
+ type: string
+ example: 'A custom value'
+ custom_value2:
+ description: 'Second custom value field for additional information'
+ type: string
+ example: 'A custom value'
+ custom_value3:
+ description: 'Third custom value field for additional information'
+ type: string
+ example: 'A custom value'
+ custom_value4:
+ description: 'Fourth custom value field for additional information'
+ type: string
+ example: 'A custom value'
+ tax_name1:
+ description: 'The name of the first tax applied to the purchase order'
+ type: string
+ example: GST
+ tax_name2:
+ description: 'The name of the second tax applied to the purchase order'
+ type: string
+ example: VAT
+ tax_rate1:
+ description: 'The rate of the first tax applied to the purchase order'
+ type: number
+ format: float
+ example: 10.00
+ tax_rate2:
+ description: 'The rate of the second tax applied to the purchase order'
+ type: number
+ format: float
+ example: 10.00
+ tax_name3:
+ description: 'The name of the third tax applied to the purchase order'
+ type: string
+ example: ''
+ tax_rate3:
+ description: 'The rate of the third tax applied to the purchase order'
+ type: number
+ format: float
+ example: 10.00
+ total_taxes:
+ description: 'The total amount of taxes applied to the purchase order'
+ type: number
+ format: float
+ example: 10.00
+ line_items:
+ type: array
+ description: 'An array of objects which define the line items of the purchase order'
+ items:
+ $ref: '#/components/schemas/InvoiceItem'
+ amount:
+ description: 'The total amount of the purchase order before taxes and discounts'
+ type: number
+ format: float
+ example: 10.00
+ balance:
+ description: 'The balance due for the purchase order after accounting for payments'
+ type: number
+ format: float
+ example: 10.00
+ paid_to_date:
+ description: 'The total amount paid on the purchase order so far'
+ type: number
+ format: float
+ example: 10.00
+ discount:
+ description: 'The discount amount or percentage applied to the purchase order'
+ type: number
+ format: float
+ example: 10.00
+ partial:
+ description: 'The partial or deposit amount for the purchase order'
+ type: number
+ format: float
+ example: 10.00
+ is_amount_discount:
+ description: 'Boolean flag indicating if the discount is a fixed amount or a percentage'
+ type: boolean
+ example: true
+ is_deleted:
+ description: 'Boolean flag indicating if the purchase order has been deleted'
+ type: boolean
+ example: false
+ uses_inclusive_taxes:
+ description: 'Boolean flag indicating if the taxes used are inclusive or exclusive'
+ type: boolean
+ example: true
+ date:
+ description: 'The date the purchase order was created'
+ type: string
+ format: date
+ example: '1994-07-30'
+ last_sent_date:
+ description: 'The last date the purchase order was sent to the vendor'
+ type: string
+ format: date
+ example: '1994-07-30'
+ next_send_date:
+ description: 'The next scheduled date for sending a reminder for the purchase order'
+ type: string
+ format: date
+ example: '1994-07-30'
+ partial_due_date:
+ description: 'The due date for the partial or deposit amount'
+ type: string
+ format: date
+ example: '1994-07-30'
+ due_date:
+ description: 'The due date for the total amount of the purchase order'
+ type: string
+ format: date
+ example: '1994-07-30'
+ settings:
+ $ref: '#/components/schemas/CompanySettings'
+ last_viewed:
+ description: Timestamp
+ type: number
+ format: integer
+ example: 1434342123
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: 1434342123
+ archived_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: 1434342123
+ custom_surcharge1:
+ description: 'First custom surcharge amount for the purchase order'
+ type: number
+ format: float
+ example: 10.00
+ custom_surcharge2:
+ description: 'Second custom surcharge amount for the purchase order'
+ type: number
+ format: float
+ example: 10.00
+ custom_surcharge3:
+ description: 'Third custom surcharge amount for the purchase order'
+ type: number
+ format: float
+ example: 10.00
+ custom_surcharge4:
+ description: 'Fourth custom surcharge amount for the purchase order'
+ type: number
+ format: float
+ example: 10.00
+ custom_surcharge_tax1:
+ description: 'Boolean flag indicating if taxes are charged on the first custom surcharge amount'
+ type: boolean
+ example: true
+ custom_surcharge_tax2:
+ description: 'Boolean flag indicating if taxes are charged on the second custom surcharge amount'
+ type: boolean
+ example: true
+ custom_surcharge_tax3:
+ description: 'Boolean flag indicating if taxes are charged on the third custom surcharge amount'
+ type: boolean
+ example: true
+ custom_surcharge_tax4:
+ description: 'Boolean flag indicating if taxes are charged on the fourth custom surcharge amount'
+ type: boolean
+ example: true
+ type: object
+
+
+ ClientContact:
+ properties:
+ id:
+ description: 'The hashed if of the contact'
type: string
example: Opnel5aKBz
- assigned_user_id:
- description: 'The assigned user of the task'
+ user_id:
+ description: 'The hashed id of the user who created the contact'
type: string
example: Opnel5aKBz
company_id:
@@ -16664,210 +17230,507 @@ components:
type: string
example: Opnel5aKBz
client_id:
- description: 'The hashed if of the client'
- type: string
- example: Opnel5aKBz
- invoice_id:
- description: 'The hashed id of the invoice associated with the task'
- type: string
- example: Opnel5aKBz
- project_id:
- description: 'The hashed id of the project associated with the task'
- type: string
- example: Opnel5aKBz
- number:
- description: 'The number of the task'
- type: string
- example: TASK-123
- time_log:
- description: 'An array of unix time stamps defining the start and end times of the task'
- type: string
- example: '[[1,2],[3,4]]'
- is_running:
- description: 'Determines if the task is still running'
- type: boolean
- example: true
- is_deleted:
- description: 'Boolean flag determining if the task has been deleted'
- type: boolean
- example: true
- task_status_id:
- description: 'The hashed id of the task status'
- type: string
- example: Opnel5aKBz
- description:
- description: 'The task description'
- type: string
- example: 'A wonder task to work on'
- duration:
- description: 'The task duration'
- type: integer
- example: ''
- task_status_order:
- description: 'The order of the task'
- type: integer
- example: '4'
- custom_value1:
- description: 'A custom value'
- type: string
- example: '2022-10-10'
- custom_value2:
- description: 'A custom value'
- type: string
- example: $1100
- custom_value3:
- description: 'A custom value'
- type: string
- example: 'I need help'
- custom_value4:
- description: 'A custom value'
- type: string
- example: INV-3343
- created_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- archived_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- type: object
- TaskStatus:
- properties:
- name:
- description: 'The task status name'
- type: string
- example: Backlog
- created_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- is_deleted:
- description: 'A boolean flag determining if the task status has been deleted'
- type: boolean
- example: true
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- archived_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- type: object
- TaxRate:
- properties:
- id:
- description: 'Thie hashed id of the tax'
- type: string
- example: Opnel5aKBz
- name:
- description: 'The tax name'
- type: string
- example: GST
- rate:
- description: 'The tax rate'
- type: number
- example: '10'
- is_deleted:
- description: 'Boolean flag determining if the tax has been deleted'
- type: boolean
- example: true
- type: object
- Template:
- properties:
- html:
- description: 'The template HTML'
- type: string
- example: ''
- type: object
- User:
- properties:
- id:
- description: 'The hashed id of the user'
+ description: 'The hashed id of the client'
type: string
example: Opnel5aKBz
first_name:
- description: 'The first name of the user'
+ description: 'The first name of the contact'
type: string
- example: Brad
+ example: John
last_name:
- description: 'The last name of the user'
+ description: 'The last name of the contact'
type: string
- example: Pitt
- email:
- description: 'The users email address'
- type: string
- example: brad@pitt.com
+ example: Doe
phone:
- description: 'The users phone number'
+ description: 'The phone number of the contact'
type: string
- example: 555-1233-23232
- signature:
- description: 'The users sign off signature'
+ example: 555-152-4524
+ custom_value1:
+ description: 'A Custom field value'
type: string
- example: 'Have a nice day!'
- avatar:
- description: 'The users avatar'
+ example: ''
+ custom_value2:
+ description: 'A Custom field value'
type: string
- example: 'https://url.to.your/avatar.png'
+ example: ''
+ custom_value3:
+ description: 'A Custom field value'
+ type: string
+ example: ''
+ custom_value4:
+ description: 'A Custom field value'
+ type: string
+ example: ''
+ email:
+ description: 'The email of the contact'
+ type: string
+ example: ''
accepted_terms_version:
- description: 'The version of the invoice ninja terms that has been accepted by the user'
+ description: 'The terms of service which the contact has accpeted'
type: string
- example: 1.0.1
- oauth_user_id:
- description: 'The provider id of the oauth entity'
+ example: 'A long set of ToS'
+ password:
+ description: 'The hashed password of the contact'
type: string
- example: jkhasdf789as6f675sdf768sdfs
- oauth_provider_id:
- description: 'The oauth entity id'
+ example: '*****'
+ confirmation-code:
+ description: 'The confirmation code used to authenticate the contacts email address'
type: string
- example: google
+ example: 333-sdjkh34gbasd
+ token:
+ description: 'A uuid based token.'
+ type: string
+ example: 333-sdjkh34gbasd
+ is_primary:
+ description: 'Defines is this contact is the primary contact for the client'
+ type: boolean
+ example: true
+ confirmed:
+ description: 'Boolean value confirms the user has confirmed their account.'
+ type: boolean
+ example: true
+ is_locked:
+ description: 'Boolean value defines if the contact has been locked out.'
+ type: boolean
+ example: true
+ send_email:
+ description: 'Boolean value determines is this contact should receive emails'
+ type: boolean
+ example: true
+ failed_logins:
+ description: 'The number of failed logins the contact has had'
+ type: number
+ format: integer
+ example: '3'
+ email_verified_at:
+ description: 'The date which the contact confirmed their email'
+ type: number
+ format: integer
+ example: '134341234234'
+ last_login:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ created_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ deleted_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
type: object
- AuthenticationError:
- type: object
+ ClientGatewayToken:
properties:
- message:
- description: 'These credentials do not match our records / Invalid Token'
+ id:
+ description: 'The hashed id of the client gateway token'
type: string
- example: 'These credentials do not match our records / Invalid Token'
- ValidationError:
- properties:
- message:
- description: 'The error message'
+ example: Opnel5aKBz
+ company_id:
+ description: 'The hashed id of the company'
type: string
- example: 'The given data was invalid.'
- errors:
- properties:
- value:
- type: array
- items:
- type: string
- type: object
+ example: '2'
+ client_id:
+ description: 'The hashed_id of the client'
+ type: string
+ example: '2'
+ token:
+ description: 'The payment token'
+ type: string
+ example: '2'
+ routing_number:
+ description: 'THe bank account routing number'
+ type: string
+ example: '2'
+ company_gateway_id:
+ description: 'The hashed id of the company gateway'
+ type: string
+ example: '2'
+ is_default:
+ description: 'Flag determining if the token is the default payment method'
+ type: boolean
+ example: 'true'
+ type: object
+ Product:
type: object
- AuthorizationError:
properties:
- message:
- description: 'Insufficient permissions for this resource.'
+ id:
type: string
- example: 'Insufficient permissions for this resource.'
- errors:
- properties:
- value:
- type: array
- items:
- type: string
- type: object
+ description: 'The hashed product ID.'
+ example: eP01N
+ company_id:
+ type: string
+ description: 'The hashed ID of the company that owns this product.'
+ example: eP01N
+ user_id:
+ type: string
+ description: 'The hashed ID of the user that created this product.'
+ example: n30m4
+ assigned_user_id:
+ type: string
+ description: 'The hashed ID of the user assigned to this product.'
+ example: pR0j3
+ project_id:
+ type: string
+ description: 'The hashed ID of the project that this product is associated with.'
+ example: pR0j3
+ vendor_id:
+ type: string
+ description: 'The hashed ID of the vendor that this product is associated with.'
+ example: pR0j3
+ custom_value1:
+ type: string
+ description: 'Custom value field 1.'
+ example: 'Custom value 1'
+ custom_value2:
+ type: string
+ description: 'Custom value field 2.'
+ example: 'Custom value 2'
+ custom_value3:
+ type: string
+ description: 'Custom value field 3.'
+ example: 'Custom value 3'
+ custom_value4:
+ type: string
+ description: 'Custom value field 4.'
+ example: 'Custom value 4'
+ product_key:
+ type: string
+ description: 'The product key.'
+ example: '1234'
+ notes:
+ type: string
+ description: 'Notes about the product.'
+ example: 'These are some notes about the product.'
+ cost:
+ type: number
+ format: float
+ description: 'The cost of the product.'
+ example: 10.0
+ price:
+ type: number
+ format: float
+ description: 'The price of the product.'
+ example: 20.0
+ quantity:
+ type: number
+ format: float
+ description: 'The quantity of the product.'
+ example: 5.0
+ tax_name1:
+ type: string
+ description: 'The name of tax 1.'
+ example: 'Tax 1'
+ tax_rate1:
+ type: number
+ format: float
+ description: 'The rate of tax 1.'
+ example: 10.0
+ tax_name2:
+ type: string
+ description: 'The name of tax 2.'
+ example: 'Tax 2'
+ tax_rate2:
+ type: number
+ format: float
+ description: 'The rate of tax 2.'
+ example: 5.0
+ tax_name3:
+ type: string
+ description: 'The name of tax 3.'
+ example: 'Tax 3'
+ tax_rate3:
+ type: number
+ format: float
+ description: 'The rate of tax 3.'
+ example: 0.0
+ archived_at:
+ type: integer
+ format: timestamp
+ description: 'The timestamp when the product was archived.'
+ example: '2022-03-18T15:00:00Z'
+ created_at:
+ type: integer
+ format: timestamp
+ description: 'The timestamp when the product was created.'
+ example: '2022-03-18T15:00:00Z'
+ updated_at:
+ description: Timestamp
+ type: integer
+ format: timestamp
+ example: '2022-03-18T12:34:56.789Z'
+ is_deleted:
+ type: boolean
+ description: 'Boolean flag determining if the product has been deleted'
+ example: false
+ in_stock_quantity:
+ type: integer
+ format: int32
+ description: The quantity of the product that is currently in stock
+ default: 0
+
+ stock_notification:
+ type: boolean
+ description: Indicates whether stock notifications are enabled for this product
+ default: true
+
+ stock_notification_threshold:
+ type: integer
+ format: int32
+ description: The minimum quantity threshold for which stock notifications will be triggered
+ default: 0
+
+ max_quantity:
+ type: integer
+ format: int32
+ description: The maximum quantity that can be ordered for this product
+
+ product_image:
+ type: string
+ description: The URL of the product image
+ format: uri-reference
+
+ Quote:
+ properties:
+ id:
+ description: 'The unique hashed identifier for the quote'
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: 'The unique hashed identifier for the user who created the quote'
+ type: string
+ example: ''
+ assigned_user_id:
+ description: 'The unique hashed identifier for the user assigned to the quote'
+ type: string
+ example: ''
+ company_id:
+ description: 'The unique hashed identifier for the company associated with the quote'
+ type: string
+ example: ''
+ client_id:
+ description: 'The unique hashed identifier for the client associated with the quote'
+ type: string
+ example: ''
+ status_id:
+ description: 'The status of the quote represented by a unique identifier'
+ type: string
+ example: ''
+ number:
+ description: 'The unique alpha-numeric quote number for the quote per company'
+ type: string
+ example: QUOTE_101
+ po_number:
+ description: 'The purchase order number associated with the quote'
+ type: string
+ example: PO-1234
+ terms:
+ description: 'The terms and conditions for the quote'
+ type: string
+ example: 'These are some quote terms. Valid for 14 days.'
+ public_notes:
+ description: 'Publicly visible notes associated with the quote'
+ type: string
+ example: 'These are public notes which the client may see'
+ private_notes:
+ description: 'Privately visible notes associated with the quote, not disclosed to the client'
+ type: string
+ example: 'These are private notes, not to be disclosed to the client'
+ footer:
+ description: 'The footer text of the quote'
+ type: string
+ example: 'The text goes in the footer of the quote'
+ custom_value1:
+ description: 'First custom value field for additional information'
+ type: string
+ example: 'A custom value'
+ custom_value2:
+ description: 'Second custom value field for additional information'
+ type: string
+ example: 'A custom value'
+ custom_value3:
+ description: 'Third custom value field for additional information'
+ type: string
+ example: 'A custom value'
+ custom_value4:
+ description: 'Fourth custom value field for additional information'
+ type: string
+ example: 'A custom value'
+ tax_name1:
+ description: 'The name of the first tax applied to the quote'
+ type: string
+ example: GST
+ tax_name2:
+ description: 'The name of the second tax applied to the quote'
+ type: string
+ example: VAT
+ tax_rate1:
+ description: 'The rate of the first tax applied to the quote'
+ type: number
+ format: float
+ example: 10.00
+ tax_rate2:
+ description: 'The rate of the second tax applied to the quote'
+ type: number
+ format: float
+ example: 10.00
+ tax_name3:
+ description: 'The name of the third tax applied to the quote'
+ type: string
+ example: ''
+ tax_rate3:
+ description: 'The rate of the third tax applied to the quote'
+ type: number
+ format: float
+ example: 10.00
+ total_taxes:
+ description: 'The total amount of taxes for the quote'
+ type: number
+ format: float
+ example: 10.00
+ line_items:
+ type: array
+ description: 'An array of objects which define the line items of the quote'
+ items:
+ $ref: '#/components/schemas/InvoiceItem'
+ amount:
+ description: 'The total amount of the quote before taxes and discounts'
+ type: number
+ format: float
+ example: 10.00
+ balance:
+ description: 'The balance due for the quote after accounting for payments'
+ type: number
+ format: float
+ example: 10.00
+ paid_to_date:
+ description: 'The total amount paid on the quote so far'
+ type: number
+ format: float
+ example: 10.00
+ discount:
+ description: 'The discount amount or percentage applied to the quote'
+ type: number
+ format: float
+ example: 10.00
+ partial:
+ description: 'The partial or deposit amount for the quote'
+ type: number
+ format: float
+ example: 10.00
+ is_amount_discount:
+ description: 'Boolean flag indicating if the discount is a fixed amount or a percentage'
+ type: boolean
+ example: true
+ is_deleted:
+ description: 'Boolean flag indicating if the quote has been deleted'
+ type: boolean
+ example: false
+ uses_inclusive_taxes:
+ description: 'Boolean flag indicating if the taxes used are inclusive or exclusive'
+ type: boolean
+ example: true
+ date:
+ description: 'The date the quote was created'
+ type: string
+ format: date
+ example: '1994-07-30'
+ last_sent_date:
+ description: 'The last date the quote was sent to the client'
+ type: string
+ format: date
+ example: '1994-07-30'
+ next_send_date:
+ description: 'The next scheduled date for sending a reminder for the quote'
+ type: string
+ format: date
+ example: '1994-07-30'
+ partial_due_date:
+ description: 'The due date for the partial or deposit amount'
+ type: string
+ format: date
+ example: '1994-07-30'
+ due_date:
+ description: 'The due date for the total amount of the quote'
+ type: string
+ format: date
+ example: '1994-07-30'
+ settings:
+ $ref: '#/components/schemas/CompanySettings'
+ last_viewed:
+ description: 'The timestamp of the last time the quote was viewed'
+ type: number
+ format: integer
+ example: 1434342123
+ updated_at:
+ description: 'The timestamp of the last update to the quote'
+ type: number
+ format: integer
+ example: 1434342123
+ archived_at:
+ description: 'The timestamp of when the quote was archived'
+ type: number
+ format: integer
+ example: 1434342123
+ custom_surcharge1:
+ description: 'First custom surcharge amount for the quote'
+ type: number
+ format: float
+ example: 10.00
+ custom_surcharge2:
+ description: 'Second custom surcharge amount for the quote'
+ type: number
+ format: float
+ example: 10.00
+ custom_surcharge3:
+ description: 'Third custom surcharge amount for the quote'
+ type: number
+ format: float
+ example: 10.00
+ custom_surcharge4:
+ description: 'Fourth custom surcharge amount for the quote'
+ type: number
+ format: float
+ example: 10.00
+ custom_surcharge_tax1:
+ description: 'Boolean flag indicating if taxes are charged on the first custom surcharge amount'
+ type: boolean
+ example: true
+ custom_surcharge_tax2:
+ description: 'Boolean flag indicating if taxes are charged on the second custom surcharge amount'
+ type: boolean
+ example: true
+ custom_surcharge_tax3:
+ description: 'Boolean flag indicating if taxes are charged on the third custom surcharge amount'
+ type: boolean
+ example: true
+ custom_surcharge_tax4:
+ description: 'Boolean flag indicating if taxes are charged on the fourth custom surcharge amount'
+ type: boolean
+ example: true
+ type: object
+ CompanyToken:
+ properties:
+ name:
+ description: 'The token name'
+ type: string
+ example: 'Token Name'
+ token:
+ description: 'The token value'
+ type: string
+ example: AS3df3jUUH765fhfd9KJuidj3JShjA
+ is_system:
+ description: 'Determines whether the token is created by the system rather than a user'
+ type: boolean
+ example: 'true'
type: object
VendorContact:
properties:
@@ -16939,121 +17802,16 @@ components:
format: integer
example: '134341234234'
type: object
- Vendor:
+ PaymentTerm:
properties:
- id:
- description: 'The hashed id of the vendor'
- type: string
- example: Opnel5aKBz
- user_id:
- description: 'The hashed id of the user who created the vendor'
- type: string
- example: Opnel5aKBz
- assigned_user_id:
- description: 'The hashed id of the assigned user to this vendor'
- type: string
- example: Opnel5aKBz
- company_id:
- description: 'The hashed id of the company'
- type: string
- example: Opnel5aKBz
- client_id:
- description: 'The hashed id of the client'
- type: string
- example: Opnel5aKBz
- contacts:
- type: array
- items:
- $ref: '#/components/schemas/VendorContact'
- name:
- description: 'The vendor name'
- type: string
- example: 'Harry''s cafe de wheels'
- website:
- description: 'The website of the vendor'
- type: string
- example: www.harry.com
- private_notes:
- description: 'The private notes of the vendor'
- type: string
- example: 'Shhh, don''t tell the vendor'
- industry_id:
- description: 'The industry id of the vendor'
- type: string
+ num_days:
+ description: 'The payment term length in days'
+ type: integer
example: '1'
- size_id:
- description: ________
+ name:
+ description: 'The payment term length in string format'
type: string
- example: ''
- address1:
- description: ________
- type: string
- example: ''
- address2:
- description: ________
- type: string
- example: ''
- city:
- description: ________
- type: string
- example: ''
- state:
- description: ________
- type: string
- example: ''
- postal_code:
- description: ________
- type: string
- example: ''
- phone:
- description: 'The client phone number'
- type: string
- example: 555-3434-3434
- country_id:
- description: ________
- type: string
- example: ''
- currency_id:
- description: ________
- type: string
- example: '4'
- custom_value1:
- description: ________
- type: string
- example: ''
- custom_value2:
- description: ________
- type: string
- example: ''
- custom_value3:
- description: ________
- type: string
- example: ''
- custom_value4:
- description: ________
- type: string
- example: ''
- vat_number:
- description: ________
- type: string
- example: ''
- id_number:
- description: ________
- type: string
- example: ''
- number:
- description: ________
- type: string
- example: ''
- is_deleted:
- description: ________
- type: boolean
- example: true
- last_login:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
+ example: 'NET 1'
created_at:
description: Timestamp
type: number
@@ -17064,237 +17822,11 @@ components:
type: number
format: integer
example: '134341234234'
- settings:
- $ref: '#/components/schemas/CompanySettings'
- type: object
- Webhook:
- properties:
- id:
- description: 'The subscription hashed id'
- type: string
- example: AS3df3A
- event_id:
- description: 'The subscription event id'
- type: string
- example: AS3df3A
- target_url:
- description: 'The api endpoint'
- type: string
- example: AS3df3A
- format:
- description: 'JSON or UBL'
- type: string
- example: JSON
- type: object
- Activity:
- properties:
- id:
- description: 'The id field of the activity'
- type: string
- example: Opnel5aKBz
- activity_type_id:
- description: 'The activity type id'
- type: string
- example: Opnel5aKBz
- client_id:
- description: 'The client hashed id'
- type: string
- example: Opnel5aKBz
- company_id:
- description: 'The company hashed id'
- type: string
- example: Opnel5aKBz
- user_id:
- description: 'The user hashed id'
- type: string
- example: Opnel5aKBz
- invoice_id:
- description: 'The invoice hashed id'
- type: string
- example: Opnel5aKBz
- payment_id:
- description: 'The payment hashed id'
- type: string
- example: Opnel5aKBz
- credit_id:
- description: 'The credit hashed id'
- type: string
- example: Opnel5aKBz
- updated_at:
- description: 'Unixtimestamp the last time the record was updated'
- type: integer
- example: '343421434'
- expense_id:
- description: 'The expense hashed id'
- type: string
- example: Opnel5aKBz
- is_system:
- description: 'Defines is the activity was performed by the system'
- type: boolean
- example: true
- contact_id:
- description: 'The contact hashed id'
- type: string
- example: Opnel5aKBz
- task_id:
- description: 'The task hashed id'
- type: string
- example: Opnel5aKBz
- notes:
- description: 'Activity Notes'
- type: string
- example: Opnel5aKBz
- token_id:
- description: 'The hashed ID of the token who performed the action'
- type: string
- example: Opnel5aKBz
- ip:
- description: 'The IP Address of the user who performed the action'
- type: string
- example: 192.168.1.252
- user:
- $ref: '#/components/schemas/User'
- client:
- $ref: '#/components/schemas/Client'
- contact:
- $ref: '#/components/schemas/ClientContact'
- recurring_invoice:
- $ref: '#/components/schemas/RecurringInvoice'
- invoice:
- $ref: '#/components/schemas/Invoice'
- credit:
- $ref: '#/components/schemas/Credit'
- quote:
- $ref: '#/components/schemas/Quote'
- payment:
- $ref: '#/components/schemas/Payment'
- expense:
- $ref: '#/components/schemas/Expense'
- task:
- $ref: '#/components/schemas/Task'
- purchase_order:
- $ref: '#/components/schemas/PurchaseOrder'
- vendor:
- $ref: '#/components/schemas/Vendor'
- vendor_contact:
- $ref: '#/components/schemas/VendorContact'
- type: object
- BankTransaction:
- properties:
- id:
- description: 'The bank integration hashed id'
- type: string
- example: AS3df3A
- company_id:
- description: 'The company hashed id'
- type: string
- example: AS3df3A
- user_id:
- description: 'The user hashed id'
- type: string
- example: AS3df3A
- transaction_id:
- description: 'The id of the transaction rule'
- type: integer
- example: 343434
- amount:
- description: 'The transaction amount'
+ archived_at:
+ description: Timestamp
type: number
- example: 10
- currency_id:
- description: 'The currency ID of the currency'
- type: string
- example: '1'
- account_type:
- description: 'The account type'
- type: string
- example: creditCard
- description:
- description: 'The description of the transaction'
- type: string
- example: 'Potato purchases for kevin'
- category_id:
- description: 'The category id'
- type: integer
- example: 1
- category_type:
- description: 'The category description'
- type: string
- example: Expenses
- base_type:
- description: 'Either CREDIT or DEBIT'
- type: string
- example: CREDIT
- date:
- description: 'The date of the transaction'
- type: string
- example: '2022-09-01'
- bank_account_id:
- description: 'The ID number of the bank account'
- type: integer
- example: '1'
- type: object
- BankIntegration:
- properties:
- id:
- description: 'The bank integration hashed id'
- type: string
- example: AS3df3A
- company_id:
- description: 'The company hashed id'
- type: string
- example: AS3df3A
- user_id:
- description: 'The user hashed id'
- type: string
- example: AS3df3A
- provider_bank_name:
- description: 'The providers bank name'
- type: string
- example: 'Chase Bank'
- bank_account_id:
- description: 'The bank account id'
- type: integer
- example: '1233434'
- bank_account_name:
- description: 'The name of the account'
- type: string
- example: 'My Checking Acc'
- bank_account_number:
- description: 'The account number'
- type: string
- example: '111 234 2332'
- bank_account_status:
- description: 'The status of the bank account'
- type: string
- example: ACTIVE
- bank_account_type:
- description: 'The type of account'
- type: string
- example: CREDITCARD
- balance:
- description: 'The current bank balance if available'
- type: number
- example: '1000000'
- currency:
- description: 'iso_3166_3 code'
- type: string
- example: USD
- type: object
- BTRules:
- properties:
- data_key:
- description: 'The key to search'
- type: string
- example: 'description,amount'
- operator:
- description: 'The operator flag of the search'
- type: string
- example: '>'
- value:
- description: 'The value to search for'
- type: string
- example: bob
+ format: integer
+ example: '134341234234'
type: object
Account:
properties:
diff --git a/openapi/components/schemas.yaml b/openapi/components/schemas.yaml
index 575dea7f8a21..3a579727752c 100644
--- a/openapi/components/schemas.yaml
+++ b/openapi/components/schemas.yaml
@@ -1,1277 +1,4 @@
schemas:
- BankTransactionRule:
- properties:
- id:
- description: 'The bank transaction rules hashed id'
- type: string
- example: AS3df3A
- company_id:
- description: 'The company hashed id'
- type: string
- example: AS3df3A
- user_id:
- description: 'The user hashed id'
- type: string
- example: AS3df3A
- name:
- description: 'The name of the transaction'
- type: string
- example: 'Rule 1'
- rules:
- description: 'A mapped collection of the sub rules for the BankTransactionRule'
- type: array
- items:
- $ref: '#/components/schemas/BTRules'
- auto_convert:
- description: 'Flags whether the rule converts the transaction automatically'
- type: boolean
- example: true
- matches_on_all:
- description: 'Flags whether all subrules are required for the match'
- type: boolean
- example: true
- applies_to:
- description: 'Flags whether the rule applies to a CREDIT or DEBIT'
- type: string
- example: CREDIT
- client_id:
- description: 'The client hashed id'
- type: string
- example: AS3df3A
- vendor_id:
- description: 'The vendor hashed id'
- type: string
- example: AS3df3A
- category_id:
- description: 'The category hashed id'
- type: string
- example: AS3df3A
- type: object
- Subscription:
- properties:
- id:
- description: ______
- type: string
- example: Opnel5aKBz
- user_id:
- description: ______
- type: string
- example: Opnel5aKBz
- product_id:
- description: ______
- type: string
- example: Opnel5aKBz
- company_id:
- description: ______
- type: string
- example: Opnel5aKBz
- recurring_invoice_id:
- description: ______
- type: string
- example: Opnel5aKBz
- is_recurring:
- description: ______
- type: boolean
- example: 'true'
- frequency_id:
- description: 'integer const representation of the frequency'
- type: string
- example: '1'
- auto_bill:
- description: 'enum setting'
- type: string
- example: always
- promo_code:
- description: ______
- type: string
- example: PROMOCODE4U
- promo_discount:
- description: ______
- type: number
- example: 10
- is_amount_discount:
- description: ______
- type: boolean
- example: 'true'
- allow_cancellation:
- description: ______
- type: boolean
- example: 'true'
- per_seat_enabled:
- description: ______
- type: boolean
- example: 'true'
- currency_id:
- description: ______
- type: integer
- example: '1'
- max_seats_limit:
- description: ______
- type: integer
- example: '100'
- trial_enabled:
- description: ______
- type: boolean
- example: 'true'
- trial_duration:
- description: ______
- type: integer
- example: '2'
- allow_query_overrides:
- description: ______
- type: boolean
- example: 'true'
- allow_plan_changes:
- description: ______
- type: boolean
- example: 'true'
- refund_period:
- description: ______
- type: integer
- example: '2'
- webhook_configuration:
- description: ______
- type: string
- example: '2'
- is_deleted:
- description: ______
- type: boolean
- example: 'true'
- archived_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- created_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- type: object
- BulkAction:
- type: array
- items:
- type: integer
- example: '[0,1,2,3,]'
- ClientContact:
- properties:
- id:
- description: 'The hashed if of the contact'
- type: string
- example: Opnel5aKBz
- user_id:
- description: 'The hashed id of the user who created the contact'
- type: string
- example: Opnel5aKBz
- company_id:
- description: 'The hashed id of the company'
- type: string
- example: Opnel5aKBz
- client_id:
- description: 'The hashed id of the client'
- type: string
- example: Opnel5aKBz
- first_name:
- description: 'The first name of the contact'
- type: string
- example: John
- last_name:
- description: 'The last name of the contact'
- type: string
- example: Doe
- phone:
- description: 'The phone number of the contact'
- type: string
- example: 555-152-4524
- custom_value1:
- description: 'A Custom field value'
- type: string
- example: ''
- custom_value2:
- description: 'A Custom field value'
- type: string
- example: ''
- custom_value3:
- description: 'A Custom field value'
- type: string
- example: ''
- custom_value4:
- description: 'A Custom field value'
- type: string
- example: ''
- email:
- description: 'The email of the contact'
- type: string
- example: ''
- accepted_terms_version:
- description: 'The terms of service which the contact has accpeted'
- type: string
- example: 'A long set of ToS'
- password:
- description: 'The hashed password of the contact'
- type: string
- example: '*****'
- confirmation-code:
- description: 'The confirmation code used to authenticate the contacts email address'
- type: string
- example: 333-sdjkh34gbasd
- token:
- description: 'A uuid based token.'
- type: string
- example: 333-sdjkh34gbasd
- is_primary:
- description: 'Defines is this contact is the primary contact for the client'
- type: boolean
- example: true
- confirmed:
- description: 'Boolean value confirms the user has confirmed their account.'
- type: boolean
- example: true
- is_locked:
- description: 'Boolean value defines if the contact has been locked out.'
- type: boolean
- example: true
- send_email:
- description: 'Boolean value determines is this contact should receive emails'
- type: boolean
- example: true
- failed_logins:
- description: 'The number of failed logins the contact has had'
- type: number
- format: integer
- example: '3'
- email_verified_at:
- description: 'The date which the contact confirmed their email'
- type: number
- format: integer
- example: '134341234234'
- last_login:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- created_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- deleted_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- type: object
- ClientGatewayToken:
- properties:
- id:
- description: 'The hashed id of the client gateway token'
- type: string
- example: Opnel5aKBz
- company_id:
- description: 'The hashed id of the company'
- type: string
- example: '2'
- client_id:
- description: 'The hashed_id of the client'
- type: string
- example: '2'
- token:
- description: 'The payment token'
- type: string
- example: '2'
- routing_number:
- description: 'THe bank account routing number'
- type: string
- example: '2'
- company_gateway_id:
- description: 'The hashed id of the company gateway'
- type: string
- example: '2'
- is_default:
- description: 'Flag determining if the token is the default payment method'
- type: boolean
- example: 'true'
- type: object
- Client:
- properties:
- id:
- description: 'The hashed id of the client'
- type: string
- example: Opnel5aKBz
- user_id:
- description: 'The hashed id of the user'
- type: string
- example: ''
- company_id:
- description: 'The hashed id of the company'
- type: string
- example: ''
- contacts:
- type: array
- items:
- $ref: '#/components/schemas/ClientContact'
- name:
- description: 'The client name'
- type: string
- example: 'Jims housekeeping'
- website:
- description: 'The client website'
- type: string
- example: www.jims.com
- private_notes:
- description: 'Private notes on the client'
- type: string
- example: 'These are very private notes'
- client_hash:
- description: 'The client hash'
- type: string
- example: asdfkjhk342hjhbfdvmnfb1
- industry_id:
- description: 'The industry id of the client'
- type: number
- example: '5'
- size_id:
- description: 'The size id of the client'
- type: number
- example: '2'
- address1:
- description: 'Address line 1'
- type: string
- example: ''
- address2:
- description: 'Address line 2'
- type: string
- example: ''
- city:
- description: City
- type: string
- example: 'Beverley Hills'
- state:
- description: State/Locality
- type: string
- example: Californnia
- postal_code:
- description: 'Zip / Postal code'
- type: string
- example: '90210'
- phone:
- description: 'The client phone number'
- type: string
- example: 555-3434-3434
- country_id:
- description: 'The client country id'
- type: number
- format: integer
- example: '1'
- custom_value1:
- description: 'A custom value'
- type: string
- example: 'Something custom'
- custom_value2:
- description: 'A custom value'
- type: string
- example: '2002-01-01'
- custom_value3:
- description: 'A custom value'
- type: string
- example: 'Something custom'
- custom_value4:
- description: 'A custom value'
- type: string
- example: 'Something custom'
- vat_number:
- description: 'The client VAT number'
- type: string
- example: VAT123
- id_number:
- description: ' The client id number'
- type: string
- example: CLIENT_ID_NUMBER
- number:
- description: 'The client number - assigned by the system typically'
- type: string
- example: ''
- shipping_address1:
- description: 'The shipping address line 1'
- type: string
- example: '5 Wallaby Way'
- shipping_address2:
- description: 'The shipping address line 2'
- type: string
- example: 'Suite 5'
- shipping_city:
- description: 'The shipping city'
- type: string
- example: Perth
- shipping_state:
- description: 'The shipping state'
- type: string
- example: 'Western Australia'
- shipping_postal_code:
- description: 'The shipping postal code'
- type: string
- example: '6110'
- shipping_country_id:
- description: 'The shipping country id'
- type: number
- format: integer
- example: '4'
- is_deleted:
- description: 'Boolean flagged determining if the client has been deleted'
- type: boolean
- example: true
- balance:
- description: 'The client balance'
- type: number
- format: float
- example: '10.00'
- paid_to_date:
- description: 'The amount the client has paid to date.'
- type: number
- format: float
- example: '10.00'
- credit_balance:
- description: 'An amount which is available to the client for future use.'
- type: number
- format: float
- example: '10.00'
- last_login:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- created_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- settings:
- $ref: '#/components/schemas/CompanySettings'
- type: object
- CompanyGateway:
- properties:
- id:
- description: 'The hashed id of the company gateway'
- type: string
- example: Opnel5aKBz
- company_id:
- description: 'The company hashed id'
- type: string
- example: '2'
- gateway_key:
- description: 'The gateway key (hash)'
- type: string
- example: '2'
- accepted_credit_cards:
- description: 'Bitmask representation of cards'
- type: integer
- example: '32'
- require_billing_address:
- description: 'Determines if the the billing address is required prior to payment.'
- type: boolean
- example: true
- require_shipping_address:
- description: 'Determines if the the billing address is required prior to payment.'
- type: boolean
- example: true
- config:
- description: 'The configuration map for the gateway'
- type: string
- example: dfadsfdsafsafd
- update_details:
- description: 'Determines if the client details should be updated.'
- type: boolean
- example: true
- fees_and_limits:
- description: 'A mapped collection of the fees and limits for the configured gateway'
- type: array
- items:
- $ref: '#/components/schemas/FeesAndLimits'
- type: object
- CompanyLedger:
- properties:
- entity_id:
- description: 'This field will reference one of the following entity hashed ID payment_id, invoice_id or credit_id'
- type: string
- example: AS3df3A
- notes:
- description: 'The notes which reference this entry of the ledger'
- type: string
- example: 'Credit note for invoice #3212'
- balance:
- description: 'The client balance'
- type: number
- format: float
- example: '10.00'
- adjustment:
- description: 'The amount the client balance is adjusted by'
- type: number
- format: float
- example: '10.00'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- created_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- type: object
- Company:
- properties:
- id:
- description: 'The company hash id'
- type: string
- example: WJxbojagwO
- size_id:
- description: 'The company size ID'
- type: string
- example: '1'
- industry_id:
- description: 'The company industry ID'
- type: string
- example: '1'
- slack_webhook_url:
- description: 'The slack webhook notification URL'
- type: string
- example: 'https://slack.com/sh328sj'
- google_analytics_key:
- description: 'The google analytics key'
- type: string
- example: '1'
- portal_mode:
- description: 'Determines the client facing urls ie: subdomain,domain,iframe'
- type: string
- example: subdomain
- subdomain:
- description: 'Specifies the first part of the company domain ie acme in acme.domain.com'
- type: string
- example: aceme
- portal_domain:
- description: 'The fully qualified domain for client facing URLS'
- type: string
- example: 'https://subdomain.invoicing.co'
- enabled_tax_rates:
- description: 'Number of taxes rates used per entity'
- type: integer
- example: '1'
- fill_products:
- description: 'Toggles filling a product description based on product key'
- type: boolean
- example: true
- convert_products:
- description: ___________
- type: boolean
- example: true
- update_products:
- description: 'Toggles updating a product description which description changes'
- type: boolean
- example: true
- show_product_details:
- description: 'Toggles showing a product description which description changes'
- type: boolean
- example: true
- custom_fields:
- description: 'Custom fields map'
- type: object
- enable_product_cost:
- description: 'Show/Hide the product cost field in the UI'
- type: boolean
- example: true
- enable_product_quantity:
- description: 'Show/hide the product quantity field (used in the UI to show the default quantity)'
- type: boolean
- example: true
- default_quantity:
- description: 'Enable/Disable whether to use a default quantity'
- type: boolean
- example: true
- custom_surcharge_taxes1:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_taxes2:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_taxes3:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_taxes4:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- logo:
- description: 'The company logo - binary'
- type: object
- example: logo.png
- settings:
- $ref: '#/components/schemas/CompanySettings'
- type: object
- CompanySettings:
- properties:
- timezone_id:
- description: 'The timezone id'
- type: string
- example: '15'
- date_format_id:
- description: 'The date format id'
- type: string
- example: '15'
- military_time:
- description: 'Toggles 12/24 hour time'
- type: boolean
- example: true
- language_id:
- description: 'The language id'
- type: string
- example: '1'
- show_currency_code:
- description: 'Toggles whether the currency symbol or code is shown'
- type: boolean
- example: true
- currency_id:
- description: 'The default currency id'
- type: string
- example: true
- payment_terms:
- description: '-1 sets no payment term, 0 sets payment due immediately, positive integers indicates payment terms in days'
- type: integer
- example: '1'
- company_gateway_ids:
- description: 'A commad separate list of available gateways'
- type: string
- example: '1,2,3,4'
- custom_value1:
- description: 'A Custom Label'
- type: string
- example: 'Custom Label'
- custom_value2:
- description: 'A Custom Label'
- type: string
- example: 'Custom Label'
- custom_value3:
- description: 'A Custom Label'
- type: string
- example: 'Custom Label'
- custom_value4:
- description: 'A Custom Label'
- type: string
- example: 'Custom Label'
- default_task_rate:
- description: 'The default task rate'
- type: number
- format: float
- example: '10.00'
- send_reminders:
- description: 'Toggles whether reminders are sent'
- type: boolean
- example: true
- enable_client_portal_tasks:
- description: 'Show/hide the tasks panel in the client portal'
- type: boolean
- example: true
- email_style:
- description: 'options include plain,light,dark,custom'
- type: string
- example: light
- reply_to_email:
- description: 'The reply to email address'
- type: string
- example: email@gmail.com
- bcc_email:
- description: 'A comma separate list of BCC emails'
- type: string
- example: 'email@gmail.com, contact@gmail.com'
- pdf_email_attachment:
- description: 'Toggles whether to attach PDF as attachment'
- type: boolean
- example: true
- ubl_email_attachment:
- description: 'Toggles whether to attach UBL as attachment'
- type: boolean
- example: true
- email_style_custom:
- description: 'The custom template'
- type: string
- example: ''
- counter_number_applied:
- description: 'enum when the invoice number counter is set, ie when_saved, when_sent, when_paid'
- type: string
- example: when_sent
- quote_number_applied:
- description: 'enum when the quote number counter is set, ie when_saved, when_sent'
- type: string
- example: when_sent
- custom_message_dashboard:
- description: 'A custom message which is displayed on the dashboard'
- type: string
- example: 'Please pay invoices immediately'
- custom_message_unpaid_invoice:
- description: 'A custom message which is displayed in the client portal when a client is viewing a unpaid invoice.'
- type: string
- example: 'Please pay invoices immediately'
- custom_message_paid_invoice:
- description: 'A custom message which is displayed in the client portal when a client is viewing a paid invoice.'
- type: string
- example: 'Thanks for paying this invoice!'
- custom_message_unapproved_quote:
- description: 'A custom message which is displayed in the client portal when a client is viewing a unapproved quote.'
- type: string
- example: 'Please approve quote'
- lock_invoices:
- description: 'Toggles whether invoices are locked once sent and cannot be modified further'
- type: boolean
- example: true
- auto_archive_invoice:
- description: 'Toggles whether a invoice is archived immediately following payment'
- type: boolean
- example: true
- auto_archive_quote:
- description: 'Toggles whether a quote is archived after being converted to a invoice'
- type: boolean
- example: true
- auto_convert_quote:
- description: 'Toggles whether a quote is converted to a invoice when approved'
- type: boolean
- example: true
- inclusive_taxes:
- description: 'Boolean flag determining whether inclusive or exclusive taxes are used'
- type: boolean
- example: true
- translations:
- description: 'JSON payload of customized translations'
- type: object
- example: ''
- task_number_pattern:
- description: 'Allows customisation of the task number pattern'
- type: string
- example: '{$year}-{$counter}'
- task_number_counter:
- description: 'The incrementing counter for tasks'
- type: integer
- example: '1'
- reminder_send_time:
- description: 'Time from UTC +0 when the email will be sent to the client'
- type: integer
- example: '32400'
- expense_number_pattern:
- description: 'Allows customisation of the expense number pattern'
- type: string
- example: '{$year}-{$counter}'
- expense_number_counter:
- description: 'The incrementing counter for expenses'
- type: integer
- example: '1'
- vendor_number_pattern:
- description: 'Allows customisation of the vendor number pattern'
- type: string
- example: '{$year}-{$counter}'
- vendor_number_counter:
- description: 'The incrementing counter for vendors'
- type: integer
- example: '1'
- ticket_number_pattern:
- description: 'Allows customisation of the ticket number pattern'
- type: string
- example: '{$year}-{$counter}'
- ticket_number_counter:
- description: 'The incrementing counter for tickets'
- type: integer
- example: '1'
- payment_number_pattern:
- description: 'Allows customisation of the payment number pattern'
- type: string
- example: '{$year}-{$counter}'
- payment_number_counter:
- description: 'The incrementing counter for payments'
- type: integer
- example: '1'
- invoice_number_pattern:
- description: 'Allows customisation of the invoice number pattern'
- type: string
- example: '{$year}-{$counter}'
- invoice_number_counter:
- description: 'The incrementing counter for invoices'
- type: integer
- example: '1'
- quote_number_pattern:
- description: 'Allows customisation of the quote number pattern'
- type: string
- example: '{$year}-{$counter}'
- quote_number_counter:
- description: 'The incrementing counter for quotes'
- type: integer
- example: '1'
- client_number_pattern:
- description: 'Allows customisation of the client number pattern'
- type: string
- example: '{$year}-{$counter}'
- client_number_counter:
- description: 'The incrementing counter for clients'
- type: integer
- example: '1'
- credit_number_pattern:
- description: 'Allows customisation of the credit number pattern'
- type: string
- example: '{$year}-{$counter}'
- credit_number_counter:
- description: 'The incrementing counter for credits'
- type: integer
- example: '1'
- recurring_invoice_number_prefix:
- description: 'This string is prepended to the recurring invoice number'
- type: string
- example: R
- reset_counter_frequency_id:
- description: 'CONSTANT which is used to apply the frequency which the counters are reset'
- type: integer
- example: '1'
- reset_counter_date:
- description: 'The explicit date which is used to reset counters'
- type: string
- example: '2019-01-01'
- counter_padding:
- description: 'Pads the counter with leading zeros'
- type: integer
- example: '1'
- shared_invoice_quote_counter:
- description: 'Flags whether to share the counter for invoices and quotes'
- type: boolean
- example: true
- update_products:
- description: 'Determines if client fields are updated from third party APIs'
- type: boolean
- example: true
- convert_products:
- description: ''
- type: boolean
- example: true
- fill_products:
- description: 'Automatically fill products based on product_key'
- type: boolean
- example: true
- invoice_terms:
- description: 'The default invoice terms'
- type: string
- example: 'Invoice Terms are...'
- quote_terms:
- description: 'The default quote terms'
- type: string
- example: 'Quote Terms are...'
- invoice_taxes:
- description: 'Taxes can be applied to the invoice'
- type: number
- example: '1'
- invoice_design_id:
- description: 'The default design id (invoice, quote etc)'
- type: string
- example: '1'
- quote_design_id:
- description: 'The default design id (invoice, quote etc)'
- type: string
- example: '1'
- invoice_footer:
- description: 'The default invoice footer'
- type: string
- example: '1'
- invoice_labels:
- description: 'JSON string of invoice labels'
- type: string
- example: '1'
- tax_rate1:
- description: 'The tax rate (float)'
- type: number
- example: '10'
- tax_name1:
- description: 'The tax name'
- type: string
- example: GST
- tax_rate2:
- description: 'The tax rate (float)'
- type: number
- example: '10'
- tax_name2:
- description: 'The tax name'
- type: string
- example: GST
- tax_rate3:
- description: 'The tax rate (float)'
- type: number
- example: '10'
- tax_name3:
- description: 'The tax name'
- type: string
- example: GST
- payment_type_id:
- description: 'The default payment type id'
- type: string
- example: '1'
- custom_fields:
- description: 'JSON string of custom fields'
- type: string
- example: '{}'
- email_footer:
- description: 'The default email footer'
- type: string
- example: 'A default email footer'
- email_sending_method:
- description: 'The email driver to use to send email, options include default, gmail'
- type: string
- example: default
- gmail_sending_user_id:
- description: 'The hashed_id of the user account to send email from'
- type: string
- example: F76sd34D
- email_subject_invoice:
- description: ''
- type: string
- example: 'Your Invoice Subject'
- email_subject_quote:
- description: ''
- type: string
- example: 'Your Quote Subject'
- email_subject_payment:
- description: ''
- type: string
- example: 'Your Payment Subject'
- email_template_invoice:
- description: 'The full template for invoice emails'
- type: string
- example: ''
- email_template_quote:
- description: 'The full template for quote emails'
- type: string
- example: ''
- email_template_payment:
- description: 'The full template for payment emails'
- type: string
- example: ''
- email_subject_reminder1:
- description: 'Email subject for Reminder'
- type: string
- example: ''
- email_subject_reminder2:
- description: 'Email subject for Reminder'
- type: string
- example: ''
- email_subject_reminder3:
- description: 'Email subject for Reminder'
- type: string
- example: ''
- email_subject_reminder_endless:
- description: 'Email subject for endless reminders'
- type: string
- example: ''
- email_template_reminder1:
- description: 'The full template for Reminder 1'
- type: string
- example: ''
- email_template_reminder2:
- description: 'The full template for Reminder 2'
- type: string
- example: ''
- email_template_reminder3:
- description: 'The full template for Reminder 3'
- type: string
- example: ''
- email_template_reminder_endless:
- description: 'The full template for enless reminders'
- type: string
- example: ''
- enable_portal_password:
- description: 'Toggles whether a password is required to log into the client portal'
- type: boolean
- example: true
- show_accept_invoice_terms:
- description: 'Toggles whether the terms dialogue is shown to the client'
- type: boolean
- example: true
- show_accept_quote_terms:
- description: 'Toggles whether the terms dialogue is shown to the client'
- type: boolean
- example: true
- require_invoice_signature:
- description: 'Toggles whether a invoice signature is required'
- type: boolean
- example: true
- require_quote_signature:
- description: 'Toggles whether a quote signature is required'
- type: boolean
- example: true
- name:
- description: 'The company name'
- type: string
- example: 'Acme Co'
- company_logo:
- description: 'The company logo file'
- type: object
- example: logo.png
- website:
- description: 'The company website URL'
- type: string
- example: www.acme.com
- address1:
- description: 'The company address line 1'
- type: string
- example: 'Suite 888'
- address2:
- description: 'The company address line 2'
- type: string
- example: '5 Jimbo Way'
- city:
- description: 'The company city'
- type: string
- example: Sydney
- state:
- description: 'The company state'
- type: string
- example: Florisa
- postal_code:
- description: 'The company zip/postal code'
- type: string
- example: '90210'
- phone:
- description: 'The company phone'
- type: string
- example: 555-213-3948
- email:
- description: 'The company email'
- type: string
- example: joe@acme.co
- country_id:
- description: 'The country ID'
- type: string
- example: '1'
- vat_number:
- description: 'The company VAT/TAX ID number'
- type: string
- example: '32 120 377 720'
- page_size:
- description: 'The default page size'
- type: string
- example: A4
- font_size:
- description: 'The font size'
- type: number
- example: '9'
- primary_font:
- description: 'The primary font'
- type: string
- example: roboto
- secondary_font:
- description: 'The secondary font'
- type: string
- example: roboto
- hide_paid_to_date:
- description: 'Flags whether to hide the paid to date field'
- type: boolean
- example: false
- embed_documents:
- description: 'Toggled whether to embed documents in the PDF'
- type: boolean
- example: false
- all_pages_header:
- description: 'The header for the PDF'
- type: boolean
- example: false
- all_pages_footer:
- description: 'The footer for the PDF'
- type: boolean
- example: false
- document_email_attachment:
- description: 'Toggles whether to attach documents in the email'
- type: boolean
- example: false
- enable_client_portal_password:
- description: 'Toggles password protection of the client portal'
- type: boolean
- example: false
- enable_email_markup:
- description: 'Toggles the use of markdown in emails'
- type: boolean
- example: false
- enable_client_portal_dashboard:
- description: 'Toggles whether the client dashboard is shown in the client portal'
- type: boolean
- example: false
- enable_client_portal:
- description: 'Toggles whether the entire client portal is displayed to the client, or only the context'
- type: boolean
- example: false
- email_template_statement:
- description: 'The body of the email for statements'
- type: string
- example: 'template matter'
- email_subject_statement:
- description: 'The subject of the email for statements'
- type: string
- example: 'subject matter'
- signature_on_pdf:
- description: 'Toggles whether the signature (if available) is displayed on the PDF'
- type: boolean
- example: false
- quote_footer:
- description: 'The default quote footer'
- type: string
- example: 'the quote footer'
- email_subject_custom1:
- description: 'Custom reminder template subject'
- type: string
- example: 'Custom Subject 1'
- email_subject_custom2:
- description: 'Custom reminder template subject'
- type: string
- example: 'Custom Subject 2'
- email_subject_custom3:
- description: 'Custom reminder template subject'
- type: string
- example: 'Custom Subject 3'
- email_template_custom1:
- description: 'Custom reminder template body'
- type: string
- example: ''
- email_template_custom2:
- description: 'Custom reminder template body'
- type: string
- example: ''
- email_template_custom3:
- description: 'Custom reminder template body'
- type: string
- example: ''
- enable_reminder1:
- description: 'Toggles whether this reminder is enabled'
- type: boolean
- example: false
- enable_reminder2:
- description: 'Toggles whether this reminder is enabled'
- type: boolean
- example: false
- enable_reminder3:
- description: 'Toggles whether this reminder is enabled'
- type: boolean
- example: false
- num_days_reminder1:
- description: 'The Reminder interval'
- type: number
- example: '9'
- num_days_reminder2:
- description: 'The Reminder interval'
- type: number
- example: '9'
- num_days_reminder3:
- description: 'The Reminder interval'
- type: number
- example: '9'
- schedule_reminder1:
- description: '(enum: after_invoice_date, before_due_date, after_due_date)'
- type: string
- example: after_invoice_date
- schedule_reminder2:
- description: '(enum: after_invoice_date, before_due_date, after_due_date)'
- type: string
- example: after_invoice_date
- schedule_reminder3:
- description: '(enum: after_invoice_date, before_due_date, after_due_date)'
- type: string
- example: after_invoice_date
- late_fee_amount1:
- description: 'The late fee amount for reminder 1'
- type: number
- example: 10
- late_fee_amount2:
- description: 'The late fee amount for reminder 2'
- type: number
- example: 20
- late_fee_amount3:
- description: 'The late fee amount for reminder 2'
- type: number
- example: 100
- endless_reminder_frequency_id:
- description: 'The frequency id of the endless reminder'
- type: string
- example: '1'
- client_online_payment_notification:
- description: 'Determines if a client should receive the notification for a online payment'
- type: boolean
- example: false
- client_manual_payment_notification:
- description: 'Determines if a client should receive the notification for a manually entered payment'
- type: boolean
- example: false
- type: object
- CompanyToken:
- properties:
- name:
- description: 'The token name'
- type: string
- example: 'Token Name'
- token:
- description: 'The token value'
- type: string
- example: AS3df3jUUH765fhfd9KJuidj3JShjA
- is_system:
- description: 'Determines whether the token is created by the system rather than a user'
- type: boolean
- example: 'true'
- type: object
- CompanyUser:
- properties:
- permissions:
- description: 'The company user permissions'
- type: string
- example: '[create_invoice]'
- settings:
- description: 'Settings that are used for the frontend applications to store user preferences / metadata'
- type: object
- example: 'json object'
- is_owner:
- description: 'Determines whether the user owns this company'
- type: boolean
- example: true
- is_admin:
- description: 'Determines whether the user is the admin of this company'
- type: boolean
- example: true
- is_locked:
- description: 'Determines whether the users access to this company has been locked'
- type: boolean
- example: true
- updated_at:
- description: 'The last time the record was modified, format Unix Timestamp'
- type: integer
- example: '1231232312321'
- deleted_at:
- description: 'Timestamp when the user was archived, format Unix Timestamp'
- type: integer
- example: '12312312321'
- account:
- $ref: '#/components/schemas/Account'
- company:
- $ref: '#/components/schemas/Company'
- user:
- $ref: '#/components/schemas/User'
- token:
- $ref: '#/components/schemas/CompanyToken'
- type: object
CreditPaymentable:
properties:
credit_id:
@@ -1283,713 +10,6 @@
type: string
example: '2'
type: object
- Credit:
- properties:
- id:
- description: 'The credit hashed id'
- type: string
- example: Opnel5aKBz
- user_id:
- description: 'The user hashed id'
- type: string
- example: ''
- assigned_user_id:
- description: 'The assigned user hashed id'
- type: string
- example: ''
- company_id:
- description: 'The company hashed id'
- type: string
- example: ''
- client_id:
- description: 'The client hashed id'
- type: string
- example: ''
- status_id:
- description: 'The status field id infors of the current status of the credit'
- type: string
- example: ''
- invoice_id:
- description: 'The linked invoice this credit is applied to'
- type: string
- example: ''
- number:
- description: 'The credit number - is a unique alpha numeric number per credit per company'
- type: string
- example: QUOTE_101
- po_number:
- description: 'The purchase order number this credit refers to'
- type: string
- example: ''
- terms:
- description: 'The credit terms field'
- type: string
- example: ''
- public_notes:
- description: 'The public notes field of the credit'
- type: string
- example: ''
- private_notes:
- description: 'The private notes field of the credit'
- type: string
- example: ''
- footer:
- description: 'The credit footer text'
- type: string
- example: ''
- custom_value1:
- description: 'A Custom value'
- type: string
- example: ''
- custom_value2:
- description: 'A Custom value'
- type: string
- example: ''
- custom_value3:
- description: 'A Custom value'
- type: string
- example: ''
- custom_value4:
- description: 'A Custom value'
- type: string
- example: ''
- tax_name1:
- description: 'The tax name'
- type: string
- example: ''
- tax_name2:
- description: 'The tax rate'
- type: string
- example: ''
- tax_rate1:
- description: 'The tax name'
- type: number
- format: float
- example: '10.00'
- tax_rate2:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- tax_name3:
- description: 'The tax name'
- type: string
- example: ''
- tax_rate3:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- total_taxes:
- description: 'The total taxes for the credit'
- type: number
- format: float
- example: '10.00'
- line_items:
- description: 'The line items array containing the line items of the credit'
- type: object
- example: ''
- amount:
- description: 'The total credit amount'
- type: number
- format: float
- example: '10.00'
- balance:
- description: 'The credit balance'
- type: number
- format: float
- example: '10.00'
- paid_to_date:
- description: _________
- type: number
- format: float
- example: '10.00'
- discount:
- description: _________
- type: number
- format: float
- example: '10.00'
- partial:
- description: _________
- type: number
- format: float
- example: '10.00'
- is_amount_discount:
- description: _________
- type: boolean
- example: true
- is_deleted:
- description: _________
- type: boolean
- example: true
- uses_inclusive_taxes:
- description: 'Defines the type of taxes used as either inclusive or exclusive'
- type: boolean
- example: true
- date:
- description: 'The Credit Date'
- type: string
- format: date
- example: '1994-07-30'
- last_sent_date:
- description: 'The last date the credit was sent out'
- type: string
- format: date
- example: '1994-07-30'
- next_send_date:
- description: 'The Next date for a reminder to be sent'
- type: string
- format: date
- example: '1994-07-30'
- partial_due_date:
- description: _________
- type: string
- format: date
- example: '1994-07-30'
- due_date:
- description: _________
- type: string
- format: date
- example: '1994-07-30'
- settings:
- $ref: '#/components/schemas/CompanySettings'
- last_viewed:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- archived_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- custom_surcharge1:
- description: 'First Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge2:
- description: 'Second Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge3:
- description: 'Third Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge4:
- description: 'Fourth Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge_tax1:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax2:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax3:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax4:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- type: object
- Design:
- properties:
- id:
- description: 'The design hashed id'
- type: string
- example: AS3df3A
- name:
- description: 'The design name'
- type: string
- example: Beauty
- design:
- description: 'The design HTML'
- type: string
- example: ''
- is_custom:
- description: 'Flag to determine if the design is a custom user design'
- type: boolean
- example: true
- is_active:
- description: 'Flag to determine if the design is available for use'
- type: boolean
- example: true
- is_deleted:
- description: 'Flag to determine if the design is deleted'
- type: boolean
- example: true
- created_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- deleted_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- type: object
- Document:
- properties:
- id:
- description: 'The document hashed id'
- type: string
- example: AS3df3A
- user_id:
- description: 'The user hashed id'
- type: string
- example: ''
- assigned_user_id:
- description: 'The assigned user hashed id'
- type: string
- example: ''
- project_id:
- description: 'The project associated with this document'
- type: string
- example: ''
- vendor_id:
- description: 'The vendor associated with this documents'
- type: string
- example: ''
- name:
- description: 'The document name'
- type: string
- example: Beauty
- url:
- description: 'The document url'
- type: string
- example: Beauty
- preview:
- description: 'The document preview url'
- type: string
- example: Beauty
- type:
- description: 'The document type'
- type: string
- example: Beauty
- disk:
- description: 'The document disk'
- type: string
- example: Beauty
- hash:
- description: 'The document hashed'
- type: string
- example: Beauty
- is_deleted:
- description: 'Flag to determine if the document is deleted'
- type: boolean
- example: true
- is_default:
- description: 'Flag to determine if the document is a default doc'
- type: boolean
- example: true
- created_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- deleted_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- type: object
- Error:
- properties:
- message:
- description: 'Something terrible went wrong'
- type: string
- example: 'Unexpected error'
- code:
- description: 'The HTTP error code, ie 5xx 4xx'
- type: integer
- example: '500'
- type: object
- ExpenseCategory:
- properties:
- id:
- description: 'The expense hashed id'
- type: string
- example: Opnel5aKBz
- name:
- description: 'The expense category name'
- type: string
- example: Accounting
- user_id:
- description: 'The user hashed id'
- type: string
- example: XS987sD
- is_deleted:
- description: 'Flag determining whether the expense category has been deleted'
- type: boolean
- example: true
- updated_at:
- description: 'The updated at timestamp'
- type: integer
- example: '2'
- created_at:
- description: 'The created at timestamp'
- type: integer
- example: '2'
- type: object
- Expense:
- properties:
- id:
- description: 'The expense hashed id'
- type: string
- example: Opnel5aKBz
- user_id:
- description: 'The user hashed id'
- type: string
- example: ''
- assigned_user_id:
- description: 'The assigned user hashed id'
- type: string
- example: ''
- company_id:
- description: 'The company hashed id'
- type: string
- example: ''
- client_id:
- description: 'The client hashed id'
- type: string
- example: ''
- invoice_id:
- description: 'The related invoice hashed id'
- type: string
- example: ''
- bank_id:
- description: 'The bank id related to this expense'
- type: string
- example: ''
- invoice_currency_id:
- description: 'The currency id of the related invoice'
- type: string
- example: ''
- expense_currency_id:
- description: 'The currency id of the expense'
- type: string
- example: ''
- invoice_category_id:
- description: 'The invoice category id'
- type: string
- example: ''
- payment_type_id:
- description: 'The payment type id'
- type: string
- example: ''
- recurring_expense_id:
- description: 'The related recurring expense this expense was created from'
- type: string
- example: ''
- private_notes:
- description: 'The private notes of the expense'
- type: string
- example: ''
- public_notes:
- description: 'The public notes of the expense'
- type: string
- example: ''
- transaction_reference:
- description: 'The transaction references of the expense'
- type: string
- example: ''
- transcation_id:
- description: 'The transaction id of the expense'
- type: string
- example: ''
- custom_value1:
- description: 'A custom value'
- type: string
- example: ''
- custom_value2:
- description: 'A custom value'
- type: string
- example: ''
- custom_value3:
- description: 'A custom value'
- type: string
- example: ''
- custom_value4:
- description: 'A custom value'
- type: string
- example: ''
- tax_name1:
- description: 'Tax name'
- type: string
- example: ''
- tax_name2:
- description: 'Tax name'
- type: string
- example: ''
- tax_rate1:
- description: 'Tax rate'
- type: number
- format: float
- example: '10.00'
- tax_rate2:
- description: 'Tax rate'
- type: number
- format: float
- example: '10.00'
- tax_name3:
- description: 'Tax name'
- type: string
- example: ''
- tax_rate3:
- description: 'Tax rate'
- type: number
- format: float
- example: '10.00'
- amount:
- description: 'The total expense amont'
- type: number
- format: float
- example: '10.00'
- foreign_amount:
- description: 'The total foreign amount of the expense'
- type: number
- format: float
- example: '10.00'
- exchange_rate:
- description: 'The exchange rate at the time of the expense'
- type: number
- format: float
- example: '0.80'
- date:
- description: 'The expense date formate Y-m-d'
- type: string
- example: '2022-12-01'
- payment_date:
- description: 'The date of payment for the expense, format Y-m-d'
- type: string
- example: ''
- should_be_invoiced:
- description: 'Flag whether the expense should be invoiced'
- type: boolean
- example: true
- is_deleted:
- description: 'Boolean determining whether the expense has been deleted'
- type: boolean
- example: true
- invoice_documents:
- description: 'Passing the expense documents over to the invoice'
- type: boolean
- example: true
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- archived_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- type: object
- FeesAndLimits:
- properties:
- min_limit:
- description: 'The minimum amount accepted for this gateway'
- type: string
- example: '2'
- max_limit:
- description: 'The maximum amount accepted for this gateway'
- type: string
- example: '2'
- fee_amount:
- description: 'The gateway fee amount'
- type: number
- format: float
- example: '2.0'
- fee_percent:
- description: 'The gateway fee percentage'
- type: number
- format: float
- example: '2.0'
- fee_tax_name1:
- description: 'Fee tax name'
- type: string
- example: GST
- fee_tax_name2:
- description: 'Fee tax name'
- type: string
- example: VAT
- fee_tax_name3:
- description: 'Fee tax name'
- type: string
- example: 'CA Sales Tax'
- fee_tax_rate1:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.0'
- fee_tax_rate2:
- description: 'The tax rate'
- type: number
- format: float
- example: '17.5'
- fee_tax_rate3:
- description: 'The tax rate'
- type: number
- format: float
- example: '25.0'
- fee_cap:
- description: 'If set the fee amount will be no higher than this amount'
- type: number
- format: float
- example: '2.0'
- adjust_fee_percent:
- description: 'Adjusts the fee to match the exact gateway fee.'
- type: boolean
- example: true
- type: object
- FillableInvoice:
- properties:
- assigned_user_id:
- description: __________
- type: string
- example: ''
- client_id:
- description: ________
- type: string
- example: ''
- number:
- description: 'The invoice number - is a unique alpha numeric number per invoice per company'
- type: string
- example: INV_101
- po_number:
- description: ________
- type: string
- example: ''
- terms:
- description: ________
- type: string
- example: ''
- public_notes:
- description: ________
- type: string
- example: ''
- private_notes:
- description: ________
- type: string
- example: ''
- footer:
- description: ________
- type: string
- example: ''
- custom_value1:
- description: ________
- type: string
- example: ''
- custom_value2:
- description: ________
- type: string
- example: ''
- custom_value3:
- description: ________
- type: string
- example: ''
- custom_value4:
- description: ________
- type: string
- example: ''
- tax_name1:
- description: ________
- type: string
- example: ''
- tax_name2:
- description: ________
- type: string
- example: ''
- tax_rate1:
- description: _________
- type: number
- example: '10.00'
- tax_rate2:
- description: _________
- type: number
- example: '10.00'
- tax_name3:
- description: ________
- type: string
- example: ''
- tax_rate3:
- description: _________
- type: number
- example: '10.00'
- line_items:
- description: _________
- type: object
- example: ''
- discount:
- description: _________
- type: number
- example: '10.00'
- partial:
- description: _________
- type: number
- example: '10.00'
- is_amount_discount:
- description: _________
- type: boolean
- example: '1'
- uses_inclusive_taxes:
- description: 'Defines the type of taxes used as either inclusive or exclusive'
- type: boolean
- example: '1'
- date:
- description: 'The Invoice Date'
- type: string
- example: '1994-07-30'
- partial_due_date:
- description: _________
- type: string
- example: '1994-07-30'
- due_date:
- description: _________
- type: string
- example: '1994-07-30'
- custom_surcharge1:
- description: 'First Custom Surcharge'
- type: number
- example: '10.00'
- custom_surcharge2:
- description: 'Second Custom Surcharge'
- type: number
- example: '10.00'
- custom_surcharge3:
- description: 'Third Custom Surcharge'
- type: number
- example: '10.00'
- custom_surcharge4:
- description: 'Fourth Custom Surcharge'
- type: number
- example: '10.00'
- type: object
GenericReportSchema:
properties:
date_range:
@@ -2049,1279 +69,12 @@
type: string
example: '2'
type: object
- Invoice:
- properties:
- id:
- description: 'The invoice hashed id'
- type: string
- example: Opnel5aKBz
- user_id:
- description: 'The user hashed id'
- type: string
- example: Opnel5aKBz
- assigned_user_id:
- description: 'The assigned user hashed id'
- type: string
- example: Opnel5aKBz
- company_id:
- description: 'The company hashed id'
- type: string
- example: Opnel5aKBz
- client_id:
- description: 'The client hashed id'
- type: string
- example: Opnel5aKBz
- status_id:
- description: 'The invoice status variable'
- type: string
- example: '4'
- number:
- description: 'The invoice number - is a unique alpha numeric number per invoice per company'
- type: string
- example: INV_101
- po_number:
- description: 'The purchase order associated with this invoice'
- type: string
- example: PO-1234
- terms:
- description: 'The invoice terms'
- type: string
- example: 'These are invoice terms'
- public_notes:
- description: 'The public notes of the invoice'
- type: string
- example: 'These are some public notes'
- private_notes:
- description: 'The private notes of the invoice'
- type: string
- example: 'These are some private notes'
- footer:
- description: 'The invoice footer notes'
- type: string
- example: ''
- custom_value1:
- description: 'A custom field value'
- type: string
- example: '2022-10-01'
- custom_value2:
- description: 'A custom field value'
- type: string
- example: 'Something custom'
- custom_value3:
- description: 'A custom field value'
- type: string
- example: ''
- custom_value4:
- description: 'A custom field value'
- type: string
- example: ''
- tax_name1:
- description: 'The tax name'
- type: string
- example: ''
- tax_name2:
- description: 'The tax name'
- type: string
- example: ''
- tax_rate1:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- tax_rate2:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- tax_name3:
- description: 'The tax name'
- type: string
- example: ''
- tax_rate3:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- total_taxes:
- description: 'The total taxes for the invoice'
- type: number
- format: float
- example: '10.00'
- line_items:
- description: 'An array of objects which define the line items of the invoice'
- type: object
- example: ''
- amount:
- description: 'The invoice amount'
- type: number
- format: float
- example: '10.00'
- balance:
- description: 'The invoice balance'
- type: number
- format: float
- example: '10.00'
- paid_to_date:
- description: 'The amount paid on the invoice to date'
- type: number
- format: float
- example: '10.00'
- discount:
- description: 'The invoice discount, can be an amount or a percentage'
- type: number
- format: float
- example: '10.00'
- partial:
- description: 'The deposit/partial amount'
- type: number
- format: float
- example: '10.00'
- is_amount_discount:
- description: 'Flag determining if the discount is an amount or a percentage'
- type: boolean
- example: true
- is_deleted:
- description: 'Defines if the invoice has been deleted'
- type: boolean
- example: true
- uses_inclusive_taxes:
- description: 'Defines the type of taxes used as either inclusive or exclusive'
- type: boolean
- example: true
- date:
- description: 'The Invoice Date'
- type: string
- format: date
- example: '1994-07-30'
- last_sent_date:
- description: 'The last date the invoice was sent out'
- type: string
- format: date
- example: '1994-07-30'
- next_send_date:
- description: 'The Next date for a reminder to be sent'
- type: string
- format: date
- example: '1994-07-30'
- partial_due_date:
- description: 'The due date for the deposit/partial amount'
- type: string
- format: date
- example: '1994-07-30'
- due_date:
- description: 'The due date of the invoice'
- type: string
- format: date
- example: '1994-07-30'
- settings:
- $ref: '#/components/schemas/CompanySettings'
- last_viewed:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- archived_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- custom_surcharge1:
- description: 'First Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge2:
- description: 'Second Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge3:
- description: 'Third Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge4:
- description: 'Fourth Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge_tax1:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax2:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax3:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax4:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- type: object
- Payment:
- properties:
- id:
- description: 'The payment hashed id'
- type: string
- example: Opnel5aKBz
- client_id:
- description: 'The client hashed id'
- type: string
- example: Opnel5aKBz
- invitation_id:
- description: 'The invitation hashed id'
- type: string
- example: Opnel5aKBz
- client_contact_id:
- description: 'The client contact hashed id'
- type: string
- example: Opnel5aKBz
- user_id:
- description: 'The user hashed id'
- type: string
- example: Opnel5aKBz
- type_id:
- description: 'The Payment Type ID'
- type: string
- example: '1'
- date:
- description: 'The Payment date'
- type: string
- example: 1-1-2014
- transaction_reference:
- description: 'The transaction reference as defined by the payment gateway'
- type: string
- example: xcsSxcs124asd
- assigned_user_id:
- description: 'The assigned user hashed id'
- type: string
- example: Opnel5aKBz
- private_notes:
- description: 'The private notes of the payment'
- type: string
- example: 'The payment was refunded due to error'
- is_manual:
- description: 'Flags whether the payment was made manually or processed via a gateway'
- type: boolean
- example: true
- is_deleted:
- description: 'Defines if the payment has been deleted'
- type: boolean
- example: true
- amount:
- description: 'The amount of this payment'
- type: number
- example: 10
- refunded:
- description: 'The refunded amount of this payment'
- type: number
- example: 10
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- archived_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- company_gateway_id:
- description: 'The company gateway id'
- type: string
- example: '3'
- paymentables:
- $ref: '#/components/schemas/Paymentable'
- invoices:
- description: ''
- type: array
- items:
- $ref: '#/components/schemas/InvoicePaymentable'
- credits:
- description: ''
- type: array
- items:
- $ref: '#/components/schemas/CreditPaymentable'
- type: object
- PaymentTerm:
- properties:
- num_days:
- description: 'The payment term length in days'
- type: integer
- example: '1'
- name:
- description: 'The payment term length in string format'
- type: string
- example: 'NET 1'
- created_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- archived_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- type: object
- Paymentable:
- properties:
- id:
- description: 'The paymentable hashed id'
- type: string
- example: AS3df3A
- invoice_id:
- description: 'The invoice hashed id'
- type: string
- example: AS3df3A
- credit_id:
- description: 'The credit hashed id'
- type: string
- example: AS3df3A
- refunded:
- description: 'The amount that has been refunded for this payment'
- type: number
- format: float
- example: '10.00'
- amount:
- description: 'The amount that has been applied to the payment'
- type: number
- format: float
- example: '10.00'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- created_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- type: object
- Product:
- properties:
- id:
- description: 'The product hashed id'
- type: string
- example: Opnel5aKBz
- type: object
- Project:
- properties:
- id:
- description: 'The project hashed id'
- type: string
- example: Opnel5aKBz
- name:
- description: 'The project name'
- type: string
- example: 'New Project'
- type: object
- PurchaseOrder:
- properties:
- id:
- description: 'The purchase order hashed id'
- type: string
- example: Opnel5aKBz
- type: object
- Quote:
- properties:
- id:
- description: 'The quote hashed id'
- type: string
- example: Opnel5aKBz
- user_id:
- description: 'The user hashed id'
- type: string
- example: ''
- assigned_user_id:
- description: 'The assigned user hashed id'
- type: string
- example: ''
- company_id:
- description: 'The company hashed id'
- type: string
- example: ''
- client_id:
- description: 'The client hashed id'
- type: string
- example: ''
- status_id:
- description: 'The status of the quote'
- type: string
- example: ''
- number:
- description: 'The quote number - is a unique alpha numeric number per quote per company'
- type: string
- example: QUOTE_101
- po_number:
- description: 'The purchase order number associated with this quote'
- type: string
- example: PO-1234
- terms:
- description: 'The quote terms'
- type: string
- example: 'These are some quote terms. Valid for 14 days.'
- public_notes:
- description: 'Public notes for the quote'
- type: string
- example: 'These are public notes which the client may see'
- private_notes:
- description: 'Private notes for the quote'
- type: string
- example: 'These are private notes, not to be disclosed to the client'
- footer:
- description: 'Footer text of quote'
- type: string
- example: 'The text goes in the footer of the quote'
- custom_value1:
- description: 'Custom value field'
- type: string
- example: 'A custom value'
- custom_value2:
- description: 'Custom value field'
- type: string
- example: 'A custom value'
- custom_value3:
- description: 'Custom value field'
- type: string
- example: 'A custom value'
- custom_value4:
- description: 'Custom value field'
- type: string
- example: 'A custom value'
- tax_name1:
- description: 'The tax name'
- type: string
- example: GST
- tax_name2:
- description: 'The tax name'
- type: string
- example: VAT
- tax_rate1:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- tax_rate2:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- tax_name3:
- description: 'The tax name'
- type: string
- example: ''
- tax_rate3:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- total_taxes:
- description: 'The total taxes for the quote'
- type: number
- format: float
- example: '10.00'
- line_items:
- description: 'An array of line items of the quote'
- type: object
- example: ''
- amount:
- description: 'The total amount of the quote'
- type: number
- format: float
- example: '10.00'
- balance:
- description: 'The balance due of the quote'
- type: number
- format: float
- example: '10.00'
- paid_to_date:
- description: 'The amount that has been paid to date on the quote'
- type: number
- format: float
- example: '10.00'
- discount:
- description: 'The quote discount'
- type: number
- format: float
- example: '10.00'
- partial:
- description: 'The partial/deposit amount'
- type: number
- format: float
- example: '10.00'
- is_amount_discount:
- description: 'Boolean flag determining if the quote is an amount or percentage'
- type: boolean
- example: true
- is_deleted:
- description: 'Boolean flag determining if the quote has been deleted'
- type: boolean
- example: true
- uses_inclusive_taxes:
- description: 'Defines the type of taxes used as either inclusive or exclusive'
- type: boolean
- example: true
- date:
- description: 'The Quote Date'
- type: string
- format: date
- example: '1994-07-30'
- last_sent_date:
- description: 'The last date the quote was sent out'
- type: string
- format: date
- example: '1994-07-30'
- next_send_date:
- description: 'The Next date for a reminder to be sent'
- type: string
- format: date
- example: '1994-07-30'
- partial_due_date:
- description: 'The date when the partial/deposit is due'
- type: string
- format: date
- example: '1994-07-30'
- due_date:
- description: 'The date the quote is valid until'
- type: string
- format: date
- example: '1994-07-30'
- settings:
- $ref: '#/components/schemas/CompanySettings'
- last_viewed:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- archived_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- custom_surcharge1:
- description: 'First Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge2:
- description: 'Second Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge3:
- description: 'Third Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge4:
- description: 'Fourth Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge_tax1:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax2:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax3:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax4:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- type: object
- RecurringExpense:
- properties:
- id:
- description: 'The hashed id of the recurring expense'
- type: string
- example: Opnel5aKBz
- user_id:
- description: 'The hashed id of the user who created the recurring expense'
- type: string
- example: Opnel5aKBz
- assigned_user_id:
- description: 'The hashed id of the user assigned to this recurring expense'
- type: string
- example: Opnel5aKBz
- company_id:
- description: 'The hashed id of the company'
- type: string
- example: Opnel5aKBz
- client_id:
- description: 'The hashed id of the client'
- type: string
- example: Opnel5aKBz
- invoice_id:
- description: 'The hashed id of the invoice'
- type: string
- example: Opnel5aKBz
- bank_id:
- description: 'The id of the bank associated with this recurring expense'
- type: string
- example: '22'
- invoice_currency_id:
- description: 'The currency id of the invoice associated with this recurring expense'
- type: string
- example: '1'
- expense_currency_id:
- description: 'The currency id of the expense associated with this recurring expense'
- type: string
- example: '1'
- invoice_category_id:
- description: 'The category id of the invoice'
- type: string
- example: '1'
- payment_type_id:
- description: 'The payment type id'
- type: string
- example: '1'
- private_notes:
- description: 'The recurring expense private notes'
- type: string
- example: 'Private and confidential'
- public_notes:
- description: 'The recurring expense public notes'
- type: string
- example: 'This is the best client in the world'
- transaction_reference:
- description: 'The recurring expense transaction reference'
- type: string
- example: EXP-1223-2333
- transcation_id:
- description: 'The transaction id of the recurring expense'
- type: string
- example: '1233312312'
- custom_value1:
- description: 'Custom value field'
- type: string
- example: $1000
- custom_value2:
- description: 'Custom value field'
- type: string
- example: '2022-10-10'
- custom_value3:
- description: 'Custom value field'
- type: string
- example: 'short text'
- custom_value4:
- description: 'Custom value field'
- type: string
- example: 'very long text'
- tax_name1:
- description: 'The tax name'
- type: string
- example: GST
- tax_name2:
- description: 'The tax name'
- type: string
- example: VAT
- tax_rate1:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- tax_rate2:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- tax_name3:
- description: 'The tax name'
- type: string
- example: ''
- tax_rate3:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- amount:
- description: 'The total amount of the recurring expense'
- type: number
- format: float
- example: '10.00'
- frequency_id:
- description: 'The frequency this recurring expense fires'
- type: number
- format: int
- example: '1'
- remaining_cycles:
- description: 'The number of remaining cycles for this recurring expense'
- type: number
- format: int
- example: '1'
- foreign_amount:
- description: 'The foreign currency amount of the recurring expense'
- type: number
- format: float
- example: '10.00'
- exchange_rate:
- description: 'The exchange rate for the expernse'
- type: number
- format: float
- example: '0.80'
- date:
- description: 'The date of the expense'
- type: string
- example: ''
- payment_date:
- description: 'The date the expense was paid'
- type: string
- example: ''
- should_be_invoiced:
- description: 'Boolean flag determining if the expense should be invoiced'
- type: boolean
- example: true
- is_deleted:
- description: 'Boolean flag determining if the recurring expense is deleted'
- type: boolean
- example: true
- last_sent_date:
- description: 'The Date it was sent last'
- type: string
- format: date
- example: '1994-07-30'
- next_send_date:
- description: 'The next send date'
- type: string
- format: date
- example: '1994-07-30'
- invoice_documents:
- description: 'Boolean flag determining if the documents associated with this expense should be passed onto the invoice if it is converted to an invoice'
- type: boolean
- example: true
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- archived_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- type: object
- RecurringInvoice:
- properties:
- id:
- description: 'The hashed id of the recurring invoice'
- type: string
- example: Opnel5aKBz
- user_id:
- description: 'The user hashed id'
- type: string
- example: Opnel5aKBz
- assigned_user_id:
- description: 'The assigned user hashed id'
- type: string
- example: Opnel5aKBz
- company_id:
- description: 'The company hashed id'
- type: string
- example: Opnel5aKBz
- client_id:
- description: 'The client hashed id'
- type: string
- example: Opnel5aKBz
- status_id:
- description: 'The invoice status variable'
- type: string
- example: '4'
- frequency_id:
- description: 'The recurring invoice frequency'
- type: number
- example: '4'
- remaining_cycles:
- description: 'The number of invoices left to be generated'
- type: number
- example: '4'
- number:
- description: 'The recurringinvoice number - is a unique alpha numeric number per invoice per company'
- type: string
- example: INV_101
- po_number:
- description: 'The purchase order associated with this recurring invoice'
- type: string
- example: PO-1234
- terms:
- description: 'The invoice terms'
- type: string
- example: 'These are invoice terms'
- public_notes:
- description: 'The public notes of the invoice'
- type: string
- example: 'These are some public notes'
- private_notes:
- description: 'The private notes of the invoice'
- type: string
- example: 'These are some private notes'
- footer:
- description: 'The invoice footer notes'
- type: string
- example: ''
- custom_value1:
- description: 'A custom field value'
- type: string
- example: '2022-10-01'
- custom_value2:
- description: 'A custom field value'
- type: string
- example: 'Something custom'
- custom_value3:
- description: 'A custom field value'
- type: string
- example: ''
- custom_value4:
- description: 'A custom field value'
- type: string
- example: ''
- tax_name1:
- description: 'The tax name'
- type: string
- example: ''
- tax_name2:
- description: 'The tax name'
- type: string
- example: ''
- tax_rate1:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- tax_rate2:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- tax_name3:
- description: 'The tax name'
- type: string
- example: ''
- tax_rate3:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- total_taxes:
- description: 'The total taxes for the invoice'
- type: number
- format: float
- example: '10.00'
- line_items:
- description: 'An array of objects which define the line items of the invoice'
- type: object
- example: ''
- amount:
- description: 'The invoice amount'
- type: number
- format: float
- example: '10.00'
- balance:
- description: 'The invoice balance'
- type: number
- format: float
- example: '10.00'
- paid_to_date:
- description: 'The amount paid on the invoice to date'
- type: number
- format: float
- example: '10.00'
- discount:
- description: 'The invoice discount, can be an amount or a percentage'
- type: number
- format: float
- example: '10.00'
- partial:
- description: 'The deposit/partial amount'
- type: number
- format: float
- example: '10.00'
- is_amount_discount:
- description: 'Flag determining if the discount is an amount or a percentage'
- type: boolean
- example: true
- is_deleted:
- description: 'Defines if the invoice has been deleted'
- type: boolean
- example: true
- uses_inclusive_taxes:
- description: 'Defines the type of taxes used as either inclusive or exclusive'
- type: boolean
- example: true
- date:
- description: 'The Invoice Date'
- type: string
- format: date
- example: '1994-07-30'
- last_sent_date:
- description: 'The last date the invoice was sent out'
- type: string
- format: date
- example: '1994-07-30'
- next_send_date:
- description: 'The Next date for a reminder to be sent'
- type: string
- format: date
- example: '1994-07-30'
- partial_due_date:
- description: 'The due date for the deposit/partial amount'
- type: string
- format: date
- example: '1994-07-30'
- due_date:
- description: 'The due date of the invoice'
- type: string
- format: date
- example: '1994-07-30'
- settings:
- $ref: '#/components/schemas/CompanySettings'
- last_viewed:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- archived_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- custom_surcharge1:
- description: 'First Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge2:
- description: 'Second Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge3:
- description: 'Third Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge4:
- description: 'Fourth Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge_tax1:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax2:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax3:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax4:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- type: object
- RecurringQuote:
- properties:
- id:
- description: 'The hashed id of the recurring quote'
- type: string
- example: Opnel5aKBz
- user_id:
- description: 'The user hashed id'
- type: string
- example: Opnel5aKBz
- assigned_user_id:
- description: 'The assigned user hashed id'
- type: string
- example: Opnel5aKBz
- company_id:
- description: 'The company hashed id'
- type: string
- example: Opnel5aKBz
- client_id:
- description: 'The client hashed id'
- type: string
- example: Opnel5aKBz
- status_id:
- description: 'The quote status variable'
- type: string
- example: '4'
- frequency_id:
- description: 'The recurring quote frequency'
- type: number
- example: '4'
- remaining_cycles:
- description: 'The number of quotes left to be generated'
- type: number
- example: '4'
- number:
- description: 'The recurringquote number - is a unique alpha numeric number per quote per company'
- type: string
- example: INV_101
- po_number:
- description: 'The purchase order associated with this recurring quote'
- type: string
- example: PO-1234
- terms:
- description: 'The quote terms'
- type: string
- example: 'These are quote terms'
- public_notes:
- description: 'The public notes of the quote'
- type: string
- example: 'These are some public notes'
- private_notes:
- description: 'The private notes of the quote'
- type: string
- example: 'These are some private notes'
- footer:
- description: 'The quote footer notes'
- type: string
- example: ''
- custom_value1:
- description: 'A custom field value'
- type: string
- example: '2022-10-01'
- custom_value2:
- description: 'A custom field value'
- type: string
- example: 'Something custom'
- custom_value3:
- description: 'A custom field value'
- type: string
- example: ''
- custom_value4:
- description: 'A custom field value'
- type: string
- example: ''
- tax_name1:
- description: 'The tax name'
- type: string
- example: ''
- tax_name2:
- description: 'The tax name'
- type: string
- example: ''
- tax_rate1:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- tax_rate2:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- tax_name3:
- description: 'The tax name'
- type: string
- example: ''
- tax_rate3:
- description: 'The tax rate'
- type: number
- format: float
- example: '10.00'
- total_taxes:
- description: 'The total taxes for the quote'
- type: number
- format: float
- example: '10.00'
- line_items:
- description: 'An array of objects which define the line items of the quote'
- type: object
- example: ''
- amount:
- description: 'The quote amount'
- type: number
- format: float
- example: '10.00'
- balance:
- description: 'The quote balance'
- type: number
- format: float
- example: '10.00'
- paid_to_date:
- description: 'The amount paid on the quote to date'
- type: number
- format: float
- example: '10.00'
- discount:
- description: 'The quote discount, can be an amount or a percentage'
- type: number
- format: float
- example: '10.00'
- partial:
- description: 'The deposit/partial amount'
- type: number
- format: float
- example: '10.00'
- is_amount_discount:
- description: 'Flag determining if the discount is an amount or a percentage'
- type: boolean
- example: true
- is_deleted:
- description: 'Defines if the quote has been deleted'
- type: boolean
- example: true
- uses_inclusive_taxes:
- description: 'Defines the type of taxes used as either inclusive or exclusive'
- type: boolean
- example: true
- date:
- description: 'The quote Date'
- type: string
- format: date
- example: '1994-07-30'
- last_sent_date:
- description: 'The last date the quote was sent out'
- type: string
- format: date
- example: '1994-07-30'
- next_send_date:
- description: 'The Next date for a reminder to be sent'
- type: string
- format: date
- example: '1994-07-30'
- partial_due_date:
- description: 'The due date for the deposit/partial amount'
- type: string
- format: date
- example: '1994-07-30'
- due_date:
- description: 'The due date of the quote'
- type: string
- format: date
- example: '1994-07-30'
- settings:
- $ref: '#/components/schemas/CompanySettings'
- last_viewed:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- archived_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- custom_surcharge1:
- description: 'First Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge2:
- description: 'Second Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge3:
- description: 'Third Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge4:
- description: 'Fourth Custom Surcharge'
- type: number
- format: float
- example: '10.00'
- custom_surcharge_tax1:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax2:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax3:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- custom_surcharge_tax4:
- description: 'Toggles charging taxes on custom surcharge amounts'
- type: boolean
- example: true
- type: object
- SystemLog:
- properties:
- id:
- description: 'The account hashed id'
- type: string
- example: AS3df3A
- company_id:
- description: 'The company hashed id'
- type: string
- example: AS3df3A
- user_id:
- description: 'The user_id hashed id'
- type: string
- example: AS3df3A
- client_id:
- description: 'The client_id hashed id'
- type: string
- example: AS3df3A
- event_id:
- description: 'The Log Type ID'
- type: integer
- example: 1
- category_id:
- description: 'The Category Type ID'
- type: integer
- example: 1
- type_id:
- description: 'The Type Type ID'
- type: integer
- example: 1
- log:
- description: 'The json object of the error'
- type: object
- example: '{''key'':''value''}'
- updated_at:
- description: Timestamp
- type: string
- example: '2'
- created_at:
- description: Timestamp
- type: string
- example: '2'
- type: object
+
+
+
+
+
+
TaskSchedulerSchema:
properties:
paused:
@@ -3405,100 +158,7 @@
type: string
example: create_client_report
type: object
- Task:
- properties:
- id:
- description: 'The hashed id of the task'
- type: string
- example: Opnel5aKBz
- user_id:
- description: 'The hashed id of the user who created the task'
- type: string
- example: Opnel5aKBz
- assigned_user_id:
- description: 'The assigned user of the task'
- type: string
- example: Opnel5aKBz
- company_id:
- description: 'The hashed id of the company'
- type: string
- example: Opnel5aKBz
- client_id:
- description: 'The hashed if of the client'
- type: string
- example: Opnel5aKBz
- invoice_id:
- description: 'The hashed id of the invoice associated with the task'
- type: string
- example: Opnel5aKBz
- project_id:
- description: 'The hashed id of the project associated with the task'
- type: string
- example: Opnel5aKBz
- number:
- description: 'The number of the task'
- type: string
- example: TASK-123
- time_log:
- description: 'An array of unix time stamps defining the start and end times of the task'
- type: string
- example: '[[1,2],[3,4]]'
- is_running:
- description: 'Determines if the task is still running'
- type: boolean
- example: true
- is_deleted:
- description: 'Boolean flag determining if the task has been deleted'
- type: boolean
- example: true
- task_status_id:
- description: 'The hashed id of the task status'
- type: string
- example: Opnel5aKBz
- description:
- description: 'The task description'
- type: string
- example: 'A wonder task to work on'
- duration:
- description: 'The task duration'
- type: integer
- example: ''
- task_status_order:
- description: 'The order of the task'
- type: integer
- example: '4'
- custom_value1:
- description: 'A custom value'
- type: string
- example: '2022-10-10'
- custom_value2:
- description: 'A custom value'
- type: string
- example: $1100
- custom_value3:
- description: 'A custom value'
- type: string
- example: 'I need help'
- custom_value4:
- description: 'A custom value'
- type: string
- example: INV-3343
- created_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- archived_at:
- description: Timestamp
- type: number
- format: integer
- example: '1434342123'
- type: object
+
TaskStatus:
properties:
name:
@@ -3551,49 +211,7 @@
type: string
example: ''
type: object
- User:
- properties:
- id:
- description: 'The hashed id of the user'
- type: string
- example: Opnel5aKBz
- first_name:
- description: 'The first name of the user'
- type: string
- example: Brad
- last_name:
- description: 'The last name of the user'
- type: string
- example: Pitt
- email:
- description: 'The users email address'
- type: string
- example: brad@pitt.com
- phone:
- description: 'The users phone number'
- type: string
- example: 555-1233-23232
- signature:
- description: 'The users sign off signature'
- type: string
- example: 'Have a nice day!'
- avatar:
- description: 'The users avatar'
- type: string
- example: 'https://url.to.your/avatar.png'
- accepted_terms_version:
- description: 'The version of the invoice ninja terms that has been accepted by the user'
- type: string
- example: 1.0.1
- oauth_user_id:
- description: 'The provider id of the oauth entity'
- type: string
- example: jkhasdf789as6f675sdf768sdfs
- oauth_provider_id:
- description: 'The oauth entity id'
- type: string
- example: google
- type: object
+
AuthenticationError:
type: object
properties:
@@ -3629,204 +247,8 @@
type: string
type: object
type: object
- VendorContact:
- properties:
- id:
- description: 'The hashed id of the vendor contact'
- type: string
- example: Opnel5aKBz
- user_id:
- description: 'The hashed id of the user id'
- type: string
- example: Opnel5aKBz
- company_id:
- description: 'The hashed id of the company'
- type: string
- example: Opnel5aKBz
- vendor_id:
- description: 'The hashed id of the vendor'
- type: string
- example: Opnel5aKBz
- first_name:
- description: 'The first name of the contact'
- type: string
- example: Harry
- last_name:
- description: 'The last name of the contact'
- type: string
- example: Windsor
- phone:
- description: 'The contacts phone number'
- type: string
- example: 555-123-1234
- custom_value1:
- description: 'A custom value'
- type: string
- example: '2022-10-10'
- custom_value2:
- description: 'A custom value'
- type: string
- example: $1000
- custom_value3:
- description: 'A custom value'
- type: string
- example: ''
- custom_value4:
- description: 'A custom value'
- type: string
- example: ''
- email:
- description: 'The contact email address'
- type: string
- example: harry@windsor.com
- is_primary:
- description: 'Boolean flag determining if the contact is the primary contact for the vendor'
- type: boolean
- example: true
- created_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- deleted_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- type: object
- Vendor:
- properties:
- id:
- description: 'The hashed id of the vendor'
- type: string
- example: Opnel5aKBz
- user_id:
- description: 'The hashed id of the user who created the vendor'
- type: string
- example: Opnel5aKBz
- assigned_user_id:
- description: 'The hashed id of the assigned user to this vendor'
- type: string
- example: Opnel5aKBz
- company_id:
- description: 'The hashed id of the company'
- type: string
- example: Opnel5aKBz
- client_id:
- description: 'The hashed id of the client'
- type: string
- example: Opnel5aKBz
- contacts:
- type: array
- items:
- $ref: '#/components/schemas/VendorContact'
- name:
- description: 'The vendor name'
- type: string
- example: 'Harry''s cafe de wheels'
- website:
- description: 'The website of the vendor'
- type: string
- example: www.harry.com
- private_notes:
- description: 'The private notes of the vendor'
- type: string
- example: 'Shhh, don''t tell the vendor'
- industry_id:
- description: 'The industry id of the vendor'
- type: string
- example: '1'
- size_id:
- description: ________
- type: string
- example: ''
- address1:
- description: ________
- type: string
- example: ''
- address2:
- description: ________
- type: string
- example: ''
- city:
- description: ________
- type: string
- example: ''
- state:
- description: ________
- type: string
- example: ''
- postal_code:
- description: ________
- type: string
- example: ''
- phone:
- description: 'The client phone number'
- type: string
- example: 555-3434-3434
- country_id:
- description: ________
- type: string
- example: ''
- currency_id:
- description: ________
- type: string
- example: '4'
- custom_value1:
- description: ________
- type: string
- example: ''
- custom_value2:
- description: ________
- type: string
- example: ''
- custom_value3:
- description: ________
- type: string
- example: ''
- custom_value4:
- description: ________
- type: string
- example: ''
- vat_number:
- description: ________
- type: string
- example: ''
- id_number:
- description: ________
- type: string
- example: ''
- number:
- description: ________
- type: string
- example: ''
- is_deleted:
- description: ________
- type: boolean
- example: true
- last_login:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- created_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- updated_at:
- description: Timestamp
- type: number
- format: integer
- example: '134341234234'
- settings:
- $ref: '#/components/schemas/CompanySettings'
- type: object
+
+
Webhook:
properties:
id:
diff --git a/openapi/components/schemas/bank_transaction_rule.yaml b/openapi/components/schemas/bank_transaction_rule.yaml
new file mode 100644
index 000000000000..07c22d3d157c
--- /dev/null
+++ b/openapi/components/schemas/bank_transaction_rule.yaml
@@ -0,0 +1,48 @@
+ BankTransactionRule:
+ properties:
+ id:
+ description: 'The bank transaction rules hashed id'
+ type: string
+ example: AS3df3A
+ company_id:
+ description: 'The company hashed id'
+ type: string
+ example: AS3df3A
+ user_id:
+ description: 'The user hashed id'
+ type: string
+ example: AS3df3A
+ name:
+ description: 'The name of the transaction'
+ type: string
+ example: 'Rule 1'
+ rules:
+ description: 'A mapped collection of the sub rules for the BankTransactionRule'
+ type: array
+ items:
+ $ref: '#/components/schemas/BTRules'
+ auto_convert:
+ description: 'Flags whether the rule converts the transaction automatically'
+ type: boolean
+ example: true
+ matches_on_all:
+ description: 'Flags whether all subrules are required for the match'
+ type: boolean
+ example: true
+ applies_to:
+ description: 'Flags whether the rule applies to a CREDIT or DEBIT'
+ type: string
+ example: CREDIT
+ client_id:
+ description: 'The client hashed id'
+ type: string
+ example: AS3df3A
+ vendor_id:
+ description: 'The vendor hashed id'
+ type: string
+ example: AS3df3A
+ category_id:
+ description: 'The category hashed id'
+ type: string
+ example: AS3df3A
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/client.yaml b/openapi/components/schemas/client.yaml
new file mode 100644
index 000000000000..f8df77644ee0
--- /dev/null
+++ b/openapi/components/schemas/client.yaml
@@ -0,0 +1,160 @@
+ Client:
+ properties:
+ id:
+ description: 'The unique identifier of the client'
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: 'The unique identifier of the user who created the client'
+ type: string
+ example: Ua6Rw4pVbS
+ company_id:
+ description: 'The unique identifier of the company the client belongs to'
+ type: string
+ example: Co7Vn3yLmW
+ contacts:
+ type: array
+ items:
+ $ref: '#/components/schemas/ClientContact'
+ name:
+ description: 'The name of the client company or organization'
+ type: string
+ example: "Jim's Housekeeping"
+ website:
+ description: 'The website URL of the client company or organization'
+ type: string
+ example: 'https://www.jims-housekeeping.com'
+ private_notes:
+ description: 'Notes that are only visible to the user who created the client'
+ type: string
+ example: 'Client prefers email communication over phone calls'
+ client_hash:
+ description: 'A unique hash value for the client'
+ type: string
+ example: asdfkjhk342hjhbfdvmnfb1
+ industry_id:
+ description: 'The unique identifier of the industry the client operates in'
+ type: number
+ example: '5'
+ size_id:
+ description: 'The unique identifier for the size category of the client company or organization'
+ type: number
+ example: '2'
+ address1:
+ description: "First line of the client's address"
+ type: string
+ example: '123 Main St'
+ address2:
+ description: "Second line of the client's address, if needed"
+ type: string
+ example: 'Apt 4B'
+ city:
+ description: 'The city the client is located in'
+ type: string
+ example: 'Beverly Hills'
+ state:
+ description: 'The state, province, or locality the client is located in'
+ type: string
+ example: 'California'
+ postal_code:
+ description: 'The postal code or ZIP code of the client'
+ type: string
+ example: '90210'
+ phone:
+ description: "The client's phone number"
+ type: string
+ example: '555-3434-3434'
+ country_id:
+ description: "The unique identifier of the client's country"
+ type: number
+ format: integer
+ example: '1'
+ custom_value1:
+ description: 'A custom field for storing additional information'
+ type: string
+ example: 'Preferred contact: Email'
+ custom_value2:
+ description: 'A custom field for storing additional information'
+ type: string
+ example: 'Account manager: John Doe'
+ custom_value3:
+ description: 'A custom field for storing additional information'
+ type: string
+ example: 'VIP client: Yes'
+ custom_value4:
+ description: 'A custom field for storing additional information'
+ type: string
+ example: 'Annual contract value: $50,000'
+ vat_number:
+ description: "The client's VAT (Value Added Tax) number, if applicable"
+ type: string
+ example: 'VAT123456'
+ id_number:
+ description: 'A unique identification number for the client, such as a tax ID or business registration number'
+ type: string
+ number:
+ description: 'A system-assigned unique number for the client, typically used for invoicing purposes'
+ type: string
+ example: 'CL-0001'
+ shipping_address1:
+ description: "First line of the client's shipping address"
+ type: string
+ example: '5 Wallaby Way'
+ shipping_address2:
+ description: "Second line of the client's shipping address, if needed"
+ type: string
+ example: 'Suite 5'
+ shipping_city:
+ description: "The city of the client's shipping address"
+ type: string
+ example: 'Perth'
+ shipping_state:
+ description: "The state, province, or locality of the client's shipping address"
+ type: string
+ example: 'Western Australia'
+ shipping_postal_code:
+ description: "The postal code or ZIP code of the client's shipping address"
+ type: string
+ example: '6110'
+ shipping_country_id:
+ description: "The unique identifier of the country for the client's shipping address"
+ type: number
+ format: integer
+ example: '4'
+ is_deleted:
+ description: 'A boolean value indicating whether the client has been deleted or not'
+ type: boolean
+ example: false
+ balance:
+ description: 'The outstanding balance the client owes'
+ type: number
+ format: float
+ example: '500.00'
+ paid_to_date:
+ description: 'The total amount the client has paid to date'
+ type: number
+ format: float
+ example: '2000.00'
+ credit_balance:
+ description: 'The available credit balance for the client to use on future purchases'
+ type: number
+ format: float
+ example: '100.00'
+ last_login:
+ description: "The timestamp of the client's last login"
+ type: number
+ format: integer
+ example: '1628686031'
+ created_at:
+ description: 'The timestamp when the client was created'
+ type: number
+ format: integer
+ example: '1617629031'
+ updated_at:
+ description: 'The timestamp when the client was last updated'
+ type: number
+ format: integer
+ example: '1628445631'
+ settings:
+ $ref: '#/components/schemas/CompanySettings'
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/client_contact.yaml b/openapi/components/schemas/client_contact.yaml
new file mode 100644
index 000000000000..aaf1c1bef6e3
--- /dev/null
+++ b/openapi/components/schemas/client_contact.yaml
@@ -0,0 +1,113 @@
+ ClientContact:
+ properties:
+ id:
+ description: 'The hashed if of the contact'
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: 'The hashed id of the user who created the contact'
+ type: string
+ example: Opnel5aKBz
+ company_id:
+ description: 'The hashed id of the company'
+ type: string
+ example: Opnel5aKBz
+ client_id:
+ description: 'The hashed id of the client'
+ type: string
+ example: Opnel5aKBz
+ first_name:
+ description: 'The first name of the contact'
+ type: string
+ example: John
+ last_name:
+ description: 'The last name of the contact'
+ type: string
+ example: Doe
+ phone:
+ description: 'The phone number of the contact'
+ type: string
+ example: 555-152-4524
+ custom_value1:
+ description: 'A Custom field value'
+ type: string
+ example: ''
+ custom_value2:
+ description: 'A Custom field value'
+ type: string
+ example: ''
+ custom_value3:
+ description: 'A Custom field value'
+ type: string
+ example: ''
+ custom_value4:
+ description: 'A Custom field value'
+ type: string
+ example: ''
+ email:
+ description: 'The email of the contact'
+ type: string
+ example: ''
+ accepted_terms_version:
+ description: 'The terms of service which the contact has accpeted'
+ type: string
+ example: 'A long set of ToS'
+ password:
+ description: 'The hashed password of the contact'
+ type: string
+ example: '*****'
+ confirmation-code:
+ description: 'The confirmation code used to authenticate the contacts email address'
+ type: string
+ example: 333-sdjkh34gbasd
+ token:
+ description: 'A uuid based token.'
+ type: string
+ example: 333-sdjkh34gbasd
+ is_primary:
+ description: 'Defines is this contact is the primary contact for the client'
+ type: boolean
+ example: true
+ confirmed:
+ description: 'Boolean value confirms the user has confirmed their account.'
+ type: boolean
+ example: true
+ is_locked:
+ description: 'Boolean value defines if the contact has been locked out.'
+ type: boolean
+ example: true
+ send_email:
+ description: 'Boolean value determines is this contact should receive emails'
+ type: boolean
+ example: true
+ failed_logins:
+ description: 'The number of failed logins the contact has had'
+ type: number
+ format: integer
+ example: '3'
+ email_verified_at:
+ description: 'The date which the contact confirmed their email'
+ type: number
+ format: integer
+ example: '134341234234'
+ last_login:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ created_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ deleted_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/client_gateway_token.yaml b/openapi/components/schemas/client_gateway_token.yaml
new file mode 100644
index 000000000000..b10587611278
--- /dev/null
+++ b/openapi/components/schemas/client_gateway_token.yaml
@@ -0,0 +1,31 @@
+ ClientGatewayToken:
+ properties:
+ id:
+ description: 'The hashed id of the client gateway token'
+ type: string
+ example: Opnel5aKBz
+ company_id:
+ description: 'The hashed id of the company'
+ type: string
+ example: '2'
+ client_id:
+ description: 'The hashed_id of the client'
+ type: string
+ example: '2'
+ token:
+ description: 'The payment token'
+ type: string
+ example: '2'
+ routing_number:
+ description: 'THe bank account routing number'
+ type: string
+ example: '2'
+ company_gateway_id:
+ description: 'The hashed id of the company gateway'
+ type: string
+ example: '2'
+ is_default:
+ description: 'Flag determining if the token is the default payment method'
+ type: boolean
+ example: 'true'
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/company.yaml b/openapi/components/schemas/company.yaml
new file mode 100644
index 000000000000..3dbd83639eb0
--- /dev/null
+++ b/openapi/components/schemas/company.yaml
@@ -0,0 +1,91 @@
+ Company:
+ properties:
+ id:
+ description: "The unique hashed identifier for the company"
+ type: string
+ example: WJxbojagwO
+ size_id:
+ description: "The unique identifier representing the company's size category"
+ type: string
+ example: '2'
+ industry_id:
+ description: "The unique identifier representing the company's industry category"
+ type: string
+ example: '5'
+ slack_webhook_url:
+ description: "The URL for the company's Slack webhook notifications"
+ type: string
+ example: 'https://hooks.slack.com/services/T00000000/B00000000/XXXXXXXXXXXXXXXXXXXXXXXX'
+ google_analytics_key:
+ description: "The company's Google Analytics tracking ID"
+ type: string
+ example: 'UA-123456789-1'
+ portal_mode:
+ description: "The mode determining how client-facing URLs are structured (e.g., subdomain, domain, or iframe)"
+ type: string
+ example: subdomain
+ subdomain:
+ description: "The subdomain prefix for the company's domain (e.g., 'acme' in acme.domain.com)"
+ type: string
+ example: acme
+ portal_domain:
+ description: "The fully qualified domain used for client-facing URLs"
+ type: string
+ example: 'https://subdomain.invoicing.co'
+ enabled_tax_rates:
+ description: "The number of tax rates used per entity"
+ type: integer
+ example: '2'
+ fill_products:
+ description: "A flag determining whether to auto-fill product descriptions based on the product key"
+ type: boolean
+ example: true
+ convert_products:
+ description: "A flag determining whether to convert products between different types or units"
+ type: boolean
+ example: true
+ update_products:
+ description: "A flag determining whether to update product descriptions when the description changes"
+ type: boolean
+ example: true
+ show_product_details:
+ description: "A flag determining whether to display product details in the user interface"
+ type: boolean
+ example: true
+ custom_fields:
+ description: "A mapping of custom fields for various objects within the company"
+ type: object
+ enable_product_cost:
+ description: "A flag determining whether to show or hide the product cost field in the user interface"
+ type: boolean
+ example: true
+ enable_product_quantity:
+ description: "A flag determining whether to show or hide the product quantity field in the user interface"
+ type: boolean
+ example: true
+ default_quantity:
+ description: "A flag determining whether to use a default quantity for products"
+ type: boolean
+ example: true
+ custom_surcharge_taxes1:
+ description: "A flag determining whether to apply taxes on custom surcharge amounts for the first custom surcharge field"
+ type: boolean
+ example: true
+ custom_surcharge_taxes2:
+ description: "A flag determining whether to apply taxes on custom surcharge amounts for the second custom surcharge field"
+ type: boolean
+ example: true
+ custom_surcharge_taxes3:
+ description: "A flag determining whether to apply taxes on custom surcharge amounts for the third custom surcharge field"
+ type: boolean
+ example: true
+ custom_surcharge_taxes4:
+ description: "A flag determining whether to apply taxes on custom surcharge amounts for the fourth custom"
+ logo:
+ description: "The company logo file in binary format"
+ type: string
+ format: binary
+ example: logo.png
+ settings:
+ $ref: '#/components/schemas/CompanySettings'
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/company_gateway.yaml b/openapi/components/schemas/company_gateway.yaml
new file mode 100644
index 000000000000..35196f5f1d25
--- /dev/null
+++ b/openapi/components/schemas/company_gateway.yaml
@@ -0,0 +1,42 @@
+ CompanyGateway:
+ properties:
+ id:
+ description: 'The hashed id of the company gateway'
+ type: string
+ example: Opnel5aKBz
+ company_id:
+ description: 'The company hashed id'
+ type: string
+ example: '2'
+ gateway_key:
+ description: 'The gateway key (hash)'
+ type: string
+ example: '2'
+ accepted_credit_cards:
+ description: 'Bitmask representation of cards'
+ type: integer
+ example: '32'
+ require_billing_address:
+ description: 'Determines if the the billing address is required prior to payment.'
+ type: boolean
+ example: true
+ require_shipping_address:
+ description: 'Determines if the the billing address is required prior to payment.'
+ type: boolean
+ example: true
+ config:
+ description: 'The configuration map for the gateway'
+ type: string
+ example: dfadsfdsafsafd
+ update_details:
+ description: 'Determines if the client details should be updated.'
+ type: boolean
+ example: true
+ fees_and_limits:
+ description: 'A mapped collection of the fees and limits for the configured gateway'
+ type: array
+ items:
+ $ref: '#/components/schemas/FeesAndLimits'
+ type: object
+
+
\ No newline at end of file
diff --git a/openapi/components/schemas/company_ledger.yaml b/openapi/components/schemas/company_ledger.yaml
new file mode 100644
index 000000000000..8527c105cfbe
--- /dev/null
+++ b/openapi/components/schemas/company_ledger.yaml
@@ -0,0 +1,31 @@
+ CompanyLedger:
+ properties:
+ entity_id:
+ description: 'This field will reference one of the following entity hashed ID payment_id, invoice_id or credit_id'
+ type: string
+ example: AS3df3A
+ notes:
+ description: 'The notes which reference this entry of the ledger'
+ type: string
+ example: 'Credit note for invoice #3212'
+ balance:
+ description: 'The client balance'
+ type: number
+ format: float
+ example: '10.00'
+ adjustment:
+ description: 'The amount the client balance is adjusted by'
+ type: number
+ format: float
+ example: '10.00'
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ created_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/company_settings.yaml b/openapi/components/schemas/company_settings.yaml
new file mode 100644
index 000000000000..04902e8a4613
--- /dev/null
+++ b/openapi/components/schemas/company_settings.yaml
@@ -0,0 +1,592 @@
+ CompanySettings:
+ properties:
+ timezone_id:
+ description: 'The timezone id'
+ type: string
+ example: '15'
+ date_format_id:
+ description: 'The date format id'
+ type: string
+ example: '15'
+ military_time:
+ description: 'Toggles 12/24 hour time'
+ type: boolean
+ example: true
+ language_id:
+ description: 'The language id'
+ type: string
+ example: '1'
+ show_currency_code:
+ description: 'Toggles whether the currency symbol or code is shown'
+ type: boolean
+ example: true
+ currency_id:
+ description: 'The default currency id'
+ type: string
+ example: true
+ payment_terms:
+ description: '-1 sets no payment term, 0 sets payment due immediately, positive integers indicates payment terms in days'
+ type: integer
+ example: '1'
+ company_gateway_ids:
+ description: 'A commad separate list of available gateways'
+ type: string
+ example: '1,2,3,4'
+ custom_value1:
+ description: 'A Custom Label'
+ type: string
+ example: 'Custom Label'
+ custom_value2:
+ description: 'A Custom Label'
+ type: string
+ example: 'Custom Label'
+ custom_value3:
+ description: 'A Custom Label'
+ type: string
+ example: 'Custom Label'
+ custom_value4:
+ description: 'A Custom Label'
+ type: string
+ example: 'Custom Label'
+ default_task_rate:
+ description: 'The default task rate'
+ type: number
+ format: float
+ example: '10.00'
+ send_reminders:
+ description: 'Toggles whether reminders are sent'
+ type: boolean
+ example: true
+ enable_client_portal_tasks:
+ description: 'Show/hide the tasks panel in the client portal'
+ type: boolean
+ example: true
+ email_style:
+ description: 'options include plain,light,dark,custom'
+ type: string
+ example: light
+ reply_to_email:
+ description: 'The reply to email address'
+ type: string
+ example: email@gmail.com
+ bcc_email:
+ description: 'A comma separate list of BCC emails'
+ type: string
+ example: 'email@gmail.com, contact@gmail.com'
+ pdf_email_attachment:
+ description: 'Toggles whether to attach PDF as attachment'
+ type: boolean
+ example: true
+ ubl_email_attachment:
+ description: 'Toggles whether to attach UBL as attachment'
+ type: boolean
+ example: true
+ email_style_custom:
+ description: 'The custom template'
+ type: string
+ example: ''
+ counter_number_applied:
+ description: 'enum when the invoice number counter is set, ie when_saved, when_sent, when_paid'
+ type: string
+ example: when_sent
+ quote_number_applied:
+ description: 'enum when the quote number counter is set, ie when_saved, when_sent'
+ type: string
+ example: when_sent
+ custom_message_dashboard:
+ description: 'A custom message which is displayed on the dashboard'
+ type: string
+ example: 'Please pay invoices immediately'
+ custom_message_unpaid_invoice:
+ description: 'A custom message which is displayed in the client portal when a client is viewing a unpaid invoice.'
+ type: string
+ example: 'Please pay invoices immediately'
+ custom_message_paid_invoice:
+ description: 'A custom message which is displayed in the client portal when a client is viewing a paid invoice.'
+ type: string
+ example: 'Thanks for paying this invoice!'
+ custom_message_unapproved_quote:
+ description: 'A custom message which is displayed in the client portal when a client is viewing a unapproved quote.'
+ type: string
+ example: 'Please approve quote'
+ lock_invoices:
+ description: 'Toggles whether invoices are locked once sent and cannot be modified further'
+ type: boolean
+ example: true
+ auto_archive_invoice:
+ description: 'Toggles whether a invoice is archived immediately following payment'
+ type: boolean
+ example: true
+ auto_archive_quote:
+ description: 'Toggles whether a quote is archived after being converted to a invoice'
+ type: boolean
+ example: true
+ auto_convert_quote:
+ description: 'Toggles whether a quote is converted to a invoice when approved'
+ type: boolean
+ example: true
+ inclusive_taxes:
+ description: 'Boolean flag determining whether inclusive or exclusive taxes are used'
+ type: boolean
+ example: true
+ translations:
+ description: 'JSON payload of customized translations'
+ type: object
+ example: ''
+ task_number_pattern:
+ description: 'Allows customisation of the task number pattern'
+ type: string
+ example: '{$year}-{$counter}'
+ task_number_counter:
+ description: 'The incrementing counter for tasks'
+ type: integer
+ example: '1'
+ reminder_send_time:
+ description: 'Time from UTC +0 when the email will be sent to the client'
+ type: integer
+ example: '32400'
+ expense_number_pattern:
+ description: 'Allows customisation of the expense number pattern'
+ type: string
+ example: '{$year}-{$counter}'
+ expense_number_counter:
+ description: 'The incrementing counter for expenses'
+ type: integer
+ example: '1'
+ vendor_number_pattern:
+ description: 'Allows customisation of the vendor number pattern'
+ type: string
+ example: '{$year}-{$counter}'
+ vendor_number_counter:
+ description: 'The incrementing counter for vendors'
+ type: integer
+ example: '1'
+ ticket_number_pattern:
+ description: 'Allows customisation of the ticket number pattern'
+ type: string
+ example: '{$year}-{$counter}'
+ ticket_number_counter:
+ description: 'The incrementing counter for tickets'
+ type: integer
+ example: '1'
+ payment_number_pattern:
+ description: 'Allows customisation of the payment number pattern'
+ type: string
+ example: '{$year}-{$counter}'
+ payment_number_counter:
+ description: 'The incrementing counter for payments'
+ type: integer
+ example: '1'
+ invoice_number_pattern:
+ description: 'Allows customisation of the invoice number pattern'
+ type: string
+ example: '{$year}-{$counter}'
+ invoice_number_counter:
+ description: 'The incrementing counter for invoices'
+ type: integer
+ example: '1'
+ quote_number_pattern:
+ description: 'Allows customisation of the quote number pattern'
+ type: string
+ example: '{$year}-{$counter}'
+ quote_number_counter:
+ description: 'The incrementing counter for quotes'
+ type: integer
+ example: '1'
+ client_number_pattern:
+ description: 'Allows customisation of the client number pattern'
+ type: string
+ example: '{$year}-{$counter}'
+ client_number_counter:
+ description: 'The incrementing counter for clients'
+ type: integer
+ example: '1'
+ credit_number_pattern:
+ description: 'Allows customisation of the credit number pattern'
+ type: string
+ example: '{$year}-{$counter}'
+ credit_number_counter:
+ description: 'The incrementing counter for credits'
+ type: integer
+ example: '1'
+ recurring_invoice_number_prefix:
+ description: 'This string is prepended to the recurring invoice number'
+ type: string
+ example: R
+ reset_counter_frequency_id:
+ description: 'CONSTANT which is used to apply the frequency which the counters are reset'
+ type: integer
+ example: '1'
+ reset_counter_date:
+ description: 'The explicit date which is used to reset counters'
+ type: string
+ example: '2019-01-01'
+ counter_padding:
+ description: 'Pads the counter with leading zeros'
+ type: integer
+ example: '1'
+ shared_invoice_quote_counter:
+ description: 'Flags whether to share the counter for invoices and quotes'
+ type: boolean
+ example: true
+ update_products:
+ description: 'Determines if client fields are updated from third party APIs'
+ type: boolean
+ example: true
+ convert_products:
+ description: ''
+ type: boolean
+ example: true
+ fill_products:
+ description: 'Automatically fill products based on product_key'
+ type: boolean
+ example: true
+ invoice_terms:
+ description: 'The default invoice terms'
+ type: string
+ example: 'Invoice Terms are...'
+ quote_terms:
+ description: 'The default quote terms'
+ type: string
+ example: 'Quote Terms are...'
+ invoice_taxes:
+ description: 'Taxes can be applied to the invoice'
+ type: number
+ example: '1'
+ invoice_design_id:
+ description: 'The default design id (invoice, quote etc)'
+ type: string
+ example: '1'
+ quote_design_id:
+ description: 'The default design id (invoice, quote etc)'
+ type: string
+ example: '1'
+ invoice_footer:
+ description: 'The default invoice footer'
+ type: string
+ example: '1'
+ invoice_labels:
+ description: 'JSON string of invoice labels'
+ type: string
+ example: '1'
+ tax_rate1:
+ description: 'The tax rate (float)'
+ type: number
+ example: '10'
+ tax_name1:
+ description: 'The tax name'
+ type: string
+ example: GST
+ tax_rate2:
+ description: 'The tax rate (float)'
+ type: number
+ example: '10'
+ tax_name2:
+ description: 'The tax name'
+ type: string
+ example: GST
+ tax_rate3:
+ description: 'The tax rate (float)'
+ type: number
+ example: '10'
+ tax_name3:
+ description: 'The tax name'
+ type: string
+ example: GST
+ payment_type_id:
+ description: 'The default payment type id'
+ type: string
+ example: '1'
+ custom_fields:
+ description: 'JSON string of custom fields'
+ type: string
+ example: '{}'
+ email_footer:
+ description: 'The default email footer'
+ type: string
+ example: 'A default email footer'
+ email_sending_method:
+ description: 'The email driver to use to send email, options include default, gmail'
+ type: string
+ example: default
+ gmail_sending_user_id:
+ description: 'The hashed_id of the user account to send email from'
+ type: string
+ example: F76sd34D
+ email_subject_invoice:
+ description: ''
+ type: string
+ example: 'Your Invoice Subject'
+ email_subject_quote:
+ description: ''
+ type: string
+ example: 'Your Quote Subject'
+ email_subject_payment:
+ description: ''
+ type: string
+ example: 'Your Payment Subject'
+ email_template_invoice:
+ description: 'The full template for invoice emails'
+ type: string
+ example: ''
+ email_template_quote:
+ description: 'The full template for quote emails'
+ type: string
+ example: ''
+ email_template_payment:
+ description: 'The full template for payment emails'
+ type: string
+ example: ''
+ email_subject_reminder1:
+ description: 'Email subject for Reminder'
+ type: string
+ example: ''
+ email_subject_reminder2:
+ description: 'Email subject for Reminder'
+ type: string
+ example: ''
+ email_subject_reminder3:
+ description: 'Email subject for Reminder'
+ type: string
+ example: ''
+ email_subject_reminder_endless:
+ description: 'Email subject for endless reminders'
+ type: string
+ example: ''
+ email_template_reminder1:
+ description: 'The full template for Reminder 1'
+ type: string
+ example: ''
+ email_template_reminder2:
+ description: 'The full template for Reminder 2'
+ type: string
+ example: ''
+ email_template_reminder3:
+ description: 'The full template for Reminder 3'
+ type: string
+ example: ''
+ email_template_reminder_endless:
+ description: 'The full template for enless reminders'
+ type: string
+ example: ''
+ enable_portal_password:
+ description: 'Toggles whether a password is required to log into the client portal'
+ type: boolean
+ example: true
+ show_accept_invoice_terms:
+ description: 'Toggles whether the terms dialogue is shown to the client'
+ type: boolean
+ example: true
+ show_accept_quote_terms:
+ description: 'Toggles whether the terms dialogue is shown to the client'
+ type: boolean
+ example: true
+ require_invoice_signature:
+ description: 'Toggles whether a invoice signature is required'
+ type: boolean
+ example: true
+ require_quote_signature:
+ description: 'Toggles whether a quote signature is required'
+ type: boolean
+ example: true
+ name:
+ description: 'The company name'
+ type: string
+ example: 'Acme Co'
+ company_logo:
+ description: 'The company logo file'
+ type: object
+ example: logo.png
+ website:
+ description: 'The company website URL'
+ type: string
+ example: www.acme.com
+ address1:
+ description: 'The company address line 1'
+ type: string
+ example: 'Suite 888'
+ address2:
+ description: 'The company address line 2'
+ type: string
+ example: '5 Jimbo Way'
+ city:
+ description: 'The company city'
+ type: string
+ example: Sydney
+ state:
+ description: 'The company state'
+ type: string
+ example: Florisa
+ postal_code:
+ description: 'The company zip/postal code'
+ type: string
+ example: '90210'
+ phone:
+ description: 'The company phone'
+ type: string
+ example: 555-213-3948
+ email:
+ description: 'The company email'
+ type: string
+ example: joe@acme.co
+ country_id:
+ description: 'The country ID'
+ type: string
+ example: '1'
+ vat_number:
+ description: 'The company VAT/TAX ID number'
+ type: string
+ example: '32 120 377 720'
+ page_size:
+ description: 'The default page size'
+ type: string
+ example: A4
+ font_size:
+ description: 'The font size'
+ type: number
+ example: '9'
+ primary_font:
+ description: 'The primary font'
+ type: string
+ example: roboto
+ secondary_font:
+ description: 'The secondary font'
+ type: string
+ example: roboto
+ hide_paid_to_date:
+ description: 'Flags whether to hide the paid to date field'
+ type: boolean
+ example: false
+ embed_documents:
+ description: 'Toggled whether to embed documents in the PDF'
+ type: boolean
+ example: false
+ all_pages_header:
+ description: 'The header for the PDF'
+ type: boolean
+ example: false
+ all_pages_footer:
+ description: 'The footer for the PDF'
+ type: boolean
+ example: false
+ document_email_attachment:
+ description: 'Toggles whether to attach documents in the email'
+ type: boolean
+ example: false
+ enable_client_portal_password:
+ description: 'Toggles password protection of the client portal'
+ type: boolean
+ example: false
+ enable_email_markup:
+ description: 'Toggles the use of markdown in emails'
+ type: boolean
+ example: false
+ enable_client_portal_dashboard:
+ description: 'Toggles whether the client dashboard is shown in the client portal'
+ type: boolean
+ example: false
+ enable_client_portal:
+ description: 'Toggles whether the entire client portal is displayed to the client, or only the context'
+ type: boolean
+ example: false
+ email_template_statement:
+ description: 'The body of the email for statements'
+ type: string
+ example: 'template matter'
+ email_subject_statement:
+ description: 'The subject of the email for statements'
+ type: string
+ example: 'subject matter'
+ signature_on_pdf:
+ description: 'Toggles whether the signature (if available) is displayed on the PDF'
+ type: boolean
+ example: false
+ quote_footer:
+ description: 'The default quote footer'
+ type: string
+ example: 'the quote footer'
+ email_subject_custom1:
+ description: 'Custom reminder template subject'
+ type: string
+ example: 'Custom Subject 1'
+ email_subject_custom2:
+ description: 'Custom reminder template subject'
+ type: string
+ example: 'Custom Subject 2'
+ email_subject_custom3:
+ description: 'Custom reminder template subject'
+ type: string
+ example: 'Custom Subject 3'
+ email_template_custom1:
+ description: 'Custom reminder template body'
+ type: string
+ example: ''
+ email_template_custom2:
+ description: 'Custom reminder template body'
+ type: string
+ example: ''
+ email_template_custom3:
+ description: 'Custom reminder template body'
+ type: string
+ example: ''
+ enable_reminder1:
+ description: 'Toggles whether this reminder is enabled'
+ type: boolean
+ example: false
+ enable_reminder2:
+ description: 'Toggles whether this reminder is enabled'
+ type: boolean
+ example: false
+ enable_reminder3:
+ description: 'Toggles whether this reminder is enabled'
+ type: boolean
+ example: false
+ num_days_reminder1:
+ description: 'The Reminder interval'
+ type: number
+ example: '9'
+ num_days_reminder2:
+ description: 'The Reminder interval'
+ type: number
+ example: '9'
+ num_days_reminder3:
+ description: 'The Reminder interval'
+ type: number
+ example: '9'
+ schedule_reminder1:
+ description: '(enum: after_invoice_date, before_due_date, after_due_date)'
+ type: string
+ example: after_invoice_date
+ schedule_reminder2:
+ description: '(enum: after_invoice_date, before_due_date, after_due_date)'
+ type: string
+ example: after_invoice_date
+ schedule_reminder3:
+ description: '(enum: after_invoice_date, before_due_date, after_due_date)'
+ type: string
+ example: after_invoice_date
+ late_fee_amount1:
+ description: 'The late fee amount for reminder 1'
+ type: number
+ example: 10
+ late_fee_amount2:
+ description: 'The late fee amount for reminder 2'
+ type: number
+ example: 20
+ late_fee_amount3:
+ description: 'The late fee amount for reminder 2'
+ type: number
+ example: 100
+ endless_reminder_frequency_id:
+ description: 'The frequency id of the endless reminder'
+ type: string
+ example: '1'
+ client_online_payment_notification:
+ description: 'Determines if a client should receive the notification for a online payment'
+ type: boolean
+ example: false
+ client_manual_payment_notification:
+ description: 'Determines if a client should receive the notification for a manually entered payment'
+ type: boolean
+ example: false
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/company_token.yaml b/openapi/components/schemas/company_token.yaml
new file mode 100644
index 000000000000..5602f33169a8
--- /dev/null
+++ b/openapi/components/schemas/company_token.yaml
@@ -0,0 +1,15 @@
+ CompanyToken:
+ properties:
+ name:
+ description: 'The token name'
+ type: string
+ example: 'Token Name'
+ token:
+ description: 'The token value'
+ type: string
+ example: AS3df3jUUH765fhfd9KJuidj3JShjA
+ is_system:
+ description: 'Determines whether the token is created by the system rather than a user'
+ type: boolean
+ example: 'true'
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/company_user.yaml b/openapi/components/schemas/company_user.yaml
new file mode 100644
index 000000000000..5d67b726ad55
--- /dev/null
+++ b/openapi/components/schemas/company_user.yaml
@@ -0,0 +1,43 @@
+ CompanyUser:
+ properties:
+ permissions:
+ description: 'The company user permissions'
+ type: string
+ example: '[create_invoice]'
+ settings:
+ description: 'Settings that are used for the frontend applications to store user preferences / metadata'
+ type: object
+ example: 'json object'
+ react_settings:
+ description: 'Dedicated settings object for the react web application'
+ type: object'
+ example: 'json object'
+ is_owner:
+ description: 'Determines whether the user owns this company'
+ type: boolean
+ example: true
+ is_admin:
+ description: 'Determines whether the user is the admin of this company'
+ type: boolean
+ example: true
+ is_locked:
+ description: 'Determines whether the users access to this company has been locked'
+ type: boolean
+ example: true
+ updated_at:
+ description: 'The last time the record was modified, format Unix Timestamp'
+ type: integer
+ example: '1231232312321'
+ deleted_at:
+ description: 'Timestamp when the user was archived, format Unix Timestamp'
+ type: integer
+ example: '12312312321'
+ account:
+ $ref: '#/components/schemas/Account'
+ company:
+ $ref: '#/components/schemas/Company'
+ user:
+ $ref: '#/components/schemas/User'
+ token:
+ $ref: '#/components/schemas/CompanyToken'
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/credit.yaml b/openapi/components/schemas/credit.yaml
new file mode 100644
index 000000000000..bc06f457ea1d
--- /dev/null
+++ b/openapi/components/schemas/credit.yaml
@@ -0,0 +1,223 @@
+ Credit:
+ properties:
+ id:
+ description: "The unique hashed ID of the credit"
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: "The unique hashed ID of the user associated with the credit"
+ type: string
+ example: 1a2b3c4d5e
+ assigned_user_id:
+ description: "The unique hashed ID of the assigned user responsible for the credit"
+ type: string
+ example: 6f7g8h9i0j
+ company_id:
+ description: "The unique hashed ID of the company associated with the credit"
+ type: string
+ example: k1l2m3n4o5
+ client_id:
+ description: "The unique hashed ID of the client associated with the credit"
+ type: string
+ example: p1q2r3s4t5
+ status_id:
+ description: "The ID representing the current status of the credit"
+ type: string
+ example: 3
+ invoice_id:
+ description: "The unique hashed ID of the linked invoice to which the credit is applied"
+ type: string
+ example: u1v2w3x4y5
+ number:
+ description: "The unique alphanumeric credit number per company"
+ type: string
+ example: QUOTE_101
+ po_number:
+ description: "The purchase order number referred to by the credit"
+ type: string
+ example: PO_12345
+ terms:
+ description: "The terms associated with the credit"
+ type: string
+ example: "Net 30"
+ public_notes:
+ description: "Public notes for the credit"
+ type: string
+ example: "Thank you for your business."
+ private_notes:
+ description: "Private notes for internal use, not visible to the client"
+ type: string
+ example: "Client is requesting a discount."
+ footer:
+ description: "The footer text for the credit"
+ type: string
+ example: "Footer text goes here."
+ custom_value1:
+ description: "Custom value 1 for additional credit information"
+ type: string
+ example: "Custom data 1"
+ custom_value2:
+ description: "Custom value 2 for additional credit information"
+ type: string
+ example: "Custom data 2"
+ custom_value3:
+ description: "Custom value 3 for additional credit information"
+ type: string
+ example: "Custom data 3"
+ custom_value4:
+ description: "Custom value 4 for additional credit information"
+ type: string
+ example: "Custom data 4"
+ tax_name1:
+ description: "The name of the first tax applied to the credit"
+ type: string
+ example: "VAT"
+ tax_name2:
+ description: "The name of the second tax applied to the credit"
+ type: string
+ example: "GST"
+ tax_rate1:
+ description: "The rate of the first tax applied to the credit"
+ type: number
+ format: float
+ example: 10.00
+ tax_rate2:
+ description: "The rate of the second tax applied to the credit"
+ type: number
+ format: float
+ example: 5.00
+ tax_name3:
+ description: "The name of the third tax applied to the credit"
+ type: string
+ example: "PST"
+ tax_rate3:
+ description: "The rate of the third tax applied to the credit"
+ type: number
+ format: float
+ example: 8.00
+ total_taxes:
+ description: "The total amount of taxes for the credit"
+ type: number
+ format: float
+ example: 23.00
+ line_items:
+ type: array
+ description: 'An array of objects which define the line items of the credit'
+ items:
+ $ref: '#/components/schemas/InvoiceItem'
+ amount:
+ description: "The total amount of the credit"
+ type: number
+ format: float
+ example: 100.00
+ balance:
+ description: "The outstanding balance of the credit"
+ type: number
+ format: float
+ example: 50.00
+ paid_to_date:
+ description: "The total amount paid to date for the credit"
+ type: number
+ format: float
+ example: 50.00
+ discount:
+ description: "The discount applied to the credit"
+ type: number
+ format: float
+ example: 10.00
+ partial:
+ description: "The partial amount applied to the credit"
+ type: number
+ format: float
+ example: 20.00
+ is_amount_discount:
+ description: "Indicates whether the discount applied is a fixed amount or a percentage"
+ type: boolean
+ example: true
+ is_deleted:
+ description: "Indicates whether the credit has been deleted"
+ type: boolean
+ example: false
+ uses_inclusive_taxes:
+ description: "Indicates whether the tax rates applied to the credit are inclusive or exclusive"
+ type: boolean
+ example: true
+ date:
+ description: "The date the credit was issued"
+ type: string
+ format: date
+ example: "1994-07-30"
+ last_sent_date:
+ description: "The date the credit was last sent out"
+ type: string
+ format: date
+ example: "1994-07-30"
+ next_send_date:
+ description: "The next scheduled date for sending a credit reminder"
+ type: string
+ format: date
+ example: "1994-07-30"
+ partial_due_date:
+ description: "The due date for the partial amount of the credit"
+ type: string
+ format: date
+ example: "1994-07-30"
+ due_date:
+ description: "The due date for the total amount of the credit"
+ type: string
+ format: date
+ example: "1994-07-30"
+ settings:
+ $ref: "#/components/schemas/CompanySettings"
+ last_viewed:
+ description: "The timestamp of the last time the credit was viewed"
+ type: number
+ format: integer
+ example: 1434342123
+ updated_at:
+ description: "The timestamp of the last time the credit was updated"
+ type: number
+ format: integer
+ example: 1434342123
+ archived_at:
+ description: "The timestamp of the last time the credit was archived"
+ type: number
+ format: integer
+ example: 1434342123
+ custom_surcharge1:
+ description: "First custom surcharge amount"
+ type: number
+ format: float
+ example: 10.00
+ custom_surcharge2:
+ description: 'Second Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge3:
+ description: 'Third Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge4:
+ description: 'Fourth Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge_tax1:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ custom_surcharge_tax2:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ custom_surcharge_tax3:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ custom_surcharge_tax4:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/design.yaml b/openapi/components/schemas/design.yaml
new file mode 100644
index 000000000000..b5ca557d7c70
--- /dev/null
+++ b/openapi/components/schemas/design.yaml
@@ -0,0 +1,42 @@
+ Design:
+ properties:
+ id:
+ description: 'The design hashed id'
+ type: string
+ example: AS3df3A
+ name:
+ description: 'The design name'
+ type: string
+ example: Beauty
+ design:
+ description: 'The design HTML'
+ type: string
+ example: ''
+ is_custom:
+ description: 'Flag to determine if the design is a custom user design'
+ type: boolean
+ example: true
+ is_active:
+ description: 'Flag to determine if the design is available for use'
+ type: boolean
+ example: true
+ is_deleted:
+ description: 'Flag to determine if the design is deleted'
+ type: boolean
+ example: true
+ created_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ deleted_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/document.yaml b/openapi/components/schemas/document.yaml
new file mode 100644
index 000000000000..96d8029e9b5b
--- /dev/null
+++ b/openapi/components/schemas/document.yaml
@@ -0,0 +1,70 @@
+ Document:
+ properties:
+ id:
+ description: 'The document hashed id'
+ type: string
+ example: AS3df3A
+ user_id:
+ description: 'The user hashed id'
+ type: string
+ example: ''
+ assigned_user_id:
+ description: 'The assigned user hashed id'
+ type: string
+ example: ''
+ project_id:
+ description: 'The project associated with this document'
+ type: string
+ example: ''
+ vendor_id:
+ description: 'The vendor associated with this documents'
+ type: string
+ example: ''
+ name:
+ description: 'The document name'
+ type: string
+ example: Beauty
+ url:
+ description: 'The document url'
+ type: string
+ example: Beauty
+ preview:
+ description: 'The document preview url'
+ type: string
+ example: Beauty
+ type:
+ description: 'The document type'
+ type: string
+ example: Beauty
+ disk:
+ description: 'The document disk'
+ type: string
+ example: Beauty
+ hash:
+ description: 'The document hashed'
+ type: string
+ example: Beauty
+ is_deleted:
+ description: 'Flag to determine if the document is deleted'
+ type: boolean
+ example: true
+ is_default:
+ description: 'Flag to determine if the document is a default doc'
+ type: boolean
+ example: true
+ created_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ deleted_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/error.yaml b/openapi/components/schemas/error.yaml
new file mode 100644
index 000000000000..e404d014fce9
--- /dev/null
+++ b/openapi/components/schemas/error.yaml
@@ -0,0 +1,11 @@
+ Error:
+ properties:
+ message:
+ description: 'Something terrible went wrong'
+ type: string
+ example: 'Unexpected error'
+ code:
+ description: 'The HTTP error code, ie 5xx 4xx'
+ type: integer
+ example: '500'
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/expense.yaml b/openapi/components/schemas/expense.yaml
new file mode 100644
index 000000000000..5801a73287b1
--- /dev/null
+++ b/openapi/components/schemas/expense.yaml
@@ -0,0 +1,155 @@
+ Expense:
+ properties:
+ id:
+ description: 'The expense hashed id'
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: 'The user hashed id'
+ type: string
+ example: ''
+ assigned_user_id:
+ description: 'The assigned user hashed id'
+ type: string
+ example: ''
+ company_id:
+ description: 'The company hashed id'
+ type: string
+ example: ''
+ client_id:
+ description: 'The client hashed id'
+ type: string
+ example: ''
+ invoice_id:
+ description: 'The related invoice hashed id'
+ type: string
+ example: ''
+ bank_id:
+ description: 'The bank id related to this expense'
+ type: string
+ example: ''
+ invoice_currency_id:
+ description: 'The currency id of the related invoice'
+ type: string
+ example: ''
+ expense_currency_id:
+ description: 'The currency id of the expense'
+ type: string
+ example: ''
+ invoice_category_id:
+ description: 'The invoice category id'
+ type: string
+ example: ''
+ payment_type_id:
+ description: 'The payment type id'
+ type: string
+ example: ''
+ recurring_expense_id:
+ description: 'The related recurring expense this expense was created from'
+ type: string
+ example: ''
+ private_notes:
+ description: 'The private notes of the expense'
+ type: string
+ example: ''
+ public_notes:
+ description: 'The public notes of the expense'
+ type: string
+ example: ''
+ transaction_reference:
+ description: 'The transaction references of the expense'
+ type: string
+ example: ''
+ transcation_id:
+ description: 'The transaction id of the expense'
+ type: string
+ example: ''
+ custom_value1:
+ description: 'A custom value'
+ type: string
+ example: ''
+ custom_value2:
+ description: 'A custom value'
+ type: string
+ example: ''
+ custom_value3:
+ description: 'A custom value'
+ type: string
+ example: ''
+ custom_value4:
+ description: 'A custom value'
+ type: string
+ example: ''
+ tax_name1:
+ description: 'Tax name'
+ type: string
+ example: ''
+ tax_name2:
+ description: 'Tax name'
+ type: string
+ example: ''
+ tax_rate1:
+ description: 'Tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ tax_rate2:
+ description: 'Tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ tax_name3:
+ description: 'Tax name'
+ type: string
+ example: ''
+ tax_rate3:
+ description: 'Tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ amount:
+ description: 'The total expense amont'
+ type: number
+ format: float
+ example: '10.00'
+ foreign_amount:
+ description: 'The total foreign amount of the expense'
+ type: number
+ format: float
+ example: '10.00'
+ exchange_rate:
+ description: 'The exchange rate at the time of the expense'
+ type: number
+ format: float
+ example: '0.80'
+ date:
+ description: 'The expense date formate Y-m-d'
+ type: string
+ example: '2022-12-01'
+ payment_date:
+ description: 'The date of payment for the expense, format Y-m-d'
+ type: string
+ example: ''
+ should_be_invoiced:
+ description: 'Flag whether the expense should be invoiced'
+ type: boolean
+ example: true
+ is_deleted:
+ description: 'Boolean determining whether the expense has been deleted'
+ type: boolean
+ example: true
+ invoice_documents:
+ description: 'Passing the expense documents over to the invoice'
+ type: boolean
+ example: true
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ archived_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/expense_category.yaml b/openapi/components/schemas/expense_category.yaml
new file mode 100644
index 000000000000..707d7d21ddc0
--- /dev/null
+++ b/openapi/components/schemas/expense_category.yaml
@@ -0,0 +1,27 @@
+ ExpenseCategory:
+ properties:
+ id:
+ description: 'The expense hashed id'
+ type: string
+ example: Opnel5aKBz
+ name:
+ description: 'The expense category name'
+ type: string
+ example: Accounting
+ user_id:
+ description: 'The user hashed id'
+ type: string
+ example: XS987sD
+ is_deleted:
+ description: 'Flag determining whether the expense category has been deleted'
+ type: boolean
+ example: true
+ updated_at:
+ description: 'The updated at timestamp'
+ type: integer
+ example: '2'
+ created_at:
+ description: 'The created at timestamp'
+ type: integer
+ example: '2'
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/fees_and_limits.yaml b/openapi/components/schemas/fees_and_limits.yaml
new file mode 100644
index 000000000000..25ab01450014
--- /dev/null
+++ b/openapi/components/schemas/fees_and_limits.yaml
@@ -0,0 +1,58 @@
+
+ FeesAndLimits:
+ properties:
+ min_limit:
+ description: 'The minimum amount accepted for this gateway'
+ type: string
+ example: '2'
+ max_limit:
+ description: 'The maximum amount accepted for this gateway'
+ type: string
+ example: '2'
+ fee_amount:
+ description: 'The gateway fee amount'
+ type: number
+ format: float
+ example: '2.0'
+ fee_percent:
+ description: 'The gateway fee percentage'
+ type: number
+ format: float
+ example: '2.0'
+ fee_tax_name1:
+ description: 'Fee tax name'
+ type: string
+ example: GST
+ fee_tax_name2:
+ description: 'Fee tax name'
+ type: string
+ example: VAT
+ fee_tax_name3:
+ description: 'Fee tax name'
+ type: string
+ example: 'CA Sales Tax'
+ fee_tax_rate1:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '10.0'
+ fee_tax_rate2:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '17.5'
+ fee_tax_rate3:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '25.0'
+ fee_cap:
+ description: 'If set the fee amount will be no higher than this amount'
+ type: number
+ format: float
+ example: '2.0'
+ adjust_fee_percent:
+ description: 'Adjusts the fee to match the exact gateway fee.'
+ type: boolean
+ example: true
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/fillable_invoice.yaml b/openapi/components/schemas/fillable_invoice.yaml
new file mode 100644
index 000000000000..d6593eefe1fe
--- /dev/null
+++ b/openapi/components/schemas/fillable_invoice.yaml
@@ -0,0 +1,123 @@
+ FillableInvoice:
+ properties:
+ assigned_user_id:
+ description: "The assigned user's hashed ID"
+ type: string
+ example: 'a1b2c3d4'
+ client_id:
+ description: "The client's hashed ID"
+ type: string
+ example: 'x1y2z3a4'
+ number:
+ description: "The unique alphanumeric invoice number for each invoice per company"
+ type: string
+ example: INV_101
+ po_number:
+ description: "The purchase order number associated with the invoice"
+ type: string
+ example: 'PO12345'
+ terms:
+ description: "The terms and conditions for the invoice"
+ type: string
+ example: 'Net 30'
+ public_notes:
+ description: "Public notes visible to the client on the invoice"
+ type: string
+ example: 'Thank you for your business.'
+ private_notes:
+ description: "Private notes for internal use only"
+ type: string
+ example: 'Client is a slow payer.'
+ footer:
+ description: "The footer text displayed on the invoice"
+ type: string
+ example: 'Authorized Signature'
+ custom_value1:
+ description: "First custom value for additional information"
+ type: string
+ example: 'Project ABC'
+ custom_value2:
+ description: "Second custom value for additional information"
+ type: string
+ example: 'Department XYZ'
+ custom_value3:
+ description: "Third custom value for additional information"
+ type: string
+ example: 'Location 123'
+ custom_value4:
+ description: "Fourth custom value for additional information"
+ type: string
+ example: 'Currency USD'
+ tax_name1:
+ description: "Name of the first tax applied to the invoice"
+ type: string
+ example: 'VAT'
+ tax_name2:
+ description: "Name of the second tax applied to the invoice"
+ type: string
+ example: 'GST'
+ tax_rate1:
+ description: "Rate of the first tax applied to the invoice"
+ type: number
+ example: 10.00
+ tax_rate2:
+ description: "Rate of the second tax applied to the invoice"
+ type: number
+ example: 5.00
+ tax_name3:
+ description: "Name of the third tax applied to the invoice"
+ type: string
+ example: 'PST'
+ tax_rate3:
+ description: "Rate of the third tax applied to the invoice"
+ type: number
+ example: 8.00
+ line_items:
+ description: "Array of line items included in the invoice"
+ type: object
+ example: "[{item1}, {item2}]"
+ discount:
+ description: "The discount applied to the invoice"
+ type: number
+ example: 10.00
+ partial:
+ description: "The partial amount applied to the invoice"
+ type: number
+ example: 20.00
+ is_amount_discount:
+ description: "Indicates whether the discount applied is a fixed amount or a percentage"
+ type: boolean
+ example: true
+ uses_inclusive_taxes:
+ description: "Indicates whether the tax rates applied to the invoice are inclusive or exclusive"
+ type: boolean
+ example: true
+ date:
+ description: "The date the invoice was issued"
+ type: string
+ example: '1994-07-30'
+ partial_due_date:
+ description: "The due date for the partial payment"
+ type: string
+ example: '1994-08-15'
+ due_date:
+ description: "The due date for the invoice"
+ type: string
+ example: '1994-08-30'
+ custom_surcharge1:
+ description: "First custom surcharge applied to the invoice"
+ type: number
+ example: 10.00
+ custom_surcharge2:
+ description: "Second custom surcharge applied to the invoice"
+ type: number
+ example: 15.00
+ custom_surcharge3:
+ description: "Third custom surcharge applied to the invoice"
+ type: number
+ example: 5.00
+ custom_surcharge4:
+ description: "Fourth custom surcharge applied to the invoice"
+ type: number
+ example: 20.00
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/invoice.yaml b/openapi/components/schemas/invoice.yaml
new file mode 100644
index 000000000000..6a09eb246788
--- /dev/null
+++ b/openapi/components/schemas/invoice.yaml
@@ -0,0 +1,220 @@
+ Invoice:
+ properties:
+ id:
+ description: 'The invoice hashed id'
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: 'The user hashed id'
+ type: string
+ example: Opnel5aKBz
+ assigned_user_id:
+ description: 'The assigned user hashed id'
+ type: string
+ example: Opnel5aKBz
+ company_id:
+ description: 'The company hashed id'
+ type: string
+ example: Opnel5aKBz
+ client_id:
+ description: 'The client hashed id'
+ type: string
+ example: Opnel5aKBz
+ status_id:
+ description: 'The invoice status variable'
+ type: string
+ example: '4'
+ number:
+ description: 'The invoice number - is a unique alpha numeric number per invoice per company'
+ type: string
+ example: INV_101
+ po_number:
+ description: 'The purchase order associated with this invoice'
+ type: string
+ example: PO-1234
+ terms:
+ description: 'The invoice terms'
+ type: string
+ example: 'These are invoice terms'
+ public_notes:
+ description: 'The public notes of the invoice'
+ type: string
+ example: 'These are some public notes'
+ private_notes:
+ description: 'The private notes of the invoice'
+ type: string
+ example: 'These are some private notes'
+ footer:
+ description: 'The invoice footer notes'
+ type: string
+ example: ''
+ custom_value1:
+ description: 'A custom field value'
+ type: string
+ example: '2022-10-01'
+ custom_value2:
+ description: 'A custom field value'
+ type: string
+ example: 'Something custom'
+ custom_value3:
+ description: 'A custom field value'
+ type: string
+ example: ''
+ custom_value4:
+ description: 'A custom field value'
+ type: string
+ example: ''
+ tax_name1:
+ description: 'The tax name'
+ type: string
+ example: ''
+ tax_name2:
+ description: 'The tax name'
+ type: string
+ example: ''
+ tax_rate1:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ tax_rate2:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ tax_name3:
+ description: 'The tax name'
+ type: string
+ example: ''
+ tax_rate3:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ total_taxes:
+ description: 'The total taxes for the invoice'
+ type: number
+ format: float
+ example: '10.00'
+ line_items:
+ type: array
+ description: 'An array of objects which define the line items of the invoice'
+ items:
+ $ref: '#/components/schemas/InvoiceItem'
+
+ amount:
+ description: 'The invoice amount'
+ type: number
+ format: float
+ example: '10.00'
+ balance:
+ description: 'The invoice balance'
+ type: number
+ format: float
+ example: '10.00'
+ paid_to_date:
+ description: 'The amount paid on the invoice to date'
+ type: number
+ format: float
+ example: '10.00'
+ discount:
+ description: 'The invoice discount, can be an amount or a percentage'
+ type: number
+ format: float
+ example: '10.00'
+ partial:
+ description: 'The deposit/partial amount'
+ type: number
+ format: float
+ example: '10.00'
+ is_amount_discount:
+ description: 'Flag determining if the discount is an amount or a percentage'
+ type: boolean
+ example: true
+ is_deleted:
+ description: 'Defines if the invoice has been deleted'
+ type: boolean
+ example: true
+ uses_inclusive_taxes:
+ description: 'Defines the type of taxes used as either inclusive or exclusive'
+ type: boolean
+ example: true
+ date:
+ description: 'The Invoice Date'
+ type: string
+ format: date
+ example: '1994-07-30'
+ last_sent_date:
+ description: 'The last date the invoice was sent out'
+ type: string
+ format: date
+ example: '1994-07-30'
+ next_send_date:
+ description: 'The Next date for a reminder to be sent'
+ type: string
+ format: date
+ example: '1994-07-30'
+ partial_due_date:
+ description: 'The due date for the deposit/partial amount'
+ type: string
+ format: date
+ example: '1994-07-30'
+ due_date:
+ description: 'The due date of the invoice'
+ type: string
+ format: date
+ example: '1994-07-30'
+ settings:
+ $ref: '#/components/schemas/CompanySettings'
+ last_viewed:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ archived_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ custom_surcharge1:
+ description: 'First Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge2:
+ description: 'Second Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge3:
+ description: 'Third Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge4:
+ description: 'Fourth Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge_tax1:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ custom_surcharge_tax2:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ custom_surcharge_tax3:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ custom_surcharge_tax4:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/invoice_item.yaml b/openapi/components/schemas/invoice_item.yaml
new file mode 100644
index 000000000000..94c512f49e1b
--- /dev/null
+++ b/openapi/components/schemas/invoice_item.yaml
@@ -0,0 +1,83 @@
+ InvoiceItem:
+ type: object
+ properties:
+ quantity:
+ type: integer
+ example: 1
+ cost:
+ type: number
+ format: float
+ example: 10.00
+ product_key:
+ type: string
+ example: 'Product key'
+ product_cost:
+ type: number
+ format: float
+ example: 10.00
+ notes:
+ type: string
+ example: 'Item notes'
+ discount:
+ type: number
+ format: float
+ example: 5.00
+ is_amount_discount:
+ type: boolean
+ example: false
+ tax_name1:
+ type: string
+ example: 'Tax name 1'
+ tax_rate1:
+ type: number
+ format: float
+ example: 10.00
+ tax_name2:
+ type: string
+ example: 'Tax name 2'
+ tax_rate2:
+ type: number
+ format: float
+ example: 5.00
+ tax_name3:
+ type: string
+ example: 'Tax name 3'
+ tax_rate3:
+ type: number
+ format: float
+ example: 3.00
+ sort_id:
+ type: string
+ example: '0'
+ line_total:
+ type: number
+ format: float
+ example: 10.00
+ gross_line_total:
+ type: number
+ format: float
+ example: 15.00
+ tax_amount:
+ type: number
+ format: float
+ example: 1.00
+ date:
+ type: string
+ format: date-time
+ example: '2023-03-19T00:00:00Z'
+ custom_value1:
+ type: string
+ example: 'Custom value 1'
+ custom_value2:
+ type: string
+ example: 'Custom value 2'
+ custom_value3:
+ type: string
+ example: 'Custom value 3'
+ custom_value4:
+ type: string
+ example: 'Custom value 4'
+ type_id:
+ type: string
+ example: '1'
+ description: '1 = product, 2 = service, 3 unpaid gateway fee, 4 paid gateway fee, 5 late fee, 6 expense'
\ No newline at end of file
diff --git a/openapi/components/schemas/payment.yaml b/openapi/components/schemas/payment.yaml
new file mode 100644
index 000000000000..d9c3f437f68d
--- /dev/null
+++ b/openapi/components/schemas/payment.yaml
@@ -0,0 +1,90 @@
+ Payment:
+ properties:
+ id:
+ description: 'The payment hashed id'
+ type: string
+ example: Opnel5aKBz
+ client_id:
+ description: 'The client hashed id'
+ type: string
+ example: Opnel5aKBz
+ invitation_id:
+ description: 'The invitation hashed id'
+ type: string
+ example: Opnel5aKBz
+ client_contact_id:
+ description: 'The client contact hashed id'
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: 'The user hashed id'
+ type: string
+ example: Opnel5aKBz
+ type_id:
+ description: 'The Payment Type ID'
+ type: string
+ example: '1'
+ date:
+ description: 'The Payment date'
+ type: string
+ example: 1-1-2014
+ transaction_reference:
+ description: 'The transaction reference as defined by the payment gateway'
+ type: string
+ example: xcsSxcs124asd
+ assigned_user_id:
+ description: 'The assigned user hashed id'
+ type: string
+ example: Opnel5aKBz
+ private_notes:
+ description: 'The private notes of the payment'
+ type: string
+ example: 'The payment was refunded due to error'
+ is_manual:
+ description: 'Flags whether the payment was made manually or processed via a gateway'
+ type: boolean
+ example: true
+ is_deleted:
+ description: 'Defines if the payment has been deleted'
+ type: boolean
+ example: true
+ amount:
+ description: 'The amount of this payment'
+ type: number
+ example: 10
+ refunded:
+ description: 'The refunded amount of this payment'
+ type: number
+ example: 10
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ archived_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ company_gateway_id:
+ description: 'The company gateway id'
+ type: string
+ example: '3'
+ paymentables:
+ $ref: '#/components/schemas/Paymentable'
+ invoices:
+ description: ''
+ type: array
+ items:
+ $ref: '#/components/schemas/InvoicePaymentable'
+ credits:
+ description: ''
+ type: array
+ items:
+ $ref: '#/components/schemas/CreditPaymentable'
+ number:
+ description: 'The payment number - is a unique alpha numeric number per payment per company'
+ type: string
+ example: PAY_101
+ type: object
+
\ No newline at end of file
diff --git a/openapi/components/schemas/payment_term.yaml b/openapi/components/schemas/payment_term.yaml
new file mode 100644
index 000000000000..a69d25cb11b6
--- /dev/null
+++ b/openapi/components/schemas/payment_term.yaml
@@ -0,0 +1,26 @@
+ PaymentTerm:
+ properties:
+ num_days:
+ description: 'The payment term length in days'
+ type: integer
+ example: '1'
+ name:
+ description: 'The payment term length in string format'
+ type: string
+ example: 'NET 1'
+ created_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ archived_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/paymentable.yaml b/openapi/components/schemas/paymentable.yaml
new file mode 100644
index 000000000000..bb099f8d47cd
--- /dev/null
+++ b/openapi/components/schemas/paymentable.yaml
@@ -0,0 +1,35 @@
+ Paymentable:
+ properties:
+ id:
+ description: 'The paymentable hashed id'
+ type: string
+ example: AS3df3A
+ invoice_id:
+ description: 'The invoice hashed id'
+ type: string
+ example: AS3df3A
+ credit_id:
+ description: 'The credit hashed id'
+ type: string
+ example: AS3df3A
+ refunded:
+ description: 'The amount that has been refunded for this payment'
+ type: number
+ format: float
+ example: '10.00'
+ amount:
+ description: 'The amount that has been applied to the payment'
+ type: number
+ format: float
+ example: '10.00'
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ created_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/product.yaml b/openapi/components/schemas/product.yaml
new file mode 100644
index 000000000000..34fe77b8d77a
--- /dev/null
+++ b/openapi/components/schemas/product.yaml
@@ -0,0 +1,138 @@
+ Product:
+ type: object
+ properties:
+ id:
+ type: string
+ description: 'The hashed product ID.'
+ example: eP01N
+ company_id:
+ type: string
+ description: 'The hashed ID of the company that owns this product.'
+ example: eP01N
+ user_id:
+ type: string
+ description: 'The hashed ID of the user that created this product.'
+ example: n30m4
+ assigned_user_id:
+ type: string
+ description: 'The hashed ID of the user assigned to this product.'
+ example: pR0j3
+ project_id:
+ type: string
+ description: 'The hashed ID of the project that this product is associated with.'
+ example: pR0j3
+ vendor_id:
+ type: string
+ description: 'The hashed ID of the vendor that this product is associated with.'
+ example: pR0j3
+ custom_value1:
+ type: string
+ description: 'Custom value field 1.'
+ example: 'Custom value 1'
+ custom_value2:
+ type: string
+ description: 'Custom value field 2.'
+ example: 'Custom value 2'
+ custom_value3:
+ type: string
+ description: 'Custom value field 3.'
+ example: 'Custom value 3'
+ custom_value4:
+ type: string
+ description: 'Custom value field 4.'
+ example: 'Custom value 4'
+ product_key:
+ type: string
+ description: 'The product key.'
+ example: '1234'
+ notes:
+ type: string
+ description: 'Notes about the product.'
+ example: 'These are some notes about the product.'
+ cost:
+ type: number
+ format: float
+ description: 'The cost of the product.'
+ example: 10.0
+ price:
+ type: number
+ format: float
+ description: 'The price of the product.'
+ example: 20.0
+ quantity:
+ type: number
+ format: float
+ description: 'The quantity of the product.'
+ example: 5.0
+ tax_name1:
+ type: string
+ description: 'The name of tax 1.'
+ example: 'Tax 1'
+ tax_rate1:
+ type: number
+ format: float
+ description: 'The rate of tax 1.'
+ example: 10.0
+ tax_name2:
+ type: string
+ description: 'The name of tax 2.'
+ example: 'Tax 2'
+ tax_rate2:
+ type: number
+ format: float
+ description: 'The rate of tax 2.'
+ example: 5.0
+ tax_name3:
+ type: string
+ description: 'The name of tax 3.'
+ example: 'Tax 3'
+ tax_rate3:
+ type: number
+ format: float
+ description: 'The rate of tax 3.'
+ example: 0.0
+ archived_at:
+ type: integer
+ format: timestamp
+ description: 'The timestamp when the product was archived.'
+ example: '2022-03-18T15:00:00Z'
+ created_at:
+ type: integer
+ format: timestamp
+ description: 'The timestamp when the product was created.'
+ example: '2022-03-18T15:00:00Z'
+ updated_at:
+ description: Timestamp
+ type: integer
+ format: timestamp
+ example: '2022-03-18T12:34:56.789Z'
+ is_deleted:
+ type: boolean
+ description: 'Boolean flag determining if the product has been deleted'
+ example: false
+ in_stock_quantity:
+ type: integer
+ format: int32
+ description: The quantity of the product that is currently in stock
+ default: 0
+
+ stock_notification:
+ type: boolean
+ description: Indicates whether stock notifications are enabled for this product
+ default: true
+
+ stock_notification_threshold:
+ type: integer
+ format: int32
+ description: The minimum quantity threshold for which stock notifications will be triggered
+ default: 0
+
+ max_quantity:
+ type: integer
+ format: int32
+ description: The maximum quantity that can be ordered for this product
+
+ product_image:
+ type: string
+ description: The URL of the product image
+ format: uri-reference
diff --git a/openapi/components/schemas/project.yaml b/openapi/components/schemas/project.yaml
new file mode 100644
index 000000000000..3588dbb4610e
--- /dev/null
+++ b/openapi/components/schemas/project.yaml
@@ -0,0 +1,88 @@
+ Project:
+ type: object
+ properties:
+ id:
+ description: 'The project hashed id'
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: 'The user hashed id'
+ type: string
+ example: Opnel5aKBz
+ assigned_user_id:
+ description: The assigned user identifier associated with the project
+ type: string
+ example: Opnel5aKBz
+ client_id:
+ type: string
+ example: Opnel5aKBz
+ description: The client identifier associated with the project
+ name:
+ type: string
+ description: The name of the project
+ example: 'New Project'
+ task_rate:
+ type: number
+ format: float
+ example: 10
+ description: The default rate per task for the project
+ due_date:
+ type: string
+ format: date
+ example: '2019-01-01'
+ description: The due date for the project
+ private_notes:
+ type: string
+ description: Private notes associated with the project
+ budgeted_hours:
+ type: number
+ format: float
+ description: The number of budgeted hours for the project
+ custom_value1:
+ type: string
+ description: Custom value field 1
+ custom_value2:
+ type: string
+ description: Custom value field 2
+ custom_value3:
+ type: string
+ description: Custom value field 3
+ custom_value4:
+ type: string
+ description: Custom value field 4
+ created_at:
+ type: number
+ format: integer
+ example: 134341234234
+ description: The timestamp of the project creation
+ updated_at:
+ type: number
+ format: integer
+ example: 134341234234
+ description: The timestamp of the last project update
+ archived_at:
+ type: number
+ format: integer
+ example: 134341234234
+ description: The timestamp of the project deletion
+ public_notes:
+ type: string
+ description: Public notes associated with the project
+ is_deleted:
+ type: boolean
+ description: A flag indicating if the project is deleted
+ number:
+ type: string
+ description: The project number
+ color:
+ type: string
+ description: The color associated with the project
+ required:
+ - id
+ - user_id
+ - company_id
+ - name
+ - task_rate
+ - budgeted_hours
+ - is_deleted
+ - color
diff --git a/openapi/components/schemas/purchase_order.yaml b/openapi/components/schemas/purchase_order.yaml
new file mode 100644
index 000000000000..3202309b4408
--- /dev/null
+++ b/openapi/components/schemas/purchase_order.yaml
@@ -0,0 +1,220 @@
+ PurchaseOrder:
+ properties:
+ id:
+ description: 'The unique hashed identifier for the purchase order'
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: 'The unique hashed identifier for the user who created the purchase order'
+ type: string
+ example: ''
+ assigned_user_id:
+ description: 'The unique hashed identifier for the user assigned to the purchase order'
+ type: string
+ example: ''
+ company_id:
+ description: 'The unique hashed identifier for the company associated with the purchase order'
+ type: string
+ example: ''
+ vendor_id:
+ description: 'The unique hashed identifier for the vendor associated with the purchase order'
+ type: string
+ example: ''
+ status_id:
+ description: 'The status of the purchase order represented by a unique identifier'
+ type: string
+ example: ''
+ number:
+ description: 'The unique alpha-numeric purchase order number per company'
+ type: string
+ example: PO_101
+ quote_number:
+ description: 'The quote number associated with this purchase order'
+ type: string
+ example: QUOTE_101
+ terms:
+ description: 'The terms and conditions for the purchase order'
+ type: string
+ example: 'These are some purchase order terms. Valid for 14 days.'
+ public_notes:
+ description: 'Publicly visible notes associated with the purchase order'
+ type: string
+ example: 'These are public notes which the vendor may see'
+ private_notes:
+ description: 'Privately visible notes associated with the purchase order, not disclosed to the vendor'
+ type: string
+ example: 'These are private notes, not to be disclosed to the vendor'
+ footer:
+ description: 'The footer text of the purchase order'
+ type: string
+ example: 'The text goes in the footer of the purchase order'
+ custom_value1:
+ description: 'First custom value field for additional information'
+ type: string
+ example: 'A custom value'
+ custom_value2:
+ description: 'Second custom value field for additional information'
+ type: string
+ example: 'A custom value'
+ custom_value3:
+ description: 'Third custom value field for additional information'
+ type: string
+ example: 'A custom value'
+ custom_value4:
+ description: 'Fourth custom value field for additional information'
+ type: string
+ example: 'A custom value'
+ tax_name1:
+ description: 'The name of the first tax applied to the purchase order'
+ type: string
+ example: GST
+ tax_name2:
+ description: 'The name of the second tax applied to the purchase order'
+ type: string
+ example: VAT
+ tax_rate1:
+ description: 'The rate of the first tax applied to the purchase order'
+ type: number
+ format: float
+ example: 10.00
+ tax_rate2:
+ description: 'The rate of the second tax applied to the purchase order'
+ type: number
+ format: float
+ example: 10.00
+ tax_name3:
+ description: 'The name of the third tax applied to the purchase order'
+ type: string
+ example: ''
+ tax_rate3:
+ description: 'The rate of the third tax applied to the purchase order'
+ type: number
+ format: float
+ example: 10.00
+ total_taxes:
+ description: 'The total amount of taxes applied to the purchase order'
+ type: number
+ format: float
+ example: 10.00
+ line_items:
+ type: array
+ description: 'An array of objects which define the line items of the purchase order'
+ items:
+ $ref: '#/components/schemas/InvoiceItem'
+ amount:
+ description: 'The total amount of the purchase order before taxes and discounts'
+ type: number
+ format: float
+ example: 10.00
+ balance:
+ description: 'The balance due for the purchase order after accounting for payments'
+ type: number
+ format: float
+ example: 10.00
+ paid_to_date:
+ description: 'The total amount paid on the purchase order so far'
+ type: number
+ format: float
+ example: 10.00
+ discount:
+ description: 'The discount amount or percentage applied to the purchase order'
+ type: number
+ format: float
+ example: 10.00
+ partial:
+ description: 'The partial or deposit amount for the purchase order'
+ type: number
+ format: float
+ example: 10.00
+ is_amount_discount:
+ description: 'Boolean flag indicating if the discount is a fixed amount or a percentage'
+ type: boolean
+ example: true
+ is_deleted:
+ description: 'Boolean flag indicating if the purchase order has been deleted'
+ type: boolean
+ example: false
+ uses_inclusive_taxes:
+ description: 'Boolean flag indicating if the taxes used are inclusive or exclusive'
+ type: boolean
+ example: true
+ date:
+ description: 'The date the purchase order was created'
+ type: string
+ format: date
+ example: '1994-07-30'
+ last_sent_date:
+ description: 'The last date the purchase order was sent to the vendor'
+ type: string
+ format: date
+ example: '1994-07-30'
+ next_send_date:
+ description: 'The next scheduled date for sending a reminder for the purchase order'
+ type: string
+ format: date
+ example: '1994-07-30'
+ partial_due_date:
+ description: 'The due date for the partial or deposit amount'
+ type: string
+ format: date
+ example: '1994-07-30'
+ due_date:
+ description: 'The due date for the total amount of the purchase order'
+ type: string
+ format: date
+ example: '1994-07-30'
+ settings:
+ $ref: '#/components/schemas/CompanySettings'
+ last_viewed:
+ description: Timestamp
+ type: number
+ format: integer
+ example: 1434342123
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: 1434342123
+ archived_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: 1434342123
+ custom_surcharge1:
+ description: 'First custom surcharge amount for the purchase order'
+ type: number
+ format: float
+ example: 10.00
+ custom_surcharge2:
+ description: 'Second custom surcharge amount for the purchase order'
+ type: number
+ format: float
+ example: 10.00
+ custom_surcharge3:
+ description: 'Third custom surcharge amount for the purchase order'
+ type: number
+ format: float
+ example: 10.00
+ custom_surcharge4:
+ description: 'Fourth custom surcharge amount for the purchase order'
+ type: number
+ format: float
+ example: 10.00
+ custom_surcharge_tax1:
+ description: 'Boolean flag indicating if taxes are charged on the first custom surcharge amount'
+ type: boolean
+ example: true
+ custom_surcharge_tax2:
+ description: 'Boolean flag indicating if taxes are charged on the second custom surcharge amount'
+ type: boolean
+ example: true
+ custom_surcharge_tax3:
+ description: 'Boolean flag indicating if taxes are charged on the third custom surcharge amount'
+ type: boolean
+ example: true
+ custom_surcharge_tax4:
+ description: 'Boolean flag indicating if taxes are charged on the fourth custom surcharge amount'
+ type: boolean
+ example: true
+ type: object
+
diff --git a/openapi/components/schemas/quote.yaml b/openapi/components/schemas/quote.yaml
new file mode 100644
index 000000000000..3b7b00a6fb57
--- /dev/null
+++ b/openapi/components/schemas/quote.yaml
@@ -0,0 +1,219 @@
+ Quote:
+ properties:
+ id:
+ description: 'The unique hashed identifier for the quote'
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: 'The unique hashed identifier for the user who created the quote'
+ type: string
+ example: ''
+ assigned_user_id:
+ description: 'The unique hashed identifier for the user assigned to the quote'
+ type: string
+ example: ''
+ company_id:
+ description: 'The unique hashed identifier for the company associated with the quote'
+ type: string
+ example: ''
+ client_id:
+ description: 'The unique hashed identifier for the client associated with the quote'
+ type: string
+ example: ''
+ status_id:
+ description: 'The status of the quote represented by a unique identifier'
+ type: string
+ example: ''
+ number:
+ description: 'The unique alpha-numeric quote number for the quote per company'
+ type: string
+ example: QUOTE_101
+ po_number:
+ description: 'The purchase order number associated with the quote'
+ type: string
+ example: PO-1234
+ terms:
+ description: 'The terms and conditions for the quote'
+ type: string
+ example: 'These are some quote terms. Valid for 14 days.'
+ public_notes:
+ description: 'Publicly visible notes associated with the quote'
+ type: string
+ example: 'These are public notes which the client may see'
+ private_notes:
+ description: 'Privately visible notes associated with the quote, not disclosed to the client'
+ type: string
+ example: 'These are private notes, not to be disclosed to the client'
+ footer:
+ description: 'The footer text of the quote'
+ type: string
+ example: 'The text goes in the footer of the quote'
+ custom_value1:
+ description: 'First custom value field for additional information'
+ type: string
+ example: 'A custom value'
+ custom_value2:
+ description: 'Second custom value field for additional information'
+ type: string
+ example: 'A custom value'
+ custom_value3:
+ description: 'Third custom value field for additional information'
+ type: string
+ example: 'A custom value'
+ custom_value4:
+ description: 'Fourth custom value field for additional information'
+ type: string
+ example: 'A custom value'
+ tax_name1:
+ description: 'The name of the first tax applied to the quote'
+ type: string
+ example: GST
+ tax_name2:
+ description: 'The name of the second tax applied to the quote'
+ type: string
+ example: VAT
+ tax_rate1:
+ description: 'The rate of the first tax applied to the quote'
+ type: number
+ format: float
+ example: 10.00
+ tax_rate2:
+ description: 'The rate of the second tax applied to the quote'
+ type: number
+ format: float
+ example: 10.00
+ tax_name3:
+ description: 'The name of the third tax applied to the quote'
+ type: string
+ example: ''
+ tax_rate3:
+ description: 'The rate of the third tax applied to the quote'
+ type: number
+ format: float
+ example: 10.00
+ total_taxes:
+ description: 'The total amount of taxes for the quote'
+ type: number
+ format: float
+ example: 10.00
+ line_items:
+ type: array
+ description: 'An array of objects which define the line items of the quote'
+ items:
+ $ref: '#/components/schemas/InvoiceItem'
+ amount:
+ description: 'The total amount of the quote before taxes and discounts'
+ type: number
+ format: float
+ example: 10.00
+ balance:
+ description: 'The balance due for the quote after accounting for payments'
+ type: number
+ format: float
+ example: 10.00
+ paid_to_date:
+ description: 'The total amount paid on the quote so far'
+ type: number
+ format: float
+ example: 10.00
+ discount:
+ description: 'The discount amount or percentage applied to the quote'
+ type: number
+ format: float
+ example: 10.00
+ partial:
+ description: 'The partial or deposit amount for the quote'
+ type: number
+ format: float
+ example: 10.00
+ is_amount_discount:
+ description: 'Boolean flag indicating if the discount is a fixed amount or a percentage'
+ type: boolean
+ example: true
+ is_deleted:
+ description: 'Boolean flag indicating if the quote has been deleted'
+ type: boolean
+ example: false
+ uses_inclusive_taxes:
+ description: 'Boolean flag indicating if the taxes used are inclusive or exclusive'
+ type: boolean
+ example: true
+ date:
+ description: 'The date the quote was created'
+ type: string
+ format: date
+ example: '1994-07-30'
+ last_sent_date:
+ description: 'The last date the quote was sent to the client'
+ type: string
+ format: date
+ example: '1994-07-30'
+ next_send_date:
+ description: 'The next scheduled date for sending a reminder for the quote'
+ type: string
+ format: date
+ example: '1994-07-30'
+ partial_due_date:
+ description: 'The due date for the partial or deposit amount'
+ type: string
+ format: date
+ example: '1994-07-30'
+ due_date:
+ description: 'The due date for the total amount of the quote'
+ type: string
+ format: date
+ example: '1994-07-30'
+ settings:
+ $ref: '#/components/schemas/CompanySettings'
+ last_viewed:
+ description: 'The timestamp of the last time the quote was viewed'
+ type: number
+ format: integer
+ example: 1434342123
+ updated_at:
+ description: 'The timestamp of the last update to the quote'
+ type: number
+ format: integer
+ example: 1434342123
+ archived_at:
+ description: 'The timestamp of when the quote was archived'
+ type: number
+ format: integer
+ example: 1434342123
+ custom_surcharge1:
+ description: 'First custom surcharge amount for the quote'
+ type: number
+ format: float
+ example: 10.00
+ custom_surcharge2:
+ description: 'Second custom surcharge amount for the quote'
+ type: number
+ format: float
+ example: 10.00
+ custom_surcharge3:
+ description: 'Third custom surcharge amount for the quote'
+ type: number
+ format: float
+ example: 10.00
+ custom_surcharge4:
+ description: 'Fourth custom surcharge amount for the quote'
+ type: number
+ format: float
+ example: 10.00
+ custom_surcharge_tax1:
+ description: 'Boolean flag indicating if taxes are charged on the first custom surcharge amount'
+ type: boolean
+ example: true
+ custom_surcharge_tax2:
+ description: 'Boolean flag indicating if taxes are charged on the second custom surcharge amount'
+ type: boolean
+ example: true
+ custom_surcharge_tax3:
+ description: 'Boolean flag indicating if taxes are charged on the third custom surcharge amount'
+ type: boolean
+ example: true
+ custom_surcharge_tax4:
+ description: 'Boolean flag indicating if taxes are charged on the fourth custom surcharge amount'
+ type: boolean
+ example: true
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/recurring_expense.yaml b/openapi/components/schemas/recurring_expense.yaml
new file mode 100644
index 000000000000..747b89baeff7
--- /dev/null
+++ b/openapi/components/schemas/recurring_expense.yaml
@@ -0,0 +1,171 @@
+ RecurringExpense:
+ properties:
+ id:
+ description: 'The hashed id of the recurring expense'
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: 'The hashed id of the user who created the recurring expense'
+ type: string
+ example: Opnel5aKBz
+ assigned_user_id:
+ description: 'The hashed id of the user assigned to this recurring expense'
+ type: string
+ example: Opnel5aKBz
+ company_id:
+ description: 'The hashed id of the company'
+ type: string
+ example: Opnel5aKBz
+ client_id:
+ description: 'The hashed id of the client'
+ type: string
+ example: Opnel5aKBz
+ invoice_id:
+ description: 'The hashed id of the invoice'
+ type: string
+ example: Opnel5aKBz
+ bank_id:
+ description: 'The id of the bank associated with this recurring expense'
+ type: string
+ example: '22'
+ invoice_currency_id:
+ description: 'The currency id of the invoice associated with this recurring expense'
+ type: string
+ example: '1'
+ expense_currency_id:
+ description: 'The currency id of the expense associated with this recurring expense'
+ type: string
+ example: '1'
+ invoice_category_id:
+ description: 'The category id of the invoice'
+ type: string
+ example: '1'
+ payment_type_id:
+ description: 'The payment type id'
+ type: string
+ example: '1'
+ private_notes:
+ description: 'The recurring expense private notes'
+ type: string
+ example: 'Private and confidential'
+ public_notes:
+ description: 'The recurring expense public notes'
+ type: string
+ example: 'This is the best client in the world'
+ transaction_reference:
+ description: 'The recurring expense transaction reference'
+ type: string
+ example: EXP-1223-2333
+ transcation_id:
+ description: 'The transaction id of the recurring expense'
+ type: string
+ example: '1233312312'
+ custom_value1:
+ description: 'Custom value field'
+ type: string
+ example: $1000
+ custom_value2:
+ description: 'Custom value field'
+ type: string
+ example: '2022-10-10'
+ custom_value3:
+ description: 'Custom value field'
+ type: string
+ example: 'short text'
+ custom_value4:
+ description: 'Custom value field'
+ type: string
+ example: 'very long text'
+ tax_name1:
+ description: 'The tax name'
+ type: string
+ example: GST
+ tax_name2:
+ description: 'The tax name'
+ type: string
+ example: VAT
+ tax_rate1:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ tax_rate2:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ tax_name3:
+ description: 'The tax name'
+ type: string
+ example: ''
+ tax_rate3:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ amount:
+ description: 'The total amount of the recurring expense'
+ type: number
+ format: float
+ example: '10.00'
+ frequency_id:
+ description: 'The frequency this recurring expense fires'
+ type: number
+ format: int
+ example: '1'
+ remaining_cycles:
+ description: 'The number of remaining cycles for this recurring expense'
+ type: number
+ format: int
+ example: '1'
+ foreign_amount:
+ description: 'The foreign currency amount of the recurring expense'
+ type: number
+ format: float
+ example: '10.00'
+ exchange_rate:
+ description: 'The exchange rate for the expernse'
+ type: number
+ format: float
+ example: '0.80'
+ date:
+ description: 'The date of the expense'
+ type: string
+ example: ''
+ payment_date:
+ description: 'The date the expense was paid'
+ type: string
+ example: ''
+ should_be_invoiced:
+ description: 'Boolean flag determining if the expense should be invoiced'
+ type: boolean
+ example: true
+ is_deleted:
+ description: 'Boolean flag determining if the recurring expense is deleted'
+ type: boolean
+ example: true
+ last_sent_date:
+ description: 'The Date it was sent last'
+ type: string
+ format: date
+ example: '1994-07-30'
+ next_send_date:
+ description: 'The next send date'
+ type: string
+ format: date
+ example: '1994-07-30'
+ invoice_documents:
+ description: 'Boolean flag determining if the documents associated with this expense should be passed onto the invoice if it is converted to an invoice'
+ type: boolean
+ example: true
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ archived_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/recurring_invoice.yaml b/openapi/components/schemas/recurring_invoice.yaml
new file mode 100644
index 000000000000..933592f5c04e
--- /dev/null
+++ b/openapi/components/schemas/recurring_invoice.yaml
@@ -0,0 +1,227 @@
+ RecurringInvoice:
+ properties:
+ id:
+ description: 'The hashed id of the recurring invoice'
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: 'The user hashed id'
+ type: string
+ example: Opnel5aKBz
+ assigned_user_id:
+ description: 'The assigned user hashed id'
+ type: string
+ example: Opnel5aKBz
+ company_id:
+ description: 'The company hashed id'
+ type: string
+ example: Opnel5aKBz
+ client_id:
+ description: 'The client hashed id'
+ type: string
+ example: Opnel5aKBz
+ status_id:
+ description: 'The invoice status variable'
+ type: string
+ example: '4'
+ frequency_id:
+ description: 'The recurring invoice frequency'
+ type: number
+ example: '4'
+ remaining_cycles:
+ description: 'The number of invoices left to be generated'
+ type: number
+ example: '4'
+ number:
+ description: 'The recurringinvoice number - is a unique alpha numeric number per invoice per company'
+ type: string
+ example: INV_101
+ po_number:
+ description: 'The purchase order associated with this recurring invoice'
+ type: string
+ example: PO-1234
+ terms:
+ description: 'The invoice terms'
+ type: string
+ example: 'These are invoice terms'
+ public_notes:
+ description: 'The public notes of the invoice'
+ type: string
+ example: 'These are some public notes'
+ private_notes:
+ description: 'The private notes of the invoice'
+ type: string
+ example: 'These are some private notes'
+ footer:
+ description: 'The invoice footer notes'
+ type: string
+ example: ''
+ custom_value1:
+ description: 'A custom field value'
+ type: string
+ example: '2022-10-01'
+ custom_value2:
+ description: 'A custom field value'
+ type: string
+ example: 'Something custom'
+ custom_value3:
+ description: 'A custom field value'
+ type: string
+ example: ''
+ custom_value4:
+ description: 'A custom field value'
+ type: string
+ example: ''
+ tax_name1:
+ description: 'The tax name'
+ type: string
+ example: ''
+ tax_name2:
+ description: 'The tax name'
+ type: string
+ example: ''
+ tax_rate1:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ tax_rate2:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ tax_name3:
+ description: 'The tax name'
+ type: string
+ example: ''
+ tax_rate3:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ total_taxes:
+ description: 'The total taxes for the invoice'
+ type: number
+ format: float
+ example: '10.00'
+ line_items:
+ description: 'An array of objects which define the line items of the invoice'
+ type: object
+ example: ''
+ amount:
+ description: 'The invoice amount'
+ type: number
+ format: float
+ example: '10.00'
+ balance:
+ description: 'The invoice balance'
+ type: number
+ format: float
+ example: '10.00'
+ paid_to_date:
+ description: 'The amount paid on the invoice to date'
+ type: number
+ format: float
+ example: '10.00'
+ discount:
+ description: 'The invoice discount, can be an amount or a percentage'
+ type: number
+ format: float
+ example: '10.00'
+ partial:
+ description: 'The deposit/partial amount'
+ type: number
+ format: float
+ example: '10.00'
+ is_amount_discount:
+ description: 'Flag determining if the discount is an amount or a percentage'
+ type: boolean
+ example: true
+ is_deleted:
+ description: 'Defines if the invoice has been deleted'
+ type: boolean
+ example: true
+ uses_inclusive_taxes:
+ description: 'Defines the type of taxes used as either inclusive or exclusive'
+ type: boolean
+ example: true
+ date:
+ description: 'The Invoice Date'
+ type: string
+ format: date
+ example: '1994-07-30'
+ last_sent_date:
+ description: 'The last date the invoice was sent out'
+ type: string
+ format: date
+ example: '1994-07-30'
+ next_send_date:
+ description: 'The Next date for a reminder to be sent'
+ type: string
+ format: date
+ example: '1994-07-30'
+ partial_due_date:
+ description: 'The due date for the deposit/partial amount'
+ type: string
+ format: date
+ example: '1994-07-30'
+ due_date:
+ description: 'The due date of the invoice'
+ type: string
+ format: date
+ example: '1994-07-30'
+ settings:
+ $ref: '#/components/schemas/CompanySettings'
+ last_viewed:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ archived_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ custom_surcharge1:
+ description: 'First Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge2:
+ description: 'Second Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge3:
+ description: 'Third Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge4:
+ description: 'Fourth Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge_tax1:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ custom_surcharge_tax2:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ custom_surcharge_tax3:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ custom_surcharge_tax4:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ type: object
+
\ No newline at end of file
diff --git a/openapi/components/schemas/recurring_quote.yaml b/openapi/components/schemas/recurring_quote.yaml
new file mode 100644
index 000000000000..98e67953cd73
--- /dev/null
+++ b/openapi/components/schemas/recurring_quote.yaml
@@ -0,0 +1,226 @@
+ RecurringQuote:
+ properties:
+ id:
+ description: 'The hashed id of the recurring quote'
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: 'The user hashed id'
+ type: string
+ example: Opnel5aKBz
+ assigned_user_id:
+ description: 'The assigned user hashed id'
+ type: string
+ example: Opnel5aKBz
+ company_id:
+ description: 'The company hashed id'
+ type: string
+ example: Opnel5aKBz
+ client_id:
+ description: 'The client hashed id'
+ type: string
+ example: Opnel5aKBz
+ status_id:
+ description: 'The quote status variable'
+ type: string
+ example: '4'
+ frequency_id:
+ description: 'The recurring quote frequency'
+ type: number
+ example: '4'
+ remaining_cycles:
+ description: 'The number of quotes left to be generated'
+ type: number
+ example: '4'
+ number:
+ description: 'The recurringquote number - is a unique alpha numeric number per quote per company'
+ type: string
+ example: INV_101
+ po_number:
+ description: 'The purchase order associated with this recurring quote'
+ type: string
+ example: PO-1234
+ terms:
+ description: 'The quote terms'
+ type: string
+ example: 'These are quote terms'
+ public_notes:
+ description: 'The public notes of the quote'
+ type: string
+ example: 'These are some public notes'
+ private_notes:
+ description: 'The private notes of the quote'
+ type: string
+ example: 'These are some private notes'
+ footer:
+ description: 'The quote footer notes'
+ type: string
+ example: ''
+ custom_value1:
+ description: 'A custom field value'
+ type: string
+ example: '2022-10-01'
+ custom_value2:
+ description: 'A custom field value'
+ type: string
+ example: 'Something custom'
+ custom_value3:
+ description: 'A custom field value'
+ type: string
+ example: ''
+ custom_value4:
+ description: 'A custom field value'
+ type: string
+ example: ''
+ tax_name1:
+ description: 'The tax name'
+ type: string
+ example: ''
+ tax_name2:
+ description: 'The tax name'
+ type: string
+ example: ''
+ tax_rate1:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ tax_rate2:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ tax_name3:
+ description: 'The tax name'
+ type: string
+ example: ''
+ tax_rate3:
+ description: 'The tax rate'
+ type: number
+ format: float
+ example: '10.00'
+ total_taxes:
+ description: 'The total taxes for the quote'
+ type: number
+ format: float
+ example: '10.00'
+ line_items:
+ description: 'An array of objects which define the line items of the quote'
+ type: object
+ example: ''
+ amount:
+ description: 'The quote amount'
+ type: number
+ format: float
+ example: '10.00'
+ balance:
+ description: 'The quote balance'
+ type: number
+ format: float
+ example: '10.00'
+ paid_to_date:
+ description: 'The amount paid on the quote to date'
+ type: number
+ format: float
+ example: '10.00'
+ discount:
+ description: 'The quote discount, can be an amount or a percentage'
+ type: number
+ format: float
+ example: '10.00'
+ partial:
+ description: 'The deposit/partial amount'
+ type: number
+ format: float
+ example: '10.00'
+ is_amount_discount:
+ description: 'Flag determining if the discount is an amount or a percentage'
+ type: boolean
+ example: true
+ is_deleted:
+ description: 'Defines if the quote has been deleted'
+ type: boolean
+ example: true
+ uses_inclusive_taxes:
+ description: 'Defines the type of taxes used as either inclusive or exclusive'
+ type: boolean
+ example: true
+ date:
+ description: 'The quote Date'
+ type: string
+ format: date
+ example: '1994-07-30'
+ last_sent_date:
+ description: 'The last date the quote was sent out'
+ type: string
+ format: date
+ example: '1994-07-30'
+ next_send_date:
+ description: 'The Next date for a reminder to be sent'
+ type: string
+ format: date
+ example: '1994-07-30'
+ partial_due_date:
+ description: 'The due date for the deposit/partial amount'
+ type: string
+ format: date
+ example: '1994-07-30'
+ due_date:
+ description: 'The due date of the quote'
+ type: string
+ format: date
+ example: '1994-07-30'
+ settings:
+ $ref: '#/components/schemas/CompanySettings'
+ last_viewed:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ archived_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ custom_surcharge1:
+ description: 'First Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge2:
+ description: 'Second Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge3:
+ description: 'Third Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge4:
+ description: 'Fourth Custom Surcharge'
+ type: number
+ format: float
+ example: '10.00'
+ custom_surcharge_tax1:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ custom_surcharge_tax2:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ custom_surcharge_tax3:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ custom_surcharge_tax4:
+ description: 'Toggles charging taxes on custom surcharge amounts'
+ type: boolean
+ example: true
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/subscription.yaml b/openapi/components/schemas/subscription.yaml
new file mode 100644
index 000000000000..da8346dcfbc5
--- /dev/null
+++ b/openapi/components/schemas/subscription.yaml
@@ -0,0 +1,111 @@
+ Subscription:
+ properties:
+ id:
+ description: Unique identifier for the subscription
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: Unique identifier for the user associated with the subscription
+ type: string
+ example: Ua6Rw4pVbS
+ product_id:
+ description: Unique identifier for the product associated with the subscription
+ type: string
+ example: Pr5Ft7yBmC
+ company_id:
+ description: Unique identifier for the company associated with the subscription
+ type: string
+ example: Co7Vn3yLmW
+ recurring_invoice_id:
+ description: Unique identifier for the recurring invoice associated with the subscription
+ type: string
+ example: Ri2Yt8zJkP
+ is_recurring:
+ description: Indicates whether the subscription is recurring
+ type: boolean
+ example: 'true'
+ frequency_id:
+ description: 'integer const representation of the frequency'
+ type: string
+ example: '1'
+ auto_bill:
+ description: 'enum setting'
+ type: string
+ example: always
+ promo_code:
+ description: Promotional code applied to the subscription
+ type: string
+ example: PROMOCODE4U
+ promo_discount:
+ description: Discount percentage or amount applied to the subscription
+ type: number
+ example: 10
+ is_amount_discount:
+ description: Indicates whether the discount is a fixed amount
+ type: boolean
+ example: 'true'
+ allow_cancellation:
+ description: Indicates whether the subscription can be cancelled
+ type: boolean
+ example: 'true'
+ per_seat_enabled:
+ description: Indicates whether the subscription pricing is per seat
+ type: boolean
+ example: 'true'
+ currency_id:
+ description: Unique identifier for the currency used in the subscription
+ type: integer
+ example: '1'
+ max_seats_limit:
+ description: Maximum number of seats allowed for the subscription
+ type: integer
+ example: '100'
+ trial_enabled:
+ description: Indicates whether the subscription has a trial period
+ type: boolean
+ example: 'true'
+ trial_duration:
+ description: Duration of the trial period in days
+ type: integer
+ example: '14'
+ allow_query_overrides:
+ description: Indicates whether query overrides are allowed for the subscription
+ type: boolean
+ example: 'true'
+ allow_plan_changes:
+ description: Indicates whether plan changes are allowed for the subscription
+ type: boolean
+ example: 'true'
+ refund_period:
+ description: Number of days within which refunds can be requested
+ type: integer
+ example: '30'
+ webhook_configuration:
+ description: Webhook configuration for the subscription
+ type: string
+ example: 'expand reference for this'
+ is_deleted:
+ description: Indicates whether the subscription has been deleted
+ type: boolean
+ example: 'false'
+ archived_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ created_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ type: object
+ BulkAction:
+ type: array
+ items:
+ type: integer
+ example: '[0,1,2,3,]'
\ No newline at end of file
diff --git a/openapi/components/schemas/system_log.yaml b/openapi/components/schemas/system_log.yaml
new file mode 100644
index 000000000000..cdce0ebd4b62
--- /dev/null
+++ b/openapi/components/schemas/system_log.yaml
@@ -0,0 +1,43 @@
+ SystemLog:
+ properties:
+ id:
+ description: 'The account hashed id'
+ type: string
+ example: AS3df3A
+ company_id:
+ description: 'The company hashed id'
+ type: string
+ example: AS3df3A
+ user_id:
+ description: 'The user_id hashed id'
+ type: string
+ example: AS3df3A
+ client_id:
+ description: 'The client_id hashed id'
+ type: string
+ example: AS3df3A
+ event_id:
+ description: 'The Log Type ID'
+ type: integer
+ example: 1
+ category_id:
+ description: 'The Category Type ID'
+ type: integer
+ example: 1
+ type_id:
+ description: 'The Type Type ID'
+ type: integer
+ example: 1
+ log:
+ description: 'The json object of the error'
+ type: object
+ example: '{''key'':''value''}'
+ updated_at:
+ description: Timestamp
+ type: string
+ example: '2'
+ created_at:
+ description: Timestamp
+ type: string
+ example: '2'
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/task.yaml b/openapi/components/schemas/task.yaml
new file mode 100644
index 000000000000..a1968dc1d572
--- /dev/null
+++ b/openapi/components/schemas/task.yaml
@@ -0,0 +1,94 @@
+ Task:
+ properties:
+ id:
+ description: 'The hashed id of the task'
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: 'The hashed id of the user who created the task'
+ type: string
+ example: Opnel5aKBz
+ assigned_user_id:
+ description: 'The assigned user of the task'
+ type: string
+ example: Opnel5aKBz
+ company_id:
+ description: 'The hashed id of the company'
+ type: string
+ example: Opnel5aKBz
+ client_id:
+ description: 'The hashed if of the client'
+ type: string
+ example: Opnel5aKBz
+ invoice_id:
+ description: 'The hashed id of the invoice associated with the task'
+ type: string
+ example: Opnel5aKBz
+ project_id:
+ description: 'The hashed id of the project associated with the task'
+ type: string
+ example: Opnel5aKBz
+ number:
+ description: 'The number of the task'
+ type: string
+ example: TASK-123
+ time_log:
+ description: 'An array of unix time stamps defining the start and end times of the task'
+ type: string
+ example: '[[1,2],[3,4]]'
+ is_running:
+ description: 'Determines if the task is still running'
+ type: boolean
+ example: true
+ is_deleted:
+ description: 'Boolean flag determining if the task has been deleted'
+ type: boolean
+ example: true
+ task_status_id:
+ description: 'The hashed id of the task status'
+ type: string
+ example: Opnel5aKBz
+ description:
+ description: 'The task description'
+ type: string
+ example: 'A wonder task to work on'
+ duration:
+ description: 'The task duration'
+ type: integer
+ example: ''
+ task_status_order:
+ description: 'The order of the task'
+ type: integer
+ example: '4'
+ custom_value1:
+ description: 'A custom value'
+ type: string
+ example: '2022-10-10'
+ custom_value2:
+ description: 'A custom value'
+ type: string
+ example: $1100
+ custom_value3:
+ description: 'A custom value'
+ type: string
+ example: 'I need help'
+ custom_value4:
+ description: 'A custom value'
+ type: string
+ example: INV-3343
+ created_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ archived_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '1434342123'
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/user.yaml b/openapi/components/schemas/user.yaml
new file mode 100644
index 000000000000..10c5fd6def26
--- /dev/null
+++ b/openapi/components/schemas/user.yaml
@@ -0,0 +1,43 @@
+ User:
+ properties:
+ id:
+ description: 'The hashed id of the user'
+ type: string
+ example: Opnel5aKBz
+ first_name:
+ description: 'The first name of the user'
+ type: string
+ example: Brad
+ last_name:
+ description: 'The last name of the user'
+ type: string
+ example: Pitt
+ email:
+ description: 'The users email address'
+ type: string
+ example: brad@pitt.com
+ phone:
+ description: 'The users phone number'
+ type: string
+ example: 555-1233-23232
+ signature:
+ description: 'The users sign off signature'
+ type: string
+ example: 'Have a nice day!'
+ avatar:
+ description: 'The users avatar'
+ type: string
+ example: 'https://url.to.your/avatar.png'
+ accepted_terms_version:
+ description: 'The version of the invoice ninja terms that has been accepted by the user'
+ type: string
+ example: 1.0.1
+ oauth_user_id:
+ description: 'The provider id of the oauth entity'
+ type: string
+ example: jkhasdf789as6f675sdf768sdfs
+ oauth_provider_id:
+ description: 'The oauth entity id'
+ type: string
+ example: google
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/vendor.yaml b/openapi/components/schemas/vendor.yaml
new file mode 100644
index 000000000000..2d8413a6e0b9
--- /dev/null
+++ b/openapi/components/schemas/vendor.yaml
@@ -0,0 +1,128 @@
+ Vendor:
+ properties:
+ id:
+ description: 'The hashed id of the vendor'
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: 'The hashed id of the user who created the vendor'
+ type: string
+ example: Opnel5aKBz
+ assigned_user_id:
+ description: 'The hashed id of the assigned user to this vendor'
+ type: string
+ example: Opnel5aKBz
+ company_id:
+ description: 'The hashed id of the company'
+ type: string
+ example: Opnel5aKBz
+ client_id:
+ description: 'The hashed id of the client'
+ type: string
+ example: Opnel5aKBz
+ contacts:
+ type: array
+ items:
+ $ref: '#/components/schemas/VendorContact'
+ name:
+ description: 'The vendor name'
+ type: string
+ example: 'Harry''s cafe de wheels'
+ website:
+ description: 'The website of the vendor'
+ type: string
+ example: www.harry.com
+ private_notes:
+ description: 'The private notes of the vendor'
+ type: string
+ example: 'Shhh, don''t tell the vendor'
+ industry_id:
+ description: 'The industry id of the vendor'
+ type: string
+ example: '1'
+ size_id:
+ description: ________
+ type: string
+ example: ''
+ address1:
+ description: ________
+ type: string
+ example: ''
+ address2:
+ description: ________
+ type: string
+ example: ''
+ city:
+ description: ________
+ type: string
+ example: ''
+ state:
+ description: ________
+ type: string
+ example: ''
+ postal_code:
+ description: ________
+ type: string
+ example: ''
+ phone:
+ description: 'The client phone number'
+ type: string
+ example: 555-3434-3434
+ country_id:
+ description: ________
+ type: string
+ example: ''
+ currency_id:
+ description: ________
+ type: string
+ example: '4'
+ custom_value1:
+ description: ________
+ type: string
+ example: ''
+ custom_value2:
+ description: ________
+ type: string
+ example: ''
+ custom_value3:
+ description: ________
+ type: string
+ example: ''
+ custom_value4:
+ description: ________
+ type: string
+ example: ''
+ vat_number:
+ description: ________
+ type: string
+ example: ''
+ id_number:
+ description: ________
+ type: string
+ example: ''
+ number:
+ description: ________
+ type: string
+ example: ''
+ is_deleted:
+ description: ________
+ type: boolean
+ example: true
+ last_login:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ created_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ settings:
+ $ref: '#/components/schemas/CompanySettings'
+ type: object
\ No newline at end of file
diff --git a/openapi/components/schemas/vendor_contact.yaml b/openapi/components/schemas/vendor_contact.yaml
new file mode 100644
index 000000000000..6e9e6934c90f
--- /dev/null
+++ b/openapi/components/schemas/vendor_contact.yaml
@@ -0,0 +1,70 @@
+ VendorContact:
+ properties:
+ id:
+ description: 'The hashed id of the vendor contact'
+ type: string
+ example: Opnel5aKBz
+ user_id:
+ description: 'The hashed id of the user id'
+ type: string
+ example: Opnel5aKBz
+ company_id:
+ description: 'The hashed id of the company'
+ type: string
+ example: Opnel5aKBz
+ vendor_id:
+ description: 'The hashed id of the vendor'
+ type: string
+ example: Opnel5aKBz
+ first_name:
+ description: 'The first name of the contact'
+ type: string
+ example: Harry
+ last_name:
+ description: 'The last name of the contact'
+ type: string
+ example: Windsor
+ phone:
+ description: 'The contacts phone number'
+ type: string
+ example: 555-123-1234
+ custom_value1:
+ description: 'A custom value'
+ type: string
+ example: '2022-10-10'
+ custom_value2:
+ description: 'A custom value'
+ type: string
+ example: $1000
+ custom_value3:
+ description: 'A custom value'
+ type: string
+ example: ''
+ custom_value4:
+ description: 'A custom value'
+ type: string
+ example: ''
+ email:
+ description: 'The contact email address'
+ type: string
+ example: harry@windsor.com
+ is_primary:
+ description: 'Boolean flag determining if the contact is the primary contact for the vendor'
+ type: boolean
+ example: true
+ created_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ updated_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ deleted_at:
+ description: Timestamp
+ type: number
+ format: integer
+ example: '134341234234'
+ type: object
\ No newline at end of file
diff --git a/resources/views/layouts/guest.blade.php b/resources/views/layouts/guest.blade.php
index 6db093859999..7447cfb82f88 100644
--- a/resources/views/layouts/guest.blade.php
+++ b/resources/views/layouts/guest.blade.php
@@ -28,8 +28,10 @@
@yield('meta_title', 'Invoice Ninja') | {{ config('app.name') }}
-
+ @if(auth()->guard('contact')->user() && !auth()->guard('contact')->user()->user->account->isPaid())
+
+ @endif
diff --git a/resources/views/layouts/master.blade.php b/resources/views/layouts/master.blade.php
index e4aef481b2e3..ac7a393cadb0 100644
--- a/resources/views/layouts/master.blade.php
+++ b/resources/views/layouts/master.blade.php
@@ -28,29 +28,9 @@
@yield('meta_title', 'Invoice Ninja') | {{ config('app.name') }}
-
-
-
-
+ @if(auth()->guard('contact')->user() && !auth()->guard('contact')->user()->user->account->isPaid())
+
+ @endif
diff --git a/resources/views/portal/ninja2020/components/livewire/billing-portal-purchasev2.blade.php b/resources/views/portal/ninja2020/components/livewire/billing-portal-purchasev2.blade.php
index d3417dded2f0..82dc46a03241 100644
--- a/resources/views/portal/ninja2020/components/livewire/billing-portal-purchasev2.blade.php
+++ b/resources/views/portal/ninja2020/components/livewire/billing-portal-purchasev2.blade.php
@@ -107,7 +107,9 @@
- {!! nl2br($product->markdownNotes()) !!}
+
+ {!! $product->markdownNotes() !!}
+
{{ \App\Utils\Number::formatMoney($product->price, $subscription->company) }}
@@ -145,7 +147,11 @@
-
{!! nl2br($product->markdownNotes()) !!}
+
+
+ {!! $product->markdownNotes() !!}
+
+
{{ \App\Utils\Number::formatMoney($product->price, $subscription->company) }} / {{ App\Models\RecurringInvoice::frequencyForKey($subscription->frequency_id) }}
@@ -186,7 +192,11 @@
-
{!! nl2br($product->markdownNotes()) !!}
+
+
+ {!! $product->markdownNotes() !!}
+
+
{{ \App\Utils\Number::formatMoney($product->price, $subscription->company) }}
@@ -234,7 +244,7 @@
@foreach($bundle->toArray() as $item)
- {{ $item['qty'] }} x {{ substr(str_replace(["\r","\n","
","
","
","
"]," ", $item['product']), 0, 30) . "..." }}
+ {{ $item['qty'] }} x {{ $item['product'] }}
{{ $item['price'] }}
@endforeach
diff --git a/resources/views/portal/ninja2020/gateways/custom/payment.blade.php b/resources/views/portal/ninja2020/gateways/custom/payment.blade.php
index d337c71897d9..42373e59628f 100644
--- a/resources/views/portal/ninja2020/gateways/custom/payment.blade.php
+++ b/resources/views/portal/ninja2020/gateways/custom/payment.blade.php
@@ -1,7 +1,15 @@
@extends('portal.ninja2020.layout.payments', ['gateway_title' => $title, 'card_title' => $title])
@section('gateway_content')
- @component('portal.ninja2020.components.general.card-element', ['title' => ctrans('texts.payment_type')])
+
+@component('portal.ninja2020.components.general.card-element', ['title' => ctrans('texts.payment_type')])
{{ $title }}
@endcomponent
@@ -11,3 +19,18 @@
{!! nl2br($instructions) !!}
@endcomponent
@endsection
+
\ No newline at end of file
diff --git a/resources/views/portal/ninja2020/generic/error.blade.php b/resources/views/portal/ninja2020/generic/error.blade.php
index 422bd36e682d..3eda46a72858 100644
--- a/resources/views/portal/ninja2020/generic/error.blade.php
+++ b/resources/views/portal/ninja2020/generic/error.blade.php
@@ -12,11 +12,16 @@
- @else
+ @elseif($company)
+ @else
+
+
 }})
+
@endif
{{ $title }}
diff --git a/resources/views/portal/ninja2020/layout/clean.blade.php b/resources/views/portal/ninja2020/layout/clean.blade.php
index 17ee40e4947f..805429cb1ed0 100644
--- a/resources/views/portal/ninja2020/layout/clean.blade.php
+++ b/resources/views/portal/ninja2020/layout/clean.blade.php
@@ -91,7 +91,9 @@
+ @if(auth()->guard('contact')->user() && !auth()->guard('contact')->user()->user->account->isPaid())
{{--
--}}
+ @endif
diff --git a/resources/views/portal/ninja2020/layout/clean_setup.blade.php b/resources/views/portal/ninja2020/layout/clean_setup.blade.php
index a6781bd4fbc9..2083e6ff5b0a 100644
--- a/resources/views/portal/ninja2020/layout/clean_setup.blade.php
+++ b/resources/views/portal/ninja2020/layout/clean_setup.blade.php
@@ -89,7 +89,10 @@
@else
@endif
+
+ @if(auth()->guard('contact')->user() && !auth()->guard('contact')->user()->user->account->isPaid())
{{--
--}}
+ @endif
diff --git a/resources/views/portal/ninja2020/quotes/includes/user-input.blade.php b/resources/views/portal/ninja2020/quotes/includes/user-input.blade.php
index afafe6d6863f..3b3f340c4dc8 100644
--- a/resources/views/portal/ninja2020/quotes/includes/user-input.blade.php
+++ b/resources/views/portal/ninja2020/quotes/includes/user-input.blade.php
@@ -7,11 +7,11 @@
- {{ ctrans('texts.notes') }}
+ {{ ctrans('texts.po_number') }}
-
diff --git a/resources/views/portal/ninja2020/quotes/show.blade.php b/resources/views/portal/ninja2020/quotes/show.blade.php
index 3e297cb4d03b..3b39a8cb81de 100644
--- a/resources/views/portal/ninja2020/quotes/show.blade.php
+++ b/resources/views/portal/ninja2020/quotes/show.blade.php
@@ -120,18 +120,5 @@
var clipboard = new ClipboardJS('.btn');
- // clipboard.on('success', function(e) {
- // console.info('Action:', e.action);
- // console.info('Text:', e.text);
- // console.info('Trigger:', e.trigger);
-
- // e.clearSelection();
- // });
-
- // clipboard.on('error', function(e) {
- // console.error('Action:', e.action);
- // console.error('Trigger:', e.trigger);
- // });
-
@endsection
diff --git a/resources/views/themes/ninja2020/clean.blade.php b/resources/views/themes/ninja2020/clean.blade.php
index f58c8f7ffab1..66ac3ebda118 100644
--- a/resources/views/themes/ninja2020/clean.blade.php
+++ b/resources/views/themes/ninja2020/clean.blade.php
@@ -78,7 +78,9 @@
+ @if(auth()->guard('contact')->user() && !auth()->guard('contact')->user()->user->account->isPaid())
{{--
--}}
+ @endif
diff --git a/routes/api.php b/routes/api.php
index aa90773fe12e..01136609845e 100644
--- a/routes/api.php
+++ b/routes/api.php
@@ -136,7 +136,6 @@ Route::group(['middleware' => ['throttle:api', 'api_db', 'token_auth', 'locale']
Route::post('charts/chart_summary', [ChartController::class, 'chart_summary'])->name('chart.chart_summary');
Route::post('claim_license', [LicenseController::class, 'index'])->name('license.index');
- Route::post('v5_claim_license', [LicenseController::class, 'v5ClaimLicense'])->name('license.v5_claim_license');
Route::resource('clients', ClientController::class); // name = (clients. index / create / show / update / destroy / edit
Route::put('clients/{client}/upload', [ClientController::class, 'upload'])->name('clients.upload');
diff --git a/tests/Feature/Scheduler/ScheduleEntityTest.php b/tests/Feature/Scheduler/ScheduleEntityTest.php
new file mode 100644
index 000000000000..76a4ddb02522
--- /dev/null
+++ b/tests/Feature/Scheduler/ScheduleEntityTest.php
@@ -0,0 +1,128 @@
+faker = \Faker\Factory::create();
+
+ Model::reguard();
+
+ $this->makeTestData();
+
+ $this->withoutMiddleware(
+ ThrottleRequests::class
+ );
+ }
+
+ public function testSchedulerStore()
+ {
+
+ $data = [
+ 'name' => 'A test entity email scheduler',
+ 'frequency_id' => RecurringInvoice::FREQUENCY_MONTHLY,
+ 'next_run' => now()->format('Y-m-d'),
+ 'template' => 'schedule_entity',
+ 'parameters' => [
+ 'entity' => 'invoice',
+ 'entity_id' => $this->invoice->hashed_id,
+ ],
+ ];
+
+ $response = $this->withHeaders([
+ 'X-API-SECRET' => config('ninja.api_secret'),
+ 'X-API-TOKEN' => $this->token,
+ ])->postJson('/api/v1/task_schedulers', $data);
+
+ $response->assertStatus(200);
+
+ }
+
+
+ public function testSchedulerStore2()
+ {
+
+ $data = [
+ 'name' => 'A test entity email scheduler',
+ 'frequency_id' => 0,
+ 'next_run' => now()->format('Y-m-d'),
+ 'template' => 'schedule_entity',
+ 'parameters' => [
+ 'entity' => 'invoice',
+ 'entity_id' => $this->invoice->hashed_id,
+ ],
+ ];
+
+ $response = $this->withHeaders([
+ 'X-API-SECRET' => config('ninja.api_secret'),
+ 'X-API-TOKEN' => $this->token,
+ ])->postJson('/api/v1/task_schedulers', $data);
+
+ $response->assertStatus(200);
+
+ }
+
+ public function testSchedulerStore4()
+ {
+
+ $data = [
+ 'name' => 'A test entity email scheduler',
+ 'next_run' => now()->format('Y-m-d'),
+ 'template' => 'schedule_entity',
+ 'parameters' => [
+ 'entity' => 'invoice',
+ 'entity_id' => $this->invoice->hashed_id,
+ ],
+ ];
+
+ $response = $this->withHeaders([
+ 'X-API-SECRET' => config('ninja.api_secret'),
+ 'X-API-TOKEN' => $this->token,
+ ])->postJson('/api/v1/task_schedulers', $data);
+
+ $response->assertStatus(200);
+
+ }
+
+
+}
\ No newline at end of file
diff --git a/tests/Feature/Scheduler/SchedulerTest.php b/tests/Feature/Scheduler/SchedulerTest.php
index 955f285b3718..5248b221942e 100644
--- a/tests/Feature/Scheduler/SchedulerTest.php
+++ b/tests/Feature/Scheduler/SchedulerTest.php
@@ -25,6 +25,7 @@ use App\DataMapper\Schedule\EmailStatement;
use App\Services\Scheduler\SchedulerService;
use Illuminate\Validation\ValidationException;
use Illuminate\Foundation\Testing\WithoutEvents;
+use App\Services\Scheduler\EmailStatementService;
use Illuminate\Routing\Middleware\ThrottleRequests;
/**
@@ -399,12 +400,13 @@ class SchedulerTest extends TestCase
$scheduler->fill($data);
$scheduler->save();
+ $scheduler->calculateNextRun();
- $service_object = new SchedulerService($scheduler);
+ // $service_object = new SchedulerService($scheduler);
- $reflectionMethod = new \ReflectionMethod(SchedulerService::class, 'calculateNextRun');
- $reflectionMethod->setAccessible(true);
- $method = $reflectionMethod->invoke(new SchedulerService($scheduler));
+ // $reflectionMethod = new \ReflectionMethod(SchedulerService::class, 'calculateNextRun');
+ // $reflectionMethod->setAccessible(true);
+ // $method = $reflectionMethod->invoke(new SchedulerService($scheduler));
$scheduler->fresh();
$offset = $this->company->timezone_offset();
@@ -434,12 +436,13 @@ class SchedulerTest extends TestCase
$scheduler->fill($data);
$scheduler->save();
+ $scheduler->calculateNextRun();
- $service_object = new SchedulerService($scheduler);
+ $service_object = new EmailStatementService($scheduler);
- $reflectionMethod = new \ReflectionMethod(SchedulerService::class, 'calculateStartAndEndDates');
+ $reflectionMethod = new \ReflectionMethod(EmailStatementService::class, 'calculateStartAndEndDates');
$reflectionMethod->setAccessible(true);
- $method = $reflectionMethod->invoke(new SchedulerService($scheduler));
+ $method = $reflectionMethod->invoke(new EmailStatementService($scheduler));
$this->assertIsArray($method);
@@ -469,16 +472,11 @@ class SchedulerTest extends TestCase
$scheduler->fill($data);
$scheduler->save();
- $service_object = new SchedulerService($scheduler);
+ $service_object = new EmailStatementService($scheduler);
- // $reflection = new \ReflectionClass(get_class($service_object));
- // $method = $reflection->getMethod('calculateStatementProperties');
- // $method->setAccessible(true);
- // $method->invokeArgs($service_object, []);
-
- $reflectionMethod = new \ReflectionMethod(SchedulerService::class, 'calculateStatementProperties');
+ $reflectionMethod = new \ReflectionMethod(EmailStatementService::class, 'calculateStatementProperties');
$reflectionMethod->setAccessible(true);
- $method = $reflectionMethod->invoke(new SchedulerService($scheduler)); // 'baz'
+ $method = $reflectionMethod->invoke(new EmailStatementService($scheduler)); // 'baz'
$this->assertIsArray($method);
diff --git a/tests/Unit/Tax/ProcessRuleTest.php b/tests/Unit/Tax/ProcessRuleTest.php
new file mode 100644
index 000000000000..f8c00ce48bb0
--- /dev/null
+++ b/tests/Unit/Tax/ProcessRuleTest.php
@@ -0,0 +1,154 @@
+withoutMiddleware(
+ ThrottleRequests::class
+ );
+
+ $this->withoutExceptionHandling();
+
+ $this->makeTestData();
+ }
+
+ public function testCorrectRuleInit()
+ {
+
+ $settings = CompanySettings::defaults();
+ $settings->country_id = '276'; // germany
+
+ $company = Company::factory()->create([
+ 'account_id' => $this->account->id,
+ 'settings' => $settings
+ ]);
+
+ $client = Client::factory()->create([
+ 'user_id' => $this->user->id,
+ 'company_id' => $company->id,
+ 'country_id' => 276,
+ 'shipping_country_id' => 276,
+ ]);
+
+ $process = new ProcessRule($company, $client);
+ $process->run();
+
+ $this->assertEquals('de', $process->getVendorCountryCode());
+
+ $this->assertEquals('de', $process->getClientCountryCode());
+
+ $this->assertFalse($process->hasValidVatNumber());
+
+ $this->assertInstanceOf(Rule::class, $process->rule);
+
+ $this->assertEquals(19, $process->getVatRate());
+
+ $this->assertEquals(7, $process->getVatReducedRate());
+
+
+ }
+
+ public function testEuCorrectRuleInit()
+ {
+
+ $settings = CompanySettings::defaults();
+ $settings->country_id = '276'; // germany
+
+ $company = Company::factory()->create([
+ 'account_id' => $this->account->id,
+ 'settings' => $settings
+ ]);
+
+ $client = Client::factory()->create([
+ 'user_id' => $this->user->id,
+ 'company_id' => $company->id,
+ 'country_id' => 56,
+ 'shipping_country_id' => 56,
+ ]);
+
+ $process = new ProcessRule($company, $client);
+ $process->run();
+
+ $this->assertEquals('de', $process->getVendorCountryCode());
+
+ $this->assertEquals('be', $process->getClientCountryCode());
+
+ $this->assertFalse($process->hasValidVatNumber());
+
+ $this->assertInstanceOf(Rule::class, $process->rule);
+
+ $this->assertEquals(21, $process->getVatRate());
+
+ $this->assertEquals(7, $process->getVatReducedRate());
+
+
+ }
+
+ public function testForeignCorrectRuleInit()
+ {
+
+ $settings = CompanySettings::defaults();
+ $settings->country_id = '276'; // germany
+
+ $company = Company::factory()->create([
+ 'account_id' => $this->account->id,
+ 'settings' => $settings
+ ]);
+
+ $client = Client::factory()->create([
+ 'user_id' => $this->user->id,
+ 'company_id' => $company->id,
+ 'country_id' => 840,
+ 'shipping_country_id' => 840,
+ ]);
+
+ $process = new ProcessRule($company, $client);
+ $process->run();
+
+ $this->assertEquals('de', $process->getVendorCountryCode());
+
+ $this->assertEquals('us', $process->getClientCountryCode());
+
+ $this->assertFalse($process->hasValidVatNumber());
+
+ $this->assertInstanceOf(Rule::class, $process->rule);
+
+ $this->assertEquals(0, $process->getVatRate());
+
+ $this->assertEquals(0, $process->getVatReducedRate());
+
+
+ }
+
+
+}
diff --git a/tests/Unit/Tax/SumTaxTest.php b/tests/Unit/Tax/SumTaxTest.php
new file mode 100644
index 000000000000..73cfcc06ffa2
--- /dev/null
+++ b/tests/Unit/Tax/SumTaxTest.php
@@ -0,0 +1,114 @@
+ [
+ [
+ "geoPostalCode" => "92582",
+ "geoCity" => "SAN JACINTO",
+ "geoCounty" => "RIVERSIDE",
+ "geoState" => "CA",
+ "taxSales" => 0.0875,
+ "taxUse" => 0.0875, // tax amount where destination does not charge sales tax, but origin does
+ "txbService" => "N", // whether services are taxed in this locale
+ "txbFreight" => "N", // whether freight is taxes in this locale
+ "stateSalesTax" => 0.06,
+ "stateUseTax" => 0.06,
+ "citySalesTax" => 0.01,
+ "cityUseTax" => 0.01,
+ "cityTaxCode" => "874",
+ "countySalesTax" => 0.0025,
+ "countyUseTax" => 0.0025,
+ "countyTaxCode" => "",
+ "districtSalesTax" => 0.015,
+ "districtUseTax" => 0.015,
+ "district1Code" => "26",
+ "district1SalesTax" => 0,
+ "district1UseTax" => 0,
+ "district2Code" => "26",
+ "district2SalesTax" => 0.005,
+ "district2UseTax" => 0.005,
+ "district3Code" => "",
+ "district3SalesTax" => 0,
+ "district3UseTax" => 0,
+ "district4Code" => "33",
+ "district4SalesTax" => 0.01,
+ "district4UseTax" => 0.01,
+ "district5Code" => "",
+ "district5SalesTax" => 0,
+ "district5UseTax" => 0, //district1-5 portion of the district tax
+ "originDestination" => "D", //location where this is taxed origin/destination/null
+ ],
+ ]
+ ];
+
+
+ protected function setUp() :void
+ {
+ parent::setUp();
+
+ $this->withoutMiddleware(
+ ThrottleRequests::class
+ );
+
+ $this->withoutExceptionHandling();
+
+ // $this->makeTestData();
+ }
+
+ public function testSumOfInvoice()
+ {
+
+ $this->assertEquals("CA", $this->response['results'][0]['geoState']);
+
+ }
+
+ public function testSumOfTaxes()
+ {
+ $sum =
+ $this->response['results'][0]['stateSalesTax'] +
+ // $this->response['results'][0]['stateUseTax'] +
+ $this->response['results'][0]['citySalesTax'] +
+ // $this->response['results'][0]['cityUseTax'] +
+ $this->response['results'][0]['countySalesTax'] +
+ // $this->response['results'][0]['countyUseTax'] +
+ $this->response['results'][0]['districtSalesTax'];
+ // // $this->response['results'][0]['districtUseTax'] +
+ // $this->response['results'][0]['district1SalesTax'] +
+ // // $this->response['results'][0]['district1UseTax'] +
+ // $this->response['results'][0]['district2SalesTax'] +
+ // // $this->response['results'][0]['district2UseTax'] +
+ // $this->response['results'][0]['district3SalesTax'] +
+ // // $this->response['results'][0]['district3UseTax'] +
+ // $this->response['results'][0]['district4SalesTax'] +
+ // // $this->response['results'][0]['district4UseTax'] +
+ // $this->response['results'][0]['district5SalesTax'];
+ // $this->response['results'][0]['district5UseTax'];
+
+ $this->assertEquals(0.0875, $sum);
+ }
+
+}
\ No newline at end of file
diff --git a/tests/Unit/Tax/VatNumberTest.php b/tests/Unit/Tax/VatNumberTest.php
new file mode 100644
index 000000000000..50135007d359
--- /dev/null
+++ b/tests/Unit/Tax/VatNumberTest.php
@@ -0,0 +1,52 @@
+run();
+
+ $this->assertFalse($result->isValid());
+ }
+
+ public function testValidVatNumber()
+ {
+ // Usage example
+ $country_code = "AT"; // Ireland
+ $vat_number = "U12345678"; // Example VAT number
+ $result = '';
+
+ $vat_checker = new VatNumberCheck($vat_number, $country_code);
+ $result = $vat_checker->run();
+
+ $this->assertFalse($result->isValid());
+ }
+}