这是本节的多页打印视图。 点击此处打印.

返回本页常规视图.

基本功能

介绍服务拥有的基本能力

请看各章节详情。

1 - 给自己发送通知

轻松给自己的微信发送通知。

获取你的 Token

调用用户级别的功能,需要用户 Token
向公众号发送 token 就可以得到自己的用户 Token

发送消息

现在调用发送消息的 API 就可以往公众号发送消息了

GET https://api.letserver.run/message/info?token=YOUR-TOKEN&msg=hello

用 curl 命令就是这样

curl "https://api.letserver.run/message/info?token=YOUR-TOKEN&msg=hello"

消息类型

目前有四个消息接口,它们的区别如下:

  • info 公众号模板消息,提醒,默认为蓝色
  • warning 公众号模板消息,警告,默认为红色
  • text 利用公众号客服消息直接发文本,每次和公众号互动后有20条额度
  • auto 先尝试发送 text ,如果失败则改用 info 接口

GET 和 POST

GET 版本的接口是为了调试和简单的使用的,比如在 CI 脚本中,写起来简单。

POST 版本接口需要把 token 携带在 Authorization Header 中。
并且还支持自定义颜色等,详情参见 接口文档

User 和 Agent

在接口文档中,除了 User 接口,还有若干 Agent 发消息接口,比如 /agent/message/info
Agent 版本和 User 版本的区别是使用的 Token 不一样。

Agent 版本是为了 Agent 能方便的直接调用,不用再传入 User Token
另外在发送模板消息时,Agent 版本会标注消息来源。

限制

公众号模板消息有每小时5条的限制,而纯文本的客服消息,是在你向公众号说话后,会在48小时内有20条发送额度。 每次说话都会重置这个额度。

2 - Agent简介

关于 Agent 的基本信息。

除了在服务器上调用我们的 API 给公众号发通知,Server饭 更有用的功能是把这个过程反过来, 在公众号输入文字控制服务器的行为,您只要一次配置,以后便有个随身的控制台了。

什么是 Agent

Agent 是一个概念,它是帮你处理你在公众号中输入的指令的一个程序。

它可以在服务器,在PC,在路由器,在智能设备中。它可以用任何语言写成。 它甚至可以没有实体,只需要在你的服务中调用 API ,就相当于完成了 Agent 的功能。

采取这种 Agent 拉取并执行命令的模式,是为了绝对的安全。你的 Agent 只会执行你允许的动作。
Server饭 的云服务不会主动访问你的服务器,这也带来了内网穿透的功能,你可以任意使用代理。

怎么写一个 Agent

这里是 Agent API

写一个 Agent 只需要按如下逻辑调用这三个 API 就好了:

  1. 每分钟调用一次 接收Job
  2. 如果返回结果是 204,证明没有 Job 需要执行。如果是 200,则解析出 Job 去执行它。
  3. 执行完成之后,调用 成功失败 修改 Job 状态,这时你在公众号中会收到相应的通知。

能更方便一点吗?

我们正在添加各个语言的 SDK,这样写起来会更方便,目前只有 Go

欢迎为你喜欢的语言写 SDK

有例子吗?

同样的,目前还只有 Go 的例子,后续会在 SDK 完成后添加 python nodejs java php 等语言。

执行shell命令的例子

管理 Docker Swarm 的例子

能再方便一点吗?

我们会写很多现成的 Agent 供大家使用。目前写好了一个,它可以通过简单配置就启动在 Linux 当中帮你执行指定的命令。

比如重启服务之类的常用需求,使用这个就完全够了。详情见下一节。

3 - 一个通用Agent

可以轻松的部署在服务器上,帮你根据配置文件执行命令,使用 Golang 编写。

如果只是想在服务器上执行简单的命令,使用我们开源的这个通用 Agent 就够了。

它的源代码在: https://github.com/hack-fan/skadi-agent-shell

