Nomad 系列-快速上手

news2025/1/12 18:04:18

系列文章

  • Nomad 系列文章

Nomad 重要术语

Nomad Terms

Nomad 安装设置相关术语

  • agent - 代理。Agent 是在 Server(服务器) 或 Client(客户端) 模式下运行的 Nomad 进程。
  • client - 客户端。Nomad 客户端负责运行分配给它的任务。它还向服务器注册自己,并监视要分配的任何工作。当运行代理时,客户端可以被称为节点 (Node)。
  • server - 服务器端。Nomad 服务器管理所有作业和客户端,监视任务,并控制哪些任务被放置在哪些客户端节点上。服务器之间相互复制数据以确保高可用性。
  • dev_agent - 开发(模式)代理是一种代理配置,它为运行 Nomad 的单节点集群提供了有用的默认值。它在服务器和客户端模式下运行,并且不会将其群集状态持久化到磁盘,这允许代理从可重复的干净状态启动,而不必在运行之间删除基于磁盘的状态。

Nomad 集群通常由三到五个服务器代理和许多客户端代理组成。

Nomad 使用的相关术语

在 Nomad 调度和运行工作负载的过程中,您将遇到以下术语。

  • task - 任务是 Nomad 中最小的工作单元(类似 K8s 中的 Pod)。任务由 task drivers 执行,drivers 包括 docker 和 exec 等,这使得 Nomad 可以灵活地支持任务类型。任务指定其所需的任务驱动程序、驱动程序的配置、约束 (constraints) 和所需的资源。
  • group - 组是在同一 Nomad 客户端上运行的一系列任务。(我个人认为类似于 K8s 中的 Deployment/Statefulset/Daemonset/Job)
  • job - 作业是 Nomad 的核心控制单元,它定义了应用程序及其配置。它可以包含一个或多个任务。(我个人认为 job 类似于 K8s 中的多个资源 yaml manifest 集合。包括:SVC/Ingress/ConfigMap/Deploy/PVC...)
  • job specification - 作业规范,也称为 jobspec,定义了 Nomad 作业的模式。它描述了作业的类型、作业运行所需的任务和资源、作业信息(如作业可以在哪些客户端上运行)等。
  • allocation - 分配是作业中的任务组与客户端节点之间的映射。当运行作业时,Nomad 将选择能够运行它的客户端,并在机器上为作业中定义的任务组中的任务分配资源。(我认为类似于 K8s 中已经在运行的 pod.)

应用程序在 jobspec 中定义为具有 jobspec 的任务组 (groups of tasks),并且一旦提交给 Nomad,就会创建一个作业 (job) 沿着该 jobspec 中定义的每个组的分配 (allocation)。

Nomad 上的应用工作流

典型的应用程序工作流程涉及几个步骤,并从 Nomad 外部开始。

在 Nomad 上运行的任何应用程序的先决条件是具有工作负载工件。Nomad 支持各种工件,包括 Docker 镜像、原始二进制文件 raw binaries、Java 应用程序 和使用 QEMU 的虚拟机映像。

Nomad 不会创建这些应用程序工件,但可以使用 CircleCI,GitHub Actions 或本地构建等 CI 工具来创建工件,然后将其推送到存储库,Nomad 可以在调度作业时从中检索它们。

创建应用程序后,工作流将继续使用 Nomad。

Nomad Workflow

  • 创建 job spec - 作业规范包含应用程序所需的任务,包括工件驻留的位置、网络配置(如端口和服务定义)、所需实例数量等等。
  • 部署 job - 作业规范将提交给 Nomad,并根据作业配置在一个或多个客户端上为作业安排分配。
  • 更新和重新部署 job - 更新应用程序代码或作业规范,然后重新提交给 Nomad 进行调度。

快速入门

接下来我们快速上手 Nomad, 主要展示如何部署示例应用程序。

