Skip to content
This repository has been archived by the owner on Dec 18, 2018. It is now read-only.

Commit

Permalink
docs(*): Document how to build with an example Dockerfile (#25)
Browse files Browse the repository at this point in the history
Provide a Dockerfile which can build a lambda for Amazon Linux. Add example for
testing provided Dockerfile. Update README to describe how to build and how to
setup the lambda.
  • Loading branch information
dbcfd authored and LegNeato committed Sep 1, 2018
1 parent 33481f7 commit 333a728
Show file tree
Hide file tree
Showing 7 changed files with 154 additions and 1 deletion.
4 changes: 4 additions & 0 deletions .dockerignore
@@ -0,0 +1,4 @@
target
LICENSE
README.md
.travis.yml
3 changes: 3 additions & 0 deletions .gitignore
Expand Up @@ -14,3 +14,6 @@ Cargo.lock

# Test artifacts
*.rmeta

.idea
*.iml
24 changes: 23 additions & 1 deletion README.md
Expand Up @@ -132,8 +132,30 @@ fn main() {
```

### Deploy
Note: These instructions will produce a MUSL binary of your rust code. If you are looking for non-MUSL binaries, you might try [docker-lambda](https://github.com/lambci/docker-lambda).

To deploy on AWS lambda, you will need a zip file of your binary, built against amazonlinux with MUSL. A docker file is provided as an example, which will work for single project binaries that need OpenSSL. It is based off of [rust-musl-builder](https://github.com/emk/rust-musl-builder).

docker pull amazonlinux
docker build --force-rm -t aws-lambda:latest --build-arg SRC=example -f docker/dockerfile .
docker run -v /tmp/artifacts:/export --rm aws-lambda:latest

Create your lambda function, uploading your zip file. Change your runtime to `go 1.x` and set your handler function to the name of your application as defined in your Cargo.toml.

If using SSL functionality (e.g. rusoto), add the following environment variables

SSL_CERT_DIR=/etc/ssl/certs
SSL_CERT_FILE=/etc/ssl/certs/ca-bundle.crt

If you are still running into SSL issues, you may need to modify your application per https://github.com/emk/rust-musl-builder#making-openssl-work.

If you are using `error_chain` in your rust code, you will also have to disable default features for a musl build. Add the following to your Cargo.toml

#Error chain users will have to disable default-features for musl
[dependencies.error-chain]
version = "~0.12"
default-features = false

TBD

### Troubleshooting

Expand Down
3 changes: 3 additions & 0 deletions docker/cargo_config
@@ -0,0 +1,3 @@
[build]
# Target musl-libc by default when running Cargo.
target = "x86_64-unknown-linux-musl"
98 changes: 98 additions & 0 deletions docker/dockerfile
@@ -0,0 +1,98 @@
FROM amazonlinux:latest AS builder

ARG SRC

ENV BUILD_DIR=/build \
OUTPUT_DIR=/output \
RUST_BACKTRACE=1 \
RUSTUP_HOME=/usr/local/rustup \
CARGO_HOME=/usr/local/cargo \
PATH=/usr/local/cargo/bin:$PATH \
PREFIX=/musl \
MUSL_VERSION=1.1.19 \
OPENSSL_VERSION=1.1.0i

RUN mkdir -p /usr/local/cargo/bin \
&& mkdir -p $BUILD_DIR \
&& mkdir -p $OUTPUT_DIR \
&& mkdir -p $PREFIX

RUN curl https://sh.rustup.rs -sSf | sh -s -- --default-toolchain stable -y

ENV BUILD_TARGET=x86_64-unknown-linux-musl

RUN rustup target add $BUILD_TARGET

RUN yum -y groupinstall "Development Tools"

WORKDIR $PREFIX

# Build any dependencies that aren't part of your build, e.g. thrift compiler

# Build Musl
ADD http://www.musl-libc.org/releases/musl-$MUSL_VERSION.tar.gz .
RUN tar -xvzf musl-$MUSL_VERSION.tar.gz \
&& cd musl-$MUSL_VERSION \
&& ./configure --prefix=$PREFIX \
&& make install \
&& cd ..

# Set environment for musl
ENV CC=$PREFIX/bin/musl-gcc \
C_INCLUDE_PATH=$PREFIX/include/ \
CPPFLAGS=-I$PREFIX/include \
LDFLAGS=-L$PREFIX/lib

# Build OpenSSL
ADD https://www.openssl.org/source/openssl-$OPENSSL_VERSION.tar.gz .

RUN echo "Building OpenSSL" \
&& tar -xzf "openssl-$OPENSSL_VERSION.tar.gz" \
&& cd openssl-$OPENSSL_VERSION \
&& ./Configure no-async no-afalgeng no-shared no-zlib -fPIC --prefix=$PREFIX --openssldir=$PREFIX/ssl linux-x86_64 \
&& make depend \
&& make install

WORKDIR $BUILD_DIR

RUN mkdir .cargo
ADD docker/cargo_config .cargo/config

ENV OPENSSL_DIR=$PREFIX \
OPENSSL_STATIC=true

ADD $SRC/src src
ADD $SRC/Cargo.toml .

RUN cargo build --target $BUILD_TARGET --release

RUN find target/$BUILD_TARGET/release -maxdepth 1 -type f -executable -exec cp '{}' $OUTPUT_DIR \;

FROM amazonlinux:latest AS package

ENV OUTPUT_DIR=/output \
ARTIFACTS_DIR=/artifacts

RUN mkdir -p $ARTIFACTS_DIR

COPY --from=builder $OUTPUT_DIR $ARTIFACTS_DIR

WORKDIR $ARTIFACTS_DIR

RUN yum -y install zip

RUN find . -maxdepth 1 -type f -executable -exec zip aws_lambda.zip '{}' \;

RUN ls -a $ARTIFACTS_DIR

FROM package

ENV ARTIFACTS_DIR=/artifacts \
EXPORT_DIR=/export

RUN mkdir -p $EXPORT_DIR

#Snapshot the directory
VOLUME $EXPORT_DIR

CMD find $ARTIFACTS_DIR -type f -name "aws_lambda.zip" -exec cp '{}' $EXPORT_DIR \;
8 changes: 8 additions & 0 deletions example/Cargo.toml
@@ -0,0 +1,8 @@
[package]
name = "aws-lambda-example"
version = "0.1.0"
authors = ["Danny Browning <danny.browning@protectwise.com>"]

[dependencies]
aws_lambda = { git = "https://github.com/srijs/rust-aws-lambda" }
log = "~0.4"
15 changes: 15 additions & 0 deletions example/src/main.rs
@@ -0,0 +1,15 @@
extern crate aws_lambda;
#[macro_use] extern crate log;

use aws_lambda::event::s3::S3Event;

fn main() {
aws_lambda::logger::init();

// start the runtime, and do
aws_lambda::start(|input: S3Event| {
info!("Event received {:?}", input);

Ok(())
})
}

0 comments on commit 333a728

Please sign in to comment.