immich-go icon indicating copy to clipboard operation
immich-go copied to clipboard

feat: support build docker image

Open pkking opened this issue 1 year ago • 29 comments

This PR want to support building docker image for this awesome project, maybe more steps can be done like publish package with github action :)

PS: will be happy to make more contributions!

pkking avatar Jun 16 '24 12:06 pkking

This is cool. Thank you. The initial idea of immich-go was to not bother tandom users with npm, docker, etc... :-)

But apparently there is an use case for docker...

Do you know how to publish the package with github actions?

Will try to add a workflow file later, ref: https://github.com/pkking/copr_docker/blob/main/.github/workflows/keygen-signd-publish.yml#L48-L110

pkking avatar Jun 17 '24 02:06 pkking

@simulot This pr contains a new workflow that can publish a docker image to docker hub && ghcr registry, you just need to add two github action secret DOCKERHUB_USERNAME and DOCKERHUB_TOKEN

Here's the newest image i pushed from the forked repo action

pkking avatar Jun 17 '24 15:06 pkking

I have more questions about this? Can we have discussion on Discord or by email?

simulot avatar Jun 17 '24 16:06 simulot

I have more questions about this? Can we have discussion on Discord or by email?

@simulot Sure thing, discord id: lcr1221 and TZ: GMT+8, if not available, can email me using the address from the PR commit :)

pkking avatar Jun 18 '24 02:06 pkking

Why would someone need Docker image for this?. :thinking:

Also, why would you use anything other than scratch as base image? My example (that also needs ca-certificates for Golang): https://github.com/erkexzcx/valetudopng/blob/main/Dockerfile

erkexzcx avatar Jun 21 '24 12:06 erkexzcx

