обход массива BPEL

#soa #bpel

#soa #bpel

Вопрос:

Мне нужно обойти массив (входные данные для BPEL) в java embed activity и сгенерировать ответ (выходную переменную) процесса BPEL.

Я использую Jdeveloper и SOA 11g

ниже приведен мой xsd

 <?xml version="1.0" encoding="UTF-8"?>
<schema attributeFormDefault="unqualified" elementFormDefault="qualified" targetNamespace="http://xmlns.oracle.com/BPELInpuandOutPutArray_jws/Project1/BPEL_input_output_array" xmlns="http://www.w3.org/2001/XMLSchema">
      <element name="process">
            <complexType>
                  <sequence>
                        <element name="simpleinput" type="string"/>
                        <element name="arrayofObjects" maxOccurs="unbounded" nillable="true">
                              <complexType>
                                    <sequence>
                                          <element name="input1" type="string"/>
                                          <element name="input2" type="string"/>
                                    </sequence>
                              </complexType>
                        </element>
                  </sequence>
            </complexType>
      </element>
      <element name="processResponse">
            <complexType>
                  <sequence>
                        <element name="arrayofObjectsoutput" maxOccurs="unbounded" nillable="true">
                              <complexType>
                                    <sequence>
                                          <element name="output1" type="string"/>
                                          <element name="output2" type="string"/>
                                    </sequence>
                              </complexType>
                        </element>
                  </sequence>
            </complexType>
      </element>
</schema>
  

пока что я могу управлять перемещением по входному массиву

 oracle.xml.parser.v2.XMLElement e1=
(oracle.xml.parser.v2.XMLElement)getVariableData("inputVariable","payload","/client:process/client:arrayofObjects[1]/client:input1"); 

System.out.println(e1.getFirstChild().getNodeValue());
  

Но мое бизнес-требование состоит в том, чтобы на основе некоторой логики установить значения в выходном массиве.
для этого я использовал следующий пример кода.

 for(int i=1; i < 4 ;i  ) 
{ 
setVariableData("outputVariable","payload","/client:processResponse/client:arrayofObjectsoutput['i']/client:output1",i);
setVariableData("outputVariable","payload","/client:processResponse/client:arrayofObjectsoutput['i']/client:output2",i);
}
  

Мне кажется, что массив будет создан длиной 3, а значение будет задано (1,1) (2,2) (3,3), но на выходе будет только значение (3,3) .
пожалуйста, скажите мне, как я могу добиться того же.

пример кода будет оценен по достоинству.

Комментарии:

1. Вы ищете XQuery?

2. Моим требованием является процесс BPEL, который должен возвращать массив объектов. как мы создадим этот aray в моей java embed activity. и верните его. поскольку я также вставил свой xsd, в котором мы можем видеть, что выходной переменной является arrayofObjectsoutput. не могли бы вы сказать мне, пожалуйста, как я могу это сделать (до сих пор я пытался и смог обойти только входной массив)

3. Этот вопрос, опять же, зависит от конкретного поставщика, поэтому, пожалуйста, добавьте примечание о том, какой продукт / инструмент вы используете. Кроме того, в большинстве случаев использование действий BPELJ считается неприятным запахом. Лучшим подходом было бы либо использовать действия <назначить>, либо преобразовать бизнес-логику в сервис.

4. Если вы публикуете образцы кода, XML или данных, пожалуйста , выделите эти строки в текстовом редакторе и нажмите на кнопку «образцы кода» ( { } ) на панели инструментов редактора, чтобы красиво оформить и выделить синтаксис!

5. Хорошо, в следующий раз я обо всем позабочусь, @vanto, пожалуйста, предоставьте любой пример процесса, который использует assign activity для добавления элемента в массив, как я пробовал с copylist, appenlistфункцией, но это не работает. Я изменил инструменты и версии, которые я использовал в вопросе. спасибо

Ответ №1:

