Highly-opinionated (ex-bullshit-free) MTPROTO proxy for Telegram. If you use v1.0 or upgrade broke you proxy, please read the chapter Version 2
Вы не можете выбрать более 25 тем Темы должны начинаться с буквы или цифры, могут содержать дефисы(-) и должны содержать не более 35 символов.

proxy_conn.go 1.5KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677
  1. package hub
  2. import (
  3. "sync"
  4. "time"
  5. "mtg/conntypes"
  6. "mtg/mtproto/rpc"
  7. "mtg/protocol"
  8. )
  9. const (
  10. proxyConnWriteTimeout = 2 * time.Minute
  11. proxyConnReadTimeout = 2 * time.Minute
  12. )
  13. type ProxyConn struct {
  14. closeOnce sync.Once
  15. req *protocol.TelegramRequest
  16. channelResponse chan *rpc.ProxyResponse
  17. channelClosed chan<- conntypes.ConnID
  18. channelWrite chan<- conntypes.Packet
  19. channelDone chan struct{}
  20. }
  21. func (p *ProxyConn) Read() (*rpc.ProxyResponse, error) {
  22. timer := time.NewTimer(proxyConnReadTimeout)
  23. defer timer.Stop()
  24. select {
  25. case <-timer.C:
  26. return nil, ErrTimeout
  27. case <-p.channelDone:
  28. return nil, ErrClosed
  29. case packet := <-p.channelResponse:
  30. return packet, nil
  31. }
  32. }
  33. func (p *ProxyConn) Write(packet conntypes.Packet) error {
  34. timer := time.NewTimer(proxyConnWriteTimeout)
  35. defer timer.Stop()
  36. select {
  37. case <-timer.C:
  38. return ErrTimeout
  39. case <-p.channelDone:
  40. return ErrClosed
  41. case p.channelWrite <- packet:
  42. return nil
  43. }
  44. }
  45. func (p *ProxyConn) put(response *rpc.ProxyResponse) {
  46. select {
  47. case <-p.channelDone:
  48. case p.channelResponse <- response:
  49. }
  50. }
  51. func (p *ProxyConn) Close() {
  52. p.closeOnce.Do(func() {
  53. close(p.channelDone)
  54. go func() {
  55. p.channelClosed <- p.req.ConnID
  56. }()
  57. })
  58. }
  59. func newProxyConn(req *protocol.TelegramRequest, channelClosed chan<- conntypes.ConnID) *ProxyConn {
  60. return &ProxyConn{
  61. channelResponse: make(chan *rpc.ProxyResponse),
  62. channelDone: make(chan struct{}),
  63. channelClosed: channelClosed,
  64. req: req,
  65. }
  66. }