Configurar o SDK do IMA para DAI

Selecione a plataforma: HTML5 Android iOS tvOS Cast Roku

Os SDKs do IMA facilitam a integração de anúncios multimídia aos seus sites e apps. Os SDKs do IMA podem solicitar anúncios de qualquer servidor de anúncios compatível com VAST e gerenciar a reprodução de anúncios nos seus apps. Com os SDKs de DAI do IMA, os apps fazem uma solicitação de stream para anúncios e vídeos de conteúdo, sejam eles VOD ou ao vivo. Em seguida, o SDK retorna um stream de vídeo combinado para que você não precise gerenciar a troca entre o anúncio e o vídeo de conteúdo no app.

Selecione a solução de DAI que você quer usar

DAI de serviço completo

Este guia demonstra como integrar o SDK do IMA DAI a um app player de vídeo simples. Se você quiser ver ou acompanhar um exemplo de integração concluído, baixe o exemplo básico do GitHub.

Visão geral da DAI da IMA

A implementação da DAI da IMA envolve dois componentes principais do SDK, conforme demonstrado neste guia:

  • StreamRequest: Um objeto que define uma solicitação de stream. As solicitações de streaming podem ser para vídeo on demand ou transmissões ao vivo. As solicitações de transmissão ao vivo especificam uma chave de recurso, enquanto as de VOD especificam um ID do CMS e um ID do vídeo. Os dois tipos de solicitação podem incluir opcionalmente uma chave de API necessária para acessar streams especificados e um código de rede do Google Ad Manager para que o SDK do IMA processe os identificadores de anúncios conforme especificado nas configurações do Google Ad Manager.
  • StreamManager: um objeto que processa streams de inserção de anúncios dinâmicos e interações com o back-end da DAI. O gerenciador de stream também processa pings de rastreamento e encaminha eventos de stream e de anúncio para o publisher.

Pré-requisitos

Assistir o vídeo

O player de vídeo de exemplo fornecido reproduz um vídeo de conteúdo pronto para uso. Implante o player de amostra no seu player Roku para garantir que o ambiente de desenvolvimento esteja configurado corretamente.

Transforme seu player de vídeo em um player de stream da DAI da IMA

Siga estas etapas para implementar um player de stream.

Criar Sdk.xml

Adicione um novo arquivo ao projeto ao lado de MainScene.xml chamado Sdk.xml e adicione o seguinte modelo:

Sdk.xml

<?xml version = "1.0" encoding = "utf-8" ?>

<component name = "imasdk" extends = "Task">
<interface>
</interface>
<script type = "text/brightscript">
<![CDATA[
  ' Your code goes here.
]]>
</script>
</component>

Você precisará editar os dois arquivos ao longo deste guia.

Carregar o framework de publicidade do Roku

O SDK de DAI do IMA depende do framework de publicidade do Roku. Para carregar o framework, adicione o seguinte a manifest e Sdk.xml:

bs_libs_required=roku_ads_lib,googleima3
Library "Roku_Ads.brs"
Library "IMA3.brs"

Carregar o SDK da DAI do IMA

Para carregar o SDK DAI do IMA, faça o seguinte:

  1. Inicialize o SDK do IMA com a chamada New_IMASDK():

    sub loadSdk()
      If m.sdk = invalid
        m.sdk = New_IMASDK()
      End If
      m.top.sdkLoaded = true
    End Sub
    
  2. Verifique se a IMA foi carregada criando um campo booleano sdkLoaded:

    <field id="sdkLoaded" type="Boolean" />
    
  3. Chame a sub-rotina loadSdk() da sub-rotina principal runThread():

    if not m.top.sdkLoaded
      loadSdk()
    End If
    
  4. Crie a função loadImaSdk() em MainScene.xml para criar e executar o objeto sdkTask:

    function loadImaSdk() as void
      m.sdkTask = createObject("roSGNode", "imasdk")
      m.sdkTask.observeField("sdkLoaded", "onSdkLoaded")
      m.sdkTask.observeField("errors", "onSdkLoadedError")
    
      ' Change to m.testLiveStream to demo live instead of VOD.
      selectedStream = m.testVodStream
      m.videoTitle = selectedStream.title
      m.sdkTask.streamData = selectedStream
    
      m.sdkTask.observeField("urlData", "urlLoadRequested")
      m.sdkTask.video = m.video
      ' Setting control to run starts the task thread.
      m.sdkTask.control = "RUN"
    end function
    
  5. Chame a função loadImaSdk() da função init().

  6. Crie as sub-rotinas de listener onSdkLoaded() e onSdkLoadedError() para responder a eventos de carregamento do SDK:

    Sub onSdkLoaded(message as Object)
      print "----- onSdkLoaded --- control ";message
    End Sub
    
    Sub onSdkLoadedError(message as Object)
      print "----- errors in the sdk loading process --- ";message
    End Sub
    

