diff --git a/VERSION.txt b/VERSION.txt index d47c52353191..5c637b26e9b1 100644 --- a/VERSION.txt +++ b/VERSION.txt @@ -1 +1 @@ -5.8.36 \ No newline at end of file +5.8.37 \ No newline at end of file diff --git a/app/Helpers/SwissQr/SwissQrGenerator.php b/app/Helpers/SwissQr/SwissQrGenerator.php index 2ccc73ed3c4b..86ed38330aa2 100644 --- a/app/Helpers/SwissQr/SwissQrGenerator.php +++ b/app/Helpers/SwissQr/SwissQrGenerator.php @@ -159,7 +159,7 @@ class SwissQrGenerator // Optionally, add some human-readable information about what the bill is for. $qrBill->setAdditionalInformation( QrBill\DataGroup\Element\AdditionalInformation::create( - $this->invoice->public_notes ? substr($this->invoice->public_notes, 0, 139) : ctrans('texts.invoice_number_placeholder', ['invoice' => $this->invoice->number]) + $this->invoice->public_notes ? substr(strip_tags($this->invoice->public_notes), 0, 139) : ctrans('texts.invoice_number_placeholder', ['invoice' => $this->invoice->number]) ) ); diff --git a/app/Http/Requests/Client/UpdateClientRequest.php b/app/Http/Requests/Client/UpdateClientRequest.php index b0307d312da3..3ffea3250f05 100644 --- a/app/Http/Requests/Client/UpdateClientRequest.php +++ b/app/Http/Requests/Client/UpdateClientRequest.php @@ -63,7 +63,7 @@ class UpdateClientRequest extends Request $rules['country_id'] = 'integer|nullable|exists:countries,id'; $rules['shipping_country_id'] = 'integer|nullable|exists:countries,id'; $rules['classification'] = 'bail|sometimes|nullable|in:individual,business,company,partnership,trust,charity,government,other'; - $rules['id_number'] = ['sometimes', 'bail', Rule::unique('clients')->where('company_id', $user->company()->id)->ignore($this->client->id)]; + $rules['id_number'] = ['sometimes', 'bail', 'nullable', Rule::unique('clients')->where('company_id', $user->company()->id)->ignore($this->client->id)]; $rules['number'] = ['sometimes', 'bail', Rule::unique('clients')->where('company_id', $user->company()->id)->ignore($this->client->id)]; $rules['settings'] = new ValidClientGroupSettingsRule(); diff --git a/config/ninja.php b/config/ninja.php index 76621119f951..47ecd5b1aa42 100644 --- a/config/ninja.php +++ b/config/ninja.php @@ -17,8 +17,8 @@ return [ 'require_https' => env('REQUIRE_HTTPS', true), 'app_url' => rtrim(env('APP_URL', ''), '/'), 'app_domain' => env('APP_DOMAIN', 'invoicing.co'), - 'app_version' => env('APP_VERSION', '5.8.36'), - 'app_tag' => env('APP_TAG', '5.8.36'), + 'app_version' => env('APP_VERSION', '5.8.37'), + 'app_tag' => env('APP_TAG', '5.8.37'), 'minimum_client_version' => '5.0.16', 'terms_version' => '1.0.1', 'api_secret' => env('API_SECRET', false), diff --git a/database/migrations/2024_03_14_201844_adjust_discount_column_max_resolution.php b/database/migrations/2024_03_14_201844_adjust_discount_column_max_resolution.php new file mode 100644 index 000000000000..3aa0099e3cf0 --- /dev/null +++ b/database/migrations/2024_03_14_201844_adjust_discount_column_max_resolution.php @@ -0,0 +1,45 @@ +decimal('discount', 20, 6)->default(0)->change(); + }); + + + Schema::table('credits', function (Blueprint $table) { + $table->decimal('discount', 20, 6)->default(0)->change(); + }); + + Schema::table('quotes', function (Blueprint $table) { + $table->decimal('discount', 20, 6)->default(0)->change(); + }); + + Schema::table('purchase_orders', function (Blueprint $table) { + $table->decimal('discount', 20, 6)->default(0)->change(); + }); + + Schema::table('recurring_invoices', function (Blueprint $table) { + $table->decimal('discount', 20, 6)->default(0)->change(); + }); + + } + + /** + * Reverse the migrations. + */ + public function down(): void + { + // + } +}; diff --git a/tests/Feature/InvoiceTest.php b/tests/Feature/InvoiceTest.php index d41a23600555..ff0c79bf41c1 100644 --- a/tests/Feature/InvoiceTest.php +++ b/tests/Feature/InvoiceTest.php @@ -20,6 +20,7 @@ use App\Models\Subscription; use App\Models\ClientContact; use App\Utils\Traits\MakesHash; use App\Models\RecurringInvoice; +use App\Factory\InvoiceItemFactory; use App\Helpers\Invoice\InvoiceSum; use App\Repositories\InvoiceRepository; use Illuminate\Database\Eloquent\Model; @@ -51,6 +52,116 @@ class InvoiceTest extends TestCase $this->makeTestData(); } + public function testMaxDiscount() + { + + + $line_items = []; + + $item = InvoiceItemFactory::create(); + $item->quantity = 1; + $item->cost = 100000000; + $item->type_id = '1'; + + $line_items[] = $item; + + $data = [ + 'status_id' => 1, + 'number' => '', + 'discount' => 0, + 'is_amount_discount' => 1, + 'po_number' => '3434343', + 'public_notes' => 'notes', + 'is_deleted' => 0, + 'custom_value1' => 0, + 'custom_value2' => 0, + 'custom_value3' => 0, + 'custom_value4' => 0, + 'client_id' => $this->client->hashed_id, + 'line_items' => $line_items, + ]; + + $response = $this->withHeaders([ + 'X-API-SECRET' => config('ninja.api_secret'), + 'X-API-TOKEN' => $this->token, + ])->postJson('/api/v1/invoices?mark_sent=true',$data) + ->assertStatus(200); + + $arr = $response->json(); + + $this->assertEquals(2, $arr['data']['status_id']); + $this->assertEquals(100000000, $arr['data']['amount']); + $this->assertEquals(100000000, $arr['data']['balance']); + + $data = [ + 'status_id' => 1, + 'number' => '', + 'discount' => 100000000, + 'is_amount_discount' => 1, + 'po_number' => '3434343', + 'public_notes' => 'notes', + 'is_deleted' => 0, + 'custom_value1' => 0, + 'custom_value2' => 0, + 'custom_value3' => 0, + 'custom_value4' => 0, + 'client_id' => $this->client->hashed_id, + 'line_items' => $line_items, + ]; + + $response = $this->withHeaders([ + 'X-API-SECRET' => config('ninja.api_secret'), + 'X-API-TOKEN' => $this->token, + ])->postJson('/api/v1/invoices?mark_sent=true', $data) + ->assertStatus(200); + + $arr = $response->json(); + + $this->assertEquals(2, $arr['data']['status_id']); + $this->assertEquals(0, $arr['data']['amount']); + $this->assertEquals(0, $arr['data']['balance']); + $this->assertEquals(100000000, $arr['data']['discount']); + + $line_items = []; + $item = InvoiceItemFactory::create(); + $item->quantity = 1; + $item->cost = 100000000; + $item->discount = 100000000; + $item->type_id = '1'; + + $line_items[] = $item; + + $data = [ + 'status_id' => 1, + 'number' => '', + 'discount' => 0, + 'is_amount_discount' => 1, + 'po_number' => '3434343', + 'public_notes' => 'notes', + 'is_deleted' => 0, + 'custom_value1' => 0, + 'custom_value2' => 0, + 'custom_value3' => 0, + 'custom_value4' => 0, + 'client_id' => $this->client->hashed_id, + 'line_items' => $line_items, + ]; + + $response = $this->withHeaders([ + 'X-API-SECRET' => config('ninja.api_secret'), + 'X-API-TOKEN' => $this->token, + ])->postJson('/api/v1/invoices?mark_sent=true', $data) + ->assertStatus(200); + + $arr = $response->json(); + + $this->assertEquals(2, $arr['data']['status_id']); + $this->assertEquals(0, $arr['data']['amount']); + $this->assertEquals(0, $arr['data']['balance']); + + + } + public function testInvoicePaymentLinkMutation() {