Running crystal in AWS lambda


#1

Hey,

I wrote a quick blog post how to run a crystal app in AWS Lambda thanks to the newly announced custom runtimes. No rocket science in there, but maybe it helps others. Despite crystal you need serverless, a node-based tool to deploy apps on AWS Lambda and optionally docker to create Linux binaries under osx.

More at https://spinscale.de/posts/2018-12-10-running-crystal-apps-in-aws-lambda/

If you have questions/suggestions, feel free to drop me a note. Once I created a properly tested version of the above, I will put it on github.

–Alex


#2

Happy new year everyone!

I have pushed some sample code and docs, so everyone can run code on AWS Lambda using crystal.

See https://github.com/spinscale/crystal-aws-lambda


#3

to make sure I do not let this thread die… I changed the above link so, that you can now use the repo as a library, so all you need is to write code like this

require "lambda_builder"

runtime = LambdaBuilder::Runtime.new

runtime.register_handler("httpevent",
  ->(input : JSON::Any) {
    req = LambdaBuilder::Util::LambdaHttpRequest.new(input)
    user = req.query_params.fetch("hello", "World")
    response = LambdaBuilder::Util::LambdaHttpResponse.new(200, "Hello #{user} from Crystal")
    # not super efficient, serializing to JSON string and then parsing, simplify this
    return JSON.parse response.to_json
  }
)

runtime.register_handler("scheduledevent",
  ->(input : JSON::Any) {
    runtime.logger.debug("Hello from scheduled event, input: #{input}")
    return JSON.parse "{}"
  }
)

runtime.register_handler("snsevent",
  ->(input : JSON::Any) {
    runtime.logger.info("SNSEvent input: #{input}")
    return JSON.parse "{}"
  }
)

runtime.run

Documentation is not yet awesome… the little one decided, reading her books is more important :slight_smile: so, PRs welcome of course


#4

You should let register_handler receive a block and capture it (&handler), that you you can avoid the unnecessary and verbose JSON::Any and proc syntax everywhere. I’ll try to send you a PR later.


#5

thanks a ton for your input, just refactored this, now one can run

require "lambda_builder"

runtime = LambdaBuilder::Runtime.new

runtime.register_handler("httpevent") do |input|
  req = LambdaBuilder::Util::LambdaHttpRequest.new(input)
  user = req.query_params.fetch("hello", "World")
  response = LambdaBuilder::Util::LambdaHttpResponse.new(200, "Hello #{user} from Crystal")
  # not super efficient, serializing to JSON string and then parsing, simplify this
  JSON.parse response.to_json
end

runtime.register_handler("scheduledevent") do |input|
  runtime.logger.debug("Hello from scheduled event, input: #{input}")
  JSON.parse "{}"
end

runtime.register_handler("snsevent") do |input|
  runtime.logger.info("SNSEvent input: #{input}")
  JSON.parse "{}"
end

runtime.run

#6

Hey @spinscale, have you tried faastruby.io? No need to fiddle with runtimes or any framework, just write:

def handler(event : FaaStRuby::Event) : FaaStRuby::Response
  render text: "Hello, Crystal!\n"
end

Then:
faastruby deploy-to workspace_name

Done. :slight_smile:
More info at https://faastruby.io/getting-started-crystal/

Full Disclosure: I am the creator of FaaStRuby