nodejs服务端自动生成ios钱包pkpass文件

编程入门 行业动态 更新时间:2024-10-11 07:27:28

nodejs服务端<a href=https://www.elefans.com/category/jswz/34/1766270.html style=自动生成ios钱包pkpass文件"/>

nodejs服务端自动生成ios钱包pkpass文件

该博客是我在原博主发文的基础上新增了一下,因为项目用到了这个ios钱包,就研究了一下,开始还弄了挺久的,第一次写,写得不好,大神请勿见笑

1、什么是PKPass文件?

PKPass 是Apple定义的一套针对商家消费券、优惠券、火车机票等票据格式类文件。包含:图标icon、缩略图thumbnail和logo外最重要的就是pass.json、manifest.json和signature等文件的一个压缩包

2、如何制作PKPass文件?


1)、服务器端制作是比较通用的做法 
这里有一个Java写的开源库: 

Java版本制作PKPass的web service 

2)、本地制作,按照下面的步骤:

1、去苹果开发者网站 
申请Pass Type id,并且生成对应的证书(申请之前需要到钥匙串:从证书颁发机构请求证书) 
2、制作pass.json 
a、准备icon、logo和strip三类图片 
b、 配置pass.json,这里还是强调一下passTypeIdentifier和teamIdentifier,前者就是上面在开发者中心创建的Pass Type ID(”pass.taokatao.mywallet“),后者是对应的团队标识,申请苹果开发者账号时会分配一个唯一的团队标识(可以在苹果开发者中心–查看账户信息中查看”Team ID“)。,其他信息根据实际情况配置。

{

"formatVersion": 1,

"passTypeIdentifier": "passfan.SSTPmon",    //这个是ios申请的

"serialNumber": "sstpserialno0202",         //序列号,这个需要随机生成,涉及到更新

"webServiceURL": "/",

"authenticationToken": "vxwxd7J8AlNNFPS8k0a0FfUFtq0ewzFdc",    //这个地方的token我是默认的为用户登陆的token

"teamIdentifier": "L36C5JJEQ2",      //ios发给你的

"locations": [

{

"longitude": -122.3748889,   //位置坐标

"latitude": 37.6189722

},

{

"longitude": -122.03118,

"latitude": 37.33182

}

],

"barcode": {

"message": "d243ec6e41fa77baed63a502c7bd2d1c",     //用户的id,需唯一

"format": "PKBarcodeFormatQR",

"altText": "会员详情见背面",

"messageEncoding": "iso-8859-1"

},

"organizationName": "产业园",    //钱包上面展示的信息

"description": "产业园会员",

"logoText": "产业园",

"foregroundColor": "rgb(255, 255, 255)",    //页面颜色

"backgroundColor": "rgb(219, 57, 68)",      //会员详情页面颜色

"generic": {

"primaryFields": [       //这里面就根据用户的个人信息,自动变换

{

"key": "name",

"value": "超级管理员"

}

],

"secondaryFields": [

{

"key": "subtitle",

"label": "单位",

"value": "公司总部"

}

],

"auxiliaryFields": [

{

"key": "level",

"label": "职位",

"value": "暂无岗位"

},

{

"key": "favorite",

"label": "所属部门",

"value": "暂无部门"

}

],

"backFields": [

{

"key": "name",

"label": "姓名",

"value": "超级管理员"

},

{

"key": "gender",

"label": "性别",

"value": "女"

},

{

"key": "mobile",

"label": "手机号",

"value": "18888888888"

},

{

"key": "org",

"label": "单位名称",

"value": "公司总部"

},

{

"key": "dept",

"label": "所在部门",

"value": "暂无部门"

},

{

"key": "position",

"label": "岗位",

"value": "暂无岗位"

},

{

"key": "accountType",

"label": "账号类型",

"value": "内部用户"

}

]

}

}


3、创建manifest.json文件,可以通过”openssl sha1 [文件路径]“分别计算出所有文件的哈希值:

            调用服务器脚本生成

{

"pass.json": "b017c82812e88ddbdd3d151f913e65f7c4dedcb1",

"logo.png": "e74c18f82afe65d084bec142da912829de3b81b4",

"logo@2x.png": "9b17e6a5126d553424dd9747ed006c96a09931de",

"icon.png": "e74c18f82afe65d084bec142da912829de3b81b4",

"icon@2x.png": "9b17e6a5126d553424dd9747ed006c96a09931de",

"icon@3x.png": "0b66a2a7404edfc68fca6676290e54313e7e6fd3",

"logo@3x.png": "0b66a2a7404edfc68fca6676290e54313e7e6fd3"

}

4、生成signature文件: 

a.通过前面导入的Pass Type证书(Pass Type ID:pass.taokatao.mywallet)导出个人信息交换(.p12)文件并指定密码(假设密码为123123),保存成”mywallet.p12“(注意是导出证书而不是导出证书下的专用秘钥)。 

