I am testing out rxjs websocket with sample code below, but when I try to publish from https://www.websocket.org/echo.html, I couldn't receive any message on the HTML, is this expected? How can I subscribe to topic from https://www.websocket.org/echo.html?
<html>
<head>
<script src="https://unpkg.com/#reactivex/rxjs#6.2.2/dist/global/rxjs.umd.js"></script>
<script>
const { WebSocketSubject } = rxjs.webSocket;
const socket$ = new WebSocketSubject('wss://echo.websocket.org');
socket$.subscribe(
(data) => console.log(data),
(err) => console.error(err),
() => console.warn('Completed!')
);
console.log('here')
</script>
</head>
<body></body>
</html>
websocket.org/echo.html does not offer broadcast thus using it for local testing will not receive any reply.
Running a local websocket server for testing is the way to go.
Related
We have created a bot using ms bot framework and wanted to pass some data to bot which user will not input. Like I was thinking if we can pass query string to below web channel.
https://webchat.botframework.com/embed/myformbot?s=XXXXXX&mycustomfield=text
And from bot api code, I can somehow read this querystring parameter...Ideally I know we don't have control over above webchat link, we are only giving access to bot api. But is this possible or any other way to pass data to bot which is not entered by user ?
We are planning to display web channel url to different sites in iframe and wanted to pass currently browsed url to identify from where user has started conversation.
Thanks
Siddharth
This is easily done using the BotFramework-WebChat library. There are just a few steps to perform to get yourself setup.
First, include a div with an id for the webchat instance of your bot to anchor to. In this example, the id is "webchat".
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=no" />
<title>Bot Chat</title>
<style>
#webchat,
#webchat>* {
border: 1px solid #333;
float: left;
min-height: 600px;
height: 600px;
position: relative;
width: 460px;
}
</style>
</head>
<body>
<div class="example">
<h2>Back Channel Bot</h2>
<div id="webchat"></div>
Next, you will want to include the following scripts in your html page. Please keep in mind that you should NOT store your secret in the browser or client app. It is included here for simplicity.
Here's what is happening. You use the Direct Line secret (from the channel settings in your Azure bot) to generate a token. The token is used to instantiate the bot webchat control. In this example, the user's location is saved in the store's payload as the activity object. This is sent to the bot on any POST_ACTIVITY event (i.e. the user interacts with the bot).
<script src='https://code.jquery.com/jquery-3.3.1.min.js'></script>
<script src='https://cdn.botframework.com/botframework-webchat/master/webchat.js'></script>
<script src='https://unpkg.com/simple-update-in/dist/simple-update-in.production.min.js'></script>
<script>
(async function () {
// To talk to your bot, you should use the token exchanged using your Direct Line secret.
// You should never put the Direct Line secret in the browser or client app.
const res = await fetch('https://directline.botframework.com/v3/directline/tokens/generate', {
method: 'POST',
headers: {
'Authorization': 'Bearer ' + secret
},
json: true
});
const { token } = await res.json();
let location = window.location.href;
let store = window.WebChat.createStore(
{},
({ dispatch }) => next => action => {
if (action.type === 'DIRECT_LINE/POST_ACTIVITY') {
// simple-update-in is used to update the "action"
action = window.simpleUpdateIn(action, ['payload', 'activity', 'channelData', 'location'], () => location);
}
return next(action);
}
);
window.WebChat.renderWebChat({
directLine: window.WebChat.createDirectLine({ token }),
store,
styleOptions: {
botAvatarInitials: 'BF',
userAvatarInitials: 'WC'
}
}, document.getElementById('webchat'));
document.querySelector('#webchat > *').focus();
})().catch(err => console.error(err));;
</script>
</body>
</html>
On the bot side, the bot is listening for the incoming message. The activity object will contain the data you sent and will look something like this:
channelData: { clientActivityID: '15469824216440.emdrovn0f5h', location: 'http://localhost:3000/' }
Hope of help!
I'm trying to use socket.io with koa.js and I was able to connect adding server = require('http').createServer(koa.callback()).listen(port); and io = require('socket.io')(server); at the very bottom of my application but now I want to emit and if possible listen to events from my controller / route. What's the best way to implement this?
I've tried adding io in my koa context like koa.context.io = io and even io.on('connection', function(socket){ koa.context.socket = socket }); but nothing is working.
Thanks in advance guys.
Accessing the socket.io instance in your koa route should not work.
Creating the socket.io instance depends on the application creating a callback function that can be used by the http server.
var server = http.createServer(app.callback());
var io = require('socket.io')(server);
This callback is generated with the help of co and requires that your app is already set up with all the middleware/routes. (see the koa source). Therefore you can't use the socket.io instance (which is created afterwards) in those routes.
Furthermore I think it is not intended to emit socket.io events in your controllers. If you want to send data back to the client that called the controller, you should do it in the response which is generated by that controller. If you want to emit further events at the server you could trigger them from the client by emitting an event that the server will receive. This way you can process the data from the client in the function you pass to socket.on(...) and don't need to implement it in the controller/routes for koa.
Here is an example for the second case, without any koa controller/route.
app.js:
var http = require('http');
var koa = require('koa');
var app = koa();
var send = require('koa-send');
app.use(function* (next) {
if (this.path !== '/') return yield next;
yield send(this, __dirname + '/index.html');
});
var server = http.createServer(app.callback());
var io = require('socket.io')(server);
io.on('connection', function (socket) {
socket.on('click', function (data) {
//process the data here
console.log('client clicked! data:');
console.log(data);
// emit an event
console.log('responding with news');
socket.emit('news', { hello: 'world' });
});
});
var port = process.env.PORT || 3000;
server.listen(port);
console.log ('Listening at port ' + port + ' ...');
index.html:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>koa-socket.io</title>
</head>
<body>
<script src="/socket.io/socket.io.js"></script>
<script>
var socket = io('http://localhost:3000');
socket.on('news', function (data) {
console.log('received news with data: ');
console.log(data);
});
function myclick () {
console.log("click");
socket.emit('click', { clickdata: 'i clicked the button' });
}
</script>
<button type="button" onclick="myclick();">Click Me and watch console at server and in browser.</button>
</body>
</html>
I realise this is a little late on the uptake, and could be deemed slightly self-serving as I'm going to suggest one of my own modules, but, you're on the right track with appending it to the app, with Koa v2 this is easier as the context is passed right along but with v1 you can tack it onto this, as koa middleware's are bound to the app instance.
Alternatively, I wrote a module to help with this exact use-case, https://github.com/mattstyles/koa-socket, it does just 2 things currently (and probably forever): it appends the socket.io server instance to the context and it allows you to write koa-style middleware for your socket listeners.
I'm actually working on a little application. I have one server written in C which is listening on the port 5260. In the other side I have a NodeJS client which is listening on the port 7777. A HTML page can be reach via this port. In the HTML page I have a simple button.
When I click on this one a message is sent to my NodeJS server and is written on the terminal. Now I would like to fetch this command and send it to my C server which is still running and waiting for a request.
My client.js :
var http = require('http');
var ejs = require('ejs');
var express=require('express');
var app = express();
app.engine('html', ejs.renderFile);
app.set('/', __dirname);
app.get('/', function(request,response) {
response.render('index.ejs.html');
})
var options = {
host: '192.168.1.154',
path: '/',
port: '5260',
method: 'POST'
};
app.post('/play', function(req, res){
var res = http.request(options);
console.log("START_BG;BG1\n");
});
app.listen(7777);
And my HTML file :
<html>
<head>
<script type="text/javascript" src="client.js"></script>
<script type="text/javascript">
function sendMessage() {
var xhr = new XMLHttpRequest();
xhr.open('POST', '/play', true);
xhr.onload = function() {
console.log(xhr);
};
xhr.send();
}
</script>
</head>
<body>
<button onclick="sendMessage()">VIDEO</button>
</body>
</html>
Well. I see some strange things in your code
1 You're making the post request to 192.168.1.254:5620/play without sending any data on it
2 You're not waiting fro the request to end and blindly print on your console without checking the result. Don't know if its the desired behaviour, but it seems a bit strange
Without more knowledge about the scenario is difficult to suggest an idea.
What is the answer you expect from the remote server?
It's suposed to print something in the (remote) console ?
What it should return via HTTP ?
Anyway I suggest you correct your code as follows:
app.post('/play', function(req, res){
var res = http.request(options, function(response){
// do any checking about response status and/or body if any
console.log("START_BG;BG1\n");
});
});
So, We are implementing some messaging system with signalR.
We included signalR through the latest version of Nuget.
The application is hosted on IIS 7. We have disabled all the URL Rewrite rules.
We are using a hub, see the following code:
[HubName("messages")]
public class Messages : Hub
{
public void Send(string message)
{
Clients.showPopUp(message);
}
}
The include files in the view:
<script src="#Url.Content("~/Scripts/jquery-1.7.1.min.js")" type="text/javascript"></script>
<script src="#Url.Content("~/Scripts/jquery.signalR.js")" type="text/javascript"></script>
<script src="#Url.Content("~/signalr/hubs")" type="text/javascript"></script>
<script src="#Url.Content("~/Scripts/Messages/Messages.js")" type="text/javascript"></script>
Content of Messages.js:
$(function () {
var messages = $.connection.messages;
messages.showPopUp = function (message) {
console.log("test");
};
$.connection.hub.start(function () {
console.log('connected');
});
});
Called when a message is submitted:
$.connection.messages.send($('#Body').val());
So what we get: no errors in Google Chrome console, no xhr request what so over for signal.
We have checked if the /signalr/hubs exists and it does, also /signalr/negotiate returns the following json:
{"Url":"/agenda/signalr","ConnectionId":"a4215b26-32f1-4a52-bf6d-4de096298a07","TryWebSockets":false,"WebSocketServerUrl":null,"ProtocolVersion":"1.0"}
When we call send we get the following in the console:
Uncaught SignalR: Connection must be started before data can be sent. Call .start() before .send()
If we debug signalR, we see start was called, but we don't hit the error or success of the jQuery ajax call and there are no xhtml requests what so ever. What are we doing wrong?
Try checking out this issue: https://github.com/SignalR/SignalR/issues/328
Solution
In jquery.signalR.js change all the
$.ajax(url, {options});
to
$.ajax({ url: url, other options...});
I am running node v0.5.11 pre
and installed socket.io. I have also install socket.io version 0.9.1
I am running server standard.
var io = require('socket.io').listen(8080);
io.sockets.on('connection', function (socket) {
socket.emit('news', { hello: 'world' });
socket.on('my other event', function (data) {
console.log(data);
});
});
which is standard server and following is client ..
<script src="/socket.io/socket.io.js"></script>
<script>
var socket = io.connect('171.69.117.215:8080');
socket.on('news', function (data) {
console.log(data);
socket.emit('my other event', { my: 'data' });
});
</script>
when I load client in Firefox using port 80 from server 171.69.117.215 I get in Firebug following error:
io is not defined
[Break On This Error]
var socket = io.connect('171.69.117.215:8080');
I know it is deployment issue as I am loading from port 80 client, which is right way to deploy socket.io application ?
Thanks in advance.
Please insert into client code ..Point to your on node.js server.
<script src="http://yournodeserver/socket.io/socket.io.js"></script>