﻿# 如何在 Windows 快速啟動一個 Oracle Database 23c Free 資料庫容器

我前幾天在企業內訓授課的時候，因為客戶主要採用 Oracle 資料庫，所以我原本想說要在 Docker 上安裝 Oracle Database 的免費版本來用，結果我在 2019 年[寫過的 Oracle Database Server 12c R2 容器文章](/post/2019/10/07/How-to-use-Oracle-Database-Server-12c-R2-containers)已經不能用了。這幾天進一步發現 Oracle 官方提供了新版本的 Oracle Database 容器映象可用，但要從官網或網路上找到一篇立即可上手的文章並不容易，我花了好幾個小時才釐清來龍去脈，這篇文章我就打算來分享新版本 Oracle Database 容器映象的安裝與使用方式。

![image](https://stwillblogassets.blob.core.windows.net/files/images/external/stwillblogassets.blob.core.windows.net/b65f6793f5034443ab0f-c333c8ae-06b5-4711-a6eb-78d58ca8c0fd.webp)

### 先瞭解 Oracle Database 有哪些「免費」版本

我因為是上課所需，所以我肯定是想安裝「免費」版本，但是 Oracle 家大業大，光是一個資料庫產品，就有超多名字，我從 [Oracle Container Registry](https://container-registry.oracle.com/) 的 [Database Repositories](https://container-registry.oracle.com/ords/f?p=113:1:6731345441857:::1:P1_BUSINESS_AREA:3&cs=3Obra03y7BGuQLW4JESEgni6EgQA1D6X2Yw7dLbuV69CuRGlwsKpV9yxAekYvUk0B5WApR16FkxW7on9eo9cWYQ) 就看到好幾個版本，光是「開源的資料庫」就有 8 個不同的 Repositories，其中光是「免費版的資料庫」也有 2 種，分別是 [Oracle Database Express Edition](https://www.oracle.com/database/technologies/appdev/xe.html) (XE) 與 [Oracle Database Free](https://www.oracle.com/database/free/)，這裡 `XE` 我還有聽過，這套真的是免費的，但另一套 `Free` 我就真的完全沒聽過，也不知道差別在哪，不知道應該安裝哪個版本才對，真的非常困擾。

雖然一時間沒辦法找到答案，但我自己分析研判後認為是這樣的：

1.  **Oracle Database Express Edition (XE)**
    
    這個 `XE` 版本出來很久了，主要就是給中小企業或開發者用的，它的功能比較簡單，但是免費，所以很多人都會用來開發或測試。
    
    目前在 `Oracle Database XE Release 21c (21.3.0.0) Docker Image Documentation` 可以看到他只有兩個 Tag 可用：`18.4.0-xe` 與 `21.3.0-xe`。
    
    所以我研判，這個就是 Oracle Database XE `18c` 與 `21c` 的版本的容器映像。
    
2.  **Oracle Database Free**
    
    這個 `Free` 版本可能是新推出的，而也從字面上看來也是道道地地的免費版，至於功能是否有受限或者是擁有 Oracle Database 完整版，就不得而知了。
    
    目前在 `Oracle Database Free Release 23c (23.3.0.0) Container Image Documentation` 可以看到他只有一個 Tag 可用：`23.3.0.0`。
    
    所以我研判，這個就是 Oracle Database `23c` 的版本的容器映像。
    

## 啟動 Oracle Database 23c Free 容器

1.  先登入 Oracle Container Registry (OCR)
    
    你必須先[建立 Oracle 帳號](https://profile.oracle.com/myprofile/account/create-account.jspx)才能進行[登入](https://container-registry.oracle.com/)。
    
    取得你的 Oracle 帳號與密碼後，就可以透過 `docker login` 來登入 OCR 伺服器：
    
    ```bash
    docker login container-registry.oracle.com
    ```
    
    登入成功後，你才可以開始下載 Oracle Database 23c Free 容器映像。
    
2.  下載容器映像
    
    直接下載最新版：
    
    ```bash
    docker pull container-registry.oracle.com/database/free:latest
    ```
    
    但我一般會直接指定版本號，以確保我下載的 Oracle 資料庫是我要的版本：
    
    ```bash
    docker pull container-registry.oracle.com/database/free:23.3.0.0
    ```
    
3.  啟動 Oracle Database 23c Free 容器
    
    ```bash
    docker run --name oracle -p 1521:1521 -e ORACLE_PWD=Test1234 -v "oradata:/opt/oracle/oradata" container-registry.oracle.com/database/free:23.3.0.0
    ```
    
    第一次啟動的時間蠻長的，因為要初始化資料庫，所以要耐心等待。
    
    你可以透過 `docker logs oracle -f` 查看初始化進度：
    
    ```bash
    docker logs oracle -f
    ```
    
    看到以下字樣就代表資料庫已經可以用了：
    
    ```
    #########################
    DATABASE IS READY TO USE!
    #########################
    ```
    
    官方容器的預設帳號密碼如下：
    
    -   SID: `FREE`
    -   帳號: `SYS`
    -   密碼: `Test1234` (這是我在 `docker run` 指令中指定的密碼)
4.  變更 `SYS` 資料庫管理員的預設密碼
    
    如果你在 `docker run` 的時候不指定 `-e ORACLE_PWD=Test1234` 環境變數時，初始化 Oracle 資料庫之後會設定一組亂數密碼，所以你勢必要修改密碼。
    
    使用以下命令可以很輕鬆的更換掉預設密碼：
    
    ```bash
    docker exec -it oracle ./setPassword.sh '<你的新密碼>'
    ```
    

### 連線到容器中的 Oracle Database 23c Free 資料庫

連線到資料庫只要跑 `oracle` 容器中的 SQL\*Plus 工具即可：

```bash
# 使用「作業系統認證」來連線到資料庫，並以 SYSDBA 身份登入
docker exec -it oracle sqlplus / as sysdba

# 使用「資料庫認證」來連線到資料庫，並以 SYSDBA 身份登入
# 使用者名稱是 SYS，密碼是 Test1234，實例是 FREE
# 注意: 要登入 SYS 帳號，一定要指定 SYSDBA 或 SYSOPER 角色
docker exec -it oracle sqlplus sys/Test1234@FREE as sysdba

# 使用「資料庫認證」來連線到資料庫
# 使用者名稱是 SYSTEM，密碼是 Test1234，實例是 FREE
# 未使用 as sysdba 連線的典型場景包括應用程式開發者、資料分析師或一般使用者的連線
# 他們需要對特定資料執行查詢、更新、插入和刪除操作，但不需要進行資料庫級別的管理任務。
# SYSTEM 是一個預設的管理賬戶，雖然它的權限低於 SYS 使用者，但仍然擁有執行大多數資料庫管理任務的能力。
docker exec -it oracle sqlplus system/Test1234@FREE

# 連線到 Oracle 資料庫中的特定 Pluggable Database (PDB)
# 注意: FREEPDB1 是 Oracle 資料庫容器中的預設 Pluggable Database 名稱
# 這裡的 pdbadmin 是在 PDB FREEPDB1 中的一個使用者。通常，這種使用者會有管理該 PDB 的權限。
docker exec -it oracle sqlplus pdbadmin/Test1234@FREEPDB1
```

如果要從容器外連到容器內的資料庫，可以這樣通過認證：

```bash
# 以 SYSDBA 的身分與 CDB$ROOT 層級登入
sqlplus sys/Test1234@//localhost:1521/FREE as sysdba

# 以 non-SYSDBA 的身分與 CDB$ROOT 層級登入
sqlplus system/Test1234@//localhost:1521/FREE

# 連到 FREE 資料庫中的 Pluggable Database (PDB) FREEPDB1
sqlplus pdbadmin/Test1234@//localhost:1521/FREEPDB1
```

> 如果是應用程式要連接到 Oracle 資料庫，上述的連接字串就可以參考出所有必要的參數。

另一種連線方式則是透過「網路服務名稱」(Network Service Name) 或 TNS Name 這種方式連線：

1.  先進入 sqlplus
    
    ```bash
    sqlplus /nolog
    ```
    
2.  輸入以下命令進行連線
    
    ```sql
    CONNECT SYS@'(DESCRIPTION=(ADDRESS=(PROTOCOL=TCP)(HOST=localhost)(PORT=1521))(CONNECT_DATA=(SERVER=DEDICATED)(SERVICE_NAME=FREE)))' as sysdba
    Enter Password:
    ```
    

你也可以先設定好 `$env:TNS_ADMIN\network\admin\tnsnames.ora` 檔案，其內容範例如下：

```
MYDB =
    (DESCRIPTION=
        (ADDRESS=
            (PROTOCOL=TCP)
            (HOST=localhost)
            (PORT=1521)
        )
        (CONNECT_DATA=
            (SERVER=DEDICATED)
            (SERVICE_NAME=FREE)
        )
    )
```

接著你就可以這樣連線：

1.  先進入 sqlplus
    
    ```bash
    sqlplus /nolog
    ```
    
2.  輸入以下命令進行連線
    
    ```sql
    CONNECT SYS/Test1234@MYDB as sysdba
    ```
    

### 為容器中的 Oracle Database 23c Free 資料庫設定啟動腳本

在 Oracle Database 23c Free 容器中有兩個特殊的資料夾，當容器啟動後，會自動執行 Shell Script (`*.sh`) 或 PL/SQL (`*.sql`) 命令：

1.  `/opt/oracle/scripts/setup`
    
    當容器剛啟動，而且 Oracle 資料庫還沒有初始化時，這個資料夾中的腳本會在資料庫被初始化之後自動執行。
    
    如果你要確保執行順序，可以用數字當前綴，例如 `01_users.sql`、`02_permissions.sql`。
    
2.  `/opt/oracle/scripts/startup`
    
    當容器剛啟動，而且 Oracle 資料庫已經找到初始化過的資料庫實例時，這個資料夾中的腳本會在資料庫被初始化之後自動執行。
    
    如果你要確保執行順序，可以用數字當前綴，例如 `01_initial.sql`、`02_reset.sh`。
    

> 當然，你也可以透過 `-v G:\oracle\startup:/opt/oracle/scripts/startup` 這種方式掛載進去。

### 整理幾個常用的 PL/SQL 命令

-   列出所有的 Instances 名稱
    
    ```sql
    SELECT INSTANCE_NAME FROM V$INSTANCE;
    ```
    
-   查看當前用戶名稱
    
    ```sql
    SELECT USER FROM DUAL;
    ```
    
-   列出所有表格清單 (在當前用戶的 schema 下)
    
    ```sql
    SELECT TABLE_NAME FROM USER_TABLES;
    ```
    
-   列出所有 schema 中的表格 (需要有足夠的權限)
    
    ```sql
    SELECT TABLE_NAME FROM ALL_TABLES;
    ```
    
-   列出資料庫中的所有表格 (需要 DBA 權限)
    
    ```sql
    SELECT TABLE_NAME FROM DBA_TABLES;
    ```
    
-   查看表格結構
    
    ```sql
    DESCRIBE table_name;
    ```
    
    也可以簡寫:
    
    ```sql
    DESC table_name;
    ```
    
-   檢視資料庫狀態
    
    ```sql
    SELECT name, open_mode FROM v$database;
    ```
    
-   檢查安裝的 Oracle 版本
    
    ```sql
    SELECT * FROM v$version;
    ```
    
-   檢視當前的 SGA (System Global Area) 配置
    
    ```sql
    SHOW sga;
    ```
    
-   列出所有的表格空間 (Tablespaces)
    
    ```sql
    SELECT tablespace_name FROM dba_tablespaces;
    ```
    
-   檢視資料庫中的所有使用者
    
    ```sql
    -- 調整每頁顯示筆數
    SET PAGESIZE 50
    
    SELECT username FROM dba_users;
    ```
    
-   檢視 Instance 的組態參數設定
    
    ```sql
    SHOW parameter;
    ```
    
-   檢視當前連線的 Session 資訊
    
    ```sql
    SELECT sid, serial#, username, status FROM v$session;
    ```
    
-   建立一個新使用者
    
    ```sql
    CREATE USER new_user IDENTIFIED BY password;
    ```
    
-   給新使用者分配許可權 (例如：賦予 DBA 角色)
    
    ```sql
    GRANT dba TO new_user;
    ```
    
-   備份資料庫控制檔案
    
    ```sql
    ALTER DATABASE BACKUP CONTROLFILE TO TRACE;
    ```
    

## 相關連結

-   Oracle Database
    -   Oracle Database XE 產品介紹: [https://www.oracle.com/database/technologies/appdev/xe.html](https://www.oracle.com/database/technologies/appdev/xe.html)
    -   Oracle Database 23c Free 產品介紹: [https://www.oracle.com/database/free/](https://www.oracle.com/database/free/)
-   [Oracle Container Registry](https://container-registry.oracle.com)
    -   點擊 `Database` -> 點擊 `free` Repository -> 可以找到 `Oracle Database Free - Repository Detail` 頁面
    -   點擊 `Database` -> 點擊 `express` Repository -> 可以找到 `Oracle Database Express Edition - Repository Detail` 頁面
    -   [Oracle Database on Docker @ GitHub](https://github.com/oracle/docker-images/tree/main/OracleDatabase)
-   下載 SQL\*Plus 工具
    -   [Oracle Instant Client Downloads for Microsoft Windows (x64) 64-bit](https://www.oracle.com/tw/database/technologies/instant-client/winx64-64-downloads.html)
        -   先下載 `Basic Package` 壓縮檔
        -   再下載 `SQL*Plus Package` 壓縮檔
        -   將兩個壓縮檔解壓縮到同一個資料夾 (例如 `C:\instantclient_21_13` 資料夾)
        -   設定 `PATH` 環境變數到 `C:\instantclient_21_13` 即可。
