使用 Cloudflare workers 做一个定时发送消息的飞书机器人

前言

上一篇介绍 Cloudflare 的文章 初步使用了下 Cloudflare 平台,帮我做 CDN 加速和无限邮箱注册,本次介绍一下 Cloudflare Worker 功能,实现一个飞书每日提醒晨会的机器人。

Cloudflare Worker 介绍

Cloudflare Worker 是 Cloudflare 提供的一种 无服务器计算平台 ,它允许开发者在 Cloudflare 的全球边缘节点上运行 JavaScript、TypeScript、或 WebAssembly 编写的代码。其核心目标是让开发者可以更接近用户地部署代码,以获得更低延迟和更高性能的 Web 应用或 API 服务。

简单讲就是一个 Serverless 服务,写一段代码就可以直接部署完成,可以触发这个接口了。

创建项目

主要参考文档 developers.cloudflare.com/workers/get...

shell 复制代码
pnpm create cloudflare@latest my-first-worker

运行后会有一个问答形式的 CLI,选择 Worker only 和 暂时不需要部署。创建好后进入项目。

shell 复制代码
cd my-first-worker
pnpm dev

src/index.ts 就是抛出函数的地方。我们打开浏览器访问这个地址也会返回这句 Hello World!

编写定时需要触发的函数

由于需要每天固定时间触发,我们需要抛出一个 scheduled 函数。

ts 复制代码
export async function isWorkday(dateStr: string): Promise<boolean> {
	try {
    const response = await fetch(`https://holiday.dreace.top/?date=${dateStr}`);
    const data = (await response.json()) as { isHoliday: boolean };
    return !data.isHoliday;
	} catch (err) {
    console.error('Failed to check workday:', err);
    // 如果接口调用失败,默认为工作日
    return true;
	}
}

async function scheduledHandler(event: ScheduledEvent, env: Env, ctx: ExecutionContext) {
	// 检查今天是否为工作日
    const today = new Date().toISOString().split('T')[0];
    const isWorkDay = await isWorkday(today);

	if (!isWorkDay) {
    console.log('今天不是工作日,无需发送消息');
    return;
	}

	await sendCardMessage();
}

async function fetchHandler(request: Request, env: Env, ctx: ExecutionContext): Promise<Response> {
	return new Response('This worker only handles scheduled tasks.');
}

export default {
	fetch: fetchHandler,
	scheduled: scheduledHandler,
};

然后在 wrangler.jsonc 添加 triggers crons 配置,表示定时触发,我的需求是周一到周五每天 9.30, Cloudflare 默认是美国时区,所以要变化一下写成美国 1.30 才对应的是中国 9.30。

这里的 crons 表达式直接让 AI 老师帮忙写就好,描述好自己的需求再检查下即可。

json 复制代码
{
	"$schema": "node_modules/wrangler/config-schema.json",
	"name": "my-first-worker",
	"main": "src/index.ts",
	"compatibility_date": "2025-04-29",
	"observability": {
            "enabled": true
	},
	"triggers": {
            "crons": ["30 1 * * 1-5"]
	}
}

然后就是发送卡片消息的主体函数部分了。你需要先在飞书添加一个自定义机器人,会给你一个 webhook 地址。

然后卡片消息可以在飞书后台配置一份富文本形式的 cardMessage。

ts 复制代码
const webhookUrl = "" // 你添加的机器人 webhook 地址

async function sendCardMessage(env: Env) {
	const nextHost = await updateNextHost(env);
	const cardMessage = {}; // 飞书卡片的富文本消息格式,可以自行去飞书后台复制一份
	try {
        const response = await fetch(webhookUrl, {
                method: 'POST',
                headers: {
                        'Content-Type': 'application/json',
                },
                body: JSON.stringify(cardMessage),
        });
        return await response.json();
	} catch (error: any) {
		return { error: error.message };
	}
}

部署上传

先执行登录命令,会打开浏览器要求你授权。

shell 复制代码
wrangler login

然后执行部署

shell 复制代码
wrangler deploy

就可以在 worker 中看到你刚刚上传的 worker 了,点进去详情还可以查看触发日志,还有各式各样的配置,十分全面,感恩 Cloudflare ~

相关推荐
天***889620 小时前
Chrome扩展安装插件教程,Edge安装插件扩展教程,浏览器安装扩展程序方法
前端·chrome·edge
心.c20 小时前
深拷贝浅拷贝
开发语言·前端·javascript·ecmascript
VermiliEiz21 小时前
k8s的calico出现ipset报错解决方法
云原生·容器·kubernetes
IT_陈寒21 小时前
Vue 3.4性能优化实战:5个鲜为人知的Composition API技巧让打包体积减少40%
前端·人工智能·后端
前端九哥21 小时前
💻【急招!27届前端实习生】广州4399实习太幸福了!江景+三餐+健身房全都有😭
前端·面试·招聘
咖啡の猫21 小时前
Vue全局事件总线
前端·javascript·vue.js
Lovereo21 小时前
我的目标检测性能优化之路:预算不够、GPU 没有、但性能我得要
前端
蒙娜丽宁21 小时前
Rust 与 WebAssembly:构建高效前端应用的全流程复盘
前端·rust·wasm
这儿有一堆花21 小时前
使用 Actix-web 开发高性能 Web 服务
前端·数据库
豆苗学前端21 小时前
10分钟带你入门websocket,并实现一个在线多人聊天室
前端·javascript·后端