Clover Coverage Report - XWiki Rendering - Parent POM 4.0-SNAPSHOT (Aggregated)
Coverage timestamp: Mon Mar 12 2012 18:03:13 CET
../../../../../../../img/srcFileCovDistChart10.png 0% of files have more coverage
108   285   34   13.5
42   190   0.31   8
8     4.25  
1    
 
  ExtendedVelocityParser       Line # 41 108 0% 34 7 95.6% 0.9556962
 
  (92)
 
1    /*
2    * See the NOTICE file distributed with this work for additional
3    * information regarding copyright ownership.
4    *
5    * This is free software; you can redistribute it and/or modify it
6    * under the terms of the GNU Lesser General Public License as
7    * published by the Free Software Foundation; either version 2.1 of
8    * the License, or (at your option) any later version.
9    *
10    * This software is distributed in the hope that it will be useful,
11    * but WITHOUT ANY WARRANTY; without even the implied warranty of
12    * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13    * Lesser General Public License for more details.
14    *
15    * You should have received a copy of the GNU Lesser General Public
16    * License along with this software; if not, write to the Free
17    * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
18    * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
19    */
20    package org.xwiki.rendering.internal.parser.xwiki10.velocity;
21   
22    import java.util.ArrayList;
23    import java.util.List;
24   
25    import org.slf4j.Logger;
26    import org.slf4j.LoggerFactory;
27    import org.xwiki.component.manager.ComponentLookupException;
28    import org.xwiki.component.manager.ComponentManager;
29    import org.xwiki.rendering.internal.parser.xwiki10.HTMLFilter;
30    import org.xwiki.rendering.parser.xwiki10.macro.VelocityMacroConverter;
31    import org.xwiki.velocity.internal.util.InvalidVelocityException;
32    import org.xwiki.velocity.internal.util.VelocityBlock;
33    import org.xwiki.velocity.internal.util.VelocityParser;
34    import org.xwiki.velocity.internal.util.VelocityParserContext;
35   
36    /**
37    * Extends {@link VelocityParser} for specific needs.
38    *
39    * @version $Id: 707a50e29197a7d18b02e4bfec2ab41ea2240bfb $
40    */
 
