Primus 客户端

注解

如果可能的话, 我们建议在客户端上使用Feathers和 feathersress/primus-client 模块.要在客户端上不使用Feathers而直接使用Primus连接, 请参阅 直接连接 部分.

加载Primus客户端库

在浏览器中, Primus客户端库(通常位于 primus/primus.js)总是必须使用 <script> 标签加载:

<script type="text/javascript" src="primus/primus.js"></script>

重要

这将使 Primus 对象全局可用.模块加载程序选项目前不可用.

客户端在NodeJS中使用

在NodeJS中, 可以按如下方式初始化Primus客户端:

const Primus = require('primus');
const Emitter = require('primus-emitter');
const Socket = Primus.createSocket({
  transformer: 'websockets',
  plugin: {
    'emitter': Emitter
  }
});
const socket = new Socket('http://api.feathersjs.com');

@feathersjs/primus-client

GitHub stars npm version Changelog

$ npm install @feathersjs/primus-client --save

@feathersjs/primus-client 模块允许通过配置的websocket库连接到通过 Primus 客户端 公开的服务.

重要

Primus套接字也用于 call 服务方法.使用套接字, 调用方法和接收实时事件通常比使用 REST客户端 更快, 并且不需要同时在同一客户端应用程序中同时使用REST和websockets.

primus(socket)

使用给定套接字和默认选项初始化Primus客户端.

