Setting options to a socket.io-client connection - angularjs

I have a socket.io server set with node.js, and a client - manager set inside of the angular application. I'm using socket.io-client library to connect. I'm passing it to controller with angular-socket-io:
app.factory('mySocket', function (socketFactory) {
return socketFactory();
});
app.factory('socket', ['mySocket', '$rootScope', socket]);
app.controller('MainController', ['$scope', 'socket', MainController]);
My server:
var app = require('express')();
var http = require('http').Server(app);
var io = require('socket.io')(http);
app.get('/', function(req, res){
});
io.on('connection', function(socket) {
socket.emit('welcome', { message: 'Welcome!', id: socket.id });
socket.on('i am client', console.log);
});
http.listen(3000, function(){
console.log('listening on *:3000');
});
And essential client service:
var socket = io.connect("http://localhost:3000");
console.log(socket);
// Add a connect listener
socket.on('connect',function() {
console.log('Client has connected to the server!');
socket.emit('i am client', "hi!");
socket.on('welcome', console.log);
});
I just couldn't connect them (two separate projects running on different ports) until I forced uri to be http://localhost:3000 in the socket.io.js file...
So my question is: how can I set my uri or host and port in the options so it gets the right uri? Just sayin, that classics like
io.connect("http://localhost:3000");
are simply not working.
EDIT: Figured it out. In the main js file, where socketFactory() is launched, it has to be like that:
app.factory('mySocket', function (socketFactory) {
var myIoSocket = io.connect('http://localhost:3000');
return socketFactory({ ioSocket: myIoSocket });
});

Related

Socket.io - angular.js. - always disconnected with "ping timeout"

