我正在参与「启航计划」


在 WWDC 2022,Apple 推出了全新的气候数据服务 WeatherKit ,供给了丰富的气候数据供开发者运用。

只要你现已购买了Apple的开发者账号,就可以运用它。

和大多数气候服务相同,WeatherKit 也是按央求次数收费的,价格如下:

  • 50 万次调用/月:会员资格已包含
  • 100 万次调用/月:49.99 美元
  • 200 万次调用/月:99.99 美元
  • 500 万次调用/月:249.99 美元
  • 1,000 万次调用/月:499.99 美元
  • 2,000 万次调用/月:999.99 美元

概况见 Apple官网:初步运用 WeatherKit – Apple Developer

可以看到,开发者默许每月有 50万次调用的额度可以运用,不用额定付费,只有超越这个数量才需求其他付费。

苹果供给了两种方法调用 WeatherKit:

  • 系统原生库 WeatherKit(仅支撑Apple途径,iOS 16.0+,iPadOS 16.0+,macOS 13.0+,Mac Catalyst 16.0+,tvOS 16.0+,watchOS 9.0+
  • Weather KIT REST API(全途径支撑)

根据苹果一贯的习气,WeatherKit系统库从 iOS 16 初步支撑,并不支撑老版其他系统。而且只支撑 Swift,不支撑OC。

所以,在现阶段,关于要支撑老版别系统的APP并没有实用价值。

但是 REST API 就不相同了,由于它是网络央求接口,它可以支撑全部版其他系统,甚至非苹果生态的 web 和 Windows等途径也可以运用。

所以,我们今日来看看,怎么初步运用WeatherKit REST API。

一、初步之前

1、创建APP ID 并添加WeatherKit 权限

初步之前需求一些准备工作,翻开苹果的开发者网站。在 Certificates, Identifiers, and Profiles 页面选择 Identifiers,创建一个新 App ID ,假如你不需求创建新的,你也可以选择已有的 APP ID。然后翻开后在 App Services 一栏勾选 WeatherKit 选项。或许需求等候30分钟让苹果同步权限之后才可以进行API央求。

Apple WeatherKit REST API 上手

这儿需求记载一下 AppID PrefixBundle ID 以及你账户的 Team ID。等一下会用到。

2、创建WeatherKit 的密钥

在 Certificates, Identifiers, and Profiles 页面选择 Keys 选项,然后新建一个Key。勾选WeatherKit 选项。

Apple WeatherKit REST API 上手

系统会提示你下载一个密钥文件,这是你调用WeatherKit服务的签名用的私钥,只能下载一次,一定要妥善保管到安全的位置,不能走漏。

然后记载一下 生成的Key的 ID。稍后会用到。

Apple WeatherKit REST API 上手

二、初步Weather Kit REST API之旅

Weather Kit REST API 运用标准的 JWTJSON Web Token )进行授权,首要我们要生成授权的 JWT,一般这一步应该在后端服务器上完成。JWT 标准文档:JWT specification

简单来说,JWT 是一个字符串,由三段base64编码的字符串组成,用英文的句号“.”分隔。

例如: eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c

榜首段和第二段都是JSON经过urlBase64编码后的字符串,这儿运用的base64和一般的有一点差异,是专门为url传递优化过的,详细改变如下:

1、去掉了结束的等号“=”

2、将加号“+”替换成短线“-”

3、将斜杠“/”替换成下划线“_”

榜首段称为头部(Header),记载了一些JWT的格式和签名方法等,详细可以参看 JWT标准文档。

第二段称为负载(Payload),是JWT的主体部分,记载了JWT的要害信息。

第三段是前两段的数字签名,是为了避免JWT被假造和篡改。

WeatherKit 对前两段的内容和签名方法都有要求。

1、Header部分

{
    "alg": "ES256",
    "kid": "ABC123DEFG",
    "id": "DEF123GHIJ.com.example.weatherkit-client"
}

其间:

