Encoding XPath Expressions with both single and double quotes

前端 未结 8 1180
孤街浪徒
孤街浪徒 2020-11-30 07:21

XPath (v1) contains no way to encode expressions.

If you only have single OR double quotes then you can use expressions such as

//review[@name=\"Bob         


        
相关标签:
8条回答
  • 2020-11-30 08:17

    I was in need of this so I created this solution, for C#.

        /// <summary>
        /// Returns a valid XPath statement to use for searching attribute values regardless of 's or "s
        /// </summary>
        /// <param name="attributeValue">Attribute value to parse</param>
        /// <returns>Parsed attribute value in concat() if needed</returns>
        public static string GetXpathStringForAttributeValue(string attributeValue)
        {
            bool hasApos = attributeValue.Contains("'");
            bool hasQuote = attributeValue.Contains("\"");
    
            if (!hasApos)
            {
                return "'" + attributeValue + "'";
            }
            if (!hasQuote)
            {
                return "\"" + attributeValue + "\"";
            }
    
            StringBuilder result = new StringBuilder("concat(");
            StringBuilder currentArgument = new StringBuilder();
            for (int pos = 0; pos < attributeValue.Length; pos++)
            {
                switch (attributeValue[pos])
                {
                    case '\'':
                        result.Append('\"');
                        result.Append(currentArgument.ToString());
                        result.Append("'\",");
                        currentArgument.Length = 0;
                        break;
                    case '\"':
                        result.Append('\'');
                        result.Append(currentArgument.ToString());
                        result.Append("\"\',");
                        currentArgument.Length = 0;
                        break;
                    default:
                        currentArgument.Append(attributeValue[pos]);
                        break;
                }
            }
            if (currentArgument.Length == 0)
            {
                result[result.Length - 1] = ')';
            }
            else
            {
                result.Append("'");
                result.Append(currentArgument.ToString());
                result.Append("')");
            }
            return result.ToString();
        }
    
    0 讨论(0)
  • 2020-11-30 08:19

    Join in the fun

    public string XPathLiteral(string text) {
    
        const string APOS = "'";
        const string QUOTE = @"""";
    
        int pos = 0;
    
        int posApos;
        int posQuote;
    
        posQuote = text.IndexOf(QUOTE, pos);
    
        if (posQuote < 0) {
            return QUOTE + text + QUOTE;
        }//if
    
        posApos = text.IndexOf(APOS, pos);
    
        if (posApos < 0) {
            return APOS + text + APOS;
        }//if
    
        bool containsApos = posApos < posQuote;
    
        StringBuilder sb = new StringBuilder("concat(", text.Length * 2);
    
        bool loop = true;
        bool comma = false;
    
        while (loop) {
    
            if (posApos < 0) {
                posApos = text.Length;
                loop = false;
            }//if
    
            if (posQuote < 0) {
                posQuote = text.Length;
                loop = false;
            }//if
    
            if (comma) {
                sb.Append(",");
            } else {
                comma = true;
            }//if
    
            if (containsApos) {
                sb.Append(QUOTE);
                sb.Append(text.Substring(pos, posQuote - pos));
                sb.Append(QUOTE);
                pos = posQuote;
                if (loop) posApos = text.IndexOf(APOS, pos + 1);
            } else {
                sb.Append(APOS);
                sb.Append(text.Substring(pos, posApos - pos));
                sb.Append(APOS);
                pos = posApos;
                if (loop) posQuote = text.IndexOf(QUOTE, pos + 1);
            }//if
    
            // Toggle
            containsApos = !containsApos;
    
        }//while
    
        sb.Append(")");
    
        return sb.ToString();
    
    }//method
    
    0 讨论(0)
提交回复
热议问题