Notesxsltransformer для Xslt

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

Dimly

#1
Доброго.

Возникла проблема в XSLT преобразовании данных с обработкой (форматированием) в процессе.
К примеру задача - поменять разделители "точка с запятой" на пробел. (о том чтобы заменить на тег <BR> - я уже молчу)

Имеем DATA.XML
Код:
<?xml version="1.0" encoding="windows-1251"?>
<?xml-stylesheet type="text/xsl" href="FILE.XSL"?>
.................................................................
<OfficePhone title="Office phone" value="1123 123;123;22" />
.................................................................
Имеем FILE.XSL
Код:
<?xml version="1.0" encoding="windows-1251"?>
<xsl:stylesheet version="1.0" 
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:xslt="urn:schemas-microsoft-com:xslt"
xmlns:ext="urn:extension-functions"
exclude-result-prefixes="xslt ext">
<xslt:script language="JavaScript" implements-prefix="ext">
function arrau(st) {
var mArr = st.split(";")
var st2 = mArr.join(" ");
return st2;
}
</xslt:script>
<xsl:output encoding="Windows-1251" method='html' indent='yes'/>
<xsl:template match="/">
.................................................................
<TD class="reportCell"><xsl:value-of select="ext:arrau2(string(OfficePhone/@value))" /></TD>
.................................................................
Если такой ХМЛ открыть в IE - то все великолепно. Значение заменяет точку с запятой на пробел.
Но если (удалив из ХМЛ вторую строку) закинуть все в LS
Код:
	Dim XML_in As NotesStream
Dim XSL_ss As NotesStream

Set XML_in=session.CreateStream
Set XSL_ss=session.CreateStream
Call XML_in.Open("DATA.xml") 
Call XSL_ss.Open("FILE.xsl")

Dim XML_out As NotesStream 
Set XML_out=session.CreateStream
Call XML_out.Open("out.html") 
XML_out.Truncate

Dim transformer As NotesXSLTransformer
Set transformer=session.CreateXSLTransformer(XML_in, XSL_ss, XML_out)
transformer.Process
то out.html- возвращает HTML точно до первого вызова скрипта, и после него просто корректно закрывает все теги, не обрабатывая информаци., оставляя даже это поле пустым.

Кстати если сделать вот так (на ва скриптах) , то тоже работает
Код:
source = new ActiveXObject("Microsoft.XMLDOM");
source.async = false;
style = new ActiveXObject("Microsoft.XMLDOM");
style.async = false;

source.load("DATA.XML");
style.load("FILE.xsl");

fff = source.transformNode(style);

f = new ActiveXObject("Scripting.FileSystemObject");
t = f.CreateTextFile("out.html", true);
t.Write(fff);
Переменная fff содержит корретный отработанный HTML.

Догадываюсь что это потому что само использование javaScript в XSL - фича MS... или же опять курил не те мануалы по яве.
(вместо xslt пробовал и msxslt - результат то же, да еще и явное использование фич MS)
 
13.03.2009
625
1
#2
а где собсно вопрос? утверждение: "Notesxsltransformer для Xslt, не понимает xslt:script language="JavaScript"" абсолютно верно.
спецификация xslt от w3c не включает подобные расширения. лотусовый парсер работает согласно спецификации. Если хочеца использовать MS расширения - нужно юзать MS-парсер.
Если хочеца юзать стандарты, то можно поискать тут: http://www.dpawson.co.uk/xsl/sect2/replace.html
А вообще, в вашем конкретном случае, корень проблемы в кривом XML, который кроме данных содержит их представление( разметку ). Правильный путь - изменить ( если возможно ) <OfficePhone title="Office phone" value="1123 123;123;22" /> на что-то типа
<OfficePhone title="Office phone">
<value>111</value>
<value>222</value>
<value>333</value>
</OfficePhone>
тогда и пробелы, и <br/> и все что хочешь можно добавлять.
 
D

Dimly

