Bloom.Book.BookData.UpdateDomFromDataSet C# (CSharp) Method

UpdateDomFromDataSet() private method

Where, for example, somewhere on a page something has data-book='foo' lang='fr', we set the value of that element to French subvalue of the data item 'foo', if we have one.
private UpdateDomFromDataSet ( DataSet data, string elementName, XmlDocument targetDom, string>.HashSet itemsToDelete ) : void
data DataSet
elementName string
targetDom System.Xml.XmlDocument
itemsToDelete string>.HashSet
return void
        private void UpdateDomFromDataSet(DataSet data, string elementName,XmlDocument targetDom, HashSet<Tuple<string, string>> itemsToDelete)
        {
            try
            {
                var query = String.Format("//{0}[(@data-book or @data-collection or @data-library or @data-book-attributes)]", elementName);
                var nodesOfInterest = targetDom.SafeSelectNodes(query);

                foreach (XmlElement node in nodesOfInterest)
                {
                    var key = node.GetAttribute("data-book").Trim();
                    if (key == string.Empty)
                    {
                        key = node.GetAttribute("data-book-attributes").Trim();
                        if (key != string.Empty)
                        {
                            UpdateAttributes(data, node, key);
                            continue;
                        }
                        key = node.GetAttribute("data-collection").Trim();
                        if (key == string.Empty)
                        {
                            key = node.GetAttribute("data-library").Trim(); //"library" is the old name for what is now "collection"
                        }
                    }

                    if (string.IsNullOrEmpty(key)) continue;

                    if (data.TextVariables.ContainsKey(key))
                    {
                        if (UpdateImageFromDataSet(data, node, key)) continue;

                        var lang = node.GetOptionalStringAttribute("lang", "*");
                        if (lang == "N1" || lang == "N2" || lang == "V")
                            lang = data.WritingSystemAliases[lang];

                        //							//see comment later about the inability to clear a value. TODO: when we re-write Bloom, make sure this is possible
                        //							if(data.TextVariables[key].TextAlternatives.Forms.Length==0)
                        //							{
                        //								//no text forms == desire to remove it. THe multitextbase prohibits empty strings, so this is the best we can do: completly remove the item.
                        //								targetDom.RemoveChild(node);
                        //							}
                        //							else
                        if (!string.IsNullOrEmpty(lang)) //if we don't even have this language specified (e.g. no national language), the  give up
                        {
                            //Ideally, we have this string, in this desired language.
                            var s = data.TextVariables[key].TextAlternatives.GetBestAlternativeString(new[] {lang, "*"});

                            if(KeysOfVariablesThatAreUrlEncoded.Contains(key))
                            {
                                Debug.Assert(!s.Contains("&amp;"),"In memory, all image urls should be encoded such that & is just &.");
                            }
                            //But if not, maybe we should copy one in from another national language
                            if (string.IsNullOrEmpty(s))
                                s = PossiblyCopyFromAnotherLanguage(node, lang, data, key);

                            //NB: this was the focus of a multi-hour bug search, and it's not clear that I got it right.
                            //The problem is that the title page has N1 and n2 alternatives for title, the cover may not.
                            //the gather page was gathering no values for those alternatives (why not), and so GetBestAlternativeSTring
                            //was giving "", which we then used to remove our nice values.
                            //REVIEW: what affect will this have in other pages, other circumstances. Will it make it impossible to clear a value?
                            //Hoping not, as we are differentiating between "" and just not being in the multitext at all.
                            //don't overwrite a datadiv alternative with empty just becuase this page has no value for it.
                            if (s == "" && !data.TextVariables[key].TextAlternatives.ContainsAlternative(lang))
                                continue;

                            //hack: until I think of a more elegant way to avoid repeating the language name in N2 when it's the exact same as N1...
                            if (data.WritingSystemAliases.Count != 0 && lang == data.WritingSystemAliases["N2"] &&
                                s ==
                                data.TextVariables[key].TextAlternatives.GetBestAlternativeString(new[]
                                {
                                    data.
                                        WritingSystemAliases
                                        ["N1"]
                                    , "*"
                                }))
                            {
                                s = ""; //don't show it in N2, since it's the same as N1
                            }
                            SetInnerXmlPreservingLabel(key, node, s);
                        }
                    }
                    else if (!HtmlDom.IsImgOrSomethingWithBackgroundImage(node))
                    {
                        // See whether we need to delete something
                        var lang = node.GetOptionalStringAttribute("lang", "*");
                        if (lang == "N1" || lang == "N2" || lang == "V")
                            lang = data.WritingSystemAliases[lang];
                        if (itemsToDelete.Contains(Tuple.Create(key, lang)))
                        {
                            SetInnerXmlPreservingLabel(key, node, "");// a later process may remove node altogether.
                        }
                    }
                }
            }
            catch (Exception error)
            {
                throw new ApplicationException(
                    "Error in UpdateDomFromDataSet(," + elementName + "). RawDom was:\r\n" +
                    targetDom.OuterXml, error);
            }
        }