aws / aws-sam-cli

CLI tool to build, test, debug, and deploy Serverless applications using AWS SAM
https://aws.amazon.com/serverless/sam/
Apache License 2.0
6.53k stars 1.17k forks source link

Using SAM Local inside docker-compose #55

Open TaylorHG opened 7 years ago

TaylorHG commented 7 years ago

I currently am able to stand up an entire system of REST API microservices using docker-compose. These REST API microservices are written in all kinds of languages and frameworks, none of which are Lambda. This is necessary to run E2E testing for this given large scale application. The inability to use Lambda functions inside this large docker-compose file is the only thing that has stopped be from adding AWS Lambda to our microservices in the past.

SAM Local got super close to fulfilling this goal by at least allowing me to run AWS Lambda functions locally. However, due to the fact that it depends on docker-lambda, I cannot run a docker container inside another docker-container (or at least I really don't want to), so it's kind of a nonstarter.

What my question really boils down to is this: At any point is it planned to be able to run SAM Local inside a docker container, without the major concerns that come along with running docker-in-docker?

sanathkr commented 7 years ago

You can run Docker inside Docker - SAM Local works in a AWS CodeBuild Docker container. Again, there are the caveats you mentioned.

I took a quick look at Compose. It is like SAM Local but working off of a compose.yaml confit file instead of SAM templates. We should be able to write a plugin or extension for Compose, if possible, to use Compose as the mechanism to spin up a new Docker container and pass invokes to it.

You seem to be well experienced with Compose. Are there plugins or extensions that one can write to extend it?

mhart commented 7 years ago

You don't need to necessarily run Docker-in-Docker for this – you could just run it as a sibling couldn't you? ie, with:

docker run -v /var/run/docker.sock:/var/run/docker.sock ...
TaylorHG commented 7 years ago

@sanathkr I definitely wouldn't call myself well experienced with compose, but from what I do know, there isn't a plugin system or anything like that. When Docker made it they kept it pretty bare bones. That being said, it works really well for what it does. I realize a ton of people might not use it, so building out a solution for the people who do, frankly, might spend resources that could be more valuable in other areas.

However, here is where I think it might be valuable to do it anyway: Being able to create an image with an instance of a SAM Local application would open up a ton of gates for how projects made with SAM Local can be consumed. Docker compose is just one instance of a toolset that takes docker images and does stuff with them. I am equally as concerned about the ability for someone to run a SAM Local application in an already dockerized CI environment. I'm seeing more and more engineering teams switching up their CI/CD pipelines to go fully dockerized. Tools like Codeship Pro popping up into existence is a great example of companies trying to push this idea across.

The way I see it, the only way to insure that people can integrate with those kinds of systems is to either a) allow engineers to wrap their SAM Local applications in their own docker applications, or potentially b) add some kind of export that allows sam local to build a docker image that is representative of the application it plans on hosting. Hopefully someone has a better idea, because I have all kinds of worries for each of those options. Who knows, maybe it is just better to create test environments in AWS itself for CI and CD, but depending on the level of effort it takes, I could see this as being a great way to enable docker-heavy engineering teams like mine to start making the move to AWS Lambda.

TaylorHG commented 7 years ago

@mhart I could, totally, and that would work for my use case specifically (I'd still be up shit's creek if I ported over my current Dockerized CI/CD platform, but I can live with hunting another one down or writing some new fancy/ghetto integration layer).

However, I am worried that will reduce the adoptability of SAM Local itself. Not being able to create a plain Docker image for a SAM Local application (without Docker running in Docker) definitely creates a complication, and it is my theory that that complication will stop certain developers from giving SAM Local (and by proxy AWS Lambda) the chance it deserves.

mhart commented 7 years ago

Personally I feel that as more and more tools become containerized, it's actually incumbent on Docker itself to make integration easier – otherwise there are going to be more and more tools that you "can't" use.

And of course by "can't" I mean, you can ☺️. I think in this case that means just documenting that if you want to use SAM Local in Docker, you need to run a container that has (or installs) Docker and start it with -v /var/run/docker.sock:/var/run/docker.sock.

PaulMaddox commented 7 years ago

