|
|
#### 项目结构
|
|
|
插件内目录src/ios下面有一个Xcode项目和plugin接口。
|
|
|
|
|
|
**Xcode项目TSBlueTherm**
|
|
|
项目内主要有3个target,分别是:
|
|
|
|
|
|
1. `TSBlueTherm`,实现BlueTherm测温仪交互功能的framework。
|
|
|
|
|
|
2. `TSBlueTherm-Universal`,把前者编译成universal库,并且拷贝到项目的src/ios目录下进行发布。
|
|
|
|
|
|
3. `TSBlueThermDemo`,测试用App,App运行framework中的功能。开发者无需把plugin引入到cordova项目中,通过该App可以大致测试和调试framework。
|
|
|
|
|
|
**接口TSBlueThermPlugin.m**
|
|
|
接口部分并不实现具体的功能,接口只是简单调用framework中的功能。
|
|
|
#### 设计理念
|
|
|
项目的关键是,接口不实现具体功能而是通过调用framework提供功能。我们可以把这种设计模式总结成「源码封装抽离」。该模式有以下好处:
|
|
|
1. 方便配置和管理。
|
|
|
相对于「源码封装抽离」,本项目将源码直接放置在plugin之内。后者设计较多的plugin.xml的配置问题,尤其当引入第三方库的时候,如果存在大量的源文件和资源,则plugin.xml的配置将非常繁琐。一旦配置出错的plugin很可能无法正常运作。这将会增加调试的工作量。
|
|
|
「抽离」模式plugin.xml的配置相对稳定,开发以及第三方资源封装在framework内。开发精力集中在framework上,而无需太多关注配置问题。如果有需要快速开发、调试,甚至可以直接替代项目中的framework(如果接口不变),而无需完整发布新的plugin。
|
|
|
|
|
|
2. 方便调试。
|
|
|
Cordova项目引入、更新plugin的操作并不复杂,但相当繁琐。在开发调、试过程频繁操作会相当影响效率。「抽离」模式极大降低plugin的更新引入操作。开发者可以先对framework进行完整的开发、调试,待稳定可靠之后再引入到cordova项目下做完整的环境和系统测试。
|
|
|
另一方面,这种开发方式脱离具体的业务流程,只关注plugin的功能,同样可以提高开发效率。
|
|
|
|
|
|
#### 项目配置
|
|
|
使用BlueTherm SDK需要对info.plist做一些额外的配置:
|
|
|
|
|
|
```
|
|
|
<key>UISupportedExternalAccessoryProtocols</key>
|
|
|
<array>
|
|
|
<string>uk.co.etiltd.bluetherm1</string>
|
|
|
</array>
|
|
|
```
|
|
|
或者在xcode中info.plist添加下面配置
|
|
|
|
|
|
![9F591C88-49B2-4145-99CE-1950B82CCEEE](/uploads/cac8ee139699df99f62801b654a54270/9F591C88-49B2-4145-99CE-1950B82CCEEE.png)
|
|
|
|
|
|
#### JavaScript接口
|
|
|
```
|
|
|
module.exports = {
|
|
|
takeTemp: function (success, error) {
|
|
|
exec(success, error, "blue-therm", "takeTemp", []);
|
|
|
},
|
|
|
stopTakeTemp: function () {
|
|
|
exec(null, null, "blue-therm", "stopTakeTemp", []);
|
|
|
},
|
|
|
getBatteryLevel: function (success, error) {
|
|
|
exec(success, error, "blue-therm", "getBatteryLevel", []);
|
|
|
}
|
|
|
};
|
|
|
```
|
|
|
|
|
|
#### 兼容情况
|
|
|
过往项目,例如`kudu-routines`,`yum-routines`,也使用到BlueTherm插件`com.myself.blueTherm`。由于有多个版本,因此插件的情况不能一概而论,但基本都类似。
|
|
|
|
|
|
为了兼容以往项目TSBlueTherm做了最大程度的兼容,正常情况开发者能够在不修改代码的情况下进行替换。
|
|
|
然而在逻辑方面新旧插件有着比较大的差异,下面只列出一些关键性的兼容问题。
|
|
|
|
|
|
**插件id**
|
|
|
|
|
|
本插件对插件id进行了修改,id从之前的`com.myself.blueTherm`改为`tts-plugin-blue-therm`。开发者如果使用本插件,必须先移除旧插件。
|
|
|
|
|
|
**库冲突**
|
|
|
由于两个插件使用的是同一个SDK库,本插件已经对该库进行封装。如果旧项目引入了BlueTherm的SDK库,开发者将之移除,否则可能造成冲突。
|
|
|
|
|
|
**旧插件的接口缺陷**
|
|
|
|
|
|
旧插件设计之初并未结合BlueTherm设备的实际运作方式进行开发,造成旧插件的接口实际并不切合设备的使用。考虑到已有项目的兼容问题,本插件在当下版本(1.0.0)仍然沿用过去的接口,但内部的运作大有不同。下面举两个例子:
|
|
|
|
|
|
- `getBatteryLevel`接口
|
|
|
旧插件误认为电池信息是直接访问,所以直接调用`[ProbeProperties batteryLevel]`以获取数据。而事实上,SDK需要先链接设备,然后向设备请求数据包,返回的数据包包含设备状态,电池情况,温度等。访问电池信息的逻辑其实与获取温度一样。实现方面插件应该把SDK的数据包转换成json,通过success回调返回给前端。事实上更合理的接口类似:
|
|
|
```
|
|
|
readData: function (success, error) {
|
|
|
...
|
|
|
}
|
|
|
```
|
|
|
|
|
|
|
|
|
- 异常处理
|
|
|
旧接口并没有实际使用error回调进行异常处理。在实际的运行中,旧插件只对部分异常通过success回调传送回前端(通过不同的信息内容标识异常)。事实上旧插件并没有正确处理交互中的异常。正因如此插件的运作异常可能因为没有得到有效处理导致App的崩溃。此外,因为异常没有得到合适处理,插件内部的运作出现问题的时候,APP也很难得知情况。
|
|
|
新插件并没有修改接口,但在内部做了必要的处理。尽可能确保插件的异常不至于造成App崩溃。
|
|
|
|
|
|
接口方面还有其他一些问题,这里不再一一列举。这里只是作为一个备忘,在资源允许的情况下,未来的版本应该对接口做一些合理的修改。 |