github.com/hxx258456/ccgo@v0.0.5-0.20230213014102-48b35f46f66f/grpc/internal/transport/http_util_test.go (about)

     1  /*
     2   *
     3   * Copyright 2014 gRPC authors.
     4   *
     5   * Licensed under the Apache License, Version 2.0 (the "License");
     6   * you may not use this file except in compliance with the License.
     7   * You may obtain a copy of the License at
     8   *
     9   *     http://www.apache.org/licenses/LICENSE-2.0
    10   *
    11   * Unless required by applicable law or agreed to in writing, software
    12   * distributed under the License is distributed on an "AS IS" BASIS,
    13   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    14   * See the License for the specific language governing permissions and
    15   * limitations under the License.
    16   *
    17   */
    18  
    19  package transport
    20  
    21  import (
    22  	"fmt"
    23  	"reflect"
    24  	"testing"
    25  	"time"
    26  )
    27  
    28  func (s) TestTimeoutDecode(t *testing.T) {
    29  	for _, test := range []struct {
    30  		// input
    31  		s string
    32  		// output
    33  		d   time.Duration
    34  		err error
    35  	}{
    36  		{"1234S", time.Second * 1234, nil},
    37  		{"1234x", 0, fmt.Errorf("transport: timeout unit is not recognized: %q", "1234x")},
    38  		{"1", 0, fmt.Errorf("transport: timeout string is too short: %q", "1")},
    39  		{"", 0, fmt.Errorf("transport: timeout string is too short: %q", "")},
    40  	} {
    41  		d, err := decodeTimeout(test.s)
    42  		if d != test.d || fmt.Sprint(err) != fmt.Sprint(test.err) {
    43  			t.Fatalf("timeoutDecode(%q) = %d, %v, want %d, %v", test.s, int64(d), err, int64(test.d), test.err)
    44  		}
    45  	}
    46  }
    47  
    48  func (s) TestEncodeGrpcMessage(t *testing.T) {
    49  	for _, tt := range []struct {
    50  		input    string
    51  		expected string
    52  	}{
    53  		{"", ""},
    54  		{"Hello", "Hello"},
    55  		{"\u0000", "%00"},
    56  		{"%", "%25"},
    57  		{"系统", "%E7%B3%BB%E7%BB%9F"},
    58  		{string([]byte{0xff, 0xfe, 0xfd}), "%EF%BF%BD%EF%BF%BD%EF%BF%BD"},
    59  	} {
    60  		actual := encodeGrpcMessage(tt.input)
    61  		if tt.expected != actual {
    62  			t.Errorf("encodeGrpcMessage(%q) = %q, want %q", tt.input, actual, tt.expected)
    63  		}
    64  	}
    65  
    66  	// make sure that all the visible ASCII chars except '%' are not percent encoded.
    67  	for i := ' '; i <= '~' && i != '%'; i++ {
    68  		output := encodeGrpcMessage(string(i))
    69  		if output != string(i) {
    70  			t.Errorf("encodeGrpcMessage(%v) = %v, want %v", string(i), output, string(i))
    71  		}
    72  	}
    73  
    74  	// make sure that all the invisible ASCII chars and '%' are percent encoded.
    75  	for i := rune(0); i == '%' || (i >= rune(0) && i < ' ') || (i > '~' && i <= rune(127)); i++ {
    76  		output := encodeGrpcMessage(string(i))
    77  		expected := fmt.Sprintf("%%%02X", i)
    78  		if output != expected {
    79  			t.Errorf("encodeGrpcMessage(%v) = %v, want %v", string(i), output, expected)
    80  		}
    81  	}
    82  }
    83  
    84  func (s) TestDecodeGrpcMessage(t *testing.T) {
    85  	for _, tt := range []struct {
    86  		input    string
    87  		expected string
    88  	}{
    89  		{"", ""},
    90  		{"Hello", "Hello"},
    91  		{"H%61o", "Hao"},
    92  		{"H%6", "H%6"},
    93  		{"%G0", "%G0"},
    94  		{"%E7%B3%BB%E7%BB%9F", "系统"},
    95  		{"%EF%BF%BD", "�"},
    96  	} {
    97  		actual := decodeGrpcMessage(tt.input)
    98  		if tt.expected != actual {
    99  			t.Errorf("decodeGrpcMessage(%q) = %q, want %q", tt.input, actual, tt.expected)
   100  		}
   101  	}
   102  
   103  	// make sure that all the visible ASCII chars except '%' are not percent decoded.
   104  	for i := ' '; i <= '~' && i != '%'; i++ {
   105  		output := decodeGrpcMessage(string(i))
   106  		if output != string(i) {
   107  			t.Errorf("decodeGrpcMessage(%v) = %v, want %v", string(i), output, string(i))
   108  		}
   109  	}
   110  
   111  	// make sure that all the invisible ASCII chars and '%' are percent decoded.
   112  	for i := rune(0); i == '%' || (i >= rune(0) && i < ' ') || (i > '~' && i <= rune(127)); i++ {
   113  		output := decodeGrpcMessage(fmt.Sprintf("%%%02X", i))
   114  		if output != string(i) {
   115  			t.Errorf("decodeGrpcMessage(%v) = %v, want %v", fmt.Sprintf("%%%02X", i), output, string(i))
   116  		}
   117  	}
   118  }
   119  
   120  // Decode an encoded string should get the same thing back, except for invalid
   121  // utf8 chars.
   122  func (s) TestDecodeEncodeGrpcMessage(t *testing.T) {
   123  	testCases := []struct {
   124  		orig string
   125  		want string
   126  	}{
   127  		{"", ""},
   128  		{"hello", "hello"},
   129  		{"h%6", "h%6"},
   130  		{"%G0", "%G0"},
   131  		{"系统", "系统"},
   132  		{"Hello, 世界", "Hello, 世界"},
   133  
   134  		{string([]byte{0xff, 0xfe, 0xfd}), "���"},
   135  		{string([]byte{0xff}) + "Hello" + string([]byte{0xfe}) + "世界" + string([]byte{0xfd}), "�Hello�世界�"},
   136  	}
   137  	for _, tC := range testCases {
   138  		got := decodeGrpcMessage(encodeGrpcMessage(tC.orig))
   139  		if got != tC.want {
   140  			t.Errorf("decodeGrpcMessage(encodeGrpcMessage(%q)) = %q, want %q", tC.orig, got, tC.want)
   141  		}
   142  	}
   143  }
   144  
   145  const binaryValue = "\u0080"
   146  
   147  func (s) TestEncodeMetadataHeader(t *testing.T) {
   148  	for _, test := range []struct {
   149  		// input
   150  		kin string
   151  		vin string
   152  		// output
   153  		vout string
   154  	}{
   155  		{"key", "abc", "abc"},
   156  		{"KEY", "abc", "abc"},
   157  		{"key-bin", "abc", "YWJj"},
   158  		{"key-bin", binaryValue, "woA"},
   159  	} {
   160  		v := encodeMetadataHeader(test.kin, test.vin)
   161  		if !reflect.DeepEqual(v, test.vout) {
   162  			t.Fatalf("encodeMetadataHeader(%q, %q) = %q, want %q", test.kin, test.vin, v, test.vout)
   163  		}
   164  	}
   165  }
   166  
   167  func (s) TestDecodeMetadataHeader(t *testing.T) {
   168  	for _, test := range []struct {
   169  		// input
   170  		kin string
   171  		vin string
   172  		// output
   173  		vout string
   174  		err  error
   175  	}{
   176  		{"a", "abc", "abc", nil},
   177  		{"key-bin", "Zm9vAGJhcg==", "foo\x00bar", nil},
   178  		{"key-bin", "Zm9vAGJhcg", "foo\x00bar", nil},
   179  		{"key-bin", "woA=", binaryValue, nil},
   180  		{"a", "abc,efg", "abc,efg", nil},
   181  	} {
   182  		v, err := decodeMetadataHeader(test.kin, test.vin)
   183  		if !reflect.DeepEqual(v, test.vout) || !reflect.DeepEqual(err, test.err) {
   184  			t.Fatalf("decodeMetadataHeader(%q, %q) = %q, %v, want %q, %v", test.kin, test.vin, v, err, test.vout, test.err)
   185  		}
   186  	}
   187  }
   188  
   189  func (s) TestParseDialTarget(t *testing.T) {
   190  	for _, test := range []struct {
   191  		target, wantNet, wantAddr string
   192  	}{
   193  		{"unix:a", "unix", "a"},
   194  		{"unix:a/b/c", "unix", "a/b/c"},
   195  		{"unix:/a", "unix", "/a"},
   196  		{"unix:/a/b/c", "unix", "/a/b/c"},
   197  		{"unix://a", "unix", "a"},
   198  		{"unix://a/b/c", "unix", "/b/c"},
   199  		{"unix:///a", "unix", "/a"},
   200  		{"unix:///a/b/c", "unix", "/a/b/c"},
   201  		{"unix:etcd:0", "unix", "etcd:0"},
   202  		{"unix:///tmp/unix-3", "unix", "/tmp/unix-3"},
   203  		{"unix://domain", "unix", "domain"},
   204  		{"unix://etcd:0", "unix", "etcd:0"},
   205  		{"unix:///etcd:0", "unix", "/etcd:0"},
   206  		{"passthrough://unix://domain", "tcp", "passthrough://unix://domain"},
   207  		{"https://google.com:443", "tcp", "https://google.com:443"},
   208  		{"dns:///google.com", "tcp", "dns:///google.com"},
   209  		{"/unix/socket/address", "tcp", "/unix/socket/address"},
   210  	} {
   211  		gotNet, gotAddr := parseDialTarget(test.target)
   212  		if gotNet != test.wantNet || gotAddr != test.wantAddr {
   213  			t.Errorf("parseDialTarget(%q) = %s, %s want %s, %s", test.target, gotNet, gotAddr, test.wantNet, test.wantAddr)
   214  		}
   215  	}
   216  }