Package-nameがkeyであるパッケージの辞書と、いくつかの詳細の辞書がvalueであるパッケージがあります。
_{
"php7.1-readline": {
"latest": "7.1.9-1+ubuntu14.04.1+deb.sury.org+1",
"origins": [
"ppa.launchpad.net"
],
"version": "7.1.6-2~ubuntu14.04.1+deb.sury.org+1",
"www": "http://www.php.net/"
},
"php7.1-xml": {
"latest": "7.1.9-1+ubuntu14.04.1+deb.sury.org+1",
"origins": [
"ppa.launchpad.net"
],
"version": "7.1.6-2~ubuntu14.04.1+deb.sury.org+1",
"www": "http://www.php.net/"
},
"plymouth": {
"version": "0.8.8-0ubuntu17.1"
},
....
}
_
上記を、値にlatest
-属性を持つパッケージのみを含む辞書に減らしたいと思います。
_json_query
_が使用するフィルターのように見えますが、構文がわかりません。そこにある例はすべて、同じ辞書の辞書ではなく、辞書のリストで動作しているようです。
たとえば、上記の辞書をjson_query('*.latest')
に「パイプ」すると、実際の最新バージョンのlistが得られます。
_[
"7.1.9-1+ubuntu14.04.1+deb.sury.org+1",
"7.1.9-1+ubuntu14.04.1+deb.sury.org+1",
"7.1.6-2~ubuntu14.04.1+deb.sury.org+1"
]
_
代わりに、辞書要素全体を取得するにはどうすればよいですか?
希望はありますか?
dict2items
フィルター 2017年12月に追加、ネイティブ機能を使用して可能です:
- debug:
msg: "{{ dict(pkg | dict2items | json_query('[?value.latest].[key, value.latest]')) }}"
結果:
"msg": {
"php7.1-readline": "7.1.9-1+ubuntu14.04.1+deb.sury.org+1",
"php7.1-xml": "7.1.9-1+ubuntu14.04.1+deb.sury.org+1"
}
この変換(I think)をJinjaフィルターだけで実行することはできませんが、Ansibleロジックを少し適用することでそこに到達できます。次のプレイブックでは、with_dict
ループを使用して辞書内の項目をループし、一致する項目から新しい辞書を作成します。
- hosts: localhost
vars:
packages: {
"php7.1-readline": {
"latest": "7.1.9-1+ubuntu14.04.1+deb.sury.org+1",
"origins": [
"ppa.launchpad.net"
],
"version": "7.1.6-2~ubuntu14.04.1+deb.sury.org+1",
"www": "http://www.php.net/"
},
"php7.1-xml": {
"latest": "7.1.9-1+ubuntu14.04.1+deb.sury.org+1",
"origins": [
"ppa.launchpad.net"
],
"version": "7.1.6-2~ubuntu14.04.1+deb.sury.org+1",
"www": "http://www.php.net/"
},
"plymouth": {
"version": "0.8.8-0ubuntu17.1"
}
}
tasks:
- set_fact:
new_packages: >
{{ new_packages|default({})|
combine({item.key: item.value}) }}
with_dict: "{{ packages }}"
when: "{{ item.value.latest is defined }}"
- debug:
var: new_packages
この質問を https://stackoverflow.com/a/41584889/2795592 にリンクするのは正しいです。
箱から出してjson_queryと同時にキーと値を操作するオプションはありません(Ansible 2.4.0以降)。
これがパッチされた json_query.py jqのようなto_entries
/from_entries
関数をサポートします。プレイブックの近くの./filter_plugins
に入れて、次のクエリを実行できます。
- debug:
msg: "{{ pkg | json_query('to_entries(@) | [?value.latest].{key:key, value:value.latest} | from_entries(@)')}}"
この結果を得るには:
"msg": {
"php7.1-readline": "7.1.9-1+ubuntu14.04.1+deb.sury.org+1",
"php7.1-xml": "7.1.9-1+ubuntu14.04.1+deb.sury.org+1"
}
暇があればすぐにPRをansibleにします。