alg :是签名方法,Apple要求,有必要为“ES256”,它标明我们应该运用 SHA256算法对内容进行哈希后运用P-256曲线的椭圆曲线数字签名算法(ECDSA)对其进行签名。

详细签名方法后门再阐明。

kid :是刚才榜首步中我们创建的Key的ID。

id :是Team ID和bundle ID 的拼接。

Header的json结构完成后运用 urlBase64对其进行编码,得到了JWT的榜首部分:

eyJhbGciOiJFUzI1NiIsImtpZCI6IkFCQzEyM0RFRkciLCJpZCI6IkRFRjEyM0dISUouY29tLmV4YW1wbGUud2VhdGhlcmtpdC1jbGllbnQifQ

2、Payload部分

{
    "iss": "DEF123GHIJ",
    "iat": 1437179036,
    "exp": 1493298100,
    "sub": "com.example.weatherkit-client"
}

iss:JWT签发者,值为你的Team ID。

iat:JWT签发时间,Unix时间戳,单位秒,整数。

exp:JWT过期时间,Unix时间戳,单位秒,整数。

sub:你app的 bundle ID

Payload的json结构完成后相同运用 urlBase64对其进行编码,得到了JWT的第二部分:

eyJpc3MiOiJERUYxMjNHSElKIiwiaWF0IjoxNDM3MTc5MDM2LCJleHAiOjE0OTMyOTgxMDAsInN1YiI6ImNvbS5leGFtcGxlLndlYXRoZXJraXQtY2xpZW50In0

3、签名

下一步,将header和payload的base64字符串用“.”拼接在一起,然后对拼接后的字符串进行 ECDSA 签名。

拼接后的字符串为:eyJhbGciOiJFUzI1NiIsImtpZCI6IkFCQzEyM0RFRkciLCJpZCI6IkRFRjEyM0dISUouY29tLmV4YW1wbGUud2VhdGhlcmtpdC1jbGllbnQifQ.eyJpc3MiOiJERUYxMjNHSElKIiwiaWF0IjoxNDM3MTc5MDM2LCJleHAiOjE0OTMyOTgxMDAsInN1YiI6ImNvbS5leGFtcGxlLndlYXRoZXJraXQtY2xpZW50In0

JWT的签发应该放在后端进行,所以这儿以 go 语言为示例:

package main
import (
	"crypto/ecdsa"
	"crypto/rand"
	"crypto/sha256"
	"crypto/x509"
	"encoding/base64"
	"encoding/pem"
	"fmt"
	"os"
)
func main() {
	sign := EccSignature("eyJhbGciOiJFUzI1NiIsImtpZCI6IkFCQzEyM0RFRkciLCJpZCI6IkRFRjEyM0dISUouY29tLmV4YW1wbGUud2VhdGhlcmtpdC1jbGllbnQifQ.eyJpc3MiOiJERUYxMjNHSElKIiwiaWF0IjoxNDM3MTc5MDM2LCJleHAiOjE0OTMyOTgxMDAsInN1YiI6ImNvbS5leGFtcGxlLndlYXRoZXJraXQtY2xpZW50In0",
		"./test.p8")
	fmt.Printf("sign: %s", sign)
}
// textToSign 等候签名的字符串,privateKeyPath 私钥文件的途径
// return: 签名
func EccSignature(textToSign string, privateKeyPath string) (sign string) {
	//------1.获取私匙------
	//Step1:翻开文件获取原始私匙
	file, err := os.Open(privateKeyPath)
	if err != nil {
		panic(err)
	}
	defer file.Close()
	fileinfo, err := file.Stat()
	if err != nil {
		panic(err)
	}
	buf := make([]byte, fileinfo.Size())
	file.Read(buf)
	//Step2:私匙的反pem编码化
	block, _ := pem.Decode(buf)
	//Step3:私匙的反x509序列化, 关于不同格式的私钥文件可以能需求运用不同的 Parse方法,关于WeatherKit供给的.p8文件,这儿运用ParsePKCS8PrivateKey
	key, err := x509.ParsePKCS8PrivateKey(block.Bytes)
	if err != nil {
		panic(err)
	}
	// 转化类型
	privKey := key.(*ecdsa.PrivateKey)
	//------求取明文的散列值------
	//Step1:创建根据sha256哈希函数的hash接口
	myHash := sha256.New()
	//Step2:写入数据
	myHash.Write([]byte(textToSign))
	//Step:求出明文的散列值
	hashText := myHash.Sum(nil)
	//------对明文的散列值进行数字签名
	r, s, err := ecdsa.Sign(rand.Reader, privKey, hashText)
	if err != nil {
		panic(err)
	}
	//Step2:得到 r和s 的字节编码
	rText := r.Bytes()
	if err != nil {
		panic(err)
	}
	sText := s.Bytes()
	if err != nil {
		panic(err)
	}
	// 运用 r||s 格式输出
	signBytes := append(rText, sText...)
	// 编码成 base64
	sign = base64.RawURLEncoding.EncodeToString(signBytes)
	return sign
}

