WebSphere Message Broker, Versión 8.0.0.5 Sistemas operativos: AIX, HP-Itanium, Linux, Solaris, Windows, z/OS

Consulte la información sobre la última versión del producto en IBM Integration Bus, Versión 9.0

cniElementAsBitstream

Utilice esta función para obtener la representación de corriente de bits del elemento especificado.

El analizador que está asociado al elemento serializa el elemento y todos los elementos hijo. El resultado de copia en la memoria asignada por el canal de llamada. En el caso especial en el que todas las opciones especificadas coinciden con las de la corriente de bits original, por ejemplo una corriente de bits leída desde una cola de WebSphere MQ por el nodo MQInput, y el mensaje no se ha modificado desde que se ha recibido la corriente de bits original, esta corriente de bits original se copia en la memoria asignada. En este caso, no es necesario que el analizador analice y vuelva a serializar el mensaje.

El algoritmo utilizado para generar la corriente de bits depende del analizador que se utilice y de las opciones especificadas. Todos los analizadores dan soporte a las modalidades siguientes:
  • RootBitStream, en el que el algoritmo que genera la corriente de bits es el mismo que el que utiliza un nodo de salida. En esta modalidad, se obtiene un resultado significativo solamente si el elemento al que se apunta está a la cabeza de un subárbol con una estructura adecuada.
  • EmbeddedBitStream, en el que no solamente el algoritmo que genera la corriente de bits es el mismo que el que utiliza un nodo de salida, sino que también se determinan los elementos siguientes, si no se especifican explícitamente, de la misma manera que el nodo de salida. Por tanto, se determinan buscando los elementos hermano anteriores de element presuponiendo que estos elementos representan cabeceras:
    • Codificación
    • CCSID
    • Conjunto de mensajes
    • Tipo de mensaje
    • Formato del mensaje

    De este modo, el algoritmo para determinar estas propiedades es esencialmente el mismo que se utiliza para la función ESQL BITSTREAM.

Algunos analizadores también dan soporte a otra modalidad, FolderBitStream, que genera una corriente de bits significativos para cualquier subárbol, siempre que el campo apuntado represente una carpeta.

Sintaxis

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
Código de retorno de la función (salida). Si especifica un puntero NULL en la entrada, el valor indica que el nodo no maneja errores. Si la entrada no es NULL, la salida significa el estado de éxito de la llamada. Las excepciones arrojadas durante la ejecución de esta llamada se vuelven a arrojar en el nodo ascendente siguiente del flujo. Llame a cciGetLastExceptionData para obtener información detallada de la excepción.
Los códigos de retorno posibles son:
  • CCI_SUCCESS
  • CCI_EXCEPTION
  • CCI_INV_ELEMENT_OBJECT
  • CCI_INV_DATA_POINTER
  • CCI_INV_DATA_BUFLEN
  • CCI_INV_BUFFER_TOO_SMALL
element
Elemento de sintaxis que se debe serializar (entrada).
value
Puntero a una estructura CciByteArray que contiene un puntero a una región de memoria asignada por el canal de llamada, y el tamaño en CciBytes de esta memoria (salida).
messageType
Definición de tipo de mensaje utilizada para crear la corriente de bits desde el árbol de elementos (entrada). Si especifica un puntero NULL, se hace caso omiso del parámetro. También se hace caso omiso del parámetro si el valor no es relevante para el analizador asociado al elemento; por ejemplo, un analizador XML genérico.
messageSet
Definición de conjunto de mensajes utilizada para crear la corriente de bits desde el árbol de elementos (entrada). Si especifica un puntero NULL, se hace caso omiso del parámetro. También se hace caso omiso del parámetro si el valor no es relevante para el analizador asociado al elemento; por ejemplo, un analizador XML genérico.
messageFormat
Formato utilizado para crear la corriente de bits desde el árbol de elementos (entrada). Si especifica un puntero NULL, se hace caso omiso del parámetro. También se hace caso omiso del parámetro si el valor no es relevante para el analizador asociado al elemento; por ejemplo, un analizador XML genérico.
encoding
La codificación a utilizar cuando se graba la corriente de bits (entrada). Este parámetro es obligatorio. Puede especificar un valor de 0 para indicar que debe utilizarse la codificación del gestor de colas.
ccsid
Identificador de juego de caracteres codificado a utilizar cuando se graba la corriente de bits (entrada). Este parámetro es obligatorio. Si especifica el valor 0, se utiliza el CCSID del gestor de colas. Un CCSID de -1 indica que la corriente de bits se genera utilizando la información de CCSID contenida en el subárbol, la cual consta del campo apuntado por el elemento y sus elementos hijo. Actualmente ningún analizador suministrado soporta esta opción.
options
Valor entero que especifica la modalidad de generación de corriente de bits que debe utilizarse. Establezca uno de los valores siguientes:
  • CCI_BITSTREAM_OPTIONS_ROOT
  • CCI_BITSTREAM_OPTIONS_EMBEDDED
  • CCI_BITSTREAM_OPTIONS_FOLDER