Criar um player de stream da IMA

Para criar um player de stream da IMA, faça o seguinte:

  1. Crie uma sub-rotina setupVideoPlayer() que faça o seguinte:

    1. Use o método createPlayer() para criar o player de stream.

    2. Faça com que o player de stream implemente três métodos de callback: loadUrl, adBreakStarted e adBreakEnded.

    3. Desative o truque de reprodução quando o stream for carregado para evitar que os usuários pulem um anúncio precedente no momento em que o stream começa, antes que o evento de início do intervalo comercial seja acionado.

    sub setupVideoPlayer()
      sdk = m.sdk
      m.player = sdk.createPlayer()
      m.player.top = m.top
      m.player.loadUrl = Function(urlData)
        ' This line prevents users from scanning during buffering
        ' or during the first second of the ad before we have a callback from roku.
        ' If there are no prerolls disabling trickplay isn't needed.
        m.top.video.enableTrickPlay = false
        m.top.urlData = urlData
      End Function
      m.player.adBreakStarted = Function(adBreakInfo as Object)
        print "---- Ad Break Started ---- "
        m.top.adPlaying = True
        m.top.video.enableTrickPlay = false
      End Function
      m.player.adBreakEnded = Function(adBreakInfo as Object)
        print "---- Ad Break Ended ---- "
        m.top.adPlaying = False
        m.top.video.enableTrickPlay = true
      End Function
      m.player.seek = Function(timeSeconds as Double)
        print "---- SDK requested seek to ----" ; timeSeconds
        m.top.video.seekMode = "accurate"
        m.top.video.seek = timeSeconds
      End Function
    End Sub
    

    Adicione um método de callback seek para oferecer suporte a anúncios puláveis. Para mais detalhes, consulte Adicionar suporte a anúncios puláveis.

  2. Adicione os campos urlData, adPlaying e video usados na sub-rotina setupVideoPlayer():

    <field id="urlData" type="assocarray" />
    <field id="adPlaying" type="Boolean" />
    <field id="video" type="Node" />
    

Criar e executar uma solicitação de stream

Para solicitar seu stream da DAI, faça o seguinte:

  1. Crie uma sub-rotina loadStream() para criar e solicitar um stream. Para oferecer suporte à interface do usuário de anúncios, como ícones do AdChoices, também é necessário transmitir uma referência ao nó que contém o vídeo de conteúdo como parte da solicitação:

    Sub loadStream()
      sdk = m.sdk
      sdk.initSdk()
      setupVideoPlayer()
    
      request = {}
      streamData = m.top.streamData
      if streamData.type = "live"
        request = sdk.CreateLiveStreamRequest(streamData.assetKey, streamData.apiKey, streamData.networkCode)
      else if streamData.type = "vod"
        request = sdk.CreateVodStreamRequest(streamData.contentSourceId, streamData.videoId, streamData.apiKey, streamData.networkCode)
      else
        request = sdk.CreateStreamRequest()
      end if
    
      request.player = m.player
      request.adUiNode = m.top.video
    
      requestResult = sdk.requestStream(request)
      If requestResult <> Invalid
        print "Error requesting stream ";requestResult
      Else
        m.streamManager = Invalid
        While m.streamManager = Invalid
          sleep(50)
          m.streamManager = sdk.getStreamManager()
        End While
        If m.streamManager = Invalid or m.streamManager["type"] <> Invalid or m.streamManager["type"] = "error"
          errors = CreateObject("roArray", 1, True)
          print "error ";m.streamManager["info"]
          errors.push(m.streamManager["info"])
          m.top.errors = errors
        Else
          m.top.streamManagerReady = True
          addCallbacks()
          m.streamManager.start()
        End If
      End If
    End Sub
    
  2. Adicione os campos streamData e streamManagerReady usados na sub-rotina loadStream():

    <field id="streamManagerReady" type="Boolean" />
    <field id="streamData" type="assocarray" />
    
  3. Se o gerenciador de streams não estiver disponível, chame a sub-rotina loadStream() da sub-rotina runThread():

    if not m.top.streamManagerReady
      loadStream()
    End If
    
  4. Selecione entre um VOD ou uma transmissão ao vivo. O exemplo a seguir tem parâmetros de stream para uma transmissão ao vivo e um stream de VOD:

    m.testLiveStream = {
      title: "Live Stream",
      assetKey: "c-rArva4ShKVIAkNfy6HUQ",
      networkCode: "21775744923",
      apiKey: "",
      type: "live"
    }
    m.testVodStream = {
      title: "VOD stream"
      contentSourceId: "2548831",
      videoId: "tears-of-steel",
      networkCode: "21775744923",
      apiKey: "",
      type: "vod"
    }
    

    Por padrão, este guia usa o stream de VOD. É possível usar a transmissão ao vivo em vez disso, mudando a variável selectedStream do objeto m.testVodStream para o objeto m.testLiveStream.

