Coursera 笔记

Module 05 · Final Project and Final Exam期末项目与期末考试

Final Project - Part B & C: Modernize Application and DevOps期末项目 - B 和 C 部分:税务计算器

预计所需时间: 45分钟

在这个云原生、DevOps、敏捷和NoSQL的最终项目B和C部分中,你将致力于税务计算器,并利用你在本课程中学到的技能对其进行增强。

目标

  1. 将应用程序容器化
  2. 作为管道的一部分运行单元测试
  3. 当所有测试通过时部署应用程序
  4. 替换硬编码的配置(税率区间)
  5. 当所有测试通过时再次部署应用程序

在 Cloud IDE 中处理文件

如果您是 Cloud IDE 的新用户,本节将向您展示如何创建和编辑文件,这些文件是您在 Cloud IDE 项目的一部分。

要查看 Cloud IDE 中的文件和目录,请单击此文件图标以显示它。

如果您已经克隆了(使用 git clone 命令)样板/起始代码,则其外观如下:

否则,空白项目看起来是这样的:

创建新文件

您可以右键单击并选择新建文件选项以在项目中创建文件。

您也可以选择 文件 -> 新建文件 来完成相同操作。

然后,它会提示您输入新文件的名称。在下面的示例中,我们正在创建 sample.html。

单击目录结构中的文件名 sample.html 将在右侧窗格中打开该文件。您可以创建各种类型的文件;例如,JavaScript 文件可以命名为 FILE_NAME.js。

在示例中,我们只是粘贴了一些基本的 HTML 代码,然后保存了文件。

并通过以下方式保存它:

  • 使用菜单
  • 在 Mac 上按 command + S 或在 Windows 上按 CTRL + S
  • 或者它也可以自动保存

验证环境和命令行工具

  1. 通过编辑器菜单打开终端窗口:Terminal > New Terminal。

注意:如果终端已经打开,请跳过此步骤。

  1. 验证 docker CLI 是否已安装。
docker --version

您应该看到以下输出,尽管版本可能不同:
3. 验证 ibmcloud CLI 是否已安装。

ibmcloud version

您应该看到以下输出,尽管版本可能不同:

启动代码引擎

  1. 在您的实验室环境菜单中,点击 Cloud 下拉菜单并选择 Code Engine。代码引擎设置面板将出现。点击 Create Project 开始。
  2. 代码引擎环境准备需要一些时间。您将在设置面板中看到进度状态。
  3. 一旦代码引擎设置完成,您会看到它处于活动状态。点击 Code Engine CLI 在终端中启动预配置的 CLI,如下所示。
  4. 您会注意到预配置的 CLI 启动并且主目录设置为当前目录。作为预配置的一部分,项目已设置,Kubeconfig 也已配置。详细信息如下所示在终端中显示。

另一种到达它的方法是点击以下操作:

创建代码引擎项目 in IDE

设置 : 创建应用程序

  1. 通过编辑器中的菜单打开终端窗口:终端 > 新终端。
  2. 如果您当前不在项目文件夹中,请复制并粘贴以下代码以切换到您的项目文件夹。
cd /home/project
  1. 运行以下命令以克隆包含此项目所需启动代码的 Git 仓库,如果该 Git 仓库尚不存在。
[ ! -d 'tax_calculator' ] && git clone https://github.com/yahya-skillup/tax_calculator.git
  1. 切换到目录 tax_calculator 开始进行实验。
cd tax_calculator
  1. 列出此目录的内容以查看本实验的工件。
ls
  1. 在终端运行以下命令以托管您的网页。
python3 -m http.server
  1. 要在浏览器中测试您的应用程序,请先运行应用程序。
    Launch Application
  2. 它看起来像这样:
  3. 在您的终端中,按 CTRL+C 停止您的网络服务器。

任务 3:手动单元测试

单元测试

单元测试是一种软件测试,旨在对软件应用程序的各个组件或单元进行隔离测试,以确保它们正确运行。单元测试的目标是验证每个代码单元是否按预期执行并满足其指定的要求。

Jasmine

Jasmine 是一个流行的 JavaScript 测试框架,提供了一种基于行为驱动开发(BDD)风格的语法,用于编写单元测试。

