From 84adefa331c4159d432d22840663c38f155cd4c1 Mon Sep 17 00:00:00 2001 From: Erlang/OTP Date: Fri, 20 Nov 2009 14:54:40 +0000 Subject: The R13B03 release. --- lib/xmerl/src/xmerl_xs.erl | 123 +++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 123 insertions(+) create mode 100644 lib/xmerl/src/xmerl_xs.erl (limited to 'lib/xmerl/src/xmerl_xs.erl') diff --git a/lib/xmerl/src/xmerl_xs.erl b/lib/xmerl/src/xmerl_xs.erl new file mode 100644 index 0000000000..f42a470a43 --- /dev/null +++ b/lib/xmerl/src/xmerl_xs.erl @@ -0,0 +1,123 @@ +%% +%% %CopyrightBegin% +%% +%% Copyright Ericsson AB 2003-2009. All Rights Reserved. +%% +%% The contents of this file are subject to the Erlang Public License, +%% Version 1.1, (the "License"); you may not use this file except in +%% compliance with the License. You should have received a copy of the +%% Erlang Public License along with this software. If not, it can be +%% retrieved online at http://www.erlang.org/. +%% +%% Software distributed under the License is distributed on an "AS IS" +%% basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See +%% the License for the specific language governing rights and limitations +%% under the License. +%% +%% %CopyrightEnd% +%% + +%% Description : Implements XSLT like transformations in Erlang + +%% @doc +% Erlang has similarities to XSLT since both languages +% have a functional programming approach. Using xmerl_xpath +% it is possible to write XSLT like transforms in Erlang. +% +%

XSLT stylesheets are often used when transforming XML +% documents, to other XML documents or (X)HTML for presentation. +% XSLT contains quite many +% functions and learning them all may take some effort. +% This document assumes a basic level of +% understanding of XSLT. +%

+%

Since XSLT is based on a functional programming approach +% with pattern matching and recursion it is possible to write +% similar style sheets in Erlang. At least for basic +% transforms. This +% document describes how to use the XPath implementation together +% with Erlangs pattern matching and a couple of functions to write +% XSLT like transforms.

+%

This approach is probably easier for an Erlanger but +% if you need to use real XSLT stylesheets in order to "comply to +% the standard" there is an adapter available to the Sablotron +% XSLT package which is written i C++. +% See also the Tutorial. +%

+ +-module(xmerl_xs). + +-export([xslapply/2, value_of/1, select/2, built_in_rules/2 ]). +-include("xmerl.hrl"). + + +%% @spec xslapply(Function, EList::list()) -> List +%% Function = () -> list() +%% @doc xslapply is a wrapper to make things look similar to +%% xsl:apply-templates. +%% +%%

Example, original XSLT:


+%% <xsl:template match="doc/title">
+%%   <h1>
+%%     <xsl:apply-templates/>
+%%   </h1>
+%% </xsl:template>
+%% 
+%% +%%

becomes in Erlang:


+%% template(E = #xmlElement{ parents=[{'doc',_}|_], name='title'}) ->
+%%   ["<h1>",
+%%    xslapply(fun template/1, E),
+%%    "</h1>"];
+%% 
+ +xslapply(Fun, EList) when is_list(EList) -> + lists:map( Fun, EList); +xslapply(Fun, E = #xmlElement{})-> + lists:map( Fun, E#xmlElement.content). + + +%% @spec value_of(E) -> List +%% E = unknown() +%% +%% @doc Concatenates all text nodes within the tree. +%% +%%

Example:


+%% <xsl:template match="title">
+%%   <div align="center">
+%%     <h1><xsl:value-of select="." /></h1>
+%%   </div>
+%% </xsl:template>
+%% 
+%% +%%

becomes:


+%%  template(E = #xmlElement{name='title'}) ->
+%%    ["<div align="center"><h1>", 
+%%      value_of(select(".", E)), "</h1></div>"]
+%% 
+value_of(E)-> + lists:reverse(xmerl_lib:foldxml(fun value_of1/2, [], E)). + +value_of1(#xmlText{}=T1, Accu)-> + [xmerl_lib:export_text(T1#xmlText.value)|Accu]; +value_of1(_, Accu) -> + Accu. + +%% @spec select(String::string(),E)-> E +%% +%% @doc Extracts the nodes from the xml tree according to XPath. +%% @see value_of/1 +select(Str,E)-> + xmerl_xpath:string(Str,E). + +%% @spec built_in_rules(Fun, E) -> List +%% +%% @doc The default fallback behaviour. Template funs should end with: +%%
template(E) -> built_in_rules(fun template/1, E). +built_in_rules(Fun, E = #xmlElement{})-> + lists:map(Fun, E#xmlElement.content); +built_in_rules(_Fun, E = #xmlText{}) -> + xmerl_lib:export_text(E#xmlText.value); +built_in_rules(_Fun, E = #xmlAttribute{}) -> + E#xmlAttribute.value; +built_in_rules(_Fun, _E) ->[]. -- cgit v1.2.3