Iniciar o stream

Crie a sub-rotina urlLoadRequested() para detectar os dados de stream e chame a sub-rotina playStream():

Sub urlLoadRequested(message as Object)
  print "Url Load Requested ";message
  data = message.getData()

  playStream(data.manifest, data.format)
End Sub

Crie o playStream() para iniciar a reprodução do stream:

Sub playStream(url as String, format as String)
  vidContent = createObject("RoSGNode", "ContentNode")
  vidContent.url = url
  vidContent.title = m.videoTitle
  vidContent.streamformat = format
  m.video.content = vidContent
  m.video.setFocus(true)
  m.video.visible = true
  m.video.control = "play"
  m.video.EnableCookies()
End Sub

Ouvir metadados de stream

Crie a sub-rotina runLoop() com um loop "while" para ser executada durante a reprodução do stream e envie metadados de stream para a IMA usando StreamManager.onMessage():

Sub runLoop()
  ' Forward all timed metadata events.
  m.top.video.timedMetaDataSelectionKeys = ["*"]

  ' Cycle through all the fields and just listen to them all.
  m.port = CreateObject("roMessagePort")
  fields = m.top.video.getFields()
  for each field in fields
    m.top.video.observeField(field, m.port)
  end for

  while True
    msg = wait(1000, m.port)
    if m.top.video = invalid
      print "exiting"
      exit while
    end if

    m.streamManager.onMessage(msg)
    currentTime = m.top.video.position
    ' Only enable trickplay after a few seconds, in case we start with an ad,
    ' to prevent users from skipping through that ad.
    If currentTime > 3 And not m.top.adPlaying
       m.top.video.enableTrickPlay = true
    End If
  end while
End Sub

Detectar eventos de anúncios

Agora que você está transmitindo metadados para a IMA, ela pode emitir eventos de anúncio durante os intervalos. Crie listeners de eventos de anúncio conforme necessário para responder a eventos de anúncio:

Function addCallbacks() as Void
  m.streamManager.addEventListener(m.sdk.AdEvent.ERROR, errorCallback)
  m.streamManager.addEventListener(m.sdk.AdEvent.START, startCallback)
  m.streamManager.addEventListener(m.sdk.AdEvent.FIRST_QUARTILE, firstQuartileCallback)
  m.streamManager.addEventListener(m.sdk.AdEvent.MIDPOINT, midpointCallback)
  m.streamManager.addEventListener(m.sdk.AdEvent.THIRD_QUARTILE, thirdQuartileCallback)
  m.streamManager.addEventListener(m.sdk.AdEvent.COMPLETE, completeCallback)
End Function

Function startCallback(ad as Object) as Void
  print "Callback from SDK -- Start called - "
End Function

Function firstQuartileCallback(ad as Object) as Void
  print "Callback from SDK -- First quartile called - "
End Function

Function midpointCallback(ad as Object) as Void
  print "Callback from SDK -- Midpoint called - "
End Function

Function thirdQuartileCallback(ad as Object) as Void
  print "Callback from SDK -- Third quartile called - "
End Function

Function completeCallback(ad as Object) as Void
  print "Callback from SDK -- Complete called - "
End Function

Function errorCallback(error as Object) as Void
  print "Callback from SDK -- Error called - "; error
  ' errors are critical and should terminate the stream.
  m.errorState = True
End Function

Adicionar suporte para anúncios puláveis (opcional)

Para oferecer suporte a anúncios puláveis, adicione um método seek ao objeto player do SDK da DAI do IMA, que busca programaticamente o vídeo até o local especificado, em segundos de ponto flutuante.

Para oferecer suporte a anúncios puláveis, defina o adUiNode na sua solicitação.

m.player.seek = Function(timeSeconds as Double)
  print "---- SDK requested seek to ----" ; timeSeconds
  m.top.video.seekMode = "accurate"
  m.top.video.seek = timeSeconds
End Function