class RerouteCancelShard<T> extends RerouteOption {

    private final T shardId;
    private final T nodeIdOrName;
    private final GenericProperties<T> properties;

    public RerouteCancelShard(T shardId, T nodeIdOrName, GenericProperties<T> properties) {
        this.shardId = shardId;
        this.nodeIdOrName = nodeIdOrName;
        this.properties = properties;
    }

    public T nodeIdOrName() {
        return nodeIdOrName;
    }

    public T shardId() {
        return shardId;
    }

    public GenericProperties<T> properties() {
        return properties;
    }

    public <U> RerouteCancelShard<U> map(Function<? super T, ? extends U> mapper) {
        return new RerouteCancelShard<>(
            mapper.apply(shardId),
            mapper.apply(nodeIdOrName),
            properties.map(mapper));
    }

    @Override
    public boolean equals(Object o) {<FILL_FUNCTION_BODY>}

    @Override
    public int hashCode() {
        return Objects.hash(nodeIdOrName, shardId, properties);
    }

    @Override
    public String toString() {
        return "RerouteCancelShard{" +
               "nodeIdOrName=" + nodeIdOrName +
               ", shardId=" + shardId +
               ", properties=" + properties +
               '}';
    }

    @Override
    public <R, C> R accept(AstVisitor<R, C> visitor, C context) {
        return visitor.visitRerouteCancelShard(this, context);
    }
}

        if (this == o) {
            return true;
        }
        if (o == null || getClass() != o.getClass()) {
            return false;
        }
        RerouteCancelShard<?> that = (RerouteCancelShard<?>) o;
        return Objects.equals(nodeIdOrName, that.nodeIdOrName) &&
               Objects.equals(shardId, that.shardId) &&
               Objects.equals(properties, that.properties);
    
<methods>public non-sealed void <init>() <variables>