Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to perform case insensitive search in XPath?

I am trying to implement case insensitive search using XPath. I have already referred how to perform a case-insensitive attribute selector in xquery so please check before marking as duplicate. I am using Lcase to convert my variable (L_search) to lowercase and lower-case functions.

My original case sensitive XPath expression is:

XPath       =  "//*[contains(., '"& search &"')]/ancestor-or-self::*/*[local-name()='home' and @locale='en']"

I have tried many combinations like :

XPath       =  "//*lower-case([contains(., '"& L_search &"')])/ancestor-or-self::*/*[local-name()='home' and @locale='en']"

XPath       =  "//*[contains(lower-case(.), '"& L_search &"')])/ancestor-or-self::*/*[local-name()='home' and @locale='en']"

But none of them is yielding a result.

This is the code I'm running:

Sub ProcessFolder(FolderPath)
    On Error Resume Next
    Set fldr = fso.GetFolder(FolderPath)

    Set Fls = fldr.files
    For Each thing in Fls
            sFSpec = FSO.GetAbsolutePathName(thing)
            objMSXML.async = True
            objMSXML.load sFSpec
             If 0 = objMSXML.parseError Then
                Dim sXPath   : sXPath       =  "//*[contains(., '"& search &"')]/ancestor-or-self::*/*[local-name()='name' and @locale='en']"

                Dim querySubject : Set querySubject = objMSXML.selectSingleNode(sXPath)
                    Set p = document.createElement("p")
                        p.innerText = thing.Path
                        document.body.appendChild p
                    If querySubject Is Nothing Then
                        MsgBox sXPath, "failed"
like image 724
Kailash Singh Avatar asked Sep 16 '25 21:09

Kailash Singh


2 Answers

VBScript supports only XPath 1.0 and not XQuery, so first edit your question title.

In XPath 1.0 the translate() function is used for case insensitivity.

//*[contains(translate(., 'ABCDEFGHIJKLMNOPQRSTUVWXYZ', 'abcdefghijklmnopqrstuvwxyz') , search)]/ancestor-or-self::*/*[local-name()='home' and @locale='en']

Where search = Lcase(V_SAEARCH)

It will work perfect. No need to use quotes around your variable.

another way to write this is:-

//*[contains(translate(., 'ABCDEFGHIJKLMNOPQRSTUVWXYZ', 'abcdefghijklmnopqrstuvwxyz') , translate('" & search & "', 'ABCDEFGHIJKLMNOPQRSTUVWXYZ', 'abcdefghijklmnopqrstuvwxyz'))]/ancestor-or-self::*/*[local-name()='home' and @locale='en']

Here search variable is being translated in XPath.

like image 77
user2816085 Avatar answered Sep 19 '25 17:09

user2816085


XPath 2.0

If you use case-insensitive matches(),

"//*[matches(., '"& search &"', 'i')]/ancestor-or-self::*/*[local-name()='home' and @locale='en']"

you won't need to worry about the case of your search variable.


See also case insensitive xpath contains() possible? for other XPath 1.0 and 2.0 solutions.

like image 22
kjhughes Avatar answered Sep 19 '25 18:09

kjhughes