Я довольно новичок в каналах GoLang, но он не работает так, как я ожидал.
У меня есть функция, для которой я хочу вызвать 3 отдельные программы и затем дождаться их завершения.Если я получаю сообщение об ошибке, я пытаюсь поместить его в CHAN, а затем обработать ошибку после завершения wg.Wait()
.
К сожалению, при циклическом просмотре результатов CHAN он зависает.Я предполагаю, что он все еще ждет, пока ЧАН заполнится, но не все программы будут выдавать ошибки.
Каков наилучший способ обработки циклических каналов, которые не всегда будут заполняться?Я также знаю, что мне не нужно использовать CHAN здесь, но я хотел убедиться, что я их понял.
Ниже мой код.
func createWorkoutPlanForUserPreconditionCheck(planID, userID, transactionID *string) (*sharedstructs.Plan, *sharedstructs.User, *sharedstructs.Profile, error) {
if planID == nil || userID == nil || transactionID == nil {
return nil, nil, nil, sharedstructs.InvalidData{Msg: "Cannot pass in Nil Parameters"}
}
plan := sharedstructs.Plan{}
user := sharedstructs.User{}
profile := sharedstructs.Profile{}
//myError := sharedstructs.InvalidData{}
ch := make(chan sharedstructs.InvalidData, 3)
var wg sync.WaitGroup
wg.Add(3)
//Get the Plan from the Plan ID
go func() {
defer wg.Done()
returnedPlan, readError := readPlan(*planID)
if readError != nil || returnedPlan == nil {
ch <- sharedstructs.InvalidData{Msg: "Could Not Retreive the User with ID: " + *userID}
} else {
plan = *returnedPlan
}
}()
//Get the User
go func() {
defer wg.Done()
returnedUser, getUserError := userdomain.GetUserByID(*userID, *transactionID)
if getUserError != nil || &returnedUser == nil {
ch <- sharedstructs.InvalidData{Msg: "Could Not Retreive the User with ID: " + *userID}
} else {
user = returnedUser
}
}()
//Get the Profile
go func() {
defer wg.Done()
readProfile, getProfileError := profiledomain.GetProfile(*userID, *transactionID)
if getProfileError != nil || readProfile == nil {
ch <- sharedstructs.InvalidData{Msg: "Could Not Retreive the User with ID: " + *userID}
} else {
profile = *readProfile
}
}()
wg.Wait()
////"Hangs Here" - PUT MY ERROR HANDLING LOGIC HERE
for err := range ch {
fmt.Println(err.Error())
}
return &plan, &user, &profile, nil
}