|
|
@@ -196,6 +196,47 @@ func (d *DefaultDispatcher) getLink(ctx context.Context) (*transport.Link, *tran
|
|
|
return inboundLink, outboundLink
|
|
|
}
|
|
|
|
|
|
+func (d *DefaultDispatcher) WrapLink(ctx context.Context, link *transport.Link) *transport.Link {
|
|
|
+ sessionInbound := session.InboundFromContext(ctx)
|
|
|
+ var user *protocol.MemoryUser
|
|
|
+ if sessionInbound != nil {
|
|
|
+ user = sessionInbound.User
|
|
|
+ }
|
|
|
+
|
|
|
+ link.Reader = &buf.TimeoutWrapperReader{Reader: link.Reader}
|
|
|
+
|
|
|
+ if user != nil && len(user.Email) > 0 {
|
|
|
+ p := d.policy.ForLevel(user.Level)
|
|
|
+ if p.Stats.UserUplink {
|
|
|
+ name := "user>>>" + user.Email + ">>>traffic>>>uplink"
|
|
|
+ if c, _ := stats.GetOrRegisterCounter(d.stats, name); c != nil {
|
|
|
+ link.Reader.(*buf.TimeoutWrapperReader).Counter = c
|
|
|
+ }
|
|
|
+ }
|
|
|
+ if p.Stats.UserDownlink {
|
|
|
+ name := "user>>>" + user.Email + ">>>traffic>>>downlink"
|
|
|
+ if c, _ := stats.GetOrRegisterCounter(d.stats, name); c != nil {
|
|
|
+ link.Writer = &SizeStatWriter{
|
|
|
+ Counter: c,
|
|
|
+ Writer: link.Writer,
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ if p.Stats.UserOnline {
|
|
|
+ name := "user>>>" + user.Email + ">>>online"
|
|
|
+ if om, _ := stats.GetOrRegisterOnlineMap(d.stats, name); om != nil {
|
|
|
+ sessionInbounds := session.InboundFromContext(ctx)
|
|
|
+ userIP := sessionInbounds.Source.Address.String()
|
|
|
+ om.AddIP(userIP)
|
|
|
+ // log Online user with ips
|
|
|
+ // errors.LogDebug(ctx, "user>>>" + user.Email + ">>>online", om.Count(), om.List())
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ return link
|
|
|
+}
|
|
|
+
|
|
|
func (d *DefaultDispatcher) shouldOverride(ctx context.Context, result SniffResult, request session.SniffingRequest, destination net.Destination) bool {
|
|
|
domain := result.Domain()
|
|
|
if domain == "" {
|
|
|
@@ -316,6 +357,7 @@ func (d *DefaultDispatcher) DispatchLink(ctx context.Context, destination net.De
|
|
|
content = new(session.Content)
|
|
|
ctx = session.ContextWithContent(ctx, content)
|
|
|
}
|
|
|
+ outbound = d.WrapLink(ctx, outbound)
|
|
|
sniffingRequest := content.SniffingRequest
|
|
|
if !sniffingRequest.Enabled {
|
|
|
d.routedDispatch(ctx, outbound, destination)
|