# 前言
學習一個框架, Ray 的想法是, 在深入理解底層實作的原理之前, 應該先知道這個框架的 使用方法
; 先學習怎麼使用這個前人造的輪子, 再學習怎麼樣造一個輪子。
所以本篇文章重點在於細讀官方文件, 並將內容理解後以 Q&A 的方式記錄下來, 加速學習以及查詢。
# Introduction
# Database Considerations
Laravel Authentication 中, 在建立 database schema for App\User
model 時, 務必確保 password 欄位要幾字元長?
60 characters
Laravel Authentication 中, 在建立 database schema for App\User
model 時, 務必確保 remember_token 欄位要幾字元長?
100 characters
# Authentication Quickstart
# Routing
Laravel Authentication 中, 如果我要快速開始 Authentication, 可以什麼 CLI 直接安裝註冊登入功能?
composer require laravel/ui |
Laravel Authentication 中, 以下 CLI 會自動產生哪一個 controller 來處理登入後的請求?
- CLI:
composer require laravel/ui
php artisan ui vue --auth - Answer:
HomeController
Laravel Authentication 中, 當我使用 CLI 來達成 Authentication Quickstart 時, 自動建立的 authentication controllers 會被建立在哪個 namespace 底下?
App\Http\Controllers\Auth
Laravel Authentication 中, 當我使用 CLI 來達成 Authentication Quickstart 時, 自動建立的 RegisterController 處理什麼工作?
註冊
Laravel Authentication 中, 當我使用 CLI 來達成 Authentication Quickstart 時, 自動建立的 LoginController 處理什麼工作?
登入
Laravel Authentication 中, 當我使用 CLI 來達成 Authentication Quickstart 時, 自動建立的 ForgotPasswordController 處理什麼工作?
發送 email 連結重設密碼
Laravel Authentication 中, 當我使用 CLI 來達成 Authentication Quickstart 時, 自動建立的 ResetPassword 處理什麼工作?
重設密碼
以下的 Laravel example code 的意思是?
- Example:
<?php
Auth::routes(['register' => false]); - Answer:
不使用 Scaffolding 的 RegisterController
# Creating Applications Including Authentication
以下的 Laravel example code 的意思是?
- Example:
laravel new projectName --auth
- Answer:
建立新專案時, 一同建立 authentication scaffolding
# Views
Laravel Authentication 中, 使用 authentication scaffolding 建立的 view 會位於哪個資料夾內?
resources/views/auth
Laravel Authentication 中, 以下的 CLI 會將 base layouts 置於死地哪個資料夾中?
resources/views/layouts
# Authenticating
# Path Customization
Laravel Authentication 中, 當我使用 authentication scaffolding 時, 預設驗證成功的使用會被導向 /home
URI, 如果我要重新定義成 /yourHome
, 那該在哪一個檔案中定義?
RouteServiceProvider
以下位於 RouteServiceProvider 的 Laravel example code 的意思是?
- Example:
<?php
public const HOME = '/yourHome'; - Answer:
Laravel Authentication 中, 當我使用 authentication scaffolding 時, 預設驗證成功的使用會被導向/home
URI, 可在 RouteServiceProvider 的 HOME property 定義要導向的位置
以下的 Laravel example code 的意思是?
- Example:
<?php
class RouteServiceProvider extends ServiceProvider
{
protected function authenticated(Request $request, $user)
{
return response([
//
]);
}
} - Answer:
當使用 authentication scaffolding 時, 預設登入驗證成功後, user 會被導向 /home URI, 如果想要自己定義驗證成功後的行為, 可使用 RouteServiceProvider 的 authenticated method
# Username Customization
以下的 Laravel example code 的意思是?
- Example:
<?php
public function username()
{
return 'name';
} - Answer:
當使用 Laravel Authentication scaffolding 時, 會使用 email 以及 password 欄位作為預設驗證欄位, 可使用 LoginController 中的 username(), 將 email 變更為任何你自訂的欄位
# Guard Customization
以下位於 Scaffolding - LoginController, RegisterController, ResetPasswordController 的 Laravel example code 的意思是?
- Example:
<?php
use Illuminate\Support\Facades\Auth;
protected function guard()
{
return Auth::guard('guard-name');
} - Answer:
在這些 scaffolding controller 中定義 guard, 所以會在預設的行為中使用定義的 guard
# Validation / Storage Customization
以下位於 Authentication Scaffolding - RegisterController 的 Laravel example code 的意思是?
- Example:
<?php
protected function validator(array $data)
{
return Validator::make($data, [
'name' => ['required', 'string', 'max:255'],
'email' => ['required', 'string', 'email', 'max:255', 'unique:users'],
'password' => ['required', 'string', 'min:6', 'confirmed'],
]);
} - Answer:
當使用 Authentication Scaffolding 時, 可在 RegisterController 的 validator method 定義註冊會員時需要什麼資料, 以及驗證的 rule
以下位於 Authentication Scaffolding - RegisterController 的 Laravel example code 的意思是?
- Example:
<?php
protected function create(array $data)
{
$user = User::create([
'name' => $data['name'],
'email' => $data['email'],
'password' => Hash::make($data['password']),
]);
Stats::create([
'user_id' => $user->id
]);
return $user;
} - Answer:
當使用 Authentication Scaffolding 時, 可在 RegisterController 中定義如何 create 一個 user, 資料要怎麼存
# Retrieving The Authenticated User
Laravel 中, 以下三種取得 authenticated user 的效果一樣嗎?
- Example:
<?php
auth()->user()
Auth::user()
$request->user() - Answer:
一樣
# Determining If The Current User Is Authenticated
以下的 Laravel example code 的意思是?
- Example:
<?php
use Illuminate\Support\Facades\Auth;
if (Auth::check()) {
// The user is logged in...
} - Answer:
判斷 current user 是否 authenticated, 回傳 boolean
# Protecting Routes
以下的 Laravel example code 的意思是?
- Example:
<?php
Route::get('profile', function () {
// Only authenticated users may enter...
})->middleware('auth'); - Answer:
使用 auth middleware 來驗證目標 url 為 ‘profile’ 的請求
以下的 Laravel example code 的意思是?
- Example:
<?php
class PostContoller extends Controller
{
public function __construct()
{
$this->middleware('auth');
}
} - Answer:
在 PostController 當中使用 auth middleware
# Redirecting Unauthenticated Users
Laravel Authentication 中, 預設會將 unauthenticated user 重導向 login
route, 如果我要自定義這個動作, 可以修改哪個檔案?
app/Http/Middleware/Authenticate.php
# Specifying A Guard
以下的 Laravel example code 的意思是?
- Example:
<?php
public function __construct()
{
$this->middleware('auth:api');
} - Answer:
指定 auth middleware 的 guard 為 api, 預設有 web 跟 api
# Password Confirmation
以下的 Laravel example code 的意思是?
- Example:
<?php
Route::get('/settings/security', function () {
})->middleware(['auth', 'password.confirm']); - Answer:
當 user 發 request 到這支 API 時, 除了會判斷身份是否 authenticated 之外, 還會導向特定頁面, 再次輸入密碼後方可存取該頁面
Laravel Authentication 中, 若我使用內建的 password.confirm middleware 來重新驗證密碼, 驗證過後, 預設有效時間是多長?
3 小時
Laravel Authentication 中, 若我使用內建的 password.confirm middleware 來重新驗證密碼, 驗證過後有效期限是 3 小時, 如果我要自定義這個時間, 可以在什麼地方定義?
auth.password_timeout
# Login Throttling
Laravel Authentication Scaffolding 中, 預設使用者輸入幾次帳密都錯誤, 會被 throttle 限制多久無法再登入?
1 分鐘
Laravel Authentication Scaffolding 中, throttle 會根據哪兩項資訊來判斷使用者的獨一性?
- username / email
- IP
# Manually Authenticating Users
以下的 Laravel example code 的意思是?
- Example:
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
class LoginController extends Controller
{
public function authenticate(Request $request)
{
$credentials = $request->only('email', 'password');
if (Auth::attempt($credentials)) {
// Authentication passed...
return redirect()->intended('dashboard');
}
}
} - Answer:
使用 Auth::attempt() 來驗證 $credentials 是否正確, 如果正確的話, redirect 到 request 原本的目標 url
Laravel Authentication 中, Auth::attempt()
method 除了 username 以及 password 之外, 還可以接受其他參數嗎?
可以哦, 會自動對應資料庫的 column
# Specifying Additional Conditions
以下的 Laravel example code 的意思是?
- Example:
<?php
if (Auth::attempt(['email' => $email, 'password' => $password, 'active' => 1])) {
// The user is active, not suspended, and exists.
} - Answer:
Auth::attempt() 除了可帶入預設 email, password 之外, 也可驗證其他 column
# Accessing Specific Guard Instances
Laravel Authentication 中, 什麼情況下, 我們可能會需要用到不同的 guard?
當我的應用同時使用不同的 authenticatable models 或 user table
以下的 Laravel example code 的意思是?
- Example:
<?php
if (Auth::guard('admin')->attempt($credentials)) {
//
} - Answer:
guard 預設為 api 或 web, 也可自定義 guard, example 中指定使用 guard'admin'
來驗證
# Remembering Users
以下的 Laravel example code 的意思是?
- Example:
<?php
if (Auth::attempt(['email' => $email, 'password' => $password], true)) {
// The user is being remembered...
} - Answer:
使用 Auth::attempt() 驗證, 且當使用 web route 時, 可在 arg2 帶入 true 啟動 remember_me feature, 會在 table 記下 remember_token
Laravel Authentication 中, 當我使用 remember me 功能時, Laravel 會在 User table 中的哪一個欄位記下 token?
remember_token
以下的 Laravel example code 的意思是?
- Example:
<?php
if (Auth::viaRemember()) {
//
} - Answer:
判斷 user 是否經由 remember_me token authenticated
# Other Authentication Methods
# Authenticate A User Instance
Laravel Authentication 中, 如果我要登入一個 model, 該 model 必須要是哪個 class 的 implementation?
Illuminate\Contracts\Auth\Authenticatable
以下的 Laravel example code 的意思是?
- Example:
<?php
Auth::login($user, true); - Answer:
使用 $user model login, 並開啟 remember_me feature
以下的 Laravel example code 的意思是?
- Example:
<?php
Auth::guard('admin')->login($user, true); - Answer:
使用指定的 guard admin 來 authenticate, 使用 $user model 登入, 並開啟 remember_me feature
# Authenticate A User By ID
以下的 Laravel example code 的意思是?
- Example:
<?php
Auth::loginUsingId(1, true); - Answer:
使用 User 來 login, 並且開啟 remember_me 的功能
# Authenticate A User Once
以下的 Laravel example code 的意思是?
- Example:
<?php
if (Auth::once($credentials)) {
//
} - Answer:
auth 過後並不會動用到 cookie 或 session 或 token, 也就是說相當於當下的 request 有效而已
# HTTP Basic Authentication
以下的 Laravel example code 的意思是?
- Example:
<?php
Route::get('profile', function () {
// Only authenticated users may enter...
})->middleware('auth.basic'); - Answer:
使用 HTTP Basic Authentication middleware, 這樣任何到 ‘profile’ 的 request 都會經過 HTTP Basic Authentication 驗證
Laravel Authentication 中, auth.basic middleware 預設會取哪一個 column 的值當作 username?
# A Note On FastCGI
Laravel Authentication 中, 當我使用 PHP FastCGI 並且想要使用 HTTP Basic Authentication 時, 需要在哪個檔案加入以下程式碼?
- 程式碼:
RewriteCond %{HTTP:Authorization} ^(.+)$
RewriteRule .* - [E=HTTP_AUTHORIZATION:%{HTTP:Authorization}] - Answer:
.htaccess file
# Stateless HTTP Basic Authentication
以下的 Laravel example code 的意思是?
- Example:
<?php
namespace App\Http\Middleware;
use Illuminate\Support\Facades\Auth;
class AuthenticateOnceWithBasicAuth
{
public function handle($request, $next)
{
return Auth::onceBasic() ?: $next($request);
}
} - Answer:
若要使用 HTTP Basic Authentication, 且不在 server 記下 session, 即關閉瀏覽器後, 使用者便需要重新登入, 那可自定義以上 middleware
# Logging out
以下的 Laravel example code 的意思是?
- Example:
<?php
use Illuminate\Support\Facades\Auth;
Auth::logout(); - Answer:
登出該使用者, 也就是說清除 server 上的 session 以及 token
# Invalidating Sessions On Other Devices
Laravel Authentication 中, 當用戶更改完密碼後, 我必須要讓該用戶在所有其他裝置失效, 若要做到這點, 我必須要讓哪一個內建的 middleware un-commented?
- Example:
<?php
'web' => [
// ...
// 這裡是?
// ...
], - Answer:
<?php
'web' => [
// ...
\Illuminate\Session\Middleware\AuthenticateSession::class,
// ...
],
以下的 Laravel example code 的意思是?
- Example:
<?php
use Illuminate\Support\Facades\Auth;
Auth::logoutOtherDevices($password); - Answer:
當 user 變更密碼之後, 可能會需要把變更密碼前的所有裝置都 logout, 這時就可以使用 logoutOtherDevices method
Laravel Authentication 中, 當用戶更改完密碼後, 我必須要讓該用戶在所有其他裝置失效, 當我啟動 AuthenticationSession middleware 來做到這點後, 如果我用來登入的 route 不是叫做 login, 那我必須要再來 exception handler 中 override 哪一個 method 來導向我設定的登入用 route?
unauthenticated method
# Social Authentication
# Adding Custom Guards
Laravel Authentication 中, 如果我要自定義 guard, 可以在哪個檔案中的 boot method 定義?
AuthServiceProvider
Laravel Authentication 中, 如果我要自定義 guard, 可以在哪個 AuthServiceProvider 的 boot method 中, 使用哪一個 method?
Auth::extend method
# Closure Request Guards
Laravel Authentication 中, 如果我要使用 closure 來自定義 custom guard, 可以在哪個檔案中的 boot method 中定義?
AuthServiceProvider
Laravel Authentication 中, 如果我要使用 closure 來自定義 custom guard, 可以在 AuthServiceProvider 中的 哪個 method 定義?
boot method
Laravel Authentication 中, 如果我要使用 closure 來自定義 custom guard, 可以在 AuthServiceProvider 中的 boot method 中使用哪個 method?
Auth::viaRequest
以下的 Laravel example code 的意思是?
- Example:
<?php
use App\User;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
public function boot()
{
$this->registerPolicies();
Auth::viaRequest('guardName', function ($request) {
return User::where('token', $request->token)->first();
});
} - Answer:
自定義一個 guard, 名為 guardName closure 內為 guard 的規則
以下的 Laravel example code 的意思是?
- Example:
<?php
use App\User;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
public function boot()
{
$this->registerPolicies();
Auth::viaRequest('custom-token', function ($request) {
// User instance or null
});
} - Answer:
在 Auth Service Provider boot() 中, 使用 Auth::viaRequest 自定義一個 closure based guard, arg1 為 guard name, arg2 為驗證的 closure, 若驗證通過則 return user instance, 若否則為 null
以下位於 config/auth.php 的 Laravel example code 的意思是?
- Example:
<?php
'guards' => [
'api' => [
'driver' => 'custom-token',
],
], - Answer:
Laravel 中, api guard 預設使用 driver 為 token, 即驗證的邏輯, 上面 example 中指定了 guard api 需使用自定義的custom-token
guard 來驗證
# Adding Custom User Providers
Laravel Authentication 中, guard 跟 provider 的差別?
- guard 是 Laravel 將把 authenticated user’s detail 存在哪, 像是 session, database, etc
- User provider 是 Laravel 如何 authenticate a user, 像是 Eloquent, 或 API, 或其他
Laravel Authentication 中, 如果我要自定義一個 user provider, 可以在哪個檔案中中的 boot method?
AuthServiceProvider
Laravel Authentication 中, 如果我要自定義一個 user provider, 可以在 AuthServiceProvider 中的 哪一個 method 定義?
boot method
# The User Provider Contract
Laravel Authentication 中, Illuminate\Contracts\Auth\UserProvider
的作用?
透過各種 method 從 persistent storage system 中取出並回傳一個 Illuminate\Contracts\Auth\Authenticatable
implementation
以下的 Laravel example code 的意思是?
- Example:
<?php
namespace Illuminate\Contracts\Auth;
interface UserProvider
{
public function retrieveById($identifier);
} - Answer:
透過 id 取得 authenticatable implementation
Laravel Authentication 中, 以下的 UserProvider contract 的作用是?
- Example:
<?php
namespace Illuminate\Contracts\Auth;
interface UserProvider
{
public function retrieveByToken($identifier, $token);
} - Answer:
透過 $identifier 以及 $token (remember_token) 取得 authenticatable implementation
Laravel Authentication 中, 以下的 UserProvider contract 的作用是?
- Example:
<?php
namespace Illuminate\Contracts\Auth;
interface UserProvider
{
public function updateRememberToken(Authenticatable $user, $token);
} - Answer:
當使用者使用 rmemeber_me 功能登入, 或登出時更新 remember_token 的值
Laravel Authentication 中, 以下的 UserProvider contract 的作用是?
- Example:
<?php
namespace Illuminate\Contracts\Auth;
interface UserProvider
{
public function retrieveByCredentials(array $credentials);
} - Answer:
透過 $credential 來取得 authenticatable implementation
Laravel Authentication 中, 以下的 UserProvider contract 的作用是?
- Example:
<?php
namespace Illuminate\Contracts\Auth;
interface UserProvider
{
public function validateCredentials(Authenticatable $user, array $credentials);
} - Answer:
驗證 $credential 並回傳 boolean
# The Authenticatable Contract
Laravel Authentication 中, 以下的 authenticatable method 的意思是?
- Example:
<?php
namespace Illuminate\Contracts\Auth;
interface Authenticatable
{
public function getAuthIdentifierName();
} - Answer:
取得 primary key 的欄位名稱
Laravel Authentication 中, 以下的 authenticatable method 的意思是?
- Example:
<?php
namespace Illuminate\Contracts\Auth;
interface Authenticatable
{
public function getAuthIdentifier();
} - Answer:
取得 primary key 欄位的 值
# Events
Laravel Authentication 中, 以下的 example 的用途是?
- Example:
<?php
protected $listen = [
'Illuminate\Auth\Events\Registered' => [
'App\Listeners\LogRegisteredUser',
],
'Illuminate\Auth\Events\Attempting' => [
'App\Listeners\LogAuthenticationAttempt',
],
'Illuminate\Auth\Events\Authenticated' => [
'App\Listeners\LogAuthenticated',
],
'Illuminate\Auth\Events\Login' => [
'App\Listeners\LogSuccessfulLogin',
],
'Illuminate\Auth\Events\Failed' => [
'App\Listeners\LogFailedLogin',
],
'Illuminate\Auth\Events\Logout' => [
'App\Listeners\LogSuccessfulLogout',
],
'Illuminate\Auth\Events\Lockout' => [
'App\Listeners\LogLockout',
],
'Illuminate\Auth\Events\PasswordReset' => [
'App\Listeners\LogPasswordReset',
],
]; - Answer:
每一個 authentication 的動作都有其 event, 可以註冊該 event 的 listener 來做相對應的事, 例如, log
留言