解析 YAML 以在 shell 中创建动态查询

解析 YAML 以在 shell 中创建动态查询

我对脚本编写非常陌生,我的任务是找出一种编写 shell 脚本的方法,该脚本将根据提供的 YAML 文档创建 SQL 查询。我可以追踪到yq要使用的解析器;但是,我一直不知道如何使用 YAML 子节点中的各个值。我需要解析的示例 YAML 是:

config:
  - system1:
      database_name: database1
      port: '1234'
      table:
        - name: table1
          values: 'table_id, value1, 30, randomValue'
        - name: table2
          values: 'table_id, value1, randomValue, randomValue, value2'
        - name: table2
          values: 'table_id, value2, randomValue, randomValue'
  - system2:
      database_name: database2
      port: '12345'
      table:
        - name: table4
          values: 'table_id, value3, 30, randomValue'
        - name: table5
          values: 'table_id, randomValue, randomValue, value4'
        - name: table6
          values: 'table_id, value3, value4'

我当前尝试编写的脚本只不过是SELECT语句,但稍后会演变:

# This will later be used to create insert/update queries based on the values so 
# will be needing a handle for that too.
psql -h localhost -p $PORT -d $DATABASE << EOF
select * from $TABLE LIMIT 10;
EOF

如果可能的话,在听起来没有必要的情况下,我希望看到有关如何使用yq库的建议,因为它支持在 SQL 部分完成后我需要对此脚本执行的一系列操作。

如果问题太愚蠢,我深表歉意,这将是我第一次接触 shell 脚本。

如果相关的话,我正在使用 Ubuntu 18.4 发行版。

答案1

使用安德烈·基斯柳克yq(围绕 JSON 处理器的 YAML 感知包装器jq)而不是 Mike Farah 的yq,您可以创建执行查询所需的 shell 语句,如下所示:

yq -r '
    .config[] |
    map(
        @sh "psql -h localhost -p \(.port) -d \(.database_name) <<END_SQL",
        (.table | map("SELECT \(.values) FROM \(.name) LIMIT 10;"))[],
        "END_SQL"
    )[]' file

或者,如果您不喜欢使用map

yq -r '
    .config[][] |
    @sh "psql -h localhost -p \(.port) -d \(.database_name) <<END_SQL",
    (.table[] | "SELECT \(.values) FROM \(.name) LIMIT 10;"), 
    "END_SQL"' file

这会迭代数组configpsql为每个元素创建一个命令。该psql命令从条目的和值(使用输出运算符为 shell 引用)获取其-p和选项参数。-dportdatabase_name@sh

实际的 SQL 语句通过此处文档重定向提供给命令,并由任意选择的字符串分隔END_SQL。这些语句values按原样使用需要提取的字段的值,并将该name值用作从中提取字段的表的名称。不对这些值执行特殊引用。

根据问题中的数据,上述命令生成以下 shell 代码:

psql -h localhost -p '1234' -d 'database1' <<END_SQL
SELECT table_id, value1, 30, randomValue FROM table1 LIMIT 10;
SELECT table_id, value1, randomValue, randomValue, value2 FROM table2 LIMIT 10;
SELECT table_id, value2, randomValue, randomValue FROM table2 LIMIT 10;
END_SQL
psql -h localhost -p '12345' -d 'database2' <<END_SQL
SELECT table_id, value3, 30, randomValue FROM table4 LIMIT 10;
SELECT table_id, randomValue, randomValue, value4 FROM table5 LIMIT 10;
SELECT table_id, value3, value4 FROM table6 LIMIT 10;
END_SQL

然后,您可以通过管道将其传递到sh -s或使用 对其求值来执行此代码eval

相关内容