b.在钥匙串中找到”Apple Worldwide Developer Relations Certification Authority“证书导出增强保密邮件(.pem),保存成”AWDRCA.pem“。 

c.将.p12证书转化为.pem证书mywallet.pem(需要输入导出时设置的密码123123),输入如下命令: 

openssl pkcs12 -in mywallet.p12 -clcerts -nokeys -out mywallet.pem -passin pass:123123

d.从.p12导出秘钥文件mywalletkey.pem(这里设置密码为123123) 

openssl pkcs12 -in mywallet.p12 -nocerts -out mywalletkey.pem -passin pass:123123 -passout pass:123123

e.根据AWDRCA.pem、mywallet.pem、mywalletkey.pem、manifest.json生成signature文件(按照提示输入mywalletkey.pem导出时设置的密码123123): 

openssl smime -binary -sign -certfile AWDRCA.pem -signer mywallet.pem -inkey mywalletkey.pem -in manifest.json -out signature -outform DER

5.将icon.png、icon@2x.png、icon@3x.png、logo.png、logo@2x.png、logo@3x.png、pass.json、manifest.json、signature压缩成pass包(这里命名为”mywallet.pkpass“)。 

zip -r mywallet.pkpass manifest.json pass.json signature logo.png logo@2x.png icon.png icon@2x.png strip.png strip@2x.png

服务端调用脚本自动生成pkpass文件的接口

 1、准备好这些文件,也就是上面步骤生成的和创建的文件,然后上传到服务器里面,我这边使用的是winscp,然后创建一个名为sha1.sh的脚本:openssl sha1 pass.json logo.png logo@2x.png icon.png icon@2x.png icon@3x.png logo@3x.png (因为登录用户的不同,所以用户的logo,icon,pass.json等会变化,所以需要脚本来自动生成sha1值)

2、然后再创建一个名为pkpass.sh的脚本:openssl smime -binary -sign -certfile AWDRCA.pem -signer sstp.pem -inkey sstp_key.pem -in manifest.json -out signature -outform DER -passin pass:111111 (111111为生成signature文件的密码)
zip -r ../../myhome/mypage/creatpkpass/sstp.pkpass manifest.json pass.json ./signature logo.png logo@2x.png icon.png icon@2x.png icon@3x.png logo@3x.png (这个脚本的作用就是自动生成signature文件和pkpass文件,并且指定的放到某一个目录下面)

3、服务端接口

 

//正则替换 把调用服务器脚本返回的sha1值改成json字符串格式

function toJson(data) {

let _data = {};

data.split("\n").filter(line => !!line).map(line => {

      return line.split(/\s*=\s*/);

}).forEach(item => {

      _data[item[0].match(/SHA1\((.+)\)/i)[1]] = item[1];

});

return JSON.stringify(_data);

}

//给ios钱包生成 .pkpass文件

router.post('/front/pkpass',function(req, res)

{

//获取登录用户信息

let userToken = req.loginUser.token;

let user = req.loginUser._id;

let trueName = req.loginUser.trueName || null;

let organization = commonService.isEmpty(req.loginUseranization) ? '暂无单位' : req.loginUseranization.name;

let jobTitle = commonService.isEmpty(req.loginUser.jobTitle) ? '暂无岗位' : req.loginUser.jobTitle.name;

let sex = req.loginUser.sex;

let mobile = req.loginUser.mobile;

let type = req.loginUser.type;

let query = {'_id':user};

let nowTime = commonService.getDateTime();

let serialNumber = 'sstp' + commonService.getRandomChar(6) + commonService.getTimeStamp();

// sessionService.set(mobile,serialNumber,60);

 

if(sex == 1){

      sex = '男';

}else{

      sex = '女';

}

if(type == 0){

      type = '内部用户';

}else if(type == 1){

      type = '园区用户';

}else{

      type = '普通用户';

}

let data = fs.readFileSync('./pass.json', 'utf8');//读取json文件

let obj = JSON.parse(data);//转为json对象

 

userService.getItem(query,null,function(err,result){   //这个地方是版本序列号,不需要的请忽略

      let serialNumber2 = result.serialNumber || null;

      let oldSerialNumber = result.oldSerialNumber || [];

      if(serialNumber2 != null){

            oldSerialNumber.push(serialNumber2);

            let fileds = {'oldSerialNumber':oldSerialNumber};

            userService.update(query,fileds,function(){});

      }

});

 

//给对象重新赋值

obj.serialNumber = serialNumber;

obj.barcode.message = userToken;

obj.generic.primaryFields[0].value = trueName;

obj.generic.secondaryFields[0].value = organization;

obj.generic.auxiliaryFields[0].value = jobTitle;

obj.generic.backFields[0].value = trueName;

obj.generic.backFields[1].value = sex;

obj.generic.backFields[2].value = mobile;

obj.generic.backFields[3].value = organization;

obj.generic.backFields[5].value = jobTitle;

obj.generic.backFields[6].value = type;

 

let updateFileds = {'serialNumber':serialNumber};

userService.update(query,updateFileds,function(){});

 

//再转为json字符串,并写回到pass.json文件

let lastData = JSON.stringify(obj);

fs.writeFileSync('./pass.json',lastData);

//调用服务器的sha1.sh脚本

process.exec('./sha1.sh',function (error, stdout, stderr) {

      if (error !== null) {

            console.log('exec error: ' + error);

      }

      var str = toJson(stdout);  //调用上面的曾泽替换方法把调用脚本返回的数据转换成json格式,再写回manifest.json文件

      fs.writeFileSync('./manifest.json',str);

 

      //调用服务器脚本

      process.exec('./pkpass.sh',function (error, stdout, stderr) {

            if (error !== null) {

            res.send(commonService.sendFail(error));

      }

      //把生成的pkpass文件以手机号+序列号的方式重命名,方便区分

      fs.rename('../../myhome/mypage/creatpkpass/sstp.pkpass', '../../myhome/mypage/creatpkpass/' + mobile + '_' + serialNumber + '.pkpass', function(err){

            if(err){

                  throw err;

            }

            res.send(commonService.sendSuccess(serialNumber));

            });

      });

});

 

});

