Skip to content

Migrate to poetry for better dependency management #194

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
wants to merge 4 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 12 additions & 1 deletion .github/workflows/test-on-push-and-pr.yml
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,17 @@ jobs:

steps:
- uses: actions/checkout@v4

- name: Set up Python
uses: actions/setup-python@v5
with:
python-version: '3.12'

- name: Install Poetry
run: |
curl -sSL https://install.python-poetry.org | python3 -
echo "$HOME/.local/bin" >> $GITHUB_PATH

- name: Run 'pr' target
run: make pr

Expand Down Expand Up @@ -45,4 +56,4 @@ jobs:
steps:
- uses: actions/checkout@v4
- name: Run ubuntu integration tests
run: DISTRO=ubuntu make test-integ
run: DISTRO=ubuntu make test-integ
6 changes: 6 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -153,3 +153,9 @@ tmp*.py
deps/artifacts/
deps/aws-lambda-cpp-*/
deps/curl-*/

# local caches
.DS_Store

# local build artifacts
build-artifacts
16 changes: 11 additions & 5 deletions .pre-commit-config.yaml
Original file line number Diff line number Diff line change
@@ -1,7 +1,13 @@
repos:
- repo: https://github.com/python/black
rev: 19.3b0
- repo: local
hooks:
- id: black
language_version: python3.9
exclude_types: ['markdown', 'ini', 'toml', 'rst']
- id: ruff-check
name: ruff
entry: poetry run ruff check --fix
language: system
types: [python]
- id: ruff-format
name: ruff format
entry: poetry run ruff format
language: system
types: [python]
28 changes: 28 additions & 0 deletions Dockerfile.build
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
FROM python:3.9-alpine AS build-image

# Install build dependencies
RUN apk add --no-cache \
build-base \
libtool \
autoconf \
automake \
elfutils-dev \
make \
cmake \
libcurl \
curl \
libstdc++ \
binutils

# Build awslambdaric
ARG RIC_BUILD_DIR="/home/build/"
RUN mkdir -p ${RIC_BUILD_DIR}
WORKDIR ${RIC_BUILD_DIR}
COPY . .
RUN pip install setuptools
RUN curl -sSL https://install.python-poetry.org | python3 - && \
ln -s /root/.local/bin/poetry /usr/local/bin/poetry
RUN make init build

# Keep the built wheel accessible
CMD ["sh", "-c", "echo 'Build complete. Wheel available in /home/build/dist/'"]
26 changes: 26 additions & 0 deletions Dockerfile.rie
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
FROM python:3.9-alpine

RUN apk add --no-cache libstdc++ curl

# Install RIE
RUN curl -Lo /usr/local/bin/aws-lambda-rie https://github.com/aws/aws-lambda-runtime-interface-emulator/releases/latest/download/aws-lambda-rie && \
chmod +x /usr/local/bin/aws-lambda-rie

