

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

# 連線至 SAP OData
<a name="connecting-to-data-sap-odata"></a>

SAP OData 是一種標準 Web 協定，用於使用 ABAP (進階業務應用程式程式設計) 查詢和更新 SAP 中存在的資料，套用和建置 HTTP 等 Web 技術，以從各種外部應用程式、平台和裝置存取資訊。使用該產品，您可以存取所需的一切，以協助您與 SAP 系統、應用程式或資料無縫整合。

**Topics**
+ [AWS Glue 支援 SAP OData](sap-odata-support.md)
+ [建立連線](sap-odata-creating-connections.md)
+ [建立 SAP OData 任務](sap-odata-creating-job.md)
+ [寫入到 SAP OData](sap-odata-writing.md)
+ [使用 SAP OData 狀態管理指令碼](sap-odata-state-management-script.md)
+ [非 ODP 實體的分區](sap-odata-non-odp-entities-partitioning.md)
+ [SAP OData 連線選項](sap-odata-connection-options.md)
+ [SAP OData 實體和欄位詳細資訊](sap-odata-entity-field-details.md)

# AWS Glue 支援 SAP OData
<a name="sap-odata-support"></a>

AWS Glue 支援 SAP OData，如下所示：

**支援作為來源？**  
是。您可以使用 AWS Glue ETL 任務從 SAP OData 查詢資料。

**支援作為目標？**  
是。您可以使用 AWS Glue ETL 任務將記錄寫入 SAP OData。

**支援的 SAP OData API 版本**  
支援下列 SAP OData API 版本：
+ 2.0

**支援的來源**  
支援下列來源：
+ ODP (Operational Data Provisioning) 來源：
  + BW Extractors (DataSources)
  + CDS Views
  + SLT
+ 非 ODP 來源，例如：
  + CDS View 服務
  + RFC 型服務
  + 自訂 ABAP 服務

**支援的 SAP 元件**  
以下是最低要求：
+ 必須為服務探索啟用目錄服務。
  + 在 SAP 系統的 SAP Gateway 中設定要擷取的營運資料佈建 (ODP) 資料來源。
  + **OData V2.0**：透過交易 `/IWFND/MAINT_SERVICE` 在您的 SAP Gateway 中啟用 OData V2.0 目錄服務。
  + 透過交易 `/IWFND/MAINT_SERVICE` 在 SAP Gateway 中啟用 OData V2.0 服務。
  + SAP OData 服務必須支援用戶端分頁/查詢選項，例如 `$top` 和 `$skip`。其還必須支援系統查詢選項 `$count`。
  + 您必須為 SAP 中的使用者提供必要的授權，以探索服務並使用 SAP OData 服務擷取資料。請參閱 SAP 提供的安全文件。
+ 如果想要使用 OAuth 2.0 作為授權機制，則必須為 OData 服務啟用 OAuth 2.0，並根據 SAP 文件註冊 OAuth 用戶端。
+ 若要根據 ODP 資料來源產生 OData 服務，SAP Gateway Foundation 必須在 ERP/BW 堆疊或中樞組態中進行本機安裝。
  + 對於 ERP/BW 應用程式，SAP NetWeaver AS ABAP 堆疊必須為 7.50 SP02 或更高版本。
  + 對於中樞系統 (SAP Gateway)，中樞系統的 SAP NetWeaver AS ABAP 必須為 7.50 SP01 或更高版本，才能進行遠端中樞設定。
+ 對於非 ODP 來源，SAP NetWeaver 堆疊版本必須為 7.40 SP02 或更高版本。

**支援的身分驗證方法**  
支援下列身分驗證方法：
+ 基本身分驗證
+ OAuth 2.0

# 先決條件
<a name="sap-odata-prerequisites"></a>

使用 SAP OData 連線啟動從 SAP OData 擷取資料 AWS Glue 的任務之前，請先完成下列先決條件：
+ 必須在 SAP 系統中啟用相關的 SAP OData Service，以確保資料來源可供取用。如果未啟用 OData 服務，Glue 任務將無法從 SAP 中存取或擷取資料。
+ 必須在 SAP 中設定適當的身分驗證機制，例如基本 （自訂） 身分驗證或 OAuth 2.0，以確保 AWS Glue 任務可以成功與 SAP OData 服務建立連線。
+ 設定 IAM 政策以授予 AWS Glue 任務適當的許可，以存取 SAP、Secrets Manager 和程序中涉及的其他 AWS 資源。
+ 如果 SAP 系統託管在私有網路中，則必須設定 VPC 連線，以確保 AWS Glue 任務可以安全地與 SAP 通訊，而不會透過公有網際網路公開敏感資料。

AWS Secrets Manager 可用來安全地存放敏感資訊，例如 SAP 登入資料， AWS Glue 任務可在執行時間動態擷取。這種方法不需要硬式編碼憑證，可提高安全性和靈活性。

下列先決條件提供step-by-step指引，說明如何設定每個元件，以在 AWS Glue 和 SAP OData 之間順暢整合。

**Topics**
+ [SAP OData 啟用](sap-odata-activation.md)
+ [IAM 政策](sap-odata-configuring-iam-permissions.md)
+ [連線/VPC 連線](sap-odata-connectivity-vpc-connection.md)
+ [SAP 身分驗證](sap-odata-authentication.md)
+ [AWS Secrets Manager 來存放您的 Auth 秘密](sap-odata-aws-secret-manager-auth-secret.md)

