只有累積,沒有奇蹟

2021年9月2日 星期四

[NETCore] ASP.NET Core 建立排程服務 - 使用 Generic Host 搭配 Quartz.Net - Part 1

前言
最近有個需求是固定時間取得特定資料進行修改,在查詢相關資料之後決定使用 ASP.NET Core Generic Host 為出發,在搭配 .NET 中熱門的排程套件 Quartz.Net,測試完畢之後再將程式註冊為 Windows Service 服務就可滿足使用者的需求,這篇文章是整理開發時的重點流程為系列文,給有需要使用 ASP.NET Core 開發排程相關應用程式需求的朋友一些參考若有問題或是錯誤的地方歡迎各位高手給予指導
GenericHostLab SampleCode 傳送門 : http://bit.ly/2Y1mqYN
Generic Host
在過去處理 HTTP 請求時可以使用 WebHostBuilder 類別來處理,在開發 ASP.NET Core 應用程式設定及建立 WebHost 以及使用 Kestrel 服務接收請求並處理應用程式的生命週期,使用 DI 設定或配置 Logging 等重要功能,但並非所有的需求都依賴於 HTTP ,如 BackgroundService 背景執行程序或是處理 Queue 的資料等工作就不需要依賴於 HTTP 請求,從 ASP.NET Core 2.1 開始提供 Generic Host (泛型主機),提供開發者可以有新的選項來開發沒有 HTTP 請求的應用程式,可以透過 MSDN 示意圖了解

CreateHostedBuilder

如果選擇 Generic Host 開發程式,建議先了解 WebHostBuilder 背後預設配置的設定方式以及做了哪些事情,在之前 ASP.NET Core 環境佈署設定 appsettings.json 文章中有介紹過,建立新的 ASP.NTE Core 應用程式預設模板可以看到在 program.cs 中內建  CreateWebHostBuilder ,此方法代碼中設定很多預設的配置,像是指定讀取資料夾中的 appsetting.json、環境變數、logging 設定、使用 Kestrel Server 等預設內容。了解 WebHostBuilder 是如何設定的也有了基本概念,就可以發現有部分內容在 HostBuilder 是可以共用的,就可以開始著手開發 Generic Host 程式,首先先建立新的 ASP.NET Core Console 專案,並開啟 Program.cs 建立 CreateHostBuilder 運算式,代碼如下
private static IHostBuilder CreateHostBuilder() =>
    new HostBuilder()
        .ConfigureHostConfiguration(configHost =>
        {
            // setup Host configuration
            configHost.SetBasePath(Directory.GetCurrentDirectory())
                .AddJsonFile("hostsettings.json", optional: true)
                .AddEnvironmentVariables();
        })
        .ConfigureAppConfiguration((hostContext, configApp) =>
        {
            // setup App configuration
            configApp.AddJsonFile("appsettings.json")
                .AddJsonFile(
                    $"appsettings.{hostContext.HostingEnvironment.EnvironmentName}.json",
                    optional: true, reloadOnChange: true)
                .AddEnvironmentVariables();
        })
        .ConfigureServices((services =>
        {
            services.Configure<HostOptions>(option =>
            {
                option.ShutdownTimeout = TimeSpan.FromSeconds(30);
            });
        }))
        .ConfigureLogging((hostingContext, logging) => 
        {
            // Get Config from Logging section
            logging.AddConfiguration(hostingContext.Configuration.GetSection("Logging"))
                    .AddEventLog();

            if (hostingContext.HostingEnvironment.IsDevelopment())
            {
                logging.AddConsole();
            }
        }); 