Способ, которым я сделал это для аналогичной ситуации, заключался в том, чтобы использовать преобразование для создания первого элемента, а затем использовать bpelx:insertAfter для вставки дополнительных элементов массива, а затем установить их.

 <assign name="Assign_2">
      <bpelx:insertAfter>
        <bpelx:from variable="outputVariable" part="payload"
                    query="/client:ArrayManipulationProcessResponse/client:arrayofObjectsoutput"/>
        <bpelx:to variable="outputVariable" part="payload"
                  query="/client:ArrayManipulationProcessResponse/client:arrayofObjectsoutput"/>
      </bpelx:insertAfter>
      <copy>
        <from expression="'MyOutput1-Index2'"/>
        <to variable="outputVariable" part="payload"
            query="/client:ArrayManipulationProcessResponse/client:arrayofObjectsoutput[2]/client:output1"/>
      </copy>
      <copy>
        <from expression="'MyOutput2-Index2'"/>
        <to variable="outputVariable" part="payload"
            query="/client:ArrayManipulationProcessResponse/client:arrayofObjectsoutput[2]/client:output2"/>
      </copy>
</assign>
  

Комментарии:

1. Привет, я сделал то же самое и также получил результат, но у меня есть одно сомнение, что при использовании bpelx:insertAfter> <bpelx:из переменной=»outputVariable» part=»payload» query=»/client: ArrayManipulationProcessResponse / client: arrayofObjectsoutput»/> <bpelx: в переменную =»outputVariable» part=»payload» query =»/client: ArrayManipulationProcessResponse/client:arrayofObjectsoutput»/> </bpelx:insertAfter> этот фрагмент кода копирует весь массив в себя, и длина массива растет экспоненциально .. можете ли вы сказать мне значение этой строки.

2. Хорошо, чтобы предотвратить экспоненциальный рост, используйте это вместо: <bpelx:из переменной=»outputVariable» часть=»полезная нагрузка» запрос=»/client: ArrayManipulationProcessResponse/client:arrayofObjectsoutput[1]»/>

Ответ №2:

Если проприетарные расширения не работают, вы можете попробовать стандартный подход BPEL и использовать XSLT-скрипт для итеративного создания результирующего документа.

Пример приведен в спецификации BPEL 2.0, стр. 65, посмотрите на итеративное построение документа.

По сути, список и добавляемый элемент передаются (через функцию doXSLTransform XPath) скрипту XSLT, который копирует элемент для добавления в список и возвращает новый документ. Затем это присваивается переменной.

Комментарии:

1. Привет, Ванто, спасибо, что поделился ссылкой. но я не могу сделать это правильно, можете ли вы поделиться со мной чем-нибудь еще на простом примере..

2. Извините, у меня нет под рукой примера. Вы можете ознакомиться с примером на svn.apache.org/viewvc/ode/branches/ode-1.3.5.x/bpel-test/src / … — он не добавляется к массиву, но показывает, как использовать XSL в BPEL. Итак, вместе с примером в спецификации BPEL вы должны быть в состоянии прийти к рабочему решению.

Ответ №3:

Я чувствую, что нет необходимости писать пользовательский Java-код для такой простой задачи. Следующий код (BPEL2.0) выполняет работу по копированию значений.

 <assign name="Copy values">
      <extensionAssignOperation>
          <bpelx:copyList>
               <bpelx:from>$inputVariable.payload/ns1:arrayofObjects</bpelx:from>
               <bpelx:to>$outputVariable.payload/ns1:arrayofObjectsoutput</bpelx:to>
           </bpelx:copyList>
      </extensionAssignOperation>
</assign>
  

Комментарии:

1. Спасибо, но моим требованием является создание массива на основе некоторой бизнес-логики. не могли бы вы, пожалуйста, пояснить, как я могу добиться того же. допустим, у меня есть сотрудник класса (объекты значений) Я создам 5 экземпляров этого класса и верну его обратно из процесса BPEL. затем я должен использовать Array для его возврата. В моем xsd я смоделировал то же самое с элементом arrayofObjectsoutput. пожалуйста, предложите мне что-нибудь.