# Add the pre-built wheel
ADD build-artifacts/*.whl /tmp/

# Install the wheel
RUN pip install /tmp/*.whl

# Copy test handler
COPY tests/integration/test-handlers/echo/app.py /var/task/app.py

# Set environment for local testing
ENV AWS_LAMBDA_RUNTIME_API="127.0.0.1:8080"
ENV LAMBDA_TASK_ROOT="/var/task"
ENV _HANDLER="app.handler"

WORKDIR /var/task

ENTRYPOINT ["/usr/local/bin/aws-lambda-rie"]
CMD ["python", "-m", "awslambdaric", "app.handler"]
71 changes: 45 additions & 26 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,23 @@ target:

.PHONY: init
init:
pip3 install -r requirements/base.txt -r requirements/dev.txt
python3 scripts/dev.py init

.PHONY: test
test: check-format
pytest --cov awslambdaric --cov-report term-missing --cov-fail-under 90 tests
test:
python3 scripts/dev.py test

.PHONY: lint
lint:
python3 scripts/dev.py lint

.PHONY: clean
clean:
python3 scripts/dev.py clean

.PHONY: build
build: clean
python3 scripts/dev.py build

.PHONY: setup-codebuild-agent
setup-codebuild-agent:
Expand All @@ -25,48 +37,55 @@ test-integ: setup-codebuild-agent

.PHONY: check-security
check-security:
bandit -r awslambdaric
poetry run bandit -r awslambdaric

.PHONY: format
format:
black setup.py awslambdaric/ tests/
poetry run ruff format awslambdaric/ tests/

.PHONY: check-format
check-format:
black --check setup.py awslambdaric/ tests/
poetry run ruff format --check awslambdaric/ tests/

.PHONY: check-docstr
check-docstr:
python3 scripts/dev.py check-docstr

# Command to run everytime you make changes to verify everything works
.PHONY: dev
dev: init test

# Verifications to run before sending a pull request
.PHONY: pr
pr: init check-format check-security dev
pr: init check-format check-annotations check-types check-type-usage check-security dev

.PHONY: codebuild
codebuild: setup-codebuild-agent
CODEBUILD_IMAGE_TAG=codebuild-agent DISTRO="$(DISTRO)" tests/integration/codebuild-local/test_all.sh tests/integration/codebuild

.PHONY: clean
clean:
rm -rf dist
rm -rf awslambdaric.egg-info
.PHONY: build-container
build-container:
./scripts/build-container.sh

.PHONY: build
build: clean
BUILD=true python3 setup.py sdist
.PHONY: test-rie
test-rie:
./scripts/test-rie.sh

define HELP_MESSAGE

Usage: $ make [TARGETS]

TARGETS
check-security Run bandit to find security issues.
format Run black to automatically update your code to match our formatting.
build Builds the package.
clean Cleans the working directory by removing built artifacts.
dev Run all development tests after a change.
init Initialize and install the requirements and dev-requirements for this project.
pr Perform all checks before submitting a Pull Request.
test Run the Unit tests.

endef
check-security Run bandit to find security issues.
check-docstr Check docstrings in project using ruff format check.
format Run ruff to automatically format your code.
build Build the package using scripts/dev.py.
clean Cleans the working directory using scripts/dev.py.
dev Run all development tests using scripts/dev.py.
init Install dependencies via scripts/dev.py.
build-container Build awslambdaric wheel in isolated container.
test-rie Test with RIE using pre-built wheel (run build-container first).
pr Perform all checks before submitting a Pull Request.
test Run unit tests using scripts/dev.py.
lint Run all linters via scripts/dev.py.
test-smoke Run smoke tests inside Docker.
test-integ Run all integration tests.
endef
64 changes: 34 additions & 30 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,26 @@ The Python Runtime Interface Client package currently supports Python versions:

## Usage

### Container-Based Builds

For development or when you need to build awslambdaric from source, you can use container-based builds to ensure consistent compilation across different platforms, and native dependencies linking.

```shell script
# Build awslambdaric wheel in a Linux container
make build-container
# Or with poetry (run 'poetry install' first):
poetry run build-container

# Test with RIE using the built wheel
make test-rie
# Or with poetry:
poetry run test-rie
```

This approach builds the C++ extensions in a Linux environment, ensuring compatibility with Lambda's runtime environment regardless of your host OS.

**Note**: Running `make build` (or `poetry run build`) on non-Linux machines will not properly link the native C++ dependencies, resulting in a non-functional runtime client. Always use container-based builds for development.

### Creating a Docker Image for Lambda with the Runtime Interface Client
First step is to choose the base image to be used. The supported Linux OS distributions are:

Expand Down Expand Up @@ -103,38 +123,23 @@ def handler(event, context):

### Local Testing

To make it easy to locally test Lambda functions packaged as container images we open-sourced a lightweight web-server, Lambda Runtime Interface Emulator (RIE), which allows your function packaged as a container image to accept HTTP requests. You can install the [AWS Lambda Runtime Interface Emulator](https://github.com/aws/aws-lambda-runtime-interface-emulator) on your local machine to test your function. Then when you run the image function, you set the entrypoint to be the emulator.

*To install the emulator and test your Lambda function*

1) From your project directory, run the following command to download the RIE from GitHub and install it on your local machine.
To test Lambda functions with the Runtime Interface Client, use the [AWS Lambda Runtime Interface Emulator (RIE)](https://github.com/aws/aws-lambda-runtime-interface-emulator). To test your local changes with RIE (Runtime Interface Emulator):

```shell script
mkdir -p ~/.aws-lambda-rie && \
curl -Lo ~/.aws-lambda-rie/aws-lambda-rie https://github.com/aws/aws-lambda-runtime-interface-emulator/releases/latest/download/aws-lambda-rie && \
chmod +x ~/.aws-lambda-rie/aws-lambda-rie
# Build your current code (do this when you make changes)
# We build on a linux machine to ensure native build dependencies are met
make build-container
# Or with poetry:
poetry run build-container

# Test with RIE (fast, repeatable)
make test-rie
# Or with poetry:
poetry run test-rie

# Test the function
curl -XPOST "http://localhost:9000/2015-03-31/functions/function/invocations" -d '{"message":"test"}'
```
2) Run your Lambda image function using the docker run command.

```shell script
docker run -d -v ~/.aws-lambda-rie:/aws-lambda -p 9000:8080 \
--entrypoint /aws-lambda/aws-lambda-rie \
myfunction:latest \
/usr/local/bin/python -m awslambdaric app.handler
```

This runs the image as a container and starts up an endpoint locally at `http://localhost:9000/2015-03-31/functions/function/invocations`.

3) Post an event to the following endpoint using a curl command:

```shell script
curl -XPOST "http://localhost:9000/2015-03-31/functions/function/invocations" -d '{}'
```

This command invokes the function running in the container image and returns a response.

*Alternately, you can also include RIE as a part of your base image. See the AWS documentation on how to [Build RIE into your base image](https://docs.aws.amazon.com/lambda/latest/dg/images-test.html#images-test-alternative).*


## Development

Expand All @@ -145,7 +150,6 @@ Clone this repository and run:
make init
make build
```

### Running tests

Make sure the project is built:
Expand Down
4 changes: 1 addition & 3 deletions awslambdaric/__init__.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,3 @@
"""
Copyright 2021 Amazon.com, Inc. or its affiliates. All Rights Reserved.
"""
"""Copyright 2021 Amazon.com, Inc. or its affiliates. All Rights Reserved."""

__version__ = "3.1.1"
5 changes: 2 additions & 3 deletions awslambdaric/__main__.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,4 @@
"""
Copyright 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved.
"""
"""Copyright 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved."""

import os
import sys
Expand All @@ -9,6 +7,7 @@


def main(args):
"""Run the Lambda runtime main entry point."""
app_root = os.getcwd()

try:
Expand Down
Loading
Loading