github.com/searKing/golang/go@v1.2.117/net/http/httphost/host.go (about) 1 // Copyright 2022 The searKing Author. All rights reserved. 2 // Use of this source code is governed by a BSD-style 3 // license that can be found in the LICENSE file. 4 5 package httphost 6 7 import ( 8 "context" 9 "fmt" 10 "net/url" 11 12 "github.com/searKing/golang/go/net/resolver" 13 ) 14 15 // unique type to prevent assignment. 16 type hostContextKey struct{} 17 18 // Host specifies TargetUrl and HostTarget to return a dynamic host. 19 type Host struct { 20 // HostTarget is as like gRPC Naming for host service discovery, with Host in TargetUrl replaced if not empty. 21 HostTarget string 22 // resolve HostTarget to host and replace host if HostTarget resolved 23 ReplaceHostInRequest bool 24 25 // HostTargetAddrResolved is the host's addr resolved and picked from resolver. 26 HostTargetAddrResolved resolver.Address 27 } 28 29 // ContextHost returns the Host associated with the 30 // provided context. If none, it returns nil. 31 func ContextHost(ctx context.Context) *Host { 32 host, _ := ctx.Value(hostContextKey{}).(*Host) 33 return host 34 } 35 36 // WithHost returns a new context based on the provided parent 37 // ctx. HTTP client requests made with the returned context will use 38 // the provided host hooks 39 func WithHost(ctx context.Context, host *Host) context.Context { 40 if host == nil { 41 panic("nil host") 42 } 43 return context.WithValue(ctx, hostContextKey{}, host) 44 } 45 46 func ParseTargetUrl(host string) (*url.URL, error) { 47 if host == "" { 48 return nil, nil 49 } 50 51 hostURL, err := url.Parse(host) 52 if err != nil { 53 return nil, fmt.Errorf("invalid host address %q: %v", host, err) 54 } 55 return hostURL, nil 56 }