cniElementAsBitstream

Obtém a representação de fluxo de bits do elemento especificado. O analisador que está associado ao elemento serializa o elemento e todos os seus filhos. O resultado é copiado para a memória alocada pelo responsável pela chamada. No caso especial em que todas as opções especificadas correspondem às do fluxo de bits originais, por exemplo, um fluxo de bits que é lido de uma fila do WebSphere MQ pelo nó MQInput e a mensagem não foi modificada desde o recebimento do fluxo de bits original, esse fluxo de bits original será copiado na memória alocada pelo usuário. Nesse caso, o analisador não precisa analisar e serializar novamente a mensagem.

O algoritmo utilizado para gerar o fluxo de bits depende do analisador sendo utilizado e das opções especificadas. Todos os analisadores suportam os seguintes modos:
  • RootBitStream, no qual o algoritmo de geração do fluxo de bits é igual ao utilizado por um nó output. Neste modo, um resultado significativo é obtido apenas se o elemento apontado estiver no topo de uma subárvore com uma estrutura apropriada.
  • EmbeddedBitStream, o qual não é apenas o algoritmo de geração de fluxo de bits igual ao utilizado por um nó output, mas também os seguintes são determinados, se não explicitamente especificados, da mesma forma que o nó output, que significa que eles são determinados pela procura dos irmãos anteriores do elemento na hipótese de que estes representam os cabeçalhos:
    • Codificação
    • CCSID
    • Conjunto de Mensagens
    • Tipo de Mensagem
    • Formato de Mensagem

    Dessa forma, o algoritmo para determinar estas propriedades é essencialmente igual ao utilizado para a função ESQL BITSTREAM.

Alguns analisadores também suportam outro modo, FolderBitStream, que gera um fluxo de bits significativo para qualquer subárvore, desde que o campo apontado represente uma pasta.

Sintaxe

CciSize cniElementAsBitstream(
    int*            returnCode,
    CciElement*      element,
    const struct CciByteArray* value,
    CciChar*                   messageType,
    CciChar*                   messageSet,
    CciChar*                   messageFormat,
    int            encoding,
    int            ccsid,
    int                        options);

Parâmetros

returnCode
O código de retorno da função (saída). Especificar um ponteiro NULL significa que o nó não deseja lidar com erros. Se a entrada não for NULL, a saída significa o status de êxito da chamada. Quaisquer exceções lançadas durante a execução desta chamada serão lançadas novamente para o próximo nó acima no fluxo. Chame cciGetLastExceptionData para obter detalhes da exceção.
Os possíveis códigos de retorno são:
  • CCI_SUCCESS
  • CCI_EXCEPTION
  • CCI_INV_ELEMENT_OBJECT
  • CCI_INV_DATA_POINTER
  • CCI_INV_DATA_BUFLEN
  • CCI_INV_BUFFER_TOO_SMALL
elemento
O elemento de sintaxe a ser serializado (entrada).
O elemento de sintaxe a ser serializado (entrada). Deve ser o último filho da raiz da mensagem.
value
Um ponteiro para uma estrutura CciByteArray contendo um ponteiro para uma região de memória alocada pelo responsável pela chamada, e o tamanho em CciBytes dessa memória (saída).
messageType
A definição de tipo de mensagem utilizada para criar o fluxo de bits a partir da árvore de elementos (entrada). Um ponteiro NULL significa que este parâmetro é ignorado. Além disso, se o analisador associado ao elemento não tiver interesse neste valor, por exemplo, se ele for um analisador XML genérico, o parâmetro é ignorado.
messageSet
A definição de conjunto de mensagem utilizada para criar o fluxo de bits a partir da árvore de elementos (entrada). Um ponteiro NULL significa que este parâmetro é ignorado. Além disso, se o analisador associado ao elemento não tiver interesse neste valor, por exemplo, se ele for um analisador XML genérico, o parâmetro também é ignorado.
messageFormat
O formato utilizado para criar o fluxo de bits a partir da árvore de elementos (entrada). Um ponteiro NULL significa que este parâmetro é ignorado. Além disso, se o analisador associado ao elemento não tiver interesse neste valor, por exemplo, se ele for um analisador XML genérico, o parâmetro é ignorado.
encoding
A codificação a ser utilizada ao gravar o fluxo de bits (entrada). Esse parâmetro é obrigatório. Você pode especificar um valor de 0 para indicar que a codificação do gerenciador de filas deve ser utilizada.
ccsid
O identificador do conjunto de caracteres codificados a ser utilizado ao gravar o fluxo de bits (entrada). Esse parâmetro é obrigatório. Você pode especificar um valor de 0 para indicar que o ccsid do gerenciador de filas deve ser utilizado. Um ccsid -1 indica que o fluxo de bits deve ser gerado utilizando as informações ccsid contidas na subárvore que consiste do campo apontado pelo elemento e seus filhos. Atualmente nenhum analisador suporta essa função.
options
O valor inteiro que especifica o modo de geração de fluxo de bits deve ser utilizado. Ele pode ter um dos seguinte valores:
  • CCI_BITSTREAM_OPTIONS_ROOT
  • CCI_BITSTREAM_OPTIONS_EMBEDDED
  • CCI_BITSTREAM_OPTIONS_FOLDER

