XPath 2.0: извлечение узлов по атрибуту, где значение нечувствительно к регистру - PullRequest
3 голосов
/ 15 сентября 2011

Я новичок в использовании XPath и пытаюсь получить узел через его атрибут, но проблема в том, что атрибут не учитывает регистр, то есть я не буду точно знать, как строка помещается в документе.

Так, например:

Учитывая документ:

<Document xmlns:my="http://www.MyDomain.com/MySchemaInstance">
  <Machines>
    <Machine FQDN="machine1.mydomain.com">
      <...>
    </Machine>
    <Machine FQDN="Machine2.MyDomain.Com">
      <...>
    </Machine>
  </Machines>
</Document>

Если я хочу получить машину1, я бы использовал XPath:

//my:Machines/my:Machine/*[@FQDN='machine1.mydomain.com']

Но подобный XPath для получения machine2 потерпит неудачу, потому что регистр не совпадает:

//my:Machines/my:Machine/*[@FQDN='machine2.mydomain.com']  //Fails

Я видел различные упоминания в постах с использованием чего-то вроде (я не уверен, как применить к этому пространства имен):

translate(@FQDN, 'ABCDEFGHIJKLMNOPQRSTUVWXYZ', 'abcdefghijklmnopqrstuvwxyz')

Но даже если я заставлю его работать, это будет очень громоздко, учитывая количество раз, когда я буду его использовать.


Наконец я прочитал, что XPath 2.0поддерживает match () и нижний регистр (), но, будучи новичком в XPath, я не понимаю, как их применять:

Например, если я попробую следующее, я получу «Неверное квалифицированное имя»: // my: Machines / my: Machine / [соответствует (@FQDN, '(? I) machine1.mydomain.com')] // my: Machines / my: Machine / [строчные (@FQDN,'machine1.mydomain.com')]


Может ли кто-нибудь предоставить пример XPath, включающий обработку пространства имен, которое будет работать?

Спасибо

1 Ответ

3 голосов
/ 15 сентября 2011

Ваш пример операторов XML и XPath не совпадает.

  • Образцы элементов XML не связаны с пространством имен.Префикс «my» namespace-prefix объявлен, но не используется для этих элементов, поэтому они находятся в «no namespace».
  • В вашем примере XPath используются фильтры предикатов для дочерних элементов Machine, а не для элемента Machine, который имеет @FQDN.

. Вы можете использоватьлюбой из этих методов ищет значение без учета регистра:

  • matches() функция, с флагом для сопоставления без учета регистра:

    //Machines/Machine[matches(@FQDN,'machine2.mydomain.com','i')]
    
  • upper-case() функция для вычисления строк в верхнем регистре:

    //Machines/Machine[upper-case(@FQDN)=upper-case('machine2.mydomain.com')]
    
  • lower-case() функция для оценки строчных букв:

    //Machines/Machine[lower-case(@FQDN)=lower-case('machine2.mydomain.com')]
    

Может ли кто-нибудь предоставить пример XPath, который включает обработку пространства имен, которое будет работать?

Не уверен, что вы имели в виду под обработкой пространств имен, но если вы хотите сопоставить эти элементы независимо от их пространства имен, вы можете использовать подстановочный оператор для пространства имен:

//*:Machines/*:Machine[matches(@FQDN,'machine2.mydomain.com','i')]
...