Giter VIP home page Giter VIP logo

polo's Introduction

Polo

Polo is a zero configuration (zeroconf, mdns or dns-sd) service discovery module written completely in Javascript. Unlike some other tools (https://github.com/agnat/node_mdns) it does not require the installation of Apple's Bonjour SDK. It's available through npm:

npm install polo

What problem does it solve?

Polo allows your servers/programs to discover eachother without having to talk to a central server and without the use of any static configuration as long as they are connected to the same local network.

Usage

First create a polo instance:

var polo = require('polo');
var apps = polo();

Now let's add a service to the app repository:

apps.put({
	name:'hello-world', // required - the name of the service
	host:'example.com', // defaults to the network ip of the machine
	port: 8080          // we are listening on port 8080.
});

If you put multiple services with the same name Polo will load balance them for you by choosing a random service. Now spin up another node process and polo will automatically distribute information about this service:

// in another process
var polo = require('polo');
var apps = polo();

apps.once('up', function(name, service) {                   // up fires everytime some service joins
	console.log(apps.get(name));                        // should print out the joining service, e.g. hello-world
});

Additionally there is a down event which fires when a services leaves the repository - it's that easy!

Options

Per default Polo will discover all services running on a network using UDP multicast. When developing it can often be very useful to disable this. To do so either provide multicast: false or set your NODE_ENV=development environment variable

var apps = polo({
	multicast: false     // disables network multicast,
	monitor: true        // fork a monitor for faster failure detection,
	heartbeat: 2*60*1000 // set the service heartbeat interval (defaults to 2min)
});

or using development mode from the shell

$ NODE_ENV=development node my-polo-app.js # also disables network multicast

Example

Let's create an HTTP service. Try to run the program below on different machines in the same network:

var http = require('http');
var polo = require('polo');
var apps = polo();

var server = http.createServer(function(req, res) {
	if (req.url !== '/') {
		res.writeHead(404);
		res.end();
		return;
	}

	res.end('hello-http is available at http://'+apps.get('hello-http').address);
});

server.listen(0, function() {
	var port = server.address().port; // let's find out which port we binded to

	apps.put({
		name: 'hello-http',
		port: port
	});

	console.log('visit: http://localhost:'+port);
});

License

This software is licensed under "MIT"

Copyright (c) 2012 Mathias Buus Madsen [email protected]

Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the 'Software'), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:

The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.

THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

polo's People

Contributors

asafyish avatar mafintosh avatar maraoz avatar nebulade avatar qrpike avatar siboulet avatar willemmulder avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

polo's Issues

Monitor trying to use port 67567

I'm getting a "RangeError: Port should be > 0 and < 65536" error when using the monitor.

I noticed the monitor tries to use port number 67567, which is invalid.

node_modules/polo/monitor.js:54:server.listen(67567, '127.0.0.1');
node_modules/polo/repository.js:84: var socket = net.connect(67567, '127.0.0.1');

Polo 0.5.0 did not work with node 0.10 and fails with dgram.js:382 throw new errnoException(process._errno, 'addMembership');

dgram.js:382
throw new errnoException(process._errno, 'addMembership');
^
Error: addMembership EBADF
at new errnoException (dgram.js:440:11)
at Socket.addMembership (dgram.js:382:11)
at module.exports (/Users/jweber/privateProjects/officeTanks/node_modules/polo/announce.js:49:9)
at null. (/Users/jweber/privateProjects/officeTanks/node_modules/polo/repository.js:212:3)
at g (events.js:175:14)
at EventEmitter.emit (events.js:98:17)
at Server. (/Users/jweber/privateProjects/officeTanks/node_modules/polo/node_modules/root/index.js:204:8)
at Server.EventEmitter.emit (events.js:92:17)
at net.js:1052:10
at process._tickCallback (node.js:415:13)

A solution is described here: nodejs/node-v0.x-archive#4944

Cant see all the services published via polo

Hi,
I am not sure whether my scenario will work with polo. This is my scenario.

I have two node js app running in two Raspberry pi, each has different IP address and different name. Both are published using apps.put(...);

