balancing.go 921 B

12345678910111213141516171819202122232425262728293031323334353637383940414243444546
  1. // +build !confonly
  2. package router
  3. import (
  4. "github.com/v2fly/v2ray-core/v4/common/dice"
  5. "github.com/v2fly/v2ray-core/v4/features/outbound"
  6. )
  7. type BalancingStrategy interface {
  8. PickOutbound([]string) string
  9. }
  10. type RandomStrategy struct {
  11. }
  12. func (s *RandomStrategy) PickOutbound(tags []string) string {
  13. n := len(tags)
  14. if n == 0 {
  15. panic("0 tags")
  16. }
  17. return tags[dice.Roll(n)]
  18. }
  19. type Balancer struct {
  20. selectors []string
  21. strategy BalancingStrategy
  22. ohm outbound.Manager
  23. }
  24. func (b *Balancer) PickOutbound() (string, error) {
  25. hs, ok := b.ohm.(outbound.HandlerSelector)
  26. if !ok {
  27. return "", newError("outbound.Manager is not a HandlerSelector")
  28. }
  29. tags := hs.Select(b.selectors)
  30. if len(tags) == 0 {
  31. return "", newError("no available outbounds selected")
  32. }
  33. tag := b.strategy.PickOutbound(tags)
  34. if tag == "" {
  35. return "", newError("balancing strategy returns empty tag")
  36. }
  37. return tag, nil
  38. }