@@ -113,18 +113,44 @@ func run(conf *config) func(c *cli.Context) error {
113113 if err != nil {
114114 return errors .Wrap (err , "failed to fetch field names" )
115115 }
116+ } else if conf .iterate {
117+ // Iterate over the time range in 1h (3600s) blocks, making sure to
118+ // stay within the request rate limit (1 request/5 seconds)
119+ hourStart := conf .startTime
120+ hourEnd := hourStart + 3600
121+ var previousRequest time.Time
122+ var requestGap time.Duration
123+ for hourStart < conf .endTime {
124+ if hourEnd > conf .endTime {
125+ hourEnd = conf .endTime
126+ }
127+ requestGap = time .Since (previousRequest )
128+ if requestGap .Seconds () < 5 {
129+ time .Sleep (requestGap )
130+ }
131+ previousRequest = time .Now ()
132+ meta , err = client .GetFromTimestamp (
133+ conf .zoneID , hourStart , hourEnd , conf .count )
134+ if err != nil {
135+ return errors .Wrap (err , "failed to fetch via timestamp" )
136+ }
137+ log .Printf ("HTTP status %d | %dms | %s" ,
138+ meta .StatusCode , meta .Duration , meta .URL )
139+ log .Printf ("Retrieved %d logs" , meta .Count )
140+ hourStart = hourEnd
141+ hourEnd += 3600
142+ }
116143 } else {
117144 meta , err = client .GetFromTimestamp (
118145 conf .zoneID , conf .startTime , conf .endTime , conf .count )
119146 if err != nil {
120147 return errors .Wrap (err , "failed to fetch via timestamp" )
121148 }
149+ log .Printf ("HTTP status %d | %dms | %s" ,
150+ meta .StatusCode , meta .Duration , meta .URL )
151+ log .Printf ("Retrieved %d logs" , meta .Count )
122152 }
123153
124- log .Printf ("HTTP status %d | %dms | %s" ,
125- meta .StatusCode , meta .Duration , meta .URL )
126- log .Printf ("Retrieved %d logs" , meta .Count )
127-
128154 return nil
129155 }
130156}
@@ -143,6 +169,7 @@ func parseFlags(conf *config, c *cli.Context) error {
143169 conf .listFields = c .Bool ("list-fields" )
144170 conf .googleStorageBucket = c .String ("google-storage-bucket" )
145171 conf .googleProjectID = c .String ("google-project-id" )
172+ conf .iterate = c .Bool ("iterate" )
146173
147174 return conf .Validate ()
148175}
@@ -161,6 +188,7 @@ type config struct {
161188 listFields bool
162189 googleStorageBucket string
163190 googleProjectID string
191+ iterate bool
164192}
165193
166194func (conf * config ) Validate () error {
@@ -181,6 +209,10 @@ func (conf *config) Validate() error {
181209 return errors .New ("Both google-storage-bucket and google-project-id must be provided to upload to Google Storage" )
182210 }
183211
212+ if conf .endTime > (conf .startTime + 3600 ) && conf .iterate == false {
213+ return errors .New ("Time range too long; ranges longer than 1h0m0s require the --iterate option" )
214+ }
215+
184216 return nil
185217}
186218
@@ -246,4 +278,8 @@ var flags = []cli.Flag{
246278 Name : "google-project-id" ,
247279 Usage : "Project ID of the Google Cloud Storage Bucket to upload logs to" ,
248280 },
281+ cli.BoolFlag {
282+ Name : "iterate" ,
283+ Usage : "Iterate over time ranges longer than normally allowed by the Logpull Rest API" ,
284+ },
249285}
0 commit comments