Как заставить Jq всегда возвращаться в массиве

Мой вклад может быть следующим:

      <?xml version="1.0" encoding="UTF-8"?>
<Package xmlns="http://soap.sforce.com/2006/04/metadata">
    <types>
        <members>UserTriggerHandler_Test</members>
        <members>UserTriggerHandasdler_Test</members>
        <name>ApexClass</name>
    </types>
    <version>52.0</version>
</Package>

Или

      <?xml version="1.0" encoding="UTF-8"?>
<Package xmlns="http://soap.sforce.com/2006/04/metadata">
    <types>
        <members>UserTriggerHandasdler_Test</members>
        <name>ApexClass</name>
    </types>
    <version>52.0</version>
</Package>

Значения Xp для них:

      {
    "Package": {
        "@xmlns": "http://soap.sforce.com/2006/04/metadata",
        "types": {
            "members": "UserTriggerHandasdler_Test",
            "name": "ApexClass"
        },
        "version": "52.0"
    }
}

а также

      {
    "Package": {
        "@xmlns": "http://soap.sforce.com/2006/04/metadata",
        "types": {
            "members": ["UserTriggerHandler_Test", "UserTriggerHandasdler_Test"],
            "name": "ApexClass"
        },
        "version": "52.0"
    }
}

Соответственно.

И я пытаюсь передать ввод в эту функцию.

      classsvalue=`cat manifest/package.xml | xq . | jq '.Package.types | if type=="array" then .[] else . end | select(.name=="ApexClass") |select(.members!="Test")|.members | join(",")'`
echo $classsvalue

Но это не удается из-за join(","). Я хочу заставить jqчтобы всегда возвращать элементы в массиве. Это возможно?

Я ожидаю выхода как "UserTriggerHandasdler_Test" а также "UserTriggerHandasdler_Test,UserTriggerHandasdler_Test" соответственно.

2 ответа

Решение

То, что вы просите, на самом деле не является массивом, поэтому я игнорирую эту часть вопроса.

      # Original, unmodified code here
.Package.types |
if type=="array" then .[] else . end |
select(.name=="ApexClass") |
select(.members!="Test") |
.members |
# New code here
if type == "string" then [.] else . end | join(",")

Эта последняя строка является критической частью - перенос результата в список, если это строка, перед выполнением .

Если вы установили https://kislyuk.github.io/yq/ версию xq в комплекте с помощьюpip install yqто у вас есть несколько дополнительных опций:

      $ xq --help

  -h, --help            show this help message and exit
  --xml-output, -x      Transcode jq JSON output back into XML and emit it
  --xml-item-depth XML_ITEM_DEPTH
                        Specify depth of items to emit (default 0; use a positive integer to stream large docs)
  --xml-dtd             Preserve XML Document Type Definition (disables streaming of multiple docs)
  --xml-root XML_ROOT   When transcoding back to XML, envelope the output in an element with this name
  --xml-force-list XML_FORCE_LIST
                        Emit a list for elements with this name even if they occur only once (option can repeat)
  --in-place, -i        Edit files in place (no backup - use caution)
  --version             show program's version number and exit

--xml-force-listСоздать список элементов с этим именем, даже если они встречаются только один раз (опция может повторяться)

Поэтому должен уметь:

      cat manifest/package.xml | xq . --xml-force-list "members"

Что обеспечитmembersвсегда является массивом, независимо от того, существует ли один экземпляр или несколько.

Здесь используется библиотека https://github.com/martinblech/xmltodict .force_listфункция.

Другие вопросы по тегам