php 편집기 Xinyi가 Go 언어에서 타임아웃을 사용하고 컨텍스트를 생성하기 위해 재시도하는 방법을 소개합니다. 코드를 작성할 때 작업 실행 시간을 제한하거나 작업이 실패하면 다시 시도해야 하는 상황에 자주 직면합니다. Go 언어는 이러한 요구 사항을 충족하는 데 도움이 될 수 있는 간단하고 강력한 메커니즘인 컨텍스트를 제공합니다. 시간 초과 및 재시도 메커니즘을 적절하게 활용함으로써 사용자 경험을 향상시키는 동시에 코드의 신뢰성과 안정성을 향상시킬 수 있습니다. 다음 글에서는 타임아웃과 재시도를 사용하여 Go 언어에서 컨텍스트를 생성하는 방법을 자세히 설명하겠습니다.
타임아웃과 여러 번의 재시도를 사용하여 이동 중에 컨텍스트를 생성하려고 합니다. 코드 샘플은 다음과 같습니다
으아악그런 다음 readretry result := readretry(port, 2, 5) // 2초 시간 초과, 5회 재시도를 호출합니다. 그러나 처음에 데이터가 준비되지 않은 경우 reader는 rcvch에 쓸 수 없습니다. 아마 꽉 찼겠죠? 왜? readwithcontext 실행이 끝난 후 채널을 닫으려고 하면 충돌이 발생합니다. 즉 닫힌 채널에 쓰는 것입니다. 충돌은 어디에 있습니까? readwithcontext가 매번 새로운 인스턴스로 시작되어 rcvch의 새 인스턴스가 생성될 것이라고 생각하며, 시간 초과로 인해 reader가 닫히면 모든 체인 기능과 해당 지역 변수(채널 포함)가 파괴됩니다. . 그런데 제가 실수를 한 것 같습니다. 그럼 어떻게 재시도하나요? 로그가 어떻게 보이는지 확인하세요.
func readretry(port io.readwritecloser, timeout, cnt int) []byte { fmt.println("in read retry") for i := 0; i < cnt; i++ { fmt.println("read attempt:", i) res := readwithcontext(timeout, port) if res != nil { return res } } return nil } func readwithcontext(timeout int, port io.readwritecloser) []byte { fmt.println("in readwithcontext") fmt.println("opening channel") rcvch := make(chan []byte) ctx, cancel := context.withtimeout(context.background(), time.duration(time.second*time.duration(timeout))) defer cancel() go reader(ctx, port, rcvch) for { select { case <-ctx.done(): fmt.println("reader: context cancelled") return nil case buf := <-rcvch: fmt.println("reader: got data") return buf } } } func reader(ctx context.context, port io.readwritecloser, rcvch chan []byte) { fmt.println("in reader") answ := make([]byte, 1024) buf := bytes.buffer{} var err error for { i := 0 i, err = port.read(answ) if err != nil && err != io.eof { log.printf("port.read: %v", err) } if i != 0 { answ = answ[:i] buf.write(answ) if buf.bytes()[len(buf.bytes())-1] == delimiter { fmt.print("received: ") printbuf(buf.bytes()) rcvch <- buf.bytes() //if there is no data in the first attempt, cannot write to the channel here!! return } } } }
재시도할 때마다 새 리더와 새 채널이 생성됩니다. readWithContext
시간이 초과되면 독자는 여전히 기다리고 있고 결국 읽을 수 있지만 이제 채널 반대편에서는 아무도 듣고 있지 않으므로 독자가 유출됩니다.
reader
고루틴과 reader
goroutine 和一个通道,使用 readWithContext
를 사용하여 읽을 수 있는 채널이 있습니다. 컨텍스트가 만료되고 모든 재시도가 소진된 경우에도 판독기를 중지해야 합니다.
위 내용은 Go에서 시간 초과 및 재시도를 사용하여 컨텍스트를 만드는 방법은 무엇입니까?의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!