如何在单个构建器 class 中使用多个构建器模式?

How to have multiple builder pattern in a single builder class?

我有两种来自上游的负载:PayloadAPayloadB

PayloadA 包含很多字段:

createTimestamp
sentTimestamp
schemaId
eventId
producerId
guid
deviceId
langId
sessionId

PayloadB 包含许多字段:

createTimestamp
sentTimestamp
schemaId
eventId
producerId
eventType
payloadVersion
creationDate
expirationSeconds
payload

因此前 5 个字段在它们之间是通用的。而且一般他们会有更多的字段。

我想为此创建一个线程安全的构建器模式。那么我应该有一个 Payload 构建器模式 class ,其中包含来自两个有效负载的所有字段吗?或者我应该在另一个 Payload 构建器 class 和 PayloadA 和 [=14= 的公共字段中包含 PayloadAPayloadB 构建器模式 class ] 将成为 Payload class?

的一部分

针对此类问题制作构建器模式的最佳方法是什么。假设 PayloadA 构建器模式 deviceId 是必填字段。对于 PayloadB 构建器模式 eventType 是必填字段。

我建议在这里使用 static nested builder (item 2) 模式。

您可以执行以下操作

  1. 创建具有共同属性的abstractclassPayload
  2. 创建 PayloadAPayloadB,它们扩展 Payload 并为每个静态嵌套 Builder
  3. 让线程安全由 using/constructing 这些对象的方法处理(不需要 Builder 是线程安全的)。

Payload

public abstract class Payload {

    private String createTimestamp;
    private String sentTimestamp;
    private String schemaId;
    private String eventId;
    private String producerId;

    //getters, setters, equals, hashcode, toString, compareTo, etc.
}

PayloadA (PayloadB would be similar)

class PayloadA extends Payload {
    private String guid;
    private String deviceId;
    private String langId;
    private String sessionId;

    private PayloadA() {
        //avoid direct instantiation
    }

    public static class Builder {

        private String guid;
        private String deviceId;
        private String langId;
        private String sessionId;

        public Builder setLangId(String langId) {
            this.langId = langId;
            return this;
        }

        public Builder(String deviceId) {
            //validations
            this.deviceId = deviceId;
        }

        public PayloadA build() {
            //validations
            return new PayloadA();
        }

        //other setters returning this Builder
    }
}

Usage (construct the appropriate Payload from the upstream data

public Payload constructPayload(final Data data) {

    //implement any thread safety mechanism as requirdhere. 
    // synchronized is just for explanatory purposes
    synchronized (data) {
        if (data.getType().equals("PayloadA")) {
            return new PayloadA.Builder(data.getDeviceId())
                    //.setGuid("someGuid")
                    //other setters
                    .build();
        } else {
            return new PayloadB.Builder(data.getEventType())
                    //.setCreationDate("someCreationDate")
                    // other setters
                    .build();
        }
    }
}

希望对您有所帮助。