I wrote another nodejs app running in my windows laptop that just listen and log all the polo services as shown below. (I ran it in a Raspberry pi as well and the result is same.)

apps.once('up', function(name, service) {
console.log(apps.get(name));
});

Issue:
I was expecting the 'up' event will display both the service when ever it starts running. But here I could only see the first service published to polo. It's not at all showing the second service.

Node js version: 0.10.26

Can any one please tell whether Polo's 'up' event can continuously listen for the services, or it will show only the service published in the app that started first?

Regards,
Sony Arouje

Multiple process on the same machine ?

Hi,

Is it possible to run to process using polo on the same machine ?
On my development machine, I am trying to use a few process that are using polo, but getting an "bind EADDRINUSE" on polo.

What is the job of monitor.js

Hej,

we use polo in a node-webkit project and have issues starting the monitor.js daemon from within node-webkit. The issue lays on the node-webkit site. See nwjs/nw.js#213 for it.

Our application seems to work fine without it. But before turning it off in production we want to be sure that we understand the aim of this daemon correctly. So that we know what functionality we and how we can circumvent if necessary the daemon behavior.

It seems to us that it deregisters a client from all other clients that know about it. Right?

Thank you for your help.

Refusing to install polo as a dependency of itself

I cannot install the node package on my end. It's giving me this :

npm ERR! node v6.11.2
npm ERR! npm  v3.10.10
npm ERR! code ENOSELF

npm ERR! Refusing to install polo as a dependency of itself
npm ERR!
npm ERR! If you need help, you may report this error at:
npm ERR!     <https://github.com/npm/npm/issues>

npm ERR! Please include the following file with any support request:
npm ERR!     D:\_prog\test\polo\npm-debug.log

npm-debug.log goes as follow :