At the moment SAM Local is very much tied to running via Dockerized Lambda runtimes, and while this discussion is good feedback and useful, it's not something that is going to change anytime soon.

For the time being, if you want to run SAM Local inside Docker, you'll need to map through the docker.sock as @mhart mentioned.

TaylorHG commented 7 years ago

Bummer, but fair enough.

GeoffreyBooth commented 7 years ago

@mhart Do you have an example of how to do what you’ve described, using -v /var/run/docker.sock:/var/run/docker.sock? I tried using https://github.com/cnadiminti/docker-aws-sam-local as such a Docker image, but I couldn’t get it to work in docker-compose (I would always get Unable to import module 'index': Error): https://github.com/cnadiminti/docker-aws-sam-local/issues/1

mhart commented 7 years ago

@GeoffreyBooth the docker image you're talking about has such an example: https://github.com/cnadiminti/docker-aws-sam-local#how-to-use-this-image

GeoffreyBooth commented 7 years ago

@mhart yes, but I can't seem to get it to work: https://github.com/cnadiminti/docker-aws-sam-local/issues/1. Have you?

mhart commented 7 years ago

@GeoffreyBooth that seems like Docker's working – just you don't have your Lambda JS files setup in the correct hierarchy?

mhart commented 7 years ago

It's looking for an index.js file with a handler function (by default)

GeoffreyBooth commented 7 years ago

The files in that folder work fine via sam local start-api, so I think that rules out file path or reference issues.

So have you gotten this to work? I'm just looking for a working example to follow.

mhart commented 7 years ago

@GeoffreyBooth yes, it works just fine for me.

$ git clone https://github.com/cnadiminti/docker-aws-sam-local
$ cd docker-aws-sam-local
$ make local-start-api
2017/11/01 15:14:53 Connected to Docker 1.32
2017/11/01 15:14:53 Fetching lambci/lambda:nodejs6.10 image for nodejs6.10 runtime...
nodejs6.10: Pulling from lambci/lambda
5aed7bd8313c: Already exists 
d60049111ce7: Already exists 
df2c17ad5e5e: Pull complete 
93956b6301bb: Pull complete 
Digest: sha256:7eb4ced6a15ae3c30effc4ec0cd3aabb2bd57c9a8330b37920c3d5d722d81083
Status: Downloaded newer image for lambci/lambda:nodejs6.10

Mounting index.handler (nodejs6.10) at http://0.0.0.0:3000/ [OPTIONS GET HEAD POST PUT DELETE TRACE CONNECT]
Mounting static files from /Users/michael/github/docker-aws-sam-local/example/public at /

You can now browse to the above endpoints to invoke your functions.
You do not need to restart/reload SAM CLI while working on your functions,
changes will be reflected instantly/automatically. You only need to restart
SAM CLI if you update your AWS SAM template.

2017/11/01 15:15:05 Invoking index.handler (nodejs6.10)
START RequestId: a2d65cf7-aed6-142e-3df2-084097da5f94 Version: $LATEST
2017-11-01T15:15:12.155Z    a2d65cf7-aed6-142e-3df2-084097da5f94    LOG: Received an event
END RequestId: a2d65cf7-aed6-142e-3df2-084097da5f94
REPORT RequestId: a2d65cf7-aed6-142e-3df2-084097da5f94  Duration: 11.39 ms  Billed Duration: 0 ms   Memory Size: 0 MB   Max Memory Used: 28 MB  
GeoffreyBooth commented 7 years ago

@mhart Thanks for your help. I took another look at that Makefile. The docker-compose.yaml that I got to work looks like this:

version: '3'

services:
  aws-sam-local:
    image: cnadiminti/aws-sam-local
    command: local start-api --docker-volume-basedir "$PWD/example" --host 0.0.0.0
    ports:
      - '3000:3000'
    volumes:
      - /var/run/docker.sock:/var/run/docker.sock
      - ./example:/var/opt

So to follow your example:

git clone https://github.com/cnadiminti/docker-aws-sam-local
cd docker-aws-sam-local
# Save the previous code block as docker-compose.yaml in this folder
docker-compose up

And then curl http://localhost:3000/ from another shell:

