cocrrent.go 1.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263
  1. package middleware
  2. import (
  3. "net/http"
  4. "sync"
  5. "github.com/gin-gonic/gin"
  6. "github.com/langgenius/dify-sandbox/internal/types"
  7. "github.com/langgenius/dify-sandbox/internal/utils/log"
  8. )
  9. func MaxWoker(max int) gin.HandlerFunc {
  10. queue := make(chan *gin.Context, max)
  11. for i := 0; i < max; i++ {
  12. i := i
  13. go func() {
  14. log.Info("code runner worker %d started", i)
  15. for {
  16. select {
  17. case c := <-queue:
  18. c.Next()
  19. }
  20. }
  21. }()
  22. }
  23. return func(c *gin.Context) {
  24. queue <- c
  25. }
  26. }
  27. type MaxRequestIface struct {
  28. current int
  29. lock *sync.RWMutex
  30. }
  31. func MaxRequest(max int) gin.HandlerFunc {
  32. log.Info("setting max requests to %d", max)
  33. m := &MaxRequestIface{
  34. current: 0,
  35. lock: &sync.RWMutex{},
  36. }
  37. return func(c *gin.Context) {
  38. m.lock.RLock()
  39. if m.current >= max {
  40. m.lock.RUnlock()
  41. c.JSON(http.StatusServiceUnavailable, types.ErrorResponse(-503, "Too many requests"))
  42. c.Abort()
  43. return
  44. }
  45. m.lock.RUnlock()
  46. m.lock.Lock()
  47. m.current++
  48. m.lock.Unlock()
  49. c.Next()
  50. m.lock.Lock()
  51. m.current--
  52. m.lock.Unlock()
  53. }
  54. }