调用了这个接口之后,会再服务器里面生成一个手机号+序列号.pkpass文件,然后把这个文件的下载链接发给ios开发人员,让ios开发人员在app用户需要生成钱包的时候调用这个接口就可以了,可以吧生成的pkpass文件下载下来发送到手机里面,如果打开能弹出下面的页面,就制作成功了

这个是我服务器生成的pkpass文件

这个是打开文件弹出来的会员钱包,信息就是该用户的基本信息 

 

这个是会员详情页面,这样就做好了

 

iOS端如何加载PKPass文件?


1、Xcode新建一个工程,Bundle Identifier中命名一个App ID 
2、选择目标Target,点击“Capabilities”标签,打开Wallet开关。此时需要勾选:Allow all team pass types.但是你看到的下面:“Add the wallet feature to your App ID”前面是红色的。不要紧这是因为你还没有创建App ID,看下面 
3、进入Apple 开发者网站,新建一个App ID,跟第一步的App ID一致,再来看看这个红色提示就消失了,正常的对勾形式出现 
4、进入目标Target,General标签,让Xcode自动为我们管理证书 
5、把上面制作的PKPass文件拖到项目中 
6、编码读取并显示。so easy!

#import "ViewController.h"
#import <PassKit/PassKit.h>

@interface ViewController ()<PKAddPassesViewControllerDelegate>

@end

@implementation ViewController

- (void)viewDidLoad {
    [super viewDidLoad];
    // Do any additional setup after loading the view, typically from a nib.

    PKAddPassButton *pkAddBtn = [[PKAddPassButton alloc] initWithAddPassButtonStyle:PKAddPassButtonStyleBlack];
    pkAddBtn.titleLabel.font = [UIFont systemFontOfSize:12];
    pkAddBtn.frame = CGRectMake(100, 100, 220, 40);
    [self.view addSubview:pkAddBtn];


    [pkAddBtn addTarget:self action:@selector(btnClick:) forControlEvents:UIControlEventTouchUpInside];

}

- (void)btnClick:(PKAddPassButton *)button {
    NSString *passPath=[[NSBundle mainBundle] pathForResource:@"mywallet" ofType:@"pkpass"];
    NSData *passData = [[NSData alloc] initWithContentsOfFile:passPath];
    NSError *error = nil;
    PKPass *pass = [[PKPass alloc] initWithData:passData error:&error];
    if (error) {
        NSLog(@"创建Pass过程中发生错误,错误信息:%@",error.localizedDescription);
    };
    PKAddPassesViewController *vc = [[PKAddPassesViewController alloc] initWithPass:pass];
    vc.delegate = self;

    [self presentViewController:vc animated:true completion:nil];

}

-(void)addPassesViewControllerDidFinish:(PKAddPassesViewController *)controller{
    NSLog(@"add pass finished.");
    [self dismissViewControllerAnimated:true completion:nil];
}
--------------------- 
来源:CSDN 
原文: 

该博客是我在原博主发文的基础上新增了一下,因为项目用到了这个ios钱包,就研究了一下,开始还弄了挺久的
 

更多推荐

nodejs服务端自动生成ios钱包pkpass文件

本文发布于:2024-02-13 16:30:52,感谢您对本站的认可!
本文链接:https://www.elefans.com/category/jswz/34/1759573.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
本文标签:自动生成   服务端   钱包   文件   nodejs

发布评论

评论列表 (有 0 条评论)
草根站长

>www.elefans.com

编程频道|电子爱好者 - 技术资讯及电子产品介绍!