package com.bls.dao;
import javax.validation.ValidationException;
import com.bls.core.place.Place;
import com.bls.core.poi.Poi;
import com.bls.core.user.User;
import com.google.common.base.Optional;
import java.util.Collection;
import java.util.Collections;
public interface PoiDao<P extends Poi> extends CommonDao<P> {
default P createWithOwner(final P entity, final User user) {
entity.setOwner(user);
return create(entity);
}
default P checkDuplicateAndCreate(final P entity, final User user) {
final Long RADIUS = 10l;
Optional<P> entityWithSameName = findNameDuplicateForOwner(user, entity.getName());
if (entityWithSameName.isPresent()) {
// Find 1 entity within {radius} meters around entity.location, owned by user
Collection<P> entitiesWithSameNameWithinRange = find(
entity.getLocation(),
RADIUS,
Collections.<String>emptyList(), // tags
Optional.of(entity.getName()),
Optional.absent(), // street
Collections.<Place.Subcategory>emptyList(), // subs
Optional.absent(), // paid
Optional.absent(), // open
Optional.of(user), // owner
Optional.of(0), // first page
1); // 1 result
if (!entitiesWithSameNameWithinRange.isEmpty()) {
throw new ValidationException(String.format("Entity name duplicate within %d meters.", RADIUS));
}
}
return createWithOwner(entity, user);
}
default P findByIdSafe(final User user, final String id) {
final Optional<P> entity = findById(id);
if (!entity.isPresent()) {
// TODO security: hide core problem
throw new ValidationException(String.format("Poi with id: %s not found - missing entity", id));
}
final User owner = entity.get().getOwner();
if (owner == null) {
// TODO security: hide core problem
throw new ValidationException(String.format("Poi with id: %s not found - missing owner for entity", id));
}
final boolean userIsPoiOwner = owner.getId().equals(user.getId());
if (!userIsPoiOwner) {
// TODO security: hide core problem
throw new ValidationException(String.format("Poi with id: %s not found - user is not an owner", id));
}
return entity.get();
}
default P updateSafe(final User user, final String id, final P entity) {
entity.setId(findByIdSafe(user, id).getId());
entity.setOwner(user);
return update(entity);
}
default Optional<P> findNameDuplicateForOwner(final User user, final String name) {
final Optional<P> entity = findOneByField("name", name);
if (!entity.isPresent()) {
return Optional.absent();
}
final User owner = entity.get().getOwner();
final boolean userIsPoiOwner = owner.getId().equals(user.getId());
if (userIsPoiOwner) {
return entity;
}
return Optional.absent();
}
}