package cz.muni.fi.pa165.core.device;

import cz.muni.fi.pa165.core.common.DomainFacade;
import cz.muni.fi.pa165.core.company.CompanyService;
import cz.muni.fi.pa165.core.helpers.exceptions.EntityConflictException;
import cz.muni.fi.pa165.core.helpers.exceptions.EntityDeletionException;
import cz.muni.fi.pa165.model.dto.device.DeviceCreateDto;
import cz.muni.fi.pa165.model.dto.device.DeviceDto;
import cz.muni.fi.pa165.model.dto.device.DeviceUpdateDto;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

@Component
public class DeviceFacade extends DomainFacade<Device, DeviceDto, DeviceCreateDto, DeviceUpdateDto> {

	private final DeviceService deviceService; // For the "DeviceService" specific methods

	private final CompanyService companyService;

	@Autowired
	public DeviceFacade(DeviceService deviceService, DeviceMapper deviceMapper, CompanyService companyService) {
		super(deviceService, deviceMapper);
		this.deviceService = deviceService;
		this.companyService = companyService;
	}

	@Override
	public DeviceDto create(DeviceCreateDto deviceCreateDto) {
		if (deviceService.findByName(deviceCreateDto.getName()) != null) {
			throw new EntityConflictException("Device with given name already exists");
		}
		Device device = mapper.fromCreateDto(deviceCreateDto);
		device.setCompany(companyService.findById(deviceCreateDto.getCompanyId()));
		return mapper.toDto(deviceService.create(device));
	}

	@Override
	public DeviceDto updateById(DeviceUpdateDto updateDto, String id) {
		if (deviceService.findByName(updateDto.getName()) != null) {
			throw new EntityConflictException("Device with given name already exists");
		}
		return super.updateById(updateDto, id);
	}

	@Override
	public DeviceDto deleteById(String id) throws EntityDeletionException {
		Device device = deviceService.findById(id);
		if (!device.getSmartMeterList().isEmpty()) {
			throw new EntityDeletionException("Device", new String[]{"smart meter"});
		}

		return mapper.toDto(this.deviceService.deleteById(id));
	}
}