在 CreateHostBuilder 中首先先建立一個 HostBuilder,命名空間為 Microsoft.Extensions.Hosting,透過 HostBuilder 來定義創建的主機後,定義以下幾件事情

  • ConfigureHostConfiguration : 設定 host 相關設定檔案
  • ConfigureAppConfiguration : 設定 application 設定檔格示為 json,檔名為 appsettings.json
  • ConfigureLogging : 設定 logging 內容設定由 config 的 Logging 區段定義,且寫到 eventLog 中
  • ConfigureServices : 設定關機餘時間延長為 30 秒 (預設為 5 秒),用意是希望收到關機指令時可以有時間處理正在的任務
  • 上述代碼要編譯成功,需要至 Nuget 安裝下列相關套件
    Install-Package Microsoft.Extensions.Hosting -Version 2.2.0
    Install-Package Microsoft.Extensions.Configuration.FileExtensions -Version 2.2.0
    Install-Package Microsoft.Extensions.Configuration.Json -Version 2.2.0
    Install-Package Microsoft.Extensions.Configuration.EnvironmentVariables -Version 2.2.0
    Install-Package Microsoft.Extensions.Configuration.CommandLine -Version 2.2.0
    Install-Package Microsoft.Extensions.Logging.Console -Version 2.2.0
    Install-Package Microsoft.Extensions.Logging.Debug -Version 2.2.0
    Install-Package Microsoft.Extensions.Logging.EventLog
    如果對於 WebHostBuilder 原理想了解更多,可以參考 andrewlock 文章 :  HostBuilder v.s WebHostBuilder 

    TimeHotedService
    下一步是建立 TimeHostedService 類別並實作 IHostedSercice 介面,IHostedService interface 中提供 StartAsync 和 StopAsync 方法,在 MSDN 提到 Start 是在 IApplicationLifetime.ApplicationStarted 觸發之後會接續執行,反之 Stop 是主機停止停止時會觸發,source code 如下
    namespace Microsoft.Extensions.Hosting
    {
        //
        // Summary:
        //     Defines methods for objects that are managed by the host.
        public interface IHostedService
        {
            //
            // Summary:
            // Triggered when the application host is ready to start the service.
            Task StartAsync(CancellationToken cancellationToken);
            //
            // Summary:
            // Triggered when the application host is performing a graceful shutdown.
            Task StopAsync(CancellationToken cancellationToken);
        }
    } 
    起手式我們可以先建立簡單的 HostedService 來驗證是否正常,如果正常了在把 Service 替換為我們想要的 Quartz.Net 實作內容,在這邊建立 TimeHostedService 類別主要功能是每秒 console 中顯示現在的時間,代碼如下
    namespace GenericHostLab.Service
    {
        internal class TimedHostedService : IHostedService, IDisposable
        {
            private readonly ILogger _logger;
            private Timer _timer;
    
            public TimedHostedService(ILogger<TimedHostedService> logger)
            {
                _logger = logger;
            }
    
            public Task StartAsync(CancellationToken cancellationToken)
            {
                _logger.LogInformation("Timed Background Service is starting.");
    
                _timer = new Timer(DoWork, null, TimeSpan.Zero, TimeSpan.FromSeconds(1));
    
                return Task.CompletedTask;
            }
    
            private void DoWork(object state)
            {
                _logger.LogInformation($"[{DateTime.Now:yyyy-MM-dd hh:mm:ss}] Timed Background Service is working.");
            }
    
            public Task StopAsync(CancellationToken cancellationToken)
            {
                _logger.LogInformation("Timed Background Service is stopping.");
    
                _timer?.Change(Timeout.Infinite, 0);
    
                return Task.CompletedTask;
            }
    
            public void Dispose()
            {
                _timer?.Dispose();
            }
        }
    }
    將 TimedHostedService 加入到 Service 中
    .ConfigureServices((hostContext, services) =>
    {
        // ...
        services.AddHostedService<TimedHostedService>();
    }
    在 main 方法中直接使用  RunConsoleAync 
    static async Task Main(string[] args)
    {
        try
        {
            var builder = CreateHostBuilder();
    
            await builder.RunConsoleAsync();        
        }
        catch (Exception e)
        {
            Console.WriteLine(e);
            throw;
        }
    }
    這邊需要注意的是由於 async 是 C# 7.1 開始支援的功能,因此如果專案預設編譯需要設定為使用 C# 7.1 來進行編譯,否則上面代碼可能會造成編譯錯誤,錯誤訊息為 : Feature 'default literal' is not available in C# 7.0. Please use language version 7.1 or greater.,解決方法只要去設定專案編譯 C# 版本即可,設定方式為 專案點選右鍵 > property > Advance 
    完成了基本功能設定,按下執行可以看到 Console 跑出來的結果如下
    這一篇介紹 Generic Host 基本設定,其中包含應用程式起來時候的配置,為了避免一篇文章太冗長看了想睡覺,下一篇再來介紹剩下的部分也就是 Quartz.Net 的方式,也可以趁這機會稍微消化一下,看是否有不懂的地方也歡迎隨時提出來,謝謝

    參考
    Creating a Quartz.NET hosted service with ASP.NET Core
    .NET 泛型主機

    2021年8月1日 星期日

    [conference] COSCUP 2021 | 初試 Casbin - 快速搭建符合 99% 產品都需要的高彈性可維護之授權控制系統

    分享心得
    在過去都是在技術研討會擔任觀眾的我,某天在跟技術大神 Ant 大聊天時不小心被推坑參加 COSCUP 開源人年會上分享 Casbin 這套 OpenSource 的授權框架,自己抱著試試看的心情沒想到投稿的議程有上,研討會進行方式今年也因為疫情的關係從線下活動改為線上的方式,但對於第一次參加公開分享擔任講者的我來說是沒有區別的(一樣緊張),花了不少時間準備這議題也請 Ant 與 Justin review 議題內容,其中也使用 Casbin.NET 來 Demo 讓大家更容易理解,另外還花了很多時間在研究影片字幕要如何加上,做完覺得線上課程的講師也是非常厲害的阿 !
    希望參加此議程的朋友們可以在有所收穫,也非常感謝 COSCUP 主辦當為給我這機會可以在台灣 最大的 Open Source 年會上進行分享,以下是分享的內容與影片連結,若有任何問題歡迎提出來一起討論。


    議程介紹
    主題 : 初試 Casbin - 快速搭建符合 99% 產品都需要的高彈性可維護之授權控制系統
    相信開發人員都設計過權限功能,在不同程式語言也都有不同的框架與設定權限方法
    在服務切割越來越微細的世代,是不是有一種方式可以在設定權限策略(Policy)上更簡單呢 ?
    Casbin 是一個開源且功能強大的權限控制庫,做到一種跨程式語言的標準 (各程式語言通用統一資源),支援 PHP、JAVA、GO等 Node.js 等常見的程式語言。也將複雜的 Authentication 與 Authorization 做簡化,將常用的授權方式 ACL, RBAC, ABAC 進行模組化。
    在本議程會與大家分享下面幾個議題
    • Casbin 是如何做到跨程式語言的標準呢 ?
    • 一些常見的授權方式在 Casbin 是怎麼做到 & 設定的呢 ?
    • Casbin 的優點與缺點是甚麼呢 ?
    

    主辦單位 : COSCUP 開源人年會
    COSCUP 是由台灣開放原始碼社群聯合推動的年度研討會,起源於 2006年,是台灣自由軟體運動 (FOSSM) 重要的推動者之一。活動包括有講座、攤位、社團同樂會等,除了邀請國際的重量級演講者之外,台灣本土的自由軟體推動者也經常在此發表演說,會議的發起人、工作人員與講者都是志願參與的志工,所有議程都是免費參加。 此外,今年 COSCUP 很榮幸的邀請到 RubyConf Taiwan 合作舉辦聯合研討會,並且如往常一樣,徵求各式各樣不同的 Open Source 相關稿件,歡迎有興趣的你/妳共襄盛舉。 開發者 (Coders)、使用者 (Users) 和推廣者 (Promoters) 是讓自由及開放原始碼軟體發光發熱的三大支柱,這個研討會就是專為這三種人舉辦的:你可以是 A 軟體的開發者、B 軟體的推廣者、C 軟體的使用者,不論你是已經踏入自由及開放原始碼軟體領域,還是一直站在門口不知如何入門,歡迎你來參加 COSCUP — Conference for Open Source Coders, Users and Promoters!

    議程表 : 連結
    共筆 : https://hackmd.io/@coscup/rymNETD0O/%2F%40coscup%2Fry-7ETDAO


    影片連結


    2021年7月7日 星期三

    [Tool] END-TO-END Test 測試工具 - Playwright

    前言
    過去提到 Web 自動化測試可能第一個念頭會透過 Selenium 來實現 ,今天要介紹的是一套新的 Open Source 自動化測試工具 Playwright,他是基於 Javascript 的跨瀏覽器 end to end 測試工具,目前屬於微軟眾多的 Open Source 專案之一,今天這篇文章就來推坑這款好用的工具,若有問題歡迎提出來一起討論。

    介紹
    Playwright 是一種 opensource 的自動化測試工具,使用 Node.js 所開發,不僅支援當今常用到的三種瀏覽器 Chrome、Firefox 以及 WebKit,還可透過簡單的設定測試在不同設備上的瀏覽器以及自定義座標與地理位置(Geo),此外,Playwright API 支援的語言有 Javscript、TypeScript、Python 及 C#,文章提到 Playwright 使用 headless browser 以及 Devops Protocol 來執行,因此速度比 Selenium 快且穩定性較高,在使用前可以先了解一下設計的初衷,在 Playwright Github 文件的 README.md 有提到下列說明
    We are the same team that originally built Puppeteer at Google, but has since then moved on. Puppeteer proved that there is a lot of interest in the new generation of ever-green, capable and reliable automation drivers. With Playwright, we'd like to take it one step further and offer the same functionality for **all** the popular rendering engines. We'd like to see Playwright vendor-neutral and shared governed.
    備註 : Puppeteer 是 Playwright 的前身,其 API 與核心概念都很相似。

    安裝 Playwright-cli
    由於小弟手邊沒有 Mac 筆電,因此使用的是以 Windows OS 為主,如果要在 Windows 下跑 Playwright 的話需要先安裝 Node.js 及 npm,可以到 Node.js 官方網站下載 Windows 安裝應用程式,如下圖所示

    安裝完畢之後,可以透過命令提示字元執行以下指令查詢是否有安裝成功
    node -vC:\Users\username>node -v
    v12.18.4
    
    C:\Users\username>npm -v
    6.14.6
    
    看到兩個指令均有回覆相關資訊,及代表安裝環境成功 !
    接著使用 npm 或是 yarn 在 Node.js 安裝 PlayWright (PlayWright需要 Node.js 10 或更高的版本)
    $ npx playwright-cli --help
    
    # To save as a dependency
    $ npm install -D playwright-cli
    

    使用方式
    Code Page
    輸入下列指令即可透過 Playwright-cli 開啟新的頁面,舉例來說我想使用 Chrome 瀏覽器來開啟小廢廢的部落格
    npx playwright-cli open marcus116.blogspot.com
    
    可以依據需求來調整要測試的瀏覽器,如果想換 webkit 瀏覽器則調整參數 open 改為 wk 即可 備註 : 實際在 windows 執行有點頓,有機會在 Mac 測測看再回報

    指定 Device
    如果希望測試時指定 Device 的型號,則可以透過 cli 的 --device 參數來指定想要測試的 device 型號 playwright.devices,舉例來說指定設備用 iPhone 開啟 wiki 網頁
    npx playwright-cli --device="iPhone 8" open wikipedia.org
    
    呈現畫面如下
    模擬地理位置
    可以指定地理位置(Geolocation),舉例來說我希望開啟瀏覽器時定位在台北車站附近
    npx playwright-cli --geolocation="25.0448717,121.5209451" open maps.google.com
    
    呈現畫面如下
    另外還支援截圖與產生 PDF 檔案的功能,詳細可以參考 playwright-cli Github 文件說明。

    在 C# 使用
    起手式第一步是到 nuget 下載 PlaywrighySharp 套件,目前最新的版本為 0.142
    使用 Visual Studio 2019 建立 NUnit 測試專案,我們使用 Chorome 開啟 google.com 並在輸入框輸入 hello world,並加上一些條件像是開啟畫面是 1024 * 1024,headless 設定為 false,按下在下搜尋按鈕,依據此邏輯接著在 UnitTest1 輸入下列代碼
    public class Tests
    {
        [SetUp]
        public async Task Setup()
        {
        }
    
        public async Task Browser()
        {
            var playwright = await Playwright.CreateAsync();
            var browser = await playwright.Chromium.LaunchAsync(headless: false);
    
            return browser;
        }
    
        public async Task Page()
        {
            var browser = await Browser();
            var page = await browser.NewPageAsync();
    
            return page;
        }
    
        [Test]
        public async Task Search_Using_Chrome()
        {
            var page = await Page();
            await page.GoToAsync("https://www.google.com");
    
            await page.SetViewportSizeAsync(1024, 1024);
    
            // textbox : hello world
            await page.TypeAsync("input[name='q']", "hello world");
    
            // Click Button
            await page.ClickAsync("input[name='btnK']");
            
            // Wait 3 second
            await page.WaitForTimeoutAsync(3000);
        }
    }
    
    然後在測試總管點選測試,即可看到測試的結果如下 結果正常,大功告成打完收工 !!!

    感想
    以上針對新的測試工具 Playwright 套件做一些基本的介紹,另外此套工作可以也在 Docker 環境跑 Playwright 腳本,若有興趣可以參考 Running Playwright in Docker,雖然接觸此工具的時間不長但對於前景的發展感覺是很不錯的,日後有機會可以做更深獲是進一步的研究跟分享,以上如果有不清楚的地方歡迎一起討論,hope it helps !

    參考
    Playwright
    WHY DO WE NEED END-TO-END TESTS?
    Playwright (vs. Puppeteer): Cross-Browser Testing done right
    What is the Microsoft Playwright Automation Tool Guide

    2021年7月1日 星期四

    [Azure] 打包 ASP.NET Core 應用程式到 Docker Hub 並發佈到 Azure

    前言
    這幾年隨著容器化技術逐漸成熟,在技術研討會與社群上可以聽到越來越多公司架構朝容器與微服務邁進,微軟也很佛心的提供 .NET 微服務 : 容器化應用程式架構指南 電子書,作為有興趣往微服務的.NET 開發人員參考。除了提供電子書之外在 Azure 提供 Web App for Container 服務,可以輕鬆的將封裝好的 Docker image 檔案部署到 Azure 上,這篇文章是參考 Microsoft Azure 官網影片的筆記,介紹如何透過 Visual Studio 2019 將 ASP.NET Core 應用程式封裝成 Linux image 檔案 push 到 Docker Hub,再透過 Web App for Container 服務部署至 Azure 雲端上使用若有問題或是錯誤的地方歡迎各方高手大大一起討論或給予指導

    前置作業
    一開始有提到要將 ASP.NET Core 應用程式包成 Docker Image 檔案並部署到 Azure,在這之中分別會用到 Docker for Windows 工具與 Visual Studio Azure development,因此在開始之前必須先確認這兩項是否有安裝成功,才可以順利進行後續的步驟

    安裝 Docker For Windows
    公司筆電使用的是 Windows 作業系統,在 Windows 上要使用 Docker 必須安裝 Docker Desktop for Windows 應用程式,安裝完畢之後還需要開啟 Windows 中的 Container & Hyper-V,安裝方式與細節可以參考小弟之前寫的 Docker for windows 初體驗 文章介紹,安裝傳送門 : Docker Desktop for Windows

    安裝 Visual Studio Component - Azure development 
    我們會將應用程式封裝成 Docker Image,接著將打包好的 image 檔案 publish 到 Azure 雲端上,這些流程都需要工具進行輔助才可以達到,在 Visual Studio 中有提供開發雲端應用程式的  Azure SDK ,與建立 Docker 容器化的工具,但這些選項在安裝 Visual Studio 時預設是不會安裝的,因此我們需要透過  Visual Studio Installer  進行安裝所需工具,安裝步驟如下
    Step 1 : 開始 > 輸入Visual Studio Installer > 選擇 "修改
    Step 2 : Workload 工作負載 > Azure 開發 選項打勾 > 確定後按右下角修改按鈕
    接著就會進行 Azure SDK 安裝,如果不確定之前是否有安裝過 Azure SDK,可以輸入下列指令確認
    Get-Module -ListAvailable | Where-Object -Property Name -Like "*Azure*"
    備註 : Azure Development 正確安裝元件清單可以參考 MSDN 介紹 : Visual Studio Community component directory - Azure Development

    建立應用程式 
    第一個步驟是建立需要上傳的範例應用程式,開啟 Visual Studio 2019 新增 DockerTest 專案,並選擇 ASP.NET Core MVC 模板應用程式
    為了方便驗證應用程式,我在 ASP.NET Core 應用程式開啟首頁 index.cshtml 中 Welcome 改為 Welcome Marcus
    <div class="text-center">
        <h1 class="display-4">Welcome Marcus</h1>
        <p>Learn about <a href="https://docs.microsoft.com/aspnet/core">building Web apps with ASP.NET Core</a>.</p>
    </div>
    接著要新增  dockerfile  檔案,Dockerfile 是一個文字檔案,開發者可以將要 build image 所有的命令指令放在 dockerfile 檔案中,最後在透過 Docker Build 指令來建立 image 檔案,在 Visual Studio 中可以透過下列步驟新增專案所屬的 Docker File
    Add Dockerfile : 專案點選右鍵 > Add > Docker Support  
    在建立 Docker Image 前必須先定義應用程式要在哪個環境下執行,有分為 Linux 以及 Windows 兩種也就是要執行環境的OS,建立前會跳出視窗詢問要建立哪一種 image,這裡我希望在 Linux 上執行 
    建立完畢後會在專案底下建立檔名為 dockerfile 檔案,可以打開建立好的 dockerfile 如果有要添加可以在其中做調整,預設的 dockerfile 內容如下 (如果上一步 Target OS 選擇 Windows 的話,OS就會看到 nanoserver-1903 )是 windows
    FROM mcr.microsoft.com/dotnet/core/aspnet:2.2-stretch-slim AS base
    WORKDIR /app
    EXPOSE 80
    EXPOSE 443
    
    FROM mcr.microsoft.com/dotnet/core/sdk:2.2-stretch AS build
    WORKDIR /src
    COPY ["DockerTest/DockerTest.csproj", "DockerTest/"]
    RUN dotnet restore "DockerTest/DockerTest.csproj"
    COPY . .
    WORKDIR "/src/DockerTest"
    RUN dotnet build "DockerTest.csproj" -c Release -o /app
    
    FROM build AS publish
    RUN dotnet publish "DockerTest.csproj" -c Release -o /app
    
    FROM base AS final
    WORKDIR /app
    COPY --from=publish /app .
    ENTRYPOINT ["dotnet", "DockerTest.dll"]

    Docker Hub
    新增完要 Demo 的 ASP.NET Core 應用程式與建立好打包 image 的指令 (Dockerfile),下一步就是要透過 Visual Studio 提供的 Publish 功能將應用程式包成 image 並發佈到指定的 Docker Hub 上,步驟如下
    Step 1 : 專案按右鍵 > 選擇 Publish  
    Step 2 : 選擇 Container Registry > Docker Hub 打勾 
    Step 3 : 會發佈到個人的 Docker repositoty,因此會要求你輸入 Docker 使用者名稱,密碼可選擇不要輸入
    Step 4 : 按下存檔之後會在專案 Properties 底下新增   PublishProifles  資料夾與設定檔,將剛剛畫面所設定的資訊都透過 XML 方式存放在該資料夾中
    Step 5 : 發布設定檔所對應到的資訊會顯示在發布畫面上,發佈到 Docker Hub 預設會加上  tag : latest ,如果公司或團隊有不同一樣的 tag 規範時在此步驟可以修改,沒問題就可以按下 Publish 按鈕
    Step 6 : 進行 Publish 時候會在 Visual Studio Output 視窗顯示發布時的資訊與內容,內容描述整個 publish 到 Docker Hub 的過程,包含專案的建置、Docker Build 執行 Dockerfile 中的指令以及建置 Docker Image 成功之後放到 Docker Hub,其中比較值得介紹的是建置 Docker Build 的過程,Docker Image 是由很多不同的 Layer 所組成,執行 Docker Build 建置的過程中會依據所定義的內容 (指令) 建立所需要的 layer,每一層 Layer 都有屬於自己的 id,整個建置完成才算是完整的 Docker Image,示意圖如下
    圖片來源 : Docker Images and How to work with them 

    如果是第一次執行 Docker Build 會執行較久的時間,是因為之前沒有下載過相關的映像檔,舉例來說如果建立 Dockerfile 時指定 Windows 時,會需要下載 windows 的 nanoserver 1809 映像檔到本機環境中,如果下一次在重新建立時會發現建置 Docker Image 過程會抓取 cache 內容,透過此機制不用每次都重新下載會加速建置 Docker Image 的速度。透過以上說明,我們再回到主題來觀察 DockerTest 範例專案中在 publish 中 output 的內容就清楚許多
    Step 1/19 : FROM mcr.microsoft.com/dotnet/core/aspnet:2.2-stretch-slim AS base
     ---> 3ee0429b27ad
    Step 2/19 : WORKDIR /app
     ---> Using cache
     ---> 129068167155
    Step 3/19 : EXPOSE 80
     ---> Using cache
     ---> 00e73d24a9b3
    ...省略
    Step 19/19 : LABEL com.microsoft.visual-studio.project-name=DockerTest
     ---> Using cache
     ---> ab2fcad3d592
     ---> 6a61a9666c82
    Successfully built 6a61a9666c82
    Successfully tagged dockertest:latest
    
    Publish 完成之後開啟所設定的 Docker Hub 網址,即可以看到剛剛發布的 DockerTest 已成功

    Web App for Container
    接下來是透過 Azure 的 Web App for Container 服務,將稍早上傳到 Docker hub 的 image 印象檔部署到 Azure 中的應用程式,首先在上方的 Search 區塊輸入  Web App for Container  關鍵字,點選該服務
    新增一個新的 Web App for Container 時需要輸入以下資訊
  • 應用程式名稱 : 這裡輸入範例的專案名稱 dockerlabtest
  • Container 需要執行的 OS : 建立 Docker Image 所選擇的執行環境
  • 設定容器 : 稍早使用 Visual Studio 上傳到 docker hub,因此在右邊區塊選擇 Docker Hub 頁籤,下方黃色圈起的區塊輸入 Docker Image 的位置,如果忘記位置可以參考 Docker Hub Repo 頁面右下方  docker pull username/dockertest ,輸入完畢之後按下套用。
  • 以上資料都輸入完畢後按下建立按鈕,Azure 就會開始進行建立應用程的動作,並在畫面上會顯示部署時的內容資訊,如果想了解部署時的細節內容也可以透過左邊區塊的按鈕下載
    將 Docker Image 部署至 Azure 之後,可透過下列標註黃色區塊開啟剛剛建立的網站
    點選之後開啟網頁可以看到一開始修改的文字 Welcome Marcus 顯示成功 !!!!
    當然,Azure 也貼心的提供監控應用程式的 dashboard,可以觀看應用程式的錯誤及 Application network in/out 相關即時資訊,方便開發者或是運維團隊監控應用程式的服務是否正常
    成功將 .NET Core 應用程式打包成 Docker Image 並部署至 Azure 上,大功告成,打完收工 !!!


    感想
    隔了 7 年的時間在重新使用 Azure 服務,初步覺得除了介面操作上比之前更加好用之外,在部署應用程式之後的監控服務服務更加完善,一開始也有提到這篇文章是照著 Microsoft Azure 官網影片 的筆記,五分鐘的影片看似很簡單但實際操作之後也隱藏了一些細節,還有影片介紹的是部署至 Windows 我這裡改介紹 Linux OS,花了一點時間了解並實作出來之後,決定將過程分享此文章(我承認標題真的很難下 XDDD),並針對自己覺得重要的部分加上說明,如果對於 Azure 提供的 Web App for Container 服務有興趣的朋友歡迎參考與一起討論,也希望這篇介紹可以有幫助到有需要的朋友,謝謝

    參考
    How to deploy ASP.NET application to Docker Hub and Azure | Azure Tips and Tricks

    Copyright © m@rcus 學習筆記 | Powered by Blogger

    Design by Anders Noren | Blogger Theme by NewBloggerThemes.com