Почему не видно лога u.logger.Debug("<- quit")?
И правильно ли я организовал работу между горутинами?
Может есть возможность упростить логику?
1.
RunIssues перебирает модели и запускает в горутине
workerStartPayment
2.
workerStartPayment или отправляет в
updateIssue или в
workerCheckStatus
func (u *issueUC) workerCheckStatus(pi string, ch chan<- updateIssue, cfg *config.Config) {
tiker := time.NewTicker(60 * time.Second)
// канал отмены
quit := make(chan struct{})
count := 0
for {
select {
case <-tiker.C:
// если количество попыток равно 5, останавливаем выполнение опроса статуса
if count == 10 {
quit <- struct{}{}
}
count++
// ------------------------
status := payment.NewGetState(pi, cfg)
status.Sign()
statusResponse := status.Send()
switch statusResponse.Status {
case payment.StatusCompleted:
u.logger.Debug("StatusCompleted stop work")
ch <- updateIssue{
Status: models.IssueStatusSuccess,
Success: true,
PaymentID: statusResponse.PaymentID,
OrderID: statusResponse.OrderID,
}
quit <- struct{}{}
case payment.StatusRejected:
u.logger.Debug("StatusRejected stop work")
ch <- updateIssue{
Status: models.IssueStatusError,
Success: false,
PaymentID: statusResponse.PaymentID,
OrderID: statusResponse.OrderID,
}
quit <- struct{}{}
default:
u.logger.Debug("default repeat work", statusResponse.OrderID, statusResponse.Status)
}
case <-quit:
u.logger.Debug("<- quit")
}
}
}
func (u *issueUC) workerStartPayment(iss *models.Issue, ch chan<- updateIssue) {
// инициализируем платежную сессию -------------------------
init := payment.NewInit(
iss.Guid,
iss.PhoneNumber,
iss.IdExternal,
iss.Amount,
iss.Details,
u.cfg,
)
init.Sign()
initResponse := init.Send()
// инициализируем платежную сессию -------------------------
// если не получилось инициализировать сессию бросаем результат в канал, чтобы обновить статус issue
if initResponse.Status != payment.StatusChecked {
ch <- updateIssue{
Status: models.IssueStatusError,
Success: false,
PaymentID: initResponse.PaymentID,
OrderID: initResponse.OrderID,
}
return
}
// если сессия успешно инициализирована
// выполняем пополнение счета по номеру телефона
payment := payment.NewPaymentPayload(initResponse.PaymentID, u.cfg)
payment.Sign()
paymentResponse := payment.Send()
// если не удалось выполнить пополнение бросаем результат в канал, чтобы обновить статус issue
if paymentResponse.Status != payment.StatusCompleting {
ch <- updateIssue{
Status: models.IssueStatusError,
Success: false,
PaymentID: paymentResponse.PaymentID,
OrderID: paymentResponse.OrderID,
}
return
}
// начинаем опрашивать статус пополнения
go u.workerCheckStatus(paymentResponse.PaymentID, ch, u.cfg)
}
func (u *issueUC) updateIssue(ch <-chan updateIssue) {
for iss := range ch {
err := u.repository.UpdateIssue(iss.OrderID, iss.Status, iss.Success)
if err != nil {
u.logger.Error("updateIssue UC, repo error")
return
}
}
}
func (u *issueUC) RunIssues(issues []*models.Issue) error {
updateIssueStatus := make(chan updateIssue, 1)
for _, iss := range issues {
go u.workerStartPayment(iss, updateIssueStatus)
}
// слушаю канал в горутине
go u.updateIssue(updateIssueStatus)
return nil
}