-
Notifications
You must be signed in to change notification settings - Fork 4.4k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
peer and metadata: Implement the Stringer interface for Peer and Metadata #7137
Changes from all commits
83118ab
20ee25c
172603c
edfd323
985347e
067b07e
e482bcc
c908bad
d36bfd5
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -90,6 +90,21 @@ func Pairs(kv ...string) MD { | |
return md | ||
} | ||
|
||
// String implements the Stringer interface for pretty-printing a MD. | ||
// Ordering of the values is non-deterministic as it ranges over a map. | ||
func (md MD) String() string { | ||
var sb strings.Builder | ||
fmt.Fprintf(&sb, "MD{") | ||
arvindbr8 marked this conversation as resolved.
Show resolved
Hide resolved
|
||
for k, v := range md { | ||
if sb.Len() > 3 { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. How about defining a |
||
fmt.Fprintf(&sb, ", ") | ||
} | ||
arvindbr8 marked this conversation as resolved.
Show resolved
Hide resolved
|
||
fmt.Fprintf(&sb, "%s=[%s]", k, strings.Join(v, ", ")) | ||
} | ||
fmt.Fprintf(&sb, "}") | ||
return sb.String() | ||
} | ||
|
||
// Len returns the number of items in md. | ||
func (md MD) Len() int { | ||
return len(md) | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,103 @@ | ||
/* | ||
* | ||
* Copyright 2024 gRPC authors. | ||
* | ||
* Licensed under the Apache License, Version 2.0 (the "License"); | ||
* you may not use this file except in compliance with the License. | ||
* You may obtain a copy of the License at | ||
* | ||
* http://www.apache.org/licenses/LICENSE-2.0 | ||
* | ||
* Unless required by applicable law or agreed to in writing, software | ||
* distributed under the License is distributed on an "AS IS" BASIS, | ||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
* See the License for the specific language governing permissions and | ||
* limitations under the License. | ||
* | ||
*/ | ||
|
||
package peer | ||
|
||
import ( | ||
"context" | ||
"fmt" | ||
"testing" | ||
|
||
"google.golang.org/grpc/credentials" | ||
) | ||
|
||
// A struct that implements AuthInfo interface and implements CommonAuthInfo() method. | ||
type testAuthInfo struct { | ||
credentials.CommonAuthInfo | ||
} | ||
|
||
func (ta testAuthInfo) AuthType() string { | ||
return fmt.Sprintf("testAuthInfo-%d", ta.SecurityLevel) | ||
} | ||
|
||
type addr struct { | ||
ipAddress string | ||
} | ||
|
||
func (addr) Network() string { return "" } | ||
|
||
func (a *addr) String() string { return a.ipAddress } | ||
|
||
func TestPeerStringer(t *testing.T) { | ||
testCases := []struct { | ||
name string | ||
peer *Peer | ||
want string | ||
}{ | ||
{ | ||
name: "+Addr-LocalAddr+ValidAuth", | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Just FYI, go There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I was trying to convey information about whether the test case included There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The use of
The above names in the test output are more readable I feel. |
||
peer: &Peer{Addr: &addr{"example.com:1234"}, AuthInfo: testAuthInfo{credentials.CommonAuthInfo{SecurityLevel: credentials.PrivacyAndIntegrity}}}, | ||
want: "Peer{Addr: 'example.com:1234', LocalAddr: <nil>, AuthInfo: 'testAuthInfo-3'}", | ||
}, | ||
{ | ||
name: "+Addr+LocalAddr+ValidAuth", | ||
peer: &Peer{Addr: &addr{"example.com:1234"}, LocalAddr: &addr{"example.com:1234"}, AuthInfo: testAuthInfo{credentials.CommonAuthInfo{SecurityLevel: credentials.PrivacyAndIntegrity}}}, | ||
want: "Peer{Addr: 'example.com:1234', LocalAddr: 'example.com:1234', AuthInfo: 'testAuthInfo-3'}", | ||
}, | ||
{ | ||
name: "+Addr-LocalAddr+emptyAuth", | ||
peer: &Peer{Addr: &addr{"1.2.3.4:1234"}, AuthInfo: testAuthInfo{credentials.CommonAuthInfo{}}}, | ||
want: "Peer{Addr: '1.2.3.4:1234', LocalAddr: <nil>, AuthInfo: 'testAuthInfo-0'}", | ||
}, | ||
{ | ||
name: "-Addr-LocalAddr+emptyAuth", | ||
peer: &Peer{AuthInfo: testAuthInfo{}}, | ||
want: "Peer{Addr: <nil>, LocalAddr: <nil>, AuthInfo: 'testAuthInfo-0'}", | ||
}, | ||
{ | ||
name: "zeroedPeer", | ||
peer: &Peer{}, | ||
want: "Peer{Addr: <nil>, LocalAddr: <nil>, AuthInfo: <nil>}", | ||
}, | ||
{ | ||
name: "nilPeer", | ||
peer: nil, | ||
want: "Peer<nil>", | ||
}, | ||
} | ||
for _, tc := range testCases { | ||
t.Run(tc.name, func(t *testing.T) { | ||
ctx := NewContext(context.Background(), tc.peer) | ||
p, ok := FromContext(ctx) | ||
if !ok { | ||
t.Fatalf("Unable to get peer from context") | ||
} | ||
if p.String() != tc.want { | ||
t.Fatalf("Error using peer String(): expected %q, got %q", tc.want, p.String()) | ||
} | ||
AnomalRoil marked this conversation as resolved.
Show resolved
Hide resolved
|
||
}) | ||
} | ||
} | ||
|
||
func TestPeerStringerOnContext(t *testing.T) { | ||
ctx := NewContext(context.Background(), &Peer{Addr: &addr{"1.2.3.4:1234"}, AuthInfo: testAuthInfo{credentials.CommonAuthInfo{SecurityLevel: credentials.PrivacyAndIntegrity}}}) | ||
want := "context.Background.WithValue(type peer.peerKey, val Peer{Addr: '1.2.3.4:1234', LocalAddr: <nil>, AuthInfo: 'testAuthInfo-3'})" | ||
if got := fmt.Sprintf("%v", ctx); got != want { | ||
t.Fatalf("Unexpected stringer output, got: %q; want: %q", got, want) | ||
} | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What do you think about sorting the keys before generating the string representation and ensuring that the output is deterministic. This will also make the unit test much simpler than what it is currently.