Напишите буквальное поле YAML с помощью нового YamlBuilder в Groovy 3.0.

Groovy 3.0 имеет новый класс YamlBuilder, который работает аналогично существующему классу JsonBuilder.

Я пытаюсь понять, могу ли я использовать YamlBuilder для создания буквального поля в YAML, например:

data: |
  this is
  a literal
  text value

Мое первое предположение заключалось в том, что многострочная строка Groovy будет работать:

new YamlBuilder() {
  data: '''\
this is
a literal
text value'''
}

Но это дает мне:

data: "this is\na literal\ntext value\n"`

Я не вижу ничего полезного в YamlBuilder Javadoc, а пример mrhaki не показывает этот вариант использования.

Кто-нибудь знает, можно ли / как это сделать?

2 ответа

Решение

Вы можете сделать следующее:

import groovy.yaml.*
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.dataformat.yaml.YAMLFactory;
import static com.fasterxml.jackson.dataformat.yaml.YAMLGenerator.Feature.LITERAL_BLOCK_STYLE

def yaml = new YamlBuilder()

yaml {
  data '''\
this is
a literal
text value'''
}

println new ObjectMapper(new YAMLFactory().configure(LITERAL_BLOCK_STYLE, true)).writeValueAsString(yaml)

Если вам нужна собственная настраиваемая сериализация

Под обложками Groovy YamlBuilder использует конвертер JSON в YAML Джексона.

Конвертер Джексона поддерживает буквальный блочный стиль, но его необходимо включить. Текущая версия YamlBuilder не поддерживает параметры настройки.

Я скопировал класс YamlBuilder и связанный с ним класс YamlConverter, чтобы изменить настройки.

В классе YamlBuilder я изменил этот метод:

public static String convertJsonToYaml(Reader jsonReader) {
    try (Reader reader = jsonReader) {
        JsonNode json = new ObjectMapper().readTree(reader);

        return new YAMLMapper().writeValueAsString(json);
    } catch (IOException e) {
        throw new YamlRuntimeException(e);
    }
}

Чтобы быть таким:

public static String convertJsonToYaml(Reader jsonReader) {
    try (Reader reader = jsonReader) {
        JsonNode json = new ObjectMapper().readTree(reader);

        YAMLMapper mapper = new YAMLMapper()
        mapper.configure(YAMLGenerator.Feature.LITERAL_BLOCK_STYLE, true)
        return mapper.writeValueAsString(json);
    } catch (IOException e) {
        throw new YamlRuntimeException(e);
    }
}

Это позволяет мне делать:

mapper.configure(YAMLGenerator.Feature.LITERAL_BLOCK_STYLE, true)

Что успешно отобразит YAML как буквальный блок:

data: |-
  this is
  a literal
  text value
Другие вопросы по тегам