package address_repository

import (
	"chonho/pkg/model"
	"gorm.io/gorm"
)

type AddressRepository interface {
	Save(address *model.UserShippingAddress) error
	First(filter AddressFilter) (*model.UserShippingAddress, error)
	UpdateAddress(filter AddressFilter, attributes map[string]interface{}) error
}
type repository struct {
	db *gorm.DB
}

func NewAddressRepository(db *gorm.DB) *repository {
	return &repository{
		db: db,
	}
}

func (r *repository) Save(address *model.UserShippingAddress) error {
	return r.db.Save(address).Error
}

type AddressFilter struct {
	Id                   int64
	UserId               int64
	ApartmentId          int64
	ApartmentHouseNumber string
	IsMainAddress        *bool
}

func (r *repository) First(filter AddressFilter) (*model.UserShippingAddress, error) {
	var address model.UserShippingAddress
	builder := r.db.Model(&address)
	if filter.Id != 0 {
		builder = builder.Where("id = ? ", filter.Id)
	}
	if filter.UserId != 0 {
		builder = builder.Where("user_id = ? ", filter.UserId)
	}
	if filter.ApartmentId != 0 {
		builder = builder.Where("apartment_id = ?", filter.ApartmentId)
	}
	if filter.ApartmentHouseNumber != "" {
		builder = builder.Where("apartment_house_number = ?", filter.ApartmentHouseNumber)
	}
	if filter.IsMainAddress != nil {
		builder = builder.Where("is_main_address = ?", filter.IsMainAddress)
	}
	err := builder.First(&address).Error
	if err != nil {
		return nil, err
	}
	return &address, nil
}

func (r *repository) UpdateAddress(filter AddressFilter, attributes map[string]interface{}) error {
	var address model.UserShippingAddress
	builder := r.db.Model(&address)
	if filter.Id != 0 {
		builder = builder.Where("id = ? ", filter.Id)
	}
	if filter.UserId != 0 {
		builder = builder.Where("user_id = ? ", filter.UserId)
	}
	if filter.ApartmentId != 0 {
		builder = builder.Where("apartment_id = ?", filter.ApartmentId)
	}
	if filter.ApartmentHouseNumber != "" {
		builder = builder.Where("apartment_house_number = ?", filter.ApartmentHouseNumber)
	}
	return builder.Updates(attributes).Error
}