Creating network "dockerawssamlocal_default" with the default driver
Creating dockerawssamlocal_aws-sam-local_1 ...
Creating dockerawssamlocal_aws-sam-local_1 ... done
Attaching to dockerawssamlocal_aws-sam-local_1
aws-sam-local_1  | 2017/11/01 17:50:39 Connected to Docker 1.32
aws-sam-local_1  | 2017/11/01 17:50:40 Fetching lambci/lambda:nodejs6.10 image for nodejs6.10 runtime...
aws-sam-local_1  | nodejs6.10: Pulling from lambci/lambda
aws-sam-local_1  | Digest: sha256:7eb4ced6a15ae3c30effc4ec0cd3aabb2bd57c9a8330b37920c3d5d722d81083
aws-sam-local_1  | Status: Image is up to date for lambci/lambda:nodejs6.10
aws-sam-local_1  |
aws-sam-local_1  | Mounting index.handler (nodejs6.10) at http://0.0.0.0:3000/ [OPTIONS GET HEAD POST PUT DELETE TRACE CONNECT]
aws-sam-local_1  | Mounting static files from /Users/Geoffrey/Sites/docker-aws-sam-local/example/public at /
aws-sam-local_1  |
aws-sam-local_1  | You can now browse to the above endpoints to invoke your functions.
aws-sam-local_1  | You do not need to restart/reload SAM CLI while working on your functions,
aws-sam-local_1  | changes will be reflected instantly/automatically. You only need to restart
aws-sam-local_1  | SAM CLI if you update your AWS SAM template.
aws-sam-local_1  |
aws-sam-local_1  | 2017/11/01 17:50:44 Invoking index.handler (nodejs6.10)
aws-sam-local_1  | START RequestId: 9aabc9ce-eb6c-126f-af7c-fc501bb46fe3 Version: $LATEST
aws-sam-local_1  | 2017-11-01T17:51:06.009Z 9aabc9ce-eb6c-126f-af7c-fc501bb46fe3    LOG: Received an event
aws-sam-local_1  | END RequestId: 9aabc9ce-eb6c-126f-af7c-fc501bb46fe3
aws-sam-local_1  | REPORT RequestId: 9aabc9ce-eb6c-126f-af7c-fc501bb46fe3   Duration: 8.97 ms   Billed Duration: 0 ms   Memory Size: 0 MB   Max Memory Used: 28 MB

The part that was stumping me was --docker-volume-basedir "$PWD/example". Apparently the $PWD here is the path on the host, e.g. /Users/Geoffrey/Sites/docker-aws-sam-local on my Mac, not /var/opt inside the container as I expected it to be.

rodgersmith commented 6 years ago

@GeoffreyBooth I have followed the sample you detailed here and successfully have gotten docker compose to start an instance of sam local as well as a dockerized instance of nats.io for it to hit. However, The sam local instance cannot seem to make a connection to the nats instance, getting an errconnectionrefused error. Is there anything specific that you must do to get aws sam local to make a connection to other dockerized containers?

GeoffreyBooth commented 6 years ago

I don't think so. This is what I used: https://github.com/cnadiminti/docker-aws-sam-local/pull/2/files

gslopez commented 6 years ago

@codemonkey2012 I have the same problem. Do you find any solution ?

Ghilteras commented 5 years ago

I think this should be reopened as there is enough demand from users to have sam local properly run in docker-compose

terlar commented 5 years ago

What issues are you having? We are using Sam 100% via docker compose at work, I could try to prepare some resources how to set it up if there is interest

dlamb92 commented 5 years ago

@terlar I'm also having issues getting sam local running inside docker compose. Would be very interested to hear more. Particularly struggling with getting other containers to be able to communicate with the aws-sam-local container, when adding depends_on: aws-sam-local to the other container. When trying to invoke a lambda function from the test container with:

lambda_client = boto3.client(
    'lambda',
    endpoint_url="http://localhost:3000",
    use_ssl=False,
    verify=False,
    config=botocore.config.Config(
        signature_version=botocore.UNSIGNED,
        retries={'max_attempts': 0},
    ),
)
lambda_client.invoke(
    FunctionName="HelloWorld",
)

And a docker-compose of:

