jasonwhite / rudolfs

A high-performance, caching Git LFS server with an AWS S3 and local storage back-end.
MIT License
392 stars 39 forks source link

How to host local only with docker? #38

Closed Zottelchen closed 3 years ago

Zottelchen commented 3 years ago

I've tried building a simple image using:

FROM jasonwhite0/rudolfs
ENTRYPOINT ["/tini", "--", "/rudolfs"]
CMD ["--host=localhost:8080","--key=xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx", "local", "--path=/lfsdata"]

It starts fine:

2021-11-17T16:15:28.856Z INFO  rudolfs > Initializing storage...
2021-11-17T16:15:28.858Z INFO  rudolfs > Local disk storage initialized.
2021-11-17T16:15:28.858Z INFO  rudolfs > Listening on 127.0.0.1:8080

I've added the following to my .lfsconfig:

[lfs]
url = "http://127.0.0.1:8080/api/ab/project"

However git push fails:

Uploading LFS objects:   0% (0/2), 0 B | 0 B/s, done.
batch response: Post "http://127.0.0.1:8080/api/ab/project/objects/batch": EOF

What did I miss?

jasonwhite commented 3 years ago

This all looks fine. What is the command used when running the Docker image? Is port 8080 exposed (e.g., -p 8080:8080)?

Zottelchen commented 3 years ago

The command was docker run -p 8080:8080 lfs (after building docker build . -t lfs). When trying to open it in the browser, it also resets the connection.

jasonwhite commented 3 years ago

I was able to reproduce the problem pretty easily. The problem is binding to localhost, which seems to be an old Docker pitfall. The solution is to either use --host=0.0.0.0:8080 or simply don't specify --host since it defaults to 0.0.0.0:8080 anyway.

If I understand correctly how Docker works, localhost resolves to 127.0.0.1 which is a loopback network interface private to the container's network namespace and doesn't have access to the outside world. Rudolfs (or any server, really) needs to bind to a network interface that is a bridge to the host network namespace.

Using 0.0.0.0 means the server shall try to bind to all available network interfaces, including both the bridge interface and loopback interface.