簡體   English   中英

使用ruamel.yaml修改YAML會添加額外的新行

[英]Modifying YAML using ruamel.yaml adds extra new lines

我需要為YAML文件中的現有鍵添加一個額外的值。 以下是我正在使用的代碼。

with open(yaml_in_path, 'r') as f:
    doc, ind, bsi = load_yaml_guess_indent(f, preserve_quotes=True)
doc['phase1'] += ['c']
with open(yaml_out_path, 'w') as f:
    ruamel.yaml.round_trip_dump(doc, f,
                                indent=2, block_seq_indent=bsi)

這是輸入和輸出。

輸入

phase1:
  - a
  # a comment.
  - b

phase2:
  - d

產量

phase1:
  - a
  # a comment.
  - b

  - c
phase2:
  - d

我如何擺脫bc之間的新界限? (當phase1是文件中的唯一鍵時,或者在phase1phase2之間沒有空phase1 ,就不會出現此問題。)

這里的問題是,空行被認為是一種注釋, ruamel.yaml中的注釋通過將它們與序列中的元素或映射中的鍵相關聯而得以保留。 該值存儲在名為ca的復雜屬性中,該屬性類似於與第二個元素相關聯的對象doc['phase1']

當然,你可以認為它應該在頂級映射/字典相關或者與相關的關鍵phase1 (如一些最后的空行注釋)或phase2的一些介紹性的空行注釋。 以上三個中的任何一個都是有效的,並且庫中目前沒有控制該策略的策略,在該策略中,空行(或添加了注釋)。

如果您輸入“真實”注釋(以#開頭),則它將phase1相關聯作為結束注釋,因為這些策略是不同的。

顯然,這需要徹底檢查,因為ruamel.yaml的最初目標是:-從YAML加載某些配置-更改某些值-將配置保存到YAML,在這種情況下,不會出現此類附加/插入問題。

因此,直到對庫進行擴展以對在何處附加(跟蹤)注釋和/或空行的控件進行控制,才有真正的解決方案。

在實現這種控制之前,可能最好的操作是:

import sys
import ruamel.yaml

yaml_str = """\
phase1:
  - a
  # a comment.
  - b

phase2:
  - d
"""

def append_move_comment(l, e):
    i = len(l) - 1
    l.append(e)
    x = l.ca.items[i][0]  # the end comment
    if x is None:
        return
    l.ca.items[i][0] = None
    l.ca.items[i+1] = [x, None, None, None]

data = ruamel.yaml.round_trip_load(yaml_str)
append_move_comment(data['phase1'], 'c')
ruamel.yaml.round_trip_dump(data, sys.stdout, indent=4, block_seq_indent=2)

我將indent值更改為4,這就是您輸入的值(之所以得到,是因為您將block_seq_indent的值指定為小)。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM