在 ServBay 中建立並運行 Webman 專案
什麼是 Webman?
Webman 是基於 Workerman 的高效能 PHP 非同步 Web 框架,專為建構高併發和高效能的 Web 應用而設計。與傳統的同步阻塞框架不同,Webman 採用事件驅動和非同步非阻塞 I/O 模型,使其在處理大量並發請求時表現優異。Webman 提供簡潔易用的 API 與靈活擴展機制,非常適合開發即時應用、API 服務、微服務等。
Webman 的主要特點與優勢
- 高效能:基於 Workerman,利用事件驅動和非同步非阻塞 I/O,能處理大量併發連線,吞吐量遠超傳統同步框架。
- 易於上手:提供直覺且簡潔的 API 及豐富功能,開發者可快速上手並建構應用。
- 多協議支援:內建支援 HTTP、WebSocket 等常見應用層協議,方便打造各類型服務。
- 靈活擴充:透過 Composer 套件、外掛和中介軟體機制,輕鬆擴充框架功能。
- 低資源消耗:相較傳統 Web 伺服器 + PHP-FPM 模式,Webman 作為常駐記憶體應用,資源開銷較低。
- 強大的社群支援:擁有活躍的開發者社群與豐富的文件資源。
Webman 能協助開發者快速構建高效能、高可用性的 Web 應用與 API 服務,特別適合需要處理高併發、低延遲場景。
使用 ServBay 建立與運行簡單的 Webman 專案
本指南將詳細說明如何在 ServBay 本機開發環境下,利用 Webman 建立並運行簡單的 Web 專案。我們將示範 Webman 安裝流程、基本路由與控制器撰寫,並說明如何整合 ServBay 所提供的資料庫(MySQL, PostgreSQL)與快取(Redis, Memcached)等服務。
TIP
ServBay 建議開發者將所有本機網站專案存放於 /Applications/ServBay/www
目錄下,以利 ServBay 統一管理(例如統一設定本機網站,原稱“主機”)。
前置條件
開始之前,請確保您已完成以下準備:
- 安裝 ServBay:您已於 macOS 成功安裝 ServBay。ServBay 提供一站式本機開發環境,內含 PHP、Composer、MySQL、PostgreSQL、Redis、Memcached 等本教學所需的全部套件。
- 啟用所需服務:透過 ServBay 控制面板,請確認下列軟體套件已安裝並正執行中:
- 您所選的 PHP 版本(建議使用較新版本,如 PHP 8.x)
- Composer(已內建於 ServBay)
- MySQL
- PostgreSQL
- Redis
- Memcached
- 請確保所選的 PHP 版本已啟用
memcached
、redis
、pdo_mysql
、pdo_pgsql
等必要 PHP 擴充。ServBay 通常預設啟用這些常用擴充,可於 ServBay 的 PHP 設定介面檢查。
- 終端機基礎操作:能熟悉使用 macOS 之終端機。
安裝 Webman
確認 Composer 可使用
ServBay 已預載 Composer,並已設定可於終端機直接執行。您可透過下列指令檢查:
bashcomposer --version
1若正確顯示 Composer 版本資訊,即代表 Composer 已準備就緒。
切換至 ServBay 網站目錄
開啟終端機,切換至 ServBay 建議的專案根目錄:
bashcd /Applications/ServBay/www
1使用 Composer 建立 Webman 專案
執行 Composer 的
create-project
指令將 Webman 框架安裝於指定目錄,這裡命名專案為servbay-webman-app
:bashcomposer create-project workerman/webman servbay-webman-app
1Composer 會自 Packagist 下載 Webman 及其核心依賴至
servbay-webman-app
目錄。進入專案目錄
安裝完畢後前往新建的專案目錄:
bashcd servbay-webman-app
1安裝必要元件
為了示範資料庫與快取功能,需要額外安裝一些 Composer 套件。Webman 常用
illuminate/database
(來自 Laravel 的資料庫元件)、illuminate/redis
等。-W
參數(--with-dependencies
)可避免安裝相依性衝突。bashcomposer require -W illuminate/database illuminate/redis illuminate/pagination illuminate/events symfony/var-dumper
1此指令會安裝 ORM、Redis 工具、分頁、事件調度與除錯用的 VarDumper 等必要元件。
建立資料庫與資料表
為讓範例程式可正常運作,我們需於 ServBay 的 MySQL 與 PostgreSQL 資料庫建立相關資料庫及 users
資料表。ServBay 預設的資料庫 root
使用者密碼為 password
。
您可使用 ServBay 內建的資料庫管理工具(如 phpMyAdmin 或 pgAdmin,可透過 ServBay 控制面板進入)或於命令列執行以下 SQL 指令。
建立資料庫
webman_app
- MySQL:sql
CREATE DATABASE IF NOT EXISTS webman_app CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci;
1 - PostgreSQL:sql
CREATE DATABASE webman_app;
1
- MySQL:
於
webman_app
資料庫中建立users
資料表- MySQL:sql
USE webman_app; CREATE TABLE users ( id INT AUTO_INCREMENT PRIMARY KEY, name VARCHAR(255) NOT NULL, email VARCHAR(255) NOT NULL UNIQUE, created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP );
1
2
3
4
5
6
7 - PostgreSQL:sql
\c webman_app; -- 連接新建立的資料庫 CREATE TABLE users ( id SERIAL PRIMARY KEY, name VARCHAR(255) NOT NULL, email VARCHAR(255) NOT NULL UNIQUE, created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP );
1
2
3
4
5
6
7
- MySQL:
撰寫 Web 專案程式碼
接下來,我們將加入實作路由、控制器及與資料庫與快取互動的邏輯程式碼。
設定路由
編輯專案根目錄下的
config/route.php
,新增下列設定作為範例用路由:php<?php use Webman\Route; use app\controller\IndexController; use app\controller\CacheController; use app\controller\DatabaseController; // 定義根路徑路由,對應至 IndexController 的 index 方法 Route::any('/', [IndexController::class, 'index']); // 定義快取相關路由 Route::any('/memcached', [CacheController::class, 'memcached']); Route::any('/redis', [CacheController::class, 'redis']); // 定義資料庫相關路由 Route::any('/mysql-add', [DatabaseController::class, 'mysqlAdd']); Route::any('/mysql', [DatabaseController::class, 'mysqlGet']); Route::any('/pgsql-add', [DatabaseController::class, 'pgsqlAdd']); Route::any('/pgsql', [DatabaseController::class, 'pgsqlGet']); // 可於此繼續擴充更多路由...
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21建立控制器檔案
於
app/controller
目錄下建立IndexController.php
、CacheController.php
及DatabaseController.php
,並依下列範例編寫內容。app/controller/IndexController.php
:處理首頁路徑請求。php<?php namespace app\controller; use support\Request; use support\Response; // 引入 Response 類別 class IndexController { /** * 處理根路徑請求的示例方法 * @param Request $request 目前請求物件 * @return Response 傳回 Response 物件 */ public function index(Request $request): Response // 明確回傳型別 { // 傳回簡單文字回應 return response('Hello ServBay & Webman!'); // 更新歡迎訊息 } }
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20app/controller/CacheController.php
:示範 Memcached 與 Redis 用法。php<?php namespace app\controller; use support\Request; use support\Response; use Memcached; // 引入 Memcached 類別 use support\Redis; // 引入 Webman 提供的 Redis Facade class CacheController { /** * 示範 Memcached 用法 * @param Request $request * @return Response */ public function memcached(Request $request): Response { // 連線至 Memcached 伺服器,ServBay 預設運行於 127.0.0.1:11211 $memcached = new Memcached(); $memcached->addServer('127.0.0.1', 11211); // 設定快取項,60 秒有效 $success = $memcached->set('servbay_key', 'Hello Memcached from ServBay!', 60); // 更新 key 與 value if (!$success) { return response('Failed to set Memcached key', 500); } // 取得快取 $value = $memcached->get('servbay_key'); // 更新 key // 回傳取得的結果 return response($value ?: 'Memcached key not found or expired'); // 若找不到則顯示提示 } /** * 示範 Redis 用法 * @param Request $request * @return Response */ public function redis(Request $request): Response { // 使用 Webman Redis Facade 設定快取項 Redis::set('servbay_redis_key', 'Hello Redis from ServBay!'); // 更新 key 與 value // 取得快取項 $value = Redis::get('servbay_redis_key'); // 更新 key // 回傳取得的結果 return response($value ?: 'Redis key not found'); // 若找不到則顯示提示 } }
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52app/controller/DatabaseController.php
:示範 MySQL 與 PostgreSQL 操作。php<?php namespace app\controller; use support\Request; use support\Response; use support\Db; // 引入 Webman 提供的 Db Facade class DatabaseController { /** * 新增 MySQL 資料庫用戶 * @param Request $request * @return Response */ public function mysqlAdd(Request $request): Response { try { // 使用 Db Facade 連線 'mysql' 並插入資料 Db::connection('mysql')->table('users')->insert([ 'name' => 'ServBay Webman MySQL User', // 範例資料 'email' => '[email protected]', // 範例信箱 'created_at' => date('Y-m-d H:i:s') // 加入 created_at ]); return response('User added to MySQL'); // 回應訊息 } catch (\Exception $e) { return response('Error adding user to MySQL: ' . $e->getMessage(), 500); // 錯誤處理 } } /** * 從 MySQL 取得用戶列表 * @param Request $request * @return Response */ public function mysqlGet(Request $request): Response { try { // 取得所有 MySQL 用戶 $users = Db::connection('mysql')->table('users')->get(); // 輸出 JSON 格式資料 return response(json_encode($users), 200, ['Content-Type' => 'application/json']); // 明確 Content-Type } catch (\Exception $e) { return response('Error getting users from MySQL: ' . $e->getMessage(), 500); // 錯誤處理 } } /** * 新增 PostgreSQL 資料庫用戶 * @param Request $request * @return Response */ public function pgsqlAdd(Request $request): Response { try { // 使用 Db Facade 連線 'pgsql' 並插入資料 Db::connection('pgsql')->table('users')->insert([ 'name' => 'ServBay Webman PgSQL User', // 範例資料 'email' => '[email protected]', // 範例信箱 'created_at' => date('Y-m-d H:i:s') // 加入 created_at ]); return response('User added to PostgreSQL'); // 回應訊息 } catch (\Exception $e) { return response('Error adding user to PostgreSQL: ' . $e->getMessage(), 500); // 錯誤處理 } } /** * 從 PostgreSQL 取得用戶列表 * @param Request $request * @return Response */ public function pgsqlGet(Request $request): Response { try { // 取得所有 PostgreSQL 用戶 $users = Db::connection('pgsql')->table('users')->get(); // 輸出 JSON 格式資料 return response(json_encode($users), 200, ['Content-Type' => 'application/json']); // 明確 Content-Type } catch (\Exception $e) { return response('Error getting users from PostgreSQL: ' . $e->getMessage(), 500); // 錯誤處理 } } }
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
設定資料庫連線
編輯專案根目錄下的
config/database.php
,設定 MySQL 與 PostgreSQL 的連線資訊。ServBay 預設資料庫主機為127.0.0.1
,MySQL 端口為3306
,PostgreSQL 為5432
,root
密碼皆為password
。php<?php /** * 資料庫設定 */ return [ // 預設使用的資料庫連線 'default' => 'mysql', // 資料庫連線設定清單 'connections' => [ 'mysql' => [ 'driver' => 'mysql', // ServBay 預設 MySQL 主機與端口 'host' => '127.0.0.1', 'port' => 3306, // 你剛建立的資料庫名 'database' => 'webman_app', // ServBay 預設 MySQL 使用者 'username' => 'root', // ServBay 預設 MySQL 密碼 'password' => 'password', 'charset' => 'utf8mb4', 'collation' => 'utf8mb4_unicode_ci', 'prefix' => '', 'strict' => true, 'engine' => null, ], 'pgsql' => [ 'driver' => 'pgsql', // ServBay 預設 PostgreSQL 主機與端口 'host' => '127.0.0.1', 'port' => 5432, // 你剛建立的資料庫名 'database' => 'webman_app', // ServBay 預設 PostgreSQL 使用者 'username' => 'root', // ServBay 預設 PostgreSQL 密碼 'password' => 'password', 'charset' => 'utf8', 'prefix' => '', 'schema' => 'public', 'sslmode' => 'prefer', // 也可選 require, verify-ca, verify-full ], // 於此可額外擴充其它連線... ], ];
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46重要提醒: 生產環境請務必更改預設資料庫密碼,且避免於程式中明碼儲存敏感資訊。
運行 Webman 專案
Webman 專案通常透過內建 start.php
腳本啟動 Workerman 程序。與傳統由 Nginx/Apache + PHP-FPM 方式不同,Webman 屬於常駐記憶體的非同步應用。
於專案根目錄 (/Applications/ServBay/www/servbay-webman-app
) 執行下列指令即可啟動 Webman:
php start.php start
執行後終端機會顯示 Webman 啟動資訊,預設將監聽於 127.0.0.1:8787
處理 HTTP 請求。
- 注意: 此處的
php
為 ServBay 提供的 PHP 執行檔。ServBay 會自動設定環境,讓終端直接可用 ServBay 安裝之 PHP 版本。 - 若要讓 Webman 於背景運行,可加上
-d
參數:php start.php start -d
。 - 停止 Webman 服務可執行:
php start.php stop
。 - 重新啟動 Webman 服務可執行:
php start.php restart
。 - 進行平滑重啟(不中斷現有請求),請執行:
php start.php reload
。
測試專案
Webman 成功啟動並監聽 127.0.0.1:8787
後,您可於瀏覽器測試下列功能頁面:
http://localhost:8787/
:顯示訊息Hello ServBay & Webman!
。http://localhost:8787/memcached
:顯示Hello Memcached from ServBay!
,代表已成功連線並使用 ServBay Memcached 服務。http://localhost:8787/redis
:顯示Hello Redis from ServBay!
,代表已成功連線並使用 ServBay Redis 服務。http://localhost:8787/mysql-add
:顯示User added to MySQL
,同時於 MySQL 的users
資料表新增紀錄。http://localhost:8787/mysql
:顯示 MySQLusers
資料表的用戶陣列(JSON 格式)。http://localhost:8787/pgsql-add
:顯示User added to PostgreSQL
,同時於 PostgreSQL 的users
資料表新增紀錄。http://localhost:8787/pgsql
:顯示 PostgreSQLusers
資料表的用戶陣列(JSON 格式)。
如果上述 URL 存取有問題,請檢查 Webman 終端機輸出有無錯誤訊息,並驗證 ServBay 之 MySQL、PostgreSQL、Redis、Memcached 服務是否啟動,及 PHP 擴充是否已勾選。
常見問答(FAQ)
- Q: 找不到
php start.php start
指令?- A: 請確保您已於終端機
cd
至servbay-webman-app
目錄。同時確認 ServBay 安裝的 PHP 已正確加入系統 PATH(ServBay 通常會自動處理此步驟)。
- A: 請確保您已於終端機
- Q: 瀏覽
localhost:8787
顯示連線失敗?- A: 請檢查終端機執行
php start.php start
時的輸出訊息,以及確保8787
端口未被其它程式占用。若已佔用,可修改 Webman 設定檔(如config/server.php
)改變監聽端口。
- A: 請檢查終端機執行
- Q: 資料庫連線失敗?
- A: 請確認 ServBay 的 MySQL 與 PostgreSQL 服務運作中。檢查
config/database.php
連線資訊(主機、端口、資料庫名稱、帳密)是否與 ServBay 設定一致(預設使用者為root
,密碼為password
)。確定已建立webman_app
資料庫及users
資料表。
- A: 請確認 ServBay 的 MySQL 與 PostgreSQL 服務運作中。檢查
- Q: Memcached 或 Redis 連線失敗?
- A: 請確認 ServBay 的 Memcached 與 Redis 服務運作正常。檢查
app/controller/CacheController.php
內連線參數是否正確(預設為127.0.0.1:11211
與127.0.0.1:6379
)。確認 PHP 版本已啟用 memcached 與 redis 擴充。
- A: 請確認 ServBay 的 Memcached 與 Redis 服務運作正常。檢查
總結
經過以上教學步驟,您已成功於 ServBay 本機開發環境建立、設定並運行一個基礎 Webman 專案。您學會如何善用 ServBay 的一站式服務,迅速完成 Webman 開發環境搭建,並整合資料庫與快取服務。Webman 的高效能特性結合 ServBay 的便捷性,將為您的 PHP 非同步開發帶來強大支援。期望本指南能協助您更有效運用 ServBay 與 Webman,打造出色且高效穩定的 Web 應用。