activescott / serverless-aws-static-file-handler

Easily serve static files with the Serverless Framework on AWS Lambda.
MIT License
52 stars 14 forks source link

When deployed on Lambda, image files are not able to be embedded as part of HTML #11

Closed chrisrothwell closed 5 years ago

chrisrothwell commented 5 years ago

Hi, me again! So I got my static website working great using Serverless Offline, but when I deploy it, something weird happens.

My endpoint serves binary files file (e.g. https://8rkav6rax2.execute-api.ap-southeast-1.amazonaws.com/stg/bin/dgwifi.png)

However when these are part of an HTML document (e.g. https://8rkav6rax2.execute-api.ap-southeast-1.amazonaws.com/stg/lp/index.html) they are not loaded. Text files work fine (CSS etc.) but there's something weird with Binary files. I guess its something weird in the headers. I experience a similar problem with fonts (.ttf files)

Have you run into this before? Any advice on how to fix this? My serverless.yml file is following your recommendation.

Thanks in advance!

Cheers, Chris.

activescott commented 5 years ago

Looking into this...

activescott commented 5 years ago

Double check that you have the custom section configured in your serverless.yml as described in the readme under Usage.

Do you have the same problem if you publish the demo in this repository?

If you continue to have issues please do the following:

  1. Post your serverless.yml file here or link to it.
  2. Copy the output after you run serverless deploy and post that here.

For example, I'm using the serverless.yml in the demo of this repository at https://github.com/activescott/serverless-aws-static-file-handler/blob/master/demo/serverless.yml

The complete output after running serverless deploy (I used the shortcut yarn sls deploy):

scott@imacbiggie-ethernet:~/src/serverless-aws-static-file-handler/demo $ yarn sls deploy
yarn run v1.12.1
$ /Users/scott/src/serverless-aws-static-file-handler/demo/node_modules/.bin/sls deploy
Serverless: WARNING: Missing "tenant" and "app" properties in serverless.yml. Without these properties, you can not publish the service to the Serverless Platform.
Serverless: Packaging service...
Serverless: Excluding development dependencies...
Serverless: aws-static-file-handler (BinaryMediaTypes): Adding the following BinaryMediaTypes to RestApi: [ 'image/png', 'image/jpeg', '*/*' ]
Serverless: aws-static-file-handler (BinaryMediaTypes): RestApi BinaryMediaTypes are now: [ 'image/png', 'image/jpeg', '*/*' ]
Serverless: Uploading CloudFormation file to S3...
Serverless: Uploading artifacts...
Serverless: Uploading service .zip file to S3 (946.33 KB)...
Serverless: Validating template...
Serverless: Updating Stack...
Serverless: Checking Stack update progress...
................
Serverless: Stack update finished...
Service Information
service: static-file-handler-demo-proxy
stage: dev
region: us-east-1
stack: static-file-handler-demo-proxy-dev
api keys:
  None
endpoints:
  GET - https://1vqkcybof7.execute-api.us-east-1.amazonaws.com/dev/
  GET - https://1vqkcybof7.execute-api.us-east-1.amazonaws.com/dev/png
  GET - https://1vqkcybof7.execute-api.us-east-1.amazonaws.com/dev/jpg
  GET - https://1vqkcybof7.execute-api.us-east-1.amazonaws.com/dev/binary/{pathvar+}
functions:
  html: static-file-handler-demo-proxy-dev-html
  png: static-file-handler-demo-proxy-dev-png
  jpg: static-file-handler-demo-proxy-dev-jpg
  binary: static-file-handler-demo-proxy-dev-binary
layers:
  None
Serverless: Removing old service artifacts from S3...
✨  Done in 40.11s.
chrisrothwell commented 5 years ago

Hi, I think my custom types are set correctly, but I noticed in your sls deploy I see a couple of lines which I don't see in mine.

Serverless: aws-static-file-handler (BinaryMediaTypes): Adding the following BinaryMediaTypes to RestApi: [ 'image/png', 'image/jpeg', '*/*' ]
Serverless: aws-static-file-handler (BinaryMediaTypes): RestApi BinaryMediaTypes are now: [ 'image/png', 'image/jpeg', '*/*' ]

I'll try publishing your demo version and see if I get the same issue. The only things I can think that are different is that I'm deploying in a VPC. When I check the headers in a browser from localhost vs the deployed version, I see some extra headers added by cloudfront, but other than that it looks the same. It's suprising that the BIN files can load standalone but they don't load as part of an HTML site :-/

In my serverless YAML file I have the following:

service: digiwifi-prod
app: digiwifi-prod
tenant: rothwellchris

custom:
  apigwBinary:
    types:
      - 'image/jpeg'
      - 'image/png'
      - 'application/font-sfnt'

provider:
  name: aws
  runtime: nodejs8.10
  stage: ${opt:stage}
  profile: digiwifiprod
  region: ap-southeast-1
  vpc:
   securityGroupIds:
    - sg-070b614ff36b19ff0
   subnetIds:
    - subnet-0365a9a7e54c9407f

  iamRoleStatements:

functions:
  staticfiles:
    handler: www/handler.staticfile
    events:
      - http:
          path: lp/{htmlpath+}
          method: get
      - http:
          path: bin/{bin+}
          method: get

resources:

plugins:
  - serverless-offline
  - serverless-apigw-binary
  - serverless-aws-static-file-handler

and my sls deploy shows the following:

C:\Users\christop\Documents\Stuff\RET\gitlabprojects\wifi-backend>sls deploy --stage stg
Serverless: Packaging service...
Serverless: Excluding development dependencies...
Serverless: Uploading CloudFormation file to S3...
Serverless: Uploading artifacts...
Serverless: Uploading service .zip file to S3 (37.37 MB)...
Serverless: Validating template...
Serverless: Updating Stack...
Serverless: Checking Stack update progress...
......................................
Serverless: Stack update finished...
Service Information
service: digiwifi-prod
stage: stg
region: ap-southeast-1
stack: digiwifi-prod-stg
api keys:
  None
endpoints:
  GET - https://xx1myjdmcc.execute-api.ap-southeast-1.amazonaws.com/stg/lp/{htmlpath+}
  GET - https://xx1myjdmcc.execute-api.ap-southeast-1.amazonaws.com/stg/bin/{bin+}
functions:
  staticfiles: digiwifi-prod-stg-staticfiles
layers:
  None
chrisrothwell commented 5 years ago

OK, after forking the demo project and deploying it (after removing the error thrown by validateLambdaProxyIntegration) this seems to work on Lambda :)

Seems I had made a few mistakes:

However upgrading to v2 of the package introduced a few other problems which I worked around:

Nevertheless, great work and I'll definitely be using this moving forward :)

activescott commented 5 years ago

Glad you got it working. The newer version of the package definitely made it more robust and it specifically added the support for the custom.apigwBinary section and using the serverless-aws-static-file-handler/plugins/BinaryMediaTypes plugin was that was probably the trick to making it work.

I didn't follow your issue about takes the htmlpath propname from the event. Sounds like you got it working though, but if you think there is a bug please submit a reproducible repo and I'll investigate. Or better yet submit a pull request with a fix!

Also sounds like something was unclear about error handling. Please enter an issue and help me understand how to make it better.

Thanks for your feedback!!