Skip to content

Commit

Permalink
Merge pull request #17 from Laravel-Lang/1.x
Browse files Browse the repository at this point in the history
Added new `LocalizationByModel` middleware
  • Loading branch information
andrey-helldar authored Jun 20, 2024
2 parents fa242a9 + c08eccf commit cab7708
Show file tree
Hide file tree
Showing 13 changed files with 293 additions and 2 deletions.
2 changes: 1 addition & 1 deletion composer.json
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@
"illuminate/http": "^10.0 || ^11.0",
"illuminate/routing": "^10.0 || ^11.0",
"illuminate/support": "^10.0 || ^11.0",
"laravel-lang/config": "^1.5",
"laravel-lang/config": "^1.6",
"laravel-lang/locales": "^2.8"
},
"require-dev": {
Expand Down
3 changes: 3 additions & 0 deletions phpunit.xml
Original file line number Diff line number Diff line change
Expand Up @@ -20,5 +20,8 @@

<env name="SESSION_DRIVER" value="array" />
<env name="CACHE_STORE" value="array" />

<env name="DB_CONNECTION" value="testing" />
<env name="DB_DATABASE" value=":memory:" />
</php>
</phpunit>
48 changes: 48 additions & 0 deletions src/Middlewares/LocalizationByModel.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
<?php

declare(strict_types=1);

namespace LaravelLang\Routes\Middlewares;

use Illuminate\Database\Eloquent\Model;
use Illuminate\Http\Request;

class LocalizationByModel extends Middleware
{
public function __construct(
protected ?string $guard = null,
) {}

protected function detect(Request $request): bool|float|int|string|null
{
if ($this->has($user = $this->user($request))) {
return $user->getAttribute($this->attribute());
}

return null;
}

protected function has(?Model $user): bool
{
return $user && $this->hasAttribute($user);
}

protected function user(Request $request): ?Model
{
return $request->user($this->guard);
}

protected function attribute(): string
{
return $this->names()->column;
}

protected function hasAttribute(Model $user): bool
{
if (method_exists($user, 'hasAttribute')) {
return $user->hasAttribute($this->attribute());
}

return array_key_exists($this->attribute(), $user->getAttributes());
}
}
3 changes: 3 additions & 0 deletions src/Services/Route.php
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
use LaravelLang\Routes\Helpers\Route as RouteName;
use LaravelLang\Routes\Middlewares\LocalizationByCookie;
use LaravelLang\Routes\Middlewares\LocalizationByHeader;
use LaravelLang\Routes\Middlewares\LocalizationByModel;
use LaravelLang\Routes\Middlewares\LocalizationByParameterPrefix;
use LaravelLang\Routes\Middlewares\LocalizationBySession;

Expand All @@ -23,6 +24,7 @@ public function group(Closure $callback): void
LocalizationByCookie::class,
LocalizationByHeader::class,
LocalizationBySession::class,
LocalizationByModel::class,
])->group($callback);

BaseRoute::prefix('{' . $this->names()->parameter . '}')
Expand All @@ -32,6 +34,7 @@ public function group(Closure $callback): void
LocalizationByCookie::class,
LocalizationByHeader::class,
LocalizationBySession::class,
LocalizationByModel::class,
])->group($callback);
}
}
12 changes: 12 additions & 0 deletions tests/Concerns/Routes.php
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
use LaravelLang\Routes\Facades\LocalizationRoute;
use LaravelLang\Routes\Middlewares\LocalizationByCookie;
use LaravelLang\Routes\Middlewares\LocalizationByHeader;
use LaravelLang\Routes\Middlewares\LocalizationByModel;
use LaravelLang\Routes\Middlewares\LocalizationByParameter;
use LaravelLang\Routes\Middlewares\LocalizationByParameterWithRedirect;
use LaravelLang\Routes\Middlewares\LocalizationBySession;
Expand Down Expand Up @@ -53,13 +54,24 @@ public function setUpRoutes(): void
->get('session/{foo}', $this->jsonResponse())
->name('via.session');

app('router')
->middleware(LocalizationByModel::class)
->get('model/default/{foo}', $this->jsonResponse())
->name('via.model.default');

app('router')
->middleware(LocalizationByModel::class . ':foo')
->get('model/guard/{foo}', $this->jsonResponse())
->name('via.model.guard');

app('router')
->middleware([
LocalizationByParameter::class,
LocalizationByParameterWithRedirect::class,
LocalizationByHeader::class,
LocalizationByCookie::class,
LocalizationBySession::class,
LocalizationByModel::class,
])
->get('clean/{foo}', $this->jsonResponse())
->name('clean');
Expand Down
68 changes: 68 additions & 0 deletions tests/Feature/Middlewares/ModelAuthorizedGuardTest.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
<?php

declare(strict_types=1);

use Tests\Constants\LocaleValue;

use function Pest\Laravel\actingAs;
use function Pest\Laravel\getJson;

test('main locale', function () {
actingAs(fakeUser(), 'foo');

$foo = 'test';

getJson(route('via.model.guard', compact('foo')))
->assertSuccessful()
->assertJsonPath($foo, LocaleValue::TranslationFrench);

assertEventNotDispatched();
});

test('aliased locale', function (string $locale) {
actingAs(fakeUser($locale));

$foo = 'test';

getJson(route('via.model.guard', compact('foo', 'locale')))
->assertSuccessful()
->assertJsonPath($foo, LocaleValue::TranslationGerman);

assertEventDispatched();
})->with('aliased-locales');