services:
  awssamlocal:
    image: cnadiminti/aws-sam-local
    command: local start-api --host 0.0.0.0 --docker-volume-basedir foo

    ports:
      - '3000:3000'
    volumes:
      - /var/run/docker.sock:/var/run/docker.sock
      - ./foo:/var/opt

  test:
    image: bar
    build:
      context: .
    depends_on:
      - awssamlocal
    command: -m unittest discover

I just get botocore.exceptions.EndpointConnectionError: Could not connect to the endpoint URL: "http://localhost:3000/2015-03-31/functions/HelloWorld/invocations"

And it's still not clear to me what the value of --docker-volume-basedir is supposed to be (running on linux).

terlar commented 5 years ago

The --docker-volume-basedir needs to be your host (local) system path, I am using $PWD. You might also need to set --docker-network and have a specific docker network to get the communication with other containers working.

A sample service using dynamodb:

services:                                                                                                                             
  api:                                                                                                                                
    image: our-private-tools-image                                            
    volumes:                                                                                                                          
      - /var/run/docker.sock:/var/run/docker.sock:ro                                                                                  
      - .:/var/opt:ro                                                                                                                 
    ports:                                                                                                                            
      - 3000                                                                                                                          
    command: sam local start-api --region eu-west-1 -n .env-sam.json --docker-network my-net -v "$PWD" --host 0.0.0.0 --debug

  dynamodb:
    image: amazon/dynamodb-local:1.11.477
    volumes:
      - dynamodb-data:/data
    ports:
      - 8000
    healthcheck:
      test: ["CMD", "bash", "-c", "cat < /dev/null > /dev/tcp/localhost/8000 || exit 1"]
      interval: 5s
      timeout: 3s
      start_period: 10s
    user: root
    command: -jar DynamoDBLocal.jar -sharedDb -dbPath /data

volumes:                                                                                                                              
  dynamodb-data:

networks:
  default:
    external:
      name: my-net
luispabon commented 5 years ago

The problem with the current way of setting up sam is that it requires docker in docker. I don't see any good reason why this has to be so, and it's making set up way more complicated than it needs to be with a ton of different moving parts that are poorly documented.

Ghilteras commented 5 years ago

@terlar this image https://hub.docker.com/r/cnadiminti/aws-sam-local/ does not support start-lambda command, just invoke and start-api so it's not really ideal, especially if you use Step Functions Local which needs a local Lambda Endpoint.

That being said I tried building my own image and running sam local docker inside docker, but the lambda execution gets so slow that the lambda times out during execution.

I still think this issue should be reopened as there is still traction no official way to do this. Ideally sam local should have an option to not spawn yet another container if you are already running one on your own via compose.

terlar commented 5 years ago

@Ghilteras I do have it working with start-lambda as well, allthough I maintain my own docker image for sam. E.g.

FROM alpine:3.9

ENV AWS_VERSION 1.16.10
ENV SAM_VERSION 0.15.0
ENV CFNLINT_VERSION 0.19.1

RUN apk add --no-cache groff python3 \
  && apk add --no-cache --virtual build-dependencies gcc musl-dev python3-dev \
  && pip3 install aws-sam-cli==${SAM_VERSION} \
  && pip3 install awscli==${AWS_VERSION} \
  && pip3 install cfn-lint==${CFNLINT_VERSION} \
  && pip3 install httpie \
  && apk del build-dependencies

ENV PAGER more
ENV PATH /var/opt/scripts:$PATH

WORKDIR /var/opt
EXPOSE 3000
CMD ["sh", "-c", "while sleep 3600; do :; done"]

With this I was able to run this via docker-compose like:

