class ImmutableTarget implements Target {

    public static Target fromJson(final JsonObject jsonObject) {

        final Set<FilteredTopic> readTopics = jsonObject.getValue(JsonFields.TOPICS)
                .map(array -> array.stream()
                        .map(JsonValue::asString)
                        .map(ConnectivityModelFactory::newFilteredTopic)
                        .collect(Collectors.toSet()))
                .orElse(Collections.emptySet());

        final JsonArray authContext = jsonObject.getValue(JsonFields.AUTHORIZATION_CONTEXT)
                .orElseGet(() -> JsonArray.newBuilder().build());
        final List<AuthorizationSubject> authorizationSubjects = authContext.stream()
                .filter(JsonValue::isString)
                .map(JsonValue::asString)
                .map(AuthorizationSubject::newInstance)
                .collect(Collectors.toList());
        final AuthorizationContext readAuthorizationContext =
                AuthorizationModelFactory.newAuthContext(DittoAuthorizationContextType.PRE_AUTHENTICATED_CONNECTION,
                        authorizationSubjects);

        final AcknowledgementLabel readIssuedAcknowledgementLabel =
                jsonObject.getValue(Target.JsonFields.ISSUED_ACKNOWLEDGEMENT_LABEL)
                        .map(AcknowledgementLabel::of)
                        .orElse(null);

        final HeaderMapping readHeaderMapping =
                jsonObject.getValue(JsonFields.HEADER_MAPPING)
                        .map(ImmutableHeaderMapping::fromJson)
                        .orElse(null);

        final PayloadMapping readMapping =
                jsonObject.getValue(JsonFields.PAYLOAD_MAPPING)
                        .map(ImmutablePayloadMapping::fromJson)
                        .orElse(ConnectivityModelFactory.emptyPayloadMapping());

        return new Builder()
                .address(jsonObject.getValueOrThrow(JsonFields.ADDRESS))
                .topics(readTopics)
                .qos(jsonObject.getValue(JsonFields.QOS).orElse(null))
                .authorizationContext(readAuthorizationContext)
                .issuedAcknowledgementLabel(readIssuedAcknowledgementLabel)
                .headerMapping(readHeaderMapping)
                .payloadMapping(readMapping)
                .build();

    }

    private  ImmutableTarget(final ImmutableTarget.Builder builder);

}