package parse_min

import (
	"fmt"
	"strconv"
	"sync"
	"wartank/pkg/alias"
	"wartank/pkg/types"
)

/*
	Потокобезопасно парсит из строки значение vbyen
*/

// ПарсерМинут -- потокобезопасный парсер vbyen из строки
type ПарсерМинут struct {
	знач alias.Мин // Значение минут
	блок sync.RWMutex
}

// НовПарсерМинут -- возвращает новый *ПарсерМинут
func НовПарсерМинут() *ПарсерМинут {
	сам := &ПарсерМинут{}
	_ = types.ИПарсерМин(сам)
	return сам
}

// ПолучМилСек -- возвращает общее число миллисекунд в значении
func (сам *ПарсерМинут) ПолучМилСек() alias.МилСек {
	return alias.МилСек(сам.знач * 60 * 1_000)
}

// Получ -- возвращает хранимое значение
func (сам *ПарсерМинут) Получ() alias.Мин {
	сам.блок.RLock()
	defer сам.блок.RUnlock()
	return сам.знач
}

// String -- возвращает строковое значение минут
func (сам *ПарсерМинут) String() string {
	сам.блок.RLock()
	defer сам.блок.RUnlock()
	res := fmt.Sprintf("%02d", сам.знач)
	return res
}

// Сброс -- сбрасывает значение минут
func (сам *ПарсерМинут) Сброс() {
	сам.блок.Lock()
	defer сам.блок.Unlock()
	сам.знач = 0
}

// Уст -- устанавливает значение минут
func (сам *ПарсерМинут) Уст(стрМин alias.Время) error {
	сам.блок.Lock()
	defer сам.блок.Unlock()
	_цМин, err := strconv.Atoi(string(стрМин))
	if err != nil {
		return fmt.Errorf("ПарсерМинут.Parse(): минуты(%v) не число, err=%w", стрМин, err)
	}
	цМин := alias.Мин(_цМин)
	if err := сам.уст(цМин); err != nil {
		return fmt.Errorf("ПарсерМинут.Parse(): in internal set, err=\n\t%w", err)
	}
	return nil
}

// УстМин -- устанавливает целочисленное значение минут
func (сам *ПарсерМинут) УстМин(цМин alias.Мин) error {
	сам.блок.Lock()
	defer сам.блок.Unlock()
	if err := сам.уст(цМин); err != nil {
		return fmt.Errorf("ПарсерМинут.Set(): in internal set, err=\n\t%w", err)
	}
	return nil
}

// Внтренняя установка минут
func (сам *ПарсерМинут) уст(цМин alias.Мин) error {
	if цМин >= 60 {
		return fmt.Errorf("ПарсерМинут.set(): минуты не в диапазоне(%v) 0..60", цМин)
	}
	сам.знач = цМин
	return nil
}
