Article: How to protect streaming using SecureToken in Wowza Streaming Engine

From turning on the debug logs, it seems to me that ModuleCoreSecurity is stripping off everything after and including the “=” sign so the hashes don’t match. Is this a bug?

_JVKyN33KaexRqoTo2LAbwICidR22K3msulK0pBcWZI= hash sent

INFO session connect-pending 192.168.5.56 -

INFO server comment - ModuleCoreSecurity.onConnect[live/streamer-1/]: isPublisher:false FlashVer: LNX 16,0,0,305

INFO server comment - ModuleCoreSecurity.onConnect[live/streamer-1/]: Initiate SecureToken Authorization.

INFO server comment - ModuleCoreSecurity.onConnect[live/streamer-1/]: All security checks passed.

INFO session connect 192.168.5.56 -

INFO stream create - -

INFO server comment - ModuleCoreSecurity.play[live/streamer-1/stream]: Check SecureToken Authorization.

INFO server comment - [live/streamer-1]ModuleCoreSecurity:current time stamp: 1423146360

INFO server comment - [live/streamer-1]ModuleCoreSecurity:clientId: 23217498

INFO server comment - [live/streamer-1]ModuleCoreSecurity:hashReceived: _JVKyN33KaexRqoTo2LAbwICidR22K3msulK0pBcWZI

INFO server comment - [live/streamer-1]ModuleCoreSecurity:creating RTMP token for ClientId:23217498 uri:rtmp://192.168.5.56:1935/live/streamer-1/stream

WARN server comment - ModuleCoreSecurity[live/streamer-1] Invalid value for token start time: null

WARN server comment - ModuleCoreSecurity[live/streamer-1] Invalid value for token end time: null

INFO server comment - [live/streamer-1]ModuleCoreSecurity:client IP: 192.168.5.56

INFO server comment - [live/streamer-1]ModuleCoreSecurity:hashCalculated: _JVKyN33KaexRqoTo2LAbwICidR22K3msulK0pBcWZI=

INFO server comment - [live/streamer-1]ModuleCoreSecurity:string hashed: live/streamer-1/stream?secret

INFO server comment - [live/streamer-1]ModuleCoreSecurity:token start time stamp: 0

INFO server comment - [live/streamer-1]ModuleCoreSecurity:token end time stamp: 0

INFO server comment - [live/streamer-1]SecureTokenDef:Hash _JVKyN33KaexRqoTo2LAbwICidR22K3msulK0pBcWZI, doesn’t match hash calculated, _JVKyN33KaexRqoTo2LAbwICidR22K3msulK0pBcWZI=

INFO session comment 23217498 ModuleCoreSecurity.play[live/streamer-1/stream]: SecureToken failed. clientId: 23217498 play denied: clientId:23217498

INFO stream destroy - -

INFO session disconnect 23217498 -

And again with _JVK=1234 hash sent

INFO session connect-pending 192.168.5.56 -

INFO server comment - ModuleCoreSecurity.onConnect[live/streamer-1/]: isPublisher:false FlashVer: LNX 16,0,0,305

INFO server comment - ModuleCoreSecurity.onConnect[live/streamer-1/]: Initiate SecureToken Authorization.

INFO server comment - ModuleCoreSecurity.onConnect[live/streamer-1/]: All security checks passed.

INFO session connect 192.168.5.56 -

INFO stream create - -

INFO server comment - ModuleCoreSecurity.play[live/streamer-1/stream]: Check SecureToken Authorization.

INFO server comment - [live/streamer-1]ModuleCoreSecurity:current time stamp: 1423146740

INFO server comment - [live/streamer-1]ModuleCoreSecurity:clientId: 452295755

INFO server comment - [live/streamer-1]ModuleCoreSecurity:hashReceived: _JVK

INFO server comment - [live/streamer-1]ModuleCoreSecurity:creating RTMP token for ClientId:452295755 uri:rtmp://192.168.5.56:1935/live/streamer-1/stream

WARN server comment - ModuleCoreSecurity[live/streamer-1] Invalid value for token start time: null

WARN server comment - ModuleCoreSecurity[live/streamer-1] Invalid value for token end time: null

INFO server comment - [live/streamer-1]ModuleCoreSecurity:client IP: 192.168.5.56

INFO server comment - [live/streamer-1]ModuleCoreSecurity:hashCalculated: _JVKyN33KaexRqoTo2LAbwICidR22K3msulK0pBcWZI=

INFO server comment - [live/streamer-1]ModuleCoreSecurity:string hashed: live/streamer-1/stream?secret

INFO server comment - [live/streamer-1]ModuleCoreSecurity:token start time stamp: 0

INFO server comment - [live/streamer-1]ModuleCoreSecurity:token end time stamp: 0

INFO server comment - [live/streamer-1]SecureTokenDef:Hash _JVK, doesn’t match hash calculated, _JVKyN33KaexRqoTo2LAbwICidR22K3msulK0pBcWZI=

INFO session comment 452295755 ModuleCoreSecurity.play[live/streamer-1/stream]: SecureToken failed. clientId: 452295755 play denied: clientId:452295755

INFO stream destroy - -

INFO session disconnect 452295755 -

