DXLExport, XSLTransform для Web-service

  • Автор темы Автор темы Eugen
  • Дата начала Дата начала

Eugen

Green Team
22.03.2012
210
1
BIT
1
Добрый день.
Есть скоринговый web-service, есть кредитный конвейер в лотусе. Надо их как то связать. Видел примеры по выгрузке DXL во внешний файл, затем его считывание и тд.
В итоге связь с web-сервисом есть, ответ получаю. Теперь стоит задача выгрузить текущий документ в xml по определенной схеме и отправить его на этот сервис, соответственно потом получить ответ и импортировать его.

Есть
<div class="sp-wrap"><div class="sp-head-wrap"><div class="sp-head folded clickable">агент</div></div><div class="sp-body"><div class="sp-content">
Код:
Dim filename As String
Dim file_out As String
Dim importer As NotesDXLImporter
Dim stream As NotesStream
Dim db As NotesDatabase
Dim uidoc As NotesUIDocument
Sub Initialize
Dim s As New NotesSession
Dim w As New NotesUIWorkspace
Dim db As NotesDatabase
Dim doc As NotesDocument
Dim transform As NotesXSLTransformer

Set db = s.CurrentDatabase
Set doc=w.Currentdocument.Document

Dim stream_in As NotesStream
Dim stream_out As NotesStream
Dim emptyStream As NotesStream

Set stream_in = s.CreateStream
Set stream_out = s.CreateStream
Set emptyStream= s.CreateStream
filename$ = "D:\svg2gfx-simple.xsl"
file_out$ = "d:\test.xml"
If Not stream_in.Open(filename$) Then
MessageBox "не могу открыть " & filename$,, "Error"
Exit Sub
End If

If Not stream_out.Open(file_out$) Then
MessageBox "Не могу открыть " & file_out$,, "Error"
Exit Sub
End If

Call emptyStream.Truncate

Dim exporter As NotesDXLExporter
Set exporter = s.CreateDXLExporter(doc, emptyStream)

Set transform=s.Createxsltransformer(emptyStream, stream_in, stream_out)
Call transform.Process()
End Sub
При запуске выдает ошибку "XSL Transform operation failed" на шаге Call transform.Process().
Собственно вопрос: возможно ли в параметрах DXLExporter`a как аутпут указать XSLTransformer, и соответственно трансформеру как инпут указать експортер? Очень хочется сделать это без выгрузки во внешний файл. И правильно ли я пытаюсь сделать это через NotesStream?

PS: похожих тем много, но что то я не нашел там нужную инфу, так что прошу сильно не пинать. Меньше года занимаюсь лотусом, поэтому прошу указать конкретные ошибки и объяснить почему.
 
Ошибка в создании transform, см. справку:
Код:
Set notesXSLTransformer = notesSession.CreateXSLTransformer( [ input [, styleSheet [, output ] ] ])
 
Ошибка в создании transform, см. справку:
Код:
Set notesXSLTransformer = notesSession.CreateXSLTransformer( [ input [, styleSheet [, output ] ] ])

У меня там просто обозвано через одно место... в моем случае stream_in - это
Код:
Set stream_in = s.CreateStream
filename$ = "D:\svg2gfx-simple.xsl"
If Not stream_in.Open(filename$) Then
MessageBox "не могу открыть " & filename$,, "Error"
Exit Sub
End If
 
возможно ли в параметрах DXLExporter`a как аутпут указать XSLTransformer, и соответственно трансформеру как инпут указать експортер? Очень хочется сделать это без выгрузки во внешний файл. И правильно ли я пытаюсь сделать это через NotesStream?
emptyStream здесь не нужен, попробуйте так:
Dim exporter As NotesDXLExporter
Set exporter = s.CreateDXLExporter(doc)

Set transform=s.Createxsltransformer(exporter, stream_in, stream_out)
Call transform.Process()

ЕМНИП, есть какие-то заморочки, у какого объекта вызывать Process — у экспортера или трансформера, попробуйте оба варианта.
ДобавленоКуда-то код в тэгах пропадает, завернул в цитату
 
Переименовал все по нормальному. В общем сделал так:
Код:
	Set emptyStream= s.CreateStream
Call emptyStream.Truncate

Dim exporter As NotesDXLExporter
Set exporter = s.CreateDXLExporter(doc, emptyStream)
Call exporter.Process

Set transform=s.Createxsltransformer(emptyStream, xsl, xml)
Call transform.Process

Вроде заработало. Теперь, если я правильно понимаю, надо браться за написание xsl? Как его потом валидировать?
 
И снова здрасьте.

Новый вопрос:
судя по описанию в хелпе выход одного трансформера может быть входом другого. Для этого надо использовать отдельный stream? Или достаточно того, который я использовал при передаче от DXLExporter`a к XSLTransformer`у? В принципе я пробовал и так, и так но результат один.

Пробую так:
Код:
Set transform=s.Createxsltransformer(emptyStream, xsl_1, stream)
Call transform.Process

Set transformer=s.Createxsltransformer(stream, xsl_2, xml)
Call transformer.Process

Выдает ошибку "XSL Transform operation failed" на шаге Call transformer.Process(т.е. когда запускается второй трансформер). Что делаю не так, подскажите пожалуйста?
 
судя по описанию в хелпе выход одного трансформера может быть входом другого
Да, и код при этом выглядит примерно так:

Код:
Dim s As New NotesSession
Dim exporter As NotesDXLExporter
Set exporter = s.CreateDXLExporter(doc)
Set transformer1 = s.Createxsltransformer(exporter, xsl_1)
Set transformer2 = s.Createxsltransformer(transformer1, xsl_2, xml)
Call exporter.Process()