前提

  • Docker 已安装
  • Nomad 二进制(包括 CLI) 已安装
  • (可选)CNI 插件已安装
  • Nomad 集群已创建并运行(至少包括 1 个 Server 和 1 个 Client)

部署示例应用程序 Job

这里我们直接使用 git clone Nomad 官方提供的 Demo:

git clone https://github.com/hashicorp-education/learn-nomad-getting-started.git
cd learn-nomad-getting-started
git checkout -b nomad-getting-started v1.1

示例应用程序在 Docker 容器中运行,由一个数据库和一个从数据库读取数据的 Web 前端组成。您将使用 参数化批处理作业 parameterized batch job 设置数据库,然后使用 定期批处理作业 periodic batch job 启动其他将数据写入数据库的短期作业。

Job 类型

Service(服务) 作业用于长期运行的服务(类似于 K8s 中的 Deployment),这些服务一直运行到显式停止。

Batch 作业是指在成功退出之前一直运行的短期作业(类似于 K8s 中的 JobCronJob)。

  • 参数化 (parameterized) 块允许您配置批处理作业以接受必需或可选的输入。您可以使用 nomad job dispatch 命令触发作业。
  • 周期性 (periodic) 块允许您安排 Nomad 作业在设置的时间运行。这些也被称为 Nomad cron jobs(类似于 K8s 中的 CronJob)。

示例应用程序 Pytechco 概述

示例应用程序 pytechco 模拟在一家技术公司工作的员工。他们联机,完成任务,然后注销。

跳转到本地计算机上示例 repo 的 jobs 目录:

cd jobs

下面每个组成应用程序的 jobspec 文件都将 driver 属性设置为 docker ,并使用 image 属性指定存储在 GHCR 中 config 块中的镜像。而 Redis 作业使用了 Docker Hub 上托管的官方 Redis 镜像。

Redis 服务

jobs/pytechco-redis.nomad.hcl 内容如下:

task "redis-task" {
  driver = "docker"
  config {
    image = "redis:7.0.7-alpine"
  }
}

pytechco-redis.nomad.hcl -此服务作业运行并将 Redis 数据库暴露为 Nomad 服务,以供其他应用程序组件连接。jobspec 将类型设置为 service ,配置 Nomad service 块(类似于 K8s 中的 Service) 以使用 Nomad 原生服务发现 (Nomad native service discovery),并创建名为 redis-svc 的服务。具体如下:

job "pytechco-redis" {
  type = "service"

  group "ptc-redis" {
    count = 1
    network {
      port "redis" {
        to = 6379
      }
    }

    service {
      name     = "redis-svc"
      port     = "redis"
      provider = "nomad"
    }

    task "redis-task" {
      driver = "docker"

      config {
        image = "redis:7.0.7-alpine"
        ports = ["redis"]
      }
    }
  }
}