version: '3.5'
services:
  api:                                                                                                                                
    image: our-private-tools-image                                            
    volumes:                                                                                                                          
      - /var/run/docker.sock:/var/run/docker.sock:ro                                                                                  
      - .:/var/opt:ro                                                                                                                 
    ports:                                                                                                                            
      - 3000                                                                                                                          
    command: sam local start-api --region eu-west-1 -n .env-sam.json --docker-network my-net -v "$PWD" --host 0.0.0.0 --debug

  lambda:
    image: our-private-tools-image
    volumes:
      - /var/run/docker.sock:/var/run/docker.sock:ro
      - .:/var/opt:ro
    ports:
      - 3001
    command: sam local start-lambda --region eu-west-1 -n .env-sam.json --docker-network my-net -v "$PWD" --host 0.0.0.0 --debug

  dynamodb:
    image: amazon/dynamodb-local:1.11.477
    volumes:
      - dynamodb-data:/data
    ports:
      - 8000
    healthcheck:
      test: ["CMD", "bash", "-c", "cat < /dev/null > /dev/tcp/localhost/8000 || exit 1"]
      interval: 5s
      timeout: 3s
      start_period: 10s
    user: root
    command: -jar DynamoDBLocal.jar -sharedDb -dbPath /data

volumes:                                                                                                                              
  dynamodb-data:

networks:
  default:
    external:
      name: my-net

It might be slow, but I haven't seen it slow to the brink of timeouts. My use case is to start this lambda container before running the tests utilizing the lambda for example. One caveat is that I do have my lambda endpoint configurable via environment variable, in production this variable is unset.

E.g. with JS:

const lambda = new AWS.Lambda({ endpoint: config.get('lambda.endpoint') })

This code snippet will return null when the environment variable is not set and hence fallback to the AWS default endpoint, but in test env via docker I set it to something like http://lambda:3001 matching the docker-compose service above.

For completeness sake, if you are using SQS as well, you can add:

  sqs:
    image: roribio16/alpine-sqs
    ports:
      - 9324
      - 9325
    stdin_open: true
    tty: true

We also configure these by environment variables, such as MY_SQS_QUEUE=http://sqs:9324/queue/default, for production you have something like this in your template.yaml (where MySqsQueue is your SQS queue resource):

Globals:
  Function:
    Environment:
      Variables:
        MY_SQS_QUEUE: !Ref MySqsQueue
metaskills commented 4 years ago

I use the HELL out of @mhart's docker images. Basically I use them for base images via docker-compose to lock down SAM to a version, install node since Ruby (in dev) needs that too. I'd very much like to see this re-opened. It would be nice if sam local start-api allowed the current container it was run under to be seen as the runtime.

If that were done, I could stop doing extra leg-work in my Dockerfile to install Lambda Layer dependencies which just increases build/test times. I totally get that the none build containers are there for a purpose since they closely mimic the runtime, but runtime for dev would be great.

Ghilteras commented 4 years ago

The problem here is that there is no official sam image for docker-compose, the fact that it works with a user image and a lot of hacking is not a good solution IMHO

CarlosDomingues commented 3 years ago

Using containers for local development is becoming increasingly common and docker in docker is still a hassle (security and performance issues).

It would be great to simply mount my code directory on an API Gateway container and get it working.

ahonnecke commented 3 years ago

I cannot imagine why this was closed, it's a very valid request and it doesn't even kind of work with the most recent version of anything. The amount of hoops one has to jump through to get this to mostly work is really astounding.

hoffa commented 3 years ago

This might not yet fully address everything, but we publish build images on the ECR Public Gallery (e.g. public.ecr.aws/sam/build-python3.8) that include the SAM CLI.

DoryZi commented 2 years ago

my-net

hi, what network did you create my-net to work? bridge? or what configuration was it ?

terlar commented 2 years ago

This was ages ago, but I don't think I did any configuration, just:

docker network create my-net

Checking the help it defaults to bridge, so that was most likely it.

CynanX commented 1 year ago