Добавлено
Выдает ошибку "XSL Transform operation failed" на шаге Call transformer.Process(т.е. когда запускается второй трансформер). Что делаю не так, подскажите пожалуйста?
Возможно, ошибка в xsl, гляньте exporter.Log
 
а насчет xsl - он нормальный, валидный и без ошибок.
 
Видел примеры по выгрузке DXL во внешний файл, затем его считывание и тд.
В итоге связь с web-сервисом есть, ответ получаю. Теперь стоит задача выгрузить текущий документ в xml по определенной схеме и отправить его на этот сервис,
Не проще сделать правильный XML ручками из данных лотусового документа?
 
Не проще сделать правильный XML ручками из данных лотусового документа?

Как это сделать? Exporter мне по умолчанию выгружает в dxl по dtd схеме, и что то я не разобрался как это изменить.
 
а насчет xsl - он нормальный, валидный и без ошибок.
Код A = 1: B = 0: C = A / B тоже валидный и без ошибок, однаки при выполнении выдает Division by zero.
Не проще сделать правильный XML ручками из данных лотусового документа?
Не смущайте товарища, он верной дорогой идёт.
 
Не смущайте товарища, он верной дорогой идёт.
Не совсем понятна задача. На мой взгляд тоже не нужен DXL, наверняка достаточно просто сформировать XML и отправить его, затем получить ответ, разобрать ответ и полученные данные записать в документ.

Вопросы к автору поста:
1. Вы WebService как вызываете: с помощью лотусового Web Service Consumer, с помощью сторонних COM объектов или вообще по HTTP отправляете методом POST?
2. XML по схеме вам нужен только для вызова WebService или в одном из полей в передаваемом сообщении WebService должен быть XML?
3. Схема сложная? Вы сможете сами в текстовом редакторе написать XML, удовлетворяющий этой схеме?
4. На стороне провайдера WebService тоже Лотус?
 
Вопросы к автору поста:
1. Вы WebService как вызываете: с помощью лотусового Web Service Consumer, с помощью сторонних COM объектов или вообще по HTTP отправляете методом POST?
2. XML по схеме вам нужен только для вызова WebService или в одном из полей в передаваемом сообщении WebService должен быть XML?
3. Схема сложная? Вы сможете сами в текстовом редакторе написать XML, удовлетворяющий этой схеме?
4. На стороне провайдера WebService тоже Лотус?

1. с помощью Web Service Consumer;
2,4. На стороне провайдера не лотус. Общение с ним идет по SOAP. Провайдер прислал мне схему, по которой должен валидироваться xml, чтобы он мог его разобрать. Если я правильно понимаю, схема взаимодействия одлжна быть примерно следующая:

Выгружаю dxl=>Трансформирую его=>Валидирую=>Передаю в Web Service Consumer(который "заворачивает" его в SOAP)=>Отправляю.

Затем еще будет гемор с разбором и полученим ответа, но до этого пока далеко...
3. У меня есть образец xml, который валидируется по этой схеме.
 
3. У меня есть образец xml, который валидируется по этой схеме.
Ну, так и не надо ничего никуда выгружать, заполните этот XML нужными данными из вашего лотус-документа и отправляйте web-сервису. Что-то мне подсказывает, что возможно даже без временных файлов обойтись.
Затем еще будет гемор с разбором и полученим ответа, но до этого пока далеко...
Рекомендую сразу сделать на Java. XPath сильно облегчит вам задачу разбора XML-ответа. А XStream, кстати, поможет сформировать XML для отправки.
 
надо не забывать (при хсл преобразовании) о нэймспэйсах, скорее-всего именно с ними и возникают накладки
хсл тупо генерит RAW хмл (если чего доп. не делали)
 
Ну, так и не надо ничего никуда выгружать, заполните этот XML нужными данными из вашего лотус-документа и отправляйте web-сервису. Что-то мне подсказывает, что возможно даже без временных файлов обойтись.

Так в том то и "прикол", что я не знаю как управлять выгрузкой. DXLExporter по умолчанию выгружает все item`ы документа. К тому же в выгрузке у меня елемен фамилия, например, называется "F", а в соответствии со схемой он должен быть "lastname", поэтому я и полез в трансформацию.

Укороченный пример того, что я имею в dxl:

Код:
<?xml version='1.0' encoding='utf-8'?>
<!DOCTYPE document SYSTEM 'xmlschemas/domino_8_5_2.dtd'>
<document xmlns='http://www.lotus.com/dxl' version='8.5' maintenanceversion='2.3'
replicaid='44257ABB0031C58A' form='CreditClaim'>
<item name='F'>
<textlist>
<text>Иванов</text>
</textlist>
</item>
<item name='I'>
<textlist>
<text>Семен</text>
</textlist>
</item>
</document>


А вот то, что мне надо получить:

Код:
<?xml version="1.0" encoding="utf-8"?>
<ApplicationFile xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="Front_Request.xsd">
<ApplicationsList>
<lastname>Иванов</lastname>
<firstname>Семен</firstname>
</ApplicationsList>
</ApplicationFile>

Т.е. у меня мало того, что dxl выгружается по dtd, так надо еще все атрибуты name сделать элементами и переименовать.

ЗЫ: с явой к сожалению, вообще не знаком. Есть в планах, но не думал, что сейчас понадобится.

Добавлено:
надо не забывать (при хсл преобразовании) о нэймспэйсах, скорее-всего именно с ними и возникают накладки
хсл тупо генерит RAW хмл (если чего доп. не делали)
как раз из-за этого и приходится делать двойную трансформацию - первая копирует все, кроме неймспейса, а вторая уже меняет структуру xml.
 
Мы в соцсетях:

Обучение наступательной кибербезопасности в игровой форме. Начать игру!