Java 8 次 类 在黄瓜中

Java 8 time classes in Cucumber

我有一个代表对象的黄瓜数据表。有些字段需要是 Instants,有些需要是 LocalDates。我环顾四周,所有关于解析 java 8 时间对象的帖子似乎都是几年前的,我想知道是否有一个库可以为我处理这个问题。

您可能首先要考虑是否需要将确切日期表达为方案的一部分。 If the dates are merely incidental to the scenario you should strongly consider removing them from the feature file.

但如果您必须这样做:jackson-databind 是必经之路。它主要用于将 POJO 与 JSON 序列化(反)序列化。由于 Cucumbers 数据 table 可以表示为 json 个地图的列表,我们可以利用它。

对于这个解释,我假设您使用的是 Cucumber-JVM 4 和 ISO8601 日期格式。如果您使用其他日期格式,还有其他资源可以帮助您。

假设您有这样的步骤:

    Given an object with dates
      | localDate  | instant                  |
      | 2019-09-05 | 2015-06-02T21:34:33.616Z |

首先定义一个接受你的对象的步骤。您的对象必须是 POJO。

import io.cucumber.java.en.Given;

import java.time.Instant;
import java.time.LocalDate;

public class DateSteps {

    @Given("an object with dates")
    public void and_object_with_dates(Dates dates) {

    }

    public static class Dates {
        public LocalDate localDate;
        public Instant instant;

    }
}

添加对 Jackson 和 JSR310 模块的依赖,以添加对 JSR310 添加的日期时间对象的支持。

        <dependency>
            <groupId>com.fasterxml.jackson.core</groupId>
            <artifactId>jackson-databind</artifactId>
            <version>2.9.8</version>
        </dependency>

        <dependency>
            <groupId>com.fasterxml.jackson.datatype</groupId>
            <artifactId>jackson-datatype-jsr310</artifactId>
            <version>2.9.8</version>
        </dependency>

配置 cucumbers 类型注册表以使用启用了 JSR310 模块的对象映射器来转换数据 table 单元格、条目和参数类型。

import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.datatype.jsr310.JSR310Module;
import io.cucumber.core.api.TypeRegistry;
import io.cucumber.core.api.TypeRegistryConfigurer;
import io.cucumber.cucumberexpressions.ParameterByTypeTransformer;
import io.cucumber.datatable.TableCellByTypeTransformer;
import io.cucumber.datatable.TableEntryByTypeTransformer;

import java.lang.reflect.Type;
import java.util.Locale;
import java.util.Map;

import static java.util.Locale.ENGLISH;

public class ParameterTypes implements TypeRegistryConfigurer {

    @Override
    public Locale locale() {
        return ENGLISH;
    }

    @Override
    public void configureTypeRegistry(TypeRegistry typeRegistry) {
        Transformer transformer = new Transformer();
        typeRegistry.setDefaultDataTableCellTransformer(transformer);
        typeRegistry.setDefaultDataTableEntryTransformer(transformer);
        typeRegistry.setDefaultParameterTransformer(transformer);
    }

    private static class Transformer implements ParameterByTypeTransformer, TableEntryByTypeTransformer, TableCellByTypeTransformer {
        ObjectMapper objectMapper = new ObjectMapper().registerModule(new JSR310Module());

        @Override
        public Object transform(String s, Type type) {
            return objectMapper.convertValue(s, objectMapper.constructType(type));
        }

        @Override
        public <T> T transform(Map<String, String> map, Class<T> aClass, TableCellByTypeTransformer tableCellByTypeTransformer) {
            return objectMapper.convertValue(map, aClass);
        }

        @Override
        public <T> T transform(String s, Class<T> aClass) {
            return objectMapper.convertValue(s, aClass);
        }
    }
}

您现在可以在任何地方使用 JSR310 日期。