const feathers = require(‘@feathersjs/feathers’);
const primusClient = require(‘@feathersjs/primus-client’);
const socket = new Primus(‘http://api.my-feathers-server.com’);

const app = feathers();

app.configure(primusClient(socket));

// Receive real-time events through Primus
app.service(‘messages’).on(‘created’, message => console.log(‘New message created’, message));

// Call the ``messages``
service app.service(‘messages’).create({ text: ‘A message from a REST client’ });
<script type="text/javascript" src="//cdnjs.cloudflare.com/ajax/libs/core-js/2.1.4/core.min.js"></script>
<script src="//unpkg.com/@feathersjs/client@^3.0.0/dist/feathers.js"></script>
<script type="text/javascript" src="primus/primus.js"></script>
<script>
  // Socket.io is exposed as the `io` global.
  var socket = new Primus('http://api.my-feathers-server.com');
  // @feathersjs/client is exposed as the `feathers` global.
  var app = feathers();

  app.configure(feathers.primus(socket));

  // Receive real-time events through Primus
  app.service('messages')
    .on('created', message => console.log('New message created', message));

  // Call the `messages` service
  app.service('messages').create({
    text: 'A message from a REST client'
  });
</script>

primus(socket, options)

使用给定套接字和给定选项初始化Primus客户端.

选项可以:

  • timeout (默认值:5000ms) - 方法调用失败并超时的时间.这通常在调用不存在的服务或服务方法时发生.

const feathers = require('@feathersjs/feathers');
const Primus = require('@feathersjs/primus-client');
const socket = new Primus('http://api.my-feathers-server.com');
const app = feathers();
app.configure(primus(socket, { timeout: 2000 }));

每个服务的超时可以像这样改变:

app.service('messages').timeout = 3000;

直接连接

在浏览器中, 可以通过从 primus/primus.js 加载客户端并实例化一个新的 Primus 实例来建立连接.与HTTP调用不同, websockets在浏览器中没有跨源限制, 因此可以连接到任何Feathers服务器.

有关详细信息, 请参阅 Primus 文档.

小技巧

套接字连接URL必须指向服务器根目录, 这是Feathers将设置Primus的地方.

<script src="primus/primus.js">
<script>
  var socket = new Primus('http://api.my-feathers-server.com');
</script>

可以通过使用方法参数发出 <servicepath>::<methodname> 事件来调用服务方法. servicepath 是服务已注册的名称(在 app.use 中), 没有前导或尾随斜杠.将使用方法调用的结果或可能发生的任何错误调用 function(error, data) Node约定之后的可选回调.

params 将在服务方法调用中设置为 params.query.其他服务参数可以通过 Primus 客户端 设置.

认证

可以通过发送带有 strategy 和 payload 的 authenticate 事件来验证套接字.有关具体示例, 请参阅 JWT身份验证 身份验证章节中的“直接连接”部分.

socket.send('authenticate', {
  strategy: 'strategyname',
  ... otherData
}, function(message, data) {
  console.log(message); // message will be null
  console.log(data); // data will be {"accessToken": "your token"}
  // You can now send authenticated messages to the server
});

find

从服务中检索所有匹配资源的列表

socket.send('find', 'messages', { status: 'read', user: 10 }, (error, data) => {
  console.log('Found all messages', data);
});

将在服务器上调用 app.service('messages').find({ query: { status: 'read', user: 10 } }).

get

从服务中检索单个资源.

socket.send('get', 'messages', 1, (error, message) => {
  console.log('Found message', message);
});

将在服务器上调用 app.service('messages').get(1, {}).

socket.send('get', 'messages', 1, { fetch: 'all' }, (error, message) => {
  console.log('Found message', message);
});

将在服务器上调用 app.service('messages').get(1, {query:{fetch:'all'}}).

create

使用 data 创建一个新资源, 它也可以是一个数组.

socket.send('create', 'messages', {
  text: 'I really have to iron'
}, (error, message) => {
  console.log('Message created', message);
});

将在服务器上调用 app.service('messages').create({ "text": "I really have to iron" }, {})

socket.send('create', 'messages', [
  { text: 'I really have to iron' },
  { text: 'Do laundry' }
]);

将在带有数组的服务器上调用 app.service('messages').create.

update

完全替换单个或多个资源.

socket.send('update', 'messages', 2, {
  text: 'I really have to do laundry'
}, (error, message) => {
  console.log('Message updated', message);
});

将在服务器上调用 app.service('messages').update(2, { "text": "I really have to do laundry" }, {}). id 也可以是 null 来更新多个资源:

socket.send('update', 'messages', null, {
  complete: true
}, { complete: false });

将在服务器上调用 app.service('messages').update(null, {complete:true}, {query:{complete:false}}).

小技巧

通常希望 update 替换整个资源, 这就是数据库适配器仅支持多个记录的 patch 的原因.

patch

使用新的 data 合并单个或多个资源的现有数据.

socket.send('patch', 'messages', 2, {
  read: true
}, (error, message) => {
  console.log('Patched message', message);
});

将在服务器上调用 app.service('messages').patch(2, {\“read \”:true}, {}). id 也可以是 null 来更新多个资源:

socket.send('patch', 'messages', null, {
  complete: true
}, {
  complete: false
}, (error, message) => {
  console.log('Patched message', message);
});

将在服务器上调用 app.service('messages').patch(null, { complete: true }, { query: { complete: false } }) 来改变所有 read app.service(‘messages’).

这是由Feathers API 开箱即用的

remove

删除一个或多个资源:

socket.send('remove', 'messages', 2, { cascade: true }, (error, message) => {
  console.log('Removed a message', message);
});

将在服务器上调用 app.service('messages').remove(2, {query:{cascade:true}}). id 也可以是 null 来删除多个资源:

socket.send('remove', 'messages', null, { read: true });

将调用 app.service('messages').remove(null, { query: { read: 'true' } }) 在服务器上删除所有 read app.service(‘messages’).

监听事件

通过监听服务事件, 可以在应用程序中实现实时行为. eventsservicepath eventname 的形式发送到套接字.

created

当服务 create 成功返回时, created 事件将与回调数据一起发布.

socket.on('messages created', function(message) {
  console.log('Got a new Message!', message);
});

updated, patched

当服务 updatepatch 方法成功回调时, updatedpatched 事件将与回调数据一起发布.

socket.on('my/messages updated', function(message) {
  console.log('Got an updated Message!', message);
});

socket.send('update', 'my/messages', 1, {
  text: 'Updated text'
}, {}, function(error, callback) {
 // Do something here
});

removed

当服务 remove 成功回调时, removed 事件将与回调数据一起发布.

socket.on('messages removed', function(message) {
  // Remove element showing the Message from the page
  $('#message-' + message.id).remove();
});