Skip to content
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

Remove muxer-multistream.Transport and refactor upgrader #1861

Closed
wants to merge 6 commits into from

Conversation

julian88110
Copy link
Contributor

Details can be found in Issue #1854.

  • Remove muxer-multistream.Transport as an entity of type network.Multiplexer.
  • Define a new type MsTransport to encapsulate the multistream selection function.
  • Revise upgrader code to use the new MsTransport for muxer negotiation.
  • Update the relevant tests.

- Decoulple multistream.Transport from network.Multiplexer.
- Introduce MsTransport to encapsulate muxer negotiation function
- Refactor code to make it more streamlined.
- Update tests to use the new MsTransport.
Copy link
Contributor

@marten-seemann marten-seemann left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think we should have the MsTransport interface, or its implementation. The point of #1854 was to get rid of this complexity, not to move it to a different package.

p2p/net/upgrader/upgrader_test.go Outdated Show resolved Hide resolved
p2p/net/upgrader/multistream.go Outdated Show resolved Hide resolved
p2p/net/upgrader/multistream.go Outdated Show resolved Hide resolved
julian88110 and others added 2 commits November 9, 2022 09:24
Co-authored-by: Marten Seemann <martenseemann@gmail.com>
@julian88110 julian88110 self-assigned this Nov 9, 2022
Copy link
Collaborator

@MarcoPolo MarcoPolo left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I agree with @marten-seemann , let's remove the muxer_multistream package. I left some notes that I think give a rough idea of the steps required. But really you can probably start by copying the NegotiateMuxer func, deleting the muxer_multistream package, and then fixing errors/tests.

You got yourself a great refactor here! and I would expect net negative code and fewer public things :)

p2p/transport/websocket/websocket_test.go Outdated Show resolved Hide resolved

func (m *errorMuxer) NewConn(c net.Conn, isServer bool, scope network.PeerScope) (network.MuxedConn, error) {
func (m *errorMuxer) NegotiateMuxer(c net.Conn, isServer bool) (*upgrader.Multiplexer, error) {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is a different test now. The old test errored when creating a muxed connection. This now errors when negotiation. I don't think we should change this test, but it would maybe we should add another test if it makes sense.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

As the multistream transport itself is removed, this test is no longer relevant so I think it should be removed now.

go func() {
defer close(done)
smconn, err = u.muxer.NewConn(conn, server, scope)
streamMuxer, err = u.mstream.NegotiateMuxer(conn, server)
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think NegotiateMuxer should take a ctx and then we don't have to do this select dance below and we don't have to spawn a go routine.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's not possible since the MultistreamMuxer doesn't take a context (see my comment in https://github.com/libp2p/go-libp2p/pull/1861/files#r1018835597). Let's not touch timeouts in this PR.

t.mux.AddHandler(path, nil)
t.tpts[path] = tpt
t.OrderPreference = append(t.OrderPreference, path)
}

func (t *Transport) NewConn(nc net.Conn, isServer bool, scope network.PeerScope) (network.MuxedConn, error) {
func (t *Transport) NegotiateMuxer(nc net.Conn, isServer bool) (*Multiplexer, error) {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is the only function you need – and it's just a thin wrapper around go-multistream. I would say:

  1. we move this to the upgrader (No one else really cares about this package (I think)).
  2. Use a ctx to set the negotiate timeout
  3. Make it private
  4. Delete this whole package. less code!

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

  1. Agreed, see https://github.com/libp2p/go-libp2p/pull/1861/files#r1017265425.
  2. I wish that was possible, but unfortunately the MultistreamMuxer doesn't take a context (because there's no io.Reader that takes a context), so we can't use a context here. Anyway, fixing this seems orthogonal to this PR.
  3. Yes please!
  4. I assume you mean struct, not package. This code is now living in the upgrader package :)

@p-shahi p-shahi linked an issue Nov 12, 2022 that may be closed by this pull request
Copy link
Contributor

@marten-seemann marten-seemann left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This looks a lot better than the last iteration!

@@ -74,15 +75,21 @@ type upgrader struct {
//
// If unset, the default value (15s) is used.
acceptTimeout time.Duration

msmuxer *mss.MultistreamMuxer //
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Empty comment?

}

var _ transport.Upgrader = &upgrader{}

func New(secureMuxer sec.SecureMuxer, muxer network.Multiplexer, opts ...Option) (transport.Upgrader, error) {
func New(secureMuxer sec.SecureMuxer, muxers map[string]network.Multiplexer, preference []string, opts ...Option) (transport.Upgrader, error) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

These constructor options are very unclean.

What you want to use here is list of <id>, <muxer>, ordered by preference. Introduce a type that reflects that.

@@ -74,15 +75,21 @@ type upgrader struct {
//
// If unset, the default value (15s) is used.
acceptTimeout time.Duration

msmuxer *mss.MultistreamMuxer //
muxers map[string]network.Multiplexer
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Given that in most cases we'll only have 2 muxers, it's probably faster to just iterate over a slice. Map lookups only amortize for larger sets.

You can make the (internal) API look a bit nicer by introducing a getMuxerByID() (*multiplexer, bool) method.

smconn, err = u.muxer.NewConn(conn, server, scope)
muxer, err = u.negotiateMuxer(conn, server)

if err == nil {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nit: Return early if err != nil.

@@ -26,6 +26,8 @@ var ErrNilPeer = errors.New("nil peer")
// AcceptQueueLength is the number of connections to fully setup before not accepting any new connections
var AcceptQueueLength = 16

var defaultNegotiateTimeout = time.Second * 60
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
var defaultNegotiateTimeout = time.Second * 60
const defaultNegotiateTimeout = time.Second * 60

priv, _, err := test.RandTestKeyPair(crypto.Ed25519, 256)
require.NoError(t, err)
id, err := peer.IDFromPrivateKey(priv)
require.NoError(t, err)
u, err := upgrader.New(&MuxAdapter{tpt: insecure.NewWithIdentity(id, priv)}, muxer, opts...)
muxerId := "/yamux/1.0.0"
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please stick to Go naming conventions.

Suggested change
muxerId := "/yamux/1.0.0"
muxerID := "/yamux/1.0.0"

@@ -163,25 +114,6 @@ func TestOutboundResourceManagement(t *testing.T) {
require.NoError(t, conn.Close())
})

t.Run("failed negotiation", func(t *testing.T) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why are you deleting this test case?

transportSet := make(map[string]struct{}, len(tpts))
muxers := make(map[string]network.Multiplexer)
preference := make([]string, 0)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Preallocate slices with the correct capacity, if you know the capacity in advance.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
Archived in project
Development

Successfully merging this pull request may close these issues.

Remove multistream.transport as an entity of type network.multiplexer
3 participants