-
Notifications
You must be signed in to change notification settings - Fork 442
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
unintuitive behavior when using &nsq.Config{} #42
Conversation
Ok, it was most likely caused by me passing &nsq.Config{} to NewConsumer() and NewProducer(). Changing it to use nsq.NewConfig() fixed this. Nevertheless, this is a bad way to fail. If &nsq.Config{} is not a valid config value, then some validation should take place and an error returned from NewConsumer() and NewProducer() (instead of panic() or some other bad behavior later on). Alternatively, &nsq.Config{} could have been silently "upgraded" by NewConsumer() and NewProducer() to have the same values as NewConfig(). I understand it might be tempting to brush this off as "read documentation" but people (including myself) don't alway read documentation from start to end and constructing objects with literal syntax is an idiom. |
these are reasonable comments, let me think about it a bit and we'll figure out how to improve this... |
sounds good to me |
RFR |
LGTM (aside from jenkins failing). Just add some comments in initialize() describing why it's there instead of in a New... function. |
unintuitive behavior when using &nsq.Config{}
If
Was this idea considered, and if so, is there a reason why it would be worse/inappropriate? |
I thought about it, but I imagined that there might be use cases where you want to pass around an I do prefer solutions that result in there being only one correct way to do things if we can come up with one. For the record, as far as I'm concerned, everything in master is fair game for improving the API before a stable release is tagged, so thanks for your feedback. |
Yeah, that's a valid concern (the only drawback that I could think of so far). One way to fix that problem that would be to declare an exported interface that type Config interface {
Set(option string, value interface{}) error
}
func NewConfig() Config {
return &config{
// default setting here
}
} This is possible in your case since all fields in current |
Yea, I thought of that too, but didn't further consider it because I was concerned about any other type being able to satisfy the interface and be able to be passed in without type safety. BUT, I forgot that you can do the old un-exported method on an exported interface trick to prevent outsiders from satisfying it: type Config interface {
Set(string, interface{}) error
sentinel()
}
type config struct {
// ...
}
func (c *config) sentinel() {} What do you think? |
It's funny that we have to do quite a few extra things to achieve the two goals:
But yeah, I think what you propose would allow that to work. It's still worth it to do extra work internal to your library if that allows you to make the public API better/cleaner. The users would have to change their internal instances of |
I got this on Ubuntu 12.04, go 1.2
This is 2b9a8b5
I'm connecting to 8 nsqlookupd hosts (which might increase the chance of this happening)
I'm not setting config.lookupdPollInterval in my code.