Obtiene la representación de corriente de bits del elemento especificado. El analizador asociado con el elemento serializa el elemento y todos los hijos. El resultado de copia en la memoria asignada por el canal de llamada. En el caso especial donde 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 por el usuario. En este caso, no es necesario que el analizador analice y vuelva a serializar el mensaje.
De este modo, el algoritmo para determinar estas propiedades es esencialmente el mismo que se utiliza para la función 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.
CciSize cniElementAsBitstream( int* returnCode, CciElement* element, const struct CciByteArray* value, CciChar* messageType, CciChar* messageSet, CciChar* messageFormat, int encoding, int ccsid, int options);
El ejemplo siguiente muestra cómo debe utilizarse el parámetro de opciones para generar la corriente de bits para distintas partes del árbol de mensaje.
MQMD RFH2 <test><data><stuff>things</stuff></data></test>el nodo propagará 3 mensajes, uno con una copia del mensaje de entrada en el dominio BLOB. Otro con una copia del RFH2 de entrada como el cuerpo del mensaje en el dominio BLOB. Otro con 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 mensajes de salida*/ /*primer mensaje con corriente de bits para el cuerpo del mensaje de entrada*/ /*segundo mensaje con corriente de bits para RFH2 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 RFH2, 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, 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) { /* 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 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;