Is it possible to identify session is coming from same device on server?

this is what a session looks like inside Meteor.server.sessions,

possible to know user is coming from the same device ?

same account can login multiple places, but how to identiy its the same device?

cross tab, cross browser?

{ id: 'FyYHbJMzsiR4yR6o6',
I20170505-17:48:58.106(8)?   server:
I20170505-17:48:58.107(8)?    { options:
I20170505-17:48:58.107(8)?       { heartbeatInterval: 15000,
I20170505-17:48:58.107(8)?         heartbeatTimeout: 15000,
I20170505-17:48:58.107(8)?         respondToPings: true },
I20170505-17:48:58.107(8)?      onConnectionHook:
I20170505-17:48:58.107(8)?       { nextCallbackId: 1,
I20170505-17:48:58.108(8)?         callbacks: [Object],
I20170505-17:48:58.108(8)?         bindEnvironment: true,
I20170505-17:48:58.108(8)?         exceptionHandler: 'onConnection callback' },
I20170505-17:48:58.108(8)?      onMessageHook:
I20170505-17:48:58.108(8)?       { nextCallbackId: 0,
I20170505-17:48:58.109(8)?         callbacks: {},
I20170505-17:48:58.109(8)?         bindEnvironment: true,
I20170505-17:48:58.109(8)?         exceptionHandler: 'onMessage callback' },
I20170505-17:48:58.109(8)?      publish_handlers:
I20170505-17:48:58.109(8)?       { 'meteor.loginServiceConfiguration': [Function],
I20170505-17:48:58.109(8)?         meteor_autoupdate_clientVersions: [Function],
I20170505-17:48:58.109(8)?         test: [Function] },
I20170505-17:48:58.110(8)?      universal_publish_handlers: [ [Function], [Function], [Function], [Function] ],
I20170505-17:48:58.110(8)?      method_handlers:
I20170505-17:48:58.110(8)?       { '/users/insert': [Function],
I20170505-17:48:58.110(8)?         '/users/update': [Function],
I20170505-17:48:58.110(8)?         '/users/remove': [Function],
I20170505-17:48:58.110(8)?         login: [Function],
I20170505-17:48:58.110(8)?         logout: [Function],
I20170505-17:48:58.111(8)?         logoutOtherClients: [Function],
I20170505-17:48:58.111(8)?         getNewToken: [Function],
I20170505-17:48:58.111(8)?         removeOtherTokens: [Function],
I20170505-17:48:58.111(8)?         configureLoginService: [Function],
I20170505-17:48:58.111(8)?         changePassword: [Function],
I20170505-17:48:58.111(8)?         forgotPassword: [Function],
I20170505-17:48:58.111(8)?         resetPassword: [Function],
I20170505-17:48:58.111(8)?         verifyEmail: [Function],
I20170505-17:48:58.111(8)?         createUser: [Function],
I20170505-17:48:58.112(8)?         '/meteor_accounts_loginServiceConfiguration/insert': [Function],
I20170505-17:48:58.112(8)?         '/meteor_accounts_loginServiceConfiguration/update': [Function],
I20170505-17:48:58.112(8)?         '/meteor_accounts_loginServiceConfiguration/remove': [Function] },
I20170505-17:48:58.112(8)?      sessions: { FyYHbJMzsiR4yR6o6: [Circular] },
I20170505-17:48:58.112(8)?      stream_server:
I20170505-17:48:58.112(8)?       { registration_callbacks: [Object],
I20170505-17:48:58.112(8)?         open_sockets: [Object],
I20170505-17:48:58.112(8)?         prefix: '/sockjs',
I20170505-17:48:58.112(8)?         server: [Object] },
I20170505-17:48:58.113(8)?      warned_about_autopublish: true },
I20170505-17:48:58.113(8)?   version: '1',
I20170505-17:48:58.113(8)?   initialized: false,
I20170505-17:48:58.114(8)?   socket:
I20170505-17:48:58.114(8)?    SockJSConnection {
I20170505-17:48:58.114(8)?      _session:
I20170505-17:48:58.114(8)?       Session {
I20170505-17:48:58.114(8)?         session_id: undefined,
I20170505-17:48:58.115(8)?         heartbeat_delay: 45000,
I20170505-17:48:58.115(8)?         disconnect_delay: 60000,
I20170505-17:48:58.115(8)?         prefix: '/sockjs',
I20170505-17:48:58.115(8)?         send_buffer: [],
I20170505-17:48:58.115(8)?         is_closing: false,
I20170505-17:48:58.116(8)?         readyState: 1,
I20170505-17:48:58.116(8)?         timeout_cb: [Function],
I20170505-17:48:58.116(8)?         to_tref: [Object],
I20170505-17:48:58.116(8)?         connection: [Circular],
I20170505-17:48:58.117(8)?         emit_open: null,
I20170505-17:48:58.117(8)?         recv: [Object] },
I20170505-17:48:58.117(8)?      id: '6af3d138-aff2-4977-a18e-2901a9c9c2de',
I20170505-17:48:58.117(8)?      headers:
I20170505-17:48:58.117(8)?       { 'x-forwarded-for': '127.0.0.1',
I20170505-17:48:58.118(8)?         'x-forwarded-proto': 'ws',
I20170505-17:48:58.118(8)?         host: 'localhost:3000',
I20170505-17:48:58.118(8)?         'user-agent': 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_12_4) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/57.0.2987.133 Safari/537.36',
I20170505-17:48:58.118(8)?         'accept-language': 'en-US,en;q=0.8,zh-CN;q=0.6,zh;q=0.4' },
I20170505-17:48:58.119(8)?      prefix: '/sockjs',
I20170505-17:48:58.119(8)?      remoteAddress: '127.0.0.1',
I20170505-17:48:58.119(8)?      remotePort: 53973,
I20170505-17:48:58.119(8)?      address: { address: '127.0.0.1', family: 'IPv4', port: 26232 },
I20170505-17:48:58.119(8)?      url: '/sockjs/396/lkhblvkt/websocket',
I20170505-17:48:58.120(8)?      pathname: '/sockjs/396/lkhblvkt/websocket',
I20170505-17:48:58.120(8)?      protocol: 'websocket',
I20170505-17:48:58.120(8)?      setWebsocketTimeout: [Function],
I20170505-17:48:58.120(8)?      send: [Function],
I20170505-17:48:58.121(8)?      _events: { close: [Object], data: [Function] },
I20170505-17:48:58.121(8)?      _eventsCount: 2,
I20170505-17:48:58.121(8)?      _meteorSession: [Circular] },
I20170505-17:48:58.121(8)?   inQueue:
I20170505-17:48:58.121(8)?    { [String: '']
I20170505-17:48:58.121(8)?      '0': undefined,
I20170505-17:48:58.121(8)?      '1': undefined,
I20170505-17:48:58.122(8)?      '2': undefined,
I20170505-17:48:58.122(8)?      '3': undefined,
I20170505-17:48:58.122(8)?      _capacity: 16,
I20170505-17:48:58.122(8)?      _length: 0,
I20170505-17:48:58.122(8)?      _front: 4 },
I20170505-17:48:58.122(8)?   blocked: false,
I20170505-17:48:58.122(8)?   workerRunning: false,
I20170505-17:48:58.123(8)?   _namedSubs:
I20170505-17:48:58.123(8)?    { LyueHq4trcmisjNBK:
I20170505-17:48:58.123(8)?       { _session: [Circular],
I20170505-17:48:58.123(8)?         connection: [Object],
I20170505-17:48:58.123(8)?         _handler: [Function],
I20170505-17:48:58.123(8)?         _subscriptionId: 'LyueHq4trcmisjNBK',
I20170505-17:48:58.124(8)?         _name: 'meteor.loginServiceConfiguration',
I20170505-17:48:58.124(8)?         _params: [],
I20170505-17:48:58.124(8)?         _subscriptionHandle: 'NLyueHq4trcmisjNBK',
I20170505-17:48:58.124(8)?         _deactivated: false,
I20170505-17:48:58.124(8)?         _stopCallbacks: [Object],
I20170505-17:48:58.125(8)?         _documents: {},
I20170505-17:48:58.125(8)?         _ready: true,
I20170505-17:48:58.125(8)?         userId: 'G62Sj2HGvoPXGume5',
I20170505-17:48:58.125(8)?         _idFilter: [Object] },
I20170505-17:48:58.125(8)?      s5FmNcucqn6av956x:
I20170505-17:48:58.125(8)?       { _session: [Circular],
I20170505-17:48:58.125(8)?         connection: [Object],
I20170505-17:48:58.126(8)?         _handler: [Function],
I20170505-17:48:58.126(8)?         _subscriptionId: 's5FmNcucqn6av956x',
I20170505-17:48:58.126(8)?         _name: 'meteor_autoupdate_clientVersions',
I20170505-17:48:58.126(8)?         _params: [],
I20170505-17:48:58.127(8)?         _subscriptionHandle: 'Ns5FmNcucqn6av956x',
I20170505-17:48:58.127(8)?         _deactivated: false,
I20170505-17:48:58.127(8)?         _stopCallbacks: [Object],
I20170505-17:48:58.127(8)?         _documents: [Object],
I20170505-17:48:58.127(8)?         _ready: true,
I20170505-17:48:58.128(8)?         userId: 'G62Sj2HGvoPXGume5',
I20170505-17:48:58.128(8)?         _idFilter: [Object] },
I20170505-17:48:58.128(8)?      fngap9dxHY5rnEtzK:
I20170505-17:48:58.128(8)?       { _session: [Circular],
I20170505-17:48:58.128(8)?         connection: [Object],
I20170505-17:48:58.129(8)?         _handler: [Function],
I20170505-17:48:58.129(8)?         _subscriptionId: 'fngap9dxHY5rnEtzK',
I20170505-17:48:58.129(8)?         _name: 'test',
I20170505-17:48:58.129(8)?         _params: [],
I20170505-17:48:58.129(8)?         _subscriptionHandle: 'Nfngap9dxHY5rnEtzK',
I20170505-17:48:58.129(8)?         _deactivated: false,
I20170505-17:48:58.130(8)?         _stopCallbacks: [],
I20170505-17:48:58.130(8)?         _documents: {},
I20170505-17:48:58.130(8)?         _ready: false,
I20170505-17:48:58.131(8)?         userId: 'G62Sj2HGvoPXGume5',
I20170505-17:48:58.131(8)?         _idFilter: [Object] } },
I20170505-17:48:58.131(8)?   _universalSubs:
I20170505-17:48:58.132(8)?    [ { _session: [Circular],
I20170505-17:48:58.132(8)?        connection: [Object],
I20170505-17:48:58.132(8)?        _handler: [Function],
I20170505-17:48:58.132(8)?        _subscriptionId: undefined,
I20170505-17:48:58.132(8)?        _name: undefined,
I20170505-17:48:58.133(8)?        _params: [],
I20170505-17:48:58.133(8)?        _subscriptionHandle: 'U7wnoJFBFr5akEXzBr',
I20170505-17:48:58.142(8)?        _deactivated: false,
I20170505-17:48:58.142(8)?        _stopCallbacks: [Object],
I20170505-17:48:58.142(8)?        _documents: [Object],
I20170505-17:48:58.142(8)?        _ready: false,
I20170505-17:48:58.142(8)?        userId: 'G62Sj2HGvoPXGume5',
I20170505-17:48:58.143(8)?        _idFilter: [Object] },
I20170505-17:48:58.143(8)?      { _session: [Circular],
I20170505-17:48:58.143(8)?        connection: [Object],
I20170505-17:48:58.143(8)?        _handler: [Function],
I20170505-17:48:58.143(8)?        _subscriptionId: undefined,
I20170505-17:48:58.143(8)?        _name: undefined,
I20170505-17:48:58.143(8)?        _params: [],
I20170505-17:48:58.144(8)?        _subscriptionHandle: 'UeFoYa6uHQZfCAdLws',
I20170505-17:48:58.144(8)?        _deactivated: false,
I20170505-17:48:58.144(8)?        _stopCallbacks: [Object],
I20170505-17:48:58.144(8)?        _documents: [Object],
I20170505-17:48:58.144(8)?        _ready: false,
I20170505-17:48:58.145(8)?        userId: 'G62Sj2HGvoPXGume5',
I20170505-17:48:58.145(8)?        _idFilter: [Object] },
I20170505-17:48:58.145(8)?      { _session: [Circular],
I20170505-17:48:58.145(8)?        connection: [Object],
I20170505-17:48:58.146(8)?        _handler: [Function],
I20170505-17:48:58.146(8)?        _subscriptionId: undefined,
I20170505-17:48:58.146(8)?        _name: undefined,
I20170505-17:48:58.146(8)?        _params: [],
I20170505-17:48:58.146(8)?        _subscriptionHandle: 'UkdHSPhDGnYpM7JADM',
I20170505-17:48:58.146(8)?        _deactivated: false,
I20170505-17:48:58.147(8)?        _stopCallbacks: [Object],
I20170505-17:48:58.147(8)?        _documents: [Object],
I20170505-17:48:58.147(8)?        _ready: false,
I20170505-17:48:58.148(8)?        userId: 'G62Sj2HGvoPXGume5',
I20170505-17:48:58.148(8)?        _idFilter: [Object] },
I20170505-17:48:58.148(8)?      { _session: [Circular],
I20170505-17:48:58.148(8)?        connection: [Object],
I20170505-17:48:58.149(8)?        _handler: [Function],
I20170505-17:48:58.149(8)?        _subscriptionId: undefined,
I20170505-17:48:58.149(8)?        _name: undefined,
I20170505-17:48:58.149(8)?        _params: [],
I20170505-17:48:58.149(8)?        _subscriptionHandle: 'UHCmQgB9RieKipCTyy',
I20170505-17:48:58.149(8)?        _deactivated: false,
I20170505-17:48:58.149(8)?        _stopCallbacks: [Object],
I20170505-17:48:58.150(8)?        _documents: {},
I20170505-17:48:58.150(8)?        _ready: false,
I20170505-17:48:58.150(8)?        userId: 'G62Sj2HGvoPXGume5',
I20170505-17:48:58.150(8)?        _idFilter: [Object] } ],
I20170505-17:48:58.151(8)?   userId: 'G62Sj2HGvoPXGume5',
I20170505-17:48:58.151(8)?   collectionViews:
I20170505-17:48:58.151(8)?    { users:
I20170505-17:48:58.151(8)?       { collectionName: 'users',
I20170505-17:48:58.151(8)?         documents: [Object],
I20170505-17:48:58.152(8)?         callbacks: [Object] },
I20170505-17:48:58.152(8)?      meteor_autoupdate_clientVersions:
I20170505-17:48:58.152(8)?       { collectionName: 'meteor_autoupdate_clientVersions',
I20170505-17:48:58.152(8)?         documents: [Object],
I20170505-17:48:58.152(8)?         callbacks: [Object] } },
I20170505-17:48:58.153(8)?   _isSending: true,
I20170505-17:48:58.153(8)?   _dontStartNewUniversalSubs: false,
I20170505-17:48:58.153(8)?   _pendingReady: [],
I20170505-17:48:58.153(8)?   _closeCallbacks: [ [Function] ],
I20170505-17:48:58.154(8)?   _socketUrl: '/sockjs/396/lkhblvkt/websocket',
I20170505-17:48:58.154(8)?   _respondToPings: true,
I20170505-17:48:58.154(8)?   connectionHandle:
I20170505-17:48:58.154(8)?    { id: 'FyYHbJMzsiR4yR6o6',
I20170505-17:48:58.154(8)?      close: [Function],
I20170505-17:48:58.154(8)?      onClose: [Function],
I20170505-17:48:58.155(8)?      clientAddress: '127.0.0.1',
I20170505-17:48:58.155(8)?      httpHeaders:
I20170505-17:48:58.155(8)?       { 'x-forwarded-for': '127.0.0.1',
I20170505-17:48:58.155(8)?         'x-forwarded-proto': 'ws',
I20170505-17:48:58.155(8)?         host: 'localhost:3000',
I20170505-17:48:58.155(8)?         'user-agent': 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_12_4) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/57.0.2987.133 Safari/537.36',
I20170505-17:48:58.156(8)?         'accept-language': 'en-US,en;q=0.8,zh-CN;q=0.6,zh;q=0.4' } },
I20170505-17:48:58.156(8)?   heartbeat:
I20170505-17:48:58.156(8)?    { heartbeatInterval: 15000,
I20170505-17:48:58.156(8)?      heartbeatTimeout: 15000,
I20170505-17:48:58.157(8)?      _sendPing: [Function],
I20170505-17:48:58.157(8)?      _onTimeout: [Function],
I20170505-17:48:58.157(8)?      _seenPacket: true,
I20170505-17:48:58.157(8)?      _heartbeatIntervalHandle:
I20170505-17:48:58.157(8)?       { _called: false,
I20170505-17:48:58.157(8)?         _idleTimeout: 15000,
I20170505-17:48:58.158(8)?         _idlePrev: [Object],
I20170505-17:48:58.158(8)?         _idleNext: [Object],
I20170505-17:48:58.158(8)?         _idleStart: 1037,
I20170505-17:48:58.158(8)?         _onTimeout: [Function: wrapper],
I20170505-17:48:58.158(8)?         _repeat: [Function] },
I20170505-17:48:58.158(8)?      _heartbeatTimeoutHandle: null } }

You’ll have to look into logging the userAgents against each login to a server only collection or somewhere in the userprofile, and then you can always check multiple login against the userAgents. For example, if a user logs in from a device with useragent userAgent: 'Mozilla/5.0 (BB10; Kbd) AppleWebKit/537.35+ (KHTML, like Gecko) Version/10.3.2.2876 Mobile Safari/537.35+' } },, you should log that against the current user. You can check this userAgent when the user logs in again from the same device or another tab. They should be a package available for this I think, but this is just the logic.