# SAP OData 啟用
<a name="sap-odata-activation"></a>

完成 SAP OData 連線的下列步驟：

## ODP 來源
<a name="sap-odata-odp-sources"></a>

必須先符合下列要求，才能從 ODP 提供者中傳輸資料：
+ 您擁有 SAP NetWeaver AS ABAP 執行個體。
+ 您的 SAP NetWeaver 執行個體包含您要從中傳輸資料的 ODP 提供者。ODP 提供者包括：
  + SAP DataSources (交易代碼 RSO2)
  + SAP 核心資料服務 ABAP CDS 檢視
  + SAP BW 或 SAP BW/4HANA 系統 (InfoObject、DataStore Object)
  + 透過 SAP Landscape Replication Server (SAP SLT)，從 SAP 來源系統即時複寫資料表和資料庫檢視
  + SAP ABAP 型來源中的 SAP HANA 資訊檢視
+ 您的 SAP NetWeaver 執行個體具有 SAP Gateway Foundation 元件。
+ 您已建立可從 ODP 提供者處擷取資料的 OData 服務。若要建立 OData 服務，請使用 SAP Gateway Service Builder。若要存取 ODP 資料，Amazon AppFlow 會使用 OData API 來呼叫此服務。如需詳細資訊，請參閱 SAP BW/4HANA 文件中的[透過 OData 產生擷取 ODP 資料的服務](https://help.sap.com/docs/SAP_BPC_VERSION_BW4HANA/dd104a87ab9249968e6279e61378ff66/69b481859ef34bab9cc7d449e6fff7b6.html?version=11.0)。
+ 若要根據 ODP 資料來源產生 OData 服務，SAP Gateway Foundation 必須在 ERP/BW 堆疊或中樞組態中進行本機安裝。
  + 對於 ERP/BW 應用程式，SAP NetWeaver AS ABAP 堆疊必須為 7.50 SP02 或更高版本。
  + 對於中樞系統 (SAP Gateway)，中樞系統的 SAP NetWeaver AS ABAP 必須為 7.50 SP01 或更高版本，才能進行遠端中樞設定。

## 非 ODP 來源
<a name="sap-odata-non-odp-sources"></a>
+ SAP NetWeaver 堆疊版本必須為 7.40 SP02 或更高版本。
+ 必須為服務探索啟用目錄服務。
  + **OData V2.0**：可透過交易 `/IWFND/MAINT_SERVICE` 在您的 SAP Gateway 中啟用 OData V2.0 目錄服務
+ SAP OData 服務必須支援用戶端分頁/查詢選項，例如 `$top` 和 `$skip`。其還必須支援系統查詢選項 `$count`。
+ 對於 OAuth 2.0，必須為 OData 服務啟用 OAuth 2.0，並根據 SAP 文件註冊 OAuth 用戶端，設定已授權的重新導向 URL，如下所示：
  + `https://<region>.console.aws.amazon.com/gluestudio/oauth`，`<region>`將 取代 AWS Glue 為正在執行的區域，例如：us-east-1。
  + 必須啟用安全設定以透過 HTTPS 進行連線。
+ 必須為 SAP 中的使用者提供必要的授權，以探索服務並使用 SAP OData 服務擷取資料。請參閱 SAP 提供的安全文件。

# IAM 政策
<a name="sap-odata-configuring-iam-permissions"></a>

## 包含用於建立和使用連線的 API 操作的政策
<a name="sap-odata-policies-api-operations"></a>

下列範例政策說明建立和使用 連線所需的 AWS IAM 許可。如果您要建立新角色，請建立包含下列項目的政策：

------
#### [ JSON ]

****  

```
{
  "Version":"2012-10-17",		 	 	 
  "Statement": [
    {
      "Effect": "Allow",
      "Action": [
        "glue:ListConnectionTypes",
        "glue:DescribeConnectionType",
        "glue:RefreshOAuth2Tokens",
        "glue:ListEntities",
        "glue:DescribeEntity"
      ],
      "Resource": "*"
    },
    {
      "Effect": "Allow",
      "Action": [
        "secretsmanager:DescribeSecret",
        "secretsmanager:GetSecretValue",
        "secretsmanager:PutSecretValue"
      ],
      "Resource": "*"
    }
  ]
}
```

------

該角色必須授予對任務使用的所有資源的存取權，例如 Amazon S3。如果不想使用上述方法，可選擇使用下列受管 IAM 政策。
+ [AWSGlueServiceRole](https://console.aws.amazon.com/iam/home#policies/arn:aws:iam::aws:policy/service-role/AWSGlueServiceRole) – 准許存取各種 AWS Glue 程序代表您執行所需的資源。這些資源包括 AWS Glue Amazon S3、IAM、CloudWatch Logs 和 Amazon EC2。如果您遵循此政策中指定資源的命名慣例，則 AWS Glue 程序具有必要的許可。此政策通常會連接至定義編目程式、工作和開發端點時所指定的角色。
+ [AWSGlueConsoleFullAccess](https://console.aws.amazon.com/iam/home#policies/arn:aws:iam::aws:policy/AWSGlueConsoleFullAccess) – 當政策連接至 的身分使用 AWS 管理主控台時，授予 AWS Glue 資源的完整存取權。如果您依照此政策中指定的資源命名慣例，使用者就能擁有完整的主控台功能。此政策通常連接到 AWS Glue 主控台的使用者。
+ [SecretsManagerReadWrite](https://console.aws.amazon.com/iam/home#policies/arn:aws:iam::aws:policy/SecretsManagerReadWrite) – 透過 AWS 管理主控台提供讀取/寫入存取權給 AWS Secrets Manager。注意：這不包括 IAM 動作，因此如果需要輪換組態，請結合 `IAMFullAccess`。

**設定 VPC 所需的 IAM 政策/許可**

使用 VPC 連線建立 AWS Glue 連線時，需要下列 IAM 許可。如需詳細資訊，請參閱[為 AWS Glue建立 IAM 政策](https://docs.aws.amazon.com/glue/latest/dg/create-service-policy.html)。

------
#### [ JSON ]

****  

```
{
  "Version":"2012-10-17",		 	 	 
  "Statement": [
    {
      "Effect": "Allow",
      "Action": [
        "ec2:CreateNetworkInterface",
        "ec2:DeleteNetworkInterface",
        "ec2:DescribeNetworkInterfaces"
      ],
      "Resource": [
        "*"
      ]
    }
  ]
}
```

------

# 連線/VPC 連線
<a name="sap-odata-connectivity-vpc-connection"></a>

VPC 連線步驟：

1. 使用現有 VPC 連線，或遵循 [Amazon VPC 文件](https://docs.aws.amazon.com/vpc/latest/userguide/create-vpc.html)建立新連線。

1. 請確保擁有將流量路由到網際網路的 NAT 閘道。

1. 選擇 VPC 端點作為 Amazon S3 閘道來建立連線。

1. 啟用 DNS 解析和 DNS 主機名稱以使用 AWS 提供的 DNS 服務。

1. 前往已建立的 VPC，並為 STS AWS Glue、Secret Manager 等不同服務新增必要的端點。

   1. 選擇建立端點。

   1. 針對服務類別，選擇 AWS 服務。

   1. 針對「服務名稱」，選擇要連線的服務。

   1. 選擇 VPC 並啟用 DNS 名稱。

   1. VPC 連線所需的 VCP 端點：

      1. [STS](https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_sts_vpc_endpoint_create.html)

      1. [AWS Glue](https://docs.aws.amazon.com/glue/latest/dg/vpc-interface-endpoints.html)

      1. [Secrets Manager](https://docs.aws.amazon.com/secretsmanager/latest/userguide/vpc-endpoint-overview.html)

## 安全群組設定
<a name="sap-odata-security-group-configuration"></a>

安全群組必須允許來自 AWS Glue VPC 的接聽連接埠流量， AWS Glue 才能連線到它。最佳實務是盡可能限制來源 IP 地址的範圍。

AWS Glue 需要特殊的安全群組，允許所有來自其本身的傳入流量。可以建立自我參考規則，其允許來自安全群組的所有流量。可以修改現有的安全群組，並將安全群組指定為來源。

從 URL 端點的 HTTPS 連接埠 (NLB 或 SAP 執行個體) 中開啟通訊。

## 連線選項
<a name="sap-odata-connectivity-options"></a>
+ HTTPS 與內部和外部 NLB 的連線，來自憑證認證機構 (CA) 的 SSL 憑證，而非自我簽署的 SSL 憑證
+ 與來自憑證認證機構 (CA) 的 SAP 執行個體 SSL 憑證的 HTTPS 連線，而非自我簽署的 SSL 憑證

# SAP 身分驗證
<a name="sap-odata-authentication"></a>

SAP 連接器同時支援 CUSTOM (這是 SAP BASIC 身分驗證) 和 OAUTH 身分驗證方法。

## 自訂身分驗證
<a name="sap-odata-custom-authentication"></a>

AWS Glue 支援自訂 （基本身分驗證） 作為建立 SAP 系統連線的方法，允許使用使用者名稱和密碼進行安全存取。此身分驗證類型適用於自動化案例，因為它允許在 SAP OData 執行個體中預先使用具有特定使用者許可的使用者名稱和密碼。 AWS Glue 可以使用使用者名稱和密碼來驗證 SAP OData APIs。在 中 AWS Glue，基本授權會實作為自訂授權。

如需基本驗證流程的公有 SAP OData 文件，請參閱 [HTTP 基本身分驗證](https://help.sap.com/docs/SAP_SUCCESSFACTORS_PLATFORM/d599f15995d348a1b45ba5603e2aba9b/5c8bca0af1654b05a83193b2922dcee2.html)。

## OAuth 2.0 身分驗證
<a name="sap-odata-oauth-2.0-authentication"></a>

AWS Glue 也支援 OAuth 2.0 做為建立 SAP 系統連線的安全身分驗證機制。這可實現無縫整合，同時確保符合現代身分驗證標準，並提高資料存取的安全性。

## AUTHORIZATION\$1CODE 授權類型
<a name="sap-odata-authentication-code-grant-type"></a>

授予類型決定 如何與 SAP OData AWS Glue 通訊，以請求存取您的資料。SAP OData 僅支援 `AUTHORIZATION_CODE` 授權類型。此授權類型被視為「三條腿的」OAuth，因為其依賴將使用者重新導向至第三方授權伺服器來驗證使用者。透過 AWS Glue 主控台建立連線時，會使用它。

使用者仍然可以選擇在 SAP OData 中建立自己的連線應用程式，並在透過 AWS Glue 主控台建立連線時提供自己的用戶端 ID 和用戶端秘密。在此案例中，它們仍會重新導向至 SAP OData 以登入並授權 AWS Glue 存取其資源。

此授權類型會產生重新整理字符和存取字符。存取字符是短期存留的，可以使用重新整理字符自動重新整理，而無需使用者互動。

如需有關建立授權碼 OAuth 流程之連線應用程式的公有 SAP OData 文件，請參閱[使用 OAuth 2.0 進行身份驗證](https://help.sap.com/docs/ABAP_PLATFORM_NEW/e815bb97839a4d83be6c4fca48ee5777/2e5104fd87ff452b9acb247bd02b9f9e.html)。

# AWS Secrets Manager 來存放您的 Auth 秘密
<a name="sap-odata-aws-secret-manager-auth-secret"></a>

您需要將 SAP OData 連線秘密存放在 AWS Secrets Manager 中，設定必要的擷取許可，如 [IAM 政策](sap-odata-configuring-iam-permissions.md)一節所指定，並在建立連線時使用它。

使用 AWS Secrets Manager 的 AWS 管理主控台為您的 SAP 來源建立秘密。如需詳細資訊，請參閱[建立 AWS Secrets Manager 秘密](https://docs.aws.amazon.com/secretsmanager/latest/userguide/create_secret.html)。 AWS Secrets Manager 中的詳細資訊應該包含下列程式碼中的元素。

## 自訂身分驗證機密
<a name="sap-odata-custom-auth-secret"></a>

您需要輸入 SAP 系統使用者名稱而非 *<your SAP username>*，輸入其密碼而非 *<your SAP username password>*，並輸入 True 或 False。在此情況下，將 `basicAuthDisableSSO` 設定為 `true` 會停用基本身分驗證請求的單一登入 (SSO)，每個請求都需要明確的使用者憑證。相反，如果可用，將其設定為 `false` 可允許使用現有的 SSO 工作階段。

```
{
   "basicAuthUsername": "<your SAP username>",
   "basicAuthPassword": "<your SAP username password>",
   "basicAuthDisableSSO": "<True/False>",
   "customAuthenticationType": "CustomBasicAuth"
}
```

## OAuth 2.0 機密
<a name="sap-odata-oauth-2.0-secret"></a>

如果您使用 OAuth 2.0 做為身分驗證機制， AWS Secrets Manager 中的秘密應該具有下列格式**的使用者受管用戶端應用程式 ClientId**。您需要輸入 SAP 用戶端機密而非 <your client secret>。

```
{"USER_MANAGED_CLIENT_APPLICATION_CLIENT_SECRET": "<your client secret>"
}
```

# 建立連線
<a name="sap-odata-creating-connections"></a>

若要設定 SAP OData 連線：

1. 登入 AWS 管理主控台並開啟[AWS Glue 主控台](https://console.aws.amazon.com/glue)。在 AWS Glue Studio 中，依照下列步驟建立連線：

   1. 按一下左側面板中的「資料連線」。

   1. 按一下「建立連線」。

   1. 在**選擇資料來源**中選取 **SAP OData** 

   1. 提供您要連線之 SAP OData 執行個體的**應用程式主機 URL**。對於非 VPC 連線，必須可透過公有網際網路存取此應用程式主機 URL。

   1. 提供您要連線之 SAP OData 執行個體的**應用程式服務路徑**。這與目錄服務路徑相同。例如：`/sap/opu/odata/iwfnd/catalogservice;v=2`. AWS Glue doesn 不接受特定物件路徑。

   1. 提供您要連線之 SAP OData 執行個體的**用戶端編號**。可接受的值為 [001-999]。範例： 010

   1. 提供您要連線之 SAP OData 執行個體的**連接埠號碼**。範例：443

   1. 提供您要連線之 SAP OData 執行個體的**登入語言**。範例：EN

   1. 選取 AWS Glue 可擔任的 AWS IAM 角色，並具有 [IAM 政策](sap-odata-configuring-iam-permissions.md)區段中所述的許可。

   1.  AWS Glue 從下拉式清單中選取您要用於 中此連線的**身分驗證類型**：OAUTH2 或 CUSTOM

      1. CUSTOM - 選取您在 [AWS Secrets Manager 來存放您的 Auth 秘密](sap-odata-aws-secret-manager-auth-secret.md) 一節中指定的機密。

      1. OAUTH 2.0 - 僅在 OAuth 2.0 的情況下鍵入下列輸入：

         1. 在**使用者管理的用戶端應用程式用戶端 Id** 下，輸入您的用戶端 ID。

         1. `USER_MANAGED_CLIENT_APPLICATION_CLIENT_SECRET` （您的用戶端秘密） 位於您在 [AWS Secrets Manager 來存放您的 Auth 秘密](sap-odata-aws-secret-manager-auth-secret.md)區段中建立的 AWS Secrets Manager。

         1. 在**授權碼 URL** 下，輸入授權碼 URL。

         1. 在**授權字符 URL** 下，輸入授權字符 URL。

         1. 在 **OAuth 範圍下**，輸入以空格分隔的 OAuth 範圍。範例：`/IWFND/SG_MED_CATALOG_0002 ZAPI_SALES_ORDER_SRV_0001`

   1. 如果想要使用您的網路，請選取網路選項。如需詳細資訊，請參閱[連線/VPC 連線](sap-odata-connectivity-vpc-connection.md)。

1. 授予與您的 AWS Glue 任務相關聯的 IAM 角色讀取 的許可`secretName`。如需詳細資訊，請參閱「[IAM 政策](sap-odata-configuring-iam-permissions.md)」。

1. 選擇**測試連線**並測試您的連線。如果連線測試通過，請按一下「下一步」，然後輸入連線名稱並儲存連線。如果已選擇網路選項 (VPC)，則無法使用測試連線功能。

# 建立 SAP OData 任務
<a name="sap-odata-creating-job"></a>

請參閱[使用 AWS Glue Studio 建置視覺化 ETL 任務](https://docs.aws.amazon.com/glue/latest/dg/author-job-glue.html)

# 營運資料佈建 (ODP) 來源
<a name="sap-odata-operational-data-provisioning-sources"></a>

營運資料佈建 (ODP) 提供技術基礎設施，可以用來支援各種目標應用程式的資料擷取和複寫，並支援這些案例中的 delta 機制。如果為 delta 程序，來源 (ODP 提供者) 中的資料會使用更新程序自動寫入 delta 佇列 (Operational Delta Queue – ODQ)，或使用擷取器界面傳遞至 delta 佇列。ODP 提供者可以是 DataSource (擷取器)、ABAP Core Data Services Views (ABAP CDS Views)、SAP BW 或 SAP BW/4HANA、SAP Landscape Transformation Replication Server (SLT) 和 SAP HANA Information Views (計算檢視)。目標應用程式 (稱為 ODQ 「訂閱者」或更普遍稱為「ODP 消費者」) 從 delta 佇列中擷取資料並繼續處理資料。

## 完整載入
<a name="sap-odata-full-load"></a>

在 SAP OData 和 ODP 實體的內容中，**完整載入**是指在單一操作中從 ODP 實體擷取所有可用資料的程序。此操作會從來源系統中擷取完整的資料集，確保目標系統擁有實體資料的完整最新副本。完全載入通常用於不支援增量載入的來源或需要重新整理目標系統時。

**範例**

您可以在建立 DynamicFrame 時，明確將 `ENABLE_CDC` 旗標設為 false。注意：`ENABLE_CDC` 預設為 false，如果您不想初始化 delta 佇列，則不需要傳送此旗標或將其設定為 true。未將此旗標設定為 true 將導致完整的載入擷取。

```
sapodata_df = glueContext.create_dynamic_frame.from_options(
    connection_type="SAPOData",
    connection_options={
        "connectionName": "connectionName",
        "ENTITY_NAME": "entityName",
        "ENABLE_CDC": "false"
    }, transformation_ctx=key)
```

## 增量載入
<a name="sap-odata-incremental-load"></a>

ODP (Operational Data Provisioning) 實體內容中的**增量載入**包括自上次資料擷取以來，僅從來源系統擷取新的或變更的資料 (delta)，避免預先處理已處理的記錄。這種方法可大幅提升效率、減少資料傳輸量、提高效能、確保系統之間的高效同步，並將處理時間降至最低，尤其是經常變更的大型資料集。

# Delta Token 型增量傳輸
<a name="sap-odata-incremental-transfers"></a>

對於支援其已啟用 ODP 的實體，若要使用變更資料擷取 (CDC) 啟用增量傳輸，請遵循下列步驟：

1. 在指令碼模式下建立增量傳輸任務。

1. 建立 DataFrame 或 Glue DynamicFrame 時，需要傳遞選項 `"ENABLE_CDC": "True"`。此選項可確保您會收到來自 SAP 的 Delta Token，其可用於後續擷取變更的資料。

Delta Token 會出現在 DELTA\$1TOKEN 資料欄中 dataframe 的最後一列。此字符可用作後續呼叫中的連接器選項，以逐步擷取下一組資料。

**範例**
+ 建立 DynamicFrame 時，我們會將 `ENABLE_CDC` 旗標設定為 `true`。注意：`ENABLE_CDC` 預設為 `false`，如果您不想初始化 delta queue，則不需要傳送此旗標或將其設定為 true。未將此旗標設定為 true 將導致完整的載入擷取。

  ```
  sapodata_df = glueContext.create_dynamic_frame.from_options(
      connection_type="SAPOData",
      connection_options={
          "connectionName": "connectionName",
          "ENTITY_NAME": "entityName",
          "ENABLE_CDC": "true"
      }, transformation_ctx=key)
  
  # Extract the delta token from the last row of the DELTA_TOKEN column
  delta_token_1 = your_logic_to_extract_delta_token(sapodata_df) # e.g., D20241029164449_000370000
  ```
+ 擷取的 delta token 可以作為選項進行傳遞，以擷取新事件。

  ```
  sapodata_df_2 = glueContext.create_dynamic_frame.from_options(
      connection_type="SAPOData",
      connection_options={
          "connectionName": "connectionName",
          "ENTITY_NAME": "entityName",
          // passing the delta token retrieved in the last run
          "DELTA_TOKEN": delta_token_1
      } , transformation_ctx=key)
  
  # Extract the new delta token for the next run
  delta_token_2 = your_logic_to_extract_delta_token(sapodata_df_2)
  ```

請注意，其中存在 `DELTA_TOKEN` 的最後一個記錄不是來自來源的交易記錄，而是僅用於傳遞 delta token 值。

除了 `DELTA_TOKEN` 之外，dataframe 的每一列都會傳回下列欄位。
+ **GLUE\$1FETCH\$1SQ**：這是一個序列欄位，按照記錄接收順序從 EPOC 時間戳記產生，對於每個記錄都是唯一的。如果您需要了解或建立來源系統中的變更順序，則可以使用此功能。只有啟用 ODP 的實體才會出現此欄位。
+ **DML\$1STATUS**：這會顯示來源中所有新插入和更新記錄的 `UPDATED`，以及已從來源中刪除之記錄的 `DELETED`。

如需有關如何管理狀態和重複使用 delta token 以透過範例擷取變更記錄的詳細資訊，請參閱 [使用 SAP OData 狀態管理指令碼](sap-odata-state-management-script.md) 一節。

## Delta Token 失效
<a name="sap-odata-invalidation"></a>

Delta Token 與服務集合和使用者相關聯。如果針對相同的服務集合和使用者啟動具有 `“ENABLE_CDC” : “true”` 的新初始提取，則 SAP OData 服務將使先前初始化後簽發的所有之前的 delta token 失效。使用過期的 delta token 叫用連接器將導致例外狀況：

`Could not open data access via extraction API RODPS_REPL_ODP_OPEN` 

# OData 服務 (非 ODP 來源)
<a name="sap-odata-non-odp-services"></a>

## 完整載入
<a name="sap-odata-non-odp-full-load"></a>

對於非 ODP (營運資料佈建) 系統，**完整載入**涉及從來源系統擷取整個資料集，並將其載入目標系統。由於非 ODP 系統本質上不支援 deltas 等進階資料擷取機制，因此程序非常簡單，但可能會耗費大量資源，具體取決於資料大小。

## 增量載入
<a name="sap-odata-non-odp-incremental-load"></a>

對於不支援 **ODP (營運資料佈建)** 的系統或實體，可透過實作時間戳記型機制來追蹤和擷取變更，手動管理增量資料傳輸。

**時間戳記型增量傳輸**

對於啟用非 ODP 的實體 (或未使用 ENABLE\$1CDC 旗標的已啟用 ODP 的實體)，我們可以在連接器中使用 `filteringExpression` 選項來指示要擷取資料的 `datetime` 間隔。此方法依賴於資料中的時間戳記欄位，表示上次建立/修改每個記錄的時間。

**範例**

擷取 2024-01-01T00：00：00.000 之後變更的記錄

```
sapodata_df = glueContext.create_dynamic_frame.from_options(
    connection_type="SAPOData",
    connection_options={
        "connectionName": "connectionName",
        "ENTITY_NAME": "entityName",
        "filteringExpression": "LastChangeDateTime >= 2024-01-01T00:00:00.000"
    }, transformation_ctx=key)
```

注意：在此範例中，`LastChangeDateTime` 欄位表示上次修改每個記錄的時間。實際欄位名稱可能會因您的特定 SAP OData 實體而有所不同。

若要在後續執行中取得新的資料子集，可以使用新的時間戳記來更新 `filteringExpression`。一般而言，這是先前擷取資料的最大時間戳記值。

**範例**

```
max_timestamp = get_max_timestamp(sapodata_df)  # Function to get the max timestamp from the previous run
next_filtering_expression = f"LastChangeDateTime > {max_timestamp}"

# Use this next_filtering_expression in your next run
```

在下一節中，我們將提供自動化方法來管理這些時間戳記型增量傳輸，無需在執行之間手動更新篩選表達式。

# 寫入到 SAP OData
<a name="sap-odata-writing"></a>

 本節說明如何使用 SAP OData AWS Glue 連接器將資料寫入 SAP OData Service。

**先決條件**
+ 存取 SAP OData 服務
+ 您想要寫入到的 SAP OData EntitySet 物件。將需要物件名稱。
+ 有效的 SAP OData 憑證和有效的連線
+ IAM [政策](https://docs.aws.amazon.com/glue/latest/dg/sap-odata-configuring-iam-permissions.html)中所述的適當許可

SAP OData 連接器支援兩種寫入操作：
+ INSERT
+ UPDATE

使用 UPDATE 寫入操作時，必須提供 ID\$1FIELD\$1NAMES 來指定記錄的外部 ID 欄位。

**範例**：

```
sapodata_write = glueContext.write_dynamic_frame.from_options(
    frame=frameToWrite,
    connection_type="sapodata",
    connection_options={
        "connectionName": "connectionName",
        "ENTITY_NAME": "entityName",
        "WRITE_OPERATION": "INSERT"
    }
```

# 使用 SAP OData 狀態管理指令碼
<a name="sap-odata-state-management-script"></a>

若要在 AWS Glue 任務中使用 SAP OData 狀態管理指令碼，請遵循下列步驟：
+ 下載狀態管理指令碼：公有 Amazon S3 儲存貯體中的 `s3://aws-blogs-artifacts-public/artifacts/BDB-4789/sap_odata_state_management.zip `。
+ 將指令碼上傳至您的 AWS Glue 任務具有存取許可的 Amazon S3 儲存貯體。
+ 參考 AWS Glue 任務中的指令碼：建立或更新 AWS Glue 任務時，請傳遞參考 Amazon S3 儲存貯體中指令碼路徑`'--extra-py-files'`的選項。例如：`--extra-py-files s3://your-bucket/path/to/sap_odata_state_management.py`
+ 在 AWS Glue 任務指令碼中匯入和使用狀態管理程式庫。

## Delta-token 型增量傳輸範例
<a name="sap-odata-delta-token-incremental-transfer"></a>

以下是如何使用狀態管理指令碼進行 Delta-token 型增量傳輸的範例：

```
from sap_odata_state_management import StateManagerFactory, StateManagerType, StateType

# Initialize the state manager
state_manager = StateManagerFactory.create_manager(
    manager_type=StateManagerType.JOB_TAG,
    state_type=StateType.DELTA_TOKEN,
    options={
        "job_name": args['JOB_NAME'],
        "logger": logger
    }
)

# Get connector options (including delta token if available)
key = "SAPODataNode"
connector_options = state_manager.get_connector_options(key)

# Use the connector options in your Glue job
df = glueContext.create_dynamic_frame.from_options(
    connection_type="SAPOData",
    connection_options={
        "connectionName": "connectionName",
        "ENTITY_NAME": "entityName",
        "ENABLE_CDC": "true",
        **connector_options
    }
)

# Process your data here...

# Update the state after processing
state_manager.update_state(key, sapodata_df.toDF())
```

## 時間戳記型增量傳輸範例
<a name="sap-odata-timestamp-incremental-transfer"></a>

以下是如何使用狀態管理指令碼進行 Delta-token 型增量傳輸的範例：

```
from sap_odata_state_management import StateManagerFactory, StateManagerType, StateType

# Initialize the state manager
state_manager = StateManagerFactory.create_manager(
    manager_type=StateManagerType.JOB_TAG,
    state_type=StateType.DELTA_TOKEN,
    options={
        "job_name": args['JOB_NAME'],
        "logger": logger
    }
)

# Get connector options (including delta token if available)
key = "SAPODataNode"
connector_options = state_manager.get_connector_options(key)

# Use the connector options in your Glue job
df = glueContext.create_dynamic_frame.from_options(
    connection_type="SAPOData",
    connection_options={
        "connectionName": "connectionName",
        "ENTITY_NAME": "entityName",
        "ENABLE_CDC": "true",
        **connector_options
    }
)

# Process your data here...

# Update the state after processing
state_manager.update_state(key, sapodata_df.toDF())
```

在這兩個範例中，狀態管理指令碼會處理在任務執行之間存放狀態 (delta token 或時間戳記) 的複雜性。其會在取得連接器選項時自動擷取最後的已知狀態，並在處理後更新狀態，確保每個任務只會處理最新的或變更的資料。

# 非 ODP 實體的分區
<a name="sap-odata-non-odp-entities-partitioning"></a>

在 Apache Spark 中，分區是指在叢集中的工作者節點之間分區和分配資料以進行平行處理的方式。每個分區都是可由任務獨立處理的資料邏輯區塊。分割是 Spark 中的基本概念，直接影響效能、可擴展性和資源使用率。 AWS Glue 工作使用 Spark 的分割機制，將資料集分割為較小的區塊 （分割區），可在叢集的工作者節點之間平行處理。請注意，分區不適用於 ODP 實體。

如需詳細資訊，請參閱 [AWS Glue Spark 和 PySpark 任務](https://docs.aws.amazon.com/glue/latest/dg/spark_and_pyspark.html)。

**先決條件**

您想要從中讀取的 SAP OData 的物件。將需要物件/實體集名稱。例如：` /sap/opu/odata/sap/API_SALES_ORDER_SRV/A_SalesOrder `。

**範例**

```
sapodata_read = glueContext.create_dynamic_frame.from_options(
    connection_type="SAPOData",
    connection_options={
        "connectionName": "connectionName",
        "ENTITY_NAME": "/sap/opu/odata/sap/API_SALES_ORDER_SRV/A_SalesOrder"
    }, transformation_ctx=key)
```

## 分區查詢
<a name="sap-odata-partitioning-queries"></a>

### 欄位型分區
<a name="sap-odata-field-based-partitioning"></a>

如果想要在 Spark 中使用並行，可以提供其他 Spark 選項 `PARTITION_FIELD`、`LOWER_BOUND`、`UPPER_BOUND` 和 `NUM_PARTITIONS`。使用這些參數，原始查詢會分區為可由 Spark 任務並行執行的子查詢的 `NUM_PARTITIONS` 數目。Integer、Date 和 DateTime 欄位在 SAP OData 連接器中支援欄位型分區。
+ `PARTITION_FIELD`：用來分區查詢的欄位名稱。
+ `LOWER_BOUND`：所選分區欄位的包含下限值。

   對於資料類型為 DateTime 的所有欄位，可接受 Spark SQL 查詢中使用的 Spark 時間戳記格式。

  有效值的範例：`"2000-01-01T00:00:00.000Z"`
+ `UPPER_BOUND`：所選分區欄位的唯一上限值。
+ `NUM_PARTITIONS`：分區數目。
+ `PARTITION_BY`：要執行的類型分區，如果為欄位型分區，則會傳遞 `FIELD`。

**範例**

```
sapodata= glueContext.create_dynamic_frame.from_options(
    connection_type="sapodata",
    connection_options={
        "connectionName": "connectionName",
        "ENTITY_NAME": "/sap/opu/odata/sap/SEPM_HCM_SCENARIO_SRV/EmployeeSet",
        "PARTITION_FIELD": "validStartDate"
        "LOWER_BOUND": "2000-01-01T00:00:00.000Z"
        "UPPER_BOUND": "2020-01-01T00:00:00.000Z"
        "NUM_PARTITIONS": "10",
        "PARTITION_BY": "FIELD"
    }, transformation_ctx=key)
```

### 記錄型分區
<a name="sap-odata-record-based-partitioning"></a>

原始查詢會分區為 Spark 任務可同時執行的子查詢的 `NUM_PARTITIONS` 數目。

記錄型分區僅支援非 ODP 實體，因為下一個 token/skip token 支援 ODP 實體中的分頁。
+ `PARTITION_BY`：要執行的類型分區。如果為記錄型分區，則會傳遞 `COUNT`。

**範例**

```
sapodata= glueContext.create_dynamic_frame.from_options(
    connection_type="sapodata",
    connection_options={
        "connectionName": "connectionName",
        "ENTITY_NAME": "/sap/opu/odata/sap/SEPM_HCM_SCENARIO_SRV/EmployeeSet",
        "NUM_PARTITIONS": "10",
        "PARTITION_BY": "COUNT"
    }, transformation_ctx=key)
```

# 限制/標註
<a name="sap-odata-limitations"></a>
+ ODP 實體與記錄型分區不相容，因為分頁是使用 skip token/delta token 來處理的。因此，對於記錄型分區，無論使用者輸入為何，maxConcurrency 的預設值都會設為 "null"。
+ 同時套用限制和分區時，限制優先於分區。

# SAP OData 連線選項
<a name="sap-odata-connection-options"></a>

以下是 SAP OData 的連線選項：
+ `ENTITY_NAME`(String) - (必要) 用於讀取。SAP OData 中的物件名稱。

  例如：/sap/opu/odata/sap/API\$1SALES\$1ORDER\$1SRV/A\$1SalesOrder
+ `API_VERSION`(String) - (選用) 用於讀取。您想要使用的 SAP OData Rest API 版本。範例：2.0。
+ `SELECTED_FIELDS`(List<String>) - 預設：empty(SELECT \$1)。用於讀取。您要為物件選取的資料欄。

  例如：SalesOrder
+ `FILTER_PREDICATE`(String) - 預設：空白。用於讀取。其應該為 Spark SQL 格式。

  例如：`SalesOrder = "10"`
+ `QUERY`(String) - 預設：空白。用於讀取。完整的 Spark SQL 查詢。

  例如：`SELECT * FROM /sap/opu/odata/sap/API_SALES_ORDER_SRV/A_SalesOrder`
+ `PARTITION_FIELD`(String) - 用於讀取。用於分區查詢的欄位。

  例如：`ValidStartDate`
+ `LOWER_BOUND`(String) - 用於讀取。所選分區欄位的包含下限值。

  例如：`"2000-01-01T00:00:00.000Z"`
+ `UPPER_BOUND`(String) - 用於讀取。所選分區欄位的唯一上限值。

  例如：`"2024-01-01T00:00:00.000Z"`
+ `NUM_PARTITIONS`(Integer) - 預設：1。用於讀取。要讀取的分區數目。
+ `INSTANCE_URL`(String) - SAP 執行個體應用程式主機 URL。

  例如：`https://example-externaldata.sierra.aws.dev`
+ `SERVICE_PATH`(String) - SAP 執行個體應用程式服務路徑。

  例如：`/sap/opu/odata/iwfnd/catalogservice;v=2`
+ `CLIENT_NUMBER`(String) - SAP 執行個體應用程式用戶端編號。

  例如：100
+ `PORT_NUMBER`(String) - 預設：SAP 執行個體應用程式連接埠號碼。

  例如：443
+ `LOGON_LANGUAGE`(String) - SAP 執行個體應用程式登入語言。

  例如：`EN`
+ `ENABLE_CDC`(String) - 定義是否在啟用 CDC 的情況下執行任務，即追蹤變更。

  例如：`True/False`
+ `DELTA_TOKEN`(String) - 根據提供的有效 Delta Token 執行增量資料提取。

  例如：`D20241107043437_000463000`
+ `PAGE_SIZE`(Integer) - 定義查詢記錄的頁面大小。預設頁面大小為 50，000。指定頁面大小時，SAP 僅傳回每個 API 呼叫定義的記錄數，而不是整個資料集。連接器仍會提供記錄總數，並使用指定的頁面大小來處理分頁。如果需要更大的頁面大小，可以選擇任何值，最高可達 500,000，這是允許的最大值。將會忽略超過 500,000 的指定頁面大小。反之，系統會使用允許的頁面大小上限。您可以新增`PAGE_SIZE`具有所需值的連線選項，在 AWS Glue Studio UI 中指定頁面大小。

  例如：`20000`

# SAP OData 實體和欄位詳細資訊
<a name="sap-odata-entity-field-details"></a>

[\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/zh_tw/glue/latest/dg/sap-odata-entity-field-details.html)