步骤

npm install
npx jasmine

应该产生如下输出,显示所有 7 个单元测试均已通过:

Randomized with seed 78367
Started
.......
7 specs, 0 failures
Finished in 0.013 seconds
Randomized with seed 78367 (jasmine --random=true --seed=78367)

评估:截取输出的屏幕,并将屏幕截图保存为 01-jasmine-tests-passing.png。

任务 4:将应用程序容器化

让我们开始现代化我们的应用程序。朝这个方向迈出的第一步是使用 Docker 将其容器化。

什么是 Docker

Docker 是一个开源平台和工具集,允许您通过容器化来自动化应用程序的部署、扩展和管理。容器是轻量级、隔离和可移植的环境,打包了应用程序及其依赖项,使其能够在不同的计算环境中一致运行。

创建 Dockerfile

你的任务:

  1. 定义 nginx 作为父镜像。
  2. 将每个文件单独复制到 /usr/share/nginx/html/。

Open Dockerfile in IDE

点击这里获取提示

FROM 是您需要使用的关键字,而 nginx 是镜像。
COPY filename.ext /usr/share/nginx/html/filename.ext 可以帮助您将文件复制到容器中。

点击这里查看解决方案

FROM nginx
COPY favicon.ico /usr/share/nginx/html/favicon.ico
COPY index.html /usr/share/nginx/html/index.html
COPY script.js /usr/share/nginx/html/script.js
COPY style.css /usr/share/nginx/html/style.css
COPY taxCalculator.js /usr/share/nginx/html/taxCalculator.js

评估:截取 Dockerfile 的屏幕截图,并将屏幕截图保存为 02-dockerfile.png。

构建 Docker 镜像

现在我们已经创建了 Dockerfile,让我们构建自定义镜像。您将把镜像命名为 tax-calculator。

点击这里获取提示

docker build -t IMAGE DIRECTORY

点击这里获取解决方案

docker build -t tax-calculator .
Sending build context to Docker daemon 4.097MB
Step 1/6 : FROM nginx
latest: Pulling from library/nginx
5b5fe70539cd: Pull complete
441a1b465367: Pull complete
3b9543f2b500: Pull complete
ca89ed5461a9: Pull complete
b0e1283145af: Pull complete
4b98867cde79: Pull complete
4a85ce26214d: Pull complete
Digest: sha256:593dac25b7733ffb7afe1a72649a43e574778bf025ad60514ef40f6b5d606247
Status: Downloaded newer image for nginx:latest
---> eb4a57159180
Step 2/6 : COPY favicon.ico /usr/share/nginx/html/favicon.ico
---> b2c02c67552a
Step 3/6 : COPY index.html /usr/share/nginx/html/index.html
---> dd3d2863eed4
Step 4/6 : COPY script.js /usr/share/nginx/html/script.js
---> b860b38bb42b
Step 5/6 : COPY style.css /usr/share/nginx/html/style.css
---> 886c1779669c
Step 6/6 : COPY taxCalculator.js /usr/share/nginx/html/taxCalculator.js
---> bb2259671dd6
Successfully built bb2259671dd6
Successfully tagged tax-calculator:latest

评估:截取输出的屏幕并将屏幕捕获保存为 03-docker-build-output.png。

列出 Docker 镜像并验证您是否能看到 tax-calculator。

docker images

部署 Docker 镜像

一旦构建了容器,就在 8080 端口上部署容器。

点击这里获取提示

docker run FLAGS PORT_MAPPING IMAGE

  • -i 是 –interactive 的缩写。即使未连接,也保持 STDIN 打开。
  • -t 是 –tty 的缩写。分配一个伪终端,将您的终端与容器连接。
  • -p –port。8080:80 将 Docker 的 80 端口映射到您云 IDE 实例的 8080 端口。

点击这里查看解决方案

docker run -it -d -p 8080:80 tax-calculator

在浏览器中测试应用程序。

Launch Application

评估:截取输出的屏幕截图,并将其保存为 04-docker-image-browser.png。

最后,清理正在运行的容器。

docker ps -aq | xargs docker stop | xargs docker rm

