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

Support context #8

Open
tejasmanohar opened this issue Jul 27, 2017 · 9 comments
Open

Support context #8

tejasmanohar opened this issue Jul 27, 2017 · 9 comments
Assignees

Comments

@tejasmanohar
Copy link
Contributor

tejasmanohar commented Jul 27, 2017

Even though the standard library's net/rpc doesn't support contexts, we should because they're getting more popular and others have asked for it. The big question is-- Should we have a Context suffixed method for every RPC endpoint, or should we make a breaking change and have context.Context as the first argument across the board?

I don't feel strongly. It's easy to add context.TODO() if you don't care about contexts in your caller, but I also don't want to trouble people too much by making a breaking change... though it may be a good opportunity for me (and others) to learn gofix.

(Added assignees for feedback)

@achille-roussel
Copy link

achille-roussel commented Jul 27, 2017

Since you're dealing with generated code I don't think the breaking change is much of an issue.

gofix is the way to go 👍 translate client.Method(...) into client.Method(context.TODO(), ...) is probably not too hard.

Also I +💯 the initiative, we need contexts everywhere!

@CarlosMecha
Copy link

CarlosMecha commented Jul 27, 2017

I would suggest having 2 methods, one without the context client.Method(...) and client.MethodWithContext(ctx, ...). If not, it's going to break all the applications using the clients. I don't think it's a good idea to force update your code because we are adding an extra feature in a library.

support context != context or nothing ;)

@tejasmanohar
Copy link
Contributor Author

I actually prefer having one generated Go function per RPC method gofix method to keep things simple, but does it feel wrong to make the New method in the generated clients require context.Context in its interface when this is not the case in the standard library?

If we're even OK with enforcing client support for contexts, what should the interface of the client we ask the user for look like?

type Client interface {
	Call(method string, args interface{}, reply interface{}) error
}

Right now, it's like so but not sure if the Call method should take context, or if it should be CallContext? What RPC client with context support are we using now? I'd like to follow that...

client template - https://github.com/segmentio/glue/blob/master/templates/client.gohtml

@gesterhuizen
Copy link

If we have a decently big installed client base, we should be careful about breaking compatibility. Given that we're generating code, we can generate a new client that has an interface which supports contexts.

How does the standard lib handle reporting back infrastructure-layer information (e.g. metrics or on-the-wire message sizes) without using a context ?

@achille-roussel
Copy link

Wild idea but since you have a code generator, you could make it generate either version. Add a command line argument to enable one version or the other.

I doubt that there would be code out there that need both version of the methods in the same project.

@tejasmanohar
Copy link
Contributor Author

How does the standard lib handle reporting back infrastructure-layer information (e.g. metrics or on-the-wire message sizes) without using a context ?

@gesterhuizen The standard library comes with a very bare RPC server and doesn't handle that.

@tejasmanohar
Copy link
Contributor Author

@achille-roussel Most of our services commit a client package with the generated code so that wouldn't be inline with our workflow since whether or not to use context is the caller's choice.

@achille-roussel
Copy link

But the caller could regenerate its own client if it didn't want context support right? Passing context.TODO() is also trivial if you have code that's not context-ready, for this reason, I wouldn't worry much about breaking changes or offering only the context-based API.

@bvk
Copy link

bvk commented Jul 12, 2018

Just FYI, since the standard net/rpc package is frozen, a fork of that package at github.com/keegancsmith/rpc adds context.Context support to rpc.Server and rpc.Client types with cancellations.

It extends Call method with a context parameter, so Client interface would become

type Client interface {
	Call(ctx context.Context, method string, args interface{}, reply interface{}) error
}

and client wrapper functions also take additional context.Context parameter as in,

func (c *Math) Sum(ctx context.Context, args math.SumArg) (*math.SumReply, error) {
	reply := new(math.SumReply)
	err := c.RPC.Call(ctx, "Math.Sum", args, reply)
	return reply, err
}

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

No branches or pull requests

7 participants