#3
а где собсно вопрос? утверждение: "Notesxsltransformer для Xslt, не понимает xslt:script language="JavaScript"" абсолютно верно.
.....................
А вообще, в вашем конкретном случае, корень проблемы в кривом XML, который кроме данных содержит их представление( разметку ).
:) Благодарю. Раз утверждение верно - значит надо искать другие пути.
Попробую работать с MS через активХ.

А данные... они такие поступают извне - и исправить что то совершенно невозможно.

Только сейчас дошло что в лотусе никто не мешает использовать Microsoft.XMLDOM и transformNode.

ЗЫ: Иногда чтобы найти правильное решение, требуется его просто обсудить.
 
13.03.2009
625
1
#4
рекомендую таки сходить по ссылке, а также погуглить "xsl string split". задача в общем-то решается без помощи темной стороны Силы :). Рекурсивный вызов substring-before рулит.
А простую замену символов похоже можно сделать через <xsl:value-of select="translate( . , ';' , ' ' )" />
 
D

Dimly

#5
Да да... так и есть

1 решение ... через ... MS

Код:
	Set source = CreateObject("Microsoft.XMLDOM")
source.async = False
Call source.load("DATA.xml")
Set style = CreateObject("Microsoft.XMLDOM")
style.async = False
Call style.load("FILE.xsl")
valu = source.transformNode(style)
после чего valu содержит корректный HTML

Сейчас начну читать ссылку. То что увидел уже говорит о том что проблема вполне решабельна самим XSL.
Еще раз спасибо.
 

lmike

нет, пердело совершенство
Lotus team
27.08.2008
6 586
272
#6
олько сейчас дошло что в лотусе никто не мешает использовать Microsoft.XMLDOM и transformNode.
в лотусе (а на самом деле в домино-нотусе, лотус - это фирма/лэйба) можно и нужно использовать java, вместо КОМов...
и как сказал turumbay можно рекурсивную ф-цию сбацать...
во когда-то писал, "на коленке":
Код:
<!--
split-string
Parameters:
$all: a semicolon-separated string
$spliter: spliter string, default="|"
$swrapper: default="'"
Output: string separated by $spliter
-->
<xsl:template name="split-string">
<xsl:param name="all" />
<xsl:param name="spliter">|</xsl:param>
<xsl:param name="swrapper">'</xsl:param>
<!-- First word in $all: -->
<xsl:variable name="first" >
<xsl:variable name="first0" select="substring-before($all,';')" />
<xsl:choose>
<xsl:when test="$first0" >
<xsl:copy-of select="$first0" />
</xsl:when>
<xsl:otherwise>
<xsl:copy-of select="$all" />
</xsl:otherwise>
</xsl:choose>
</xsl:variable>

<!-- <xsl:message>DEBUG $all=<xsl:value-of select="$all" />, $first="<xsl:value-of select="$first"/>"</xsl:message>
<xsl:message>DEBUG <xsl:value-of select="string-length($first)"/></xsl:message>
-->
<xsl:choose>
<xsl:when test="string-length($first)" >
<xsl:value-of select="$swrapper"/><xsl:value-of select="$first" /><xsl:value-of select="$swrapper"/>
<xsl:if test="substring-after($all,';')">
<xsl:value-of select="$spliter" />
<xsl:call-template name="split-string">
<xsl:with-param name="all" >
<!-- <xsl:message>DEBUG after:<xsl:value-of select="substring-after($all,';')" /></xsl:message>-->
<xsl:value-of select="substring-after($all,';')" />
</xsl:with-param>
<xsl:with-param name="spliter" select="$spliter"/>
<xsl:with-param name="swrapper" select="$swrapper"/>
</xsl:call-template>
</xsl:if>
</xsl:when>
<xsl:otherwise>
<xsl:value-of select="$swrapper"/><xsl:value-of select="$all"/><xsl:value-of select="$swrapper"/>
</xsl:otherwise>
</xsl:choose>
</xsl:template>