async.Run as global context, async operations run immediately

This commit is contained in:
Li Jie
2024-09-10 11:43:44 +08:00
parent 44c4488fcc
commit 12f460e376
4 changed files with 178 additions and 220 deletions

View File

@@ -40,59 +40,54 @@ func sleep(i int, d time.Duration) async.Future[int] {
}
func main() {
RunIO()
RunAllAndRace()
RunTimeout()
RunMultipleCallbacksNodelay()
RunMultipleCallbacksDelay()
RunSocket()
async.Run(func(resolve func(async.Void)) {
RunIO()
RunAllAndRace()
RunTimeout()
RunMultipleCallbacksNodelay()
RunMultipleCallbacksDelay()
RunSocket()
})
}
func RunIO() {
println("RunIO with Await")
// Hide `resolve` in Go+
async.Run(async.Async(func(resolve func(async.Void)) {
println("read file")
defer resolve(async.Void{})
content, err := async.Await(ReadFile("all.go")).Get()
println("read file")
content, err := async.Await(ReadFile("all.go")).Get()
if err != nil {
fmt.Printf("read err: %v\n", err)
return
}
fmt.Printf("read content: %s\n", content)
err = async.Await(WriteFile("2.out", content))
if err != nil {
fmt.Printf("write err: %v\n", err)
return
}
fmt.Printf("write done\n")
// Translated Await to BindIO in Go+:
println("RunIO with BindIO")
ReadFile("all.go").Then(func(v tuple.Tuple2[[]byte, error]) {
content, err := v.Get()
if err != nil {
fmt.Printf("read err: %v\n", err)
return
}
fmt.Printf("read content: %s\n", content)
err = async.Await(WriteFile("2.out", content))
if err != nil {
fmt.Printf("write err: %v\n", err)
return
}
fmt.Printf("write done\n")
}))
// Translated Await to BindIO in Go+:
println("RunIO with BindIO")
async.Run(async.Async(func(resolve func(async.Void)) {
ReadFile("all.go").Then(func(v tuple.Tuple2[[]byte, error]) {
content, err := v.Get()
WriteFile("2.out", content).Then(func(v error) {
err = v
if err != nil {
fmt.Printf("read err: %v\n", err)
resolve(async.Void{})
fmt.Printf("write err: %v\n", err)
return
}
fmt.Printf("read content: %s\n", content)
WriteFile("2.out", content).Then(func(v error) {
err = v
if err != nil {
fmt.Printf("write err: %v\n", err)
resolve(async.Void{})
return
}
println("write done")
resolve(async.Void{})
})
println("write done")
})
}))
})
}
func RunAllAndRace() {
@@ -102,160 +97,133 @@ func RunAllAndRace() {
println("Run All with Await")
async.Run(async.Async(func(resolve func(async.Void)) {
async.All(sleep(1, ms200), sleep(2, ms100), sleep(3, ms300)).Then(func(v []int) {
fmt.Printf("All: %v\n", v)
resolve(async.Void{})
})
}))
async.All(sleep(1, ms200), sleep(2, ms100), sleep(3, ms300)).Then(func(v []int) {
fmt.Printf("All: %v\n", v)
})
println("Run Race with Await")
async.Run(async.Async(func(resolve func(async.Void)) {
first := async.Race(sleep(1, ms200), sleep(2, ms100), sleep(3, ms300))
v := async.Await(first)
fmt.Printf("Race: %v\n", v)
resolve(async.Void{})
}))
first := async.Race(sleep(1, ms200), sleep(2, ms100), sleep(3, ms300))
v := async.Await(first)
fmt.Printf("Race: %v\n", v)
// Translated to in Go+:
println("Run All with BindIO")
async.Run(async.Async(func(resolve func(async.Void)) {
async.All(sleep(1, ms200), sleep(2, ms100), sleep(3, ms300)).Then(func(v []int) {
fmt.Printf("All: %v\n", v)
resolve(async.Void{})
})
}))
async.All(sleep(1, ms200), sleep(2, ms100), sleep(3, ms300)).Then(func(v []int) {
fmt.Printf("All: %v\n", v)
})
println("Run Race with BindIO")
async.Run(async.Async(func(resolve func(async.Void)) {
async.Race(sleep(1, ms200), sleep(2, ms100), sleep(3, ms300)).Then(func(v int) {
fmt.Printf("Race: %v\n", v)
resolve(async.Void{})
})
}))
async.Race(sleep(1, ms200), sleep(2, ms100), sleep(3, ms300)).Then(func(v int) {
fmt.Printf("Race: %v\n", v)
})
}
func RunTimeout() {
println("Run Timeout with Await")
async.Run(async.Async(func(resolve func(async.Void)) {
fmt.Printf("Start 100 ms timeout\n")
async.Await(timeout.Timeout(100 * time.Millisecond))
fmt.Printf("timeout\n")
resolve(async.Void{})
}))
fmt.Printf("Start 100 ms timeout\n")
async.Await(timeout.Timeout(100 * time.Millisecond))
fmt.Printf("timeout\n")
// Translated to in Go+:
println("Run Timeout with BindIO")
async.Run(async.Async(func(resolve func(async.Void)) {
fmt.Printf("Start 100 ms timeout\n")
timeout.Timeout(100 * time.Millisecond).Then(func(async.Void) {
fmt.Printf("timeout\n")
resolve(async.Void{})
})
}))
fmt.Printf("Start 100 ms timeout\n")
timeout.Timeout(100 * time.Millisecond).Then(func(async.Void) {
fmt.Printf("timeout\n")
})
}
func RunMultipleCallbacksNodelay() {
println("Run Multiple Callbacks")
runCnt := atomic.Int32{}
async.Run(async.Async(func(resolve func(async.Void)) {
nodelay := async.Async(func(resolve func(async.Void)) {
println("nodelay")
runCnt.Add(1)
resolve(async.Void{})
})
cbCnt := atomic.Int32{}
cb := func() {
if cbCnt.Add(1) == 2 {
resolve(async.Void{})
nodelay := async.Async(func(resolve func(async.Void)) {
println("nodelay")
runCnt.Add(1)
})
cbCnt := atomic.Int32{}
cb := func() {
if cbCnt.Add(1) == 2 {
if runCnt.Load() != 1 {
panic("runCnt != 1, got: " + fmt.Sprint(runCnt.Load()))
} else {
println("runCnt == 1")
}
}
nodelay.Then(func(async.Void) {
println("nodelay done")
cb()
})
nodelay.Then(func(async.Void) {
println("nodelay done again")
cb()
})
}))
if runCnt.Load() != 1 {
panic("runCnt != 1")
}
nodelay.Then(func(async.Void) {
println("nodelay done")
cb()
})
nodelay.Then(func(async.Void) {
println("nodelay done again")
cb()
})
}
func RunMultipleCallbacksDelay() {
println("Run Multiple Callbacks")
runCnt := atomic.Int32{}
async.Run(async.Async(func(resolve func(async.Void)) {
delay := async.Async(func(resolve func(async.Void)) {
timeout.Timeout(100 * time.Millisecond).Then(func(async.Void) {
println("delay")
runCnt.Add(1)
resolve(async.Void{})
})
})
cbCnt := atomic.Int32{}
cb := func() {
if cbCnt.Add(1) == 2 {
resolve(async.Void{})
delay := async.Async(func(resolve func(async.Void)) {
timeout.Timeout(100 * time.Millisecond).Then(func(async.Void) {
println("delay")
runCnt.Add(1)
})
})
cbCnt := atomic.Int32{}
cb := func() {
if cbCnt.Add(1) == 2 {
if runCnt.Load() != 1 {
panic("runCnt != 1, got: " + fmt.Sprint(runCnt.Load()))
} else {
println("runCnt == 1")
}
}
delay.Then(func(async.Void) {
println("delay done")
cb()
})
delay.Then(func(async.Void) {
println("delay done again")
cb()
})
}))
if runCnt.Load() != 1 {
panic("runCnt != 1")
}
delay.Then(func(async.Void) {
println("delay done")
cb()
})
delay.Then(func(async.Void) {
println("delay done again")
cb()
})
}
func RunSocket() {
println("Run Socket")
async.Run(async.Async(func(resolve func(async.Void)) {
println("RunServer")
println("RunServer")
RunServer().Then(func(async.Void) {
println("RunServer done")
resolve(async.Void{})
RunServer().Then(func(async.Void) {
println("RunServer done")
})
println("RunClient")
timeout.Timeout(100 * time.Millisecond).Then(func(async.Void) {
RunClient("Bob").Then(func(async.Void) {
println("RunClient done")
})
println("RunClient")
timeout.Timeout(100 * time.Millisecond).Then(func(async.Void) {
RunClient("Bob").Then(func(async.Void) {
println("RunClient done")
resolve(async.Void{})
})
RunClient("Uncle").Then(func(async.Void) {
println("RunClient done")
resolve(async.Void{})
})
RunClient("Uncle").Then(func(async.Void) {
println("RunClient done")
})
}))
})
}
func RunClient(name string) async.Future[async.Void] {