class ExposedThingProperty extends ThingProperty<T> {

    public CompletableFuture<T> write(T value) {
        // call write handler (if any)
        if (state.getWriteHandler() != null) {
            log.debug("'{}' calls registered writeHandler for Property '{}'", thing.getId(), name);

            try {
                return state.getWriteHandler().apply(value).whenComplete((customValue, e) -> {
                    log.debug("'{}' write handler for Property '{}' sets custom value '{}'", thing.getId(), name, customValue);
                    if (!Objects.equals(state.getValue(), customValue)) {
                        state.setValue(customValue);

                        // inform property observers
                        state.getSubject().onNext(Optional.ofNullable(customValue));
                    }
                });
            }
            catch (Exception e) {
                return failedFuture(e);
            }
        }
        else {
            if (!Objects.equals(state.getValue(), value)) {
                log.debug("'{}' sets Property '{}' to internal value '{}'", thing.getId(), name, value);
                state.setValue(value);

                // inform property observers
                state.getSubject().onNext(Optional.ofNullable(value));
            }

            return completedFuture(null);
        }
    }

    @SuppressWarnings("squid:S107") public  ExposedThingProperty(String name,
                                ExposedThing thing,
                                PropertyState<T> state,
                                String objectType,
                                String description,
                                Map<String, String> descriptions,
                                String type,
                                boolean observable,
                                boolean readOnly,
                                boolean writeOnly,
                                Map<String, Map<String, Object>> uriVariables,
                                Map<String, Object> optionalProperties);
    public  ExposedThingProperty(String name, ThingProperty<T> property, ExposedThing thing);

}