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

http-transport legs #23

Merged
merged 12 commits into from
Oct 28, 2021
Merged

http-transport legs #23

merged 12 commits into from
Oct 28, 2021

Conversation

willscott
Copy link
Collaborator

Conceptually, provide the same publisher and subscriber interface as legs, but with subscriber pulling from static files that the publisher makes available in an HTTP directory.

  • does not handle alerts of updated head in-band. a second notification protocol would be needed, as this will either poll, or use manual calls toSync to fetch.

@willscott
Copy link
Collaborator Author

relevant perhaps to @warpfork

http/subscribe.go Outdated Show resolved Hide resolved
http/subscribe.go Outdated Show resolved Hide resolved
http/subscribe.go Outdated Show resolved Hide resolved
http/subscribe.go Outdated Show resolved Hide resolved
subscribe.go Outdated Show resolved Hide resolved
@willscott
Copy link
Collaborator Author

This now has a publisher, subscriber and a test to demonstrate syncing.

test/util.go Outdated Show resolved Hide resolved
test/util.go Outdated Show resolved Hide resolved
subscribe.go Outdated Show resolved Hide resolved
interface.go Outdated Show resolved Hide resolved
"github.com/multiformats/go-multiaddr"
)

var defaultPollTime = time.Hour
Copy link
Contributor

Choose a reason for hiding this comment

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

const?

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

I can imagine testing wanting to change this

http/subscribe.go Outdated Show resolved Hide resolved
http/subscribe.go Outdated Show resolved Hide resolved
http/subscribe.go Show resolved Hide resolved
http/subscribe.go Outdated Show resolved Hide resolved
func (h *httpSubscriber) fetchHead(ctx context.Context) (cid.Cid, error) {
var cidStr string
if err := h.fetch(ctx, "head", func(msg io.Reader) error {
return json.NewDecoder(msg).Decode(&cidStr)
Copy link
Contributor

Choose a reason for hiding this comment

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

Beware that you might have fallen prey to golang/go#36225 here. You should either ensure there isn't a second JSON value, or use json.Unmarshal, which does that for you.

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

the worry is there's extra tailing error from the server after a valid CID, and we should error rather than reading the first CID and moving on?
It feels like an edge case where i'd rather not write the longer code of reading into a buffer and then unmarshaling since the end result here is we're trusting the server to tell us the head, and if we don't trust that response there's an availability attack anyway.

Copy link
Collaborator

Choose a reason for hiding this comment

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

@willscott I think the issue is that if there is an error with that first CID, it will not be caught:

r := strings.NewReader("{} bad data")

var m map[string]interface{}
d := json.NewDecoder(r)
if err := d.Decode(&m); err != nil {
	panic(err) // not triggered
}

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

the first entry would need to deserialize to a valid cid.
in the example the first entry {} deserializes to a valid map.

the fact remains: we're asking the server for a head. if they give us a failure / non-understandable response we fail availability. if they're purposefully corrupting their head response it's the same net result even if we go and ask for the CID here, so i'm not seeing this as causing any additional failure modes.

Copy link
Contributor

@mvdan mvdan Oct 28, 2021

Choose a reason for hiding this comment

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

Right, this is about a valid JSON value followed by garbage (or another JSON value) instead of EOF. Unmarshal catches that as an error, while Decode silently ignores the extra garbage.

This distinction is probably not hugely important in this particular scenario, so Will's response seems reasonable. We trust the response here. I think I'd still use Unmarshal for the sake of defensive programming, but I don't think it would actually make a difference in practice, unless the server has some serious bugs.

@willscott willscott merged commit e83b734 into main Oct 28, 2021
@willscott willscott deleted the http branch October 28, 2021 14:43
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants