From 002e4a7aabe7171d651b0a59afe8300f1af5140c Mon Sep 17 00:00:00 2001 From: David Bomba Date: Wed, 2 Oct 2024 10:05:28 +1000 Subject: [PATCH 1/4] Fixes for static analysis --- app/Console/Commands/CheckDb.php | 143 ------------------ app/Http/Middleware/SetWebDb.php | 9 ++ .../Middleware/ThrottleRequestsWithPredis.php | 18 ++- app/Models/Account.php | 4 +- composer.json | 2 +- config/database.php | 28 +--- phpstan.neon | 2 + 7 files changed, 35 insertions(+), 171 deletions(-) delete mode 100644 app/Console/Commands/CheckDb.php diff --git a/app/Console/Commands/CheckDb.php b/app/Console/Commands/CheckDb.php deleted file mode 100644 index 31a846470dc1..000000000000 --- a/app/Console/Commands/CheckDb.php +++ /dev/null @@ -1,143 +0,0 @@ -LogMessage('Checking - V5_DB1'); - - foreach ($this->entities as $entity) { - $count_db_1 = $entity::on('db-ninja-01')->count(); - $count_db_2 = $entity::on('db-ninja-02a')->count(); - - $diff = $count_db_1 - $count_db_2; - - if ($diff != 0) { - $this->logMessage("{$entity} DB1: {$count_db_1} - DB2: {$count_db_2} - diff = {$diff}"); - } - } - - $this->LogMessage('Checking - V5_DB2'); - - foreach ($this->entities as $entity) { - $count_db_1 = $entity::on('db-ninja-02')->count(); - $count_db_2 = $entity::on('db-ninja-01a')->count(); - - $diff = $count_db_1 - $count_db_2; - - if ($diff != 0) { - $this->logMessage("{$entity} DB1: {$count_db_1} - DB2: {$count_db_2} - diff = {$diff}"); - } - } - } - - private function logMessage($str) - { - $str = date('Y-m-d h:i:s').' '.$str; - $this->info($str); - $this->log .= $str."\n"; - } -} diff --git a/app/Http/Middleware/SetWebDb.php b/app/Http/Middleware/SetWebDb.php index edf3993c906d..a86004841000 100644 --- a/app/Http/Middleware/SetWebDb.php +++ b/app/Http/Middleware/SetWebDb.php @@ -1,4 +1,13 @@ redis = \Illuminate\Support\Facades\Redis::connection('sentinel-cache'); + parent::__construct($limiter); /** @phpstan-ignore-line */ + + /** @phpstan-ignore-next-line */ + $this->redis = \Illuminate\Support\Facades\Redis::connection('sentinel-cache'); /** @phpstan-ignore-line */ } /** diff --git a/app/Models/Account.php b/app/Models/Account.php index 001b05100dcc..9a07d271c8b3 100644 --- a/app/Models/Account.php +++ b/app/Models/Account.php @@ -55,9 +55,9 @@ use Laracasts\Presenter\PresentableTrait; * @property string|null $referral_code * @property int|null $created_at * @property int|null $updated_at - * @property int $is_scheduler_running + * @property bool $is_scheduler_running * @property int|null $trial_duration - * @property int $is_onboarding + * @property bool $is_onboarding * @property object|null $onboarding * @property bool $is_migrated * @property string|null $platform diff --git a/composer.json b/composer.json index d188feead9a7..dc06712b3342 100644 --- a/composer.json +++ b/composer.json @@ -211,4 +211,4 @@ ], "minimum-stability": "dev", "prefer-stable": true -} +} \ No newline at end of file diff --git a/config/database.php b/config/database.php index da5827229278..1cfcfd61fde3 100644 --- a/config/database.php +++ b/config/database.php @@ -98,22 +98,6 @@ return [ 'options' => [], ], - 'db-ninja-01a' => [ - 'driver' => 'mysql', - 'host' => env('DB_HOST1', env('DB_HOST', '127.0.0.1')), - 'database' => env('DB_DATABASE2', env('DB_DATABASE', 'forge')), - 'username' => env('DB_USERNAME2', env('DB_USERNAME', 'forge')), - 'password' => env('DB_PASSWORD2', env('DB_PASSWORD', '')), - 'port' => env('DB_PORT1', env('DB_PORT', '3306')), - 'charset' => 'utf8mb4', - 'collation' => 'utf8mb4_unicode_ci', - 'prefix' => '', - 'prefix_indexes' => true, - 'strict' => env('DB_STRICT', false), - 'engine' => 'InnoDB ROW_FORMAT=DYNAMIC', - 'options' => [], - ], - 'db-ninja-02' => [ 'driver' => 'mysql', 'host' => env('DB_HOST2', env('DB_HOST', '127.0.0.1')), @@ -130,13 +114,13 @@ return [ 'options' => [], ], - 'db-ninja-02a' => [ + 'db-ninja-03' => [ 'driver' => 'mysql', - 'host' => env('DB_HOST2', env('DB_HOST', '127.0.0.1')), - 'database' => env('DB_DATABASE1', env('DB_DATABASE', 'forge')), - 'username' => env('DB_USERNAME1', env('DB_USERNAME', 'forge')), - 'password' => env('DB_PASSWORD1', env('DB_PASSWORD', '')), - 'port' => env('DB_PORT2', env('DB_PORT', '3306')), + 'host' => env('DB_HOST3', env('DB_HOST', '127.0.0.1')), + 'database' => env('DB_DATABASE3', env('DB_DATABASE', 'forge')), + 'username' => env('DB_USERNAME3', env('DB_USERNAME', 'forge')), + 'password' => env('DB_PASSWORD3', env('DB_PASSWORD', '')), + 'port' => env('DB_PORT3', env('DB_PORT', '3306')), 'charset' => 'utf8mb4', 'collation' => 'utf8mb4_unicode_ci', 'prefix' => '', diff --git a/phpstan.neon b/phpstan.neon index f0eab2441b2c..befa53f47f9e 100644 --- a/phpstan.neon +++ b/phpstan.neon @@ -6,6 +6,7 @@ parameters: level: 5 paths: - app + - Modules excludePaths: analyseAndScan: - 'vendor' @@ -16,6 +17,7 @@ parameters: - 'app/DataMapper/Analytics/*' - 'app/PaymentDrivers/Authorize/*' - 'app/PaymentDrivers/AuthorizePaymentDriver.php' + - 'app/Http/Middleware/ThrottleRequestsWithPredis.php' - 'app/Utils/Traits/*' universalObjectCratesClasses: - App\DataMapper\Tax\RuleInterface From 105b5c967bb70444c231958d9819cbf086a8666d Mon Sep 17 00:00:00 2001 From: David Bomba Date: Wed, 2 Oct 2024 10:59:14 +1000 Subject: [PATCH 2/4] Fixes for tests --- .../Requests/Product/StoreProductRequest.php | 9 ++++++++ tests/Feature/ProductTest.php | 21 +++++++++++++++++++ 2 files changed, 30 insertions(+) diff --git a/app/Http/Requests/Product/StoreProductRequest.php b/app/Http/Requests/Product/StoreProductRequest.php index 6984288cf859..ee8f588bcc6b 100644 --- a/app/Http/Requests/Product/StoreProductRequest.php +++ b/app/Http/Requests/Product/StoreProductRequest.php @@ -52,6 +52,11 @@ class StoreProductRequest extends Request $rules['stock_notification_threshold'] = 'sometimes|numeric'; $rules['stock_notification'] = 'sometimes|bool'; + $rules['tax_rate1'] = 'bail|sometimes|numeric'; + $rules['tax_rate2'] = 'bail|sometimes|numeric'; + $rules['tax_rate3'] = 'bail|sometimes|numeric'; + + return $rules; } @@ -67,6 +72,10 @@ class StoreProductRequest extends Request $input['assigned_user_id'] = $this->decodePrimaryKey($input['assigned_user_id']); } + $input['tax_name1'] = $input['tax_name1'] ?? ''; + $input['tax_name2'] = $input['tax_name2'] ?? ''; + $input['tax_name3'] = $input['tax_name3'] ?? ''; + $this->replace($input); } } diff --git a/tests/Feature/ProductTest.php b/tests/Feature/ProductTest.php index b394870de75b..7bdea3e817c8 100644 --- a/tests/Feature/ProductTest.php +++ b/tests/Feature/ProductTest.php @@ -53,6 +53,27 @@ class ProductTest extends TestCase } + public function testRequiredFields() + { + + $product = [ + 'cost' => 10, + 'vendor_id' => $this->vendor->hashed_id + ]; + + $response = $this->withHeaders([ + 'X-API-SECRET' => config('ninja.api_secret'), + 'X-API-TOKEN' => $this->token, + ])->postJson('/api/v1/products', $product) + ->assertStatus(200); + + $arr = $response->json(); + + $p = Product::find($this->decodePrimaryKey($arr['data']['id'])); + + $this->assertNull($p->vendor_id); + } + public function testProductCostMigration() { $items = []; From 040e8cf72f601c232dec54ead9522ddd3d90f620 Mon Sep 17 00:00:00 2001 From: David Bomba Date: Wed, 2 Oct 2024 11:20:36 +1000 Subject: [PATCH 3/4] Fixes for user validation --- app/Http/Requests/User/UpdateUserRequest.php | 8 +-- tests/Feature/UserTest.php | 68 ++++++++++++++++++++ 2 files changed, 72 insertions(+), 4 deletions(-) diff --git a/app/Http/Requests/User/UpdateUserRequest.php b/app/Http/Requests/User/UpdateUserRequest.php index f4e6d8d029d7..60331315d177 100644 --- a/app/Http/Requests/User/UpdateUserRequest.php +++ b/app/Http/Requests/User/UpdateUserRequest.php @@ -38,9 +38,7 @@ class UpdateUserRequest extends Request 'password' => 'nullable|string|min:6', ]; - if (isset($input['email'])) { - $rules['email'] = ['email', 'sometimes', new UniqueUserRule($this->user, $input['email'])]; - } + $rules['email'] = ['email', 'sometimes', new UniqueUserRule($this->user, $input['email'])]; if (Ninja::isHosted() && $this->phone_has_changed && $this->phone && isset($this->phone)) { $rules['phone'] = ['sometimes', 'bail', 'string', new HasValidPhoneNumber()]; @@ -53,9 +51,11 @@ class UpdateUserRequest extends Request { $input = $this->all(); - if (array_key_exists('email', $input)) { + if (isset($input['email']) && is_string($input['email']) && strlen($input['email']) > 2) { $input['email'] = trim($input['email']); } + elseif(isset($input['email'])) + $input['email'] = false; if (array_key_exists('first_name', $input)) { $input['first_name'] = strip_tags($input['first_name']); diff --git a/tests/Feature/UserTest.php b/tests/Feature/UserTest.php index 441fea7cefa5..1733a2d08ea4 100644 --- a/tests/Feature/UserTest.php +++ b/tests/Feature/UserTest.php @@ -109,6 +109,74 @@ class UserTest extends TestCase } + public function testValidEmailUpdate() + { + + $company_token = $this->mockAccount(); + $user = $company_token->user; + $user->load('company_user'); + + $data = $user->toArray(); + + $response = $this->withHeaders([ + 'X-API-SECRET' => config('ninja.api_secret'), + 'X-API-TOKEN' => $company_token->token, + 'X-API-PASSWORD' => 'ALongAndBriliantPassword', + ])->putJson('/api/v1/users/'.$user->hashed_id.'?include=company_user', $data); + + $response->assertStatus(200); + + } + + + public function testNullEmail() + { + + $company_token = $this->mockAccount(); + $user = $company_token->user; + $user->load('company_user'); + + $data = $user->toArray(); + $data['email'] = ''; + unset($data['password']); + + $response = $this->withHeaders([ + 'X-API-SECRET' => config('ninja.api_secret'), + 'X-API-TOKEN' => $company_token->token, + 'X-API-PASSWORD' => 'ALongAndBriliantPassword', + ])->putJson('/api/v1/users/'.$user->hashed_id.'?include=company_user', $data); + + $response->assertStatus(422); + + $data = $user->toArray(); + unset($data['password']); + + $response = $this->withHeaders([ + 'X-API-SECRET' => config('ninja.api_secret'), + 'X-API-TOKEN' => $company_token->token, + 'X-API-PASSWORD' => 'ALongAndBriliantPassword', + ])->putJson('/api/v1/users/'.$user->hashed_id.'?include=company_user', $data); + + $response->assertStatus(200); + + $data = $user->toArray(); + + $data['email'] = $this->faker->unique()->safeEmail(); + unset($data['password']); + + $response = $this->withHeaders([ + 'X-API-SECRET' => config('ninja.api_secret'), + 'X-API-TOKEN' => $company_token->token, + 'X-API-PASSWORD' => 'ALongAndBriliantPassword', + ])->putJson('/api/v1/users/'.$user->hashed_id.'?include=company_user', $data); + + $response->assertStatus(200); + + $arr = $response->json(); + $this->assertEquals($arr['data']['email'], $data['email']); + } + + public function testUserLocale() { $this->user->language_id = "13"; From 806652f5898f21b9c0e91a4d5d34512e24272685 Mon Sep 17 00:00:00 2001 From: David Bomba Date: Wed, 2 Oct 2024 11:22:10 +1000 Subject: [PATCH 4/4] Fixes for validation of company import when migrating --- app/Jobs/Util/Import.php | 2 ++ 1 file changed, 2 insertions(+) diff --git a/app/Jobs/Util/Import.php b/app/Jobs/Util/Import.php index 81bfa656c537..e1d0938c8812 100644 --- a/app/Jobs/Util/Import.php +++ b/app/Jobs/Util/Import.php @@ -433,6 +433,8 @@ class Import implements ShouldQueue $rules = (new UpdateCompanyRequest())->rules(); + unset($rules['expense_mailbox']); + $validator = Validator::make($data, $rules); if ($validator->fails()) {