Trying to do this recently with the new versions of SAM. I can curl to the lambda (thanks to the newer container-host and container-host-interface parameters, but the lambda is 'not found'.

template.yaml:

AWSTemplateFormatVersion: '2010-09-09'
Transform: AWS::Serverless-2016-10-31
Description: >
  sam-app

  Sample SAM Template for sam-app

Globals:
  Function:
    Timeout: 30
    MemorySize: 512
  Api:
    Cors:
      AllowMethods: "'DELETE,GET,PATCH,POST,PUT,OPTIONS'"
      AllowHeaders: "'content-type','x-api-key','x-amz-security-token','authorization','x-amz-user-agent','x-amz-date'"
      AllowOrigin: "'*'"
      AllowCredentials: "'*'"

Resources:
  AwsApiGateway:
    Type: AWS::Serverless::HttpApi
    Properties:
      Name: Basic AWS API Gateway
      StageName: dev

  MyLambdaFunction:
    Type: "AWS::Serverless::Function"
    Properties:
      Runtime: python3.11
      Handler: lambda_function.lambda_handler
      CodeUri: source_code/
      MemorySize: 250
      Timeout: 30
      Description: 'My test lambda.'
      Policies: AmazonDynamoDBFullAccess
      Environment:
        Variables:
          sam_local_environment: 'true'
      Events:
        Api:
          Type: HttpApi
          Properties:
            ApiId: !Ref AwsApiGateway
            Path: /{proxy+}/hello
            Method: GET

docker-compose.yaml:

version: "3.5"

services:
  aws-sam-local:
    build:
      context: .
      dockerfile: Dockerfile-sam
    command: sam local start-api --host=0.0.0.0 --container-host=host.docker.internal --container-host-interface=127.0.0.1 --debug
    ports:
      - '3000:3000'
    volumes:
      - /var/run/docker.sock:/var/run/docker.sock:ro
      - .:/var/opt:ro
    links:
      - "dynamodb:dynamo-local"
    environment:
      SAM_CLI_CONTAINER_CONNECTION_TIMEOUT: 30
      sam_local_environment: 'true'
  dynamodb:
    image: amazon/dynamodb-local:latest
    ports:
      - '8000:8000'
    healthcheck:
      test: ["CMD", "bash", "-c", "cat < /dev/null > /dev/tcp/localhost/8000 || exit 1"]
      interval: 5s
      timeout: 3s
      start_period: 10s
    user: root
    command: -jar DynamoDBLocal.jar -inMemory -sharedDb

Dockerfile-sam:

FROM public.ecr.aws/docker/library/docker

RUN apk update && \
    apk add gcc py-pip python3-dev libffi-dev musl-dev && \
    pip install --upgrade pip setuptools wheel && \
    pip install --upgrade aws-sam-cli

WORKDIR /var/opt

ENTRYPOINT []
CMD ["/bin/bash"]

Output:

test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,541 | Config file location: /var/opt/samconfig.toml
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,542 | Loading configuration values from [default.['local', 'start-api'].parameters] (env.command_name.section) in config file at '/var/opt/samconfig.toml'...
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,542 | Configuration values successfully loaded.
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,542 | Configuration values are: {'stack_name': 'sam-pipeline-app', 'warm_containers': 'EAGER'}
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,546 | Using SAM Template at /var/opt/.aws-sam/build/template.yaml
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,558 | Using config file: samconfig.toml, config environment: default
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,558 | Expand command line arguments to:
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,558 | --template_file=/var/opt/.aws-sam/build/template.yaml --host=0.0.0.0 --container_host=host.docker.internal --container_host_interface=127.0.0.1 --port=3000 --static_dir=public --layer_cache_basedir=/root/.aws-sam/layers-pkg --warm_containers=EAGER
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,610 | local start-api command is called
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,613 | No Parameters detected in the template
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,621 | There is no customer defined id or cdk path defined for resource AwsApiGateway, so we will use the resource logical id as the resource id
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,621 | Sam customer defined id is more priority than other IDs. Customer defined id for resource CodePipelineLambdaFunction is CodePipelineLambdaFunction
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,621 | 0 stacks found in the template
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,621 | No Parameters detected in the template
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,626 | There is no customer defined id or cdk path defined for resource AwsApiGateway, so we will use the resource logical id as the resource id
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,626 | Sam customer defined id is more priority than other IDs. Customer defined id for resource CodePipelineLambdaFunction is CodePipelineLambdaFunction
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,626 | 2 resources found in the stack
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,626 | Found Serverless function with name='CodePipelineLambdaFunction' and CodeUri='CodePipelineLambdaFunction'
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,626 | --base-dir is not presented, adjusting uri CodePipelineLambdaFunction relative to /var/opt/.aws-sam/build/template.yaml
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,627 | watch resource /var/opt/.aws-sam/build/template.yaml
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,627 | Create Observer for resource /var/opt/.aws-sam/build/template.yaml with recursive True
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,628 | watch resource /var/opt/.aws-sam/build/template.yaml's parent /var/opt/.aws-sam/build
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,628 | Create Observer for resource /var/opt/.aws-sam/build with recursive False
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,631 | Initializing the lambda functions containers.
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,632 | Async execution started
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,632 | Invoking function functools.partial(<function InvokeContext._initialize_all_functions_containers.<locals>.initialize_function_container at 0xffff9cc756c0>, Function(function_id='CodePipelineLambdaFunction', name='CodePipelineLambdaFunction', functionname='CodePipelineLambdaFunction', runtime='python3.11', memory=250, timeout=30, handler='lambda_function.lambda_handler', imageuri=None, packagetype='Zip', imageconfig=None, codeuri='/var/opt/.aws-sam/build/CodePipelineLambdaFunction', environment={'Variables': {'SAM_CLI_TELEMETRY': 0, 'sam_local_environment': 'true', 'configured_environments': '{"proteus": ["DEV", "UAT", "PROD"]}'}}, rolearn=None, layers=[], events={'Api': {'Type': 'HttpApi', 'Properties': {'ApiId': 'AwsApiGateway', 'Path': '/{proxy+}/api/v10/deployments/progress', 'Method': 'GET'}}}, metadata={'SamResourceId': 'CodePipelineLambdaFunction'}, inlinecode=None, codesign_config_arn=None, architectures=None, function_url_config=None, function_build_info=<FunctionBuildInfo.BuildableZip: ('BuildableZip', 'Regular ZIP function which can be build with SAM CLI')>, stack_path='', runtime_management_config=None))
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,633 | Waiting for async results
test-lambda-aws-sam-local-1  | 2023-09-13 14:06:59,635 | Loading AWS credentials from session with profile 'None'
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:01,660 | Resolving code path. Cwd=/var/opt/.aws-sam/build, CodeUri=/var/opt/.aws-sam/build/CodePipelineLambdaFunction
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:01,661 | Resolved absolute path to code is /var/opt/.aws-sam/build/CodePipelineLambdaFunction
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:05,888 | watch resource /var/opt/.aws-sam/build/CodePipelineLambdaFunction
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:05,889 | Create Observer for resource /var/opt/.aws-sam/build/CodePipelineLambdaFunction with recursive True
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:06,234 | watch resource /var/opt/.aws-sam/build/CodePipelineLambdaFunction's parent /var/opt/.aws-sam/build
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:06,238 | Code /var/opt/.aws-sam/build/CodePipelineLambdaFunction is not a zip/jar file
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:09,798 | Local image is up-to-date
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:09,819 | Using local image: public.ecr.aws/lambda/python:3.11-rapid-x86_64.
test-lambda-aws-sam-local-1  |
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:09,819 | Mounting /var/opt/.aws-sam/build/CodePipelineLambdaFunction as /var/task:ro,delegated, inside runtime container
test-lambda-aws-sam-local-1  |
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:10,008 | Async execution completed
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:10,008 | Containers Initialization is done.
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:10,009 | Detected Inline Swagger definition
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:10,009 | Parsing Swagger document using 3.0 specification
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:10,009 | Lambda function integration not found in Swagger document at path='/{proxy+}/api/v10/deployments/progress' method='get'
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:10,009 | Found '0' APIs in resource 'AwsApiGateway'
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:10,009 | Found '0' authorizers in resource 'AwsApiGateway'
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:10,009 | Found '1' API Events in Serverless function with name 'CodePipelineLambdaFunction'
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:10,009 | Removed duplicates from '1' Explicit APIs and '0' Implicit APIs to produce '1' APIs
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:10,009 | 1 APIs found in the template
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:10,010 | Mounting CodePipelineLambdaFunction at http://0.0.0.0:3000/{proxy+}/api/v10/deployments/progress [GET]
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:10,010 | You can now browse to the above endpoints to invoke your functions. You do not need to restart/reload SAM CLI while working on your functions, changes will be reflected instantly/automatically. If you used sam build before running local commands, you will need to re-run sam build for the changes to be picked up. You only need to restart SAM CLI if you update your AWS SAM template
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:10,010 | Localhost server is starting up. Multi-threading = True
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:10 WARNING: This is a development server. Do not use it in a production deployment. Use a production WSGI server instead.
test-lambda-aws-sam-local-1  |  * Running on all addresses (0.0.0.0)
test-lambda-aws-sam-local-1  |  * Running on http://127.0.0.1:3000
test-lambda-aws-sam-local-1  |  * Running on http://192.168.208.3:3000
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:10 Press CTRL+C to quit
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:25,763 | Constructed Event Version 2.0 to invoke Lambda. Event: {'version': '2.0', 'routeKey': 'GET /{proxy+}/api/v10/deployments/progress', 'rawPath': '/pdi/api/v10/deployments/progress', 'rawQueryString': '', 'cookies': [], 'headers': {'Host': '127.0.0.1:3000', 'User-Agent': 'curl/8.1.2', 'Accept': '*/*', 'X-Forwarded-Proto': 'http', 'X-Forwarded-Port': '3000'}, 'requestContext': {'accountId': '123456789012', 'apiId': '1234567890', 'http': {'method': 'GET', 'path': '/pdi/api/v10/deployments/progress', 'protocol': 'HTTP/1.1', 'sourceIp': '192.168.208.1', 'userAgent': 'Custom User Agent String'}, 'requestId': 'a9fd017e-b467-483e-bd6d-d189c47fedd9', 'routeKey': 'GET /{proxy+}/api/v10/deployments/progress', 'stage': 'dev', 'time': '13/Sep/2023:14:06:59 +0000', 'timeEpoch': 1694614019, 'domainName': 'localhost', 'domainPrefix': 'localhost'}, 'body': '', 'pathParameters': {'proxy': 'pdi'}, 'stageVariables': None, 'isBase64Encoded': False}
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:25,764 | Found one Lambda function with name 'CodePipelineLambdaFunction'
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:25,764 | Invoking lambda_function.lambda_handler (python3.11)
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:25,764 | Loading AWS credentials from session with profile 'None'
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:27,801 | Resolving code path. Cwd=/var/opt/.aws-sam/build, CodeUri=/var/opt/.aws-sam/build/CodePipelineLambdaFunction
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:27,802 | Resolved absolute path to code is /var/opt/.aws-sam/build/CodePipelineLambdaFunction
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:27,823 | Reuse the created warm container for Lambda function 'CodePipelineLambdaFunction'
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:27,829 | Lambda function 'CodePipelineLambdaFunction' is already running
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:27,838 | Starting a timer for 30 seconds for function 'CodePipelineLambdaFunction'
test-lambda-aws-sam-local-1  | START RequestId: 682c6a92-9078-4dd3-955e-df4c55568130 Version: $LATEST
Traceback (most recent call last):-sam-local-1  | [ERROR] Runtime.ImportModuleError: Unable to import module 'lambda_function': No module named 'lambda_function'
test-lambda-aws-sam-local-1  | END RequestId: 682c6a92-9078-4dd3-955e-df4c55568130
test-lambda-aws-sam-local-1  | REPORT RequestId: 682c6a92-9078-4dd3-955e-df4c55568130   Init Duration: 1.31 ms  Duration: 497.44 ms Billed Duration: 498 ms Memory Size: 250 MB Max Memory Used: 250 MB
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:29,366 | Unable to find Click Context for getting session_id.
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:29,370 | No Content-Type given. Defaulting to 'application/json'.
test-lambda-aws-sam-local-1  | 2023-09-13 14:07:29 192.168.208.1 - - [13/Sep/2023 14:07:29] "GET /pdi/api/v10/deployments/progress HTTP/1.1" 200 -
CynanX commented 1 year ago

I should add, when running outside of docker compose, the lambda responds fine.. so this is related to running it inside docker compose.

CynanX commented 1 year ago

As per usual, spend hours trying to find a solution, post online and then figure it out!

Now working after changing my docker-compose lines to:

 command: sam local start-api -v "${PWD}/.aws-sam/build" --host=0.0.0.0 --container-host=host.docker.internal --container-host-interface=127.0.0.1

and

 volumes:
   - /var/run/docker.sock:/var/run/docker.sock:ro
   - ${PWD}:${PWD}:ro