Prowered By Edwon Lim
- 新浪微博粉丝服务私信管理工具,用于认证用户(蓝V,橙V)的自主服务,
- 详见 http://open.weibo.com/wiki/粉丝服务开发模式指南
- 从0.5.0版本开始,为完整的稳定版本。
- 0.6版本增加转发监听
- 0.7版本增加分词以及更详细文档
- 0.7.2 整合Util
- 0.8版本增加了整合微信公共账号后台的功能(无缝从微信迁移到微博)
- 0.8.1 支持把模拟接口放到BAE上(修复文件的本地缓存导致的错误)
- 消息自动回复:回复内容包括文本消息、媒体Card、包含图片的消息、包含地理位置的消息。
- 事件自动回复:关注和取消关注时,自动发送私信。
- 目录机制:加入目录规则,可根据目录的不同,回复不同的消息,对未处理的消息进行分词后匹配。
- 留言箱:用户可以给不同的对象留言,例如投诉、询问,支持将留言转发至私信,邮件以及URL提交。
- 活动事件:通过私信进行活动,如抽奖和秒杀,并将结果制成Excel。
- 客服系统:通过私信转发,实现一个账号,多人接入的客服系统,一个大V账号可以接多个客服(微博账号),用户与大V账号的私信会被转发到客服账号。
支持二维码生成、邮件功能、上传功能、发微博、分词等。
用npm
安装:
npm install weibo-pm
require
引入
var pm = require("weibo-pm");
初始化模块 : 用户名,用户id,用户密码,在粉丝服务器管理平台中绑定的appkey (此用户要对APPKEY授权)
pm.init(username, uid, password, appkey);
组件:pm.listener
监听所有消息
pm.listener.on(function(msg) {
// 处理消息
});
监听事件消息(关注和取消关注)
pm.listener.onEvent(function(msg) {
// 处理消息
});
监听私信消息(包括文本,图片,地理位置,语音等)
pm.listener.onMessage(function(msg) {
// 处理消息
});
监听@消息 (需要申请高级权限)
pm.listener.onMention(function(msg) {
// 处理消息
});
启动监听(每4分钟会自动重新建立HTTP长连接(文档上要求的,为了减少服务器压力))
pm.listener.start();
组件:pm.reply
需要回复的消息的id,类型和数据,详细参看文档 (每条消息最多只可被回复 3 次)
pm.reply(msgId, type, data, function(rs) {
// 处理结果
});
文档:http://open.weibo.com/wiki/2/messages/reply
组件:pm.send
用户id,类型和数据,详细参看文档 (只可给粉丝发送消息)
pm.send(uid, type, data, function(rs) {
// 处理结果
});
文档:http://open.weibo.com/wiki/2/messages/send
给订阅用户
推送消息 (此接口还没开放,开放后,会及时更新)
组件:pm.Util.OpenAPI
可以通过此接口,调用微博开放平台的接口,详细参看文档 (暂不支持Post提交文件)
// GET 请求
pm.Util.OpenAPI.get("users/show", "uid=1908736117", function(data) {
// 处返回理数据
});
// POST 请求
pm.Util.OpenAPI.post("statuses/update", "status=" + encodeURIComponent("这是一条测试微博"), function(data) {
// 处返回理数据
});
组件:pm.Util.Upload
可以通过此接口,上传文件到微盘
pm.Util.Upload(options, function(data) {
// 处理返回数据,返回数据中包含fid, vfid, tovfid及几张缩略图的地址。
});
options
参数如下:
toUid
: 对方的用户id,必选,否则对方看不到fid
: 文件的id(微盘) 可选 自动下载后再上传filePath
: 文件的路径 可选url
: 文件的网络地址 可选 自动下载后再上传qrCode
: 二维码包含的信息 可选 先生成二维码,再上传
fid
, filePath
, url
, qrCode
选择其一。
组件:pm.Util.Status
可以通过此接口,发布微博
pm.Util.Stauts(options, function(data) {
// 平台标准返回
});
options
参数如下:
text
: 微博内容,必选pic
: 图片路径 可选 (暂时仅支持本地图片,以后会拓展)visible
: 可见度 可选
组件:pm.Util.Base62
对微博的ID进行转换
pm.Util.Base62.encode(mid);
pm.Util.Base62.decode(id);
微博的ID为mid
,微博的实际路径为http://weibo.com/用户id/base62的微博id
。
组件:pm.Util.Debug
- 打开日志输出
pm.Util.Debug.open()
- 日志输出
pm.Util.Debug.log(......)
组件:pm.Message
在每次回复和发送私信的过程中,都可以创建一个消息实体
var message = new pm.Message();
设置需要回复的消息的id或者用户的id (两者必选其一)
message.setId("msg id");
message.setUid("user id");
设置文本信息,将发出文本消息
message.setText("message text");
添加图文信息,将发出图文消息,展示为媒体Card
message.addArticle("title", "summary", "image", "url");
设置地理位置,将发出地理位置的消息
message.setPosition("longitude", "latitude");
设置图片(上传所得的id),将发出带有图片的消息
message.setImage(vfid, tovfid);
设置图片路径,将发出带有图片的消息
message.setImagePath("/path/to/file");
设置图片网络路径,将发出带有图片的消息
message.setImageUrl("http://path/to/file");
设置图片微盘id,将发出带有图片的消息
message.setImageId(id);
设置二维码信息,将发出带有图片的消息
message.setQrCode("This is \"QRCode Info\".");
成功回调
message.success(function(rs) {
// 处理成功结果
});
失败错误回调
message.error(function(rs) {
// 处理失败结果
});
开始发送
message.send();
简单示例
new Message()
.setUid("1908736117")
.setText("Hello World!")
.success(function(rs){alert("success")})
.error(function(rs){alert("error")})
.send();
组件:pm.MentionManager
(需要申请前文所说的Mention权限)
pm.MentionManager.start();
// 微博的id 监听函数
pm.MentionManager.addRepostListener(statusId, function(user) {
// 返回的user.uid是用户的id
});
pm.MentionManager.removeRepostListener(statusId);
// 微博的id 监听函数
pm.MentionManager.addCommentListener(statusId, function(user) {
// 返回的user.uid是用户的id
});
pm.MentionManager.removeCommentListener(statusId);
pm.ReplyManager.reset();
组件:pm.ReplyManager
pm.ReplyManager.start();
启动后,基本API Listener会失效。(基本API Listener不是队列是单个绑定)
目录配置信息:
items
: 目录(功能)及进入目录后,提示的信息(下面的配置中js
,css
,html
对应的是目录,而咨询
,投诉
,反馈
,客服
则是对应的功能,将在后面具体讲解)hotKey
: 关键词,用户发送关键词,会回复目录帮助信息helpText
: 目录帮助信息backText
: 退出目录返回的信息backKey
: 退出目录的关键词segment
: 是否对未匹配的内容分词后,再匹配目录名segmentTip
: 匹配后回复的提示信息timeout
: 自动退出目录的等待时间,单位是秒 300表示5分钟没有消息,自动退出目录到根目录。
pm.ReplyManager.openFloor({
"items": {
"js": "欢迎来到js脚本目录!发送 1 、 2 、 3 查看相应内容。",
"css": "欢迎来到css样式目录!发送 1 、 2 、 3 查看相应内容。",
"html": "欢迎来到html页面目录!发送 1 、 2 、 3 查看相应内容。",
"咨询": "请输入您需要咨询的问题。",
"投诉": "请输入您需要投诉的问题。",
"反馈": "请输入您需要反馈的问题。",
"客服": null
},
"hotKey": ["menu", "菜单"],
"helpText": "欢迎您的访问:\n请发送\"js\",\"css\",\"html\"进入相应目录,输入\"0\"退出相应目录;\n发送`咨询`,`投诉`,`反馈`,`客服`进入相应功能。",
"backText": {
"js": "已经退出 js 目录。",
"css": "已经退出 css 目录。",
"html": "已经退出 html 目录。"
},
"backKey": ["0"],
"segment" : true,
"segmentTip" : "您找的是不是\"KEY\"?可以尝试输入\"KEY\"。",
"timeout": 300
});
处理过程是真正处理消息和回复消息的业务逻辑,开发者这可以自定义一些业务逻辑。
处理过程是一个对象,里面要包含onMessage
, onEvent
, onQuitFloor
, onEnterFloor
中的一个或几个方法,当有相应事件时,会调用对应方法,接收到消息后,进项处理。
每个方法都可以有返回值
- 如果返回值是"break",那么消息不会继续进入到后续的处理过程中,类似于阻止冒泡
- 如果返回值是"keep",那么此目录的有效时间将变为1天
var Process = {
onMessage : function(msg, reply, floor) {}, // 有私信消息
onEvent : function(msg, reply) {}, // 有事件消息
onQuitFloor : function(msg, reply, floor) {}, // 退出目录
onEnterFloor : function(msg, reply, floor) {} // 进入目录
}
参数中msg
是消息,reply
是pm.Message
实体,已经设置好id
和uid
,设置回复内容后,可直接发送,floor
为目录,开启目录功能后,会有此参数。
pm.ReplyManager.addProcess(process);
添加处理过程后,会为process添加3个方法
销毁处理过程(不是真正的销毁,是从处理过程的队列里移除):
process.destory();
重置用户至根目录:
process.resetUser(uid)
移动用户到固定目录:
// 用户id,目录,目录持续时间
process.moveUser(uid, floor, time);
pm.ReplyManager.removeProcess(process);
pm.ReplyManager.reset();
根据用户的地域和性别回复相应内容。
var process = {
onMessage : function(msg, reply) {
// 判断消息是不是符合要求
if (msg.type == "text" && msg.text == "我是") {
// 查询用户信息
pm.OpenAPI.get("users/show", "uid=" + msg.fromUid, function(data) {
// 回复消息
reply.setText(data.location + " " + (data.gender == "m" ? "纯爷们" : "女汉子")).send();
});
}
}
}
// 城市和代码对应关系
var cities = {"北京" : "101010100"};
var process = {
onMessage : function(msg, reply) {
// 判断消息是否符合标注
if (msg.type == "text" && msg.text.indexOf("天气") > -1) {
// 获取地理位置
var addr = msg.text.replace(/天气/, "");
if (cities[addr]) {
// 请求天气接口
http.request({
hostname : "m.weather.com.cn",
path : ("/data/" + cities[addr] + ".html")
}, function(res){
var rs = "";
res.on("data", function(chunk) {
rs += chunk + '';
});
res.on("end", function() {
rs = JSON.parse(rs).weatherinfo;
// 回复消息
reply.setText(rs.city + "\n" + rs.date_y + " " + rs.week + "\n天气:" + rs.weather1 + " " + rs.wind1 + "\n温度:" + rs.temp1 + "\n" + rs.index_d).send();
});
}).end();
}
}
}
};
(function(module) {
var btc = require('btc');
var filter = {
bitstamp : function(value) {
var text = 'BitStamp : \n';
text += 'High : $' + value.high + '\n';
text += 'Low : $' + value.low + '\n';
text += 'Ask : $' + value.ask + '\n';
text += 'Bid : $' + value.bid + '\n';
text += 'Last : $' + value.last + '\n';
text += 'Volume : ' + value.volume + '\n';
return text;
},
mtgox : function(value) {
var ticker = value.data;
var text = 'Mtgox : \n';
text += 'High : ' + ticker.high.display + '\n';
text += 'Low : ' + ticker.low.display + '\n';
text += 'Avg : ' + ticker.avg.display + '\n';
text += 'Vwap : ' + ticker.vwap.display + '\n';
text += 'Last : ' + ticker.last.display + '\n';
text += 'Volume : ' + ticker.vol.display + '\n';
return text;
},
futures796 : function(value) {
var ticker = value.ticker;
var text = 'Futures796 : \n';
text += 'High : $' + ticker.high + '\n';
text += 'Low : $' + ticker.low + '\n';
text += 'Buy : $' + ticker.buy + '\n';
text += 'Sell : $' + ticker.sell + '\n';
text += 'Last : $' + ticker.last + '\n';
text += 'Volume : ' + ticker.vol + '\n';
return text;
},
chbtc : function(value) {
var ticker = value.ticker;
var text = 'ChBtc : \n';
text += 'High : ¥' + ticker.high + '\n';
text += 'Low : ¥' + ticker.low + '\n';
text += 'Buy : ¥' + ticker.buy + '\n';
text += 'Sell : ¥' + ticker.sell + '\n';
text += 'Last : ¥' + ticker.last + '\n';
text += 'Volume : ' + ticker.vol + '\n';
return text;
},
okcoin : function(value) {
var ticker = value.ticker;
var text = 'OKCoin : \n';
text += 'High : ¥' + ticker.high + '\n';
text += 'Low : ¥' + ticker.low + '\n';
text += 'Buy : ¥' + ticker.buy + '\n';
text += 'Sell : ¥' + ticker.sell + '\n';
text += 'Last : ¥' + ticker.last + '\n';
text += 'Volume : ' + ticker.vol + '\n';
return text;
},
btcchina : function(value) {
var ticker = value.ticker;
var text = 'BtcChina : \n';
text += 'High : ¥' + ticker.high + '\n';
text += 'Low : ¥' + ticker.low + '\n';
text += 'Buy : ¥' + ticker.buy + '\n';
text += 'Sell : ¥' + ticker.sell + '\n';
text += 'Last : ¥' + ticker.last + '\n';
text += 'Volume : ' + ticker.vol + '\n';
return text;
},
fxbtc : function(value) {
var ticker = value.ticker;
var text = 'FxBtc : \n';
text += 'High : ¥' + ticker.high + '\n';
text += 'Low : ¥' + ticker.low + '\n';
text += 'Bid : ¥' + ticker.bid + '\n';
text += 'Ask : ¥' + ticker.ask + '\n';
text += 'Last : ¥' + ticker.last + '\n';
text += 'Volume : ' + ticker.vol + '\n';
return text;
},
btc100 : function(value) {
var ticker = value.ticker;
var text = 'BTC100 : \n';
text += 'High : ¥' + ticker.high + '\n';
text += 'Low : ¥' + ticker.low + '\n';
text += 'Bid : ¥' + ticker.bid + '\n';
text += 'Ask : ¥' + ticker.ask + '\n';
text += 'Last : ¥' + ticker.last + '\n';
text += 'Volume : ' + ticker.vol + '\n';
return text;
}
};
module.exports = {
onMessage : function(msg, reply, floor) {
if (floor == 'btc') {
msg.text = msg.text.toLowerCase();
if (!filter[msg.text]) {
msg.text = 'btcchina';
}
btc.price(msg.text, function(err, prices){
reply.setText(filter[msg.text](prices)).send();
});
}
}
};
})(module);
-
模拟微信服务器,向公共账号开发者后台请求数据,格式与微信完全相同,省去开发者代码改造的麻烦。
-
模拟实现上传下载,用户查询等微信接口,数据格式和微信相同,开发者只需更改API的url的host即可。
在不用修改任何代码逻辑的情况下,将自动回复功能从微信迁移到微博公共账号上
组件:pm.WeChat.Process
pm.ReplyManager.addProcess(
new pm.WeChat.Process(
"http://sipc.sinaapp.com/index.php",
"sipc******",
"http://weibopm.duapp.com",
"wechat"
)
);
- 前两个参数是
URL
和Token
,和微信后台配置是相同的,如下面的图示。 - 第三个参数是模拟API的Host(下节将说明)。
- 第四个参数示
floor
,表示此目录下的消息会推送给URL
,没有此参数,则全部消息都会推送到URL
上。
注意:
- 现在仅支持文字、图片、地理位置的推送。
- 现在仅支持文字、图片、图文消息的回复。
- 常用的一般是文字和图文,而且不分目录,因此后两个参数基本上可以忽略。
- 怎么区分消息是从微信还是微博来?我觉得你的微信ID和微博的ID是不同的,判断
ToUserName
即可。
微信公共平台给开发者提供了一些API,url
前缀为: https://api.weixin.qq.com
,在这里为了让开发者更容易迁移,提供一个模拟微信API的模块。
组件:pm.WeChat.Server
// appid, secret 和 端口
pm.WeChat.Server("abc", "123", 8080);
这样开发者只需把url
改成此服务的部署的地址即可,例如:
https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=abc&secret=123
改为你的服务地址/cgi-bin/token?grant_type=client_credential&appid=abc&secret=123
即可,返回结果和微信的接口完全相同。
现在支持的常用接口有:
/cgi-bin/token
/cgi-bin/media/upload
/cgi-bin/media/get
/cgi-bin/message/custom/send
/cgi-bin/user/info
根据用户的消息/事件,静态匹配,并自动回复静态内容。
组件: pm.ReplyProcess.replyForEvent
根据用户的关注/取消关注事件,回复静态消息。
示例如下:
var rfe = pm.ReplyProcess.replyForEvent;
rfe.init({
"follow" : "亲!欢迎关注本账号!输入 menu 或 菜单 查看相应内容。", // 关注回复
"unfollow" : "不要离开我,行不行吗?呜呜!" // 取消关注回复
});
pm.ReplyManager.addProcess(rfe);
组件: pm.ReplyProcess.replyForText
根据用户的文本消息,回复静态消息。
示例如下:
var rft = pm.ReplyProcess.replyForText;
rft.init({
"js": {
"1": ["text", "js是很神奇的东西"],
"2": [
"articles",
[
["js很牛", "js太牛了", "http://tp2.sinaimg.cn/1908736117/180/5678518790/1", "http://weibo.com"],
["js很牛逼", "js太牛逼了", "http://tp2.sinaimg.cn/1908736117/180/5678518790/1", "http://weibo.com"]
]
],
"3" : ["imagePath", "/Users/Apple/Documents/npm.png"]
},
"css": {
"1": ["text", "css是很神奇的东西"],
"2": ["image", 1055597360, 1055597367],
"3": ["imageUrl", "http://tp2.sinaimg.cn/1908736117/180/5678518790/1"]
},
"html": {
"1": ["text", "html是很神奇的东西"],
"2": ["position", "116.309868", "39.984371"],
"3": ["qrCode", "http://weibo.com"]
}
});
pm.ReplyManager.addProcess(rft);
抽奖活动:通过私信发送固定消息后可以参与抽奖,结束时,会随机抽出幸运用户,自动发送获奖和未获奖的消息。 可以创建多次抽奖活动。
组件: pm.ReplyProcess.Lottery
示例如下:
// 创建示例
var lot = new pm.ReplyProcess.Lottery();
// 设置开始和结束时间
lot.setTime("2013/11/11 00:00:00", "2013/11/11 01:00:00");
// 设置参与活动的固定消息
lot.setKey(["抽奖", "cj"]);
// 设置回复内容
lot.setContent({
beforeEvent : "抽奖还未开始!",
onEvent : "成功参与抽奖,请耐心等待结果!",
repeat : "您已成功参与抽奖!每人只可参与一次!",
afterEvent : "抽奖已经结束!",
prize : "恭喜您获得【NAME】- TEXT ,稍后我们将私信联系您。",
none : "很遗憾,您没有抽中任何奖项,谢谢您的参与!"
});
// 增加奖项
lot.addPrize("特等奖", "宝马一辆", 1);
lot.addPrize("一等奖", "Mac Pro一台", 1);
lot.addPrize("二等奖", "MacBook Pro一台", 1);
// 设置结果输出文件 Excel
lot.setLogFile("/Users/Apple/Downloads/lot.xlsx");
// 增加处理过程
pm.ReplyManager.addProcess(lot);
获取结果 : lot.getResult();
抽奖活动:通过私信发送固定消息后可以参与秒杀,秒杀按照私信先来后到来排序,先到先得,秒完为止。 可以创建多次秒杀活动。
组件: pm.ReplyProcess.SecKill
示例如下:
// 创建秒杀活动实例
var sk = new pm.ReplyProcess.SecKill();
// 设置开始和结束时间
sk.setTime("2013/11/11 00:00:00", "2013/11/11 01:00:00");
// 设置参与活动的固定消息
sk.setKey(["秒杀", "ms"]);
// 设置回复内容
sk.setContent({
beforeEvent : "秒杀还未开始!",
repeat : "您已成功秒杀!每人只可秒杀一次!",
afterEvent : "秒杀已经结束!",
success : "恭喜您获得 - NAME ,稍后我们将私信联系您。",
none : "商品已经全部被秒杀!"
});
// 增加奖项
sk.setPrize("宝马一辆", 1);
// 设置结果输出文件 Excel
sk.setLogFile("/Users/Apple/Downloads/sk.xlsx");
// 增加处理过程
pm.ReplyManager.addProcess(sk);
获取结果 : sk.getResult();
图示:
转发相应微博后,会用私信通知粉丝,然后粉丝回复相应内容,即可获得优惠劵。
组件:pm.ReplyProcess.RepostDiscount
// 创建活动实例
var rd = new pm.ReplyProcess.RepostDiscount("转发优惠活动");
// 设计关键字
rd.setKey("优惠");
// 设置优惠劵数量
rd.setNum(100);
// 设置时间和发送的微博
rd.setConf("2013/11/11 00:00:00", "2013/11/11 01:00:00", {
text : "[Test] 关注本账号,并转发此微博,有机会获得本店优惠劵一张。【测试测试测试】"
});
// 设置回复内容
rd.setContent({
repostSuccess : "非常感谢您转发我们的微博,现在您可以回复\"优惠\"获得优惠券。",
success : "您已经成功获得优惠劵,消费时请出示微博昵称即可。",
repeat : "您已经获得过优惠券,请不要重复获取。",
none : "优惠劵已经派发完,歇歇您的参与"
});
// 添加处理过程
pm.ReplyManager.addProcess(rd);
图示:
信箱,留言箱,提供用户留言功能,并具有分类的功能(创建多个MailBox实例),为大V提供真正的留言功能。
组件: pm.ReplyProcess.MailBox
它能将用户的留言以三种形式存储:
- 以私信的形式转发给其他固定的账号,这是这个账号和大V得私信列表就是留言记录。
- 以邮件的形式发到固定的账号,当然两个邮件账号之间的邮件列表就是留言记录,而且方便处理。
- 以http post形式提交到指定的url,这个适用于公司有自己的留言系统的。
示例代码
// 创建MailBox实例
var mb = new pm.ReplyProcess.MailBox("咨询系统");
// 设置相应关键字
mb.setKey("咨询");
// 设置回复内容
mb.setContent({
"success": "您的咨询问题已经收到,我们将找专业人员为您解答!",
"notSupport": "对不起,系统不支持您的消息类型。"
});
// 设置类型 message 第二个参数为uid列表,是转发给的用户的id
mb.setType("message", ["2609545991"]);
// 添加处理过程
pm.ReplyManager.addProcess(mb);
示例代码
// 创建MailBox实例
var mb = new pm.ReplyProcess.MailBox("投诉系统");
// 设置相应关键字
mb.setKey("投诉");
// 设置回复内容
mb.setContent({
"success": "您的投诉问题已经收到,我们将找专业人员为您解答!",
"notSupport": "对不起,系统不支持您的消息类型。"
});
// 设置类型
mb.setType("mail", {
"host": "smtp.163.com", // 邮件服务器,暂时仅支持stmp协议
"secureConnection": true, // 加密否
"port": 465, // 端口
"user": "[email protected]", // 发邮件的邮箱账户
"pass": "******", // 对应的密码
"toUser": "[email protected]" // 发给的邮箱账户
});
// 添加处理过程
pm.ReplyManager.addProcess(mb);
示例代码
// 创建MailBox实例
var mb = new pm.ReplyProcess.MailBox("反馈系统");
// 设置相应关键字
mb.setKey("反馈");
// 设置回复内容
mb.setContent({
"success": "您的反馈问题已经收到,我们将找专业人员为您解答!",
"notSupport": "对不起,系统不支持您的消息类型。"
});
// 设置类型
mb.setType("server", {
"url" : "http://127.0.0.1:8080/",
"token" : "feedback"
});
// 添加处理过程
pm.ReplyManager.addProcess(mb);
注意:为了防止url
被非法提交,server
接收的post
参数里有token
,tag
,timestamp
三个参数,
其中 token
应该等于 sha1(tag + static_token + timestamp)
,static_token
为配置中的feedback
。
因为static_token
是不公开的,服务器可以通过token
验证请求是不是来自本系统,从而排除非法提交。
基于微博私信的客服系统,使一个大V账号,可以连接多个客服账号,而用户只需和大V进行私信交互,就可实现和客服的一对一交交流。首先方便了用户,让用户通过与只一个账号互动,而完成很多事情,然后对于大V用户,更容易管理,并借助微博私信的便利,形成自己的客服系统。
组件: pm.ReplyProcess.CustomerService
示例如下:
// 创建客服系统实例
var cs = new pm.ReplyProcess.CustomerService();
// 设置启用时间
cs.setTime("9:30", "19:00");
// 设置关键字
cs.setKey(["客服"]);
// 设置客服人员名称和对应的微博用户Id
cs.setWorkers({
"小洋" : "2609545991"
});
// 设置回复内容
cs.setContent({
outerTime : "对不起,现在不是客服服务时间。\n(服务时间9:30~19:00)",
enter : "欢迎使用客服系统,系统正在自动为您连接客服人员,请稍候!\n(发送0可以退出客服系统)",
follow : "【注意】由于系统限制,关注本账号,成为本账号的粉丝,才能正常使用客服系统。",
wait : "【排队中】现在业务非常繁忙,请您稍等片刻!\n(发送0可以退出客服系统)",
startConv : "已经连接到客服人员,客服【 NAME 】为您服务!\n(发送0可以退出客服系统)",
stopConv : "您已经退出客服系统,欢迎下次再次使用。",
worker : "【 NAME 】:\n欢迎进入客服人员工作系统:\n发送next接待下一位客户;\n发送 talk:用户昵称或用户id 与相应直接沟通;\n发送exit退出与当前客户的交流;\n发送0退出客服系统。",
none : "客服系统中现在没有等待的客户。",
new : "有新客户进入客服系统,发送next进行接待。",
startWork : "客户已经接入。",
stopWork : "和客户的交谈已经结束,发送next接待下一位客户。",
notSupport : "对不起,客服系统不支持您的消息类型。",
noUser : "用户不存在或者不是此账号的粉丝。"
});
// 添加处理过程
pm.ReplyManager.addProcess(cs);
- 对于客服,需要输入关键字
客服
,即可进入客服系统,进入后会有相应提示。(客服最好是大V的互粉用户) - 发送
next
,可以接待下一位客户。 - 当然也可以用
talk:edwon_lim
直接联系客户。 - 连接成功后,会用客户信息的简介。
- 对于客服人员,会有特殊的输入规则,
qr:二维码信息
:客户会收到一个二维码图片,url:图片地址
:客户会收到相应图片,pos:精度,纬度
:客户会收到一个带有地理位置信息的消息place:地点名
:客户会收到一个带有地理位置信息的消息(地点名尽量明确,否则容易有差错)
- 客服人员可以输入
exit
结束与此客户的连接。 - 输入
0
,可以立刻退出客服系统。
由于大V账号不是非常容易申请,很有可能很多开发者共用一个账号测试,这样一个人发的测试消息,另一个人的程序也会收到,容易造成错乱。
对于这种情况,可以在初始化时使用filter
来解决:
var allowUids = [1908736117, 2609545991];
pm.init(username, uid, password, appkey, function(msg) {
if (allowUids.indexOf(msg.fromUid) > -1) {
return true;
}
});
只处理uid
是1908736117和2609545991的消息,这样不同的程序会处理不同的消息。
当私信量足够大的时候,单独一个服务可能在压力和处理速度上会遇到瓶颈,而nodejs的效率要与编译性语言稍差,所以这就需要将服务部署很多份,而且互不影响。
-
对于
Event
活动,可以单独部署一个服务,这个服务不支持目录,不支持各种回复,只支持此活动,活动的消息,别的服务不会处理,只是这个服务进行处理。活动进行完,可以直接停止服务,不用再占用资源。 -
同样的,不同类型的处理过程(Process)可以部署到不同的环境,不同的机器上。
-
也可以使用开发测试时的方法,使用
filter
设定每个服务处理消息的uid
范围,不用的服务处理不同范围用户的消息,这样可以分流压力。
可以统一配置这些功能:
pm.configure(options);
配置格式为:
{
"floor": {
"items": {
"js": "欢迎来到js脚本目录!输入 1 、 2 、 3 查看相应内容。",
"css": "欢迎来到css样式目录!输入 1 、 2 、 3 查看相应内容。",
"html": "欢迎来到html页面目录!输入 1 、 2 、 3 查看相应内容。",
"咨询": "请输入您需要咨询的问题。",
"投诉": "请输入您需要投诉的问题。",
"反馈": "请输入您需要反馈的问题。",
"客服": null
},
"hotKey": [
"menu",
"菜单"
],
"helpText": "欢迎您的访问:\n请发送\"js\",\"css\",\"html\"进入相应目录,输入\"0\"退出相应目录;\n发送`咨询`,`投诉`,`反馈`,`客服`进入相应功能。",
"backText": {
"js": "已经退出 js 目录。",
"css": "已经退出 css 目录。",
"html": "已经退出 html 目录。"
},
"backKey": [
"0"
],
"segment" : true,
"segmentTip" : "您找的是不是\"KEY\"?可以尝试输入\"KEY\"。",
"timeout": 300
},
"forText": {
"js": {
"1": [
"text",
"js是很神奇的东西"
],
"2": [
"articles",
[
[
"js很牛",
"js太牛了",
"http://tp2.sinaimg.cn/1908736117/180/5678518790/1",
"http://weibo.com"
],
[
"js很牛逼",
"js太牛逼了",
"http://tp2.sinaimg.cn/1908736117/180/5678518790/1",
"http://weibo.com"
]
]
],
"3" : [
"imagePath",
"/Users/Apple/Documents/npm.png"
]
},
"css": {
"1": [
"text",
"css是很神奇的东西"
],
"2": [
"image",
1055597360,
1055597367
],
"3": [
"imageUrl",
"http://tp2.sinaimg.cn/1908736117/180/5678518790/1"
]
},
"html": {
"1": [
"text",
"html是很神奇的东西"
],
"2": [
"position",
"116.309868",
"39.984371"
],
"3": [
"qrCode",
"http://weibo.com"
]
}
},
"forEvent": {
"follow": "亲!欢迎关注本账号!输入 menu 或 菜单 查看相应内容。",
"unfollow": "不要离开我,行不行吗?呜呜!"
},
"customer": {
"startTime": "9:00",
"endTime": "21:30",
"key": "客服",
"workers": {
"小洋": "2609545991"
},
"content": {
"outerTime": "对不起,现在不是客服服务时间。\n(服务时间9:30~21:30)",
"enter": "欢迎使用客服系统,系统正在自动为您连接客服人员,请稍候!\n(发送0可以退出客服系统)",
"follow": "【注意】由于系统限制,关注本账号,成为本账号的粉丝,才能正常使用客服系统。",
"wait": "【排队中】现在业务非常繁忙,请您稍等片刻!\n(发送0可以退出客服系统)",
"startConv": "已经连接到客服人员,客服【 NAME 】为您服务!\n(发送0可以退出客服系统)",
"stopConv": "您已经退出客服系统,欢迎下次再次使用。",
"worker": "【 NAME 】:\n欢迎进入客服人员工作系统:\n发送next接待下一位客户;\n发送 talk:用户昵称或用户id 与相应直接沟通;\n发送exit退出与当前客户的交流;\n发送0退出客服系统。",
"none": "客服系统中现在没有等待的客户。",
"new": "有新客户进入客服系统,发送next进行接待。",
"startWork": "客户已经接入。",
"stopWork": "和客户的交谈已经结束,发送next接待下一位客户。",
"notSupport": "对不起,客服系统不支持您的消息类型。",
"noUser": "用户不存在或者不是此账号的粉丝。",
"noPlace": "地点不存在。"
}
},
"box": [
{
"name": "咨询信箱",
"key": "咨询",
"type": "message",
"data": [
"2609545991"
],
"content": {
"success": "您的咨询问题已经收到,我们将找专业人员为您解答!",
"notSupport": "对不起,系统不支持您的消息类型。"
}
},
{
"name": "投诉信箱",
"key": "投诉",
"type": "mail",
"data": {
"host": "smtp.163.com",
"secureConnection": true,
"port": 465,
"user": "[email protected]",
"pass": "******",
"toUser": "[email protected]"
},
"content": {
"success": "您的投诉已经受理,谢谢您的支持!",
"notSupport": "对不起,系统不支持您的消息类型。"
}
},
{
"name": "反馈信箱",
"key": "反馈",
"type": "server",
"data": {
"url" : "http://127.0.0.1:8080/",
"token" : "feedback"
},
"content": {
"success": "您的咨询问题已经收到,我们将找专业人员为您解答!",
"notSupport": "对不起,系统不支持您的消息类型。"
}
}
],
"event": [
{
"type": "Lottery",
"name" : "双11抽奖活动",
"startTime": "2013/11/11 00:00:00",
"endTime": "2013/11/11 01:00:00",
"key": [
"抽奖",
"cj"
],
"prize": [
[
"特等奖",
"宝马一辆",
1
],
[
"一等奖",
"Mac Pro一台",
1
],
[
"二等奖",
"MacBook Pro一台",
1
]
],
"content": {
"beforeEvent": "抽奖还未开始!",
"onEvent": "成功参与抽奖,请耐心等待结果!",
"repeat": "您已成功参与抽奖!每人只可参与一次!",
"afterEvent": "抽奖已经结束!",
"prize": "恭喜您获得【NAME】- TEXT ,稍后我们将私信联系您。",
"none": "很遗憾,您没有抽中任何奖项,谢谢您的参与!"
}
},
{
"type": "SecKill",
"name" : "双11日秒杀活动",
"startTime": "2013/11/11 00:00:00",
"endTime": "2013/11/11 01:00:00",
"key": [
"秒杀",
"ms"
],
"prize": {
"name": "宝马M",
"num": 1
},
"content": {
"beforeEvent": "秒杀还未开始!",
"repeat": "您已成功秒杀!每人只可秒杀一次!",
"afterEvent": "秒杀已经结束!",
"success": "恭喜您获得 - NAME ,稍后我们将私信联系您。",
"none": "商品已经全部被秒杀!"
}
},
{
"type": "RepostDiscount",
"name" : "转发微博换优惠劵活动",
"startTime": "2013/11/11 00:00:00",
"endTime": "2013/11/11 01:00:00",
"key": [
"优惠"
],
"status" : {
"text" : "[Test] 关注本账号,并转发此微博,有机会获得本店优惠劵一张。"
},
"num" : 100,
"content" : {
"repostSuccess" : "非常感谢您转发我们的微博,现在您可以回复\"优惠\"获得优惠券。",
"success" : "您已经成功获得优惠劵,消费时请出示微博昵称即可。",
"repeat" : "您已经获得过优惠券,请不要重复获取。",
"none" : "优惠劵已经派发完,歇歇您的参与"
}
}
]
}
- 优化代码。
- 集成系统,统一管理多份部署的服务。
- 桌面系统,基于Node-Webkit开发桌面端的服务,方便操作,可视直观。