github.com/annwntech/go-micro/v2@v2.9.5/api/resolver/vpath/vpath.go (about)

     1  // Package vpath resolves using http path and recognised versioned urls
     2  package vpath
     3  
     4  import (
     5  	"errors"
     6  	"net/http"
     7  	"regexp"
     8  	"strings"
     9  
    10  	"github.com/annwntech/go-micro/v2/api/resolver"
    11  )
    12  
    13  func NewResolver(opts ...resolver.Option) resolver.Resolver {
    14  	return &Resolver{opts: resolver.NewOptions(opts...)}
    15  }
    16  
    17  type Resolver struct {
    18  	opts resolver.Options
    19  }
    20  
    21  var (
    22  	re = regexp.MustCompile("^v[0-9]+$")
    23  )
    24  
    25  func (r *Resolver) Resolve(req *http.Request, opts ...resolver.ResolveOption) (*resolver.Endpoint, error) {
    26  	// parse options
    27  	options := resolver.NewResolveOptions(opts...)
    28  	if req.URL.Path == "/" {
    29  		return nil, errors.New("unknown name")
    30  	}
    31  
    32  	parts := strings.Split(req.URL.Path[1:], "/")
    33  	if len(parts) == 1 {
    34  		return &resolver.Endpoint{
    35  			Name:   r.withNamespace(req, parts...),
    36  			Host:   req.Host,
    37  			Method: req.Method,
    38  			Path:   req.URL.Path,
    39  			Domain: options.Domain,
    40  		}, nil
    41  	}
    42  
    43  	// /v1/foo
    44  	if re.MatchString(parts[0]) {
    45  		return &resolver.Endpoint{
    46  			Name:   r.withNamespace(req, parts[0:2]...),
    47  			Host:   req.Host,
    48  			Method: req.Method,
    49  			Path:   req.URL.Path,
    50  			Domain: options.Domain,
    51  		}, nil
    52  	}
    53  
    54  	return &resolver.Endpoint{
    55  		Name:   r.withNamespace(req, parts[0]),
    56  		Host:   req.Host,
    57  		Method: req.Method,
    58  		Path:   req.URL.Path,
    59  		Domain: options.Domain,
    60  	}, nil
    61  }
    62  
    63  func (r *Resolver) String() string {
    64  	return "path"
    65  }
    66  
    67  func (r *Resolver) withNamespace(req *http.Request, parts ...string) string {
    68  	ns := r.opts.Namespace(req)
    69  	if len(ns) == 0 {
    70  		return strings.Join(parts, ".")
    71  	}
    72  
    73  	return strings.Join(append([]string{ns}, parts...), ".")
    74  }