Skip to content

Commit 59dc2ce

Browse files
authored
API: Add ListRule() for routing (#5569)
#5569 (comment)
1 parent 5846f94 commit 59dc2ce

File tree

8 files changed

+456
-282
lines changed

8 files changed

+456
-282
lines changed

app/router/command/command.go

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -60,13 +60,28 @@ func (s *routingServer) AddRule(ctx context.Context, request *AddRuleRequest) (*
6060
return nil, errors.New("unsupported router implementation")
6161

6262
}
63+
6364
func (s *routingServer) RemoveRule(ctx context.Context, request *RemoveRuleRequest) (*RemoveRuleResponse, error) {
6465
if bo, ok := s.router.(routing.Router); ok {
6566
return &RemoveRuleResponse{}, bo.RemoveRule(request.RuleTag)
6667
}
6768
return nil, errors.New("unsupported router implementation")
6869
}
6970

71+
func (s *routingServer) ListRule(ctx context.Context, request *ListRuleRequest) (*ListRuleResponse, error) {
72+
if bo, ok := s.router.(routing.Router); ok {
73+
response := &ListRuleResponse{}
74+
for _, v := range bo.ListRule() {
75+
response.Rules = append(response.Rules, &ListRuleItem{
76+
Tag: v.GetOutboundTag(),
77+
RuleTag: v.GetRuleTag(),
78+
})
79+
}
80+
return response, nil
81+
}
82+
return nil, errors.New("unsupported router implementation")
83+
}
84+
7085
// NewRoutingServer creates a statistics service with statistics manager.
7186
func NewRoutingServer(router routing.Router, routingStats stats.Channel) RoutingServiceServer {
7287
return &routingServer{

app/router/command/command.pb.go

Lines changed: 315 additions & 272 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

app/router/command/command.proto

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -104,6 +104,17 @@ message RemoveRuleRequest {
104104

105105
message RemoveRuleResponse {}
106106

107+
message ListRuleRequest {}
108+
109+
message ListRuleItem {
110+
string tag = 1;
111+
string ruleTag = 2;
112+
}
113+
114+
message ListRuleResponse{
115+
repeated ListRuleItem rules = 1;
116+
}
117+
107118
service RoutingService {
108119
rpc SubscribeRoutingStats(SubscribeRoutingStatsRequest)
109120
returns (stream RoutingContext) {}
@@ -114,6 +125,8 @@ service RoutingService {
114125

115126
rpc AddRule(AddRuleRequest) returns (AddRuleResponse) {}
116127
rpc RemoveRule(RemoveRuleRequest) returns (RemoveRuleResponse) {}
128+
129+
rpc ListRule(ListRuleRequest) returns (ListRuleResponse) {}
117130
}
118131

119132
message Config {}

app/router/command/command_grpc.pb.go

Lines changed: 47 additions & 9 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

app/router/router.go

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ package router
22

33
import (
44
"context"
5-
sync "sync"
5+
"sync"
66

77
"github.com/xtls/xray-core/common"
88
"github.com/xtls/xray-core/common/errors"
@@ -181,6 +181,21 @@ func (r *Router) RemoveRule(tag string) error {
181181
return errors.New("empty tag name!")
182182

183183
}
184+
185+
// ListRule implements routing.Router
186+
func (r *Router) ListRule() []routing.Route {
187+
r.mu.Lock()
188+
defer r.mu.Unlock()
189+
ruleList := make([]routing.Route, 0)
190+
for _, rule := range r.rules {
191+
ruleList = append(ruleList, &Route{
192+
outboundTag: rule.Tag,
193+
ruleTag: rule.RuleTag,
194+
})
195+
}
196+
return ruleList
197+
}
198+
184199
func (r *Router) pickRouteInternal(ctx routing.Context) (*Rule, routing.Context, error) {
185200
// SkipDNSResolve is set from DNS module.
186201
// the DOH remote server maybe a domain name,

features/routing/router.go

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@ type Router interface {
1616
PickRoute(ctx Context) (Route, error)
1717
AddRule(config *serial.TypedMessage, shouldAppend bool) error
1818
RemoveRule(tag string) error
19+
ListRule() []Route
1920
}
2021

2122
// Route is the routing result of Router feature.
@@ -65,6 +66,11 @@ func (DefaultRouter) RemoveRule(tag string) error {
6566
return common.ErrNoClue
6667
}
6768

69+
// ListRule implements Router.
70+
func (DefaultRouter) ListRule() []Route {
71+
return nil
72+
}
73+
6874
// Start implements common.Runnable.
6975
func (DefaultRouter) Start() error {
7076
return nil

main/commands/all/api/api.go

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,7 @@ var CmdAPI = &base.Command{
2929
cmdInboundUserCount,
3030
cmdAddRules,
3131
cmdRemoveRules,
32+
cmdListRules,
3233
cmdSourceIpBlock,
3334
cmdOnlineStats,
3435
cmdOnlineStatsIpList,
Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,43 @@
1+
package api
2+
3+
import (
4+
routerService "github.com/xtls/xray-core/app/router/command"
5+
"github.com/xtls/xray-core/main/commands/base"
6+
)
7+
8+
var cmdListRules = &base.Command{
9+
CustomFlags: true,
10+
UsageLine: "{{.Exec}} api lsrules [--server=127.0.0.1:8080]",
11+
Short: "List routing rules",
12+
Long: `
13+
List routing rules in Xray.
14+
15+
Arguments:
16+
17+
-s, -server <server:port>
18+
The API server address. Default 127.0.0.1:8080
19+
20+
-t, -timeout <seconds>
21+
Timeout in seconds for calling API. Default 3
22+
23+
Example:
24+
25+
{{.Exec}} {{.LongName}} --server=127.0.0.1:8080
26+
`,
27+
Run: executeListRules,
28+
}
29+
30+
func executeListRules(cmd *base.Command, args []string) {
31+
setSharedFlags(cmd)
32+
cmd.Flag.Parse(args)
33+
34+
conn, ctx, close := dialAPIServer()
35+
defer close()
36+
37+
client := routerService.NewRoutingServiceClient(conn)
38+
resp, err := client.ListRule(ctx, &routerService.ListRuleRequest{})
39+
if err != nil {
40+
base.Fatalf("failed to list rules: %s", err)
41+
}
42+
showJSONResponse(resp)
43+
}

0 commit comments

Comments
 (0)