任务 5:在 IBM Cloud 上手动部署

作为这个学习平台的一部分,您将获得 IBM Cloud 上的基本基础设施。您无需进行外部注册,所有设置都已为您完成。

创建 Code Engine 项目 in IDE

构建和标记 Docker 镜像

Docker build 命令从 Dockerfile 构建 Docker 镜像。

点击这里获取提示

docker build DIRECTORY FLAGS us.icr.io/${SN_ICR_NAMESPACE}/tax-calculator

点击这里获取解决方案

cd /home/project/tax_calculator
docker build . -t us.icr.io/${SN_ICR_NAMESPACE}/tax-calculator

将镜像推送到 IBM Cloud

要将镜像上传到注册中心,请使用 docker push。

让我们将镜像推送到 IBM Cloud。

点击此处查看解决方案

docker push us.icr.io/${SN_ICR_NAMESPACE}/tax-calculator
Using default tag: latest
The push refers to repository [us.icr.io/sn-labs-muhammady/tax-calculator]
89f563e661f3: Pushed
cc5d73bc425a: Pushed
65e19533a8e4: Pushed
6eece4e1cc01: Pushed
39f800da4b18: Pushed
9e96226c58e7: Pushed
12a568acc014: Pushed
7757099e19d2:  Pushed
bf8b62fb2f13: Pushed
4ca29ffc4a01: Pushed
a83110139647 :  Pushed
ac4d164fef90: Pushed
latest: digest: sha256:eafeeb9f52852df0d229962f4dbfdceb5dddf1e3b5c8455782ab18acf466fca9 size: 2815

评估:截取输出的屏幕截图,并将其保存为 05-docker-icr-push.png。

将镜像部署到 IBM Cloud

在 IBM Cloud Code Engine 上部署镜像。

ibmcloud ce application create --name tax-calculator --image us.icr.io/${SN_ICR_NAMESPACE}/tax-calculator --registry-secret icr-secret --port 80

检查状态

ibmcloud ce application get --name tax-calculator

评估:截取输出的屏幕并将屏幕截图保存为 06-deployed-on-cloud.png。

从输出中获取云 URL,格式类似于以下内容:https://tax-calculator.somerandomalphanumeric.us-south.codeengine.appdomain.cloud

任务 6:设置管道

您现在将创建管道,以执行作为持续部署一部分的手动操作。

打开一个新的终端并转到 /home/project。

cd /home/project

克隆为 Tekton 管道提供的样板 yaml 文件。

[ ! -d 'tc-pipeline' ] && git clone https://github.com/yahya-skillup/tc-pipeline.git

切换到目录 tc-pipeline 开始处理管道。

cd tc-pipeline

您还可以在项目结构中查看您的代码。

任务 7:为管道使用添加任务

Open tasks.yaml in IDE

创建 npminstall 任务

添加一个名为 npminstall 的新任务,使用镜像 node:20-buster-slim,运行以下命令:

set -e
echo "***** Environment *****"
npm --version
pwd
echo "***** Cleaning npm cache *****"
npm cache clean --force
echo "***** Running npm install *****"
npm install

点击这里获取提示

apiVersion: tekton.dev/v1beta1
kind: Task
metadata:
  name: npm
spec:
  workspaces:
    - name: source
  steps:
    - name: TASK_NAME
      image: IMAGE_NAME
      workingDir: $(workspaces.source.path)
      script: |
        #!/bin/bash
        COMMANDS

点击这里查看解决方案

apiVersion: tekton.dev/v1beta1
kind: Task
metadata:
  name: npm
spec:
  workspaces:
    - name: source
  steps:
    - name: npminstall
      image: node:20-buster-slim
      workingDir: $(workspaces.source.path)
      script: |
        #!/bin/bash
        set -e
        echo "***** Environment *****"
        npm --version
        pwd
        echo "***** Cleaning npm cache *****"
        npm cache clean --force
        echo "***** Running npm install *****"
        npm install
---

创建 Jasmine 任务

添加一个名为 jasmine 的新任务,使用镜像 node:20-buster-slim,运行以下命令:

set -e
echo "***** Running jasminetests *****"
npx jasmine

