Skip navigation
Currently Being Moderated

Problem with custom Authentication Token

Jan 17, 2012 7:13 AM

Tags: #osmf #flash_access #drm #action_script #custom_auth

Hello,

 

I'm trying to use custom authentication token, but i don't manage to get the OSMF based player to send the token to the server.

 

I will describe the whole process that we use to achieve this.

 

the java code to create the policy for custom authentication:

 

import com.adobe.flashaccess.sdk.policy.LicenseServerInfo;
import com.adobe.flashaccess.sdk.policy.Policy;
import com.adobe.flashaccess.sdk.policy.PolicyException;
import com.adobe.flashaccess.sdk.policy.ServerInfo.AuthenticationType;
import com.adobe.flashaccess.sdk.rights.PlayRight;
import com.adobe.flashaccess.sdk.rights.Right;
 
import java.io.FileOutputStream;
import java.io.IOException;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.List;
 
public class CreatePolicy
{
    public static void main(String[] args) {
        Policy policy = new Policy(false);
        policy.setName("custom_policy");
        policy.setLicenseServerInfo(new LicenseServerInfo(AuthenticationType.Custom));
 
    PlayRight play = new PlayRight();
    List<Right> rightsList = new ArrayList<Right>();
    rightsList.add(play);
        policy.setRights(rightsList);
 
        try
        {
            // Serialize the policy                                                                                                                                                                                                                                                                                                                                                                                                      
            byte[] policyBytes = policy.getBytes();
            System.out.println("Created policy with ID: " + policy.getId());
            // Write policy to a file.  Alternatively, the policy could be stored in a database.                                                                                                                                                                                                                                                                                                                                         
            FileOutputStream out = new FileOutputStream("custom.pol");
            out.write(policyBytes);
            out.close();
        } catch (PolicyException e) {
            // The policy could not be created, because required fields were not set.                                                                                                                                                                                                                                                                                                                                                    
            e.printStackTrace();
        } catch (IOException e) {
            // Error writing policy to file                                                                                                                                                                                                                                                                                                                                                                                              
            e.printStackTrace();
        }
    }
}

 

Here is the output of Adobe Policy Manager for this policy:

 

Adobe(R) Flash Access Policy Manager
version 2.0.2.0061
=======================
Policy Report:
=============

Policy ID: 2B765152-4833-3E5E-8C78-B2488E4C987C
Policy Name: custom_policy
Revision: 1

License Server Authentication: custom

Unlimited License Caching

Right: Play

 

Then we modify this policy to add some metadata and use it to package a standard mp4 file.

 

Here is the output of Adobe(R) Flash Access Media Packager for this packaged mp4 file:

 

Adobe(R) Flash Access Media Packager
version 2.0.2.0061
=======================
Source file: mp4_h264_aac_fa2-1326491966.mp4
License Server: http://lic.dev.int.secret.net
License ID: 9EC8E136-9D2D-3D12-B042-7EC97212C1D3
Content ID: 4e6f6bbddede83536f000000.4f10b739dede83376c000000
Packager: CN=MyCorp-PKG-20111123,OU=Adobe Flash Access,OU=Packager,O=Adobe Systems Incorporated,C=US
Packaging time: Fri Jan 13 23:59:25 CET 2012
Policies:


Policy ID: 2B765152-4833-3E5E-8C78-B2488E4C987C
Policy Name: custom_policy
Revision: 2

License Server Authentication: custom

License Caching Duration: 1440 minutes (1 day)

Right: Application Defined Right
    media_id =
        4f10b739dede83376c000000
    user_id =
        4e6f6bbddede83536f000000
Right: Play

CustomProperties: 
    media_id =
        4f10b739dede83376c000000
    user_id =
        4e6f6bbddede83536f000000


SUCCESS

 

The file is stored on a standard HTTP server.

 

Here is the code of the OSMF 1.6 based video player:

 