This is fixed in 4.1.1

There appeared to be a bug that would strip off the trailing “=” from the received hash meaning it would never match the wowza calculated hash.

Update fixed it.

From your example you need to adjust your hash paramiter to the following

$string = “vod/sample.mp4?192.168.1.2&mySharedSecret&myTokenPrefixCustomParameter=abcdef&myTokenPrefixendtime=1500000000&myTokenPrefixstarttime=1395230400”;

$hash = hash(‘sha256’, $string, 1);

this will generate the SHA-256 string and output as a BASE64 encoded string.

you then need to sanitise or URL Safe the string.

hop that helps

@Wowza: I agree with these guys the documentation regarding hashing really could use some examples on the acctual generation of the hash

e.g Showing a code example of how to generate the correctly formatted hash in php, classic asp and asp.net would be a good idea.

? question

Important: The client web server should generate the hash when it generates the client webpage. You shouldn’t use JavaScript code in the client webpage to generate the hash as the code is visible in the webpage source and would pose a potential security risk.

as I talked about above, If you do not create hash from a web page, how do I generate from where?

Hash value is corrected…

Are the hashes used in this guide accurate?

Using the quoted string above I get a URL safe base64 encoded SHA256 hash as follows:

kJ591xB2lT-X0OA9UdoRx61uwp6A_IoSc_jCx_9h1l8=

This might seem a pedantic question, but if a guide is there to follow then I need a working example.

Patrickz’s post was very useful. Here’s how I tackled this in a .Net 4.5 web app:

using System;
using System.Net;
using System.Security.Cryptography;
using System.Text;
namespace MyMediaServer
{
    public class MyMediaStream
    {
        public static string Get()
        {
            var wowzaContentURL = "http://example.com:1935/MyVodApp/mp4:sample.mp4/playlist.m3u8";
            var wowzaContentPath = "MyVodApp/mp4:sample.mp4";
            var wowzaSecureToken = "abc123";
            var wowzaTokenPrefix = "MyToken";
            var wowzaCustomParameter = wowzaTokenPrefix + "CustomParameter=myParameter";
            var wowzaSecureTokenStartTime = wowzaTokenPrefix + "starttime=" + DateTimeToUnixTimeStamp(DateTime.Now);
            var wowzaSecureTokenEndTime = wowzaTokenPrefix + "endtime=" + DateTimeToUnixTimeStamp(DateTime.Now.AddHours(2));
            // hashstr should = "MyVodApp/mp4:sample.mp4?abc123&MyTokenCustomParameter=myParameter&MyTokenendtime=1432676901.3294&MyTokenstarttime=1432669696.2954"
            var hashstr = wowzaContentPath + "?" + wowzaSecureToken  + "&" + wowzaCustomParameter + "&" + wowzaSecureTokenEndTime + "&" + wowzaSecureTokenStartTime;
            SHA256 sha256 = new SHA256Managed();
            var sha256Bytes = Encoding.Default.GetBytes(hashstr);
            var cryString = sha256.ComputeHash(sha256Bytes);
            var usableHash = Convert.ToBase64String(cryString).Replace("+", "-").Replace("/", "_");
            // I got "d1b-2bc4Sd86k2OwKp0c8fYFzyvCNjReModi_IyVHw8="
            // which means url should = "http://example.com:1935/MyVodApp/mp4:sample.mp4/playlist.m3u8?MyTokenstarttime=1432669696.2954&MyTokenendtime=1432676901.3294&MyTokenCustomParameter=myParameter&MyTokenhash=d1b-2bc4Sd86k2OwKp0c8fYFzyvCNjReModi_IyVHw8="
            var url = wowzaContentURL + "?" + wowzaSecureTokenStartTime + "&" + wowzaSecureTokenEndTime + "&" + wowzaCustomParameter + "&" + wowzaTokenPrefix + "hash=" + usableHash;
            WebRequest request = WebRequest.Create(url);
            request.Method = "POST";
            request.ContentType = "application/x-www-form-urlencoded";
            WebResponse response = request.GetResponse();
            Uri uri = response.ResponseUri;
            response.Close();
            // Wowza Media Server returns uri.AbsoluteUri:
            // http://example.com:1935/MyVodApp/mp4:sample.mp4/playlist.m3u8?MyTokenstarttime=1432669696.2954&MyTokenendtime=1432676901.3294&MyTokenCustomParameter=myParameter&MyTokenhash=d1b-2bc4Sd86k2OwKp0c8fYFzyvCNjReModi_IyVHw8=
            return uri.AbsoluteUri;
        }
        private static double DateTimeToUnixTimeStamp(DateTime dateTime)
        {
            return (dateTime - new DateTime(1970, 1, 1).ToLocalTime()).TotalSeconds;
        }
    }
}

I’ve tested this (using my domain and shared secret) and it works. The next step for me is JW Player integration.

can any one tell me

How to protect streaming using SecureToken in Wowza Streaming Engine using java

@vikas kumar This workflow is updated and will provide you with the most current steps.

https://www.wowza.com/docs/how-to-protect-streaming-using-securetoken-in-wowza-streaming-engine

thanks, I can work :slight_smile:

i add ip in hash it not working. pls help me