Перво-наперво, я использую Hyn-Multi Tenant в моем приложении laravel 6. Там, где есть центральная база данных [connection = system], обрабатывает базу данных нескольких арендаторов. Пока этот пакет мне очень помог, но моему приложению нужна реализация паспорта для apis, которая не описана в пакете.
Однако есть другие учебные пособия , которые требуют реализацию паспорта для пакета Hyn. Я последовал за ними и смог создать токен доступа для каждого пользователя-арендатора.
Это моя конфигурация / аутентификация. php:
return [
'defaults' => [
'guard' => 'web',
'passwords' => 'system-users',
],
'guards' => [
'web' => [
'driver' => 'session',
'provider' => 'system',
],
'staff' => [
'driver' => 'session',
'provider' => 'staff',
],
'api' => [
'driver' => 'passport',
'provider' => 'staff',
'hash' => false,
],
'student' => [
'driver' => 'passport',
'provider' => 'student',
'hash' => false,
],
],
'providers' => [
'system' => [
'driver' => 'eloquent',
'model' => App\Models\System\User::class,
],
'staff' => [
'driver' => 'eloquent',
'model' => App\Models\Tenant\Staff::class,
],
'student' => [
'driver' => 'eloquent',
'model' => App\Models\Tenant\Student::class,
],
// 'users' => [
// 'driver' => 'database',
// 'table' => 'users',
// ],
],
В каждой модели моего арендатора используется UsesTenantConnection
trait
Это мое промежуточное ПО EnforceTenancy
<?php
namespace App\Http\Middleware;
use Closure;
use Illuminate\Support\Facades\Config;
class EnforceTenancy
{
/**
* Handle an incoming request.
*
* @param \Illuminate\Http\Request $request
* @param \Closure $next
* @return mixed
*/
public function handle($request, Closure $next)
{
Config::set('database.default', 'tenant');
return $next($request);
}
}
Это мой AuthServiceProvider. php
public function boot()
{
$this->registerPolicies();
Passport::routes(null, ['middleware' => 'tenancy.enforce']);
// FOLLOWING CODE IS HAVING PROBLEM
//Passport::useTokenModel(OAuthAccessToken::class);
//Passport::useClientModel(OAuthClient::class);
//Passport::useAuthCodeModel(OAuthCode::class);
//Passport::usePersonalAccessClientModel(OAuthPersonalAccessClient::class);
$this->commands([
\Laravel\Passport\Console\InstallCommand::class,
\Laravel\Passport\Console\ClientCommand::class,
\Laravel\Passport\Console\KeysCommand::class,
]);
\Laravel\Passport\Passport::tokensExpireIn(\Carbon\Carbon::now()->addMinutes(10));
\Laravel\Passport\Passport::refreshTokensExpireIn(\Carbon\Carbon::now()->addDays(1));
}
Пока все хорошо, теперь я собираюсь объяснить в пунктах,
- Когда я звоню
createToken('MyApp')
, я могу сгенерировать токен на базе данных арендатора, например:
if (Auth::guard('staff')->attempt(['email' => $request->email, 'password' => $request->password])) {
$user = Auth::guard('staff')->user();
$auth_tokens = $user->createToken('MyApp');
$access_token = $auth_tokens->accessToken;
...
}
, но для доступа к API, защищенному входом в систему, я отправляю носитель токен доступа в заголовке
window.axios
.get("/api/meta",{
headers: fetchAuthHeaders()
})
.then(response => {
if(true == response.data.status) {
var data = response.data.data;
this.school.name = data.school_meta.name;
this.school.logo = data.school_meta.logo;
} else{
alert(response.data.message);
}
})
API. php
Route::domain('{hostname}.lvh.me')->group(function () {
Route::middleware('tenant.exists')->group(function () {
Route::get('/get-oauth-secret', 'Tenant\MetaController@getOAuthData');
Route::post('validate-login','Tenant\AuthController@validateLogin');
Route::middleware(['auth:api'])->group(function (){
Route::get('meta','Tenant\AuthController@getMetaData'); //this api
});
});
});
Я получаю ответ как {"message":"Unauthenticated."}
Как только токен сгенерирован на шаге 1, я копирую этот токен и вставляю его в заголовочный раздел почтальона и раскомментирую пользовательские модели паспортов в AuthServiceProvider. php, как показано ниже
AuthServiceProvider . php
public function boot()
{
...
// UNCOMMENTED FOLLOWING CUSTOM PASSPORT MODELS
Passport::useTokenModel(OAuthAccessToken::class);
Passport::useClientModel(OAuthClient::class);
Passport::useAuthCodeModel(OAuthCode::class);
Passport::usePersonalAccessClientModel(OAuthPersonalAccessClient::class);
...
}
Теперь я могу получить доступ к api/meta
маршруту, но при входе в систему и создании токена я получаю сообщение об ошибке:
ErrorException: Trying to get property 'id' of non-object in file /home/winlappy1/Desktop/multi_tenancy/vendor/laravel/passport/src/PersonalAccessTokenFactory.php on line 98
Я просто хочу знать, где Я иду не так, я знаю, что мои объяснения довольно двусмысленные и запутанные, но это все, как я могу объяснить свою проблему. Я готов предоставить дополнительные разъяснения, но мне нужно решить эту проблему.