

 Amazon Redshift 將不再支援從修補程式 198 開始建立新的 Python UDFs。現有 Python UDF 將繼續正常運作至 2026 年 6 月 30 日。如需詳細資訊，請參閱[部落格文章](https://aws.amazon.com/blogs/big-data/amazon-redshift-python-user-defined-functions-will-reach-end-of-support-after-june-30-2026/)。

本文為英文版的機器翻譯版本，如內容有任何歧義或不一致之處，概以英文版為準。

# 資料庫安全
<a name="r_Database_objects"></a>

您可以控制哪些使用者可以存取哪些資料庫物件來管理資料庫安全性。您可以為使用者指派角色或群組，而您授予使用者、角色或群組的許可決定了他們可以存取哪些資料庫物件。

**Topics**
+ [Amazon Redshift 安全性概觀](c_security-overview.md)
+ [預設的資料庫使用者許可](r_Privileges.md)
+ [superuser](r_superusers.md)
+ [使用者](r_Users.md)
+ [Groups (群組)](r_Groups.md)
+ [結構描述](r_Schemas_and_tables.md)
+ [角色型存取控制 (RBAC)](t_Roles.md)
+ [資料列層級安全性](t_rls.md)
+ [中繼資料安全性](t_metadata_security.md)
+ [動態資料遮罩](t_ddm.md)
+ [限定範圍權限](t_scoped-permissions.md)

能否存取資料庫物件取決於您授予使用者或角色的許可。下列準則彙總資料庫安全性的運作方式：
+ 依預設，只對物件擁有者授予許可。
+ Amazon Redshift 資料庫使用者是可以連接至資料庫的具名使用者。使用者會以兩種方式獲得許可：直接明確地或隱含地將這些許可指派給帳戶、成為已獲得許可的群組成員。
+ 群組是可以集體獲指派許可，以簡化安全維護的使用者集合。
+ 結構描述是資料庫資料表和其他資料庫物件的集合。結構描述與檔案系統目錄相似，但結構描述無法巢狀化。使用者可獲得存取單一結構描述或多個結構描述的權限。

此外，Amazon Redshift 還採用下列功能，讓您更好地控制哪些使用者可以存取哪些資料庫物件：
+  角色型存取控制 (RBAC) 可讓您將許可指派給角色，然後再套用至使用者，讓您控制大型使用者群組的許可。與群組不同，角色可以繼承其他角色的許可。

  資料列層級安全 (RLS) 可讓您定義政策，限制所選擇資料列的存取權，然後將這些政策套用至使用者或群組。

   動態資料遮罩 (DDM) 可在查詢執行期轉換資料，進一步保護您的資料，讓您可以允許使用者存取資料，但不會暴露敏感詳細資料。

如需安全性實作的範例，請參閱[控制使用者和群組存取的範例](t_user_group_examples.md)。

如需保護資料的相關資訊，請參閱《Amazon Redshift 管理指南》**中的 [Amazon Redshift](https://docs.aws.amazon.com/redshift/latest/mgmt/iam-redshift-user-mgmt.html) 中的安全性。

# Amazon Redshift 安全性概觀
<a name="c_security-overview"></a>



Amazon Redshift 資料庫安全性不同於其他類型的 Amazon Redshift 安全性。除了本節描述的資料庫安全性外，Amazon Redshift 還提供這些功能來管理安全性：
+  **登入憑證** — 對 Amazon Redshift AWS 管理主控台的存取是由 AWS 您的帳戶許可所控制。如需詳細資訊，請參閱[登入資料](https://docs.aws.amazon.com/general/latest/gr/aws-security-credentials.html)。
+  **存取管理** — 若要控制對特定 Amazon Redshift 資源的存取，您可以定義 AWS Identity and Access Management (IAM) 帳戶。(如需詳細資訊，請參閱[控制 Amazon Redshift 資源的存取](https://docs.aws.amazon.com/redshift/latest/mgmt/iam-redshift-user-mgmt.html))。
+  **叢集安全群組** — 若要授予其他使用者 Amazon Redshift 叢集的傳入存取，您可以定義叢集安全群組，並將它與叢集建立關聯。如需詳細資訊，請參閱 [Amazon Redshift 叢集安全群組](https://docs.aws.amazon.com/redshift/latest/mgmt/working-with-security-groups.html)。
+  **VPC** — 若要使用虛擬聯網環境來保護叢集的存取，您可以在 Amazon 虛擬私有雲端 (VPC) 啟動叢集。如需詳細資訊，請參閱[管理虛擬私有雲端 (VPC)中的叢集](https://docs.aws.amazon.com/redshift/latest/mgmt/managing-clusters-vpc.html)。
+  **叢集加密** — 若要加密您的所有使用者建立的資料表中的資料，您可以在啟動叢集時開啟叢集加密。如需詳細資訊，請參閱 [Amazon Redshift 叢集](https://docs.aws.amazon.com/redshift/latest/mgmt/working-with-clusters.html)。
+  **SSL 連線** — 若要加密您的 SQL 用戶端與您的叢集之間的連線，您可以使用 Secure Sockets Layer (SSL) 加密。如需詳細資訊，請參閱[使用 SSL 連接至您的叢集](https://docs.aws.amazon.com/redshift/latest/mgmt/connecting-ssl-support.html)。
+  **載入資料加密** — 若要在您將資料表載入資料檔案上傳至 Amazon S3 時加密這些檔案，您可以使用伺服器端加密或用戶端加密。當您從伺服器端加密的資料載入時，Amazon S3 會以透明的方式處理解密。當您從用戶端加密的資料載入時，Amazon Redshift COPY 命令會在載入資料表時解密資料。如需詳細資訊，請參閱[將加密資料上傳到 Amazon S3](t_uploading-encrypted-data.md)。
+ **傳輸中的資料** — 為了保護您的 AWS 雲端內傳輸中的資料，Amazon Redshift 會使用硬體加速 SSL 與 Amazon S3 或 Amazon DynamoDB 通訊，以進行 COPY、UNLOAD、備份和還原操作。
+ **資料欄層級存取控制** — 若要讓資料的資料欄層級在 Amazon Redshift 中存取控制，請使用資料欄層級授權及撤銷陳述式，而不需實作檢視型存取控制或使用其他系統。
+ **資料列層級安全控制** — 若要具有 Amazon Redshift 中資料的資料列層級安全控制，請建立政策並將政策附加至角色或使用者，限制他們存取政策中定義的資料列。

# 預設的資料庫使用者許可
<a name="r_Privileges"></a>

當您建立資料庫物件時，您是其擁有者。依預設，只有超級使用者或物件擁有者才能查詢物件、修改物件，或授予物件許可。對於要使用物件的使用者，您必須將必要的許可授予使用者或包含使用者的群組。資料庫超級使用者具有與資料庫擁有者相同的許可。

Amazon Redshift 支援下列許可：SELECT、INSERT、UPDATE、DELETE、REFERENCES、CREATE、TEMPORARY 和 USAGE。不同的許可與不同的物件類型相關聯。如需有關 Amazon Redshift 支援的資料庫物件許可資訊，請參閱 [GRANT](r_GRANT.md) 命令。

只有擁有者才有修改或銷毀物件的許可。

根據預設，所有使用者對資料庫的 PUBLIC 結構描述都具有 CREATE 和 USAGE 許可。若要不允許使用者在資料庫的 PUBLIC 結構描述內建立物件，請使用 REVOKE 命令來移除該許可。

若要撤銷先前授予的許可，請使用 [REVOKE](r_REVOKE.md) 命令。物件擁有者的許可 (例如 DROP、GRANT 和 REVOKE 許可) 是隱含的，而且無法授予或撤銷。物件擁有者可以撤銷自己的普通許可，例如，使自己以及其他人只能讀取資料表。無論 GRANT 和 REVOKE 命令，超級使用者都能保留所有許可。

# 超級使用者
<a name="r_superusers"></a>

<a name="def_superusers"></a>資料庫超級使用者具有與所有資料庫之資料庫擁有者相同的許可。

*admin* 使用者 (即您啟動叢集時所建立的使用者) 是超級使用者。

您必須是超級使用者才能建立超級使用者。

Amazon Redshift 系統資料表和系統檢視分為只有超級使用者才能看見或所有使用者都能看見。只有超級使用者才能查詢指定為「超級使用者才能看見」的系統資料表和系統檢視。如需相關資訊，請參閱[SYS 監控檢視](serverless_views-monitoring.md)。

超級使用者可以檢視所有目錄資料表。如需相關資訊，請參閱[系統目錄資料表](c_intro_catalog_views.md)。

資料庫超級使用者會略過所有許可檢查。無論 GRANT 和 REVOKE 命令，超級使用者都能保留所有許可。使用超級使用者角色時必須謹慎。建議您以不是超級使用者的角色執行大部分工作。您可以使用更嚴格的許可建立管理員角色。如需有關建立角色的詳細資訊，請參閱 [角色型存取控制 (RBAC)](t_Roles.md)

若要建立新的資料庫超級使用者，請以超級使用者身分登入資料庫，然後發出 CREATE USER 命令，或搭配 CREATEUSER 許可的 ALTER USER 命令。

```
CREATE USER adminuser CREATEUSER PASSWORD '1234Admin';
ALTER USER adminuser CREATEUSER;
```

若要建立、修改或捨棄超級使用者，請使用相同的命令來管理使用者。如需詳細資訊，請參閱[建立、更改和刪除使用者](r_Users-creatingaltering-and-deleting-users.md)。

# 使用者
<a name="r_Users"></a>

您可以使用 Amazon Redshift SQL 命令 CREATE USER 和 ALTER USER 來建立和管理資料庫使用者。或是，您可以使用自訂的 Amazon Redshift JDBC 或 ODBC 驅動程式設定您的 SQL 用戶端。這些驅動程式會管理隨著資料庫登入的一部分建立使用者資料庫和暫時密碼的程序。

驅動程式會根據 AWS Identity and Access Management (IAM) 身分驗證來驗證資料庫使用者。如果您已在 外部管理使用者身分 AWS，您可以使用 SAML 2.0 相容身分提供者 (IdP) 來管理對 Amazon Redshift 資源的存取。您可以使用 IAM 角色來設定 IdP AWS ，並允許聯合身分使用者產生臨時資料庫登入資料並登入 Amazon Redshift 資料庫。如需詳細資訊，請參閱[使用 IAM 身分驗證產生資料庫使用者登入資料](https://docs.aws.amazon.com/redshift/latest/mgmt/generating-user-credentials.html)。

Amazon Redshift 使用者帳戶只能由資料庫超級使用者建立和捨棄。使用者在登入 Amazon Redshift 時會進行身份驗證。他們可以擁有資料庫和資料庫物件 (例如資料表)。他們也可以將這些物件的許可授予使用者、群組和結構描述，以控制誰有權存取哪個物件。具有 CREATE DATABASE 權限的使用者可以建立資料庫，並授予那些資料庫的許可。超級使用者具有所有資料庫的資料庫所有權。

# 建立、更改和刪除使用者
<a name="r_Users-creatingaltering-and-deleting-users"></a>

資料庫使用者適用於資料倉儲叢集 (而且不是根據個別資料庫)。
+  若要建立使用者，請使用 [CREATE USER](r_CREATE_USER.md) 命令。
+  若要建立超級使用者，請使用 [CREATE USER](r_CREATE_USER.md) 命令與 CREATEUSER 選項搭配。
+ 若要移除現有的使用者，請使用 [DROP USER](r_DROP_USER.md) 命令。
+ 若要變更使用者 (例如變更密碼)，請使用 [ALTER USER](r_ALTER_USER.md) 命令。
+ 若要檢視使用者清單，請查詢 PG\$1USER 目錄資料表。

  ```
  select * from pg_user;
  
    usename   | usesysid | usecreatedb | usesuper | usecatupd |  passwd  | valuntil | useconfig
  ------------+----------+-------------+----------+-----------+----------+----------+-----------
   rdsdb      |        1 | t           | t        | t         | ******** |          |
   masteruser |      100 | t           | t        | f         | ******** |          |
   dwuser     |      101 | f           | f        | f         | ******** |          |
   simpleuser |      102 | f           | f        | f         | ******** |          |
   poweruser  |      103 | f           | t        | f         | ******** |          |
   dbuser     |      104 | t           | f        | f         | ******** |          |
  (6 rows)
  ```

# Groups (群組)
<a name="r_Groups"></a>

群組是全部被授予與群組相關聯之任何許可的使用者集合。您可以使用群組來指派許可。例如，您可以為銷售、管理和支援建立不同的群組，並給與每個群組中的使用者適當權限，讓他們可在工作時存取所需的資料。您可以授予或撤銷群組層級的許可，而且那些變更將適用於群組的所有成員，但超級使用者除外。

若要檢視所有使用者群組，請查詢 PG\$1GROUP 系統目錄資料表：

```
select * from pg_group;
```

例如，若要依群組列出所有資料庫使用者，請執行下列 SQL。

```
SELECT u.usesysid
,g.groname
,u.usename
FROM pg_user u
LEFT JOIN pg_group g ON u.usesysid = ANY (g.grolist)
```

# 建立、更改和刪除群組
<a name="r_Groups-creating-altering-and-deleting-groups"></a>

只有超級使用者才能建立、更改或捨棄群組。

您可以執行下列動作：
+ 若要建立群組，請使用 [CREATE GROUP](r_CREATE_GROUP.md) 命令。
+ 若要將使用者新增至現有群組或從中移除使用者，請使用 [ALTER GROUP](r_ALTER_GROUP.md) 命令。
+ 若要刪除群組，請使用 [DROP GROUP](r_DROP_GROUP.md) 命令。此命令只會捨棄群組，不會捨棄其成員使用者。

# 控制使用者和群組存取的範例
<a name="t_user_group_examples"></a>

此範例會建立使用者群組和使用者，然後將連接至 Web 應用程式用戶端之 Amazon Redshift 資料庫的各種許可授予他們。此範例採用三個使用者群組：Web 應用程式的一般使用者、Web 應用程式的進階使用者，以及 Web 開發人員。

如需如何從群組移除使用者的相關資訊，請參閱 [ALTER GROUP](r_ALTER_GROUP.md)。

1. 建立將在其中指派使用者的群組。下列一組命令會建立三個不同的使用者群組：

   ```
   create group webappusers;
   
   create group webpowerusers;
   
   create group webdevusers;
   ```

1.  建立數個具有不同許可的資料庫使用者，並將他們新增至群組。

   1.  建立兩個使用者，並將他們新增至 WEBAPPUSERS 群組：

      ```
      create user webappuser1 password 'webAppuser1pass'
      in group webappusers;
      
      create user webappuser2 password 'webAppuser2pass'
      in group webappusers;
      ```

   1.  建立 Web 開發人員使用者，並將其新增至 WEBDEVUSERS 群組：

      ```
      create user webdevuser1 password 'webDevuser2pass'
      in group webdevusers;
      ```

   1.  建立一個超級使用者。此使用者將具有建立其他使用者的管理權限：

      ```
      create user webappadmin  password 'webAppadminpass1'
      createuser;
      ```

1.  建立要與 Web 應用程式所使用之資料庫資料表相關聯的結構描述，並將各種使用者群組存取授予這個結構描述：

   1.  建立 WEBAPP 結構描述：

      ```
      create schema webapp;
      ```

   1.  將 USAGE 許可授予 WEBAPPUSERS 群組：

      ```
      grant usage on schema webapp to group webappusers;
      ```

   1.  將 USAGE 許可授予 WEBPOWERUSERS 群組：

      ```
      grant usage on schema webapp to group webpowerusers;
      ```

   1.  將 ALL 許可授予 WEBDEVUSERS 群組：

      ```
      grant all on schema webapp to group webdevusers;
      ```

   基本使用者和群組現在已完成設定。您現在可以修改使用者和群組。

1.  例如，下列命令會更改 WEBAPPUSER1 的 search\$1path 參數。

   ```
   alter user webappuser1 set search_path to webapp, public;
   ```

   在未指定結構描述的情況下，當簡單名稱參考物件時，SEARCH\$1PATH 會指定資料庫物件 (例如資料表和函數) 的結構描述搜尋順序。

1.  您也可以在建立群組之後將使用者新增至群組，例如將 WEBAPPUSER2 新增至 WEBPOWERUSERS 群組：

   ```
   alter group webpowerusers add user webappuser2;
   ```

# 結構描述
<a name="r_Schemas_and_tables"></a>

資料庫包含一或多個具名結構描述。資料庫中的每個結構描述都包含資料表和其他類型的具名物件。依預設，資料庫具有名為 PUBLIC 的單一結構描述。您可以使用結構描述，在常見名稱下將資料庫物件分組。結構描述與檔案系統目錄相似，但結構描述無法巢狀化。

相同的資料庫物件名稱可在相同資料庫的不同結構描述中使用，而不會發生衝突。例如，MY\$1SCHEMA 和 YOUR\$1SCHEMA 都可以包含名為 MYTABLE 的資料表。具有必要許可的使用者可以跨資料庫中的多個結構描述存取物件。

依預設，物件是在資料庫搜尋路徑中的第一個結構描述內建立。如需相關資訊，請參閱本節後續的[搜尋路徑](#c_Search_path)。

結構描述可以協助在多使用者環境中採用下列方式解決組織和並行問題：
+ 讓多個開發人員可在同一個資料庫中工作，而彼此不會互相干擾。
+ 將資料庫物件組織成邏輯群組，讓它們更便於管理。
+ 讓應用程式能夠將其物件放入個別結構描述中，以便其名稱將不會與其他應用程式使用的物件名稱發生衝突。

## 搜尋路徑
<a name="c_Search_path"></a>

搜尋路徑是在 search\$1path 參數中搭配逗號分隔的結構描述名稱清單定義的。當以未包括結構描述限定詞的簡單名稱參考物件 (如資料表或函數) 時，此搜尋路徑會指定搜尋結構描述的順序。

如果在未指定目標結構描述的情況下建立物件，則物件會新增至搜尋路徑中列出的第一個結構描述。當名稱相同的物件存在於不同結構描述時，未指定結構描述的物件名稱將參考搜尋路徑中的第一個結構描述，其中包含具有該名稱的物件。

若要變更目前工作階段的預設結構描述，請使用 [SET](r_SET.md) 命令。

如需詳細資訊，請參閱《組態參考》中的 [search\$1path](r_search_path.md) 說明。

# 建立、更改和刪除結構描述
<a name="r_Schemas_and_tables-creating-altering-and-deleting-schemas"></a>

任何使用者都可以建立結構描述，以及更改或捨棄他們擁有的結構描述。

您可以執行下列動作：
+ 若要建立結構描述，請使用 [CREATE SCHEMA](r_CREATE_SCHEMA.md) 命令。
+ 若要變更結構描述的擁有者，請使用 [ALTER SCHEMA](r_ALTER_SCHEMA.md) 命令。
+ 若要刪除結構描述及其物件，請使用 [DROP SCHEMA](r_DROP_SCHEMA.md)命令。
+ 若要在結構描述內建立資料表，請建立格式為 *schema\$1name.table\$1name* 的資料表。

若要檢視所有結構描述的清單，請查詢 PG\$1NAMESPACE 系統目錄資料表：

```
select * from pg_namespace;
```

若要檢視屬於結構描述的資料表清單，請查詢 PG\$1TABLE\$1DEF 系統目錄資料表。例如，下列查詢會傳回 PG\$1CATALOG 結構描述的資料表清單。

```
select distinct(tablename) from pg_table_def
where schemaname = 'pg_catalog';
```

# 結構描述型許可
<a name="r_Schemas_and_tables-schema-based-privileges"></a>

 結構描述型許可是由結構描述的擁有者決定：
+ 根據預設，所有使用者對資料庫的 PUBLIC 結構描述都具有 CREATE 和 USAGE 許可。若要不允許使用者在資料庫的 PUBLIC 結構描述內建立物件，請使用 [REVOKE](r_REVOKE.md) 命令來移除該許可。
+ 除非物件擁有者將 USAGE 許可授予他們，否則使用者無法存取結構描述中他們未擁有的任何物件。
+ 如果已將另一個使用者所建立之結構描述的 CREATE 許可授予使用者，則那些使用者便可在該結構描述中建立物件。

# 角色型存取控制 (RBAC)
<a name="t_Roles"></a>

透過使用角色型存取控制 (RBAC) 在 Amazon Redshift 中管理資料庫許可，您可以簡化 Amazon Redshift 中的安全許可管理。您可以控制使用者在廣泛或精細層級上執行的動作，以確保敏感資料的存取安全。您也可以控制使用者存取通常僅限超級使用者存取的工作。透過將不同許可指派給不同角色，並將其指派給不同的使用者，您可以更精細地控制使用者存取權。

獲派角色的使用者只能執行其授權指派角色所指定的工作。例如，具有指派角色且具有 CREATE TABLE 和 DROP TABLE 許可的使用者只有執行這些工作的授權。您可以透過授予不同層級的安全許可給不同的使用者，以控制使用者存取權，讓他們能存取工作所需的資料。

RBAC 會根據使用者的角色需求，將最低許可政策套用至使用者，而不論所涉及的物件類型為何。授予和撤銷許可是在角色層級上執行的，而不需要更新個別資料庫物件的許可。

透過 RBAC，您可以建立具有許可的角色，使其可執行過去需要超級使用者許可的命令。使用者只要獲得包含這些許可的角色授權，就可以執行這些命令。同樣地，您也可以建立角色來限制對某些命令的存取，並將角色指派給已獲得該角色授權的超級使用者或使用者。

若要了解 Amazon Redshift RBAC 的運作方式，請觀看以下影片。

[![AWS Videos](http://img.youtube.com/vi/https://www.youtube.com/embed/IhHQ7mZ-tp4/0.jpg)](http://www.youtube.com/watch?v=https://www.youtube.com/embed/IhHQ7mZ-tp4)


# 角色階層
<a name="t_role_hierarchy"></a>

*角色*是您可以指派給使用者或其他角色的許可集合。您可以將系統或資料庫許可指派給角色。使用者會繼承指派角色的許可。

在 RBAC 中，使用者可以擁有巢狀角色。您可以將角色授予使用者和角色。將角色授予使用者時，您可以使用此角色包含的所有權限來授權使用者。將角色 r1 授予使用者時，您可以使用 r1 的許可來授權使用者。使用者現在擁有 r1 的許可，以及他們已有的任何現有許可。

將角色 (r1) 授予另一個角色 (r2) 時，您可以使用 r1 的所有許可來授權 r2。此外，將 r2 授予另一個角色 (r3) 時，r3 的許可會結合 r1 和 r2 的許可。角色階層會讓 r2 從 r1 繼承許可。Amazon Redshift 會透過每個角色授權來傳播許可。將 r1 授予 r2，然後再將 r2 授予 r3，即可將這三個角色的所有許可授權給 r3。因此，透過將 r3 授予使用者，使用者就會擁有這三個角色的所有許可。

Amazon Redshift 不允許建立角色授權循環。當巢狀角色被指派回角色階層中較早的角色 (例如 r3 被指派回 r1) 時，就會發生角色授權循環。如需建立角色及管理角色指派的相關資訊，請參閱 [管理 RBAC 中的角色](r_roles-managing.md)。

# 角色指派
<a name="t_role_assignment"></a>

超級使用者和擁有 CREATE ROLE 許可的一般使用者可以使用 CREATE ROLE 陳述式來建立角色。超級使用者和角色管理員可以使用 GRANT ROLE 陳述式將角色授予其他人。他們可以使用 REVOKE ROLE 陳述式來撤銷其他人的角色，以及使用 DROP ROLE 陳述式來捨棄角色。角色管理員包括角色擁有者和獲派角色具有 ADMIN OPTION 許可的使用者。

只有超級使用者或角色管理員可以授予和撤銷角色。您可以對一個或多個角色或使用者授予或撤銷一個或多個角色。在 GRANT ROLE 陳述式中使用 WITH ADMIN OPTION 選項會為所有承授者提供所有授予角色的管理選項。

Amazon Redshift 支援不同的角色指派組合，例如授予多個角色或擁有多個承授者。WITH ADMIN OPTION 僅適用於使用者，而不適用於角色。同樣地，使用 REVOKE ROLE 陳述式中的 WITH ADMIN OPTION 選項，可移除承授者的角色和管理授權。與 ADMIN OPTION 搭配使用時，只能撤銷角色的管理授權。

下列範例會從 `user2` 中撤銷 `sample_role2` 角色的管理授權。

```
REVOKE ADMIN OPTION FOR sample_role2 FROM user2;
```

如需建立角色及管理角色指派的相關資訊，請參閱 [管理 RBAC 中的角色](r_roles-managing.md)。

# Amazon Redshift 系統定義角色
<a name="r_roles-default"></a>

Amazon Redshift 會提供使用特定許可定義的系統定義角色。系統專屬角色會以 `sys:` 字首開頭。只有具有適當存取權的使用者才能修改系統定義角色或建立自訂的系統定義角色。您無法針對自訂系統定義角色使用 `sys:` 字首。

下表摘要說明角色及其許可。

[\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/zh_tw/redshift/latest/dg/r_roles-default.html)

## 用於資料共用的系統定義角色和使用者
<a name="r_roles-datashare"></a>

 Amazon Redshift 會建立供內部使用的角色和使用者，以對應資料共用和資料共用取用者。每個內部角色名稱和使用者名稱都有預留命名空間字首 `ds:`。其格式如下：

[\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/zh_tw/redshift/latest/dg/r_roles-default.html)

 每個資料共用都會有為其建立的資料共用角色。此角色具有目前授予資料共用的所有許可。每個資料共用取用者都會有為其建立的資料共用使用者。此使用者擁有授予單一資料共用角色的許可。新增至多個資料共用的取用者會擁有為每個資料共用建立的資料共用使用者。

須有這些使用者和角色，資料共用才能正常運作。這些使用者和角色無法修改或捨棄，也無法供客戶存取或用於其執行的任何任務。您可以放心忽略它們。如需資料共用的詳細資訊，請參閱 [Amazon Redshift 中的跨叢集共用資料](https://docs.aws.amazon.com/redshift/latest/dg/datashare-overview.html)。

**注意**  
您無法使用 `ds:` 字首來建立使用者定義的角色或使用者。

# RBAC 的系統許可
<a name="r_roles-system-privileges"></a>

下列是您可以對角色授予或撤銷的系統許可清單。

[\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/zh_tw/redshift/latest/dg/r_roles-system-privileges.html)

# 資料庫物件許可
<a name="r_roles-database-privileges"></a>

除了系統許可外，Amazon Redshift 還包含可定義存取選項的資料庫物件許可。其中包含的選項包括能夠讀取資料表和檢視中的資料、寫入資料、建立資料表及捨棄資料表。如需詳細資訊，請參閱[GRANT](r_GRANT.md)。

透過使用 RBAC，您可以將資料庫物件許可指派給角色，類似於使用系統許可的方式。然後，您可以將角色指派給使用者、授權具有系統許可的使用者，以及使用資料庫許可授權使用者

# RBAC 的 ALTER DEFAULT PRIVILEGES
<a name="r_roles-alter-default-privileges"></a>

使用 ALTER DEFAULT PRIVILEGES 陳述式來定義日後由指定使用者建立的物件將套用的存取許可預設設定。根據預設，使用者只能變更自己擁有的預設存取許可。使用 RBAC，您可以設定角色的預設存取許可。如需詳細資訊，請參閱 [ALTER DEFAULT PRIVILEGES](r_ALTER_DEFAULT_PRIVILEGES.md) 命令。

RBAC 可讓您將資料庫物件許可指派給角色，類似於系統許可。然後，您可以將角色指派給使用者、使用系統和/或資料庫許可授權使用者。

# RBAC 中角色使用的考量
<a name="r_role-usage-notes"></a>

使用 RBAC 角色時，請考慮以下事項：
+ Amazon Redshift 不允許循環的角色授權。您不能將 r1 授予 r2，然後又將 r2 授予 r1。
+ RBAC 適用於原生 Amazon Redshift 物件和 Amazon Redshift Spectrum 資料表。
+ 身為 Amazon Redshift 管理員，您可以將叢集升級至最新的維護修補程式，以開始使用 RBAC。
+ 只有超級使用者和擁有 CREATE ROLE 系統許可的使用者才能建立角色。
+ 只有超級使用者和角色管理員可以修改和捨棄角色。
+ 角色名稱不能與使用者名稱相同。
+ 角色名稱不能包含無效字元，例如「:/\$1n」。
+ 角色名稱不能是保留字，例如 PUBLIC。
+ 角色名稱不能以預設角色的保留字首開頭 (`sys:`)。
+ 將具有 RESTRICT 參數的角色授予其他角色時，您無法刪除該角色。預設設定為 RESTRICT。當您嘗試捨棄繼承另一個角色的角色時，Amazon Redshift 會擲回錯誤。
+ 沒有角色管理員許可的使用者無法予與或撤銷角色。
+ 系統資料表和檢視並未完全支援 RBAC。系統資料表和檢視的 RBAC 許可不會在升級、降級或調整規模的過程中持續存在。建議使用 [Amazon Redshift 系統定義角色用於資料共用的系統定義角色和使用者](r_roles-default.md) 來管理系統資料表和檢視許可。如需系統資料表的詳細資訊，請前往 [系統資料表和檢視參考](cm_chap_system-tables.md)。

# 管理 RBAC 中的角色
<a name="r_roles-managing"></a>

欲執行下列動作，請使用下列命令：
+ 若要建立角色，請使用 [CREATE ROLE](r_CREATE_ROLE.md) 命令。
+ 若要重新命名角色或變更角色的擁有者，請使用 [ALTER ROLE](r_ALTER_ROLE.md) 命令。
+ 若要刪除角色，請使用 [DROP ROLE](r_DROP_ROLE.md) 命令。
+ 若要將角色授予使用者，請使用 [GRANT](r_GRANT.md) 命令。
+ 若要撤銷使用者的角色，請使用 [REVOKE](r_REVOKE.md) 命令。
+ 若要將系統許可授予角色，請使用 [GRANT](r_GRANT.md) 命令。
+ 若要撤銷角色的系統許可，請使用 [REVOKE](r_REVOKE.md) 命令。

若要檢視叢集或工作群組中的角色清單，請參閱 [SVV\$1ROLES](r_SVV_ROLES.md)。

# 教學課程：使用 RBAC 建立角色並進行查詢
<a name="r_tutorial-RBAC"></a>

透過 RBAC，您可以建立具有許可的角色，使其可執行過去需要超級使用者許可的命令。使用者只要獲得包含這些許可的角色授權，就可以執行這些命令。

在本教學課程中，您會使用角色型存取控制 (RBAC) 來管理您在資料庫中建立的許可。然後您會連線到資料庫，並透過兩個不同的角色查詢資料庫，以測試 RBAC 的功能。

您建立並用來查詢資料庫的兩個角色為 `sales_ro` 和 `sales_rw`。您以具有 `sales_ro` 角色的使用者身分建立 `sales_ro` 角色並查詢資料。`sales_ro` 使用者只能使用 SELECT 命令，而無法使用 UPDATE 命令。然後，您以具有 `sales_rw` 角色的使用者身分建立 `sales_rw` 角色並查詢資料。`sales_rw` 使用者可使用 SELECT 命令和 UPDATE 命令。

此外，您可以建立角色來限制對某些命令的存取，並將角色指派給超級使用者或使用者。

**工作**
+ [先決條件](#tutorial-rbac-prereqs)
+ [步驟 1：建立管理員使用者](#tutorial-rbac-step1)
+ [步驟 2：設定結構描述](#tutorial-rbac-step2)
+ [步驟 3：建立唯讀使用者](#tutorial-rbac-step3)
+ [步驟 4：以唯讀使用者身分查詢資料](#tutorial-rbac-step4)
+ [步驟 5：建立讀寫使用者](#tutorial-rbac-step5)
+ [步驟 6：以具有繼承唯讀角色的使用者身分查詢資料](#tutorial-rbac-step6)
+ [步驟 7：對讀寫角色授予更新和插入許可](#tutorial-rbac-step7)
+ [步驟 8：以讀寫使用者身分查詢資料](#tutorial-rbac-step8)
+ [步驟 9：以管理員使用者身分分析和清空資料庫中的資料表](#tutorial-rbac-step9)
+ [步驟 10：以讀寫使用者身分截斷資料表](#tutorial-rbac-step10)
+ [RBAC 的系統函式 (選用)](#tutorial-rbac-system-functions)
+ [RBAC 的系統檢視 (選用)](#tutorial-rbac-system-views)
+ [搭配 RBAC 使用資料列層級安全 (選用)](#tutorial-rbac-rls)

## 先決條件
<a name="tutorial-rbac-prereqs"></a>
+ 建立透過 TICKIT 範例資料庫載入的 Amazon Redshift 叢集或無伺服器工作群組。若要建立無伺服器工作群組，請參閱[開始使用 Redshift Serverless 資料倉儲](https://docs.aws.amazon.com/redshift/latest/gsg/new-user-serverless.html)。若要建立叢集，請參閱[建立範例 Amazon Redshift 叢集](https://docs.aws.amazon.com/redshift/latest/gsg/rs-gsg-launch-sample-cluster.html)。如需 TICKIT 範例庫的相關資訊，請參閱 [範本資料庫](c_sampledb.md)。
+ 可存取具有超級使用者或角色管理員許可的使用者。只有超級使用者或角色管理員可以授予和撤銷角色。如需 RBAC 所需許可的詳細資訊，請參閱 [RBAC 的系統許可](r_roles-system-privileges.md)。
+ 請參閱[RBAC 中角色使用的考量](r_role-usage-notes.md)。

## 步驟 1：建立管理員使用者
<a name="tutorial-rbac-step1"></a>

若要針對本教學課程進行設定，請建立資料庫管理員角色，並在此步驟中將其附加至資料庫管理員使用者。您必須以超級使用者或角色管理員的身分建立資料庫管理員。

在 Amazon Redshift [查詢編輯器 v2](https://docs.aws.amazon.com/redshift/latest/mgmt/query-editor-v2-using.html) 中執行所有查詢。

1. 若要建立管理員角色 db\$1admin，請使用下列範例。

   ```
   CREATE ROLE db_admin;
   ```

1. 若要建立名為 dbadmin 的資料庫使用者，請使用下列範例。

   ```
   CREATE USER dbadmin PASSWORD 'Test12345';
   ```

1. 若要將名為 sys:dba 的系統定義角色授予 db\$1admin 角色，請使用下列範例。獲得授予的 sys:dba 角色後，dbadmin 使用者就可以建立結構描述和資料表。如需詳細資訊，請參閱[Amazon Redshift 系統定義角色用於資料共用的系統定義角色和使用者](r_roles-default.md)。

## 步驟 2：設定結構描述
<a name="tutorial-rbac-step2"></a>

在此步驟中，您會以資料庫管理員的身分連線至資料庫。然後您會建立兩個結構描述，並在其中新增資料。

1. 使用查詢編輯器 v2 以 dbadmin 使用者身分連線至 dev 資料庫。如需連線至資料庫的詳細資訊，請參閱[使用查詢編輯器 v2](https://docs.aws.amazon.com/redshift/latest/mgmt/query-editor-v2-using.html)。

1. 若要建立銷售和行銷資料庫結構描述，請使用下列範例。

   ```
   CREATE SCHEMA sales;
   CREATE SCHEMA marketing;
   ```

1. 若要在銷售結構描述的資料表中建立和插入值，請使用下列範例。

   ```
   CREATE TABLE sales.cat(
   catid smallint,
   catgroup varchar(10),
   catname varchar(10),
   catdesc varchar(50)
   );
   INSERT INTO sales.cat(SELECT * FROM category);
   
   CREATE TABLE sales.dates(
   dateid smallint,
   caldate date,
   day char(3),
   week smallint,
   month char(5),
   qtr char(5),
   year smallint,
   holiday boolean
   );
   INSERT INTO sales.dates(SELECT * FROM date);
   
   CREATE TABLE sales.events(
   eventid integer,
   venueid smallint,
   catid smallint,
   dateid smallint,
   eventname varchar(200),
   starttime timestamp
   );
   INSERT INTO sales.events(SELECT * FROM event);
   
    CREATE TABLE sales.sale(
   salesid integer,
   listid integer,
   sellerid integer,
   buyerid integer,
   eventid integer,
   dateid smallint,
   qtysold smallint,
   pricepaid decimal(8,2),
   commission decimal(8,2),
   saletime timestamp
   );
   INSERT INTO sales.sale(SELECT * FROM sales);
   ```

1. 若要在行銷結構描述的資料表中建立和插入值，請使用下列範例。

   ```
   CREATE TABLE marketing.cat(
   catid smallint,
   catgroup varchar(10),
   catname varchar(10),
   catdesc varchar(50)
   );
   INSERT INTO marketing.cat(SELECT * FROM category);
   
   CREATE TABLE marketing.dates(
   dateid smallint,
   caldate date,
   day char(3),
   week smallint,
   month char(5),
   qtr char(5),
   year smallint,
   holiday boolean
   );
   INSERT INTO marketing.dates(SELECT * FROM date);
   
   CREATE TABLE marketing.events(
   eventid integer,
   venueid smallint,
   catid smallint,
   dateid smallint,
   eventname varchar(200),
   starttime timestamp
   );
   INSERT INTO marketing.events(SELECT * FROM event);
   
   CREATE TABLE marketing.sale(
   marketingid integer,
   listid integer,
   sellerid integer,
   buyerid integer,
   eventid integer,
   dateid smallint,
   qtysold smallint,
   pricepaid decimal(8,2),
   commission decimal(8,2),
   saletime timestamp
   );
   INSERT INTO marketing.sale(SELECT * FROM marketing);
   ```

## 步驟 3：建立唯讀使用者
<a name="tutorial-rbac-step3"></a>

在此步驟中，您會建立唯讀角色並為該唯讀角色建立 salesanalyst 使用者。銷售分析師只需要以唯讀方式存取銷售結構描述中的資料表，即可完成尋找產生最高佣金事件的指派任務。

1. 以 dbadmin 使用者身分連線至資料庫。

1. 若要建立 sales\$1ro 角色，請使用下列範例。

   ```
   CREATE ROLE sales_ro;
   ```

1. 若要建立 salesanalyst 使用者，請使用下列範例。

   ```
   CREATE USER salesanalyst PASSWORD 'Test12345';
   ```

1. 若要對 sales\$1ro 角色授予使用和選取銷售結構描述之物件的權限，請使用下列範例。

   ```
   GRANT USAGE ON SCHEMA sales TO ROLE sales_ro;
   GRANT SELECT ON ALL TABLES IN SCHEMA sales TO ROLE sales_ro;
   ```

1. 若要對 salesanalyst 使用者授予 sales\$1ro 角色，請使用下列範例。

   ```
   GRANT ROLE sales_ro TO salesanalyst;
   ```

## 步驟 4：以唯讀使用者身分查詢資料
<a name="tutorial-rbac-step4"></a>

在此步驟中，salesanalyst 使用者會查詢銷售結構描述中的資料。然後 salesanalyst 使用者會嘗試更新行銷結構描述中的資料表和讀取資料表。

1. 以 salesanalyst 使用者身分連線至資料庫。

1. 若要尋找佣金最高的 10 筆銷售，請使用下列範例。

   ```
   SET SEARCH_PATH TO sales;
   SELECT DISTINCT events.dateid, sale.commission, cat.catname
   FROM sale, events, dates, cat   
   WHERE events.dateid=dates.dateid AND events.dateid=sale.dateid AND events.catid = cat.catid
   ORDER BY 2 DESC LIMIT 10;
                  
   +--------+------------+----------+
   | dateid | commission | catname  |
   +--------+------------+----------+
   |   1880 |     1893.6 | Pop      |
   |   1880 |     1893.6 | Opera    |
   |   1880 |     1893.6 | Plays    |
   |   1880 |     1893.6 | Musicals |
   |   1861 |       1500 | Plays    |
   |   2003 |       1500 | Pop      |
   |   1861 |       1500 | Opera    |
   |   2003 |       1500 | Plays    |
   |   1861 |       1500 | Musicals |
   |   1861 |       1500 | Pop      |
   +--------+------------+----------+
   ```

1. 若要從銷售結構描述中的事件資料表選取 10 個事件，請使用下列範例。

   ```
   SELECT * FROM sales.events LIMIT 10;
                  
   +---------+---------+-------+--------+--------------------+---------------------+
   | eventid | venueid | catid | dateid |     eventname      |      starttime      |
   +---------+---------+-------+--------+--------------------+---------------------+
   |    4836 |      73 |     9 |   1871 | Soulfest           | 2008-02-14 19:30:00 |
   |    5739 |      41 |     9 |   1871 | Fab Faux           | 2008-02-14 19:30:00 |
   |     627 |     229 |     6 |   1872 | High Society       | 2008-02-15 14:00:00 |
   |    2563 |     246 |     7 |   1872 | Hamlet             | 2008-02-15 20:00:00 |
   |    7703 |      78 |     9 |   1872 | Feist              | 2008-02-15 14:00:00 |
   |    7903 |      90 |     9 |   1872 | Little Big Town    | 2008-02-15 19:30:00 |
   |    7925 |     101 |     9 |   1872 | Spoon              | 2008-02-15 19:00:00 |
   |    8113 |      17 |     9 |   1872 | Santana            | 2008-02-15 15:00:00 |
   |     463 |     303 |     8 |   1873 | Tristan und Isolde | 2008-02-16 19:00:00 |
   |     613 |     236 |     6 |   1873 | Pal Joey           | 2008-02-16 15:00:00 |
   +---------+---------+-------+--------+--------------------+---------------------+
   ```

1. 若要嘗試更新 eventid 1 的 eventname，請執行下列範例。此範例將導致許可遭拒錯誤，因為 salesanalyst 使用者對銷售結構描述中的事件資料表只擁有 SELECT 許可。若要更新事件資料表，您必須對 sales\$1ro 角色授予 UPDATE 許可。如需授予更新資料表之許可的詳細資訊，請參閱 [GRANT](r_GRANT.md) 的 UPDATE 參數。如需 UPDATE 命令的詳細資訊，請參閱 [UPDATE](r_UPDATE.md)。

   ```
   UPDATE sales.events
   SET eventname = 'Comment event'
   WHERE eventid = 1;
                     
   ERROR: permission denied for relation events
   ```

1. 若要嘗試從行銷結構描述的事件資料表中選取所有內容，請使用下列範例。此範例將導致許可遭拒錯誤，因為 salesanalyst 使用者對銷售結構描述中的事件資料表只具有 SELECT 許可。若要從行銷結構描述的事件資料表中選取資料，您必須對 sales\$1ro 角色授予行銷結構描述中事件資料表的 SELECT 許可。

   ```
   SELECT * FROM marketing.events;
                  
                  ERROR: permission denied for schema marketing
   ```

## 步驟 5：建立讀寫使用者
<a name="tutorial-rbac-step5"></a>

在此步驟中，負責在銷售結構描述中建置擷取、轉換和載入 (ETL) 管道以進行資料處理的銷售工程師將擁有唯讀存取權，但稍後會授予讀取和寫入存取權讓他們能夠執行任務。

1. 以 dbadmin 使用者身分連線至資料庫。

1. 若要在銷售結構描述中建立 sales\$1rw 角色，請使用下列範例。

   ```
   CREATE ROLE sales_rw;
   ```

1. 若要建立 salesengineer 使用者，請使用下列範例。

   ```
   CREATE USER salesengineer PASSWORD 'Test12345';
   ```

1. 若要藉由指派 sales\$1ro 角色的方式，對 sales\$1rw 角色授予使用和選取銷售結構描述之物件的權限，請使用下列範例。如需了解在 Amazon Redshift 中，角色如何繼承許可的詳細資訊，請參閱 [角色階層](t_role_hierarchy.md)。

   ```
   GRANT ROLE sales_ro TO ROLE sales_rw;
   ```

1. 若要對 salesengineer 使用者授予 sales\$1rw 角色，請使用下列範例。

   ```
   GRANT ROLE sales_rw TO salesengineer;
   ```

## 步驟 6：以具有繼承唯讀角色的使用者身分查詢資料
<a name="tutorial-rbac-step6"></a>

在此步驟中，salesengineer 使用者會在獲得讀取許可之前，嘗試更新事件資料表。

1. 以 salesengineer 使用者身分連線至資料庫。

1. salesengineer 使用者可以從銷售結構描述的事件資料表成功讀取資料。若要從銷售結構描述中的事件資料表選取 eventid 1 的事件，請使用下列範例。

   ```
   SELECT * FROM sales.events where eventid=1;
                     
   +---------+---------+-------+--------+-----------------+---------------------+
   | eventid | venueid | catid | dateid |    eventname    |      starttime      |
   +---------+---------+-------+--------+-----------------+---------------------+
   |       1 |     305 |     8 |   1851 | Gotterdammerung | 2008-01-25 14:30:00 |
   +---------+---------+-------+--------+-----------------+---------------------+
   ```

1. 若要嘗試從行銷結構描述的事件資料表中選取所有內容，請使用下列範例。salesengineer 使用者未具備行銷結構描述中資料表的許可，因此這個查詢會導致許可遭拒錯誤。若要從行銷結構描述的事件資料表中選取資料，您必須對 sales\$1rw 角色授予行銷結構描述中事件資料表的 SELECT 許可。

   ```
   SELECT * FROM marketing.events;
   
   ERROR: permission denied for schema marketing
   ```

1. 若要嘗試更新 eventid 1 的 eventname，請執行下列範例。此範例將導致許可遭拒錯誤，因為 salesengineer 使用者對銷售結構描述中的事件資料表只擁有選取許可。若要更新事件資料表，您必須對 sales\$1rw 角色授予 UPDATE 許可。

   ```
   UPDATE sales.events
   SET eventname = 'Comment event'
   WHERE eventid = 1;
   
   ERROR: permission denied for relation events
   ```

## 步驟 7：對讀寫角色授予更新和插入許可
<a name="tutorial-rbac-step7"></a>

在此步驟中，您會對 sales\$1rw 角色授予更新和插入許可。

1. 以 dbadmin 使用者身分連線至資料庫。

1. 若要對 sales\$1rw 角色授予 UPDATE、INSERT 和 DELETE 許可，請使用下列範例。

   ```
   GRANT UPDATE, INSERT, ON ALL TABLES IN SCHEMA sales TO role sales_rw;
   ```

## 步驟 8：以讀寫使用者身分查詢資料
<a name="tutorial-rbac-step8"></a>

在此步驟中，salesengineer 會在其角色獲得插入和更新許可後，成功更新資料表。接下來，salesengineer 會嘗試分析和清空事件資料表，但是會失敗。

1. 以 salesengineer 使用者身分連線至資料庫。

1. 若要更新 eventid 1 的 eventname，請執行下列範例。

   ```
   UPDATE sales.events
   SET eventname = 'Comment event'
   WHERE eventid = 1;
   ```

1. 若要檢視先前查詢中所做的變更，請使用下列範例從銷售結構描述中的事件資料表選取 eventid 1 的事件。

   ```
   SELECT * FROM sales.events WHERE eventid=1;
   
   +---------+---------+-------+--------+---------------+---------------------+
   | eventid | venueid | catid | dateid |   eventname   |      starttime      |
   +---------+---------+-------+--------+---------------+---------------------+
   |       1 |     305 |     8 |   1851 | Comment event | 2008-01-25 14:30:00 |
   +---------+---------+-------+--------+---------------+---------------------+
   ```

1. 若要分析銷售結構描述中更新的事件資料表，請使用下列範例。此範例將導致許可遭拒錯誤，因為 salesengineer 使用者未具備必要的許可，也不是銷售結構描述中事件資料表的擁有者。若要分析事件資料表，您必須使用 GRANT 命令，對 sales\$1rw 角色授予 ANALYZE 許可。如需 ANALYZE 命令的詳細資訊，請參閱 [ANALYZE](r_ANALYZE.md)。

   ```
   ANALYZE sales.events;
                  
                  ERROR: skipping "events" --- only table or database owner can analyze
   ```

1. 若要清空更新的事件資料表，請使用下列範例。此範例將導致許可遭拒錯誤，因為 salesengineer 使用者未具備必要的許可，也不是銷售結構描述中事件資料表的擁有者。若要清空事件資料表，您必須使用 GRANT 命令，對 sales\$1rw 角色授予 VACUUM 許可。如需 VACUUM 命令的詳細資訊，請參閱 [VACUUM](r_VACUUM_command.md)。

   ```
   VACUUM sales.events;
                     
   ERROR: skipping "events" --- only table or database owner can vacuum it
   ```

## 步驟 9：以管理員使用者身分分析和清空資料庫中的資料表
<a name="tutorial-rbac-step9"></a>

在此步驟中，dbadmin 使用者會分析和清空所有資料表。使用者對此資料庫具有管理員許可，因此能夠執行這些命令。

1. 以 dbadmin 使用者身分連線至資料庫。

1. 若要分析銷售結構描述中的事件資料表，請使用下列範例。

   ```
   ANALYZE sales.events;
   ```

1. 若要清空銷售結構描述中的事件資料表，請使用下列範例。

   ```
   VACUUM sales.events;
   ```

1. 若要分析行銷結構描述中的事件資料表，請使用下列範例。

   ```
   ANALYZE marketing.events;
   ```

1. 若要清空行銷結構描述中的事件資料表，請使用下列範例。

   ```
   VACUUM marketing.events;
   ```

## 步驟 10：以讀寫使用者身分截斷資料表
<a name="tutorial-rbac-step10"></a>

在此步驟中，salesengineer 使用者會嘗試截斷銷售結構描述中的事件資料表，但只有在 dbadmin 使用者對其授予截斷許可時才會成功。

1. 以 salesengineer 使用者身分連線至資料庫。

1. 若要嘗試從銷售結構描述的事件資料表中刪除所有列，請使用下列範例。此範例將導致錯誤，因為 salesengineer 使用者未具備必要的許可，也不是銷售結構描述中事件資料表的擁有者。若要截斷事件資料表，您必須使用 GRANT 命令，對 sales\$1rw 角色授予 TRUNCATE 許可。如需 TRUNCATE 命令的相關資訊，請參閱 [TRUNCATE](r_TRUNCATE.md)。

   ```
   TRUNCATE sales.events;
                  
   ERROR: must be owner of relation events
   ```

1. 以 dbadmin 使用者身分連線至資料庫。

1. 若要對 sales\$1rw 角色授予截斷資料表權限，請使用下列範例。

   ```
   GRANT TRUNCATE TABLE TO role sales_rw;
   ```

1. 使用查詢編輯器 v2 以 salesengineer 使用者身分連線至資料庫。

1. 若要從銷售結構描述中的事件資料表讀取前 10 個事件，請使用下列範例。

   ```
   SELECT * FROM sales.events ORDER BY eventid LIMIT 10;
                  
   +---------+---------+-------+--------+-----------------------------+---------------------+
   | eventid | venueid | catid | dateid |          eventname          |      starttime      |
   +---------+---------+-------+--------+-----------------------------+---------------------+
   |       1 |     305 |     8 |   1851 | Comment event               | 2008-01-25 14:30:00 |
   |       2 |     306 |     8 |   2114 | Boris Godunov               | 2008-10-15 20:00:00 |
   |       3 |     302 |     8 |   1935 | Salome                      | 2008-04-19 14:30:00 |
   |       4 |     309 |     8 |   2090 | La Cenerentola (Cinderella) | 2008-09-21 14:30:00 |
   |       5 |     302 |     8 |   1982 | Il Trovatore                | 2008-06-05 19:00:00 |
   |       6 |     308 |     8 |   2109 | L Elisir d Amore            | 2008-10-10 19:30:00 |
   |       7 |     309 |     8 |   1891 | Doctor Atomic               | 2008-03-06 14:00:00 |
   |       8 |     302 |     8 |   1832 | The Magic Flute             | 2008-01-06 20:00:00 |
   |       9 |     308 |     8 |   2087 | The Fly                     | 2008-09-18 19:30:00 |
   |      10 |     305 |     8 |   2079 | Rigoletto                   | 2008-09-10 15:00:00 |
   +---------+---------+-------+--------+-----------------------------+---------------------+
   ```

1. 若要截斷銷售結構描述中的事件資料表，請使用下列範例。

   ```
   TRUNCATE sales.events;
   ```

1. 若要從銷售結構描述中更新的事件資料表讀取資料，請使用下列範例。

   ```
   SELECT * FROM sales.events ORDER BY eventid LIMIT 10;
                  
   +---------+---------+-------+--------+-----------------------------+---------------------+
   | eventid | venueid | catid | dateid |          eventname          |      starttime      |
   +---------+---------+-------+--------+-----------------------------+---------------------+
   ```

### 建立行銷結構描述的唯讀和讀寫角色 (選用)
<a name="tutorial-rbac-create-marketing-schema"></a>

在此步驟中，您會建立行銷結構描述的唯讀和讀寫角色。

1. 以 dbadmin 使用者身分連線至資料庫。

1. 若要建立行銷結構描述的唯讀和讀寫角色，請使用下列範例。

   ```
   CREATE ROLE marketing_ro;
   
   CREATE ROLE marketing_rw;
   
   GRANT USAGE ON SCHEMA marketing TO ROLE marketing_ro, ROLE marketing_rw;
   
   GRANT SELECT ON ALL TABLES IN SCHEMA marketing TO ROLE marketing_ro;
   
   GRANT ROLE marketing_ro TO ROLE marketing_rw;
   
   GRANT INSERT, UPDATE, DELETE ON ALL TABLES IN SCHEMA marketing TO ROLE marketing_rw;
   
   CREATE USER marketinganalyst PASSWORD 'Test12345';
   
   CREATE USER marketingengineer PASSWORD 'Test12345';
   
   GRANT ROLE marketing_ro TO marketinganalyst;
   
   GRANT ROLE marketing_rw TO marketingengineer;
   ```

## RBAC 的系統函式 (選用)
<a name="tutorial-rbac-system-functions"></a>

Amazon Redshift 有兩個函式，可提供有關其他群組或角色的使用者成員資格和角色成員資格的系統資訊：role\$1is\$1member\$1of 和 user\$1is\$1member\$1of。這些函式可供超級使用者和一般使用者使用。超級使用者可以查看所有角色成員資格。一般使用者只能查看本身可存取之角色的成員資格。

使用 role\$1is\$1member\$1of 函式

1. 以 salesengineer 使用者身分連線至資料庫。

1. 若要查看 sales\$1rw 角色是否為 sales\$1ro 角色的成員，請使用下列範例。

   ```
   SELECT role_is_member_of('sales_rw', 'sales_ro');
                  
   +-------------------+
   | role_is_member_of |
   +-------------------+
   | true              |
   +-------------------+
   ```

1. 若要查看 sales\$1ro 角色是否為 sales\$1rw 角色的成員，請使用下列範例。

   ```
   SELECT role_is_member_of('sales_ro', 'sales_rw');
                  
   +-------------------+
   | role_is_member_of |
   +-------------------+
   | false             |
   +-------------------+
   ```

使用 user\$1is\$1member\$1of 函式

1. 以 salesengineer 使用者身分連線至資料庫。

1. 下列範例會嘗試查看 salesanalyst 使用者的使用者成員資格。此查詢會導致錯誤，因為 salesengineer 無法存取 salesanalyst。若要成功執行此命令，請以 salesanalyst 使用者身分連線至資料庫，然後使用此範例。

   ```
   SELECT user_is_member_of('salesanalyst', 'sales_ro');
                  
   ERROR
   ```

1. 以超級使用者身分連線至資料庫。

1. 若要在以超級使用者身分連線時查看 salesanalyst 使用者的成員資格，請使用下列範例。

   ```
   SELECT user_is_member_of('salesanalyst', 'sales_ro');
                  
   +-------------------+
   | user_is_member_of |
   +-------------------+
   | true              |
   +-------------------+
   ```

1. 以 dbadmin 使用者身分連線至資料庫。

1. 若要查看 salesengineer 使用者的成員資格，請使用下列範例。

   ```
   SELECT user_is_member_of('salesengineer', 'sales_ro');
                  
   +-------------------+
   | user_is_member_of |
   +-------------------+
   | true              |
   +-------------------+
                  
   SELECT user_is_member_of('salesengineer', 'marketing_ro');
   
   +-------------------+
   | user_is_member_of |
   +-------------------+
   | false             |
   +-------------------+
                  
   SELECT user_is_member_of('marketinganalyst', 'sales_ro');
                  
   +-------------------+
   | user_is_member_of |
   +-------------------+
   | false             |
   +-------------------+
   ```

## RBAC 的系統檢視 (選用)
<a name="tutorial-rbac-system-views"></a>

若要透過角色來檢視角色、使用者的角色指派、角色階層和資料庫物件的權限，請使用 Amazon Redshift 的系統檢視。這些檢視可供超級使用者和一般使用者使用。超級使用者可以查看所有角色詳細資訊。一般使用者只能查看本身可存取之角色的詳細資訊。

1. 若要檢視叢集中明確授予角色的使用者清單，請使用下列範例。

   ```
   SELECT * FROM svv_user_grants;
   ```

1. 若要檢視叢集中明確授予角色的角色清單，請使用下列範例。

   ```
   SELECT * FROM svv_role_grants;
   ```

如需完整的系統檢視清單，請參閱 [SVV 中繼資料檢視](svv_views.md)。

## 搭配 RBAC 使用資料列層級安全 (選用)
<a name="tutorial-rbac-rls"></a>

若要對敏感資料進行精細的存取控制，請使用資料列層級安全 (RLS)。如需 RLS 的詳細資訊，請參閱 [資料列層級安全性](t_rls.md)。

在本節中，您會建立 RLS 政策以提供許可給 `salesengineer` 使用者，使其只能檢視 `cat` 資料表中 `catdesc` 值為 Major League Baseball 的列。然後您會以 `salesengineer` 使用者身分查詢資料庫。

1. 以 `salesengineer` 使用者身分連線至資料庫。

1. 若要檢視 `cat` 資料表中的前 5 個項目，請使用下列範例。

   ```
   SELECT * 
   FROM sales.cat
   ORDER BY catid ASC
   LIMIT 5;
                     
   +-------+----------+---------+---------------------------------+
   | catid | catgroup | catname |             catdesc             |
   +-------+----------+---------+---------------------------------+
   |     1 | Sports   | MLB     | Major League Baseball           |
   |     2 | Sports   | NHL     | National Hockey League          |
   |     3 | Sports   | NFL     | National Football League        |
   |     4 | Sports   | NBA     | National Basketball Association |
   |     5 | Sports   | MLS     | Major League Soccer             |
   +-------+----------+---------+---------------------------------+
   ```

1. 以 `dbadmin` 使用者身分連線至資料庫。

1. 若要為 `cat` 資料表中的 `catdesc` 欄建立 RLS 政策，請使用下列範例。

   ```
   CREATE RLS POLICY policy_mlb_engineer
   WITH (catdesc VARCHAR(50)) 
   USING (catdesc = 'Major League Baseball');
   ```

1. 若要將 RLS 政策連接至 `sales_rw` 角色，請使用下列範例。

   ```
   ATTACH RLS POLICY policy_mlb_engineer ON sales.cat TO ROLE sales_rw; 
   ```

1. 若要更改資料表以開啟 RLS，請使用下列範例。

   ```
   ALTER TABLE sales.cat ROW LEVEL SECURITY ON; 
   ```

1. 以 `salesengineer` 使用者身分連線至資料庫。

1. 若要長式檢視 `cat` 資料表中的前 5 個項目，請使用下列範例。請注意，只有在 `catdesc` 欄為 `Major League Baseball` 時，才會顯示項目。

   ```
   SELECT * 
   FROM sales.cat
   ORDER BY catid ASC
   LIMIT 5;
                  
   +-------+----------+---------+-----------------------+
   | catid | catgroup | catname |        catdesc        |
   +-------+----------+---------+-----------------------+
   |     1 | Sports   | MLB     | Major League Baseball |
   +-------+----------+---------+-----------------------+
   ```

1. 以 `salesanalyst` 使用者身分連線至資料庫。

1. 若要長式檢視 `cat` 資料表中的前 5 個項目，請使用下列範例。請注意，不會顯示任何項目，因為已套用預設拒絕所有政策。

   ```
   SELECT * 
   FROM sales.cat
   ORDER BY catid ASC
   LIMIT 5;
                  
   +-------+----------+---------+-----------------------+
   | catid | catgroup | catname |        catdesc        |
   +-------+----------+---------+-----------------------+
   ```

1. 以 `dbadmin` 使用者身分連線至資料庫。

1. 若要對 `sales_ro` 角色授予 IGNORE RLS 許可，請使用下列範例。這樣就會對 `salesanalyst` 使用者授予忽略 RLS 政策的許可，因為其為 `sales_ro` 角色的成員。

   ```
   GRANT IGNORE RLS TO ROLE sales_ro; 
   ```

1. 以 `salesanalyst` 使用者身分連線至資料庫。

1. 若要檢視 `cat` 資料表中的前 5 個項目，請使用下列範例。

   ```
   SELECT * 
   FROM sales.cat
   ORDER BY catid ASC
   LIMIT 5;
                  
   +-------+----------+---------+---------------------------------+
   | catid | catgroup | catname |             catdesc             |
   +-------+----------+---------+---------------------------------+
   |     1 | Sports   | MLB     | Major League Baseball           |
   |     2 | Sports   | NHL     | National Hockey League          |
   |     3 | Sports   | NFL     | National Football League        |
   |     4 | Sports   | NBA     | National Basketball Association |
   |     5 | Sports   | MLS     | Major League Soccer             |
   +-------+----------+---------+---------------------------------+
   ```

1. 以 `dbadmin` 使用者身分連線至資料庫。

1. 若要撤銷 `sales_ro` 角色的 IGNORE RLS 許可，請使用下列範例。

   ```
   REVOKE IGNORE RLS FROM ROLE sales_ro;
   ```

1. 以 `salesanalyst` 使用者身分連線至資料庫。

1. 若要長式檢視 `cat` 資料表中的前 5 個項目，請使用下列範例。請注意，不會顯示任何項目，因為已套用預設拒絕所有政策。

   ```
   SELECT * 
   FROM sales.cat
   ORDER BY catid ASC
   LIMIT 5;
                  
   +-------+----------+---------+-----------------------+
   | catid | catgroup | catname |        catdesc        |
   +-------+----------+---------+-----------------------+
   ```

1. 以 `dbadmin` 使用者身分連線至資料庫。

1. 若要從 `cat` 資料表分離 RLS 政策，請使用下列範例。

   ```
   DETACH RLS POLICY policy_mlb_engineer ON cat FROM ROLE sales_rw;
   ```

1. 以 `salesanalyst` 使用者身分連線至資料庫。

1. 若要長式檢視 `cat` 資料表中的前 5 個項目，請使用下列範例。請注意，不會顯示任何項目，因為已套用預設拒絕所有政策。

   ```
   SELECT * 
   FROM sales.cat
   ORDER BY catid ASC
   LIMIT 5;
                  
   +-------+----------+---------+---------------------------------+
   | catid | catgroup | catname |             catdesc             |
   +-------+----------+---------+---------------------------------+
   |     1 | Sports   | MLB     | Major League Baseball           |
   |     2 | Sports   | NHL     | National Hockey League          |
   |     3 | Sports   | NFL     | National Football League        |
   |     4 | Sports   | NBA     | National Basketball Association |
   |     5 | Sports   | MLS     | Major League Soccer             |
   +-------+----------+---------+---------------------------------+
   ```

1. 以 `dbadmin` 使用者身分連線至資料庫。

1. 若捨棄 RLS 政策，請使用下列範例。

   ```
   DROP RLS POLICY policy_mlb_engineer;
   ```

1. 若要移除 RLS，請使用下列範例。

   ```
   ALTER TABLE cat ROW LEVEL SECURITY OFF;
   ```

## 相關主題
<a name="tutorial-rbac-related-topics"></a>

如需 RBAC 的詳細資訊，請參閱下列文件：
+ [角色階層](t_role_hierarchy.md)
+ [角色指派](t_role_assignment.md)
+ [資料庫物件許可](r_roles-database-privileges.md)
+ [RBAC 的 ALTER DEFAULT PRIVILEGES](r_roles-alter-default-privileges.md)

# 資料列層級安全性
<a name="t_rls"></a>

使用 Amazon Redshift 中的資料列層級安全 (RLS)，您可以對敏感資料進行精細的存取控制。您可以根據資料庫物件層級定義的安全政策，決定哪些使用者或角色可以存取結構描述或資料表內的特定資料記錄。除了可用來授予使用者資料欄子集許可的資料欄層級安全之外，還可以使用 RLS 政策進一步限制可見資料欄的特定資料列存取。如需資料欄層級安全的相關資訊，請參閱 [欄位層級存取控制的使用須知](r_GRANT-usage-notes.md#r_GRANT-usage-notes-clp)。

在資料表上強制執行 RLS 政策時，您可以在使用者執行查詢時限制傳回的結果集。

建立 RLS 政策時，您可以指定運算式來指出 Amazon Redshift 是否在查詢中傳回資料表中的任何現有資料列。藉由建立 RLS 政策來限制存取，您不必在查詢中新增或外部化其他條件。

建立 RLS 政策時，建議您建立簡單的政策，並避免在政策中使用複雜的陳述式。定義 RLS 政策時，請勿在以政策為基礎的政策定義中使用過多的資料表聯結。

當政策參照查閱資料表時，除了政策所在的資料表之外，Amazon Redshift 還會掃描其他表格。對於已附加 RLS 政策的使用者，以及未附加任何政策的使用者，相同查詢之間會有效能差異。

# 在 SQL 陳述式中使用 RLS 政策
<a name="t_rls_statements"></a>

在 SQL 陳述式中使用 RLS 政策時，Amazon Redshift 會套用下列規則：
+ 根據預設，Amazon Redshift 會將 RLS 政策套用至 SELECT、UPDATE 和 DELETE 陳述式。
+ 對於 SELECT 和 UNLOAD，Amazon Redshift 會根據您定義的政策篩選資料列。
+ 對於 UPDATE，Amazon Redshift 只會更新您可以看到的資料列。如果政策限制了資料表中的資料列子集，您就無法將其更新。
+ 對於 DELETE，您只能刪除您可以看到的資料列。如果政策限制了資料表中的資料列子集，您就無法將其刪除。對於 TRUNCATE，您仍然可以截斷資料表。
+ 對於 CREATE TABLE LIKE，使用 LIKE 選項建立的資料表不會繼承從來源資料表設定的許可。同樣地，目標資料表不會繼承來源資料表的 RLS 政策。

# 每個使用者結合多個政策
<a name="t_rls_combine_policies"></a>

Amazon Redshift 中的 RLS 支援為每個使用者和物件附加多個政策。為使用者定義多個政策時，Amazon Redshift 會使用 AND 或 OR 語法 (取決於資料表的 RLS CONJUNCTION TYPE 設定) 套用所有政策。如需結合類型的更多相關資訊，請參閱 [ALTER TABLE](r_ALTER_TABLE.md)。

資料表上的多個政策都可以與您建立關聯。您可以直接附加多個政策，或者您屬於多個角色，而這些角色附加了不同的政策。

當多個政策應限制指定關係中的資料列存取時，您可以將關係的 RLS CONJUNCTION TYPE 設定為 AND。請考量下列範例。Alice 只能看到具有 NBA「貓名」的體育賽事做為指定政策。

```
-- Create an analyst role and grant it to a user named Alice.
CREATE ROLE analyst;
CREATE USER alice WITH PASSWORD 'Name_is_alice_1';
GRANT ROLE analyst TO alice;

-- Create an RLS policy that only lets the user see sports.
CREATE RLS POLICY policy_sports
WITH (catgroup VARCHAR(10))
USING (catgroup = 'Sports');

-- Create an RLS policy that only lets the user see NBA.
CREATE RLS POLICY policy_nba
WITH (catname VARCHAR(10))
USING (catname = 'NBA');

-- Attach both to the analyst role.
ATTACH RLS POLICY policy_sports ON category TO ROLE analyst;
ATTACH RLS POLICY policy_nba ON category TO ROLE analyst;

-- Activate RLS on the category table with AND CONJUNCTION TYPE. 
ALTER TABLE category ROW LEVEL SECURITY ON CONJUNCTION TYPE AND;

-- Change session to Alice.
SET SESSION AUTHORIZATION alice;

-- Select all from the category table.
SELECT catgroup, catname
FROM category;

 catgroup | catname 
---------+---------
 Sports   | NBA
(1 row)
```

當多個策略應允許使用者查看指定關係中的更多資料列時，使用者可以將關係的 RLS CONJUNCTION TYPE 設定為 OR。請考量下列範例。Alice 只能看到「音樂會」和「體育」做為指定政策。

```
-- Create an analyst role and grant it to a user named Alice.
CREATE ROLE analyst;
CREATE USER alice WITH PASSWORD 'Name_is_alice_1';
GRANT ROLE analyst TO alice;

-- Create an RLS policy that only lets the user see concerts.
CREATE RLS POLICY policy_concerts
WITH (catgroup VARCHAR(10))
USING (catgroup = 'Concerts');

-- Create an RLS policy that only lets the user see sports.
CREATE RLS POLICY policy_sports
WITH (catgroup VARCHAR(10))
USING (catgroup = 'Sports');

-- Attach both to the analyst role.
ATTACH RLS POLICY policy_concerts ON category TO ROLE analyst;
ATTACH RLS POLICY policy_sports ON category TO ROLE analyst;

-- Activate RLS on the category table with OR CONJUNCTION TYPE. 
ALTER TABLE category ROW LEVEL SECURITY ON CONJUNCTION TYPE OR;

-- Change session to Alice.
SET SESSION AUTHORIZATION alice;

-- Select all from the category table.
SELECT catgroup, count(*)
FROM category
GROUP BY catgroup ORDER BY catgroup;

 catgroup | count 
---------+-------
 Concerts |  3
 Sports   |  5
(2 rows)
```

# RLS 政策擁有權和管理
<a name="t_rls_ownership"></a>

身為擁有 sys:secadmin 角色的超級使用者、安全管理員或使用者，您可以建立、修改、連接和分離 RLS 政策。RLS 政策可以連接至資料表、檢視、近期繫結檢視 (LBV) 和具體化視觀表 (MV)。在物件層級上，您可以開啟或關閉資料列層級安全，而不必修改資料表的結構描述定義。

若要開始使用資料列層級安全，下列是您可以使用的 SQL 陳述式：
+ 使用 ALTER TABLE 陳述式來開啟或關閉資料表、檢視或近期繫結檢視上的 RLS。如需詳細資訊，請參閱[ALTER TABLE](r_ALTER_TABLE.md)。
+ 使用 ALTER MATERIALIZED VIEW 陳述式在具體化視觀表 (MV) 上開啟或關閉 RLS。如需詳細資訊，請參閱[ALTER MATERIALIZED VIEW](r_ALTER_MATERIALIZED_VIEW.md)。
+ 使用 CREATE RLS POLICY 陳述式為一或多個資料表建立安全政策，並在政策中指定一或多個使用者或角色。

  如需詳細資訊，請參閱[CREATE RLS POLICY](r_CREATE_RLS_POLICY.md)。
+ 使用 ALTER RLS POLICY 陳述式來修改政策，例如變更政策定義。您可以針對多個資料表或檢視使用相同的政策。

  如需詳細資訊，請參閱[ALTER RLS POLICY](r_ALTER_RLS_POLICY.md)。
+ 使用 ATTACH RLS POLICY 陳述式可將政策附加至一或多個關係、一或多個使用者或角色。

  如需詳細資訊，請參閱[ATTACH RLS POLICY](r_ATTACH_RLS_POLICY.md)。
+ 使用 DETACH RLS POLICY 陳述式從一或多個關係、一或多個使用者或是角色中將政策分離。

  如需詳細資訊，請參閱[DETACH RLS POLICY](r_DETACH_RLS_POLICY.md)。
+ 您可以使用 DROP RLS POLICY 陳述式來捨棄政策。

  如需詳細資訊，請參閱[DROP RLS POLICY](r_DROP_RLS_POLICY.md)。
+ 您可以使用 GRANT 和 REVOKE 陳述式，明確授予及撤銷參考查閱資料表之 RLS 政策的 SELECT 許可。如需詳細資訊，請參閱[GRANT](r_GRANT.md)及[REVOKE](r_REVOKE.md)。

若要監控所建立的證測，sys:secadmin 可以檢視 [SVV\$1RLS\$1POLICY](r_SVV_RLS_POLICY.md) 和 [SVV\$1RLS\$1ATTACHED\$1POLICY](r_SVV_RLS_ATTACHED_POLICY.md)。

若要列出受 RLS 保護的關係，sys:secadmin 可以檢視 [SVV\$1RLS\$1RELATION](r_SVV_RLS_RELATION.md)。

若要追蹤參照受 RLS 保護關係之查詢上的 RLS 政策應用程式，超級使用者、sys:operator 或任何具有系統許可 ACCESS SYSTEM TABLE 的使用者都可以檢視 [SVV\$1RLS\$1APPLIED\$1POLICY](r_SVV_RLS_APPLIED_POLICY.md)。請注意，在預設情況下，sys:secadmin 不會授予這些許可。

若要允許使用者完整存取受 RLS 保護的關係，您可以授予 IGNORE RLS 許可。超級使用者或 sys:secadmin 會自動獲得 IGNORE RLS 許可。如需詳細資訊，請參閱[GRANT](r_GRANT.md)。

若要說明 EXPLAIN 計劃中查詢的 RLS 政策篩選，以針對與 RLS 相關的查詢進行疑難排解，您可以將 EXPLAIN RLS 許可授予任何使用者。如需詳細資訊，請參閱[GRANT](r_GRANT.md)及[EXPLAIN](r_EXPLAIN.md)。

# 政策相依物件和原則
<a name="t_rls_object_dependency"></a>

為了提供應用程式的安全性，並防止政策物件過時或無效，Amazon Redshift 不允許捨棄或變更 RLS 政策所參照的物件。

以下列出 Amazon Redshift 針對 RLS 政策追蹤的結構描述物件相依性。
+ 追蹤目標資料表的結構描述物件相依性時，Amazon Redshift 會遵循下列規則：
  + 當您捨棄目標資料表時，Amazon Redshift 會將政策與關係、使用者、角色或公開分離。
  + 當您重新命名目標資料表名稱時，附加的政策不會受到影響。
  + 如果您先將政策捨棄或分離，您只能捨棄政策定義中參照的目標資料表資料欄。這也適用於指定 CASCADE 選項時。您可以捨棄目標資料表中的其他資料欄。
  + 您無法重命名目標資料表的參照資料欄。若要重新命名參照的資料欄，請先將政策分離。這也適用於指定 CASCADE 選項時。
  + 即使您指定 CASCADE 選項，也無法變更參照資料欄的類型。
+ 追蹤查閱資料表的結構描述物件相依性時，Amazon Redshift 會遵循下列規則：
  + 您無法捨棄查閱資料表。若要捨棄查閱資料表，請先捨棄參照查詢資料表的政策。
  + 您無法重新命名查閱資料表。若要重新命名查閱資料表，請先捨棄參照查詢資料表的政策。這也適用於指定 CASCADE 選項時。
  + 您無法捨棄政策定義中使用的查閱資料表資料欄。若要捨棄政策定義中使用的查閱資料表資料欄，請先捨棄參照查詢資料表的政策。這也適用於在 ALTER TABLE DROP COLUMN 陳述式中指定 CASCADE 選項時。您可以捨棄查閱資料表中的其他資料欄。
  + 您無法重命名查閱資料表的參照資料欄。若要重新命名參照的資料欄，請先捨棄參照查詢資料表的政策。這也適用於指定 CASCADE 選項時。
  + 您無法變更參照資料欄的類型。
+ 捨棄使用者或角色時，Amazon Redshift 會自動分離附加到該使用者或角色的所有政策。
+ 當您在 DROP SCHEMA 陳述式中使用 CASCADE 選項時，Amazon Redshift 也會捨棄結構描述中的關係。還會捨棄任何其他結構描述中依賴於已捨棄結構描述中關係的關係。對於政策中作為查閱資料表的關係，Amazon Redshift 會使 DROP SCHEMA DDL 失敗。對於 DROP SCHEMA 陳述式捨棄的任何關係，Amazon Redshift 會將所有附加到這些關係的政策分離。
+ 您只能在捨棄政策時捨棄查詢函數 (政策定義中參照的函數)。這也適用於指定 CASCADE 選項時。
+ 將政策附加至資料表時，Amazon Redshift 會檢查此資料表是否為不同政策中的查閱資料表。如果是這種情況，Amazon Redshift 將不允許在此資料表中附加政策。
+ 建立 RLS 政策時，Amazon Redshift 會檢查此資料表是否為任何其他 RLS 政策的目標資料表。如果是這種情況，Amazon Redshift 將不允許在此資料表上建立政策。

## 範例
<a name="t_rls_object_dependency-example"></a>

下列範例說明如何追蹤結構描述相依性。

```
-- The CREATE and ATTACH policy statements for `policy_events` references some
-- target and lookup tables.
-- Target tables are tickit_event_redshift and target_schema.target_event_table.
-- Lookup table is tickit_sales_redshift.
-- Policy `policy_events` has following dependencies:
--   table tickit_sales_redshift column eventid, qtysold
--   table tickit_event_redshift column eventid
--   table target_event_table column eventid
--   schema public and target_schema
CREATE RLS POLICY policy_events
WITH (eventid INTEGER)
USING (
    eventid IN (SELECT eventid FROM tickit_sales_redshift WHERE qtysold <3)
);

ATTACH RLS POLICY policy_events ON tickit_event_redshift TO ROLE analyst;

ATTACH RLS POLICY policy_events ON target_schema.target_event_table TO ROLE consumer;
```

# 使用 RLS 政策的考量事項和限制
<a name="t_rls_usage"></a>

## 考量事項
<a name="t_rls_considerations"></a>

以下是使用 RLS 政策時的考量事項：
+ Amazon Redshift 會將 RLS 政策套用至 SELECT、UPDATE 或 DELETE 陳述式。
+ Amazon Redshift 不會將 RLS 政策套用至 INSERT、COPY、ALTER TABLE APPEND 陳述式。
+ RLS 政策可以連接至資料表、檢視、近期繫結檢視 (LBV) 和具體化視觀表 (MV)。
+ 資料列層級安全可搭配資料欄層級安全來保護您的資料。
+ 針對來源關係開啟 RLS 時，Amazon Redshift 會針對超級使用者、已明確授予系統許可 IGNORE RLS 的使用者或 sys:secadmin 角色支援 ALTER TABLE APPEND 陳述式。在這種情況下，您可以執行 ALTER TABLE APPEND 陳述式，藉由從現有來源資料表移動資料來將資料列附加至目標資料表。Amazon Redshift 會將所有元組從來源關係移動到目標關係。目標關係的 RLS 狀態不會影響 ALTER TABLE APPEND 陳述式。
+ 若要協助從其他資料倉儲系統移轉，您可以指定變數名稱和值，以設定和擷取用於連線的自訂工作階段內容變數。

  下列範例會針對資料列層級安全 (RLS) 政策設定工作階段內容變數。

  ```
  -- Set a customized context variable.
  SELECT set_config(‘app.category’, ‘Concerts’, FALSE);
  
  -- Create a RLS policy using current_setting() to get the value of a customized context variable.
  CREATE RLS POLICY policy_categories
  WITH (catgroup VARCHAR(10)) 
  USING (catgroup = current_setting('app.category', FALSE));
  
  -- Set correct roles and attach the policy on the target table to one or more roles.
  ATTACH RLS POLICY policy_categories ON tickit_category_redshift TO ROLE analyst, ROLE dbadmin;
  ```

  如需有關如何設定和擷取自訂工作階段內容變數的詳細資訊，請前往 [SET](r_SET.md)、[SET\$1CONFIG](r_SET_CONFIG.md)、[SHOW](r_SHOW.md)、[CURRENT\$1SETTING](r_CURRENT_SETTING.md) 和 [RESET](r_RESET.md)。如需修改伺服器組態的一般詳細資訊，請前往 [修改伺服器組態](cm_chap_ConfigurationRef.md#t_Modifying_the_default_settings)。
**重要**  
 在 RLS 政策內使用工作階段內容變數時，安全政策會依賴調用政策的使用者或角色。在 RLS 政策中使用工作階段內容變數時，請小心避免安全漏洞。
+ 在 DECLARE 和 FETCH 之間或後續 FETCH 陳述式之間使用 SET SESSION AUTHORIZATION 變更工作階段使用者，將不會根據 DECLARE 時間的使用者政策重新整理已就緒的計劃。當游標與受 RLS 保護的資料表搭配使用時，請避免變更工作階段使用者。
+ 當檢視物件中的基底物件受到 RLS 保護時，附加至執行查詢之使用者的政策會套用至個別的基底物件。這與物件層級許可檢查不同，檢視擁有者的許可會根據檢視基礎物件進行檢查。您可以在查詢的 EXPLAIN 計畫輸出中檢視受到 RS 保護的關係。
+ 在附加至使用者的關係的 RLS 政策中參照使用者定義函數 (UDF) 時，使用者必須擁有 UDF 的 EXECUTE 許可，才能查詢關係。
+  資料列層級安全性可能會限制最佳查詢效果。在大型資料集上部署受 RLS 保護的視觀表之前，我們建議您仔細評估查詢效能。
+  套用至最新繫結視觀表的資料列層級安全政策，可能會推入聯合資料表。這些 RLS 政策可能會顯示在外部處理引擎日誌檔中。

## 限制
<a name="t_rls_limitations"></a>

下列是使用 RLS 政策時的限制：
+ RLS 政策無法連接到外部資料表和其他數種關係類型。如需詳細資訊，請參閱[ATTACH RLS POLICY](r_ATTACH_RLS_POLICY.md)。
+ Amazon Redshift 可針對具有複雜聯結的特定 RLS 政策支援 SELECT 陳述式，但不支援 UPDATE 或 DELETE 陳述式。如果使用 UPDATE 或 DELETE，Amazon Redshift 會傳回以下錯誤：

  ```
  ERROR: One of the RLS policies on target relation is not supported in UPDATE/DELETE.
  ```
+ 每當在附加至使用者的關係的 RLS 政策中參照使用者定義函數 (UDF) 時，使用者必須擁有 UDF 的 EXECUTE 許可，才能查詢關係。
+ 不支援相關子查詢。Amazon Redshift 會傳回以下錯誤：

  ```
  ERROR: RLS policy could not be rewritten.
  ```
+ Amazon Redshift 不支援使用 RLS 進行資料共用。如果關係沒有關閉用於資料共用的 RLS，則取用者叢集上的查詢會失敗，並出現下列錯誤：

  ```
  RLS-protected relation "rls_protected_table" cannot be accessed via datasharing query.
  ```

  您可以使用 ALTER TABLE 命令搭配 ROW LEVEL SECURITY OFF FOR DATASHARES 參數來關閉資料共用的 RLS。如需使用 ALTER TABLE 啟用或停用 RLS 的詳細資訊，請前往 [ALTER TABLE](r_ALTER_TABLE.md)。
+ 在跨資料庫查詢中，Amazon Redshift 會阻止您讀取受 RLS 保護的關係。具有 IGNORE RLS 許可的使用者可以使用跨資料庫查詢存取受保護的關係。當沒有 IGNORE RLS 許可的使用者透過跨資料庫查詢存取受 RLS 保護的關係時，會出現下列錯誤：

  ```
  RLS-protected relation "rls_protected_table" cannot be accessed via cross-database query.
  ```
+ ALTER RLS POLICY 只支援 USING ( using\$1predicate\$1exp ) 子句修改 RLS 政策。執行 ALTER RLS POLICY 時，您無法使用 WITH 子句修改 RLS 政策。
+ 如果下列任一組態選項的值不符合工作階段的預設值，您就無法查詢已開啟資料列層級安全的關係：
  +  `enable_case_sensitive_super_attribute` 
  +  `enable_case_sensitive_identifier` 
  +  `downcase_delimited_identifier` 

  如果您嘗試查詢已開啟資料列層級安全的關係，並看到「受 RLS 保護的關係不支援工作階段層級組太，因為區分大小寫設定與其預設值不同」的訊息，請考慮重設工作階段的組態選項。
+  當您佈建的叢集或無伺服器命名空間具有任何資料列層級安全性政策時，一般使用者會無法使用下列命令：

  ```
  ALTER <current_user> SET enable_case_sensitive_super_attribute/enable_case_sensitive_identifier/downcase_delimited_identifier
  ```

  建立 RLS 政策時，建議您變更一般使用者的預設組態選項設定，以符合建立政策時的工作階段組態選項設定。超級使用者和擁有 ALTER USER 權限的使用者可以使用參數群組設定或 ALTER USER 命令來執行此操作。如需有關參數群組的詳細資訊，請參閱《Amazon Redshift 管理指南》**中的 [Amazon Redshift 參數群組](https://docs.aws.amazon.com/redshift/latest/mgmt/working-with-parameter-groups.html)。如需 ALTER USER 命令的相關資訊，請參閱 [ALTER USER](r_ALTER_USER.md)。
+  使用 [CREATE VIEW](r_CREATE_VIEW.md) 命令的一般使用者，無法取代具有資料列層級安全政策的視觀表和近期繫結視觀表。若要以 RLS 政策取代視觀表或 LBV，請先卸離任何附加的 RLS 政策、取代視觀表或 LBV，然後重新附加政策。具有 `sys:secadmin permission` 的超級使用者和一般使用者都可以在具有 RLS 政策，但未卸離政策的視觀表或 LBV 上使用 CREATE VIEW。
+  具有資料列層級安全政策的視觀表無法參考系統資料表和系統視觀表。
+  一般視觀表所參考的近期繫結視觀表，不得為受 RLS 保護。
+  RLS 保護的關係和來自資料湖的巢狀資料，均無法在相同的查詢中存取。

# RLS 效能的最佳實務
<a name="t_rls_performance"></a>

以下最佳實務可確保 Amazon Redshift 在受 RLS 保護的資料表上獲得更好的效能。

## 運算子和函數的安全性
<a name="t_rls_safe_operators"></a>

查詢受 RLS 保護的資料表時，使用某些運算子或函數可能會導致效能降低。Amazon Redshift 會將運算子和函數分類為在查詢受 RLS 保護的資料表時是安全或不安全的。當函數或運算子沒有因為輸入而有任何可觀察到的副作用時，函數或運算子就會被歸類為 RLS 安全。特別是，RLS 安全函數或運算子不能是以下其中一項：
+ 輸出一個輸入值，或任何依賴於輸入值的值，無論有沒有錯誤訊息。
+ 失敗或傳回依賴於輸入值的錯誤。

RLS 不安全的運算子包括：
+ 算術運算子 — \$1、-、/、\$1、%。
+ 文字運算子 — LIKE 和 SIMILAR TO。
+ 轉換運算子。
+ UDF。

使用下列 SELECT 陳述式來檢查運算子和函數的安全性。

```
SELECT proname, proc_is_rls_safe(oid) FROM pg_proc;
```

在受 RLS 保護的資料表上規劃查詢時，Amazon Redshift 會對包含 RLS 不安全運算子和函數的使用者述詞的評估順序施加限制。查詢受 RLS 保護的資料表時，參照 RLS 不安全運算子或函數的查詢可能會導致效能降低。當 Amazon Redshift 無法將 RLS 不安全述詞推送至基底資料表掃描以利用排序索引鍵時，效能可能會大幅降低。為了獲得更好的效能，請避免使用利用排序索引鍵的 RLS 不安全述詞進行查詢。若要確認 Amazon Redshift 能夠向下推送運算子和函數，您可以將 EXPLAIN 陳述式與系統許可 EXPLACE RLS 結合使用。

## 結果快取
<a name="t_rls_result_cache"></a>

為了縮短查詢執行期並改善系統效能，Amazon Redshift 會將特定查詢類型的結果快取在領導者節點的記憶體中。

當未受保護資料表的所有條件皆成立，且下列所有條件皆成立時，Amazon Redshift 會在新查詢掃描受 RLS 保護的資料表時使用快取結果：
+ 政策中的資料表或檢視尚未經過修改。
+ 政策並未使用每次執行時都必須求值的函數，例如 GETDATE 或 CURRENT\$1USER。

為了獲得更好的效能，請避免使用不符合前述條件的政策述詞。

如需 Amazon Redshift 中結果快取的詳細資訊，請參閱 [結果快取](c_challenges_achieving_high_performance_queries.md#result-caching)。

## 複雜政策
<a name="t_rls_complex_policies"></a>

為了獲得更好的效能，請避免在聯結多個資料表的子查詢中使用複雜的政策。

# 資料列層級安全完整範例
<a name="t_rls-example"></a>

以下是說明超級使用者如何建立某些使用者和角色的端對端範例。然後，具有 secadmin 角色的使用者會建立、附加、分離和捨棄 RLS 政策。此範例會使用票卷範例資料庫。如需詳細資訊，請參閱《Amazon Redshift 入門指南》**中的[將資料從 Amazon S3 載入到 Amazon Redshift](https://docs.aws.amazon.com/redshift/latest/gsg/rs-gsg-create-sample-db.html)。

```
-- Create users and roles referenced in the policy statements.
CREATE ROLE analyst;
CREATE ROLE consumer;
CREATE ROLE dbadmin;
CREATE ROLE auditor;
CREATE USER bob WITH PASSWORD 'Name_is_bob_1';
CREATE USER alice WITH PASSWORD 'Name_is_alice_1';
CREATE USER joe WITH PASSWORD 'Name_is_joe_1';
CREATE USER molly WITH PASSWORD 'Name_is_molly_1';
CREATE USER bruce WITH PASSWORD 'Name_is_bruce_1';
GRANT ROLE sys:secadmin TO bob;
GRANT ROLE analyst TO alice;
GRANT ROLE consumer TO joe;
GRANT ROLE dbadmin TO molly;
GRANT ROLE auditor TO bruce;
GRANT ALL ON TABLE tickit_category_redshift TO PUBLIC;
GRANT ALL ON TABLE tickit_sales_redshift TO PUBLIC;
GRANT ALL ON TABLE tickit_event_redshift TO PUBLIC;

-- Create table and schema referenced in the policy statements.
CREATE SCHEMA target_schema;
GRANT ALL ON SCHEMA target_schema TO PUBLIC;
CREATE TABLE target_schema.target_event_table (LIKE tickit_event_redshift);
GRANT ALL ON TABLE target_schema.target_event_table TO PUBLIC;

-- Change session to analyst alice.
SET SESSION AUTHORIZATION alice;

-- Check the tuples visible to analyst alice.
-- Should contain all 3 categories.
SELECT catgroup, count(*)
FROM tickit_category_redshift
GROUP BY catgroup ORDER BY catgroup;

-- Change session to security administrator bob.
SET SESSION AUTHORIZATION bob;

CREATE RLS POLICY policy_concerts
WITH (catgroup VARCHAR(10))
USING (catgroup = 'Concerts');

SELECT poldb, polname, polalias, polatts, polqual, polenabled, polmodifiedby FROM svv_rls_policy WHERE poldb = CURRENT_DATABASE();

ATTACH RLS POLICY policy_concerts ON tickit_category_redshift TO ROLE analyst, ROLE dbadmin;

ALTER TABLE tickit_category_redshift ROW LEVEL SECURITY ON;

SELECT * FROM svv_rls_attached_policy;

-- Change session to analyst alice.
SET SESSION AUTHORIZATION alice;

-- Check that tuples with only `Concert` category will be visible to analyst alice.
SELECT catgroup, count(*)
FROM tickit_category_redshift
GROUP BY catgroup ORDER BY catgroup;

-- Change session to consumer joe.
SET SESSION AUTHORIZATION joe;

-- Although the policy is attached to a different role, no tuples will be
-- visible to consumer joe because the default deny all policy is applied.
SELECT catgroup, count(*)
FROM tickit_category_redshift
GROUP BY catgroup ORDER BY catgroup;

-- Change session to dbadmin molly.
SET SESSION AUTHORIZATION molly;

-- Check that tuples with only `Concert` category will be visible to dbadmin molly.
SELECT catgroup, count(*)
FROM tickit_category_redshift
GROUP BY catgroup ORDER BY catgroup;

-- Check that EXPLAIN output contains RLS SecureScan to prevent disclosure of
-- sensitive information such as RLS filters.
EXPLAIN SELECT catgroup, count(*) FROM tickit_category_redshift GROUP BY catgroup ORDER BY catgroup;

-- Change session to security administrator bob.
SET SESSION AUTHORIZATION bob;

-- Grant IGNORE RLS permission so that RLS policies do not get applicable to role dbadmin.
GRANT IGNORE RLS TO ROLE dbadmin;

-- Grant EXPLAIN RLS permission so that anyone in role auditor can view complete EXPLAIN output.
GRANT EXPLAIN RLS TO ROLE auditor;

-- Change session to dbadmin molly.
SET SESSION AUTHORIZATION molly;

-- Check that all tuples are visible to dbadmin molly because `IGNORE RLS` is granted to role dbadmin.
SELECT catgroup, count(*)
FROM tickit_category_redshift
GROUP BY catgroup ORDER BY catgroup;

-- Change session to auditor bruce.
SET SESSION AUTHORIZATION bruce;

-- Check explain plan is visible to auditor bruce because `EXPLAIN RLS` is granted to role auditor.
EXPLAIN SELECT catgroup, count(*) FROM tickit_category_redshift GROUP BY catgroup ORDER BY catgroup;

-- Change session to security administrator bob.
SET SESSION AUTHORIZATION bob;

DETACH RLS POLICY policy_concerts ON tickit_category_redshift FROM ROLE analyst, ROLE dbadmin;

-- Change session to analyst alice.
SET SESSION AUTHORIZATION alice;

-- Check that no tuples are visible to analyst alice.
-- Although the policy is detached, no tuples will be visible to analyst alice
-- because of default deny all policy is applied if the table has RLS on.
SELECT catgroup, count(*)
FROM tickit_category_redshift
GROUP BY catgroup ORDER BY catgroup;

-- Change session to security administrator bob.
SET SESSION AUTHORIZATION bob;

CREATE RLS POLICY policy_events
WITH (eventid INTEGER) AS ev
USING (
    ev.eventid IN (SELECT eventid FROM tickit_sales_redshift WHERE qtysold <3)
);

ATTACH RLS POLICY policy_events ON tickit_event_redshift TO ROLE analyst;
ATTACH RLS POLICY policy_events ON target_schema.target_event_table TO ROLE consumer;

RESET SESSION AUTHORIZATION;

-- Can not cannot alter type of dependent column.
ALTER TABLE target_schema.target_event_table ALTER COLUMN eventid TYPE float;
ALTER TABLE tickit_event_redshift ALTER COLUMN eventid TYPE float;
ALTER TABLE tickit_sales_redshift ALTER COLUMN eventid TYPE float;
ALTER TABLE tickit_sales_redshift ALTER COLUMN qtysold TYPE float;

-- Can not cannot rename dependent column.
ALTER TABLE target_schema.target_event_table RENAME COLUMN eventid TO renamed_eventid;
ALTER TABLE tickit_event_redshift RENAME COLUMN eventid TO renamed_eventid;
ALTER TABLE tickit_sales_redshift RENAME COLUMN eventid TO renamed_eventid;
ALTER TABLE tickit_sales_redshift RENAME COLUMN qtysold TO renamed_qtysold;

-- Can not drop dependent column.
ALTER TABLE target_schema.target_event_table DROP COLUMN eventid CASCADE;
ALTER TABLE tickit_event_redshift DROP COLUMN eventid CASCADE;
ALTER TABLE tickit_sales_redshift DROP COLUMN eventid CASCADE;
ALTER TABLE tickit_sales_redshift DROP COLUMN qtysold CASCADE;

-- Can not drop lookup table.
DROP TABLE tickit_sales_redshift CASCADE;

-- Change session to security administrator bob.
SET SESSION AUTHORIZATION bob;

DROP RLS POLICY policy_concerts;
DROP RLS POLICY IF EXISTS policy_events;

ALTER TABLE tickit_category_redshift ROW LEVEL SECURITY OFF;

RESET SESSION AUTHORIZATION;

-- Drop users and roles.
DROP USER bob;
DROP USER alice;
DROP USER joe;
DROP USER molly;
DROP USER bruce;
DROP ROLE analyst;
DROP ROLE consumer;
DROP ROLE auditor FORCE;
DROP ROLE dbadmin FORCE;
```

# 中繼資料安全性
<a name="t_metadata_security"></a>

如同 Amazon Redshift 的資料列層級安全性一樣，中繼資料安全性可讓您更精細地控制中繼資料。如果針對已佈建的叢集或無伺服器工作群組啟用中繼資料安全性，則使用者可以查看其具有檢視存取權之物件的中繼資料。中繼資料安全性可讓您根據需求分開可見性。例如，您可以使用單一資料倉儲來集中所有資料儲存。但是，如果您為多個扇區儲存資料，則管理安全性會較為棘手。啟用中繼資料安全性後，可以設定可見性。一個扇區的使用者對其物件有更高可見性，同時可限制對另一個磁區使用者的檢視權。中繼資料安全性支援所有物件類型，例如結構描述、資料表、視觀表、具體化視觀表、預存程序、使用者定義函數和機器學習模型。

使用者可以在下列情況下查看物件的中繼資料：
+ 如果將物件存取權授予使用者。
+ 如果將物件存取權授予使用者所屬的群組或角色。
+ 物件是公有的。
+ 使用者是資料庫物件的擁有者。

若要啟用中繼資料安全性，請使用 [ALTER SYSTEM](https://docs.aws.amazon.com/redshift/latest/dg/r_ALTER_SYSTEM.html) 命令。以下是如何使用具有中繼資料安全性的 ALTER SYSTEM 命令的語法。

```
ALTER SYSTEM SET metadata_security=[true|t|on|false|f|off];
```

當您啟用中繼資料安全性時，擁有必要權限的所有使用者都有權查看他們可存取之物件的相關中繼資料。如果您只想讓特定使用者查看中繼資料安全性，請將 `ACCESS CATALOG` 權限授予某角色，然後再將該角色指派給使用者。如需有關使用角色進一步控制安全性的詳細資訊，請參閱[角色型存取控制](https://docs.aws.amazon.com/redshift/latest/dg/t_Roles.html)。

下列範例示範如何將 `ACCESS CATALOG` 權限授予某角色，然後再將該角色指派給使用者。如需有關授予權限的詳細資訊，請參閱 [GRANT](https://docs.aws.amazon.com/redshift/latest/dg/r_GRANT.html) 命令。

```
CREATE ROLE sample_metadata_viewer;

GRANT ACCESS CATALOG TO ROLE sample_metadata_viewer;

GRANT ROLE sample_metadata_viewer to salesadmin;
```

如果您偏好使用已定義的角色，則[系統定義的角色](https://docs.aws.amazon.com/redshift/latest/dg/r_roles-default.html)`operator`、`secadmin`、`dba` 和 `superuser` 所有角色都具有檢視物件中繼資料的必要權限。預設情況下，超級使用者可以查看完整的目錄。

```
GRANT ROLE operator to sample_user;
```

如果您使用角色來控制中繼資料安全性，則可以存取角色型存取控制隨附的所有系統檢視和功能。例如，您可以查詢 [SVV\$1ROLES](https://docs.aws.amazon.com/redshift/latest/dg/r_SVV_ROLES.html) 檢視以查看所有角色。若要查看使用者是否為角色或群組的成員，請使用 [USER\$1IS\$1MEMBER\$1OF](https://docs.aws.amazon.com/redshift/latest/dg/r_USER_IS_MEMBER_OF.html) 函數。如需 SVV 視觀表的完整清單，請參閱 [SVV 中繼資料視觀表](https://docs.aws.amazon.com/redshift/latest/dg/svv_views.html)。如需系統資訊函數清單，請參閱[系統資訊函數](https://docs.aws.amazon.com/redshift/latest/dg/r_System_information_functions.html)。

# 動態資料遮罩
<a name="t_ddm"></a>

**注意**  
Amazon Redshift 會在記錄對 Data Catalog 檢視進行之查詢的相關資訊時，自動遮罩特定系統資料表欄，以防止暴露敏感的中繼資料。如需詳細資訊，請參閱《Amazon Redshift 管理指南》**中的[安全記錄](https://docs.aws.amazon.com/redshift/latest/mgmt/db-auditing-secure-logging.html)。

使用 Amazon Redshift 中的動態資料遮罩 (DDM)，您可以保護資料倉儲中的敏感資料。您可以操控 Amazon Redshift 在查詢時向使用者顯示敏感資料的方式，而無需在資料庫中進行轉換。您可以透過將自訂混淆規則套用至指定使用者或角色的遮罩政策，來控制資料的存取。如此一來，您就可以回應不斷變更的隱私權需求，而不必修改基礎資料或編輯 SQL 查詢。

動態資料遮罩原則會隱藏、混淆或虛擬化符合指定格式的資料。當附加至資料表時，遮罩運算式會套用至其一或多個資料欄。您可以進一步修改遮罩政策，只將政策套用至特定使用者，或套用至可以使用 [角色型存取控制 (RBAC)](t_Roles.md) 建立的使用者定義角色。此外，您可以在建立遮罩政策時使用條件資料欄，在儲存格層級上套用 DDM。如需條件式遮罩的詳細資訊，請參閱 [條件式動態資料遮罩](t_ddm-conditional.md)。

您可以將不同混淆層級的多個遮罩政策套用至資料表中的相同資料欄，並將期指派給不同的角色。當您有不同角色且搭配套用至一個資料欄的不同政策時，為避免發生衝突，您可以為每個應用程式設定優先順序。如此一來，您就可以控制指定使用者或角色可以存取的資料。DDM 政策可以部分或完全修訂資料，或使用以 SQL、Python 或 AWS Lambda撰寫的使用者定義函數來雜湊資料。透過使用雜湊來遮罩資料，您可以在不存取潛在敏感資訊的情況下對此資料套用聯結。

# 管理動態資料遮罩政策的 SQL 命令
<a name="r_ddm-procedures"></a>

您可以執行下列動作來建立、連接、分離和刪除動態資料遮罩政策：
+ 若要建立 DDM 政策，請使用 [CREATE MASKING POLICY](r_CREATE_MASKING_POLICY.md) 命令。

  以下是使用 SHA-2 雜湊函數建立遮罩政策的範例。

  ```
  CREATE MASKING POLICY hash_credit 
  WITH (credit_card varchar(256)) 
  USING (sha2(credit_card + 'testSalt', 256));
  ```
+ 若要變更現有的 DDM 政策，請使用 [ALTER MASKING POLICY](r_ALTER_MASKING_POLICY.md) 命令。

  下列是變更現有遮罩政策的範例。

  ```
  ALTER MASKING POLICY hash_credit
  USING (sha2(credit_card + 'otherTestSalt', 256));
  ```
+ 若要將資料表上的 DDM 政策附加至一或多個使用者或角色，請使用 [ATTACH MASKING POLICY](r_ATTACH_MASKING_POLICY.md) 命令。

  下列是將遮罩政策附加至資料欄/角色組的範例。

  ```
   ATTACH MASKING POLICY hash_credit 
  ON credit_cards (credit_card) 
  TO ROLE science_role 
  PRIORITY 30;
  ```

  PRIORITY 子句會決定當多個政策附加至相同資料欄時，哪個遮罩政策會套用至使用者工作階段。例如，如果上述範例中的使用者在相同的信用卡資料欄中附加了另一個遮罩政策，且優先順序為 20，那麼 science\$1role 的政策就是適用的政策，因為其具有較高的優先順序 30。
+ 若要將資料表上的 DDM 政策與一或多個使用者或角色分離，請使用 [DETACH MASKING POLICY](r_DETACH_MASKING_POLICY.md) 命令。

  下列是將遮罩政策從資料欄/角色組分離的範例。

  ```
  DETACH MASKING POLICY hash_credit 
  ON credit_cards(credit_card) 
  FROM ROLE science_role;
  ```
+ 若要從所有資料庫捨棄 DDM 政策，請使用 [DROP MASKING POLICY](r_DROP_MASKING_POLICY.md) 命令。

  以下是從所有資料庫捨棄遮罩政策的範例。

  ```
  DROP MASKING POLICY hash_credit;  
  ```

# 動態資料遮罩政策階層
<a name="t_ddm-hierarchy"></a>

附加多項遮罩政策時，請考慮下列事項：
+ 您可以將多個遮罩政策附加至單一資料欄。
+ 當查詢適用多個遮罩政策時，則會套用附加至每個資料欄且優先順序最高的政策。請考量下列範例。

  ```
  ATTACH MASKING POLICY partial_hash
  ON credit_cards(address, credit_card)
  TO ROLE analytics_role 
  PRIORITY 20;
  
  ATTACH MASKING POLICY full_hash
  ON credit_cards(credit_card, ssn)
  TO ROLE auditor_role 
  PRIORITY 30;
  
  SELECT address, credit_card, ssn
  FROM credit_cards;
  ```

  執行 SELECT 陳述式時，具有分析和稽核角色的使用者會看到已套用 `partial_hash` 遮罩政策的位址欄。他們會看到套用 `full_hash` 遮罩政策的信用卡和 SSN 資料欄，因為原 `full_hash` 政策在信用卡資料欄上具有較高的優先權。
+  如果附加遮罩政策時未指定優先順序，則預設的優先順序為 0。
+ 您無法將兩個政策附加至具有相同優先順序的相同資料欄。
+ 您無法將兩個政策附加到使用者和欄或角色和欄的相同組合。
+ 當連結至相同使用者或角色時，沿著相同的 SUPER 路徑套用多個遮罩政策時，只有優先順序最高的附件才會生效。請考慮下列範例。

  第一個範例顯示在相同路徑上附加的兩個遮罩政策，優先順序較高的政策會生效。

  ```
  ATTACH MASKING POLICY hide_name
  ON employees(col_person.name)
  TO PUBLIC
  PRIORITY 20;
  
  ATTACH MASKING POLICY hide_last_name
  ON employees(col_person.name.last)
  TO PUBLIC
  PRIORITY 30;
  
  --Only the hide_last_name policy takes effect.
  SELECT employees.col_person.name FROM employees;
  ```

  第二個範例顯示連接至相同 SUPER 物件中不同路徑的兩個遮罩政策，因此在政策之間不會發生衝突。兩項附件同時採用。

  ```
  ATTACH MASKING POLICY hide_first_name
  ON employees(col_person.name.first)
  TO PUBLIC
  PRIORITY 20;
  
  ATTACH MASKING POLICY hide_last_name
  ON employees(col_person.name.last)
  TO PUBLIC
  PRIORITY 20;
  
  --Both col_person.name.first and col_person.name.last are masked.
  SELECT employees.col_person.name FROM employees;
  ```

若要確認哪個遮罩政策適用於指定的使用者和資料欄，或角色和資料欄的組合，具有 [https://docs.aws.amazon.com/redshift/latest/dg/r_roles-default.html](https://docs.aws.amazon.com/redshift/latest/dg/r_roles-default.html) 角色的使用者可以在 [SVV\$1ATTACHED\$1MASKING\$1POLICY](r_SVV_ATTACHED_MASKING_POLICY.md) 系統檢視中查詢資料欄/角色或資料欄/使用者配對。如需詳細資訊，請參閱[動態資料遮罩系統檢視](r_ddm-svv.md)。

# 搭配 SUPER 資料類型路徑使用動態資料遮罩
<a name="t_ddm-super"></a>

 Amazon Redshift 支援將動態資料遮罩政策附加到 SUPER 類型資料欄的路徑。如需 SUPER 資料類型的相關資訊，請參閱 [Amazon Redshift 中的半結構化資料](super-overview.md)。

將遮罩政策附加至 SUPER 類型資料欄的路徑時，請考慮下列事項。
+ 將遮罩政策附加至資料欄上的路徑時，必須將該資料欄定義為 SUPER 資料類型。您只能將遮罩政策套用至 SUPER 路徑上的*純量*值。您無法將遮罩政策套用至複雜的結構或陣列。
+ 只要 SUPER 路徑不衝突，您就可以將不同的遮罩政策套用至單一 SUPER 資料欄上的多個純量值。例如，SUPER 路徑 `a.b` 和 `a.b.c` 衝突，因為它們位於相同路徑，而且 `a.b` 是 `a.b.c` 的上層。SUPER 路徑`a.b.c` 和 `a.b.d` 沒有衝突。
+ 在使用者查詢執行期套用政策之前，Amazon Redshift 無法檢查遮罩政策附加的路徑是否存在於資料中，且為預期類型的路徑。例如，當您將遮罩 TEXT 值的遮罩政策附加到包含 INT 值的 SUPER 路徑時，Amazon Redshift 會嘗試在路徑上轉換為該值的類型。

  在這種情況下，Amazon Redshift 在執行期的行為取決於您用於查詢 SUPER 物件的組態設定。根據預設，Amazon Redshift `NULL`處於寬鬆模式，並且會像指定的 SUPER 路徑一樣解析遺失的路徑和無效轉換。如需與 SUPER 相關之組態設定的詳細資訊，請參閱 [SUPER 組態](super-configurations.md)。
+ SUPER 是一種無結構描述類型，這表示 Amazon Redshift 無法確認在指定的 SUPER 路徑上的值是否存在。如果您將遮罩政策附加到不存在的 SUPER 路徑，且 Amazon Redshift 處於寬鬆模式，則 Amazon Redshift 會將路徑解析為 `NULL` 值。建議您在將遮罩政策附加至 SUPER 資料欄的路徑時，考慮 SUPER 物件的預期格式，以及具有未預期屬性的可能性。如果您認為 SUPER 資料欄中可能有未預期的結構描述，請考慮將遮罩政策直接附加至 SUPER 資料欄。您可以使用 SUPER 類型資訊函數來檢查屬性和類型，並使用 `OBJECT_TRANSFORM` 遮罩值。如需 SUPER 類型資訊函數的詳細資訊，請參閱 [SUPER 類型資訊函數](c_Type_Info_Functions.md)。

## 範例
<a name="t_ddm-super-examples"></a>

**將遮罩政策附加至 SUPER 路徑**  
下列範例會將多個遮罩政策附加至一個資料欄中的多個 SUPER 類型路徑。

```
CREATE TABLE employees (
    col_person SUPER
);

INSERT INTO employees
VALUES
    (
        json_parse('
            {
                "name": {
                    "first": "John",
                    "last": "Doe"
                },
                "age": 25,
                "ssn": "111-22-3333",
                "company": "Company Inc."
            }
        ')
    ),
    (
        json_parse('
            {
                "name": {
                    "first": "Jane",
                    "last": "Appleseed"
                },
                "age": 34,
                "ssn": "444-55-7777",
                "company": "Organization Org."
            }
        ')
    )
;
GRANT ALL ON ALL TABLES IN SCHEMA "public" TO PUBLIC;

-- Create the masking policies.

-- This policy converts the given name to all uppercase letters.
CREATE MASKING POLICY mask_first_name
WITH(first_name TEXT)
USING ( UPPER(first_name) );

-- This policy replaces the given name with the fixed string 'XXXX'.
CREATE MASKING POLICY mask_last_name
WITH(last_name TEXT)
USING ( 'XXXX'::TEXT );

-- This policy rounds down the given age to the nearest 10.
CREATE MASKING POLICY mask_age
WITH(age INT)
USING ( (FLOOR(age::FLOAT / 10) * 10)::INT );

-- This policy converts the first five digits of the given SSN to 'XXX-XX'.
CREATE MASKING POLICY mask_ssn
WITH(ssn TEXT)
USING ( 'XXX-XX-'::TEXT || SUBSTRING(ssn::TEXT FROM 8 FOR 4) );

-- Attach the masking policies to the employees table.
ATTACH MASKING POLICY mask_first_name
ON employees(col_person.name.first)
TO PUBLIC;

ATTACH MASKING POLICY mask_last_name
ON employees(col_person.name.last)
TO PUBLIC;

ATTACH MASKING POLICY mask_age
ON employees(col_person.age)
TO PUBLIC;

ATTACH MASKING POLICY mask_ssn
ON employees(col_person.ssn)
TO PUBLIC;

-- Verify that your masking policies are attached.
SELECT
    policy_name,
    TABLE_NAME,
    priority,
    input_columns,
    output_columns
FROM
    svv_attached_masking_policy;

   policy_name   | table_name | priority |           input_columns           |          output_columns
-----------------+------------+----------+-----------------------------------+-----------------------------------
 mask_age        | employees  |        0 | ["col_person.\"age\""]            | ["col_person.\"age\""]
 mask_first_name | employees  |        0 | ["col_person.\"name\".\"first\""] | ["col_person.\"name\".\"first\""]
 mask_last_name  | employees  |        0 | ["col_person.\"name\".\"last\""]  | ["col_person.\"name\".\"last\""]
 mask_ssn        | employees  |        0 | ["col_person.\"ssn\""]            | ["col_person.\"ssn\""]
(4 rows)

-- Observe the masking policies taking effect.
SELECT col_person FROM employees ORDER BY col_person.age;

-- This result is formatted for ease of reading.
         col_person
--------------------------------
{
    "name": {
        "first": "JOHN",
        "last": "XXXX"
    },
    "age": 20,
    "ssn": "XXX-XX-3333",
    "company": "Company Inc."
}
{
    "name": {
        "first": "JANE",
        "last": "XXXX"
    },
    "age": 30,
    "ssn": "XXX-XX-7777",
    "company": "Organization Org."
}
```

以下是 SUPER 路徑的無效遮罩政策附件的一些範例。

```
-- This attachment fails because there is already a policy
-- with equal priority attached to employees.name.last, which is
-- on the same SUPER path as employees.name.
ATTACH MASKING POLICY mask_ssn
ON employees(col_person.name)
TO PUBLIC;
ERROR:  DDM policy "mask_last_name" is already attached on relation "employees" column "col_person."name"."last"" with same priority
               
-- Create a masking policy that masks DATETIME objects.
CREATE MASKING POLICY mask_date
WITH(INPUT DATETIME)
USING ( INPUT );
               
-- This attachment fails because SUPER type columns can't contain DATETIME objects.
ATTACH MASKING POLICY mask_date
ON employees(col_person.company)
TO PUBLIC;
ERROR:  cannot attach masking policy for output of type "timestamp without time zone" to column "col_person."company"" of type "super
```

以下是將遮罩政策附加至不存在的 SUPER 路徑的範例。預設情況下，Amazon Redshift 會將路徑解析到 `NULL`。

```
ATTACH MASKING POLICY mask_first_name
ON employees(col_person.not_exists)
TO PUBLIC;

SELECT col_person FROM employees LIMIT 1;

-- This result is formatted for ease of reading.
         col_person
-----------------------------------
{
    "name": {
        "first": "JOHN",
        "last": "XXXX"
    },
    "age": 20,
    "ssn": "XXX-XX-3333",
    "company": "Company Inc.",
    "not_exists": null
}
```

# 條件式動態資料遮罩
<a name="t_ddm-conditional"></a>

您可以在遮罩運算式中使用條件運算式建立遮罩政策，以在儲存格層級上遮罩資料。例如，您可以建立一個遮罩政策，根據該資料列中其他資料欄的值，將不同的遮罩套用至值。

以下是使用條件式資料遮罩來建立並附加遮罩政策的範例，該遮罩政策會修改涉及詐騙的部分信用卡號碼，同時完全隱藏所有其他信用卡號碼。您必須是超級使用者或具有 [https://docs.aws.amazon.com/redshift/latest/dg/r_roles-default.html](https://docs.aws.amazon.com/redshift/latest/dg/r_roles-default.html) 角色才能執行此範例。

```
--Create an analyst role.
CREATE ROLE analyst;

--Create a credit card table. The table contains an is_fraud boolean column,
--which is TRUE if the credit card number in that row was involved in a fraudulent transaction.
CREATE TABLE credit_cards (id INT, is_fraud BOOLEAN, credit_card_number VARCHAR(16));

--Create a function that partially redacts credit card numbers.
CREATE FUNCTION REDACT_CREDIT_CARD (credit_card VARCHAR(16))
RETURNS VARCHAR(16) IMMUTABLE
AS $$
    import re
    regexp = re.compile("^([0-9]{6})[0-9]{5,6}([0-9]{4})")
 
    match = regexp.search(credit_card)
    if match != None:
        first = match.group(1)
        last = match.group(2)
    else:
        first = "000000"
        last = "0000"
    
    return "{}XXXXX{}".format(first, last)
$$ LANGUAGE plpythonu;

--Create a masking policy that partially redacts credit card numbers if the is_fraud value for that row is TRUE,
--and otherwise blanks out the credit card number completely.
CREATE MASKING POLICY card_number_conditional_mask
    WITH (fraudulent BOOLEAN, pan varchar(16)) 
    USING (CASE WHEN fraudulent THEN REDACT_CREDIT_CARD(pan)
                ELSE Null
           END);

--Attach the masking policy to the credit_cards/analyst table/role pair. 
ATTACH MASKING POLICY card_number_conditional_mask ON credit_cards (credit_card_number)
 USING (is_fraud, credit_card_number)
 TO ROLE analyst PRIORITY 100;
```

# 動態資料遮罩系統檢視
<a name="r_ddm-svv"></a>

超級使用者、具有 `sys:operator` 角色的使用者，以及具有 ACCESS SYSTEM TABLE 許可的使用者，都可以存取下列與 DDM 相關的系統檢視。
+  [SVV\$1MASKING\$1POLICY](r_SVV_MASKING_POLICY.md) 

   使用 SVV\$1MASKING\$1POLICY 來檢視叢集上或工作群組上建立的所有遮罩政策。
+  [SVV\$1ATTACHED\$1MASKING\$1POLICY](r_SVV_ATTACHED_MASKING_POLICY.md) 

  使用 SVV\$1ATTACHED\$1MASKING\$1POLICY 可檢視目前連線資料庫上連接政策的所有關係和使用者或角色。
+  [SYS\$1APPLIED\$1MASKING\$1POLICY\$1LOG](SYS_APPLIED_MASKING_POLICY_LOG.md) 

  使用 SYS\$1APPLIED\$1MASKING\$1POLICY\$1LOG 追蹤遮罩政策套用在參考受 DDM 保護之關係的查詢上的情形。

以下是您可以使用系統檢視找到的一些資訊範例。

```
--Select all policies associated with specific users, as opposed to roles
SELECT policy_name,
       schema_name,
       table_name,
       grantee
FROM svv_attached_masking_policy
WHERE grantee_type = 'user';     

--Select all policies attached to a specific user
SELECT policy_name,
       schema_name,
       table_name,
       grantee
FROM svv_attached_masking_policy
WHERE grantee = 'target_grantee_name'            
            
--Select all policies attached to a given table
SELECT policy_name,
       schema_name,
       table_name,
       grantee
FROM svv_attached_masking_policy
WHERE table_name = 'target_table_name'
      AND schema_name = 'target_schema_name';            
            
--Select the highest priority policy attachment for a given role
SELECT samp.policy_name,
       samp.priority,
       samp.grantee,
       smp.policy_expression
FROM svv_masking_policy AS smp
JOIN svv_attached_masking_policy AS samp
    ON samp.policy_name = smp.policy_name
WHERE
    samp.grantee_type = 'role' AND
    samp.policy_name = mask_get_policy_for_role_on_column(
        'target_schema_name', 
        'target_table_name', 
        'target_column_name', 
        'target_role_name')
ORDER BY samp.priority desc
LIMIT 1;         

--See which policy a specific user will see on a specific column in a given relation
SELECT samp.policy_name,
       samp.priority,
       samp.grantee,
       smp.policy_expression
FROM svv_masking_policy AS smp
JOIN svv_attached_masking_policy AS samp
    ON samp.policy_name = smp.policy_name
WHERE
    samp.grantee_type = 'role' AND
    samp.policy_name = mask_get_policy_for_user_on_column(
        'target_schema_name',
        'target_table_name',
        'target_column_name',
        'target_user_name')
ORDER BY samp.priority desc; 
         
 --Select all policies attached to a given relation.
SELECT policy_name,
schema_name,
relation_name,
database_name
FROM sys_applied_masking_policy_log
WHERE relation_name = 'relation_name'
AND schema_name = 'schema_name';
```

# 使用動態資料遮罩時的考量
<a name="t_ddm-considerations"></a>

使用動態資料遮罩時，請考量下列內容：
+  查詢從資料表建立的物件 (例如檢視) 時，使用者會根據自己的遮罩政策 (而非建立物件之使用者的政策) 來看到結果。例如，具有分析師角色的使用者查詢由 secadmin 建立的檢視時，就會看到附加到分析師角色的遮罩政策的結果。
+  為了防止 EXPLAIN 命令暴露敏感遮罩政策篩選條件，只有具有 SYS\$1EXPLAIN\$1DDM 許可的使用者才能看到 EXPLAIN 輸出中套用的遮罩政策。依預設，使用者沒有 SYS\$1EXPLAIN\$1DDM 許可。

  以下是對角色授予許可的語法。

  ```
  GRANT EXPLAIN MASKING TO ROLE rolename
  ```

   如需 EXPLAIN 命令的詳細資訊，請參閱 [EXPLAIN](r_EXPLAIN.md)。
+  具有不同角色的使用者可以根據所使用的篩選條件或聯結條件看到不同的結果。例如，如果執行命令的使用者套用可混淆特定資料欄的遮罩政策，則使用該資料欄的值在資料表上執行 SELECT 命令將會失敗。
+  DDM 政策必須在任何述詞操作或預測之前套用。遮罩政策可能包含下列項目：
  + 低成本常數操作，例如將值轉換為 null
  + 中等成本操作，例如 HMAC 雜湊
  + 高成本操作，例如呼叫外部 Lambda 使用者定義函數

  如此一來，我們建議您盡可能使用簡單遮罩運算式。
+  您可以針對具有資料列層級安全政策的角色使用 DDM 政策，但請注意，RLS 政策會在 DDM 之前套用。動態資料遮罩表達式無法讀取受 RLS 保護的資料列。如需 RLS 的詳細資訊，請參閱 [資料列層級安全性](t_rls.md)。
+  使用 [COPY](r_COPY.md) 命令從 parquet 複製到受保護的目標資料表時，您應該在 COPY 陳述式中明確指定資料欄。如需使用 COPY 對應資料欄的詳細資訊，請參閱 [欄映射選項](copy-parameters-column-mapping.md)。
+  DDM 政策無法附加至下列關係：
  +  系統表格和目錄 
  +  外部資料表 
  +  資料共用資料表
  +  跨資料庫關係 
  +  暫時資料表 
  +  相關查詢 
+  DDM 政策可以包含查閱資料表。查閱資料表可以存在於 USING 子句中。下列關係類型無法用作查閱資料表：
  +  系統表格和目錄 
  +  外部資料表 
  +  資料共用資料表 
  +  檢視、具體化視觀表和近期繫結視觀表 
  +  跨資料庫關係 
  +  暫時資料表 
  +  相關查詢 

  以下是將遮罩政策附加至查閱資料表的範例。

  ```
  --Create a masking policy referencing a lookup table
  CREATE MASKING POLICY lookup_mask_credit_card WITH (credit_card TEXT) USING (
    CASE
      WHEN
        credit_card IN (SELECT credit_card_lookup FROM credit_cards_lookup)      
      THEN '000000XXXX0000'
      ELSE REDACT_CREDIT_CARD(credit_card)
      END
    ); 
    
  --Provides access to the lookup table via a policy attached to a role
  GRANT SELECT ON TABLE credit_cards_lookup TO MASKING POLICY lookup_mask_credit_card;
  ```
+  如果遮罩政策會產生與目標資料欄類型和大小不相容的輸出，則您無法附加該遮罩政策。例如，您無法將輸出 12 個字元長字串的遮罩政策附加至 VARCHAR(10) 資料欄。Amazon Redshift 支援以下例外情況：
  +  輸入類型為 INTN 的遮罩政策可以附加至大小為 INTM 的政策，只要 M < N 即可。例如，BIGINT (INT8) 輸入政策可附加至 smallint (INT4) 資料欄。
  +  輸入類型為 NUMERIC 或 DECIMAL 的遮罩政策一律可以附加至 FLOAT 資料欄。
+ 您無法使用 DDM 政策搭配資料共用。如果資料共用的資料生產者將 DDM 政策附加至資料共用中的資料表，則使用者無法從嘗試查詢資料表的資料取用者中存取資料表。嘗試在生產者端叢集或命名空間上將關聯新增至資料共用的作業會失敗，並顯示下列錯誤：

  ```
  <ddm_protected_relation> or a relation dependent on it is protected by a masking policy and cannot be added to a datashare
  ```

  如果您將遮罩政策連接到生產者端上的關係，且該關係已包含在資料共用中，則嘗試在取用者端查詢關係的作業會失敗，並顯示下列錯誤：

  ```
  cross-cluster query of the masked relation <ddm_protected_relation> is not supported.
  ```

  您可以使用 ALTER TABLE 命令搭配 MASKING OFF FOR DATASHARES 參數來關閉資料共用的 DDM。如需詳細資訊，請參閱[ALTER TABLE](r_ALTER_TABLE.md)。
+ 如果下列任一組態選項的值不符合工作階段的預設值，您就無法查詢已附加 DDM 咒測的關係：
  +  `enable_case_sensitive_super_attribute` 
  +  `enable_case_sensitive_identifier` 
  +  `downcase_delimited_identifier` 

  如果您嘗試查詢已附加 DDM 政策的關係，並看到「受 DDM 保護的關係不支援工作階段層級組太，因為區分大小寫設定與其預設值不同」的訊息，請考慮重設工作階段的組態選項。
+  當您佈建的叢集或無伺服器命名空間具有任何動態資料遮罩政策時，一般使用者會無法使用下列命令：

  ```
  ALTER <current_user> SET enable_case_sensitive_super_attribute/enable_case_sensitive_identifier/downcase_delimited_identifier
  ```

  建立 DDM 政策時，建議您變更一般使用者的預設組態選項設定，以符合建立政策時的工作階段組態選項設定。超級使用者和擁有 ALTER USER 權限的使用者可以使用參數群組設定或 ALTER USER 命令來執行此操作。如需有關參數群組的詳細資訊，請參閱《Amazon Redshift 管理指南》**中的 [Amazon Redshift 參數群組](https://docs.aws.amazon.com/redshift/latest/mgmt/working-with-parameter-groups.html)。如需 ALTER USER 命令的相關資訊，請參閱 [ALTER USER](r_ALTER_USER.md)。
+ 使用 [CREATE VIEW](r_CREATE_VIEW.md) 命令的一般使用者，無法取代具有附加的 DDM 政策的視觀表和近期繫結視觀表。若要以 DDM 政策取代視觀表或 LBV，請先卸離任何附加的 DDM 政策、取代視觀表或 LBV，然後重新附加政策。具有 `sys:secadmin` 權限的超級使用者和一般使用者都可以在具有 DDM 政策，但未卸離政策的視觀表或 LBV 上使用 CREATE VIEW。
+ 具有附加 DDM 政策的視觀表，無法參考系統資料表和視觀表。近期繫結視觀表可以參考系統資料表和視觀表。
+ 具有附加 DDM 政策的近期繫結視觀表，無法參考資料湖 (例如 JSON 文件) 中的巢狀資料。
+  如果任何視觀表都參考近期繫結視觀表，則近期繫結視觀表便無法附加 DDM 政策。
+  附加至近期繫結視觀表的 DDM 政策，會依資料欄名稱附加。在查詢時，Amazon Redshift 會驗證附加到近期繫結視觀表的所有遮罩政策是否已成功套用，而且近期繫結視觀表的輸出資料欄類型是否符合附加的遮罩政策的類型。如果驗證失敗，Amazon Redshift 會傳回查詢的錯誤訊息。
+ 您可以在建立 DDM 政策時使用自訂的工作階段內容變數。下列範例會設定 DDM 政策的工作階段內容變數。

  ```
  -- Set a customized context variable.
  SELECT set_config('app.city', 'XXXX', FALSE);
  
  -- Create a MASKING policy using current_setting() to get the value of a customized context variable.
  CREATE MASKING POLICY city_mask
  WITH (city VARCHAR(30))
  USING (current_setting('app.city')::VARCHAR(30));
  
  -- Attach the policy on the target table to one or more roles.
  ATTACH MASKING POLICY city_mask 
  ON tickit_users_redshift(city) 
  TO ROLE analyst, ROLE dbadmin;
  ```

  如需有關如何設定和擷取自訂工作階段內容變數的詳細資訊，請前往 [SET](r_SET.md)、[SET\$1CONFIG](r_SET_CONFIG.md)、[SHOW](r_SHOW.md)、[CURRENT\$1SETTING](r_CURRENT_SETTING.md) 和 [RESET](r_RESET.md)。如需修改伺服器組態的一般詳細資訊，請前往 [修改伺服器組態](cm_chap_ConfigurationRef.md#t_Modifying_the_default_settings)。
**重要**  
 在 DDM 政策內使用工作階段內容變數時，安全政策會依賴調用政策的使用者或角色。在 DDM 政策中使用工作階段內容變數時，請小心避免安全漏洞。

# 動態資料遮罩完整範例
<a name="ddm-example"></a>

以下是一個端對端範例，說明如何建立遮罩政策並將其附加至資料欄。這些政策可讓使用者存取資料欄並查看不同的值，視附加至其角色的政策中的混淆程度而定。您必須是超級使用者或具有 [https://docs.aws.amazon.com/redshift/latest/dg/r_roles-default.html](https://docs.aws.amazon.com/redshift/latest/dg/r_roles-default.html) 角色才能執行此範例。

## 建立遮罩政策
<a name="ddm-example-create"></a>

首先，建立一個資料表，並填入信用卡值。

```
--create the table         
CREATE TABLE credit_cards (
  customer_id INT,
  credit_card TEXT
);

--populate the table with sample values
INSERT INTO credit_cards
VALUES
  (100, '4532993817514842'),
  (100, '4716002041425888'),
  (102, '5243112427642649'),
  (102, '6011720771834675'),
  (102, '6011378662059710'),
  (103, '373611968625635')
;

--run GRANT to grant permission to use the SELECT statement on the table
GRANT SELECT ON credit_cards TO PUBLIC;

--create two users
CREATE USER regular_user WITH PASSWORD '1234Test!';

CREATE USER analytics_user WITH PASSWORD '1234Test!';

--create the analytics_role role and grant it to analytics_user
--regular_user does not have a role
CREATE ROLE analytics_role;

GRANT ROLE analytics_role TO analytics_user;
```

接下來，建立要套用至分析角色的遮罩政策。

```
--create a masking policy that fully masks the credit card number
CREATE MASKING POLICY mask_credit_card_full
WITH (credit_card VARCHAR(256))
USING ('000000XXXX0000'::TEXT);

--create a user-defined function that partially obfuscates credit card data
CREATE FUNCTION REDACT_CREDIT_CARD (credit_card TEXT)
RETURNS TEXT IMMUTABLE
AS $$
    import re
    regexp = re.compile("^([0-9]{6})[0-9]{5,6}([0-9]{4})")
 
    match = regexp.search(credit_card)
    if match != None:
        first = match.group(1)
        last = match.group(2)
    else:
        first = "000000"
        last = "0000"
    
    return "{}XXXXX{}".format(first, last)
$$ LANGUAGE plpythonu;

--create a masking policy that applies the REDACT_CREDIT_CARD function
CREATE MASKING POLICY mask_credit_card_partial
WITH (credit_card VARCHAR(256))
USING (REDACT_CREDIT_CARD(credit_card));

--confirm the masking policies using the associated system views
SELECT * FROM svv_masking_policy;

SELECT * FROM svv_attached_masking_policy;
```

## 附加遮罩政策
<a name="ddm-example-attach"></a>

將遮罩政策附加至信用卡資料表。

```
--attach mask_credit_card_full to the credit card table as the default policy
--all users will see this masking policy unless a higher priority masking policy is attached to them or their role
ATTACH MASKING POLICY mask_credit_card_full
ON credit_cards(credit_card)
TO PUBLIC;

--attach mask_credit_card_partial to the analytics role
--users with the analytics role can see partial credit card information
ATTACH MASKING POLICY mask_credit_card_partial
ON credit_cards(credit_card)
TO ROLE analytics_role
PRIORITY 10;

--confirm the masking policies are applied to the table and role in the associated system view
SELECT * FROM svv_attached_masking_policy;

--confirm the full masking policy is in place for normal users by selecting from the credit card table as regular_user
SET SESSION AUTHORIZATION regular_user;

SELECT * FROM credit_cards;

--confirm the partial masking policy is in place for users with the analytics role by selecting from the credit card table as analytics_user
SET SESSION AUTHORIZATION analytics_user;

SELECT * FROM credit_cards;
```

## 修改遮罩政策
<a name="ddm-example-alter"></a>

下一節說明如何修改動態資料遮罩政策。

```
--reset session authorization to the default
RESET SESSION AUTHORIZATION;

--alter the mask_credit_card_full policy
ALTER MASKING POLICY mask_credit_card_full
USING ('00000000000000'::TEXT);	
	
--confirm the full masking policy is in place after altering the policy, and that results are altered from '000000XXXX0000' to '00000000000000'
SELECT * FROM credit_cards;
```

## 分離並捨棄遮罩政策
<a name="ddm-example-detach"></a>

下列區段說明如何移除資料表中的所有動態資料遮罩政策，以分離和捨棄遮罩政策。

```
--reset session authorization to the default
RESET SESSION AUTHORIZATION;

--detach both masking policies from the credit_cards table
DETACH MASKING POLICY mask_credit_card_full 
ON credit_cards(credit_card) 
FROM PUBLIC;

DETACH MASKING POLICY mask_credit_card_partial 
ON credit_cards(credit_card) 
FROM ROLE analytics_role;

--drop both masking policies
DROP MASKING POLICY mask_credit_card_full;

DROP MASKING POLICY mask_credit_card_partial;
```

# 限定範圍權限
<a name="t_scoped-permissions"></a>

限定範圍許可讓您能夠對使用者或角色授予資料庫或結構描述內某一種類型的所有物件的許可。具有限定範圍許可的使用者和角色對於資料庫或結構描述內所有目前和未來的物件擁有指定的許可。

您可以在 [SVV\$1DATABASE\$1PRIVILEGES](r_SVV_DATABASE_PRIVILEGES.md) 中檢視資料庫層級限定範圍許可的範圍。您可以在 [SVV\$1SCHEMA\$1PRIVILEGES](r_SVV_SCHEMA_PRIVILEGES.md) 中檢視結構描述層級限定範圍許可的範圍。

 如需套用限定範圍的權限的詳細資訊，請參閱 [GRANT](r_GRANT.md) 和 [REVOKE](r_REVOKE.md)。

# 使用限定範圍的權限考量
<a name="t_scoped-permissions-considerations"></a>

使用限定範圍的權限時，請考量下列事項：
+ 您可以使用限定範圍許可，對指定的使用者或角色授予或撤銷資料庫或結構描述範圍的許可。
+ 您無法對使用者群組授予限定範圍許可。
+ 授予或撤銷限定範圍的權限會變更範圍中所有目前和未來物件的權限。
+ 限定範圍許可和物件層級許可彼此獨立運作。例如，在下列兩種情況下，使用者都會維持資料表的許可。
  + 使用者在資料表 schema1.table1 上獲得授予 SELECT，並在 schema1 上獲得授予 SELECT 限定範圍許可。接著在結構描述 schema1 中撤銷了使用者對所有資料表的 SELECT。使用者仍在 schema1.table1 上保留 SELECT。
  + 使用者在資料表 schema1.table1 上獲得授予 SELECT，並在 schema1 上獲得授予 SELECT 限定範圍許可。接著撤銷了使用者對 schema1.table1 的 SELECT。使用者仍在 schema1.table1 上保留 SELECT。
+ 若要授予或撤銷限定範圍的權限，您必須符合下列其中一項條件：
  + 超級使用者。
  + 具有該權限授予選項的使用者。如需授予選項的詳細資訊，請前往 [GRANT](r_GRANT.md) 中的 WITH GRANT OPTION 參數。
+ 限定範圍的權限只能授予或撤銷已連線資料庫的物件，或從資料共用匯入的資料庫撤銷。
+ 您可以使用限定範圍許可來設定從資料共用建立的資料庫上的預設許可。被授予共用資料庫限定範圍權限的取用者端資料共用使用者，將自動獲得新增到生產者端資料共用之任何新物件的那些權限。
+ 生產者可對資料共用授予結構描述內物件的限定範圍許可 (預覽版) 