LocationService { public synchronized void removeLocation(long id) { Optional<Location> optionalLocation = repository.find(id); if (!optionalLocation.isPresent()) { eventPublisher.publishEvent( new ErrorEvent(this, "Location [" + id + "] cannot be removed because it doesn't exist.")); return; } Location removedLocation = optionalLocation.get(); List<Location> locations = repository.locations(); if (locations.size() > 1) { Location depot = locations.stream() .min(comparingLong(Location::id)) .orElseThrow(() -> new IllegalStateException( "Impossible. Locations have size (" + locations.size() + ") but the stream is empty.")); if (removedLocation.equals(depot)) { eventPublisher.publishEvent( new ErrorEvent(this, "You can only remove depot if there are no visits.")); return; } } optimizer.removeLocation(removedLocation); repository.removeLocation(id); distanceMatrix.removeLocation(removedLocation); } @Autowired  LocationService(
            LocationRepository repository,
            RouteOptimizer optimizer,
            DistanceMatrix distanceMatrix,
            ApplicationEventPublisher eventPublisher); synchronized boolean createLocation(Coordinates coordinates, String description); synchronized boolean addLocation(Location location); synchronized void removeLocation(long id); synchronized void removeAll();  }
@Test void removing_nonexistent_location_should_publish_error() { when(repository.find(location.id())).thenReturn(Optional.empty()); locationService.removeLocation(location.id()); verifyNoInteractions(optimizer); verify(repository, never()).removeLocation(anyLong()); verify(eventPublisher).publishEvent(any(ErrorEvent.class)); }
@Test void removing_depot_when_there_are_other_locations_should_publish_error() { Location depot = new Location(1, coordinates); Location visit = new Location(2, coordinates); when(repository.locations()).thenReturn(Arrays.asList(depot, visit)); when(repository.find(depot.id())).thenReturn(Optional.of(depot)); locationService.removeLocation(depot.id()); verifyNoInteractions(optimizer); verifyNoInteractions(distanceMatrix); verify(repository, never()).removeLocation(anyLong()); verify(eventPublisher).publishEvent(any(ErrorEvent.class)); }
@Test void removing_visit_should_be_successful() { Location depot = new Location(1, coordinates); Location visit = new Location(2, coordinates); when(repository.locations()).thenReturn(Arrays.asList(depot, visit)); when(repository.find(visit.id())).thenReturn(Optional.of(visit)); locationService.removeLocation(visit.id()); verify(optimizer).removeLocation(visit); verify(distanceMatrix).removeLocation(visit); verify(repository).removeLocation(visit.id()); verifyNoInteractions(eventPublisher); }
@Test void removing_depot_should_be_successful_when_it_is_the_last_location() { when(repository.locations()).thenReturn(Collections.singletonList(location)); when(repository.find(location.id())).thenReturn(Optional.of(location)); locationService.removeLocation(location.id()); verify(repository).removeLocation(location.id()); verify(optimizer).removeLocation(location); verifyNoInteractions(eventPublisher); }