|
@@ -1,181 +1,66 @@
|
|
|
package TestCode
|
|
|
|
|
|
import (
|
|
|
- "github.com/allanpk716/ChineseSubFinder/internal/pkg/random_useragent"
|
|
|
- "github.com/allanpk716/ChineseSubFinder/internal/pkg/rod_helper"
|
|
|
- "github.com/go-rod/rod/lib/proto"
|
|
|
- "github.com/panjf2000/ants/v2"
|
|
|
+ "fmt"
|
|
|
"golang.org/x/net/context"
|
|
|
+ "runtime"
|
|
|
"sync"
|
|
|
"time"
|
|
|
)
|
|
|
|
|
|
-func DownloadTest() error {
|
|
|
+func hardWork(job interface{}) error {
|
|
|
+ index := job.(int)
|
|
|
+ println("Index:", index, "Start")
|
|
|
+ time.Sleep(time.Second * 10)
|
|
|
+ println("Index:", index, "End")
|
|
|
+ return nil
|
|
|
+}
|
|
|
+
|
|
|
+func requestWork(ctx context.Context, job interface{}) error {
|
|
|
+ ctx, cancel := context.WithTimeout(ctx, time.Second*2)
|
|
|
+ defer cancel()
|
|
|
|
|
|
- testFunc := func(i interface{}) error {
|
|
|
- inData := i.(InputData)
|
|
|
+ done := make(chan error, 1)
|
|
|
+ panicChan := make(chan interface{}, 1)
|
|
|
+ go func() {
|
|
|
defer func() {
|
|
|
- println(inData.Index, "testFunc done.")
|
|
|
+ if p := recover(); p != nil {
|
|
|
+ panicChan <- p
|
|
|
+ }
|
|
|
}()
|
|
|
- println(inData.Index, "start...")
|
|
|
-
|
|
|
- err2 := oneStep(inData)
|
|
|
- if err2 != nil {
|
|
|
- return err2
|
|
|
- }
|
|
|
|
|
|
- return nil
|
|
|
+ done <- hardWork(job)
|
|
|
+ }()
|
|
|
|
|
|
- //return goStep(inData)
|
|
|
+ select {
|
|
|
+ case err := <-done:
|
|
|
+ return err
|
|
|
+ case p := <-panicChan:
|
|
|
+ panic(p)
|
|
|
+ case <-ctx.Done():
|
|
|
+ return ctx.Err()
|
|
|
}
|
|
|
+}
|
|
|
|
|
|
- antPool, err := ants.NewPoolWithFunc(2, func(inData interface{}) {
|
|
|
- data := inData.(InputData)
|
|
|
- defer data.Wg.Done()
|
|
|
- ctx, cancel := context.WithTimeout(context.Background(), 3*time.Second)
|
|
|
- defer cancel()
|
|
|
- data.Ctx = ctx
|
|
|
- done := make(chan error, 1)
|
|
|
- panicChan := make(chan interface{}, 1)
|
|
|
- go func() {
|
|
|
+func Process() {
|
|
|
+ const total = 10
|
|
|
+ var wg sync.WaitGroup
|
|
|
+ wg.Add(total)
|
|
|
+ now := time.Now()
|
|
|
+ for i := 0; i < total; i++ {
|
|
|
+ go func(index int) {
|
|
|
defer func() {
|
|
|
if p := recover(); p != nil {
|
|
|
- panicChan <- p
|
|
|
+ fmt.Println("oops, panic")
|
|
|
}
|
|
|
}()
|
|
|
|
|
|
- done <- testFunc(data)
|
|
|
- }()
|
|
|
-
|
|
|
- select {
|
|
|
- case err := <-done:
|
|
|
- if err != nil {
|
|
|
- println("done with Error", err.Error())
|
|
|
- }
|
|
|
- return
|
|
|
- case p := <-panicChan:
|
|
|
- println("got panic", p)
|
|
|
- case <-ctx.Done():
|
|
|
- println("got time out", ctx.Err())
|
|
|
- return
|
|
|
- }
|
|
|
- })
|
|
|
- if err != nil {
|
|
|
- return err
|
|
|
- }
|
|
|
- defer antPool.Release()
|
|
|
- wg := sync.WaitGroup{}
|
|
|
-
|
|
|
- for i := 0; i < 10; i++ {
|
|
|
- wg.Add(1)
|
|
|
- err = antPool.Invoke(InputData{Index: i, Wg: &wg})
|
|
|
- if err != nil {
|
|
|
- println("antPool.Invoke", err)
|
|
|
- }
|
|
|
+ defer wg.Done()
|
|
|
+ requestWork(context.Background(), index)
|
|
|
+ }(i)
|
|
|
}
|
|
|
wg.Wait()
|
|
|
-
|
|
|
- println("All Done.")
|
|
|
-
|
|
|
- return nil
|
|
|
-}
|
|
|
-
|
|
|
-func goStep(inData InputData) error {
|
|
|
- outDataChan := make(chan int)
|
|
|
- for i := 0; i < 2; i++ {
|
|
|
- go func(cxt context.Context, in int) {
|
|
|
-
|
|
|
- var outData int
|
|
|
- outData = -1
|
|
|
- defer func() {
|
|
|
- println(inData.Index, in, "go func done")
|
|
|
- outDataChan <- outData
|
|
|
- }()
|
|
|
-
|
|
|
- browser, err := rod_helper.NewBrowser("", true)
|
|
|
- if err != nil {
|
|
|
- println(inData.Index, in, "rod_helper.NewBrowser", err)
|
|
|
- return
|
|
|
- }
|
|
|
- defer func() {
|
|
|
- _ = browser.Close()
|
|
|
- println(inData.Index, in, "browser closed")
|
|
|
- }()
|
|
|
- ontTime := false
|
|
|
-
|
|
|
- for {
|
|
|
- select {
|
|
|
- case <-cxt.Done():
|
|
|
- return
|
|
|
- default:
|
|
|
- if ontTime == true {
|
|
|
- return
|
|
|
- }
|
|
|
- ontTime = true
|
|
|
-
|
|
|
- page, err := rod_helper.NewPageNavigate(browser, "https://www.baidu.com", 5*time.Second, 5)
|
|
|
- if err != nil {
|
|
|
- println("NewPageNavigate time out", err)
|
|
|
- return
|
|
|
- }
|
|
|
- page.MustSetUserAgent(&proto.NetworkSetUserAgentOverride{
|
|
|
- UserAgent: random_useragent.RandomUserAgent(true),
|
|
|
- })
|
|
|
- err = page.WaitLoad()
|
|
|
- time.Sleep(10 * time.Second)
|
|
|
-
|
|
|
- outData = in
|
|
|
- }
|
|
|
- }
|
|
|
-
|
|
|
- }(inData.Ctx, i)
|
|
|
- }
|
|
|
-
|
|
|
- countResult := 0
|
|
|
- for {
|
|
|
- select {
|
|
|
- case <-inData.Ctx.Done():
|
|
|
- // 超时退出
|
|
|
- return nil
|
|
|
- case v, ok := <-outDataChan:
|
|
|
- if ok == true {
|
|
|
- println(inData.Index, "outData ok", v)
|
|
|
- } else {
|
|
|
- println(inData.Index, "outData not ok", v)
|
|
|
- }
|
|
|
- countResult++
|
|
|
- // 跳出,收到够反馈了
|
|
|
- if countResult == 2 {
|
|
|
- return nil
|
|
|
- }
|
|
|
- }
|
|
|
- }
|
|
|
-}
|
|
|
-
|
|
|
-func oneStep(inData InputData) error {
|
|
|
- browser, err := rod_helper.NewBrowser("", true)
|
|
|
- if err != nil {
|
|
|
- println(inData.Index, "rod_helper.NewBrowser", err)
|
|
|
- return err
|
|
|
- }
|
|
|
- defer func() {
|
|
|
- _ = browser.Close()
|
|
|
- println(inData.Index, "browser closed")
|
|
|
- }()
|
|
|
- page, err := rod_helper.NewPageNavigate(browser, "https://www.baidu.com", 10*time.Second, 5)
|
|
|
- if err != nil {
|
|
|
- return err
|
|
|
- }
|
|
|
- page.MustSetUserAgent(&proto.NetworkSetUserAgentOverride{
|
|
|
- UserAgent: random_useragent.RandomUserAgent(true),
|
|
|
- })
|
|
|
- err = page.WaitLoad()
|
|
|
- time.Sleep(10 * time.Second)
|
|
|
- return nil
|
|
|
-}
|
|
|
-
|
|
|
-type InputData struct {
|
|
|
- Ctx context.Context
|
|
|
- Index int
|
|
|
- Wg *sync.WaitGroup
|
|
|
+ fmt.Println("elapsed:", time.Since(now))
|
|
|
+ time.Sleep(time.Second * 20)
|
|
|
+ fmt.Println("number of goroutines:", runtime.NumGoroutine())
|
|
|
}
|