41    public class ExtendedVelocityParser extends VelocityParser
42    {
43    /**
44    * The Logger to use for logging.
45    */
46    private static final Logger LOGGER = LoggerFactory.getLogger(VelocityParser.class);
47   
48    private ComponentManager componentManager;
49   
 
50  92 toggle public ExtendedVelocityParser(ComponentManager componentManager)
51    {
52  92 super();
53   
54  92 this.componentManager = componentManager;
55    }
56   
 
57  59 toggle @Override
58    public int getDirective(char[] array, int currentIndex, StringBuffer velocityBlock, VelocityParserContext context)
59    throws InvalidVelocityException
60    {
61  59 int i = currentIndex + 1;
62   
63  59 ExtendedVelocityParserContext econtext = (ExtendedVelocityParserContext) context;
64   
65    // Get macro name
66  59 StringBuffer directiveNameBuffer = new StringBuffer();
67  59 i = getDirectiveName(array, i, directiveNameBuffer, null, context);
68  59 String directiveName = directiveNameBuffer.toString();
69   
70  59 StringBuffer directiveBuffer = new StringBuffer();
71   
72  59 if (VELOCITYDIRECTIVE_ALL.contains(directiveName)) {
73    // get the velocity directive
74  19 if (VELOCITYDIRECTIVE_END.contains(directiveName)) {
75  7 if ("macro".equals(context.getCurrentElement().getName())) {
76  1 HTMLFilter.appendHTMLClose(directiveBuffer, econtext.getFilterContext(), true);
77    }
78   
79  7 context.popVelocityElement();
80    }
81   
82  19 directiveBuffer.append(array, currentIndex, i - currentIndex);
83   
84  19 if (!VELOCITYDIRECTIVE_NOPARAM.contains(directiveName)) {
85    // Skip spaces
86  11 i = getSpaces(array, i, directiveBuffer, context);
87   
88  11 if (i < array.length && array[i] == '(') {
89    // Skip condition
90  11 i = getMethodParameters(array, i, directiveBuffer, context);
91    } else {
92  0 throw new InvalidVelocityException();
93    }
94    }
95   
96    // consume the end of the line
97  19 i = getDirectiveEndOfLine(array, i, directiveBuffer, context);
98   
99  19 econtext.setVelocity(true);
100  19 context.setType(VelocityBlock.VelocityType.DIRECTIVE);
101   
102  19 if (VELOCITYDIRECTIVE_BEGIN.contains(directiveName)) {
103  7 context.pushVelocityElement(new VelocityBlock(directiveName, VelocityBlock.VelocityType.DIRECTIVE));
104   
105  7 if ("macro".equals(directiveName)) {
106  1 HTMLFilter.appendHTMLOpen(directiveBuffer, econtext.getFilterContext(), true);
107    }
108    }
109    } else {
110  40 directiveBuffer.append(array, currentIndex, i - currentIndex);
111   
112    // Skip spaces
113  40 i = getSpaces(array, i, directiveBuffer, context);
114   
115  40 if (i < array.length && array[i] == '(') {
116  37 ((ExtendedVelocityParserContext) context).setInline(true);
117   
118  37 List<String> parameters = new ArrayList<String>();
119    // Get condition
120  37 i = getMacroParameters(array, i, directiveBuffer, parameters, econtext);
121  37 String convertedMacro = convertMacro(directiveName, parameters, econtext);
122   
123  37 if (convertedMacro != null) {
124    // Apply conversion
125  31 directiveBuffer.setLength(0);
126  31 directiveBuffer.append(convertedMacro);
127    } else {
128  6 econtext.setVelocity(true);
129  6 context.setType(VelocityBlock.VelocityType.MACRO);
130    }
131    } else {
132  3 throw new InvalidVelocityException();
133    }
134    }
135   
136  56 velocityBlock.append(directiveBuffer);
137   
138  56 return i;
139    }
140   
 
141  37 toggle public String convertMacro(String name, List<String> parameters, ExtendedVelocityParserContext context)
142    {
143  37 String convertedMacro = null;
144   
145  37 try {
146  37 VelocityMacroConverter currentMacro = this.componentManager.lookup(VelocityMacroConverter.class, name);
147   
148  31 convertedMacro = currentMacro.convert(name, parameters, context.getFilterContext());
149   
150  31 if (convertedMacro != null) {
151  31 context.setInline(currentMacro.isInline());
152  31 context.setProtectedBlock(currentMacro.protectResult());
153   
154  31 context.setConversion(true);
155    }
156    } catch (ComponentLookupException e) {
157  6 LOGGER.debug("Can't find macro converter [" + name + "]", e);
158    } catch (Exception e) {
159  0 LOGGER.debug("Failed to convert macro [" + name + "]", e);
160    }
161   
162  37 return convertedMacro;
163    }
164   
 
165  37 toggle public int getMacroParameters(char[] array, int currentIndex, StringBuffer velocityBlock,
166    List<String> parameterList, ExtendedVelocityParserContext context)
167    {
168  37 velocityBlock.append('(');
169   
170  37 int i = currentIndex + 1;
171   
172  37 boolean isVelocity = false;
173   
174  84 for (; i < array.length;) {
175  81 i = getMacroParametersSeparator(array, i, velocityBlock, context);
176   
177  81 if (i < array.length) {
178    // If ')' it's the end of parameters
179  81 if (array[i] == ')') {
180  34 velocityBlock.append(')');
181  34 ++i;
182  34 break;
183    }
184   
185    // Skip parameter
186  47 StringBuffer parameterBlock = new StringBuffer();
187  47 i = getMacroParameter(array, i, parameterBlock, context);
188  47 isVelocity |= context.isVelocity();
189  47 parameterList.add(parameterBlock.toString());
190   
191  47 velocityBlock.append(parameterBlock);
192    }
193    }
194   
195  37 context.setVelocity(isVelocity);
196   
197  37 return i;
198    }
199   
 
200  13 toggle @Override
201    public int getSimpleComment(char[] array, int currentIndex, StringBuffer velocityBlock,
202    VelocityParserContext context)
203    {
204  13 ((ExtendedVelocityParserContext) context).setVelocity(true);
205  13 ((ExtendedVelocityParserContext) context).setInline(true);
206   
207  13 return super.getSimpleComment(array, currentIndex, velocityBlock, context);
208    }
209   
 
210  8 toggle @Override
211    public int getMultilinesComment(char[] array, int currentIndex, StringBuffer velocityBlock,
212    VelocityParserContext context)
213    {
214  8 ((ExtendedVelocityParserContext) context).setVelocity(true);
215  8 ((ExtendedVelocityParserContext) context).setInline(true);
216   
217  8 return super.getMultilinesComment(array, currentIndex, velocityBlock, context);
218    }
219   
 
220  48 toggle @Override
221    public int getEscape(char[] array, int currentIndex, StringBuffer velocityBlock, VelocityParserContext context)
222    {
223  48 char escapeChar = array[currentIndex];
224   
225  48 int i = currentIndex + 1;
226   
227  48 boolean isVelocity = false;
228  48 boolean escaped = false;
229   
230  494 for (; i < array.length;) {
231  493 if (!escaped) {
232  491 if (array[i] == '\\') {
233  2 escaped = true;
234  489 } else if (array[i] == '$') {
235  4 try {
236  4 i = getVar(array, i, null, context);
237  3 isVelocity = true;
238  3 continue;
239    } catch (InvalidVelocityException e) {
240  1 LOGGER.debug("Not a valid variable at char [" + i + "]", e);
241    }
242  485 } else if (array[i] == escapeChar) {
243  47 ++i;
244  47 break;
245    }
246    } else {
247  2 escaped = false;
248    }
249   
250  443 ++i;
251    }
252   
253  48 if (velocityBlock != null) {
254  0 velocityBlock.append(array, currentIndex, i - currentIndex);
255    }
256   
257  48 ((ExtendedVelocityParserContext) context).setVelocity(isVelocity);
258   
259  48 return i;
260    }
261   
 
262  44 toggle @Override
263    public int getVar(char[] array, int currentIndex, StringBuffer velocityBlock, VelocityParserContext context)
264    throws InvalidVelocityException
265    {
266  44 StringBuffer varName = new StringBuffer();
267   
268  44 int i = super.getVar(array, currentIndex, varName, null, context);
269   
270  36 if (velocityBlock != null) {
271  31 if ("msg".equals(varName.toString())) {
272    // Make sure translated messages are protected since it can contain html
273  3 velocityBlock.append("{{html clean=\"false\"}}");
274  3 velocityBlock.append(array, currentIndex, i - currentIndex);
275  3 velocityBlock.append("{{/html}}");
276    } else {
277  28 velocityBlock.append(array, currentIndex, i - currentIndex);
278    }
279    }
280   
281  36 ((ExtendedVelocityParserContext) context).setVelocity(true);
282   
283  36 return i;
284    }
285    }