以上代码说明如下:

  • type = "service": service type 的 job, 类似于 K8s 中的 Deployment
  • group "ptc-redis": group 块 ptc-redis
  • count = 1: 副本数为 1
  • to = 6379: 位于 network 块中,指示连接到 (to) 容器中的 6379 端口 (host 或 bridge 端口随机分派)
  • service {: service 块,类似于 K8s 中的 Service
  • provider = "nomad": Nomad 从 1.3 版本及以后,新增 Nomad native service. 🐾注意:如果不指定,默认使用 consul service.(前提是需要安装 consul)
  • task "redis-task" {: task 块,类似于 K8s 中的 Pod.
  • driver = "docker": Nomad 不同于 K8s. K8s 默认只支持一种运行时,即容器运行时;Nomad 默认就支持多种运行时 (nomad 的术语是driver), 典型如:docker, java, raw binarier, QEMU 等,这里指定使用 docker driver.
  • config {: 这里是特定于 docker 的 driver 的配置,包括:imageports
  • image = "redis:7.0.7-alpine": Docker Hub 的 redis:7.0.7-alpine" 镜像
  • ports = ["redis"]: 对外暴露的端口列表,这里是 redis, 即在 network 中定义的 to = 6379
Web 服务

pytechco-web.nomad.hcl -此服务作业运行 Web 应用程序前端,显示存储在数据库中的值和活动员工。jobspec 将类型设置为 service ,并为应用程序使用静态端口 5000 。它还使用 nomadService 内置函数来获取 Redis 数据库服务的地址和端口信息。

job "pytechco-web" {
  type = "service"

  group "ptc-web" {
    count = 1
    network {
      port "web" {
        static = 5000
      }
    }

    service {
      name     = "ptc-web-svc"
      port     = "web"
      provider = "nomad"
    }

    task "ptc-web-task" {
      template {
        data        = <<EOH
{{ range nomadService "redis-svc" }}
REDIS_HOST={{ .Address }}
REDIS_PORT={{ .Port }}
FLASK_HOST=0.0.0.0
REFRESH_INTERVAL=500
{{ end }}
EOH
        destination = "local/env.txt"
        env         = true
      }

      driver = "docker"

      config {
        image = "ghcr.io/hashicorp-education/learn-nomad-getting-started/ptc-web:1.0"
        ports = ["web"]
      }
    }
  }
}

详细说明如下(大部分和 redis 类似,这里不重复介绍了):

  • static = 5000: 位于 network 块中,指定静态端口为 5000. 与to 不一样在于,to 指定内部端口,外部端口随机分派;static 内外部端口都相同,这里是 5000 端口。
  • template {: template 块。作用类似于 K8s 中的 ConfigMap.
  • data = <<EOH: 具体配置内容,这里是引用 nomadService 内置函数来获取 Redis 数据库服务的地址和端口信息。配置内容为 EOH 包裹的内容。
    • REDIS_HOST={{ .Address }}: 即运行后的分派 (alloc) 的外部(通常是 host) 地址
    • REDIS_PORT={{ .Port }}: 即运行后分派的外部端口(不是 6379), 是一个 20000-30000 之间的随机端口。
  • destination = "local/env.txt: 配置文件在分派后的位置。
  • env = true: 同时也将REDIS_HOST REDIS_PORT 等设置为分配 (alloc) 容器中的环境变量。
Setup Parameterized Batch

pytechco-setup.nomad.hcl -此参数化批处理作业 (parameterized batch job) 使用默认值设置数据库。您可以多次调度它来重置数据库。jobspec 将类型设置为 batch ,并有一个带有 meta_required 属性的 parameterized 块,在分派时需要 budget 的值。

job "pytechco-setup" {
  type = "batch"

  parameterized {
    meta_required = ["budget"]
  }

  group "ptc-setup" {
    count = 1

    task "ptc-setup-task" {

      template {
        data        = <<EOH
{{ range nomadService "redis-svc" }}
REDIS_HOST={{ .Address }}
REDIS_PORT={{ .Port }}
{{ end }}
PTC_BUDGET={{ env "NOMAD_META_budget" }}
EOH
        destination = "local/env.txt"
        env         = true
      }
      driver = "docker"

      config {
        image = "ghcr.io/hashicorp-education/learn-nomad-getting-started/ptc-setup:1.0"
      }
    }
  }
}

具体说明如下:

  • type = "batch" Job 类型为 batch, 类似于 K8s 中的 JobCronJob
  • parameterized {: 该 Job 有一个带有 meta_required 属性的 parameterized 块,在分派时需要 budget 的值
  • PTC_BUDGET={{ env "NOMAD_META_budget }} 获取环境变量 NOMAD_META_budget 的值并赋给 PTC_BUDGET
Employee Periodic Batch

pytechco-employee.nomad.hcl -此定期批处理作业使员工联机。它随机化了员工的工作类型和其他变量,如他们工作的时间和他们完成任务的速度。jobspec 将类型设置为 batch ,并有一个 periodic 块将 cron 属性设置为允许它每 3 秒启动一个新作业的值。

job "pytechco-employee" {
  type = "batch"

  periodic {
    cron             = "0/3 * * * * * *"
    prohibit_overlap = false
  }

  group "ptc-employee" {
    count = 1

    task "ptc-employee-task" {

      restart {
        attempts = 2
        delay    = "15s"
        interval = "10s"
        mode     = "fail"
      }

      template {
        data        = <<EOH
{{ range nomadService "redis-svc" }}
REDIS_HOST={{ .Address }}
REDIS_PORT={{ .Port }}
PTC_EMPLOYEE_ID={{ env "NOMAD_SHORT_ALLOC_ID"}}
{{ end }}
EOH
        destination = "local/env.txt"
        env         = true
      }
      driver = "docker"

      config {
        image = "ghcr.io/hashicorp-education/learn-nomad-getting-started/ptc-employee:1.0"
        // args = [
        //     "--employee-type", "sales_engineer"
        // ]
      }
    }
  }
}

具体说明如下:

  • periodic {: type = "batch" 再加上 periodic, 就类似于 K8s 中的 CronJob
  • restart {: Batch 执行过程中的异常重启机制配置。
  • PTC_EMPLOYEE_ID={{ env "NOMAD_SHORT_ALLOC_ID"}}: 将环境变量 NOMAD_SHORT_ALLOC_ID(该环境变量由 Nomad 生成,类似于 K8s 的 pod name) 赋值给 PTC_EMPLOYEE_ID
  • // args = [: // HCL 中的注释,此行不起作用。argsdocker driver config 中的 args 配置。

从 Nomad 1.5.0 开始, datacenter 属性默认为集群中所有可用的数据中心( "*" )。因此,本教程的作业规范将省略该属性,因为默认值已足够。如果您运行的是较早版本的 Nomad CLI 和集群二进制文件,则需要包含并设置该属性。

部署应用程序

具体命令如下:

提交数据库 Job:

$ nomad job run pytechco-redis.nomad.hcl
==> 2023-03-10T12:16:09-05:00: Monitoring evaluation "d44af37b"
    2023-03-10T12:16:09-05:00: Evaluation triggered by job "pytechco-redis"
    2023-03-10T12:16:10-05:00: Evaluation within deployment: "0ea05651"
    2023-03-10T12:16:10-05:00: Allocation "be0bda79" created: node "2c9f4b7e", group "ptc-redis"
    2023-03-10T12:16:10-05:00: Evaluation status changed: "pending" -> "complete"
==> 2023-03-10T12:16:10-05:00: Evaluation "d44af37b" finished with status "complete"
==> 2023-03-10T12:16:10-05:00: Monitoring deployment "0ea05651"
  ✓ Deployment "0ea05651" successful

    2023-03-10T12:16:24-05:00
    ID          = 0ea05651
    Job ID      = pytechco-redis
    Job Version = 0
    Status      = successful
    Description = Deployment completed successfully

    Deployed
    Task Group  Desired  Placed  Healthy  Unhealthy  Progress Deadline
    ptc-redis   1        1       1        0          2023-03-10T17:26:23Z

提交 web Job:

nomad job run pytechco-web.nomad.hcl

获取 webapp 的 IP 地址。以下命令获取 Web 作业的分配 ID,并使用该 ID 获取分配的状态。然后,它在分配状态输出中搜索 IP 地址,并将 IP 地址格式化为与 webapp 端口的链接。在浏览器中打开输出中的 URL 以查看 webapp 前端。

nomad node status -verbose \
    $(nomad job allocs pytechco-web | grep -i running | awk '{print $2}') | \
    grep -i ip-address | awk -F "=" '{print $2}' | xargs | \
    awk '{print "http://"$1":5000"}'

提交 Setup Job:

nomad job run pytechco-setup.nomad.hcl

通过提供 budget 值分派该 setup job:

$ nomad job dispatch -meta budget="200" pytechco-setup
Dispatched Job ID = pytechco-setup/dispatch-1678468734-396cfa83
Evaluation ID     = 53a77034

==> 2023-03-10T12:18:54-05:00: Monitoring evaluation "53a77034"
    2023-03-10T12:18:54-05:00: Evaluation triggered by job "pytechco-setup/dispatch-1678468734-396cfa83"
    2023-03-10T12:18:54-05:00: Allocation "d6c60ffd" created: node "2c9f4b7e", group "ptc-setup"
    2023-03-10T12:18:54-05:00: Evaluation status changed: "pending" -> "complete"
==> 2023-03-10T12:18:54-05:00: Evaluation "53a77034" finished with status "complete"

提交 Employee Job:

nomad job run pytechco-employee.nomad.hcl

跳转到 Nomad UI,单击 "Jobs" 页面,然后单击 pytechco-employee job。由于这是一个 cron batch job,您可以看到它每 3 秒创建一个新作业。

Nomad UI - pytechco-employee cron batch job

跳转回 webapp URL。效果如下:

PyTechCo Demo App

更新应用程序

首先,停止 employee job:

nomad job stop -purge pytechco-employee

通过使用新 budget 500 再次分派 setup job 来重置数据库:

$ nomad job dispatch -meta budget="500" pytechco-setup
Dispatched Job ID = pytechco-setup/dispatch-1678469008-6ffe1c0c
Evaluation ID     = e8e420f0

==> 2023-03-10T12:23:28-05:00: Monitoring evaluation "e8e420f0"
    2023-03-10T12:23:28-05:00: Evaluation triggered by job "pytechco-setup/dispatch-1678469008-6ffe1c0c"
    2023-03-10T12:23:28-05:00: Allocation "74acf63e" created: node "2c9f4b7e", group "ptc-setup"
    2023-03-10T12:23:28-05:00: Evaluation status changed: "pending" -> "complete"
==> 2023-03-10T12:23:28-05:00: Evaluation "e8e420f0" finished with status "complete"

打开 pytechco-employee.nomad.hcl 文件并取消注释任务配置的 args 块,使作业仅创建类型为 sales_engineer 的员工。然后将cron更新为 0/1 * * * * * * ,使作业每秒运行一次。保存文件。

...
        cron = "0/1 * * * * * *"
...

        args = [
            "--employee-type", "sales_engineer"
        ]
...

再次提交 employee job 并跳转到 Web 应用程序。请注意,所有在线员工现在都只是销售工程师 (sales_enginee)(之前是有多个不同的员工类型),而且他们中的更多人在任何给定时间都在线。

$ nomad job run pytechco-employee.nomad.hcl
Job registration successful
Approximate next launch time: 2023-03-10T17:24:18Z (1s from now)

清理应用程序

停止并清理所有 Jobs:

nomad job stop -purge pytechco-employee
nomad job stop -purge pytechco-web
nomad job stop -purge pytechco-redis
nomad job stop -purge pytechco-setup

总结

本文中,我们一起了解了 Nomad 的术语,并根据官方 Demo, 部署和更新了 Nomad Job。同时穿插了解了 Nomad 和 K8s 的一些类比和对比。

后面就正式进入具体实战环节,包括:Nomad 与 Traefik 和 Tailscale 的集成等独家内容。敬请期待。💪💪💪

📚️参考文档

  • Introduction to Nomad Nomad
  • Deploy and Update a Job

三人行, 必有我师; 知识共享, 天下为公. 本文由东风微鸣技术博客 EWhisper.cn 编写.

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/981290.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

JVM----GC(垃圾回收)详解

一、Automatic Garbage Collection&#xff08;垃圾回收&#xff09;简介 Automatic Garbage Collection &#xff08;自动垃圾回收&#xff09;是JVM的一个特性&#xff0c;JVM会启动相关的线程&#xff0c;该线程会轮训检查heap memeory&#xff0c;并确定哪些是未被引用的(…

滚动菜单 flutter

想实现这个功能&#xff1a; 下面的代码可以实现&#xff1a; import package:flutter/material.dart;void main() > runApp(MyApp());class MyApp extends StatelessWidget {static const String _title Flutter Code Sample;overrideWidget build(BuildContext context)…

【MySQL】CRUD (增删改查) 基础

CRUD&#xff08;增删改查&#xff09;基础 一. CRUD二. 新增 &#xff08;Create&#xff09;1. 单行数据 全列插入2. 多行数据 指定列插入 三. 查询&#xff08;Retrieve&#xff09;1. 全列查询2. 指定列查询3. 查询字段为表达式4. 别名5. 去重&#xff1a;DISTINCT6. 排序…

【算法】希尔 (Shell) 排序 详解

希尔排序 详解 希尔排序代码实现 排序&#xff1a; 排序&#xff0c;就是使一串记录&#xff0c;按照其中的某个或某些关键字的大小&#xff0c;递增或递减的排列起来的操作。 稳定性&#xff1a; 假定在待排序的记录序列中&#xff0c;存在多个具有相同的关键字的记录&#x…

生信豆芽菜-机器学习筛选特征基因

网址&#xff1a;http://www.sxdyc.com/mlscreenfeature 一、使用方法 1、准备数据 第一个文件&#xff1a;特征表达数据 第二个文件&#xff1a;分组信息&#xff0c;第一列为样本名&#xff0c;第二列为患者分组 第三个文件&#xff1a;分析基因名 2、选择机器学习的方…

[学习笔记]CS224W

资料&#xff1a; 课程网址 斯坦福CS224W图机器学习、图神经网络、知识图谱【同济子豪兄】 斯坦福大学CS224W图机器学习公开课-同济子豪兄中文精讲 图的基本表示 图是描述各种关联现象的通用语言。与传统数据分析中的样本服从独立同分布假设不一样&#xff0c;图数据自带关联…

学习SpringMvc第二战之【SpringMVC之综合案例】

目录 一. 参数传递 1.前期准备工作&#xff08;替换pom.xml中的部分依赖&#xff09; 1.1将log4j替换成为slf4j(将打印语句替换成为日志文件输出结果) 2.正式操作 1.基础传参 1.1创建方法&#xff0c;用于验证传参 1.2构建界面回显 1.3设置访问路径&#xff08;localho…

【PHP代码审计】反序列化漏洞实战

文章目录 概述资源下载地址Typecho代码审计-漏洞原理call_user_func()_applyFilter()、get()与__get__toString()__construct()install.php POC利用漏洞利用复现利用链执行phpinfo()GET利用POST利用 getshell生成payload漏洞利用蚁剑连接 总结 概述 序列化&#xff0c;“将对象…

污水处理厂3D数字孪生三维可视系统降低设备风险隐患

当相对传统与保守的水务行业&#xff0c;与激进与开放的互联网发生碰撞之后&#xff0c;产生了最好的一个名词是&#xff1a;“智慧水务”&#xff0c;谈及智慧水务&#xff0c;自然免不了当下最具热度的技术“元宇宙”&#xff0c;水资源再生是我国追求高质量发展的新策略&…

fastadmin列表,关联筛选查询

fastadmin文章表关联分类表&#xff0c;分类筛选默认按分类名模糊查询&#xff0c;项目需求是下拉选择分类&#xff0c;根据分类id直接筛选。最终效果如下图。 var table $("#table");//在普通搜索渲染后table.on(post-common-search.bs.table, function (event, ta…

Elasticsearch脑裂

文章目录 Elasticsearch脑裂 Elasticsearch脑裂 Elasticsearch脑裂是指由于网络分区或节点间通信故障导致集群中的节点无法互相正常通信&#xff0c;从而导致数据不一致的情况。这可能会导致集群中的多个节点同时自认为是主节点&#xff08;master&#xff09;&#xff0c;并开…

mysql(十)mysql主从复制--主库切换

概述 可能为了更迭升级服务器&#xff0c;或者主库出现问题&#xff0c;又或者只是希望重新分配容量&#xff0c;此时需要切换主库。 如果这是计划内的切换&#xff0c;会相对容易点。只需要在从库上使用CHANGE MASTER TO命令&#xff0c;并设置合适的值。大多数的值都是可选…

大数据技术之Hadoop:使用命令操作HDFS(四)

目录 一、创建文件夹 二、查看指定目录下的内容 三、上传文件到HDFS指定目录下 四、查看HDFS文件内容 五、下载HDFS文件 六、拷贝HDFS文件 七、HDFS数据移动操作 八、HDFS数据删除操作 九、HDFS的其他命令 十、hdfs web查看目录 十一、HDFS客户端工具 11.1 下载插件…

OpenWrt系统内核设置

系统内核设置&#xff1a;OpenWrt也是一个 Linux 操作系统&#xff0c;因此它和其他Linux 操作系统一样&#xff0c; 可以通过一些配置文件配置。 一、/etc/sysctl.conf 配置文件 这个文件是系统启动预加载的内核配置文件&#xff0c;通过sysctl命令读取和设置到系统当中。这个…

openGauss学习笔记-62 openGauss 数据库管理-两地三中心跨Region容灾

文章目录 openGauss学习笔记-62 openGauss 数据库管理-两地三中心跨Region容灾62.1 基于流式复制的异地容灾解决方案62.1.1 概述62.1.2 规格与约束62.1.2.1 特性规格62.1.2.2 特性约束 62.1.3 影响容灾性能指标的GUC参数设置62.1.3.1 检查点相关参数设置的影响62.1.3.2 极致RTO…

android 车载widget小部件部分详细源码实战开发-千里马车载车机framework开发实战课程

官网参考链接&#xff1a;https://developer.android.google.cn/develop/ui/views/appwidgets/overview 1、什么是小部件 App widgets are miniature application views that can be embedded in other applications (such as the home screen) and receive periodic updates…

LED显示屏安全亮度参数设置方法和防护

随着LED显示屏应用领域越来越广&#xff0c;但其高亮度造成的光污染&#xff0c;常受到的人们的诟病。为了更好的避免光污染&#xff0c;我整理了一些关于LED显示安全亮度参数设置方法和安全防护措施。你知道LED广告牌是如何工作的吗&#xff1f; 设置LED显示屏的安全亮度参数和…

android上架备案公钥和md5获取工具

最近很多公司上架遇到了一个问题&#xff0c;就是要提供app的备案证明&#xff0c;现在android上架都需要备案了&#xff0c;但是我们的证书都是通过工具生成的&#xff0c;哪里知道公钥和md5那些东西呢&#xff1f;无论安卓备案还是ios备案都需要提供公钥和md5。 包括ios的备案…

ChatGPT Prompting开发实战(五)

一、如何编写有效的prompt 对于大语言模型来说&#xff0c;编写出有效的prompt能够帮助模型更好地理解用户的意图(intents)&#xff0c;生成针对用户提问来说是有效的答案&#xff0c;避免用户与模型之间来来回回对话多次但是用户不能从LLM那里得到有意义的反馈。本文通过具体…

异步请求库的实际应用案例:爬取豆瓣经典电影

在日常爬虫过程中&#xff0c;你有没有遇到过需要爬取大量数据的情况&#xff0c;但是传统的同步请求方式让您等得焦头烂额&#xff1f; 这个问题的根源在于传统的同步请求方式。当我们使用同步请求时&#xff0c;程序会一直等待服务器的响应&#xff0c;直到数据返回后才能继续…