这是一个基于 深圳实验学校 的网上订餐系统开发的 API。开发者可以省略原先冗杂而无法避免的传值代码、摆脱原本繁琐而不易理解的操作逻辑,通过封装好的 szsy-canteen API 更为简洁的接口实现网上订餐交互。

szsy-canteen API 使用 Golang 编写而成,保证其效率和性能。API 适用于对学校网上订餐系统客户端的二次开发 💗

English | 简体中文 | 正體中文

为何使用

简而言之,逻辑简单、省流高效。

由于最原始的初衷是降低学校网上订餐系统的移动端开发成本,在 API 的设计上,将 优化逻辑节省流量 作为重要的考量指标。这里举个例子。API 提供了直接获取「可订餐日期」列表的接口,就避免了客户端「获取所有日期包括不必要的」(浪费流量)和「判断日期是否可以订餐」(复杂逻辑)等操作的开销。

当然,因为开发时间比较有限和个人能力实属不足,API 的部分设计比较粗糙。欢迎新的 contribution,或者你有新的关于订餐服务的实现,希望你可以让我知道,我会在 README 中更新你的推广 link 😄

如何配置

如果你是 64位 Windows 或 Linux 上的开发者,可以直接下载各自系统的预编译包,双击执行后 API 将默认开启在本地机器 2018 端口上。

如果你试图自己编译运行,需要安装配置 Golang 的开发环境并下载完整的源码文件进行编译。可以执行以下命令生成该平台下的可执行文件。

1
go build main.go

简单上手

szsy-canteen API 提供了以下接口:

  • login :登录网上订餐系统获取基本信息并得到进一步操作所需的口令

  • dates :获取所有当前可以订餐(即未超过订餐时间)的日期列表

  • menu :获取指定日期的菜单详情以及订餐情况

  • order :提交指定日期的订餐请求

  • logout :登出网上订餐系统

默认配置中 API 的 URL 应是

1
http://localhost:2018/

登录网上订餐系统

将 一卡通用户名 和 使用 MD5 算法加密后的密码 写入 JSON 字段,以下是一个例子

1
2
3
4
{
    "账号":"2152000",
    "密码":"80d9ba95cce518bf747bda3bc98faef8"
}

考虑到安全的因素,设计上决定把用 MD5 加密密码的工作交给请求端,即这里你需要自行 MD5 加密密码字符串并把加密后的密码字符串提供给 密码 一项。

使用 POST 方法提交到 URL

1
http://localhost:2018/login

API 端将返回一个如下 JSON

1
2
3
4
5
{
    "姓名":"XXX",
    "余额":"666.66元",
    "口令":"6E19822908B2FEA56F7BF,bnfh4fsigr5z04ebdeo"
}

真实返回的 口令 一值将会比示例中展现的长得多,这里为了排版做了精简。

获取可订日期列表

将登录时获得的口令写入 JSON 字段

1
2
3
{
    "口令":"6E19822908B2FEA56F7BF,bnfh4fsigr5z04ebdeo"
}

使用 POST 方法提交到 URL

1
http://localhost:2018/dates

你将会得到返回 JSON 如下

1
2
3
4
5
{
    "可订日期":["2018-06-26","2018-06-27","2018-06-28","2018-06-29",
    "2018-07-02","2018-07-03","2018-07-04","2018-07-05",
    "2018-07-06","2018-07-09","2018-07-10","2018-07-13"]
} 

返回的日期列表将会包含 当前月与下个月的可订餐日期,即 API 也会尝试请求到下个月的菜单,不会遗漏下个月未超出订餐时间的菜单。学校更新菜单最多一次性更新两个月的份量。所以你可以放心把这份工作交给 szsy-canteen API 操心。

获取指定日期菜单

同样地,将登录时获得的口令写入 JSON 字段

1
2
3
{
    "口令":"6E19822908B2FEA56F7BF,bnfh4fsigr5z04ebdeo"
}

使用 POST 方法提交到含有「指定日期」参数的 URL

1
http://localhost:2018/menu/?date=2018-07-06

你可以得到返回如下

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
{
    "不订餐":null,
    "早餐":
        [
            ["0","套餐","早餐套餐","5.00","0"],
            ["1","牛奶","学生奶","2.04","0"],
            ["2","蛋类","五香鸡蛋","1.40","0"],
            ["3","点心","巧克力面包","1.40","0"],
            ["4","点心","玉米酥","1.40","0"],
            ["5","点心","南瓜米糕","1.40","0"],
            ["6","点心","鲜肉包","1.40","0"],
            ["7","粉面类","水饺","1.60","0"]
        ],
    "午餐":
        [
            ["0","套餐","午餐套餐","12.00","0"],
            ["1","水果","杨桃","1.30","0"],
            ["2","菜肴","蒜茸炒黄芽白","1.80","0"],
            ["3","菜肴","炒小瓜片","1.80","0"],
            ["4","菜肴","剁椒蒸鱼(微辣)","4.40","0"],
            ["5","菜肴","肉末豆角","3.60","0"],
            ["6","菜肴","土豆烧肉","5.60","0"],
            ["7","菜肴","香辣翅根2个","6.70","0"]
        ],
    "晚餐":null
}