例如得到签名字符串:f2SAjBpBGyidryrlGyVaso2yLPRufYULjdhI0zcqxB07iN9OI9rvQaHo1xxoTfTD9A6DVpb96sE8leGyTo0dYg

将签名后得到的base64字符串相同运用“.”拼接在刚才的字符串后门,就完成了JWT的签发。

得到毕竟的JWT:

eyJhbGciOiJFUzI1NiIsImtpZCI6IkFCQzEyM0RFRkciLCJpZCI6IkRFRjEyM0dISUouY29tLmV4YW1wbGUud2VhdGhlcmtpdC1jbGllbnQifQ.eyJpc3MiOiJERUYxMjNHSElKIiwiaWF0IjoxNDM3MTc5MDM2LCJleHAiOjE0OTMyOTgxMDAsInN1YiI6ImNvbS5leGFtcGxlLndlYXRoZXJraXQtY2xpZW50In0.f2SAjBpBGyidryrlGyVaso2yLPRufYULjdhI0zcqxB07iN9OI9rvQaHo1xxoTfTD9A6DVpb96sE8leGyTo0dYg

毕竟得到的JWT格式应该是header.payload.sign这样的三段结构,你可在 JWT.io 中选择ES256然后运用他的证书进行签名后对自己的签名方法进行验证(注意:为了安全起见,请不要将自己的私钥随便复制到网页中)。

将它回来给APP或许前端等需求央求WeatherKit REST API 的地方。

4、主张央求

总算,经过前面的准备,我们现已具有了央求Weather Kit REST API的全部前提条件。

主张央求很简单,就是正常的GET央求,仅仅需求在HTTP HEADER中参加一个字段:

Authorization: Bearer [developer token]

将 [developer token] 替换为你签发的 JWT。

然后根据Weather Kit REST API 文档所描绘的途径和参数主张央求,就能正常得到气候数据了。

这儿以Postman为例

在 Authorization一栏选择 Bearer Token 将JWT填入右边的Token输入框就可以主动添加到Header中。

你也可以自己手动在 Header参数中添加 Authorization 字段。

Apple WeatherKit REST API 上手

主张央求:

Apple WeatherKit REST API 上手

三、最终

个人 感觉WeatherKit REST API仍是很不错的,不需求额定付费就能有50万次每月的访问量,关于小体量的个人开发者完全够用了。

还有一点值得注意的是,依照苹果的要求,假如你运用了WeatherKit,你应该在APP中标明数据来历:

Apple WeatherKit REST API 上手

Apple WeatherKit REST API 上手


参看:

  • 官方接口文档:Weather Kit REST API

  • WWDC 2022 WeatherKit 视频: Meet WeatherKit – WWDC22 – Videos – Apple Developer

  • 官方中文简介:初步运用 WeatherKit – Apple Developer

  • JWT 官方标准: JWT specification

  • JWT 验证东西:JWT.io