package
{
     import flash.display.Sprite;
     import flash.utils.ByteArray;
 
     import org.osmf.events.MediaPlayerStateChangeEvent;
     import org.osmf.media.DefaultMediaFactory;
     import org.osmf.media.MediaElement;
     import org.osmf.media.MediaPlayerSprite;
     import org.osmf.media.MediaPlayerState;
     import org.osmf.media.MediaResourceBase;
     import org.osmf.media.URLResource;
     import org.osmf.metadata.MetadataNamespaces;
     import org.osmf.net.StreamingURLResource;
     import org.osmf.traits.DRMTrait;
     import org.osmf.traits.MediaTraitType;
     import org.osmf.events.DRMEvent;
     import org.osmf.traits.DRMState;
 
     public class MyPlayer extends Sprite
     {
          private var protectedMP4:String = "http://secret.net/mp4_h264_aac_fa2-1326491966.mp4";
          private var player:MediaPlayerSprite = null;
          private var streamingResource:StreamingURLResource = null;
 
          public function MyPlayer()
          {
               var factory:DefaultMediaFactory = new DefaultMediaFactory();
               streamingResource = new StreamingURLResource(protectedMP4);
               var mediaElement:MediaElement = factory.createMediaElement(streamingResource);
 
               player = new MediaPlayerSprite();
               addChild(player);
               player.mediaPlayer.addEventListener(DRMEvent.DRM_STATE_CHANGE, this.onDRMStateChange);
 
               player.mediaPlayer.autoPlay = true;
               player.mediaPlayer.media = mediaElement;
          }
 
          protected function onDRMStateChange(event : DRMEvent) : void
          {
                trace('onDRMStateChange ' + event.drmState);
                if (event.drmState == DRMState.AUTHENTICATING)
                {
                    //player.mediaPlayer.authenticateWithToken("token");
                    var drmTrait:DRMTrait = player.mediaPlayer.media.getTrait(MediaTraitType.DRM) as DRMTrait;
                    drmTrait.authenticateWithToken("token");
                }
          }
 
     }
}

 

This code is heavily based on code found in another forum thread about custom token and OSMF

 

the problem is that we don t really know when to use authenticateWithToken() if we call it on the DRMState.AUTHENTICATING event it will loop and stack overflow because calling authenticateWithToken will trigger the AUTHENTICATING event so it will loop until it will stack overflow.

 

I also tried to call it in AUTHENCATION_NEEDED (i had to modify to server code to return this event) but then custom Token is never recieved by the server.

 

For completness here is the part of the server code where i'd like to retrieve the raw authentication token, this code is heavily based on the reference implementation

 


