github.com/sagernet/sing-box@v1.9.0-rc.20/experimental/libbox/command_select.go (about) 1 package libbox 2 3 import ( 4 "encoding/binary" 5 "net" 6 7 "github.com/sagernet/sing-box/outbound" 8 E "github.com/sagernet/sing/common/exceptions" 9 "github.com/sagernet/sing/common/rw" 10 ) 11 12 func (c *CommandClient) SelectOutbound(groupTag string, outboundTag string) error { 13 conn, err := c.directConnect() 14 if err != nil { 15 return err 16 } 17 defer conn.Close() 18 err = binary.Write(conn, binary.BigEndian, uint8(CommandSelectOutbound)) 19 if err != nil { 20 return err 21 } 22 err = rw.WriteVString(conn, groupTag) 23 if err != nil { 24 return err 25 } 26 err = rw.WriteVString(conn, outboundTag) 27 if err != nil { 28 return err 29 } 30 return readError(conn) 31 } 32 33 func (s *CommandServer) handleSelectOutbound(conn net.Conn) error { 34 groupTag, err := rw.ReadVString(conn) 35 if err != nil { 36 return err 37 } 38 outboundTag, err := rw.ReadVString(conn) 39 if err != nil { 40 return err 41 } 42 service := s.service 43 if service == nil { 44 return writeError(conn, E.New("service not ready")) 45 } 46 outboundGroup, isLoaded := service.instance.Router().Outbound(groupTag) 47 if !isLoaded { 48 return writeError(conn, E.New("selector not found: ", groupTag)) 49 } 50 selector, isSelector := outboundGroup.(*outbound.Selector) 51 if !isSelector { 52 return writeError(conn, E.New("outbound is not a selector: ", groupTag)) 53 } 54 if !selector.SelectOutbound(outboundTag) { 55 return writeError(conn, E.New("outbound not found in selector: ", outboundTag)) 56 } 57 return writeError(conn, nil) 58 }