0 info it worked if it ends with ok
1 verbose cli [ 'C:\\Program Files\\nodejs\\node.exe',
1 verbose cli   'C:\\Program Files\\nodejs\\node_modules\\npm\\bin\\npm-cli.js',
1 verbose cli   'install',
1 verbose cli   '--save',
1 verbose cli   'polo' ]
2 info using [email protected]
3 info using [email protected]
4 silly loadCurrentTree Starting
5 silly install loadCurrentTree
6 silly install readLocalPackageData
7 silly fetchPackageMetaData polo
8 silly fetchNamedPackageData polo
9 silly mapToRegistry name polo
10 silly mapToRegistry using default registry
11 silly mapToRegistry registry https://registry.npmjs.org/
12 silly mapToRegistry data Result {
12 silly mapToRegistry   raw: 'polo',
12 silly mapToRegistry   scope: null,
12 silly mapToRegistry   escapedName: 'polo',
12 silly mapToRegistry   name: 'polo',
12 silly mapToRegistry   rawSpec: '',
12 silly mapToRegistry   spec: 'latest',
12 silly mapToRegistry   type: 'tag' }
13 silly mapToRegistry uri https://registry.npmjs.org/polo
14 verbose request uri https://registry.npmjs.org/polo
15 verbose request no auth needed
16 info attempt registry request try #1 at 22:23:34
17 verbose request id b92331ebd4d9b95b
18 verbose etag W/"586e0d9b-8c21"
19 verbose lastModified Thu, 05 Jan 2017 09:10:51 GMT
20 http request GET https://registry.npmjs.org/polo
21 http 304 https://registry.npmjs.org/polo
22 verbose headers { date: 'Sat, 19 Aug 2017 02:23:35 GMT',
22 verbose headers   via: '1.1 varnish',
22 verbose headers   'cache-control': 'max-age=300',
22 verbose headers   etag: 'W/"586e0d9b-8c21"',
22 verbose headers   age: '16',
22 verbose headers   connection: 'keep-alive',
22 verbose headers   'x-served-by': 'cache-ord1741-ORD',
22 verbose headers   'x-cache': 'HIT',
22 verbose headers   'x-cache-hits': '1',
22 verbose headers   'x-timer': 'S1503109415.402597,VS0,VE0',
22 verbose headers   vary: 'Accept-Encoding, Accept' }
23 silly get cb [ 304,
23 silly get   { date: 'Sat, 19 Aug 2017 02:23:35 GMT',
23 silly get     via: '1.1 varnish',
23 silly get     'cache-control': 'max-age=300',
23 silly get     etag: 'W/"586e0d9b-8c21"',
23 silly get     age: '16',
23 silly get     connection: 'keep-alive',
23 silly get     'x-served-by': 'cache-ord1741-ORD',
23 silly get     'x-cache': 'HIT',
23 silly get     'x-cache-hits': '1',
23 silly get     'x-timer': 'S1503109415.402597,VS0,VE0',
23 silly get     vary: 'Accept-Encoding, Accept' } ]
24 verbose etag https://registry.npmjs.org/polo from cache
25 verbose get saving polo to C:\Users\iTouchTheSky\AppData\Roaming\npm-cache\registry.npmjs.org\polo\.cache.json
26 verbose correctMkdir C:\Users\iTouchTheSky\AppData\Roaming\npm-cache correctMkdir not in flight; initializing
27 silly install normalizeTree
28 silly loadCurrentTree Finishing
29 silly loadIdealTree Starting
30 silly install loadIdealTree
31 silly cloneCurrentTree Starting
32 silly install cloneCurrentTreeToIdealTree
33 silly cloneCurrentTree Finishing
34 silly loadShrinkwrap Starting
35 silly install loadShrinkwrap
36 silly loadShrinkwrap Finishing
37 silly loadAllDepsIntoIdealTree Starting
38 silly install loadAllDepsIntoIdealTree
39 silly rollbackFailedOptional Starting
40 silly rollbackFailedOptional Finishing
41 silly runTopLevelLifecycles Finishing
42 silly install printInstalled
43 verbose stack Error: Refusing to install polo as a dependency of itself
43 verbose stack     at checkSelf (C:\Program Files\nodejs\node_modules\npm\lib\install\validate-args.js:53:14)
43 verbose stack     at Array.<anonymous> (C:\Program Files\nodejs\node_modules\npm\node_modules\slide\lib\bind-actor.js:15:8)
43 verbose stack     at LOOP (C:\Program Files\nodejs\node_modules\npm\node_modules\slide\lib\chain.js:15:14)
43 verbose stack     at chain (C:\Program Files\nodejs\node_modules\npm\node_modules\slide\lib\chain.js:20:5)
43 verbose stack     at C:\Program Files\nodejs\node_modules\npm\lib\install\validate-args.js:16:5
43 verbose stack     at C:\Program Files\nodejs\node_modules\npm\node_modules\slide\lib\async-map.js:52:35
43 verbose stack     at Array.forEach (native)
43 verbose stack     at C:\Program Files\nodejs\node_modules\npm\node_modules\slide\lib\async-map.js:52:11
43 verbose stack     at Array.forEach (native)
43 verbose stack     at asyncMap (C:\Program Files\nodejs\node_modules\npm\node_modules\slide\lib\async-map.js:51:8)
44 verbose cwd D:\_prog\test\polo
45 error Windows_NT 10.0.15063
46 error argv "C:\\Program Files\\nodejs\\node.exe" "C:\\Program Files\\nodejs\\node_modules\\npm\\bin\\npm-cli.js" "install" "--save" "polo"
47 error node v6.11.2
48 error npm  v3.10.10
49 error code ENOSELF
50 error Refusing to install polo as a dependency of itself
51 error If you need help, you may report this error at:
51 error     <https://github.com/npm/npm/issues>
52 verbose exit [ 1, true ]

Error catching "down" event

I have a master-slave setup with the following codes:
SLAVE:

var polo = require('polo')({'multicast': false});
polo.put({
    'name': 'sniper-agent',
    'port': 24368
});

MASTER:

var polo = require('polo')({'multicast': true});
polo.once('up', function(name, service) {
    if (name == 'my-agent') {
        console.log(service);
    }
});
polo.once('down', function(name, service) {
    if (name == 'my-agent') {
        console.log(service);
    }
});

After both of them started, the discovery works perfectly. However, as soon as either of the process is terminated, the other also crashes with the following error:

events.js:72
        throw er; // Unhandled 'error' event
              ^
Error: read ECONNRESET
    at errnoException (net.js:901:11)
    at TCP.onread (net.js:556:19)

Discoverable Setup

I am trying to run a discoverable zeroconf setup on an Intel Galileo board. At first I thought that simply using:

var polo = require('polo');
var apps = polo();

apps.put({
    name:'hello-world', // required - the name of the service
    // Leaving host blank as it "defaults to the network ip of the machine"
    port: 9800               // we are listening on port 8080.
});

Would let me 'see' the 'hello-world' instance on the same network. But no matter what I try it doesn't appear to be available. I can ssh into the Galileo on my network, and can send messages directly to its ports. (And read them via node, currently tested with an Open Sound Control implementation) So it is definitely there.

Is there something more that I need to put together in order to see it on the network? Or am I just starting the wrong thing here entirely.

Thank you,
Boris

Note: I don't need this to be an HTTP server, I just need to discover the device and then connect to an open sound control instance on it.

dgram multicast not working in nodejs v11

Consider this very simple test.js

require('dgram').createSocket('udp4').bind(60547);
setTimeout(function() { echo "exiting after 1 minute" }, 60000);

With node v10 we can spawn as many instance of test.js as we want.
With node v11.13 and later spawning the second instance results in the following error:

Error: bind EADDRINUSE
    at exports._errnoException (util.js:742:11)
    at dgram.js:222:28
    at dns.js:82:18
    at process._tickCallback (node.js:378:11)

To fix it, we need to specify an option as following:

require('dgram').createSocket({'type': 'udp4', 'reuseAddr': true}).bind(60547);

Not able to use package

Hi, I am getting the following error on require('polo') :-

Root.prototype.proto = process.EventEmitter.prototype;
^

TypeError: Cannot read property 'prototype' of undefined
at Object. (/home/himanshu/Documents/socket/node_modules/root/index.js:27:48)
at Module._compile (module.js:571:32)
at Object.Module._extensions..js (module.js:580:10)
at Module.load (module.js:488:32)
at tryModuleLoad (module.js:447:12)
at Function.Module._load (module.js:439:3)
at Module.require (module.js:498:17)
at require (internal/module.js:20:19)
at Object. (/home/himanshu/Documents/socket/node_modules/polo/repository.js:1:74)
at Module._compile (module.js:571:32)

Kindly guide me through this.

Tests not passing : [err] 2/6 - 2-up-down.js -> timeout

Hello,
I'm interested in this module for distributed applications, but I can't get the test suite to pass.

I just cloned the repository, ran npm install and then npm test and the second test (up-down) is not passing.

Is there something I am doing wrong? Should I setup something else to run tests?

Detecting failure between wifi and wired device

I have a set-up with 2 devices connected to the same logical network on the same physical router, one via Ethernet cable, and one via Wifi.
Even though both devices can ping each other, polo running on one fails to detect the other and vice versa.

Suggestion: add zeroconf / mdns / bonjour keywords somewhere in readme for visibility

This project deserves more visibility! Despite it being a full-javascript solution that does not require the installation of Bonjour like other modules (e.g. https://github.com/agnat/node_mdns), it is pretty hard to find, because it does not use the terminology that many people are looking for.

I thus suggest using more of the common keywords on the readme page, at the least "zeroconf", "mdns" and "bonjour"..!

Leaving the repository

Currently the readme states:

Additionally there is a down event which fires when a service leaves the repository

What is the recommend way for a service to leave the repository?
The apps.put() method is used to register a service but I cannot find a way to unregister.

package dependencies version

the control of dependencies versions for the root package are too lazy, the root package aims to install router at version greater than 0.6.0.
As you are rewritting a new router version, the root package install this new version and API are not compatible.
Could you please fix the package.json of root ( version 0.4.6 ), it would be helpful to install the polo package.

As workaround, I've to put "router":"0.6.2" in my package dependencies before "polo".

Thks in advance

The lack of txtRecord

txtRecord is kinda useful when there are other sort of metadata that you would like to publish, but it is not available in this implementation. Are there any plans for this?

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.