Using Valve with Docker
Source:vignettes/articles/Using-Valve-with-Docker.Rmd
Using-Valve-with-Docker.Rmd
Valve is intended to make plumber APIs more effective in a production setting. It is recommended to deploy plumber APIs to production in a Docker container (or use Posit Connect if you have company budget and more use cases than a single API).
At the end is an example Dockerfile
that can act as a
reference for you. If you have an existing Dockerfile that you use to
deploy a plumber API, all you need to do to use Valve is to
- install Rust,
- install Valve, and
- change your
ENTRYPOINT
.
Below are the key additional and changes you would have to make.
# Install Rust toolchain & add to the path
RUN apt-get install -y -q build-essential curl
RUN curl https://sh.rustup.rs -sSf | sh -s -- -y
ENV PATH="/root/.cargo/bin:${PATH}"
# Install Valve binary from Github
RUN cargo install valve-rs --no-default-features
# Start Valve app
ENTRYPOINT valve -f /api/plumber.R -h 0.0.0.0 -p 8000 --workers 10 --n-max 10 --check-unused 10 --max-age 300
The first 3 commands install the appropriate system requirement to
install Rust, install Rust, then adds cargo
to the path.
Afterwards, the valve binary is installed from crates.io
.
Lastly, an ENTRYPOINT
is defined to run your plumber
API.
The ENTRYPOINT
is where you have control over how Valve
will scale. Most importantly, the -f
flag should point to a
plumber.R
script—wherever that might be in your Dockerfile.
The host must be 0.0.0.0
for a Docker container.
You can configure the additional arguments as you need. See the README
for more on how these arguments work.
Example Dockerfile
#> FROM rocker/r-ver:4.3.0
#> ENV RENV_CONFIG_REPOS_OVERRIDE https://packagemanager.rstudio.com/cran/latest
#>
#> ENV VALVE_HOST 0.0.0.0
#> ENV VALVE_PORT 8000
#>
#> RUN apt-get update -qq && apt-get install -y --no-install-recommends \
#> libcurl4-openssl-dev \
#> libicu-dev \
#> libsodium-dev \
#> libssl-dev \
#> make \
#> zlib1g-dev \
#> && apt-get clean
#>
#> COPY renv.lock renv.lock
#> RUN Rscript -e "install.packages('renv')"
#> RUN Rscript -e "renv::restore()"
#> COPY plumber.R /api/plumber.R
#>
#> # Install Rust toolchain & add to the path
#> RUN apt-get install -y -q \
#> build-essential \
#> curl
#> RUN curl https://sh.rustup.rs -sSf | sh -s -- -y
#> ENV PATH="/root/.cargo/bin:${PATH}"
#>
#> # Install Valve binary from Github
#> RUN cargo install valve-rs --no-default-features
#>
#> EXPOSE ${VALVE_PORT}
#>
#> # Start Valve app
#> ENTRYPOINT valve -f /api/plumber.R -h $VALVE_HOST -p $VALVE_PORT --workers 10 --n-max 10 --check-unused 10 --max-age 300
The above Dockerfile is included in valve and can be
found via
system.file("docker/Dockerfile", package = "valve")
. It was
build with the included plumber API
system.file("docker/plumber.R", package = "valve")
.
To replciate, copy the files into a directory of your choosing.
Ensure Docker desktop is open. Then build the container with
docker build -t valve:latest .
. Then you can run the
container with:
docker run -p 8000:8000 valve:latest