github.com/searKing/golang/go@v1.2.117/database/dsn/dsn.go (about)

     1  package dsn
     2  
     3  import (
     4  	"fmt"
     5  	"net/url"
     6  	"strings"
     7  )
     8  
     9  // See https://en.wikipedia.org/wiki/Data_source_name
    10  // <driver>://<username>:<password>@<host>:<port>/<database>[?<param1>=<value1>&<paramN>=<valueN>]
    11  // schema://[user[:password]@][net[(addr)]]/dbname[?param1=value1&paramN=valueN]
    12  
    13  // GetDriverName returns the driver name of a given DSN.
    14  func GetDriverName(dsn string) string {
    15  	scheme, _, _ := Split(dsn)
    16  	return scheme
    17  }
    18  
    19  // Split splits dsn into a driver name(scheme) and left component.
    20  // If there is no :// in dsn, Split returns an empty driver name and
    21  // dsn without schema.
    22  // The returned values have the property that dsn = driver+dsnSchemaOmitted.
    23  // schema://[user[:password]@][net[(addr)]]/dbname[?param1=value1&paramN=valueN]
    24  // =>
    25  // [user[:password]@][net[(addr)]]/dbname[?param1=value1&paramN=valueN]
    26  func Split(dsn string) (scheme string, connect string, query url.Values) {
    27  	{
    28  		parts := strings.SplitN(dsn, "://", 2)
    29  		if len(parts) == 0 {
    30  			scheme = ""
    31  			connect = dsn
    32  		} else if len(parts) == 1 {
    33  			scheme = ""
    34  			connect = parts[0]
    35  		} else {
    36  			scheme = parts[0]
    37  			connect = parts[1]
    38  		}
    39  	}
    40  	{
    41  		parts := strings.SplitN(connect, "?", 2)
    42  		if len(parts) == 2 {
    43  			connect = parts[0]
    44  			query, _ = url.ParseQuery(parts[1])
    45  		}
    46  	}
    47  	return
    48  }
    49  
    50  // Join joins driver name(scheme) and dsn without schema into a single path,
    51  // separating them with slashes.
    52  func Join(scheme string, connect string, query url.Values) (dsn string) {
    53  	rawQuery := query.Encode()
    54  	if rawQuery != "" {
    55  		connect = fmt.Sprintf("%s?%s", connect, rawQuery)
    56  	}
    57  	if scheme == "" {
    58  		return connect
    59  	}
    60  	return fmt.Sprintf("%s://%s", scheme, connect)
    61  
    62  }
    63  
    64  // Masking hiding original username and password with character '*'
    65  // [user[:password]@][net[(addr)]]/dbname[?param1=value1&paramN=valueN]
    66  func Masking(dsn string) string {
    67  	scheme, connect, query := Split(dsn)
    68  	if connect == "" {
    69  		return Join(scheme, "", query)
    70  	}
    71  	pos := strings.LastIndex(connect, "@")
    72  	if pos < 0 { // No Auth
    73  		return dsn
    74  	}
    75  
    76  	return Join(scheme, fmt.Sprintf("*:*@%s", connect[pos+1:]), query)
    77  }