I'm having a little difficulty understanding PEX-f...
# general
a
I'm having a little difficulty understanding PEX-files and how I can use them to package my python-application but also interact with third-party dependencies. The goal: Create a PEX containing a FastAPI application that I can copy to a Docker image and serve using Gunicorn. Before serving, I must run another third-party dependency (Python Click App) to fetch some secrets from an internal secrets management server. I have the following BUILD file:
Copy code
file(name="secrets-config", source="secrets-config.yml")

pex_binary(
    name="my_service",
    dependencies=["//:root#secrets-handler", "//:root#gunicorn"],
    execution_mode="venv",
)

docker_image(
    name="my_service_docker",
    dependencies=[":secrets-config"],
)
If I don't set an entrypoint for the
pex_binary
I can do
./my_service
inside the container to start a Python REPL in which
secrets-handler
is importable. However,
secrets-handler
is a Click-app which I need to invoke with some parameters. Is this possible, and if so, does anyone see where I'm going wrong? Admittedly, I'm very inexperienced when it comes to packaging in Python. Before migrating to pants I would use
bash -c 'secrets-handler --args ... && gunicorn ...'
in the
command
section of my compose-file, which worked fine as
secrets-handler
and
gunicorn
were both installed by poetry on the local path inside the container. I am using Poetry at the top-level to define my universe of available packages, hence the
//:root
definitions, in case that was unclear.
In case anyone comes across this thread later, I've discovered one possible way to do this:
Copy code
file(name="secrets-config", source="secrets-config.yml")

pex_binary(
    name="gunicorn",
    script="gunicorn",
    dependencies=["//:root#gunicorn", "//:root#uvicorn", "projects/my-service/my_service"],
)

pex_binary(
    name="secrets",
    script="secrets",
    dependencies=["//:root#secrets-handler"],
)

docker_image(
    name="my_service",
    dependencies=[":secrets-config"],
)
By
COPY
-ing
gunicorn.pex
to
/bin/gunicorn
and
secrets.pex
to
/bin/secrets
I can set the docker-compose command to be:
Copy code
command: bash -c '/bin/secrets --args ... && /bin/gunicorn my_service.main:app ...'
This works as I would expect!