web_worker.go 3.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384
  1. // package web_worker -- веб-воркер бота
  2. package web_worker
  3. import (
  4. "context"
  5. "fmt"
  6. "io"
  7. "net/http"
  8. "strings"
  9. "sync"
  10. "time"
  11. "wartank/pkg/components/arena_net/web_worker/net_stat"
  12. "wartank/pkg/components/kernel/logger"
  13. "wartank/pkg/types"
  14. )
  15. // ВебВоркер -- объект сетевого исполнителя бота
  16. type ВебВоркер struct {
  17. botNet types.ИБотСеть
  18. conn *http.Client
  19. статистика *net_stat.СетьСтата
  20. лог types.ИЛоггер
  21. block sync.Mutex
  22. }
  23. // НовВебВоркер -- возвращает веб-воркера бота
  24. func НовВебВоркер(botNet types.ИБотСеть, conn *http.Client) *ВебВоркер {
  25. лог := logger.НовЛоггер("ВебВоркер")
  26. лог.Инфо("НовВебВоркер()\n")
  27. сам := &ВебВоркер{
  28. botNet: botNet,
  29. conn: conn,
  30. статистика: net_stat.НовСетьСтата(botNet),
  31. лог: лог,
  32. }
  33. _ = types.ИВебВоркер(сам)
  34. return сам
  35. }
  36. // Получ -- потокобезопасно возвращает список строк по ссылке
  37. func (сам *ВебВоркер) Получ(strLink string) ([]string, error) {
  38. сам.block.Lock()
  39. defer сам.block.Unlock()
  40. // if strLink == "https://wartank.ru/production/Mine" {
  41. сам.лог.Отладка("Получ(): link=%v\n", strLink)
  42. // }
  43. ctxCancel, fnCancel := context.WithTimeout(сам.botNet.Контекст(), time.Second*10)
  44. defer fnCancel()
  45. запрос, ош := http.NewRequestWithContext(ctxCancel, "GET", strLink, nil)
  46. if ош != nil {
  47. сам.статистика.IncErr()
  48. return nil, fmt.Errorf("ВебВоркер.Получ(): при создании запроса, err=\n\t%w", ош)
  49. }
  50. запрос.Header.Set("User-Agent", "Mozilla Firefox 106.1")
  51. ответ, ош := сам.conn.Do(запрос)
  52. if ош != nil {
  53. сам.статистика.IncErr()
  54. return nil, fmt.Errorf("ВебВоркер.Получ(): при выполнении GET-запроса, err=\n\t%w", ош)
  55. }
  56. defer ответ.Body.Close()
  57. if ответ.StatusCode != http.StatusOK {
  58. сам.статистика.IncErr()
  59. return nil, fmt.Errorf("ВебВоркер.Получ(): code=%v, status=%v", ответ.StatusCode, ответ.Status)
  60. }
  61. binData, ош := io.ReadAll(ответ.Body)
  62. if ош != nil {
  63. сам.статистика.IncErr()
  64. return nil, fmt.Errorf("ВебВоркер.Получ(): при чтении тела ответа, err=\n\t%w", ош)
  65. }
  66. if len(binData) == 0 {
  67. сам.статистика.IncErr()
  68. return nil, fmt.Errorf("ВебВоркер.Получ(): пустое тело ответа, err=\n\t%w", ош)
  69. }
  70. lenData := len(binData) + len(strLink)
  71. сам.статистика.AddByte(lenData)
  72. lstString := strings.Split(string(binData), "\n")
  73. if len(lstString) == 0 {
  74. сам.статистика.IncErr()
  75. return nil, fmt.Errorf("ВебВоркер.Получ(): lstString is empty")
  76. }
  77. return lstString, nil
  78. }