注意:

使用通知事件呼叫 Oracle Cloud Infrastructure 自訂功能,並將更新的訊息發布到 Lark 協同合作工具

簡介

Oracle Cloud Infrastructure (OCI) 客戶會透過訂閱的 OCI 通知主題收到通知,這些主題涵蓋執行處理事件、警示、主控台公告等事件。這些訂閱的主題也支援 OCI 函數作為「通知目標」,讓客戶能夠在通知事件期間呼叫自訂函數,並將更新的通知詳細資訊傳送至支援 API 呼叫的通訊通道。在本教學課程中,我們將告訴您如何將這些更新的通知轉送給具有訊息傳遞 API 的企業協同合作平台 Lark

使用自訂 OCI 函數,您可以擷取各種資料並執行動作,以下為幾個範例:

本教學課程內容將提供全方位的逐步解說,說明如何觸發自訂 OCI 函數以回應執行處理的電源事件 (例如 STOP)。使用者可以彈性自訂此函數,並根據各種訂閱的 OCI 通知主題觸發此函數。如需有關 OCI 函數的詳細資訊,請參閱 OCI Functions Overview

目標

OCI Functions 可讓您撰寫自訂程式碼,根據 OCI 通知、OCI 公告訂閱的通知主題、運算執行處理的事件等進行呼叫。在本教學課程中,我們建立了以 Python 程式碼撰寫的自訂函數,此函數會根據通知事件呼叫,並使用程式碼中的 Webhook URL 將更新的訊息發布至 Lark 協同合作工具。這可讓您選擇包含和更新一般使用者可使用的必要其他資訊。

必要條件

對象

本教學課程的對象為 Cloud Service 提供者管理員和專業人員。

架構

以下是解決方案的範例使用案例拓樸和高階架構。

OCI Azure Interconnect 跨區域連線架構

若要建立自訂 OCI 函數並根據通知事件呼叫此函數,您可以參照此架構。您可以依照本教學課程中概述的一系列作業,設定並驗證此架構。

作業 1:建立動態群組

動態群組可讓您將 OCI 運算執行處理群組為「主要」動作者 (類似於使用者群組)。

注意:您必須有管理員權限才能建立動態群組。

  1. 登入 OCI 主控台租用戶帳戶。

  2. 從服務功能表中,選取識別與安全性,然後從識別區段中選取動態群組

  3. 按一下建立動態群組 (Create Dynamic Group)

  4. 輸入有意義的名稱描述

  5. 規則 1 區段中,新增下列行:

    ALL {resource.type = 'fnfunc', resource.compartment.id = 'ocid1.compartment.oc1', instance.compartment.id = 'ocid1.compartment.XXXXX'}

    注意:

    • 以您想要的區間 ID 取代區間 ID。
    • 您也可以在動態群組中包含特定函數資源 OCID。
  6. 按一下建立,即可順利建立您的動態群組,如下列影像所示。

    已建立動態群組

作業 2:建立動態群組 OCI IAM 原則

Oracle Cloud Infrastructure Identity and Access Management (OCI IAM) 可讓您控制可存取您雲端資源的人員。為了使此架構能夠運作,我們需要將功能即服務法斯的存取權授予運算、網路和數個其他服務。

  1. 從服務功能表中,選取識別與安全性,然後從識別區段中選取政策

  2. 按一下建立原則

  3. 輸入適當的名稱描述,並確定選擇正確的區間 (在此範例中,將使用區間名稱 oc-demo)。

  4. Policy Builder 區段中,確定啟用顯示手動編輯器選項並貼上以下幾行:

    Allow dynamic-group <dynamic_group_name> to read instances in compartment <compartment_name_path>

    Allow dynamic-group <dynamic_group_name> to read vnics in compartment <compartment_name_path>

    Allow dynamic-group <dynamic_group_name> to read vnic-attachments in compartment <compartment_name_path>

    注意:請將 dynamic_group_name 名稱和 compartment_name_path 取代為所需的值。

  5. 按一下建立 (Create) ,原則應順利在根目錄 / 您的區間層次建立,如下列影像所示。

    已建立的 IAM 原則

作業 3:建立儲存庫以儲存自訂函數影像

容器登錄可讓您在 Oracle 管理的登錄中儲存、共用及管理容器映像檔 (例如 Docker 映像檔)。

  1. 在主控台中開啟服務功能表,然後按一下開發人員服務。在容器底下,按一下容器登錄

  2. 按一下建立儲存區域 (Create Repository)

  3. 建立儲存區域對話方塊中,指定您選擇的區間儲存區域名稱,然後將其保留為專用

  4. 按一下建立儲存區域,應該在您的指定區間中順利建立您的容器登錄,如下列影像所示。

    已建立的容器登錄儲存庫

作業 4:建立一個搭配子網路的虛擬雲端網路,用於儲存應用程式功能。

虛擬雲端網路 (VCN) 是您在 OCI 中定義的網路。它包括子網路、路由表和閘道。

