Added RedirectUsingNamedRoute
[castle.git] / InversionOfControl / Castle.Windsor / Configuration / Interpreters / XmlProcessor / ElementProcessors / IfProcessingInstructionProcessor.cs
blob59511a279b7f70bd82715b0d7089d65b606d073a
1 // Copyright 2004-2008 Castle Project - http://www.castleproject.org/
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 // http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
15 namespace Castle.Windsor.Configuration.Interpreters.XmlProcessor.ElementProcessors
17 using System;
18 using System.Collections;
19 using System.Xml;
21 enum StatementState
23 Init,
24 Collect,
25 Finished
28 public class IfProcessingInstructionProcessor : AbstractXmlNodeProcessor
30 private static readonly XmlNodeType[] acceptNodes = new XmlNodeType[] {XmlNodeType.ProcessingInstruction};
32 private static readonly String IfPiName = "if";
33 private static readonly String EndPiName = "end";
34 private static readonly String ElsePiName = "else";
35 private static readonly String ElsifPiName = "elsif";
37 public IfProcessingInstructionProcessor()
41 public override String Name
43 get { return IfPiName; }
46 public override XmlNodeType[] AcceptNodeTypes
48 get { return acceptNodes; }
51 public override void Process(IXmlProcessorNodeList nodeList, IXmlProcessorEngine engine)
53 XmlProcessingInstruction node = nodeList.Current as XmlProcessingInstruction;
55 AssertData(node, true);
57 StatementState state = engine.HasFlag(node.Data) ? StatementState.Collect : StatementState.Init;
59 ArrayList nodesToProcess = new ArrayList();
60 int nestedLevels = 0;
62 RemoveItSelf(nodeList.Current);
64 while(nodeList.MoveNext())
66 if (nodeList.Current.NodeType == XmlNodeType.ProcessingInstruction)
68 XmlProcessingInstruction pi = nodeList.Current as XmlProcessingInstruction;
70 if (pi.Name == EndPiName)
72 nestedLevels--;
74 if (nestedLevels < 0)
76 RemoveItSelf(nodeList.Current);
77 break;
80 else if (pi.Name == IfPiName)
82 nestedLevels++;
84 else if (nestedLevels == 0)
86 if (pi.Name == ElsePiName || pi.Name == ElsifPiName)
88 ProcessElseElement(pi, engine, ref state);
89 continue;
94 if (state == StatementState.Collect)
96 nodesToProcess.Add(nodeList.Current);
98 else
100 RemoveItSelf(nodeList.Current);
104 if (nestedLevels != -1)
106 throw new XmlProcessorException("Unbalanced pi if element");
109 if (nodesToProcess.Count > 0)
111 engine.DispatchProcessAll(new DefaultXmlProcessorNodeList(nodesToProcess));
115 private void ProcessElseElement(XmlProcessingInstruction pi, IXmlProcessorEngine engine, ref StatementState state)
117 AssertData(pi, pi.Name == ElsifPiName);
119 if (state == StatementState.Collect)
121 state = StatementState.Finished;
123 else if (pi.Name == ElsePiName || engine.HasFlag(pi.Data))
125 if (state == StatementState.Init)
127 state = StatementState.Collect;
131 RemoveItSelf(pi);
132 return;
135 private void AssertData(XmlProcessingInstruction pi, bool requireData)
137 String data = pi.Data.Trim();
139 if (data == "" && requireData)
141 throw new XmlProcessorException("Element '{0}' must have a flag attribute", pi.Name);
143 else if (data != "")
145 if (!requireData)
147 throw new XmlProcessorException("Element '{0}' cannot have any attributes", pi.Name);