opentok/opentok-node

createSession modifies passed in options object

Closed this issue · 5 comments

Using this api and passing the options { mediaMode : "routed" } doesn't actually seem to created a routed connection. When I connect iOS clients they can't publish to more than one subscriber.... however, if I hard code tokens and session ids generated by the online dashboard for OpenTok, everything works perfectly.

I'm now going to implement a version of my own using the OpenTok REST api and the "https" request module to see if this avoids the issue.

So I wrote this to test the session id as generated via the REST api and fixed my problem:

var http = require('https');
var qs = require('qs');
var xmljson = require('xmljson').to_json;

function invoke(url, params, callback)
{
    try
    {
        var postData = qs.stringify(params || {});
        var options = {
            host: 'api.opentok.com',
            path: url,
            method: 'POST',
            headers: {
                'Content-Type': 'application/x-www-form-urlencoded',
                'Content-Length': postData.length,
                'X-TB-PARTNER-AUTH' : global.config.opentok.key+':'+global.config.opentok.secret,
            },
        };
        var req = http.request(options, function(res){
            var str = "";
            res.setEncoding('utf8');
            res.on('data', function (chunk) { str += chunk; });
            res.on('end', function () {
                xmljson(str,callback);
            });
        });
        req.on('error',function(e){
            if (callback) callback(e);
        });
        req.write(postData);
        req.end();
    }
    catch (ex)
    {
        if (callback) callback(ex);
    }
}

exports.createSession = function(callback)
{
    invoke('/hl/session/create',{ 'p2p.preference' : 'disabled' },function(err,data){
        if (err || !data)
        {
            callback(err || "Unable to issue session id");
        }
        else
        {
            callback(false,data.sessions.Session.session_id);
        }
    });
};

@EvilTrev that's interesting... Can you give me a Session ID that was generated from the SDK (not your REST experiment) so I can take a look at why it might not be routed?

I've worked out what is going on... so I put this code back in place:

exports.createSession = function(callback)
{
    console.log("Options :",global.config.opentok.options);
    opentok.createSession(global.config.opentok.options, function(err,session){
        if (err || !session)
        {
            if (callback) callback(err || "No session");
        }
        else
        {
            console.log("SessionId :",session.sessionId);
            if (callback) callback(err,session.sessionId);
        }
    });
}

And here is the output from a couple of attempts:

Options : { mediaMode: 'routed' }
SessionId : 1_MX4zMzQ1NzkzMn5-MTQyMTg3ODcwODkzMH44VTB3ZVNqZ3gwQW5HanBCUVM3M29hamZ-fg

Options : { 'p2p.preference': 'disabled' }
SessionId : 2_MX4zMzQ1NzkzMn5-MTQyMTg3ODgwMTUyM34wSy84eExxRHRzYmpDVm42N2R5N1JQZ0Z-UH4

It looks like my shared and static config object being passed in is modified by the function used to create session keys. The first attempt works, the following attempts do not (due to alterations).

@EvilTrev wow that's a tricky one, but good catch.

It looks like the implementation actually does copy the options as backupOpts because we intended not to alter that object, but then we ignored that and altered it anyway. Should be a straight forward fix. Would accept PR :)

I'm just glad to help out!