1
1
package producer
2
2
3
3
import (
4
- "math"
5
4
"sync"
6
5
"sync/atomic"
7
6
"time"
@@ -43,7 +42,7 @@ func initIoWorker(client sls.ClientInterface, retryQueue *RetryQueue, logger log
43
42
44
43
func (ioWorker * IoWorker ) sendToServer (producerBatch * ProducerBatch ) {
45
44
level .Debug (ioWorker .logger ).Log ("msg" , "ioworker send data to server" )
46
- beginMs := GetTimeMs ( time .Now (). UnixNano () )
45
+ sendBegin := time .Now ()
47
46
var err error
48
47
if producerBatch .isUseMetricStoreUrl () {
49
48
// not use compress type now
@@ -57,67 +56,59 @@ func (ioWorker *IoWorker) sendToServer(producerBatch *ProducerBatch) {
57
56
}
58
57
err = ioWorker .client .PostLogStoreLogsV2 (producerBatch .getProject (), producerBatch .getLogstore (), req )
59
58
}
59
+ sendEnd := time .Now ()
60
+
61
+ // send ok
60
62
if err == nil {
61
- level .Debug (ioWorker .logger ).Log ("msg" , "sendToServer suecssed,Execute successful callback function" )
62
- if producerBatch .attemptCount < producerBatch .maxReservedAttempts {
63
- nowMs := GetTimeMs (time .Now ().UnixNano ())
64
- attempt := createAttempt (true , "" , "" , "" , nowMs , nowMs - beginMs )
65
- producerBatch .result .attemptList = append (producerBatch .result .attemptList , attempt )
66
- }
67
- producerBatch .result .successful = true
63
+ level .Debug (ioWorker .logger ).Log ("msg" , "sendToServer success" )
64
+ defer ioWorker .producer .monitor .recordSuccess (sendBegin , sendEnd )
65
+ producerBatch .OnSuccess (sendBegin )
68
66
// After successful delivery, producer removes the batch size sent out
69
67
atomic .AddInt64 (& ioWorker .producer .producerLogGroupSize , - producerBatch .totalDataSize )
70
- if len (producerBatch .callBackList ) > 0 {
71
- for _ , callBack := range producerBatch .callBackList {
72
- callBack .Success (producerBatch .result )
73
- }
74
- }
75
- } else {
76
- if ioWorker .retryQueueShutDownFlag .Load () {
77
- if len (producerBatch .callBackList ) > 0 {
78
- for _ , callBack := range producerBatch .callBackList {
79
- ioWorker .addErrorMessageToBatchAttempt (producerBatch , err , false , beginMs )
80
- callBack .Fail (producerBatch .result )
81
- }
82
- }
83
- return
84
- }
85
- level .Info (ioWorker .logger ).Log ("msg" , "sendToServer failed" , "error" , err )
86
- if slsError , ok := err .(* sls.Error ); ok {
87
- if _ , ok := ioWorker .noRetryStatusCodeMap [int (slsError .HTTPCode )]; ok {
88
- ioWorker .addErrorMessageToBatchAttempt (producerBatch , err , false , beginMs )
89
- ioWorker .excuteFailedCallback (producerBatch )
90
- return
91
- }
92
- }
93
- if producerBatch .attemptCount < producerBatch .maxRetryTimes {
94
- ioWorker .addErrorMessageToBatchAttempt (producerBatch , err , true , beginMs )
95
- retryWaitTime := producerBatch .baseRetryBackoffMs * int64 (math .Pow (2 , float64 (producerBatch .attemptCount )- 1 ))
96
- if retryWaitTime < producerBatch .maxRetryIntervalInMs {
97
- producerBatch .nextRetryMs = GetTimeMs (time .Now ().UnixNano ()) + retryWaitTime
98
- } else {
99
- producerBatch .nextRetryMs = GetTimeMs (time .Now ().UnixNano ()) + producerBatch .maxRetryIntervalInMs
100
- }
101
- level .Debug (ioWorker .logger ).Log ("msg" , "Submit to the retry queue after meeting the retry criteria。" )
102
- ioWorker .retryQueue .sendToRetryQueue (producerBatch , ioWorker .logger )
103
- } else {
104
- ioWorker .excuteFailedCallback (producerBatch )
105
- }
68
+ return
106
69
}
70
+
71
+ slsError := parseSlsError (err )
72
+ canRetry := ioWorker .canRetry (producerBatch , slsError )
73
+ level .Error (ioWorker .logger ).Log ("msg" , "sendToServer failed" ,
74
+ "retryTimes" , producerBatch .attemptCount ,
75
+ "requestId" , slsError .RequestID ,
76
+ "errorCode" , slsError .Code ,
77
+ "errorMessage" , slsError .Message ,
78
+ "logs" , len (producerBatch .logGroup .Logs ),
79
+ "canRetry" , canRetry )
80
+ if ! canRetry {
81
+ defer ioWorker .producer .monitor .recordFailure (sendBegin , sendEnd )
82
+ producerBatch .OnFail (slsError , sendBegin )
83
+ atomic .AddInt64 (& ioWorker .producer .producerLogGroupSize , - producerBatch .totalDataSize )
84
+ return
85
+ }
86
+
87
+ // do retry
88
+ ioWorker .producer .monitor .recordRetry (sendEnd .Sub (sendBegin ))
89
+ producerBatch .addAttempt (slsError , sendBegin )
90
+ producerBatch .nextRetryMs = producerBatch .getRetryBackoffIntervalMs () + time .Now ().UnixMilli ()
91
+ level .Debug (ioWorker .logger ).Log ("msg" , "Submit to the retry queue after meeting the retry criteria。" )
92
+ ioWorker .retryQueue .sendToRetryQueue (producerBatch , ioWorker .logger )
107
93
}
108
94
109
- func (ioWorker * IoWorker ) addErrorMessageToBatchAttempt (producerBatch * ProducerBatch , err error , retryInfo bool , beginMs int64 ) {
110
- if producerBatch .attemptCount < producerBatch .maxReservedAttempts {
111
- slsError := err .(* sls.Error )
112
- if retryInfo {
113
- level .Info (ioWorker .logger ).Log ("msg" , "sendToServer failed,start retrying" , "retry times" , producerBatch .attemptCount , "requestId" , slsError .RequestID , "error code" , slsError .Code , "error message" , slsError .Message )
114
- }
115
- nowMs := GetTimeMs (time .Now ().UnixNano ())
116
- attempt := createAttempt (false , slsError .RequestID , slsError .Code , slsError .Message , nowMs , nowMs - beginMs )
117
- producerBatch .result .attemptList = append (producerBatch .result .attemptList , attempt )
95
+ func parseSlsError (err error ) * sls.Error {
96
+ if slsError , ok := err .(* sls.Error ); ok {
97
+ return slsError
98
+ }
99
+ return & sls.Error {
100
+ Message : err .Error (),
101
+ }
102
+ }
103
+
104
+ func (ioWorker * IoWorker ) canRetry (producerBatch * ProducerBatch , err * sls.Error ) bool {
105
+ if ioWorker .retryQueueShutDownFlag .Load () {
106
+ return false
118
107
}
119
- producerBatch .result .successful = false
120
- producerBatch .attemptCount += 1
108
+ if _ , ok := ioWorker .noRetryStatusCodeMap [int (err .HTTPCode )]; ok {
109
+ return false
110
+ }
111
+ return producerBatch .attemptCount < producerBatch .maxRetryTimes
121
112
}
122
113
123
114
func (ioWorker * IoWorker ) closeSendTask (ioWorkerWaitGroup * sync.WaitGroup ) {
@@ -131,13 +122,3 @@ func (ioWorker *IoWorker) startSendTask(ioWorkerWaitGroup *sync.WaitGroup) {
131
122
ioWorker .maxIoWorker <- 1
132
123
ioWorkerWaitGroup .Add (1 )
133
124
}
134
-
135
- func (ioWorker * IoWorker ) excuteFailedCallback (producerBatch * ProducerBatch ) {
136
- level .Info (ioWorker .logger ).Log ("msg" , "sendToServer failed,Execute failed callback function" )
137
- atomic .AddInt64 (& ioWorker .producer .producerLogGroupSize , - producerBatch .totalDataSize )
138
- if len (producerBatch .callBackList ) > 0 {
139
- for _ , callBack := range producerBatch .callBackList {
140
- callBack .Fail (producerBatch .result )
141
- }
142
- }
143
- }
0 commit comments