CKEditor 5 教學 (三),上傳圖片至 Amazon S3
要想讓文章的內容更為生動,圖片可以說是必不可少的東西,畢竟圖文並茂的文章絕對是大大的加分。
一般的文章編輯器,都會提供插入圖片的功能。本文中我們會使用 CKEditor 官方提供的 CKFinder 套件,實作一個將圖片插入文章內容中的功能。
關於 CKEditor 的基礎安裝教學,可以查看前兩篇文章:
本次演示是在 Laravel 專案上進行。
如果要啟用圖片上傳的功能,必須要先有 CKEditor 的圖片套件,這個套件在預設時就已經安裝。
有安裝的話,就可以在 ckeditor5-build-classic/src/ckeditor.js 中引入的套件看到以下這行:
import Image from "@ckeditor/ckeditor5-image/src/image";
確認一下你的編輯器上方功能列有圖片上傳的圖案。
這時我們先安裝 ckfinder-laravel-package 這個套件,使用 composer 安裝。
composer require ckfinder/ckfinder-laravel-package
安裝好之後還需要下指令來下載 CKFinder 的檔案,下載的檔案會放在 vendor/ckfinder
裡面。
php artisan ckfinder:download
接下來產出一個設定檔案,可以用來設定上傳檔案種類、大小以及 S3 的相關設定。
這個指令會在 config 資料夾底下生成一個 ckfinder.php
。
php artisan vendor:publish --tag=ckfinder-config
因為 CKFinder 有自帶 CSRF 保護,因此我們需要更改 Laravel 的 Middleware 設定。
其中一個需要修改的檔案是 app/Http/Middleware/EncryptCookies.php
,避免加密 CKFinder 的 cookie。
<?php
namespace App\Http\Middleware;
use Illuminate\Cookie\Middleware\EncryptCookies as Middleware;
class EncryptCookies extends Middleware
{
/**
* The names of the cookies that should not be encrypted.
*
* @var array
*/
protected $except = [
// 避免 Laravel 加密 CKFinder 的 cookie
'ckCsrfToken',
];
}
另外一個檔案是 app/Http/Middleware/VerifyCsrfToken.php
。如果是 CKFinder 的相關網址,就不使用 Laravel 自帶的 CSRF 的保護。
<?php
namespace App\Http\Middleware;
use Illuminate\Foundation\Http\Middleware\VerifyCsrfToken as Middleware;
class VerifyCsrfToken extends Middleware
{
/**
* The URIs that should be excluded from CSRF verification.
*
* @var array
*/
protected $except = [
// CKFinder 的相關路由不使用 Laravel 自帶的 CSRF 的保護
'ckfinder/*',
];
}
然後在 routes/web.php
中加入 CKFinder 的路由。
use CKSource\CKFinderBridge\Controller\CKFinderController;
Route::any('/ckfinder/connector', [CKFinderController::class, 'requestAction'])->name('ckfinder_connector');
之後我們在 CKEditor 的 JS 程式碼中設定 CKFinder 的上傳 URL。
ClassicEditor.create( document.querySelector( '#editor' ), {
ckfinder: {
// Upload the images to the server using the CKFinder QuickUpload command.
uploadUrl: "https://你的網站DNS/ckfinder/connector?command=QuickUpload&type=Images&responseType=json"
},
})
.then( editor => {
console.log( 'Editor was initialized', editor );
})
.catch( err => {
console.error( err.stack );
});
在設定上傳的設定檔案之前,我們需要在 .env
檔案中設定 S3 的金鑰。
AWS_ACCESS_KEY_ID=S3 的 Key ID
AWS_SECRET_ACCESS_KEY=S3 的 Access Key
AWS_DEFAULT_REGION=S3 的地區代碼
AWS_BUCKET=S3 的 Bucket 名稱
最後就是完成上傳的設定檔案,首先我們先設定 Backends 區塊,這裡使用我們剛剛在 .env
中設定的 S3 金鑰。
/*=================================== Backends ========================================*/
// http://docs.cksource.com/ckfinder3-php/configuration.html#configuration_options_backends
$config['backends']['awss3'] = array(
'name' => 'awss3',
'adapter' => 's3',
'bucket' => env('AWS_BUCKET'),
'region' => env('AWS_DEFAULT_REGION'),
'key' => env('AWS_ACCESS_KEY_ID'),
'secret' => env('AWS_SECRET_ACCESS_KEY'),
'visibility' => 'public',
);
再來設定 Resource Types 的區塊。
剛剛在 JS 程式碼中設定的 UploadUrl
,其中的參數 type=Images
,代表使用 'name' => 'Images'
這個區塊的上傳設定。
其中的 'backend' => 'awss3'
,代表要使用 'name' => 'awss3'
的 Backend 區塊設定。
/*================================ Resource Types =====================================*/
// http://docs.cksource.com/ckfinder3-php/configuration.html#configuration_options_resourceTypes
$config['defaultResourceTypes'] = 'Images';
$config['resourceTypes'][] = array(
// UploadUrl 中的 type=Images 代表要使用這個區塊的上傳設定
'name' => 'Images',
// S3 的上傳目錄
'directory' => 'images/post',
// 檔案最大容量的限制
'maxSize' => '1M',
// 允許的副檔名
'allowedExtensions' => 'bmp,gif,jpeg,jpg,png',
'deniedExtensions' => '',
// 使用剛剛在 Backends 區塊的 AWS S3 設定
'backend' => 'awss3',
);
如此一來,就可以在文章中插入圖片,寫一個圖文並茂的文章內容了。