Trying to connect with Angular js + socket.io to the server (Node.js - nestsJS)
I have both React and Angular app
in react app everything is work
in Angularjs I got always "ping timeout" and then it try to recconect - on the server I saw the connection and it pass the authentication flow.
when I going to the network tab(WS) I got my events after authenticated in the backend so it looks like its a client issue
so every ~30sec the console output disconnect + reason "ping timeout"
Angular code -socket service
.factory('socket', socket);
socket.$inject = ["$rootScope"];
function socket($rootScope) {
const options = {
transports:['websocket'],
// allowUpgrades: false,
query: {
token : "token",
},
forceNew: true
}
var socket = io.connect('/', { ...options, path: `/socket.io` });
return {
on: function(eventName, callback) {
socket.on(eventName, function() {
var args = arguments;
$rootScope.$apply(function() {
callback.apply(socket, args);
});
});
},
emit: function(eventName, data, callback) {
socket.emit(eventName, data, function() {
var args = arguments;
$rootScope.$apply(function() {
if (callback) {
callback.apply(socket, args);
}
});
})
}
};
controller:
socket.on('connect', function (data) {
console.log("connect")
});
socket.on('connection', function (data) {
console.log("connect")
});
socket.on('disconnect', function (data) {
console.log("disconnect")
console.log(data)
});
socket.on('events-test', function (data) {
console.log("test")
console.log(data)
})
in the network tab i can see the "events-test" events and it will create a new "ws" tab evrey reconnection
Solved by change the socket-io client version to 2.3.0
Use socketio version 2 on the client side to match the server. 3 and 4 are incompatible with server v2

Node and Angular socket error in browser console

I am using Node(server) + Angular(client) to implement socket in my application.
Angular bower.json socket components : "angular-socket-io":
"^0.7.0","socket.io-client": "^1.7.2",
Node js socket component in package.json : "socket.io": "^1.7.3",
I am seeing this below web socket error in my chrome browser console :
WebSocket connection to
'wss://ireporter.apple.com/uitracker/socket.io/?EIO=3&transport=websocket&sid=4qBY-qoxEzUQZOvUAACb'
failed: Error during WebSocket handshake: net::ERR_CONNECTION_RESET
WrappedWebSocket # VM43:161
This error happens probably only in a production environment. Cannot remember seeing this error in when running the application in local.
Also posting ONLY the socket related code from both server and client side :
Node js server-side code
start.js file
var express = require('express');
var configure = require("./config/configure");
var logger = require("./config/components/logger")
var app = express();
var server = require('http').Server(app);
server.listen(process.env.PORT || config.port, function() {
logger.info("Express server listening on port", config.port );
});
//Configure with all the basic middlewares and configs
configure(app,server);
configure.js file
var socket = require('./middleware/socket/socket.js');
module.exports = function (app,server) {
app.use(socket(server));
}
socket.js file
"use strict";
var logger = require("../../components/logger");
module.exports = function(server){
var io = require('socket.io')(server, {path: '/appname/socket.io'});
require('./socketServer.js')(io, logger);
return function (req, res, next) {
req.io = io;
next();
};
};
socketServer.js
//export function for listening to the socket
module.exports = function(io, logger) {
io.on('connection', function(socket) {
socket.on('notification:update', function(data) {
io.emit('notification:update', data);
});
});
};
Angular js Client Side code :
Socket.js
MyApp.factory('Socket', function ($rootScope) {
var socket = io.connect('' , {path: '/appname/socket.io'});
return {
on: function (eventName, callback) {
socket.on(eventName, function () {
var args = arguments;
$rootScope.$apply(function () {
callback.apply(socket, args);
});
});
},
emit: function (eventName, data, callback) {
socket.emit(eventName, data, function () {
var args = arguments;
$rootScope.$apply(function () {
if (callback) {
callback.apply(socket, args);
}
});
})
}
};
});
notificationController.js
Socket.on('notification:update', function(data) {
});
-- Could anyone suggest how to resolve the console error?
Turns out there was another reverse proxy in front of your server that I had no control of. Please check your server setings. the problem is not about the code.
Error during WebSocket handshake: net::ERR_CONNECTION_RESET
Also try this one to test your server side.
<script src="https://cdnjs.cloudflare.com/ajax/libs/socket.io/1.7.2/socket.io.js"></script>
<script>
/*var socket = io('', {
path: '/appname/socket.io'
});*/
var socket = io.connect('' , {path: '/appname/socket.io'});
socket.on('notification:update', function (message) {
console.log('notification:update ', message);
});
setTimeout(function() {
console.log('emit demo');
socket.emit('notification:update', 'DEMO');
}, 1000);
socket.on('connect', function (data) {
console.log('connection');
});
</script>

Using Nodejs, Express and AngularJS to display IP in the browser

I'm learning Nodejs and ExpressJS. I'm trying to use ExpressJS and 2 Node modules (request-ip and geoip2) to get the client IP address for geolocation and then outputting the geolocation in the browser using AngularJS (1.x).
So far for my Nodejs and Expressjs code I have
var express = require('express');
// require request-ip and register it as middleware
var requestIp = require('request-ip');
// to convert the ip into geolocation coords
var geoip2 = require('geoip2');
// Init app
var app = express();
var port = process.env.PORT || 8000;
geoip2.init(); // init the db
//app.use(requestIp.mw({ attributeName: 'myCustomAttributeName'}));
var ip = '207.97.227.239';//67.183.57.64, 207.97.227.239
// respond to homepage req
app.get('/', function (req, res, next) {
//var ip = req.myCustomAttributeName;// use this for live
//var ip = '207.97.227.239';/* use this for testing */
console.log('requestIP is ' + ip);
next();
// geolocation
geoip2.lookupSimple(ip, function(error, result) {
if (error) {
console.log("Error: %s", error);
}
else if (result) {
console.log(result);//ipType was causing console.log duplication, IDK why
}
});
});
// set static folder
app.use('/', express.static(__dirname + '/public'));
app.listen(port, function(){
console.log('user location app is running');
});
And for Angular I have
angular.module('UserLocation', []);
angular.module('UserLocation')
.controller('MainController', MainController);
MainController.$inject = ['$http'];
function MainController($http) {
var vm = this;
vm.result = '';
vm.message = 'Hello World';
vm.getLocation = function() {
console.log();
return $http.get('localhost:8000', {
params: {result: result}
})
.then(function(result){
console.log(result);
})
};
};
vm.result in the Angular controller is for the result from the geoip2 Node module that performs the geolocation.
I can get the result in the console no problem but I'm not to sure how to pass it to Angular. I'm using the $http service but I'm not sure where to go from here...?
How do I pass the result from the geoip2 Node module to my Angular controller with $http?
The problem is that you are calling next before you are even done.
app.get('/', function (req, res, next) {
//next(); this line should be commented
// geolocation
geoip2.lookupSimple(ip, function(error, result) {
if (error)
return res.status(400).json({error: 'Something happened'});
return res.send(result);
});
});
Then on angular
$http({
method: 'GET',
url: '/yourURL'
}).then(function (response) {
console.log(response);
});
If you want to use the user IP to get location:
app.get('/', function (req, res, next) {
//next(); this line should be commented
// geolocation
var ip = req.headers['x-forwarded-for'] ||
req.connection.remoteAddress ||
req.socket.remoteAddress ||
req.connection.socket.remoteAddress;
geoip2.lookupSimple(ip, function(error, result) {
if (error)
return res.status(400).json({error: 'Something happened'});
return res.send(result);
});
});

socket.io GET /socket.io/?EIO=3&transport=polling&t=LV9VGzC" Error (404): "Not found"

//backend code
var express = require("express");
var app = express();
var http = require('http');
var startServer=http.createServer(app);
var socketIO = require('socket.io').listen(startServer);
startServer.listen(8080, function () {
console.log('server running on',8080)
});
socketIO.on('connection', function (socket) {
console.log('>>>>>>>>>>>>>>>>>>>>>>>>>>>>connected')
var userSocketObject = {};
userSocketObject.socket_id = socket.id;
socket.emit('news', { hello: 'world' });
socket.on('my other event', function (data) {
console.log(data);
});
});
//index.html code angularjs
var socket = io.connect('http://127.0.0.1:8080');
socket.on('news', function(data){
console.log(data);
socket.emit('my other event', {my: 'data'});
});
I'm trying to connect but I'm getting an error in the browser:
GET http://127.0.0.1:8080/socket.io/?EIO=3&transport=polling&t=LV9VGzC" Error (404): "Not found"
i have resolved the problem , the problem was in directory path app.use(express.static(path.join('public')))
Try changing your backend code into
var socketio = require('socket.io')(startServer, {
path: '/socket.io-client'
});
socketio.on('connection', function (socket) {
socket.on('my other event', function (data) {
console.log(data);
});
});
And on the clientside, the easiest way is to follow the instructions given in this repo: https://github.com/btford/angular-socket-io

Is it possible to use socket.io between NodeJS and AngularJS

I have two independent applications (frontEnd and BackEnd). The backEnd is in NodeJS using express framework and the FrontEnd is in AngularJS. Is it possible to use socket.io to send a message from the server (NodeJS) to the client (AngularJS)? How I can do that? I've tried with the following code but it is not working:
server code
var app = require('express')();
var server = require('http').Server(app);
var io = require('socket.io')(server);
io.sockets.on('connection', function(socket) {
//This message is not showing
console.log("socket");
socket.volatile.emit('notification', {message: 'push message'});
});
client code
angular.module('pysFormWebApp')
.factory('mySocket', function (socketFactory) {
var mySocket = socketFactory({
prefix: 'foo~',
ioSocket: io.connect('http://localhost:3000/')
});
mySocket.forward('error');
return mySocket;
});
angular.module('formModule')
.controller('typingCtrl', ['$scope', 'mySocket', typingCtrl]);
function typingCtrl ($scope, mySocket) {
mySocket.forward('someEvent', $scope);
$scope.$on('socket:someEvent', function (ev, data) {
$scope.theData = data;
console.log(data);
});
thanks for the help
This is how I set my connection up. I'm not sure if it's the best way, but it definitely works and I haven't had any performance issues to date.
Client Code:
angular.module('whatever').factory('socket', function ($rootScope) {
var socket = io.connect('yourhost');
return {
on: function (eventName, callback) {
socket.on(eventName, function () {
var args = arguments;
$rootScope.$apply(function () {
callback.apply(socket, args);
});
});
},
emit: function (eventName, data, callback) {
socket.emit(eventName, data, function () {
var args = arguments;
$rootScope.$apply(function () {
if (callback) {
callback.apply(socket, args);
}
});
})
}
};
});
angular.module('whatever').controller("MainCtrl", MainCtrl);
function MainCtrl($scope, socket) {
socket.on('channelname', function(data) {
console.log("message: " + data.message);
});
}
Server Code:
var Express = require('express');
var app = new Express();
var server = Http.createServer(app);
var io = require('socket.io')(server);
io.on('connection', function(socket) {
socket.emit("channelname", {
message: "messagecontent"
});
});

Resources