7
votes

I am working on open source community project Azure Media Services Upload and Play Videos in MVC since 2015. I was not using any delivery encryption earlier, so I started working on AES.

In all the source code/samples by Azure Media Services Team, i noticed test token was being generated just after uploading the content and this works well in my case too. But, how do I generate test token next time onward for playback?

What I understood is that, we need token each time player requests playback. Technically, player creates a request to key service provider and received updated token.

So to get updated token, I tried couple of ways n not able to fix this, i see error "A ContentKey (Id = '...', Type = 'EnvelopeEncryption') which contains the same type already links to this asset".

enter image description here

This looks like a valid error message because key of type EnvelopeEncryption was already added and associated with asset after uploading content, and upon requesting again this pops-up.

The code given below is copied from here.

    public ActionResult Index()
    {
        var model = new List<VideoViewModel>();

        var videos = db.Videos.OrderByDescending(o => o.Id).ToList();
        foreach (var video in videos)
        {
            var viewModel = new VideoViewModel();
            viewModel.Id = video.Id;
            viewModel.EncodedAssetId = video.EncodedAssetId;
            viewModel.IsEncrypted = video.IsEncrypted;
            viewModel.LocatorUri = video.LocatorUri;

            // If encrypted content, then get token to play
            if (video.IsEncrypted)
            {
                IAsset asset = GetAssetById(video.EncodedAssetId);
                IContentKey key = CreateEnvelopeTypeContentKey(asset);
                viewModel.Token = GenerateToken(key);
            }

            model.Add(viewModel);
        }

        return View(model);
   }

Above method calls media service key service provider.

How do I fix this?

1
Are you looking to integrate with Azure Active directory sign in or you will use your own auth provider? Reason i am asking is because there are more recent examples showing integration with AADGeorge Trifonov
I'm creating Media Services sample MVC open source app. So, this app will be available for everyone, so no authentication as of now. But certainly, user may customize according to their needs. But I don't think AAD or Auth setup will help.Abhimanyu

1 Answers

0
votes

You can look into AMS explorer sources

when you creating a restriction policy yo are doing something like this:

//Initilizing ContentKeyAuthorizationPolicyRestriction
  ContentKeyAuthorizationPolicyRestriction restriction = new ContentKeyAuthorizationPolicyRestriction
  {
      Name = "Authorization Policy with Token Restriction",
      KeyRestrictionType = (int)ContentKeyRestrictionType.TokenRestricted,
      Requirements = TokenRestrictionTemplateSerializer.Serialize(restrictionTemplate)};

  restrictions.Add(restriction);

  //Saving IContentKeyAuthorizationPolicyOption on server so it can be associated with IContentKeyAuthorizationPolicy
  IContentKeyAuthorizationPolicyOption policyOption = objCloudMediaContext.ContentKeyAuthorizationPolicyOptions.Create("myDynamicEncryptionPolicy", ContentKeyDeliveryType.BaselineHttp, restrictions, String.Empty);
  policy.Options.Add(policyOption);

  //Saving Policy
  policy.UpdateAsync();

Key field here is irements = TokenRestrictionTemplateSerializer.Serialize(restriction.Requirements)};

You need to fetch corresponding asset restriction you created first place and desirialize TokenRestriction Template back with

TokenRestrictionTemplate tokenTemplate = TokenRestrictionTemplateSerializer.Deserialize(tokenTemplateString);

Based on what type of key and encryption you use

                            if (tokenTemplate.PrimaryVerificationKey.GetType() == typeof(SymmetricVerificationKey))
                            {
                                InMemorySymmetricSecurityKey tokenSigningKey = new InMemorySymmetricSecurityKey((tokenTemplate.PrimaryVerificationKey as SymmetricVerificationKey).KeyValue);
                                signingcredentials = new SigningCredentials(tokenSigningKey, SecurityAlgorithms.HmacSha256Signature, SecurityAlgorithms.Sha256Digest);
                            }
                            else if (tokenTemplate.PrimaryVerificationKey.GetType() == typeof(X509CertTokenVerificationKey))
                            {
                                if (signingcredentials == null)
                                {
                                    X509Certificate2 cert = DynamicEncryption.GetCertificateFromFile(true).Certificate;
                                    if (cert != null) signingcredentials = new X509SigningCredentials(cert);
                                }
                            }
                            JwtSecurityToken token = new JwtSecurityToken(issuer: tokenTemplate.Issuer, audience: tokenTemplate.Audience, notBefore: DateTime.Now.AddMinutes(-5), expires: DateTime.Now.AddMinutes(Properties.Settings.Default.DefaultTokenDuration), signingCredentials: signingcredentials, claims: myclaims);
                            JwtSecurityTokenHandler handler = new JwtSecurityTokenHandler();
                            string token = handler.WriteToken(token);