点击这里获取提示

apiVersion: tekton.dev/v1beta1
kind: Task
metadata:
  name: npm
spec:
  workspaces:
    - name: source
  steps:
    - name: TASK_NAME
      image: IMAGE_NAME
      workingDir: $(workspaces.source.path)
      script: |
        #!/bin/bash
        COMMANDS

点击这里查看解决方案

apiVersion: tekton.dev/v1beta1
kind: Task
metadata:
  name: jasmine
spec:
  workspaces:
    - name: source
  steps:
    - name: jasminetests
      image: node:20-buster-slim
      workingDir: $(workspaces.source.path)
      script: |
        #!/bin/bash
        set -e
        echo "***** Running jasminetests *****"
        npx jasmine
---

评估:截取 tasks.yaml 的屏幕并将其保存为 07-tasks-yaml.png。

创建一个秘密

工作区允许任务声明在运行时需要由 TaskRuns 提供的文件系统部分。TaskRun 可以通过多种方式使这些文件系统部分可用:

  • 使用只读的 ConfigMap 或 Secret
  • 与其他任务共享的现有 PersistentVolumeClaim
  • 从提供的 VolumeClaimTemplate 创建 PersistentVolumeClaim
  • 或者只是一个在 TaskRun 完成时被丢弃的 emptyDir

您需要创建上述提到的秘密的第一步。

秘密:秘密是一个包含少量敏感数据的对象,例如密码、令牌或密钥。

您需要以下秘密才能部署到 IBM 容器注册表。

kubectl create secret docker-registry docker-reg-creds \
  --docker-server=us.icr.io \
  --docker-username=iamapikey \
  --docker-password=$IBMCLOUD_API_KEY

任务 8:创建管道

由于我们的 DevOps 过程通过管道进行了简化,用于测试、打包和部署,我们只需触发它以进行部署,只要满足所有标准,就可以完全放心它会正常工作。

与任务的模板 yaml 类似,您将获得 pipeline.yaml。

调用 npminstall 任务

添加一个名为 npminstall 的新任务,其中 taskRef / name 为 npm,在 clone 之后运行:

点击这里获取提示

- name: NAME
  workspaces:
    - name: source
      workspace: pipeline-workspace
  taskRef:
    name: TASKREF-NAME
  runAfter:
    - RUNNING-AFTER

点击这里获取解决方案

- name: npminstall
  workspaces:
    - name: source
      workspace: pipeline-workspace
  taskRef:
    name: npm
  runAfter:
    - clone

调用 jasmine 任务

添加一个名为 tests 的新任务,其中 taskRef / name 为 jasmine,在 npminstall 之后运行:

点击这里获取提示

- name: NAME
  workspaces:
    - name: source
      workspace: pipeline-workspace
  taskRef:
    name: TASKREF-NAME
  runAfter:
    - RUNNING-AFTER

点击这里查看解决方案

- name: tests
  workspaces:
    - name: source
      workspace: pipeline-workspace
  taskRef:
    name: jasmine
  runAfter:
    - npminstall

调用 buildah 任务

添加一个名为 build 的新任务,其中 taskRef / name 为 buildah,类型为 ClusterTask,将 IMAGE 参数的值设置为 $(params.build-image),在 tests 之后运行。

此外,您还需要添加 dockerconfig-ws,而不仅仅是 pipeline-workspace。

点击这里获取提示

- name: NAME
  workspaces:
    - name: source
      workspace: pipeline-workspace
    - name: dockerconfig
      workspace: dockerconfig-ws
  taskRef:
    name: TASKREF-NAME
    kind: KIND
  params:
  - name: PARAM-NAME
    value: "PARAM-VALUE"
  runAfter:
    - RUNNING-AFTER

点击这里查看解决方案

- name: build
  workspaces:
    - name: source
      workspace: pipeline-workspace
  taskRef:
    name: buildah
    kind: ClusterTask
  params:
  - name: IMAGE
    value: "us.icr.io/$(context.pipelineRun.namespace)/$(params.app-name)"
  runAfter:
    - tests

评估:截取 pipeline.yaml 的屏幕并将其保存为 08-pipeline-changes.png。