注意:如果您已經有 VCN,可以略過此作業並繼續進行作業 5

  1. 按一下 OCI Web 主控台左上角的服務功能表。

  2. 網路底下,選取虛擬雲端網路

  3. 在「虛擬雲端網路 (Virtual Cloud Networks)」頁面上,按一下啟動 VCN 精靈

  4. 選取使用網際網路連線建立 VCN ,然後按一下啟動 VCN 精靈

  5. 完成 VCN 組態,然後按一下下一步 (Next)

  6. 按一下建立,即可順利建立具有子網路的虛擬雲端網路,如下圖所示。

    使用子網路建立的虛擬網路

作業 5:建立應用模組以儲存功能

  1. 開啟服務功能表,然後按一下開發人員服務。在函數下方,按一下應用程式

  2. 按一下建立應用程式

  3. 建立應用程式視窗中,選取應用程式的名稱 (例如 function-app),選取您在任務 4 中建立的 VCN,然後選取公用子網路。

  4. 按一下建立,應該順利建立函數應用程式,如下列影像所示。

    已建立函數應用程式

作業 6:部署儲存函數的函數

此步驟將使用可從此教學課程的「先決條件」段落下載的壓縮存檔。

  1. 瀏覽至您的 OCI 雲端主控台,然後按一下 Developer ToolsCloud Shell

    啟動 Cloud Shell

  2. 按一下啟動 Cloud Shell 按鈕後,頁面結尾會顯示新的小型 Shell 視窗。在該視窗的右上角,按一下齒輪功能表並選取上傳

    上傳壓縮檔

  3. 上傳此教學課程「先決條件」段落中可用的 zip 檔案,並瀏覽至複製的目錄。

  4. 您將會看到建立如下的 func.py 檔案,以確保您能夠讀取 notification JSON 並新增其他欄位 (例如 IP 位址詳細資訊),然後使用更新的訊息將訊息傳送到 Lark Webhook URL。

    • parse_message :函數讀取通知 JSON 並更新訊息
    • get_ip_address :使用運算、網路從屬端程式庫讀取其他詳細資訊 (例如以執行處理資源 OCID 為基礎的 IP 位址) 的函數。
    • make_post :使用 Webhook URL 將張貼至 Lark 通道的功能。

    注意:

    • 我們使用 OCI python sdk,但您可以使用 go/java sdks,根據其他支援的語言進行自訂。
    • 您必須更新您的 Webhook URL,可以是 Lark 或其他協同合作工具 (例如 Slack)。
    • 您可以根據需求自訂此函數。我們使用特定通知 JSON 有效負載來讀取值,但您也可以使用主控台公告 JSON 或其他事件 JSON。
    ###
    This is a sample code,
    End user can modify as needed
    ###
    import io
    import oci
    import json
    import logging
    import requests
    
    """
    Read Notification Message
    Add IP address of Resource.
    """
    def parse_message(body):
        notification = ""
        ocid = ""
        type = body["source"]
        description = body["eventType"]
        compartment_id = body["data"]["compartmentId"]
        compartment_name = body["data"]["compartmentName"]
        affected_resources = ""
    
        if len(body["data"]) > 0:
            signer = oci.auth.signers.get_resource_principals_signer()
            affected_resources = "Affected Resources: "
            ocid = body["data"]["resourceId"]
            notification_reason = body["data"]["additionalDetails"]["instanceActionType"]
            affected_resources += "\nResource OCID: " + ocid
            resource_ip_address = get_ip_address(signer, ocid)
            affected_resources += "\nResource Private IP Address: " + resource_ip_address
    
        notification = type + " " + "\n\n" + compartment_name + " - " + compartment_id + "\n\n" + description + "\n\n" + affected_resources + "\n\n" + notification_reason
        logging.getLogger().debug(notification)
    
        make_post(notification)
    
    """
    Get Resource IP address
    based of resource OCID.
    """
    def get_ip_address(signer, resource_id):
        compute_client = oci.core.ComputeClient(config={}, signer=signer)
        network_client = oci.core.VirtualNetworkClient(config={}, signer=signer)
        instance_details = compute_client.get_instance(instance_id=resource_id).data
        vnic_response = compute_client.list_vnic_attachments(compartment_id=instance_details.compartment_id, instance_id=resource_id)
        vnics = vnic_response.data
    
        for vnic in vnics:
            vnic_details = network_client.get_vnic(vnic_id=vnic.vnic_id).data
            private_ip = vnic_details.private_ip
            return private_ip
    
    """
    Post a Message to Lark.
    You can also use OCI Vault/Secret to store Lark credentials and access them here.
    """
    def make_post(post_text):
        url = "https://open.larksuite.com/open-apis/bot/v2/hook/XXXX"
        headers = {
            "Content-Type": "application/json"
        }
        req_body = {
            "msg_type": "text",
            "content": {
                "text": post_text
            }
        }
        payload = json.dumps(req_body)
        try:
            post_response=requests.post(url=url, data=payload, headers=headers)
        except Exception as e:
            logging.getLogger().error(e)
            return
    
        response_dict = json.loads(post_response.text)
        code = response_dict.get("StatusCode", -1)
    
        if code != 0:
            logging.getLogger().error("error sending post text, code: " + str(code))
        return
    
    def to_bool(a):
        return True if a == "True" else False
    
    """This is the function entry point.
    ctx will contain function variables defined in OCI console,
    data contains the payload
    """
    def handler(ctx, data: io.BytesIO = None):
        try:
            cfg = dict(ctx.Config())
            for a in cfg:
                cfg[a]=to_bool(cfg[a])
    
        except Exception as e:
            print('ERROR: Missing configuration keys', e, flush=True)
            logging.getLogger().debug(cfg)
            return 'error parsing config keys: ' + str(ex)
    
        try:
            raw_body = data.getvalue()
            body = json.loads(raw_body)
            logging.getLogger().info(body)
            parse_message(body)
        except (Exception, ValueError) as ex:
            logging.getLogger().error('error parsing json payload: ' + str(ex))
            return 'error parsing json payload: ' + str(ex)
    
  5. 使用 fn deploy 命令部署函數,以在雲端 Shell 建立函數停駐程式映像檔及關聯的相依性。您可以將映像檔推送至指定的 Docker 登錄,並將函數部署至先前建立之應用程式中的 OCI 函數。

    fn -v deploy --app <app-name>
    

    例如:

    fn -v deploy --app function-app
    

    注意:您可以檢視 func.yaml 檔案,請參閱函數碼頭影像必要詳細資訊。

  6. 部署之後,應該順利建立您的函數,如下圖所示。

    已建立函數