@simulot you can also use ghcr.io (GitHub's registry) instead of Dockerhub.

      - name: Login to GitHub Container Registry
        uses: docker/login-action@v3
        with:
          registry: ghcr.io
          username: ${{ github.actor }}
          password: ${{ secrets.GITHUB_TOKEN }}

erkexzcx avatar Jun 21 '24 12:06 erkexzcx

@erkexzcx Thanks, I prefer this option.

Is it possible to leverage github actions to generate binaries for all platforms? triggered by tagging the main branch?

simulot avatar Jun 21 '24 15:06 simulot

@pkking what is the benefit of Docker to begin with? Here is why I believe Docker images are not needed:

  1. This app does not run as a service/daemon (unless I am missing something?)
  2. This app has zero dependencies, literally a single statically linked binary.
  3. Putting this binary into a container would end up with...the same binary, just with extra steps. :shrug:

erkexzcx avatar Jun 21 '24 17:06 erkexzcx

Why would someone need Docker image for this?. 🤔

Also, why would you use anything other than scratch as base image? My example (that also needs ca-certificates for Golang): https://github.com/erkexzcx/valetudopng/blob/main/Dockerfile

Hi @erkexzcx, my use case is i want to run immich-go in cronjob, each time the job scheduled, will need to upgrade immich and immich-go both firstly and i didnt find a one click upgrade script except using docker, so that's it :)

pkking avatar Jun 22 '24 01:06 pkking

@simulot you can also use ghcr.io (GitHub's registry) instead of Dockerhub.

      - name: Login to GitHub Container Registry
        uses: docker/login-action@v3
        with:
          registry: ghcr.io
          username: ${{ github.actor }}
          password: ${{ secrets.GITHUB_TOKEN }}

https://github.com/simulot/immich-go/pull/306/files#diff-551d1fcf87f78cc3bc18a7b332a4dc5d8773a512062df881c5aba28a6f5c48d7R47-R53 this PR will push the image to both dockerhub and ghcr

pkking avatar Jun 22 '24 01:06 pkking

Hi @erkexzcx, my use case is i want to run immich-go in cronjob, each time the job scheduled, will need to upgrade immich and immich-go both firstly and i didnt find a one click upgrade script except using docker, so that's it :)

That's legit. But this will put the maintenance and the support for this release on me. I don't master the docker environnement enough for providing a good support.

What if you release the docker image on your own, synchronized with immich-go release? I'll add a section in the readme file that points to your repo?

simulot avatar Jun 22 '24 09:06 simulot

my use case is i want to run immich-go in cronjob, each time the job scheduled

Instead of using Docker....

0 3 * * * docker run -it simulot/immich-go <args>

you can totally use binary just in a same way...

0 3 * * * /usr/local/bin/immich-go <args>

@simulot not that it would bring more maintenance, but there is barely any benefit of providing Docker image for a tool like this. Imagine this would have been nodejs project - totally makes sense to provide Docker image as user wouldn't need to install nodejs and with Docker you can ensure that user uses the right nodejs version, the right configuration, you provide isolated and consistent environment etc. With Golang, it's just a single binary, no external deps and personally I don't see any reason to provide Docker image.

Certain services, including the ones that I (barelly) maintain, they are running as services/daemons and even tho they can be used as regular binaries, I also provide Docker images because it's way more convenient to have all your services at your home server to be running under a single "roof" which is Docker service. But again - those are services/daemons that run 24/7, while this tool is supposed to be ran once and that's it.

erkexzcx avatar Jun 22 '24 09:06 erkexzcx

@erkexzcx your point is valid. I have started immich-go exactly because I wouldn't install node.js and all other dependencies on my laptop. A golang program is a perfect fit for that need.

Some users are using immich-go not for the google photos import but for synchronise regularly immich with another source of photos. They run immich-go as a cron task. Certainly a niche usage. Immich-go is open source, and every one can contribute. So why not. @pkking can maintain the image on is own.

simulot avatar Jun 22 '24 10:06 simulot

my use case is i want to run immich-go in cronjob, each time the job scheduled

Instead of using Docker....

0 3 * * * docker run -it simulot/immich-go <args>

you can totally use binary just in a same way...

0 3 * * * /usr/local/bin/immich-go <args>

@simulot not that it would bring more maintenance, but there is barely any benefit of providing Docker image for a tool like this. Imagine this would have been nodejs project - totally makes sense to provide Docker image as user wouldn't need to install nodejs and with Docker you can ensure that user uses the right nodejs version, the right configuration, you provide isolated and consistent environment etc. With Golang, it's just a single binary, no external deps and personally I don't see any reason to provide Docker image.

Certain services, including the ones that I (barelly) maintain, they are running as services/daemons and even tho they can be used as regular binaries, I also provide Docker images because it's way more convenient to have all your services at your home server to be running under a single "roof" which is Docker service. But again - those are services/daemons that run 24/7, while this tool is supposed to be ran once and that's it.

@erkexzcx Thats right, so thats an XY problem, the actual reason i want to use docker is because i want to upgrade immich-go to latest version before each cronjob started, for immich-go in docker, just

* * * * * sync_photos.sh

then

cat sync_photos.sh
#!/bin/bash
docker rmi  simulot/immich-go
docker run -t --rm  simulot/immich-go upload <path to upload>

Without a docker image, i can't find a way to do this, if anyone provided a one Liner script to achive this, that would be The One as well :)

And yes, @simulot i'd like maintain the docker and github actions stuff is this PR get merged

pkking avatar Jun 22 '24 16:06 pkking

@erkexzcx Thats right, so thats an XY problem, the actual reason i want to use docker is because i want to upgrade immich-go to latest version before each cronjob started, for immich-go in docker, just

* * * * * sync_photos.sh

then

cat sync_photos.sh
#!/bin/bash
docker rmi  simulot/immich-go
docker run -t --rm  simulot/immich-go upload <path to upload>

Without a docker image, i can't find a way to do this, if anyone provided a one Liner script to achive this, that would be The One as well :)

Don't take me for serious here, but it is more than doable... :sweat_smile:

#!/bin/bash

# Exit on any error
set -e

# Find latest version
latest=$(curl -s https://api.github.com/repos/simulot/immich-go/releases/latest | grep tag_name | sed 's/.*"tag_name": "\(.*\)",/\1/')

# Download latest version
curl -L -o /tmp/immich-go_Linux_x86_64.tar.gz "https://github.com/simulot/immich-go/releases/download/$latest/immich-go_Linux_x86_64.tar.gz"

# Extract archive to /tmp
tar -xf /tmp/immich-go_Linux_x86_64.tar.gz -C /tmp/

# Copy binary to /usr/local/bin
sudo cp /tmp/immich-go /usr/local/bin

# Do what you need
immich-go --version

erkexzcx avatar Jun 22 '24 18:06 erkexzcx

Do what you need

immich-go --version

Got it

simulot avatar Jun 23 '24 05:06 simulot

@simulot and @pkking Having a docker image was a great idea. It's totally doable to use @erkexzcx script to update immich-go but it's still a lot more complicated than: docker pull simulot/immich-go

It's also easier than downloading/installing the binaries.

Docker is not only for 24/7 services. It's also great for simple commands ligne immich-go. One you start to use docker, it make sense to use it for everything.

Immich CLI has a docker image. (yes with npm it make even more sense to have one...)

Please reconsider the possibility to merge this PR.

redge76 avatar Sep 12 '24 12:09 redge76

I am OK to maintain docker stuffs, although i didnot use immich-go for a while.

Also i notice some actions already been added to the project to help, thats awesome, if you guys need docker images, im happy to reopen this PR @simulot @erkexzcx @redge76

pkking avatar Sep 15 '24 09:09 pkking

There are some usages I didn't see, there is maintainer. So let's do it

Thanks for help

simulot avatar Sep 15 '24 09:09 simulot

@simulot please enable the CI, also please add a action secret DOCKERHUB_USERNAME and DOCKERHUB_TOKEN, after that, each time a new tag added, the action will push the image to dockerhub and ghcr as simulot/immich-go

NOTE: i add a new CI to prevent the docker image build failed, each time the golang compiler changed, the ci will complain and people should know Dockerfile need some tweak as well ;)

pkking avatar Sep 15 '24 16:09 pkking

In my case i wanted to run it once on my nas without the chance of forgetting any immich-go files on my nas after i was done. This would be the reason why I would prefer docker for this

blaues0cke avatar Jan 14 '25 20:01 blaues0cke

Immich-go consists in one file of 12mb called immich-go. No installation, no dependencies... Does it really need for a docker image?

simulot avatar Jan 14 '25 20:01 simulot

Yes, for a lot of us, it does.

Once you start using Docker to self-host your services, you don't want some "black sheep" service that doesn't use Docker, while all the others do. Docker keeps a separation between the configuration and the runtime environment. Programs inside the container won’t "leak" files onto the host system. I’m sure immich-go is "clean," but I generally don’t want to bother checking. Easy re-installation after a disk crash. All the Docker container configurations are stored in a directory tree, making them easy to back up. If I need to move all the services to another system, I just copy the directory and run a few "docker-compose" commands.

Usually if some project does not have a docker image I try to find another one.... But immich-go has no credible alternative.

redge76 avatar Jan 14 '25 22:01 redge76

Most of users are using immich-go once, on their regular machine.

Anyway, I'll do it soon as it seams not so complicated. But at the moment, I try to get a reliable version.

simulot avatar Jan 16 '25 07:01 simulot

I have cleaned the CI/CD pipe line, released the long waited new version. I'm now ready to include a docker image to the project.

I'm still totally noob concerning Docker image building. So help is welcome.

I would like the following:

  • Understand the need for QEMU and COSIGN
  • The docker image building
  • The documentation in the readme
  • An example of the a docker-compose file.

The go binary is quite self-contained. I think it can run without the share C library when compiled with the static flag.

Thank you for the help

simulot avatar Feb 12 '25 19:02 simulot

I'm still not comfortable with the docker build.

Is it possible to take advantage of the binary build step to build the docker images? AMD64 and ARM64 binaries are ready without the need of QEMU, correct?

simulot avatar Feb 14 '25 21:02 simulot

I'm still not comfortable with the docker build.

Is it possible to take advantage of the binary build step to build the docker images? AMD64 and ARM64 binaries are ready without the need of QEMU, correct?

yes, you can put the container image build step right after the release event, so no need to build the binary twice, but the QEMU is still needed because the image build process can't be cross architecture

pkking avatar Feb 22 '25 00:02 pkking

I'd not expect QEMU to be needed for something like this. Compiling Go for the various architectures can be done without any additional tooling.

If possible, I'd suggest looking into GoReleaser. It also direct support for building Docker containers and pushing them as part of a release.

This would help keep the Github Actions simpler while keeping things a little more standardized compared to other larger Go projects.

Just my 2c :) I can look around for a project that does this and drop a note here when I have time to do so.

Shackelford-Arden avatar Mar 01 '25 21:03 Shackelford-Arden

Just my 2c :) I can look around for a project that does this and drop a note here when I have time to do so.

That would be nice, i'm busy with errors, and github actions are not easy to debug

simulot avatar Mar 01 '25 22:03 simulot