Valores de Retorno

  • Se bem-sucedido, o tamanho correto da memória necessária para suspender o fluxo de bits será retornado.
  • Se a memória alocada pelo responsável pela chamada era insuficiente, returnCode é definido como CCI_BUFFER_TOO_SMALL.
  • Se uma exceção ocorrer durante a execução, returnCode é definido como CCI_EXCEPTION.

Exemplo

O exemplo a seguir demonstra como o parâmetro de opções deve ser utilizado para gerar o fluxo de bits para as diferentes partes da árvore de mensagens.

Esse código pode ser copiado na função _evaluate do nó Transform de amostra. Para uma mensagem de entrada tal como:
MQMDRFH2
<test><data><stuff>things</stuff></data></test>
o nó propagará 3 mensagens, uma contendo uma cópia da mensagem de entrada no domínio BLOB. Uma contendo uma cópia da entrada RFH2 como o corpo da mensagem no domínio BLOB. Uma contendo a pasta <data></data> como o corpo da mensagem no domínio BLOB.
CciMessage*          outMsg[3];
  CciTerminal*         terminalObject;
  CciElement*          bodyChild;
  CciElement*          inRootElement;
  CciElement*          inSourceElement[3];
  CciElement*          outRootElement;
  CciElement*          outBlobElement;
  CciElement*          outBody;
  struct CciByteArray  bitstream[3];
  int                  bitstreamOptions[3];
  int                  retvalue;
  int                  rc = 0;
  int                  loopCount;
  CCI_EXCEPTION_ST     exception_st = {CCI_EXCEPTION_ST_DEFAULT};
  const CciChar*       constBLOBParserName  =
                 cciString("NONE",BIP_DEF_COMP_CCSID);
  const CciChar*       constBLOBElementName =
                 cciString("BLOB",BIP_DEF_COMP_CCSID);
  const CciChar*       constEmptyString     =
                 cciString("",BIP_DEF_COMP_CCSID);

  /*construir e propagar 3 mensagens de saída*/
  /*a primeira mensagem possui o fluxo de bits para o corpo da mensagem de entrada*/
  /*a segunda mensagem possui o fluxo de bits para a entrada RFH2*/
  /*a terceira mensagem possui o fluxo de bits para o subelemento da mensagem de entrada*/

  /* Obter o elemento raiz da mensagem de entrada */
  inRootElement=cniRootElement(&rc, message);
  /*CCI_CHECK_RC();*/
  checkRC(rc);

  /*configurar a matriz de elementos de origem e opções de fluxos de bits*/

  /*corpo da mensagem*/
  inSourceElement[0] =  cniLastChild(&rc,inRootElement);
  checkRC(rc);

  /*Essa é a raiz do corpo da mensagem, portanto, é utilizado o modo RootBitStream*/
  bitstreamOptions[0] = CCI_BITSTREAM_OPTIONS_ROOT;

  
  /*último cabeçalho*/
  inSourceElement[1] = cniPreviousSibling(&rc,inSourceElement[0]);
  checkRC(rc);

  /*Essa é a raiz do RFH2, portanto, é utilizado o modo RootBitStream*/
  bitstreamOptions[1] = CCI_BITSTREAM_OPTIONS_ROOT;

  
  /*body.FIRST(primeiro filho do corpo da mensagem) */
  inSourceElement[2] = cniFirstChild(&rc,inSourceElement[0]);
  checkRC(rc);
  
  /*body.FIRST.FIRST */
  inSourceElement[2] = cniFirstChild(&rc,inSourceElement[2]);
  checkRC(rc);

  /*Essa é uma subárvore dentro do corpo da mensagem, portanto, é utilizado o modo FolderBitStream*/
  bitstreamOptions[2] = CCI_BITSTREAM_OPTIONS_FOLDER;

  
  for (loopCount=0;loopCount<3;loopCount++) {
    int bufLength;

    /* Criar nova mensagem para saída */
    outMsg[loopCount] = cniCreateMessage(&rc, cniGetMessageContext(&rc, message));
    checkRC(rc);

    /* Obter o elemento raiz da mensagem de saída */
    outRootElement = cniRootElement(&rc, outMsg[loopCount]);
    checkRC(rc);

    /* Copiar  conteúdo da mensagem de entrada para a mensagem de saída */
    cniCopyElementTree(&rc, inRootElement, outRootElement);
    checkRC(rc);

    /* Obter o último filho da raiz (ou seja, o corpo)  */
    bodyChild = cniLastChild(&rc, outRootElement);    checkRC(rc);

    /*remover o corpo da mensagem que foi copiado da mensagem de entrada*/
    cniDetach(&rc,
              bodyChild);
    checkRC(rc);

    /*criar o novo corpo da mensagem de saída no domínio BLOB*/
    outBody = cniCreateElementAsLastChildUsingParser(&rc,
                                           outRootElement,
                                           constBLOBParserName);
    checkRC(rc);

    /*criar o elemento BLOB*/
    outBlobElement = cniCreateElementAsLastChild(&rc,
                                outBody);
    checkRC(rc);

    cniSetElementName(&rc,
                      outBlobElement,
                      constBLOBElementName);
    checkRC(rc);
    
    /*Configure o valor do elemento blob, obtendo o fluxo de bits para o
    elemento */
    bitstream[loopCount].size=512;
    bitstream[loopCount].pointer=(CciByte*)malloc(sizeof(CciByte) * 512);
    
    bufLength = cniElementAsBitstream(&rc,
                          inSourceElement[loopCount],
                          &bitstream[loopCount],
                          constEmptyString,/*assumir a mensagem XML sem nenhum interesse*/
                          constEmptyString,/* tipo, conjunto ou formato*/
                          constEmptyString,
                          0,/*Utilizar o CCSID do Gerenciador de Filas & Codificação*/
                          0,
                          bitstreamOptions[loopCount]);
    

    if (rc==CCI_BUFFER_TOO_SMALL)
    {
        free(bitstream[loopCount].pointer);
        bitstream[loopCount].size=bufLength;
        bitstream[loopCount].pointer=(CciByte*)malloc(sizeof(CciByte) * bitstream[loopCount].size);

        bufLength = cniElementAsBitstream(&rc,
                          inSourceElement[loopCount],
                          &bitstream[loopCount],
                          constEmptyString,/*assumir a mensagem XML sem nenhum interesse*/
                          constEmptyString,/* tipo, conjunto ou formato*/
                          constEmptyString,
                          0,/*Utilizar o CCSID do Gerenciador de Filas & Codificação*/
                          0,
                          bitstreamOptions[loopCount]);
    }
    checkRC(rc);
    bitstream[loopCount].size=bufLength;
    
    cniSetElementByteArrayValue(&rc,
                                outBlobElement,
                                &bitstream[loopCount]);
    checkRC(rc);
  }

  /* Obter manuseio do terminal de saída */
  terminalObject = getOutputTerminalHandle( (NODE_CONTEXT_ST *)context,
                                            (CciChar*)constOut);

  /* Se o terminal existir e for anexado, propague-o */
  if (terminalObject) {
    if (cniIsTerminalAttached(&rc, terminalObject)) {
      /* Como esta é uma mensagem nova e alterada, ela deve ser finalizada... */
      cniFinalize(&rc, outMsg[0], CCI_FINALIZE_NONE);
      cniFinalize(&rc, outMsg[1], CCI_FINALIZE_NONE);
      cniFinalize(&rc, outMsg[2], CCI_FINALIZE_NONE);
      retvalue = cniPropagate(&rc, terminalObject, destinationList, exceptionList, outMsg[0]);
      retvalue = cniPropagate(&rc, terminalObject, destinationList, exceptionList, outMsg[1]);
      retvalue = cniPropagate(&rc, terminalObject, destinationList, exceptionList, outMsg[2]);
      if (retvalue == CCI_FAILURE) {
        if (rc == CCI_EXCEPTION) {
          			/* Obter detalhes da exceção */
          memset(&exception_st, 0, sizeof(exception_st));
                    cciGetLastExceptionData(&rc, &exception_st);
          /* Qualquer identificação de erros local pode ir aqui */

          /* Assegurar-se de que a mensagem será excluída antes de retornar/emitir */
          cniDeleteMessage(0, outMsg[0]);
          cniDeleteMessage(0, outMsg[1]);
          cniDeleteMessage(0, outMsg[2]);

          /* É necessário "reemitir" a exceção; observe que não há retorno */
                cciRethrowLastException(&rc);
        }
        else {

          /* Algum outro erro...o plug-in pode escolher para registrá-lo utilizando a função de utilitário */
          /* CciLog()

        }
      }
      else {
      }
    }
  }
  else {
    /* O terminal não existe...vários erros internos. O plug-in pode querer */
    /* registrar um erro aqui, utilizando a função de utilitário cciLog().                 */
  }

  /* Excluir as mensagens criadas agora e finalizadas */
  cniDeleteMessage(0, outMsg[0]);
  cniDeleteMessage(0, outMsg[1]);
  cniDeleteMessage(0, outMsg[2]);

  free((void*) constBLOBParserName);
  free((void*) constBLOBElementName);
  free((void*) constEmptyString);
  return;
Avisos | Marcas Registradas | Downloads | Biblioteca | Suporte | Feedback
Direitos Autorais IBM Corporation 1999, 2006 Última Atualização: 1 Sep 2006
as07885_