作業 7:將函數訂閱主題

  1. 開啟服務功能表,然後按一下開發人員服務。在應用程式整合下,按一下通知。請確定位於正確的區間中。

  2. 按一下建立主題

  3. 設定適當的名稱,然後按一下建立

  4. 建立主題之後,請從主題清單中選取該主題。

  5. 主題視窗的資源左側選取訂閱,然後按一下建立訂閱

  6. 建立訂閱側邊視窗中,選取要作為函數的協定,選取區間、應用程式以及在工作 6 中建立的函數。

  7. 按一下建立,您的函數應順利訂閱主題,如下列影像所示。

    已建立通知訂閱

作業 8:建立執行環境與通知事件規則

若要驗證此步驟中的函數,我們將會對停止執行處理之類的事件建立作業 7 中的執行處理和關聯的建立通知主題。

  1. 在主控台中,瀏覽至運算執行處理以建立運算執行處理。

  2. 按一下建立執行處理圖示,並提供必要的詳細資訊:

    • 執行處理名稱
    • 執行處理的區間
    • 選取想要的 AD
    • 選取網路 VCN 和公用子網路
    • 複製 - 貼上您的公用 ssh 金鑰
    • 按一下「建立」。
  3. 等待執行處理顯示 running ,然後使用下列命令登入執行處理。

    ssh opc@<public ip> -i <private key>
    
  4. 瀏覽至運算執行處理執行處理詳細資訊通知視窗,以建立通知事件。

  5. 按一下建立通知,然後選取 QuickStart 範本,例如執行處理狀態變更為已停止

  6. 輸入事件規則名稱,然後從任務 7 選取建立的主題,然後按一下建立通知。您的通知事件規則應該順利建立到訂閱的主題,如下圖所示。

    建立的事件規則

作業 9:驗證通知事件規則

在此步驟中,您將會停止將觸發相關通知主題的執行處理。您也可以包含電子郵件地址以查看通知有效負載。

  1. 瀏覽至建立的執行處理,然後按一下停止

  2. 執行處理停止之後,您應該透過訂閱的通知主題取得電子郵件,並且應觸發函數。

  3. 確認您已收到如下圖所示的電子郵件。

    OCI 通知主題電子郵件

  4. 前往您用來包含 Webhook URL 的標誌管道。

    Lark 通知公告

    注意:如果您根據自訂功能,從收到的電子郵件仔細看到此更新訊息,我們就會使用 OCI sdk 包含執行處理的 IP 位址。

  5. [ 選擇性 ] 您也可以根據主控台公告詳細資訊,將此通知主題與更新函數詳細資訊建立關聯。您可以依照這些文件進行深入了解

    注意:您必須修改自訂函數程式碼,以確保您讀取正確的 JSON 有效負載並進行相應修改。您可以使用從服務團隊收到的公告 JSON 有效負載範例。

    OCI 公告通知訂閱

接下來的步驟

本教學課程介紹一般使用者如何使用自訂函數讀取通知 JSON 有效負載,並使用 OCI SDK 程式庫更新該有效負載,並將訊息發布到一般協同合作工具 (例如標誌 )。您可以展開此函數來新增其他詳細資訊,例如資源標記、網路詳細資訊等等。

確認書

其他學習資源

探索 docs.oracle.com/learn 的其他實驗室,或者存取更多 Oracle Learning YouTube 頻道上的免費學習內容。此外,請瀏覽 education.oracle.com/learning-explorer 以成為 Oracle Learning 檔案總管。

如需產品文件,請造訪 Oracle Help Center