每一道菜包含的信息点顺序排列如下

1
["编号","类型","菜名","单价","订餐个数"]

不订餐 的这一项一般都应为 null 值,如示例。当然,如果早餐午餐 选择了不订餐,那么 不订餐 的值应为

1
"不订餐":["早餐","午餐"]

示例中 2018年7月10日 是周五,所以晚餐的菜单缺失,即 晚餐 的值为 null

提交订餐信息请求

将登录时获得的口令和早午晚三餐的订餐信息写入 JSON 字段

1
2
3
4
5
6
{
    "口令":"6E19822908B2FEA56F7BF,bnfh4fsigr5z04ebdeo",
    "早餐":"套餐",
    "午餐":"0,0,2,0,0,1,0,1",
    "晚餐":"不订餐"
}

订餐信息有三种格式可以填入,示例给出了所有情况

  1. 套餐(即等价于「1,0,0,0,0,0,0,0」)

  2. 不订餐(即等价于勾选上「不订餐」选项)

  3. 给出以逗号为分隔符的八道菜的订餐个数

所以,本例中这位同学的早餐选择了套餐随缘,午餐选择 2份蒜茸炒黄芽白、1份肉末豆角 和 1份香辣翅根2个,晚餐选择了不订餐。

遇到周五晚上,即晚餐菜单缺失的情况,应给予 晚餐 这一项 null 值,而非省略 晚餐 此项。此处为了演示 不订餐 字段,晚餐 暂且填入该字段,但实际上应该是null 😂

你会发现八道菜中第一道菜是 套餐,实际上后面的菜的订餐个数若不为 0 时,套餐 的值无论为何值都会被 0 覆盖。

接着使用 POST 方法提交到含有「指定日期」参数的 URL

1
http://localhost:2018/order/?date=2018-07-10

你可能得到如下几种返回信息

  1. 提交成功(即请求提交成功,订餐信息已写入系统)

  2. 账户异常(即此账户被冻结或有其它异常情况,往往是欠费)

  3. 超过订餐时间(即该日不在允许订餐时间范围内,可通过提交前检查日期是否存在于「可订餐日期」列表内而避免此错误)

  4. 提交失败(客户端网络超时或学校服务器宕机等原因导致)

学校的服务器处理订餐信息所需的时间远超于正常所需时间 😂,所以你往往需要等待几秒才可以得到反馈(实验人应有深刻的体会)不要因此过于频繁地提交订餐信息,你可能会提交失败,更糟的是得到错误的返回信息。

登出网上订餐系统

将登录时获得的口令写入 JSON 字段

1
2
3
{
    "口令":"6E19822908B2FEA56F7BF,bnfh4fsigr5z04ebdeo"
}

使用 POST 方法提交到 URL

1
http://localhost:2018/logout

得到 登出成功 后即可完成登出。

有关口令过期的错误

szsy-canteen API 的错误提示都比较明确易读,但还是要对这条作单独的说明。

如果你在使用口令请求日期列表、获取某日菜单或是提交订餐请求时,得到了 口令错误或过期 的错误提示,这意味着你的口令有可能过期了。这时,你需要做的就是重新 login 以获得新的口令。

关于订多份餐的提示

原则上,学校的网上订餐系统限制每道菜最多选择 3 份,这是网站上的 JavaScript 脚本限制的。然而使用 API 没有这个限制,理论上你可以订超过 3 份的数量。

经过实际测试,5 份以内个数成功率较大,基本可以提交成功,份数过于夸张大的成功率基本为零,会有 提交失败 的错误返回。之前闲着无聊尝试过的提交成功的最大份数为 20 份,对,20份卤鸡腿。

当然,这里不是漏洞。份数达到了 20 份也代表你需要支付 20 份的账单(要不然我也不会在这里堂而皇之地陈述这些)

在这里加这段文字是想提出一个建议:作为开发者的你,在开发客户端的时候,也许可以提供一个可以显性修改份数的入口。毕竟偶尔在「净荤菜」上给自己加点餐也是充满了幸福感的一件事。

致谢

@xlfjn

@GrakePch

感谢以上两位在开发过程中提供的技术上和精神上的支持 💗