package service

import (
	"errors"
	"sws_xcx/models"

	"github.com/jinzhu/gorm"
)

type DeviceService struct {
	rdb *gorm.DB
	wdb *gorm.DB
}

func NewDeviceService() *DeviceService {
	return &DeviceService{
		rdb: ReadDB(),
		wdb: WriteDB(),
	}
}

func (s *DeviceService) GetDeviceInfo(id int) (models.Device, error) {
	var device models.Device
	err := s.rdb.Model(&device).First(&device, id).Error
	if err == gorm.ErrRecordNotFound {
		err = nil
	}
	return device, err
}

// func (s *DeviceService) GetDeviceBind(deviceId uint64, userId uint64) (models.DeviceRelate, error) {
// 	var device_relate models.DeviceRelate
// 	db := s.rdb.Model(&device_relate)
// 	if deviceId > 0 {
// 		db = db.Where("device_id = ?", deviceId)
// 	}
// 	if userId > 0 {
// 		db = db.Where("user_id = ?", userId)
// 	}
// 	err := db.First(&device_relate).Error
// 	if err == gorm.ErrRecordNotFound {
// 		err = nil
// 	}
// 	return device_relate, err
// }

func (s *DeviceService) GetDeviceByNo(serialno string) (models.Device, error) {
	var device models.Device
	err := s.rdb.Model(&device).Where("serialno = ?", serialno).First(&device).Error
	if err == gorm.ErrRecordNotFound {
		err = nil
	}
	return device, err
}

func (s *DeviceService) GetMyDevices(userId uint64) ([]*models.Device, error) {
	var devices []*models.Device
	sql := "select d.* from device as d inner join device_relate as dr on d.id = dr.device_id where dr.user_id = ? and dr.delete_flag = 0"
	err := s.rdb.Raw(sql, userId).Scan(&devices).Error
	if err != nil {
		return nil, err
	}
	return devices, nil
}

func (s *DeviceService) BindDevice(userId uint64, qrcode string) error {
	var device models.Device
	err := s.rdb.Model(&device).Where("qr_code = ?  and delete_flag =0", qrcode).First(&device).Error
	if err != nil {
		if err == gorm.ErrRecordNotFound {
			return errors.New("设备不存在")
		}
		return err
	}
	dr := &models.DeviceRelate{}
	err = s.rdb.Model(dr).Where("device_id = ?", device.Id).First(dr).Error
	if err != nil {
		if err == gorm.ErrRecordNotFound {
			dr = &models.DeviceRelate{
				UserId:   userId,
				DeviceId: device.Id,
				Name:     device.DeviceName,
			}

			return s.wdb.Model(dr).Create(dr).Error
		}
		return err
	}

	if dr.UserId != userId {
		if dr.DeleteFlag == 0 {
			return errors.New("该设备已绑定其他用户")
		} else { //其他用户解绑了设备
			return s.wdb.Model(dr).Updates(map[string]interface{}{"delete_flag": 0, "user_id": userId}).Error
		}
	} else if dr.DeleteFlag == 1 { //直接解绑了该设备 重新绑定

		return s.wdb.Model(dr).Update("delete_flag", 0).Error

	} else {
		return errors.New("设备已绑定")
	}

}

func (s *DeviceService) BindDeviceById(userId, deviceId uint64) error {
	var device models.Device
	err := s.rdb.Model(&device).Where("id= ?  and delete_flag =0", deviceId).First(&device).Error
	if err != nil {
		if err == gorm.ErrRecordNotFound {
			return errors.New("设备不存在")
		}
		return err
	}
	dr := &models.DeviceRelate{}
	err = s.rdb.Model(dr).Where("device_id = ?", device.Id).First(dr).Error
	if err != nil {
		if err == gorm.ErrRecordNotFound {
			dr = &models.DeviceRelate{
				UserId:   userId,
				DeviceId: device.Id,
				Name:     device.DeviceName,
			}

			return s.wdb.Model(dr).Create(dr).Error
		}
		return err
	}

	if dr.UserId != userId {
		if dr.DeleteFlag == 0 {
			return errors.New("该设备已绑定其他用户")
		} else { //其他用户解绑了设备
			return s.wdb.Model(dr).Updates(map[string]interface{}{"delete_flag": 0, "user_id": userId}).Error
		}
	} else if dr.DeleteFlag == 1 { //直接解绑了该设备 重新绑定

		return s.wdb.Model(dr).Update("delete_flag", 0).Error

	} else {
		return errors.New("设备已绑定")
	}

}

func (s *DeviceService) UnbindDevice(userId uint64, deviceId uint64) error {
	var device models.Device
	err := s.rdb.Model(&device).Where("id = ? and delete_flag =0", deviceId).First(&device).Error
	if err != nil {
		if err == gorm.ErrRecordNotFound {
			return errors.New("设备不存在")
		}
		return err
	}

	dr := &models.DeviceRelate{}
	err = s.rdb.Model(dr).Where("device_id = ? and user_id = ?", deviceId, userId).First(dr).Error
	if err != nil {
		return err
	}
	return s.wdb.Model(dr).Where("id=?", dr.Id).Update("delete_flag", 1).Error
}

func (s *DeviceService) CreateDeviceMessageLog(log models.DeviceMessageLog) error {
	return s.wdb.Model(&log).Create(&log).Error
}

func (s *DeviceService) GetDeviceRelateByDeviceId(deviceId uint64) (*models.DeviceRelate, error) {
	dr := &models.DeviceRelate{}
	err := s.rdb.Model(dr).Where("device_id = ?", deviceId).First(dr).Error
	if err != nil && err != gorm.ErrRecordNotFound {
		return nil, err
	}
	return dr, nil
}