命令和服务的名字叫 skadi , 和我们的开源项目保持一致。

安装

Debian/Ubuntu

第一步,增加软件源

curl -1sLf \
  'https://dl.cloudsmith.io/public/hackfan/skadi/setup.deb.sh' \
  | sudo -E bash

如果你本身用的 root 用户,请去掉命令中的 sudo

第二步,更新源,安装 skadi

apt update
apt install skadi

这里安装就完成了,skadi 在安装完成后并不会立即启动,因为还需要配置 Agent Token, 请参考后续的配置环节。

ps. 如果你对第一步的自动脚本不放心,那么可以用如下步骤手动增加软件源:

apt-get install -y debian-keyring  # debian only
apt-get install -y debian-archive-keyring  # debian only
apt-get install -y apt-transport-https
curl -1sLf 'https://dl.cloudsmith.io/public/hackfan/skadi/gpg.75A5AACF21FC017E.key' | apt-key add -
curl -1sLf 'https://dl.cloudsmith.io/public/hackfan/skadi/config.deb.txt?distro=ubuntu&codename=xenial' > /etc/apt/sources.list.d/hackfan-skadi.list
apt-get update

注意:你需要更改上述命令中的 ubuntuxenial 为你的发行版和版本。

ps2. 卸载软件源

在使用 apt 卸载 skadi 之后,你也许还想卸载软件源,执行如下命令即可卸载干净:

