php Editor Banana is here to share an interesting trick with you - "continue reading data after pausing for one second". In programming, sometimes we need to wait for a period of time before continuing to perform subsequent operations, and this technique can help us achieve this goal. Whether it is used for delayed operations of network requests, or to avoid certain time-consuming operations from affecting the execution efficiency of the program, this technique can play an important role. Below, we will introduce in detail how to implement this function in php.
I am using curl to get data from an endpoint and transfer it to the program. The main function of the program reads data like this
reader := bufio.NewReader(os.Stdin) var buf bytes.Buffer line, err := reader.ReadString(`\n`) for { if err != nil{ buf.WriteString(line) break } buf.WriteString(line) } var data Memstats err = json.Unmarshal(buf.Bytes(), &data)
Everything is normal until here. However, my end goal is to repeatedly curl the endpoint like this for a period of time so that the program reads N JSON blobs arriving at N time intervals.
for i in {1..10}; do curl localhost:6000/debug/vars | ./myprogram; sleep 1; done
Every time you curl to the endpoint, you will arrive at the same structured data. So I have to move the data reading code into function readStdIn
which I will call repeatedly until curl stops sending data and every time my program receives json data I will Unmarshal into a struct and add it to the slice. To call readStdIn repeatedly, I used a for loop, and to read the data in readStdIn, I also used a for loop. readStdIn
The function never completes. why not?
The main function
for{ reader := bufio.NewReader(os.Stdin) h.readStdIn(reader) time.Sleep(1 * time.Second) var err error //check to see if curl sent more data, if not I break out of main function and continue on with program and hopefully an array full of Memstats newbytes, err := reader.ReadByte() if err != nil{ break } }
readStdIn function
func (rt *Graph)readStdIn(reader *bufio.Reader){ var buf bytes.Buffer line, err := reader.ReadString('\n') for { if err != nil{ if err == io.EOF{ buf.WriteString(line) break }else{ fmt.Println(err.Error()) os.Exit(1) } } } buf.WriteString(line) } var data Memstats err = json.Marshal(buf.Bytes(), &data) rt.Memstats = append(rt.Memstats, &record) }
You can also use the scanner by customizing the function or changing the bash script. But I believe both are more complex than the code below.
<code>package main import ( "encoding/json" "errors" "fmt" "io" "os" ) func main() { fmt.Println("Start") decoder := json.NewDecoder(os.Stdin) for { var u User err := decoder.Decode(&u) if errors.Is(err, io.EOF) { fmt.Println("End") break } if err != nil { fmt.Println("Can not decode into json", err) continue } fmt.Println(u) } } type User struct { UserId int `json:"userId"` Id int `json:"id"` Title string `json:"title"` } </code>
<code>function repeatedCurl() { for i in $(seq 1 3); do # sleep 1 # optional you can emit curl -s "https://jsonplaceholder.typicode.com/posts/$i" done } repeatedCurl | ./foo </code>
<code>package main import ( "bufio" "fmt" "os" ) func main() { fmt.Println("Start") scanner := bufio.NewScanner(bufio.NewReader(os.Stdin)) for scanner.Scan() { fmt.Println(scanner.Text()) } fmt.Println("End") } </code>
It works for both creating new program instances (like your example) and normal pipe usage.
<code>function repeatedDateEcho() { while sleep 1; do echo "$(date)" done } repeatedDateEcho | ./myprogram </code>
Output:
Start Thu Jan 18 22:59:31 +03 2024 Thu Jan 18 22:59:32 +03 2024 Thu Jan 18 22:59:33 +03 2024 Thu Jan 18 22:59:34 +03 2024
while sleep 1; do echo "$(date)" | ./my program; complete
Output:
Start Thu Jan 18 22:58:46 +03 2024 End Start Thu Jan 18 22:58:47 +03 2024 End
The above is the detailed content of Continue reading data after pausing for one second. For more information, please follow other related articles on the PHP Chinese website!