test('empty locale', function (int|string|null $locale) {
actingAs(fakeUser($locale));

$foo = 'test';

getJson(route('via.model.guard', compact('foo', 'locale')))
->assertSuccessful()
->assertJsonPath($foo, LocaleValue::TranslationFrench);

assertEventNotDispatched();
})->with('empty-locales');

test('uninstalled locale', function (string $locale) {
actingAs(fakeUser($locale));

$foo = 'test';

getJson(route('via.model.guard', compact('foo', 'locale')))
->assertSuccessful()
->assertJsonPath($foo, LocaleValue::TranslationFrench);

assertEventDispatched();
})->with('uninstalled-locales');

test('unknown locale', function (int|string $locale) {
actingAs(fakeUser($locale));

$foo = 'test';

getJson(route('via.model.guard', compact('foo', 'locale')))
->assertSuccessful()
->assertJsonPath($foo, LocaleValue::TranslationFrench);

assertEventDispatched();
})->with('unknown-locales');
68 changes: 68 additions & 0 deletions tests/Feature/Middlewares/ModelAuthorizedTest.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
<?php

declare(strict_types=1);

use Tests\Constants\LocaleValue;

use function Pest\Laravel\actingAs;
use function Pest\Laravel\getJson;

test('main locale', function () {
actingAs(fakeUser());

$foo = 'test';

getJson(route('via.model.default', compact('foo')))
->assertSuccessful()
->assertJsonPath($foo, LocaleValue::TranslationFrench);

assertEventNotDispatched();
});

test('aliased locale', function (string $locale) {
actingAs(fakeUser($locale));

$foo = 'test';

getJson(route('via.model.default', compact('foo', 'locale')))
->assertSuccessful()
->assertJsonPath($foo, LocaleValue::TranslationGerman);

assertEventDispatched();
})->with('aliased-locales');

test('empty locale', function (int|string|null $locale) {
actingAs(fakeUser($locale));

$foo = 'test';

getJson(route('via.model.default', compact('foo', 'locale')))
->assertSuccessful()
->assertJsonPath($foo, LocaleValue::TranslationFrench);

assertEventNotDispatched();
})->with('empty-locales');

test('uninstalled locale', function (string $locale) {
actingAs(fakeUser($locale));

$foo = 'test';

getJson(route('via.model.default', compact('foo', 'locale')))
->assertSuccessful()
->assertJsonPath($foo, LocaleValue::TranslationFrench);

assertEventDispatched();
})->with('uninstalled-locales');

test('unknown locale', function (int|string $locale) {
actingAs(fakeUser($locale));

$foo = 'test';

getJson(route('via.model.default', compact('foo', 'locale')))
->assertSuccessful()
->assertJsonPath($foo, LocaleValue::TranslationFrench);

assertEventDispatched();
})->with('unknown-locales');
27 changes: 27 additions & 0 deletions tests/Feature/Middlewares/ModelUnauthorized.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
<?php

declare(strict_types=1);

use Tests\Constants\LocaleValue;

use function Pest\Laravel\getJson;

test('with guard', function () {
$foo = 'test';

getJson(route('via.model.guard', compact('foo')))
->assertSuccessful()
->assertJsonPath($foo, LocaleValue::TranslationFrench);

assertEventNotDispatched();
});

test('without guard', function () {
$foo = 'test';

getJson(route('via.model.default', compact('foo')))
->assertSuccessful()
->assertJsonPath($foo, LocaleValue::TranslationFrench);

assertEventNotDispatched();
});
14 changes: 14 additions & 0 deletions tests/Fixtures/Models/User.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
<?php

declare(strict_types=1);

namespace Tests\Fixtures\Models;

use Illuminate\Foundation\Auth\User as Authenticatable;

class User extends Authenticatable
{
protected $fillable = [
'locale',
];
}
12 changes: 12 additions & 0 deletions tests/Helpers/Models.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
<?php

declare(strict_types=1);

use Tests\Fixtures\Models\User;

function fakeUser(int|string|null $locale = null): User
{
return User::create([
'locale' => $locale,
]);
}
3 changes: 2 additions & 1 deletion tests/Pest.php
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
<?php

use Illuminate\Foundation\Testing\DatabaseTransactions;
use Illuminate\Support\Facades\Event;

uses(Tests\TestCase::class)
uses(Tests\TestCase::class, DatabaseTransactions::class)
->beforeEach(fn () => Event::fake())
->in('Feature', 'Unit');
10 changes: 10 additions & 0 deletions tests/TestCase.php
Original file line number Diff line number Diff line change
Expand Up @@ -32,8 +32,18 @@ protected function defineEnvironment($app): void

$config->set('app.locale', LocaleValue::LocaleMain);

$config->set('auth.guards.foo', [
'driver' => 'session',
'provider' => 'users',
]);

$config->set(Name::Shared() . '.aliases', [
LocaleValue::LocaleAliasParent => LocaleValue::LocaleAlias,
]);
}

protected function defineDatabaseMigrations(): void
{
$this->loadMigrationsFrom(__DIR__ . '/database/migrations');
}
}
25 changes: 25 additions & 0 deletions tests/database/migrations/2024_06_20_000000_create_users_table.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
<?php

declare(strict_types=1);

use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

return new class extends Migration {
public function up(): void
{
Schema::create('users', function (Blueprint $table) {
$table->id();

$table->string('locale')->nullable();

$table->timestamps();
});
}

public function down(): void
{
Schema::dropIfExists('users');
}
};

0 comments on commit cab7708

Please sign in to comment.