rm /etc/apt/sources.list.d/hackfan-skadi.list
apt-get clean
rm -rf /var/lib/apt/lists/*
apt-get update

Redhat/CentOS/Amazon/Fedora/SUSE

第一步,增加软件源

curl -1sLf \
  'https://dl.cloudsmith.io/public/hackfan/skadi/setup.rpm.sh' \
  | sudo -E bash

如果你本身用的 root 用户,请去掉命令中的 sudo

第二步,更新源,安装 skadi,如果是 Fedora或SUSE用户,自行替换命令为 dnf/zypper

yum install skadi

这里安装就完成了,skadi 在安装完成后并不会立即启动,因为还需要配置 Agent Token, 请参考后续的配置环节。

ps. 如果你对第一步的自动脚本不放心,那么可以用如下步骤手动增加软件源,这里仅列出 Redhat/CentOS 脚本:

yum install yum-utils pygpgme
rpm --import 'https://dl.cloudsmith.io/public/hackfan/skadi/gpg.75A5AACF21FC017E.key'
curl -1sLf 'https://dl.cloudsmith.io/public/hackfan/skadi/config.rpm.txt?distro=el&codename=7' > /tmp/hackfan-skadi.repo
yum-config-manager --add-repo '/tmp/hackfan-skadi.repo'
yum -q makecache -y --disablerepo='*' --enablerepo='hackfan-skadi'

注意:你需要更改上述命令中的 el7 为你的发行版和版本。

ps2. 卸载软件源

在使用 apt 卸载 skadi 之后,你也许还想卸载软件源,执行如下命令即可卸载干净:

rm /etc/yum.repos.d/hackfan-skadi.repo
rm /etc/yum.repos.d/hackfan-skadi-source.repo

配置

配置文件在 /etc/skadi/skadi.yml 按照注释自行修改即可。

# 调试模式,打开可以看到更多日志,使用 journalctl -u skadi 查看日志
debug: false
# 可以直接填写token到这里,或者用 skadi TOKEN 命令去写入
token:
# shortcuts 将一个单词精确的翻译为一条命令
# short: 你在公众号输入的消息
# dir: 命令的工作目录,可选。有的命令不需要工作目录就不填。
# cmd: 精确的命令。
shortcuts:
  - short: date
    cmd: "date --rfc-3339=second"
  - short: lsroot
    dir: /
    cmd: ls
# commands 是一个命令白名单,这里列出命令,在公众号使用时可以随意加参数。
# dir: 命令的工作目录,可选。有的命令不需要工作目录就不填。
# prefix: 允许的命令,比如这里允许free,实际使用时可以输入 free -k
commands:
  - prefix: free
# templates 是一个模板引擎,可以预留参数,调用时只用输入参数
# name: 调用时接在 Agent 名称后的第一个词
# dir: 命令的工作目录,可选。有的命令不需要工作目录就不填。
# temp: 模板,用的 golang 的模板引擎
# 示例 name:"Hi" temp:"echo I am not %s!"
# 在公众号输入 [Hi 傻瓜] 会收到结果 [I am not 傻瓜!]
templates:
  - name: Hi
    temp: "echo I am not %s!"

修改完配置文件后,用命令重启服务,它们就生效了。

sudo systemctl restart skadi

一些示例

重新部署一个 docker stack, 发送xxx 重启就会重启这个 stack

shortcuts:
    - short: 重启
      # 你的 compose file 的位置
      dir: "/root/swarm/"
      # docker-compose.yml 是你的 compose file 名称, api 是你的 stack 名称
      cmd: "docker stack deploy --prune --with-registry-auth -c docker-compose.yml api"

如果服务器上有多个 stack ,我们可以把配置文件和 stack 做成同名,然后为了使用方便,可以写一个shell,up.sh

docker stack deploy --prune --with-registry-auth -c $1.yml $1

然后用模板功能,最终效果是发送 xxx up api 就会重启 api 这个stack

templates:
    - name: up
      temp: "sh up.sh %s"
      dir: "/root/swarm"

4 - 延迟队列

把 Server饭 当作一个可靠的延迟队列。

为什么需要延迟队列

很多业务场景都要用到延迟队列:

  • 新订单如果未付款在一个小时后自动关闭。
  • 订单发货后15天自动确认收货。
  • 餐厅消费后一个小时请求评价。

类似的还有很多,不一一列举了。

延迟队列的误解

因为叫队列,所以如果项目用了某种队列,第一反应就是去看这种队列是不是支持延迟队列

很不幸,各家队列和云服务商提供的队列,都对延迟队列支持的不怎么好。只有 RabbitMQ 稍微好一点。

为什么会这样呢?因为延迟队列和传统的队列压根是两种东西。想兼容当然不容易了。 传统的队列一般都是先进先出,可以是生产消费模式或者广播订阅模式。更侧重于性能、可靠性、顺序性等方面的改善。

但是延迟队列实际上是一种持久存储的计划任务,它更应该和传统的队列结合使用。Job存储在一个安全可靠的地方,到时间了拿出来放某个队列供消费。

为什么 Server饭 是一个不错的选择

  1. 网上有很多在代码中实现延迟队列的教程,各个语言也有轮子,这个方式是最不推荐的。把信息存在内存当中,难道服务永远不升级重启了?
  2. 用 Redis 当延迟队列,可以使用 zset 或者 过期事件实现。问题是同样的,一般的 redis 没那么可靠,除非你用的有可靠性保障的 Redis 集群。
  3. 自己写一个有独立存储的延迟队列。如果你有这个力气当然是可以的……一般来说延迟队列在总的需求中占比很小,你可能没有那么多的时间预算去写一个服务,然后维护它。
  4. 想找一个类似的云服务,结果这个功能太小了,找不到。

这个时候我们开箱即用的接口就很方便了。

一个例子

我已经在 坚橙艺术 中实际使用了一段时间,分享给大家。

  1. 订单123卖家发货后,调用 延迟任务接口发送15天订单完成 123
  2. 如果买家在收货之后手动点击了确认收货,则系统自动调用订单完成的函数。
  3. 如果卖家在发货一周后着急确认,客服在询问买家确实收货后,在 LetServerRun 公众号发送 订单完成 123
  4. 15天后,Agent 收到当时设定的延迟任务,会再执行一次。这就要求这个订单完成需要判断订单状态,保证自己是幂等的,重复执行也不会出错。