LicenseHandler licenseHandler = null;
 
 
try {
 
 
ServletInputStream in = request.getInputStream();
 
 
ServletOutputStream out = response.getOutputStream();
 
 
HandlerConfiguration context = getHandlerContext();
 
 
ServerCredential licenseServerCred = getLicenseParams().getLicenseServerCred();
 
 
licenseHandler = new LicenseHandler(context, in, out, licenseServerCred);
 
 
licenseHandler.parseRequest();
 
 
List<? extends LicenseRequestMessage> requests = licenseHandler.getRequests();
 
 
// Multiple request in one message is not supported in FAXS 2.0 client.                                                                                                                                                                                                                                                                                                                                                  
 
 
 
 
for (LicenseRequestMessage licenseReq : requests)
 
 
{
 
 
try {
 
 
if (licenseReq.getRawAuthenticationToken() != null)
 
 
{
 
 
LOG.info("We have a auth token");
 
 
LOG.info(licenseReq.getAuthenticationToken());
 
 
}
 
 
else
 
 
{
 
 
LOG.info("No auth token :(");
 
 
licenseReq.setErrorData(AdobeErrorData.LACQ_AUTHENTICATION_REQUIRED);
 
 
}
 
 
 
 
V2ContentMetaData metadata = licenseReq.getContentInfo().getContentMetadata();
 
 
ApplicationProperties applicationProperties = null;
 
 
String usageModelString = null;
 
 
if (metadata != null)
 
 
{
 
 
applicationProperties = metadata.getCustomProperties();
 
 
if (applicationProperties != null)
 
 
{
 
 
//usageModelString = applicationProperties.getSingleValueAsUTF8String(DEMOMODE);                                                                                                                                                                                                                                                                                                                         
 
 
 
 
}
 
 
}
 
 
License license = null;
 
 
license = generateLicense(licenseReq);
 
 
 
 
// If desired, modify the expiration or rights in the license                                                                                                                                                                                                                                                                                                                                                    
 
 
 
 
if (license != null)
 
 
{
 
 
logLicenseInformation(license);
 
 
} else {
 
 
// No license and no error set.                                                                                                                                                                                                                                                                                                                                                                              
 
 
 
 
LOG.error("Unknown error while generating license");
 
 
licenseReq.setErrorData(AdobeErrorData.SERVER_ERROR);
 
 
}
 
 

 

 

licenseReq.getRawAuthenticationToken() always return null, and i checked in the log that this is the good policy that we recieve as the policy id is the same.

 

What are we doing wrong?

 

Thanx

 
Replies
  • Currently Being Moderated
    Jan 19, 2012 8:41 PM   in reply to _sebest_

    DRMState.AUTHENCATION_NEEDED or DRMState.AUTHENTICATION_ERROR is irrelevent to auth token. I suspect that OSMF client does not send out correct token request to license server.

     

    To debug it further, in drmTrait.authenticateWithToken("token"), can you try to  add a logic casting Object to ByteArray for "token"?

     

    Or else, please try to use sample video player implemented by Action Script SDK rather than OSMF.

     
    |
    Mark as:
  • Currently Being Moderated
    Mar 19, 2012 5:45 AM   in reply to _sebest_

    Hi,

     

    I'm wondering if you could contact me with regards the patched version of OSMF you have with the 'delayLoadVoucher' property? I'm having similar issues with OSMF, DRM and custom token authentication.

     

    The authentication request seems to be sent automatically without my authentication code being called and with the DRMTrait, if I listen for the

    DRMState.AUTHENTICATING event the actual event never gets triggered and therefore I cannot seem to authenticate the content.

     
    |
    Mark as:
  • Currently Being Moderated
    Mar 19, 2012 7:11 AM   in reply to _sebest_

    Couly you tell me the version of OSMF it should report?

     

    I can set the delayLoadVoucher no problem however the INITIALIZED event never occurs.

     

    Do you have a contact at Adobe that you might be ablel to provide me with?

     

    Thanks,

    Mat

     
    |
    Mark as:
  • Currently Being Moderated
    Mar 20, 2012 7:44 AM   in reply to n53mat

    n53mat:   If you're still having a problem, I will ask our team internally if there is some resolution to the OSMF problem.   

     

    They may be aware of it.

     

    Regards,


    Stephen

     
    |
    Mark as:
  • Currently Being Moderated
    Mar 27, 2012 6:53 AM   in reply to _sebest_

    The OSMF team has some suggestions and an example of the INITIALIZED state for debug.

     

    Will send it to you via email.

     

    Regards,

     

    Stephen

     
    |
    Mark as:
  • Currently Being Moderated
    Apr 19, 2012 10:33 AM   in reply to Stephen D. [Adobe]

    Stephen,

     

    Is it possible to get the OSMF example emailed to me? Also which version of OSMF is the initialized event supposedf to be added to. I have 2.0.2494 and I don't see INITIALIZED  in the DRMState.as file. Is there a way to tell from the SWC which verison it is? Can I add a listener to see when the DRMTrait is loaded?

     
    |
    Mark as:
  • Currently Being Moderated
    Apr 19, 2012 4:31 PM   in reply to _sebest_

    We attempted to use this fixed OSMF and using this process

     

    If the scenario is "the token is known beforehand through external means and you just want to provide it at the start before the DRM tries to authenticate", then we have a workaround until the proper modification will be made to OSMF DRM-related workflows.

    The basic idea is:

    •       monitor when DRMTrait is added and change its delayLoadVoucher property to true (a new property)

    •       Once the DMRContentData has been set inside the DRMTrait, it will dispatch a new state : INITIALIZED

    •       On this state – you can use authenticateWithToken or authenticate to start the protected content workflow

     

     

    Unfortunatly it did not work. You never get an opertunity to call drmTrait.authenticateWithToken(); 

     

    I'll do a post with a solution we got working with Katherine and Eric's help

     
    |
    Mark as:
  • Currently Being Moderated
    Apr 19, 2012 4:54 PM   in reply to _sebest_

    Since the name of the content lets call it Video1.f4v always has a metadata file on the server called Video1.f4v.metadata we do the following.

     

    Step 1. Create a urlloader and load the meta data file.

    Step 2. Call DRMManager.getDRMManager().setAuthenticationToken.

    Step 3. Play the content

     

    Here is some example source code. Please note you will require to set up the server side and by on a machine

     

    package

    {

        import flash.display.MovieClip;

        import flash.events.Event;

        import flash.net.URLLoader;

        import flash.net.URLLoaderDataFormat;

        import flash.net.URLRequest;

        import flash.net.drm.DRMContentData;

        import flash.net.drm.DRMManager;

        import flash.system.Capabilities;

        import flash.utils.ByteArray;

        import org.osmf.containers.MediaContainer;

        import org.osmf.elements.VideoElement;

        import org.osmf.media.MediaPlayer;

        import org.osmf.media.URLResource;

        import org.osmf.net.NetLoader;

     

     

        //Sets the size of the SWF

        [SWF(width="800", height="600")]

     

        public class PluginTest2 extends MovieClip

        {

     

            ////////////////////////////////////////////////////

            //DECLARATIONS

            ////////////////////////////////////////////////////

            public var urlLoader:URLLoader = new URLLoader();

            // Media Objects

            public var player:MediaPlayer;

            public var container:MediaContainer;

            // Customer datapacker class

            public var currentVideo:String = new String();

            public var currentVideoMetadata:String = new String();

     

            ////////////////////////////////////////////////////

            //CONSTRUCTOR

            ////////////////////////////////////////////////////

     

            public function PluginTest2()

            {

                trace("DRMManager supported " + DRMManager.isSupported);

                trace("FlashPlayer Version " + Capabilities.version );

     

                if ( DRMManager.isSupported == true ) {

                   initPlayer();

                }

            }

     

            ////////////////////////////////////////////////////

            // Set up and init a URL request

            ////////////////////////////////////////////////////

     

            public function initPlayer():void

            {

                currentVideo = "http://192.168.0.51:8080/content/lq2.f4v"

                currentVideoMetadata = "http://192.168.0.51:8080/content/lq2.f4v.metadata"

                urlLoader.dataFormat = URLLoaderDataFormat.BINARY;

                urlLoader.addEventListener(Event.COMPLETE,onUrlLoaded);

                urlLoader.load(new URLRequest(currentVideoMetadata));   

            }

     

            private function onUrlLoaded(evt:Event ):void {

                var strAuthToken:String = new String("A Valid Token");

                var authToken:ByteArray = new ByteArray();

                authToken.writeObject(strAuthToken);

                var drmContentData:DRMContentData = new DRMContentData(urlLoader.data);

                DRMManager.getDRMManager().setAuthenticationToken(drmContentData.serv erURL,drmContentData.domain,authToken);

                playContent();

            }

     

            private function playContent():void{

                var resource:URLResource = null;

                resource = new URLResource( currentVideo );

                resource.mimeType = "video/mp4";

                 var netLoader:NetLoader = new NetLoader();

                 var element:VideoElement = new VideoElement( resource, netLoader );

                player = new MediaPlayer( element );

                 container = new MediaContainer();

                container.addMediaElement( element );

                container.width = 300;

                container.height = 200;

                //Adds the container to the stage

                this.addChild(container);

            }

     

        }

    }

     
    |
    Mark as:
  • Currently Being Moderated
    Feb 19, 2013 10:20 AM   in reply to Stephen D. [Adobe]

    Hi Stephen,

     

    Can you email the example to me too?

     

    Thx,

     
    |
    Mark as:
  • Currently Being Moderated
    Jan 7, 2014 9:31 AM   in reply to jimkoning

    Can I also get a copy of this OSMF version which has the DRMState.INITIALIZED available

     

    Many thanks

     
    |
    Mark as:
  • Currently Being Moderated
    Jan 10, 2014 9:31 AM   in reply to eoinlandyc4

    Jim and Eoin,

     

    You should receive this patch soon via your account contacts.

     

    The team is deciding about how to best publish this patch, since several have asked for it.

     

    Regards,

     

    Stephen

     
    |
    Mark as:
  • Currently Being Moderated
    Jan 27, 2014 12:34 PM   in reply to Stephen D. [Adobe]

    I'd also like to request a copy of the lastest OSMF version (swc+source if possible).

    We are AAXS customers, but not sure who our account contact is.

     

    Thanks,

    - Abey

     

    Abey George

     
    |
    Mark as:
  • Currently Being Moderated
    Feb 5, 2014 2:02 PM   in reply to Stephen D. [Adobe]

    Could I also be added to the list to receive this patch?

     

    Thank you.

     
    |
    Mark as:
  • Currently Being Moderated
    Mar 26, 2014 6:30 PM   in reply to Stephen D. [Adobe]

    Has there been an update to this?

     

    Yes could you also add me to the list.

     
    |
    Mark as:

More Like This

  • Retrieving data ...

Bookmarked By (0)

Answers + Points = Status

  • 10 points awarded for Correct Answers
  • 5 points awarded for Helpful Answers
  • 10,000+ points
  • 1,001-10,000 points
  • 501-1,000 points
  • 5-500 points