Valores de retorno

  • Si la ejecución se realiza satisfactoriamente, se devuelve el tamaño correcto de memoria necesaria para contener la corriente de bits.
  • Si la memoria asignada por el canal de llamada no ha sido suficiente, returnCode es CCI_BUFFER_TOO_SMALL.
  • Si se produce una excepción durante la ejecución, returnCode es CCI_EXCEPTION.

Ejemplo

El ejemplo siguiente muestra cómo puede utilizar el parámetro de opciones para generar la corriente de bits para distintas partes del árbol de mensaje.

Este código puede copiarse en la función _evaluate del nodo Transform de ejemplo. Para un mensaje de entrada como:
MQMD
MQRFH2
<test><data><aaa>text</aaa></data></test>
el nodo propaga tres mensajes:
  • Uno que contiene una copia del mensaje de entrada en el dominio BLOB
  • Uno que contiene una copia de la cabecera MQRFH2 de entrada como el cuerpo del mensaje en el dominio BLOB
  • Uno que contiene la carpeta <data></data> como el cuerpo del mensaje en el dominio 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);

  /*crear y propagar 3 mensajes de salida*/
  /*primer mensaje con corriente de bits para el cuerpo del mensaje de entrada*/
  /*segundo mensaje con corriente de bits para MQRFH2 de entrada*/
  /*tercer mensaje con corriente de bits para subelemento del mensaje de entrada*/

  /* Obtener el elemento raíz del mensaje de entrada */
  inRootElement = cniRootElement(&rc, message);
  /*CCI_CHECK_RC();*/
  checkRC(rc);

  /*establecer la matriz de opciones de corriente de bits y elementos origen*/

  /*cuerpo del mensaje*/
  inSourceElement[0] =  cniLastChild(&rc,inRootElement);
  checkRC(rc);

  /*Esta es la raíz del mensaje, por lo que se usa la modalidad RootBitStream*/
  bitstreamOptions[0] = CCI_BITSTREAM_OPTIONS_ROOT;

  
  /*última cabecera*/
  inSourceElement[1] = cniPreviousSibling(&rc,inSourceElement[0]);
  checkRC(rc);

  /*Esta es la raíz de MQRFH2, por lo que se usa la modalidad RootBitStream*/
  bitstreamOptions[1] = CCI_BITSTREAM_OPTIONS_ROOT;

  
  /*body.FIRST(primer hijo del cuerpo del mensaje) */
  inSourceElement[2] = cniFirstChild(&rc,inSourceElement[0]);
  checkRC(rc);
  
  /*body.FIRST.FIRST */
  inSourceElement[2] = cniFirstChild(&rc,inSourceElement[2]);
  checkRC(rc);

  /*Es un subárbol dentro del cuerpo del mensaje, se usa la modalidad FolderBitStream*/
  bitstreamOptions[2] = CCI_BITSTREAM_OPTIONS_FOLDER;

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

    /* Crear nuevo mensaje para salida */
    outMsg[loopCount] = cniCreateMessage(&rc, cniGetMessageContext(&rc, message));
    checkRC(rc);

    /* Obtener el elemento raíz del mensaje de salida */
    outRootElement = cniRootElement(&rc, outMsg[loopCount]);
    checkRC(rc);

    /* Copiar el contenido del mensaje de entrada en el mensaje de salida */
    cniCopyElementTree(&rc, inRootElement, outRootElement);
    checkRC(rc);

    /* Obtener el último hijo del elemento raíz (por ej., el cuerpo)  */
    bodyChild = cniLastChild(&rc, outRootElement);
    checkRC(rc);

    /*desechar el cuerpo del mensaje que se ha copiado del mensaje de entrada*/
    cniDetach(&rc,
              bodyChild);
    checkRC(rc);

    /*crear el nuevo cuerpo del mensaje de salida en el dominio BLOB*/
    outBody = cniCreateElementAsLastChildUsingParser(&rc,
                                           outRootElement,
                                           constBLOBParserName);
    checkRC(rc);

    /*crear el elemento BLOB*/
    outBlobElement = cniCreateElementAsLastChild(&rc,
                                outBody);
    checkRC(rc);

    cniSetElementName(&rc,
                      outBlobElement,
                      constBLOBElementName);
    checkRC(rc);
    
    /*Establecer el valor del elemento blob obteniendo la corriente de bits para
    el elemento */
    bitstream[loopCount].size=512;
    bitstream[loopCount].pointer=(CciByte*)malloc(sizeof(CciByte) * 512);
    
    bufLength = cniElementAsBitstream(&rc,
                          inSourceElement[loopCount],
                          &bitstream[loopCount],
                          constEmptyString,/*suponemos mensaje XML, por lo que*/
                          constEmptyString,/*no interesa tipo, conjunto o formato*/
                          constEmptyString,
                          0,/*Usar CCSID & codificación de gestor de colas*/
                          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,/*suponemos mensaje XML, por lo que*/
                          constEmptyString,/*no interesa tipo, conjunto o formato*/
                          constEmptyString,
                          0,/*Usar CCSID & codificación de gestor de colas*/
                          0,
                          bitstreamOptions[loopCount]);      
    }
    checkRC(rc);
    bitstream[loopCount].size=bufLength;
    
    cniSetElementByteArrayValue(&rc,
                                outBlobElement,
                                &bitstream[loopCount]);
    checkRC(rc);
  }

  /* Obtener manejador de terminal de salida */
  terminalObject = getOutputTerminalHandle( (NODE_CONTEXT_ST *)context,
                                            (CciChar*)constOut);

  /* Si el terminal existe y se adjunta, propagar al mismo */
  if (terminalObject) {
    if (cniIsTerminalAttached(&rc, terminalObject)) {
      /* Al ser un mensaje nuevo y cambiado, debe finalizarse... */
      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, localEnvironment, exceptionList, outMsg[0]);
      retvalue = cniPropagate(&rc, terminalObject, localEnvironment, exceptionList, outMsg[1]);
      retvalue = cniPropagate(&rc, terminalObject, localEnvironment, exceptionList, outMsg[2]);
      if (retvalue == CCI_FAILURE) {
        if (rc == CCI_EXCEPTION) {
          /* Obtener detalles de la excepción */
          memset(&exception_st, 0, sizeof(exception_st));
          cciGetLastExceptionData(&rc, &exception_st);

          		/* Aquí puede ir cualquier manejo de errores locales */

          /* Asegúrese de que se suprime el mensaje antes de devolver/generar */
          cniDeleteMessage(0, outMsg[0]);
          cniDeleteMessage(0, outMsg[1]);
          cniDeleteMessage(0, outMsg[2]);

          /* Se debe volver a generar la excepción; observe que no regresa */
          cciRethrowLastException(&rc);
        }
        else {

          /* Algún otro error... el plugin puede elegir anotarlo utilizando la función */
          /* de programa de utilidad CciLog()                                          */

        }
      }
      else {
      }
    }
  }
  else {
    /* El terminal no existía... error interno grave. Es posible que el plugin */
    /* quiera anotar un error aquí utilizando la función de programa de utilidad cciLog().                 */
  }

  /* Suprimir los mensajes que hemos creado; hemos terminado con ellos. */
  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 | Descargas | Biblioteca | Soporte | Comentarios

Copyright IBM Corporation 1999, 2014Copyright IBM Corporation 1999, 2014.

        
        Última actualización:
        
        Última actualización: 2015-02-28 17:00:23


Tema de referenciaTema de referencia | Versión 8.0.0.5 | as07885_