internal void Parse(XmlElement configNode)
{
Contract.Requires<ArgumentNullException>(configNode != null);
this.ValidationResult = ResourceManager.ValidateElement(configNode, ConfigSchemaPath);
if (!this.ValidationResult.Success)
return;
var nm = XmlNamespaces.Manager;
var packageElement = configNode.SelectSingleNode("p:package", nm);
this.Type = (ProjectType) Enum.Parse(typeof(ProjectType), configNode.Name, true);
if (this.Type == ProjectType.Project && packageElement != null)
{
this.Type = ProjectType.ExtensionProject;
}
foreach (XmlElement child in configNode.SelectNodes(
string.Format("*[namespace-uri() != '{0}']", XmlNamespaces.ProjectConfigurationNamespace)))
{
customElements.Add(child);
}
foreach (XmlElement element in configNode.SelectNodes("p:dependencies/p:extension", nm))
{
string extensionName = element.GetAttribute("name");
if (!this.Dependencies.Contains(extensionName))
this.Dependencies.Add(extensionName);
}
XmlNode variablesNode = configNode.SelectSingleNode("p:variables", nm);
if (variablesNode != null)
{
if (this.VariablesNode != null)
{
foreach (XmlElement variableNode in variablesNode.SelectNodes("*"))
{
var importReady = this.VariablesNode.OwnerDocument.ImportNode(variableNode, true);
var id = variableNode.GetAttribute("id");
var current = this.VariablesNode.SelectSingleNode(
string.Format("intl:variable[@id='{0}']", id), nm);
if (current != null)
this.VariablesNode.ReplaceChild(importReady, current);
else
this.VariablesNode.AppendChild(importReady);
}
}
else
{
this.VariablesNode = variablesNode;
}
this.Variables = new Dictionary<string, NameValueCollection>();
var variables = variablesNode.SelectNodes("intl:variable", nm);
foreach (XmlElement elem in variables)
{
var values = elem.SelectNodes("intl:value", nm);
var valueDictionary = new NameValueCollection();
if (values.Count == 0)
{
valueDictionary["default"] = elem.InnerText;
}
else
{
foreach (XmlElement val in values)
valueDictionary.Add(val.GetAttribute("locale"), val.InnerText.Trim());
}
this.Variables[elem.GetAttribute("id")] = valueDictionary;
}
}
XmlElement routingNode = configNode.SelectSingleElement("p:routing", nm);
XmlElement pathsNode = configNode.SelectSingleElement("p:paths", nm);
string nodeValue = configNode.GetAttribute("name");
if (!string.IsNullOrEmpty(nodeValue))
this.Name = nodeValue;
nodeValue = configNode.GetAttribute("sharedCategory");
if (!string.IsNullOrEmpty(nodeValue))
this.SharedCategory = nodeValue;
nodeValue = configNode.GetAttribute("defaultLocale");
if (!string.IsNullOrEmpty(nodeValue))
this.DefaultLocale = nodeValue;
nodeValue = configNode.GetAttribute("defaultCategory");
if (!string.IsNullOrEmpty(nodeValue))
this.DefaultCategory = nodeValue;
nodeValue = configNode.GetAttribute("autoInternationalize");
if (!string.IsNullOrEmpty(nodeValue))
this.AutoInternationalize = nodeValue.ContainsAnyOf("yes", "1", "true");
nodeValue = configNode.GetAttribute("debugMode");
if (!string.IsNullOrEmpty(nodeValue))
this.IsDebugEnabled = nodeValue.ContainsAnyOf("yes", "1", "true");
if (pathsNode != null)
{
this.PathTemplates.Parse(pathsNode);
XmlNode node = pathsNode.SelectSingleNode("p:AssetPath", nm);
if (node != null)
{
nodeValue = node.InnerText;
if (!string.IsNullOrEmpty(nodeValue))
this.AssetPath = nodeValue.TrimEnd('/') + "/";
}
}
if (routingNode != null)
this.Routing.Parse(routingNode);
XmlElement linkingNode = configNode.SelectSingleElement("p:linking", nm);
if (linkingNode != null)
this.Linking.Parse(linkingNode);
XmlElement environmentNode = configNode.SelectSingleElement("p:environment", nm);
if (environmentNode != null)
this.Environment.Parse(environmentNode);
XmlElement cachingNode = configNode.SelectSingleElement("p:viewcaching", nm);
if (cachingNode != null)
this.ViewCaching.Parse(cachingNode);
foreach (XmlElement libraryNode in configNode.SelectNodes("p:libraries/p:library", nm))
{
ResourceLibraryInfo info = new ResourceLibraryInfo(libraryNode, this.Id);
this.ResourceLibraries.Add(info.Name, info);
}
foreach (XmlElement moduleNode in configNode.SelectNodes("p:modules/p:module", nm))
{
ModuleConfiguration moduleConfig = new ModuleConfiguration(moduleNode, this.Id);
var moduleKey = string.IsNullOrWhiteSpace(moduleConfig.Category)
? moduleConfig.Name
: moduleConfig.Category + "/" + moduleConfig.Name;
this.Modules.Add(moduleKey, moduleConfig);
}
var localeNodes = configNode.SelectNodes("p:internationalization/p:locale", nm);
if (localeNodes.Count != 0)
{
this.Locales = new Dictionary<string, LocaleInfo>();
this.Categories[this.DefaultCategory].Locales.Clear();
foreach (XmlElement locale in localeNodes)
{
var name = locale.GetAttribute("name");
var info = new LocaleInfo(locale);
this.Locales[name] = info;
this.Categories[this.DefaultCategory].Locales.Add(name);
}
}
if (this.Locales.Count != 0 && !this.Locales.ContainsKey(this.DefaultLocale))
{
string firstLocale = this.Locales.First().Key;
log.ErrorFormat("The default locale '{0}' doesn't exist, resetting it to '{1}'.", this.DefaultLocale, firstLocale);
this.DefaultLocale = firstLocale;
}
var categoryNodes = configNode.SelectNodes("p:categories/p:category", nm);
if (categoryNodes.Count != 0)
{
this.Categories.Clear();
foreach (XmlElement categoryElement in categoryNodes)
{
var category = new CategoryInfo(categoryElement);
this.Categories[category.Name] = category;
var undefinedLocales = category.Locales.Where(name => !this.Locales.ContainsKey(name)).ToList();
if (undefinedLocales.Count != 0)
{
log.ErrorFormat("Category '{0}' is configured to use these unsupported locales: {1}.",
category.Name, string.Join(",", undefinedLocales));
}
}
}
if (this.Categories.Count != 0 && !this.Categories.ContainsKey(this.DefaultCategory))
{
string firstCategory = this.Categories.First().Key;
log.ErrorFormat("The default category '{0}' doesn't exist, resetting it to '{1}'.", this.DefaultCategory, firstCategory);
this.DefaultCategory = firstCategory;
}
foreach (XmlElement viewNode in configNode.SelectNodes("p:metaViews/p:metaView", nm))
{
var name = viewNode.GetAttribute("name");
var info = new MetaViewInfo(viewNode);
this.MetaViews[name] = info;
}
foreach (XmlElement viewNode in configNode.SelectNodes("p:errorViews/p:view", nm))
{
var error = viewNode.GetAttribute("error");
var info = new ErrorViewInfo(viewNode);
this.ErrorViews[error] = info;
}
this.Package = new PackageConfiguration(packageElement);
if (this.Changed != null)
this.Changed(this, EventArgs.Empty);
}