<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Jalerson Lima</title>
    <description>The latest articles on DEV Community by Jalerson Lima (@jalerson).</description>
    <link>https://dev.to/jalerson</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F111697%2F29f2cd59-52be-4ab5-a655-ad72e4fbb24a.jpg</url>
      <title>DEV Community: Jalerson Lima</title>
      <link>https://dev.to/jalerson</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/jalerson"/>
    <language>en</language>
    <item>
      <title>Be careful when using error reporting services and serverless functions</title>
      <dc:creator>Jalerson Lima</dc:creator>
      <pubDate>Sat, 31 Aug 2019 07:13:22 +0000</pubDate>
      <link>https://dev.to/jalerson/be-careful-when-using-error-reporting-services-and-serverless-functions-5ei9</link>
      <guid>https://dev.to/jalerson/be-careful-when-using-error-reporting-services-and-serverless-functions-5ei9</guid>
      <description>&lt;p&gt;First, a disclaimer: the problem presented by this blog post happened when using AWS Lambda, Honeybadger, and Ruby. If you're using a different cloud provider, error reporting service and/or programming language, this might not be a problem, &lt;strong&gt;which doesn't mean you shouldn't be aware of it&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;That said, let's start.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://www.honeybadger.io" rel="noopener noreferrer"&gt;Honeybadger&lt;/a&gt; is a popular service for monitoring errors and application uptime like many others. We use it in production for a long time and it's taking care nicely, however, when we started using Honeybadger to report eventual problems in our AWS Lambda functions, a very interesting and unexpected situation happened.&lt;/p&gt;

&lt;p&gt;We started to notice that Honeybadger eventually failed to report errors from our lambda functions, which is very tricky because we rely on it to notifies us when something goes wrong. If there are no notifications, there are no problems, right? We have more important things to do rather than watching the logs in Cloudwatch all over the day.&lt;/p&gt;

&lt;p&gt;This week I was intentionally provoking errors in one particular lambda function, just to check if Honeybadger would report errors, but it didn't.&lt;/p&gt;

&lt;p&gt;According to the Honeybadger documentation (&lt;a href="https://docs.honeybadger.io/lib/ruby/gem-reference/architecture.html" rel="noopener noreferrer"&gt;Architecture Deep-Dive&lt;/a&gt;), the &lt;code&gt;Worker&lt;/code&gt;, which is responsible for pulling &lt;code&gt;Notice&lt;/code&gt; from the &lt;code&gt;Queue&lt;/code&gt;, runs in a different thread to not block the execution of your application while reporting errors. This is great, however, it represents a problem when running in serverless functions.&lt;/p&gt;

&lt;p&gt;The &lt;a href="https://docs.aws.amazon.com/lambda/latest/dg/running-lambda-code.html" rel="noopener noreferrer"&gt;AWS Lambda Execution Context&lt;/a&gt; page says:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;Background processes or callbacks initiated by your Lambda function that did not complete when the function ended resume if AWS Lambda chooses to reuse the execution context. You should make sure any background processes or callbacks in your code are complete before the code exits.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;Which means, when your lambda function finishes the execution, the &lt;code&gt;Worker&lt;/code&gt;, which runs in a different thread, might not have finished sending the error notification.&lt;/p&gt;

&lt;p&gt;Fortunately, the solution is simple. However, it took me some time to find it because, until the moment I'm writing this post, it's not available in Honeybadger documentation (yes, I needed to dive into their code).&lt;/p&gt;

&lt;p&gt;When using the &lt;code&gt;Honeybadger.notify&lt;/code&gt; method, make sure to set &lt;code&gt;sync: true&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Honeybadger.notify(error, sync: true)
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;When using &lt;code&gt;sync: true&lt;/code&gt;, Honeybadger will send the notification immediately, and not pushing it into the queue to be processed by the worker: &lt;a href="https://github.com/honeybadger-io/honeybadger-ruby/blob/master/lib/honeybadger/agent.rb#L161" rel="noopener noreferrer"&gt;https://github.com/honeybadger-io/honeybadger-ruby/blob/master/lib/honeybadger/agent.rb#L161&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Alternatively, you can also call &lt;code&gt;Honeybadger.flush&lt;/code&gt; after calling &lt;code&gt;Honeybadger.notify&lt;/code&gt; to force Honeybadger to send all the notifications: &lt;a href="https://github.com/honeybadger-io/honeybadger-ruby/blob/master/lib/honeybadger/agent.rb#L314" rel="noopener noreferrer"&gt;https://github.com/honeybadger-io/honeybadger-ruby/blob/master/lib/honeybadger/agent.rb#L314&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;If you want to know more about this matter, take a look at this nice article in DZone: &lt;a href="https://dzone.com/articles/multi-threaded-programming-with-aws-lambda" rel="noopener noreferrer"&gt;Multi-Threaded Programming With AWS Lambda&lt;/a&gt;&lt;/p&gt;

</description>
      <category>ruby</category>
      <category>serverless</category>
      <category>lambda</category>
      <category>monitoring</category>
    </item>
    <item>
      <title>Hello Serverless with Jets and Dynamoid</title>
      <dc:creator>Jalerson Lima</dc:creator>
      <pubDate>Tue, 15 Jan 2019 11:09:10 +0000</pubDate>
      <link>https://dev.to/jalerson/hello-serverless-with-jets-and-dynamoid-3fi8</link>
      <guid>https://dev.to/jalerson/hello-serverless-with-jets-and-dynamoid-3fi8</guid>
      <description>&lt;p&gt;&lt;a href="http://rubyonjets.com" rel="noopener noreferrer"&gt;Jets&lt;/a&gt; is a Ruby framework which allows us to easily create and deploy serverless applications to AWS. Jets is adopting several concepts and patterns from Rails, which makes much easier the adoption of serverless architectures by Rails developers.&lt;/p&gt;

&lt;p&gt;Jets is in early stages of maturity, however, its creator, &lt;a href="https://github.com/tongueroo" rel="noopener noreferrer"&gt;Tung Nguyen&lt;/a&gt;, is making a lot of effort to improve the framework and the community around it is growing.&lt;/p&gt;

&lt;p&gt;The application we'll be using as an example is the same previously used in &lt;a href="https://dev.to/jalerson/building-aws-lambdas-for-real-world-using-ruby-and-serverless-framework-2p49"&gt;Building AWS Lambdas for Real World using Ruby and Serverless Framework&lt;/a&gt;: a simple app which will consume data posted by Github. This sample project is available &lt;a href="https://github.com/jalerson/jetsapp" rel="noopener noreferrer"&gt;clicking here&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Like &lt;a href="https://www.youtube.com/watch?v=mLyOj_QD4a4" rel="noopener noreferrer"&gt;Leeroy Jenkins&lt;/a&gt; would say: &lt;em&gt;Alright, time's up! Let's do this!&lt;/em&gt;&lt;/p&gt;

&lt;h1&gt;
  
  
  Prerequisites
&lt;/h1&gt;

&lt;p&gt;Obviously, have Jets installed is necessary. If you don't have, go to your terminal and install it:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;$ gem install jets
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;


&lt;p&gt;In order to deploy your app to AWS, you'll need to have your AWS keys set up in &lt;code&gt;~/.aws/credentials&lt;/code&gt;. In case you don't have, please refer to &lt;a href="https://docs.aws.amazon.com/cli/latest/userguide/cli-configure-files.html" rel="noopener noreferrer"&gt;Configuration and Credential files&lt;/a&gt;.&lt;/p&gt;
&lt;h1&gt;
  
  
  Creating our Jets app
&lt;/h1&gt;

&lt;p&gt;Since we're not interested in assets serving, let's create our app using API mode:&lt;br&gt;
&lt;/p&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;$ jets new jetsapp --mode=api
$ cd jetsapp
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;


&lt;p&gt;By default, Jets supports &lt;a href="http://rubyonjets.com/docs/database-activerecord/" rel="noopener noreferrer"&gt;ActiveRecord&lt;/a&gt; and DynamoDB via &lt;a href="https://github.com/tongueroo/dynomite" rel="noopener noreferrer"&gt;Dynomite&lt;/a&gt;. However, I'm interested in something different here: I want to use &lt;a href="https://github.com/Dynamoid/dynamoid" rel="noopener noreferrer"&gt;Dynamoid&lt;/a&gt;, which is a stable and mature Ruby ORM for AWS DynamoDB.&lt;/p&gt;

&lt;p&gt;That said, let's update our Gemfile to add Dynamoid and remove mysql2.&lt;br&gt;
&lt;/p&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;# gem "mysql2", "~&amp;gt; 0.5.2"
gem 'dynamoid', '~&amp;gt; 3.1.0'
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;


&lt;p&gt;Don't forget to update your dependencies by executing &lt;code&gt;bundle install&lt;/code&gt; in your terminal.&lt;/p&gt;

&lt;p&gt;Dynamoid requires AWS credentials in order to properly connect to DynamoDB. If we were in Rails, we could easily do it using &lt;a href="https://guides.rubyonrails.org/configuring.html#initialization-events" rel="noopener noreferrer"&gt;initializers&lt;/a&gt;. Fortunately, &lt;a href="http://rubyonjets.com/docs/initializers/" rel="noopener noreferrer"&gt;initializers are one of the cool stuff adopted by Jets&lt;/a&gt; from Rails.&lt;/p&gt;

&lt;p&gt;So, we just need to create &lt;code&gt;config/initializers/dynamoid.rb&lt;/code&gt; and add the following:&lt;/p&gt;


&lt;div class="ltag_gist-liquid-tag"&gt;
  
&lt;/div&gt;



&lt;p&gt;We're configuring the &lt;code&gt;namespace&lt;/code&gt;, which is optional (default is &lt;code&gt;dynamoid&lt;/code&gt;) and it's a prefix for our DynamoDB tables. We're also setting our AWS access key id, secret key and region. Obviously, we're keeping all these data in our environment variables.&lt;/p&gt;

&lt;p&gt;Last but not least, we're creating DynamoDB tables based on the models we have in &lt;code&gt;app/models&lt;/code&gt;. Don't worry about the recreation of these tables when you perform a redeploy: Dynamoid takes care of it.&lt;/p&gt;

&lt;p&gt;Now, let's update our &lt;code&gt;.env&lt;/code&gt; file:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;ACCESS_KEY_ID=&amp;lt;your_access_key_id&amp;gt;
SECRET_ACCESS_KEY=&amp;lt;your_secret_access_key&amp;gt;
REGION=&amp;lt;region&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;


&lt;p&gt;&lt;strong&gt;Important&lt;/strong&gt;: while writing this article, I figured out that are some &lt;a href="https://docs.aws.amazon.com/lambda/latest/dg/current-supported-versions.html#lambda-environment-variables" rel="noopener noreferrer"&gt;environment variable names reserved by AWS&lt;/a&gt;, for instance, &lt;code&gt;AWS_REGION&lt;/code&gt;. So take care to not use them :D&lt;/p&gt;
&lt;h3&gt;
  
  
  Models
&lt;/h3&gt;

&lt;p&gt;Let's continue updating the &lt;code&gt;app/models/application_item.rb&lt;/code&gt;, which is intended to be the parent class of all DynamoDB models. The default &lt;code&gt;ApplicationItem&lt;/code&gt; generated by Jets looks like this:&lt;/p&gt;


&lt;div class="ltag_gist-liquid-tag"&gt;
  
&lt;/div&gt;



&lt;p&gt;Since we're not using &lt;code&gt;Dynomite&lt;/code&gt;, we can remove it and include the &lt;code&gt;Dynamoid::Document&lt;/code&gt;.&lt;/p&gt;


&lt;div class="ltag_gist-liquid-tag"&gt;
  
&lt;/div&gt;


&lt;p&gt;After that, let's build our &lt;code&gt;GithubEvent&lt;/code&gt; model.&lt;/p&gt;


&lt;div class="ltag_gist-liquid-tag"&gt;
  
&lt;/div&gt;


&lt;p&gt;As you can see, we're defining the table name, fields names and types (the default is &lt;code&gt;string&lt;/code&gt;), as well as some validation rules. &lt;a href="https://github.com/Dynamoid/dynamoid#magic-columns" rel="noopener noreferrer"&gt;Dynamoid automatically creates three fields&lt;/a&gt;: &lt;code&gt;id&lt;/code&gt; (string), &lt;code&gt;created_at&lt;/code&gt; (datetime) and &lt;code&gt;updated_at&lt;/code&gt; (datetime).&lt;/p&gt;

&lt;p&gt;Dynamoid also allows use to use: &lt;a href="https://github.com/Dynamoid/dynamoid#default-values" rel="noopener noreferrer"&gt;default field values&lt;/a&gt;, &lt;a href="https://github.com/Dynamoid/dynamoid#custom-types" rel="noopener noreferrer"&gt;custom field types&lt;/a&gt;, &lt;a href="https://github.com/Dynamoid/dynamoid#associations" rel="noopener noreferrer"&gt;associations&lt;/a&gt;, &lt;a href="https://github.com/Dynamoid/dynamoid#validations" rel="noopener noreferrer"&gt;validations&lt;/a&gt;, &lt;a href="https://github.com/Dynamoid/dynamoid#callbacks" rel="noopener noreferrer"&gt;callbacks&lt;/a&gt;, &lt;a href="https://github.com/Dynamoid/dynamoid#sti" rel="noopener noreferrer"&gt;STI (Single Table Inheritance)&lt;/a&gt;, &lt;a href="https://github.com/Dynamoid/dynamoid#object-creation" rel="noopener noreferrer"&gt;record creation&lt;/a&gt;, &lt;a href="https://github.com/Dynamoid/dynamoid#querying" rel="noopener noreferrer"&gt;querying&lt;/a&gt; and much more.&lt;/p&gt;

&lt;h3&gt;
  
  
  Controller
&lt;/h3&gt;

&lt;p&gt;Using Jets, we can create a simple &lt;a href="http://rubyonjets.com/docs/functions/" rel="noopener noreferrer"&gt;lambda function&lt;/a&gt;, or we can build our controller and each action will be transformed into an AWS lambda function. Let's use the second approach just because we can!&lt;/p&gt;


&lt;div class="ltag_gist-liquid-tag"&gt;
  
&lt;/div&gt;


&lt;p&gt;The &lt;code&gt;github&lt;/code&gt; action will be responsible for receiving Github events data. The implementation couldn't be simpler! As you can see, even though we're not implementing a lambda function (which has the &lt;code&gt;event&lt;/code&gt; and &lt;code&gt;context&lt;/code&gt; arguments), the &lt;code&gt;event&lt;/code&gt; variable is available. Btw, &lt;code&gt;params&lt;/code&gt; is also available!&lt;/p&gt;

&lt;h3&gt;
  
  
  Finishing
&lt;/h3&gt;

&lt;p&gt;Let's add the route to our &lt;code&gt;config/routes.rb&lt;/code&gt; file:&lt;/p&gt;


&lt;div class="ltag_gist-liquid-tag"&gt;
  
&lt;/div&gt;


&lt;p&gt;And finally, execute &lt;code&gt;jets deploy&lt;/code&gt; in our terminal to deploy our application. If you don't want to use the default profile to deploy, simply execute &lt;code&gt;AWS_PROFILE=&amp;lt;profile_name&amp;gt; jets deploy&lt;/code&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  Final considerations
&lt;/h2&gt;

&lt;p&gt;I really like the idea of Jets framework: to bring concepts and patterns from Rails world to make our lives easier while migrating to serverless. Although the framework is still not mature for critical applications, I will definitely give it a try.&lt;/p&gt;

&lt;p&gt;Special thanks to &lt;a href="https://twitter.com/tongueroo" rel="noopener noreferrer"&gt;Tung Nguyen&lt;/a&gt; for the awesome support!&lt;/p&gt;

&lt;h1&gt;
  
  
  Looking for a job?
&lt;/h1&gt;

&lt;p&gt;If you're looking for a job and are willing to relocate to Frankfurt (Germany), consider to take a look on the &lt;a href="https://creditshelf-jobs.personio.de/?language=en#department-43306" rel="noopener noreferrer"&gt;positions available at creditshelf&lt;/a&gt;.&lt;/p&gt;

</description>
      <category>serverless</category>
      <category>aws</category>
      <category>jets</category>
      <category>ruby</category>
    </item>
    <item>
      <title>Automating code checks with overcommit</title>
      <dc:creator>Jalerson Lima</dc:creator>
      <pubDate>Sun, 30 Dec 2018 12:22:21 +0000</pubDate>
      <link>https://dev.to/jalerson/automating-code-checks-with-overcommit-1cc3</link>
      <guid>https://dev.to/jalerson/automating-code-checks-with-overcommit-1cc3</guid>
      <description>&lt;p&gt;A few months ago, I was looking for something to prevent me to commit/push code with a debugger call, &lt;code&gt;byebug&lt;/code&gt; for example. Then I found something that I didn't know at the moment: &lt;a href="https://git-scm.com/book/en/v2/Customizing-Git-Git-Hooks" rel="noopener noreferrer"&gt;Git Hooks&lt;/a&gt;. Git Hooks allow running custom scripts when certain actions occur, for example: commit, push, merge, checkout, etc.&lt;/p&gt;

&lt;p&gt;You can put whatever you want in these custom scripts, including to check if you did something &lt;em&gt;not so clever&lt;/em&gt;, for example, push code with a &lt;code&gt;byebug&lt;/code&gt; call. And if you search in Google, you'll find a couple of Git hook scripts to prevent you from doing that.&lt;/p&gt;

&lt;p&gt;But then, as a Ruby developer, I thought: &lt;em&gt;Hey, there's always a gem, right!?&lt;/em&gt;. Right! And it's called &lt;a href="https://github.com/brigade/overcommit" rel="noopener noreferrer"&gt;overcommit&lt;/a&gt;. Overcommit is a Ruby gem which allows you to easily manage and configure your Git hooks.&lt;/p&gt;

&lt;p&gt;To start using overcommit is very simple:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;$ gem install overcommit
$ overcommit --install
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The &lt;code&gt;overcommit --install&lt;/code&gt; command will create a &lt;code&gt;.overcommit.yml&lt;/code&gt; settings file in the current folder and also back up existing hooks. The &lt;a href="https://github.com/brigade/overcommit/blob/master/config/default.yml" rel="noopener noreferrer"&gt;default settings file&lt;/a&gt; includes the following hooks:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;CapitalizedSubject&lt;/strong&gt;: Ensures commit message subject lines start with a capital letter&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;EmptyMessage&lt;/strong&gt;: Checks that the commit message is not empty&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;SingleLineSubject&lt;/strong&gt;: Ensures commit message subject lines are followed by a blank line&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;TextWidth&lt;/strong&gt;: Ensures the number of columns the subject and commit message lines occupy is under the preferred limits&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;TrailingPeriod&lt;/strong&gt;: Ensures commit message subject lines do not have a trailing period&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;AuthorEmail&lt;/strong&gt;: Checks the format of an author's email address&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;AuthorName&lt;/strong&gt;: Ensures that a commit author has a name with at least first and last names&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;BrokenSymlinks&lt;/strong&gt;: Checks for broken symlinks&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;CaseConflicts&lt;/strong&gt;: Checks for files that would conflict in case-insensitive filesystems&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Of course, you can easily disable any of these hooks:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;  CapitalizedSubject:
    enabled: false
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Every time you perform changes in the settings file, you also need to update the signature running &lt;code&gt;overcommit --sign&lt;/code&gt;. You can also disable signature checking by setting &lt;code&gt;verify_signatures: false&lt;/code&gt; in your &lt;code&gt;.overcommit.yml&lt;/code&gt; file. However, please &lt;a href="https://github.com/brigade/overcommit#security" rel="noopener noreferrer"&gt;read the security implications&lt;/a&gt; before doing that.&lt;/p&gt;

&lt;h1&gt;
  
  
  Recommended built-in hooks
&lt;/h1&gt;

&lt;p&gt;The hooks described in this section are the ones I'm currently using and recommend. You can also find, between parenthesis in the hook title, in which action the hooks are being executed.&lt;/p&gt;

&lt;h2&gt;
  
  
  &lt;a href="https://docs.rubocop.org/" rel="noopener noreferrer"&gt;RuboCop&lt;/a&gt; (PreCommit)
&lt;/h2&gt;

&lt;p&gt;Runs RuboCop against any modified Ruby files.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;  RuboCop:
    enabled: true
    on_warn: fail
    problem_on_unmodified_line: ignore
    command: ['bundle', 'exec', 'rubocop']
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;on_warn: fail&lt;/code&gt;: blocks the commit in case of warnings&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;problem_on_unmodified_line: ignore&lt;/code&gt;: ignore problems in lines of code you did not add/change&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  &lt;a href="https://github.com/rubysec/bundler-audit" rel="noopener noreferrer"&gt;BundleAudit&lt;/a&gt; (PreCommit)
&lt;/h2&gt;

&lt;p&gt;Checks for vulnerable versions of gems in Gemfile.lock.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;  BundleAudit:
    enabled: true
    flags: ['--update']
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;flags: ['--update']&lt;/code&gt;: force BundleAudit to update before checking&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  &lt;a href="https://github.com/brigade/overcommit/blob/master/lib/overcommit/hook/pre_commit/bundle_check.rb" rel="noopener noreferrer"&gt;BundleCheck&lt;/a&gt; (PreCommit)
&lt;/h2&gt;

&lt;p&gt;Check if local Gemfile.lock matches Gemfile when either changes, unless &lt;code&gt;Gemfile.lock&lt;/code&gt; is ignored by git.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;  BundleCheck:
    enabled: true
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  &lt;a href="https://github.com/brigade/overcommit/blob/master/lib/overcommit/hook/pre_commit/forbidden_branches.rb" rel="noopener noreferrer"&gt;ForbiddenBranches&lt;/a&gt; (PreCommit and PrePush)
&lt;/h2&gt;

&lt;p&gt;Prevents commits to branches matching one of the configured patterns.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;  ForbiddenBranches:
    enabled: true
    branch_patterns: ['master']
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  &lt;a href="https://github.com/DamirSvrtan/fasterer" rel="noopener noreferrer"&gt;Fasterer&lt;/a&gt; (PreCommit)
&lt;/h2&gt;

&lt;p&gt;Runs &lt;code&gt;fasterer&lt;/code&gt; against any modified Ruby files.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;  Fasterer:
    enabled: true
    exclude:
      - 'vendor/**/*.rb'
      - 'db/schema.rb'
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  CustomScript (PreCommit)
&lt;/h2&gt;

&lt;p&gt;Runs a custom command/script before commit.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;  CustomScript:
    quiet: true
    enabled: true
    command: ['i18n-tasks', 'normalize']
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The previous hook will run &lt;code&gt;i18n-tasks normalize&lt;/code&gt; before commit. &lt;code&gt;normalize&lt;/code&gt; is a task of the &lt;a href="https://github.com/glebm/i18n-tasks" rel="noopener noreferrer"&gt;i18n-tasks&lt;/a&gt; gem.&lt;/p&gt;

&lt;h2&gt;
  
  
  &lt;a href="https://github.com/brigade/overcommit/blob/master/lib/overcommit/hook/post_checkout/bundle_install.rb" rel="noopener noreferrer"&gt;BundleInstall&lt;/a&gt; (PostCheckout, PostMerge and PostRewrite)
&lt;/h2&gt;

&lt;p&gt;Runs &lt;code&gt;bundle install&lt;/code&gt; when a change is detected in the repository's dependencies.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;  BundleInstall:
    enabled: true
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h1&gt;
  
  
  Other (probably) useful built-in hooks
&lt;/h1&gt;

&lt;p&gt;These are the hooks I'm not currently using but I'm willing to give a try.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;a href="http://www.foodcritic.io" rel="noopener noreferrer"&gt;Foodcritic&lt;/a&gt;: linting tool for writing better and safer code&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/railsbp/rails_best_practices" rel="noopener noreferrer"&gt;RailsBestPractices&lt;/a&gt;: code metric tool to check the quality of Rails code&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/brigade/overcommit/blob/master/lib/overcommit/hook/pre_commit/rails_schema_up_to_date.rb" rel="noopener noreferrer"&gt;RailsSchemaUpToDate&lt;/a&gt;: Check to see whether the schema file is in line with the migrations&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/troessner/reek" rel="noopener noreferrer"&gt;Reek&lt;/a&gt;: Code smell detector for Ruby&lt;/li&gt;
&lt;li&gt;
&lt;a href="http://brakemanscanner.org/" rel="noopener noreferrer"&gt;Brakeman&lt;/a&gt;: Vulnerability scanner designed for Rails applications. It statically analyzes code to find security issues&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/brigade/overcommit/blob/master/lib/overcommit/hook/pre_commit/fix_me.rb" rel="noopener noreferrer"&gt;FixMe&lt;/a&gt;: Check for "token" (&lt;code&gt;TODO&lt;/code&gt;, &lt;code&gt;FIXME&lt;/code&gt;, etc.) strings before commit&lt;/li&gt;
&lt;li&gt;
&lt;a href="http://bundler.io/bundle_outdated.html" rel="noopener noreferrer"&gt;BundleOutdated&lt;/a&gt;: List installed gems with newer versions available&lt;/li&gt;
&lt;/ul&gt;

&lt;h1&gt;
  
  
  Looking for a job?
&lt;/h1&gt;

&lt;p&gt;If you're looking for a job and you live around Frankfurt am Main or you're willing to move, we have positions available at &lt;a href="https://creditshelf.com" rel="noopener noreferrer"&gt;creditshelf&lt;/a&gt;. &lt;strong&gt;All positions available for English speakers&lt;/strong&gt;.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://creditshelf-jobs.personio.de/job/26809" rel="noopener noreferrer"&gt;Ruby on Rails Developer&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://creditshelf-jobs.personio.de/job/83994" rel="noopener noreferrer"&gt;DevOps Engineer&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://creditshelf-jobs.personio.de/job/99614" rel="noopener noreferrer"&gt;Frontend Developer&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://creditshelf-jobs.personio.de/job/99754" rel="noopener noreferrer"&gt;Software Quality Engineer&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://creditshelf-jobs.personio.de/job/79886" rel="noopener noreferrer"&gt;Python Developer&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://creditshelf-jobs.personio.de/job/79886" rel="noopener noreferrer"&gt;Fullstack Java/Python Developer&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>git</category>
      <category>hooks</category>
      <category>overcommit</category>
      <category>ruby</category>
    </item>
    <item>
      <title>Building AWS Lambdas for Real World using Ruby and Serverless Framework</title>
      <dc:creator>Jalerson Lima</dc:creator>
      <pubDate>Sun, 09 Dec 2018 12:08:02 +0000</pubDate>
      <link>https://dev.to/jalerson/building-aws-lambdas-for-real-world-using-ruby-and-serverless-framework-2p49</link>
      <guid>https://dev.to/jalerson/building-aws-lambdas-for-real-world-using-ruby-and-serverless-framework-2p49</guid>
      <description>&lt;p&gt;You may be wondering: "&lt;em&gt;Why AWS Lambdas for Real World?&lt;/em&gt;". Well, since &lt;a href="https://aws.amazon.com/blogs/compute/announcing-ruby-support-for-aws-lambda/" rel="noopener noreferrer"&gt;Amazon announced Ruby support for AWS Lambdas&lt;/a&gt; on November 29th, I've been reading about it because I'm a Ruby enthusiastic.&lt;/p&gt;

&lt;p&gt;Currently, you can easily find several blog posts and tutorials explaining how to build your own Lambda functions in Ruby, most of them using the famous Hello World as example, which is good as a starting point, but, let's be honest, you won't need to build something as simple as a Hello World. You will need to face real-world issues regarding automated testing, using other services, building/deploying, handling dependencies, etc.&lt;/p&gt;

&lt;p&gt;In this post, I'd like to share some ideas with those who, like me, started to reach a bit deeper in this matter, and discuss how to tackle these real-world issues using Ruby and &lt;a href="https://serverless.com" rel="noopener noreferrer"&gt;Serverless Framework&lt;/a&gt;. Be aware that I'm not claiming that these are the best practices. My goal here is, as I mentioned, share some ideas and start a discussion about them.&lt;/p&gt;

&lt;p&gt;The application that I'll be using as an example to illustrate these ideas is a &lt;a href="https://developer.github.com/apps/" rel="noopener noreferrer"&gt;GitHub App&lt;/a&gt; which will consume data from Github and calculate some metrics. The first step, which will be the focus of this post, is to receive data sent from the Github Webhook and store it in a DynamoDB table.&lt;/p&gt;

&lt;h1&gt;
  
  
  Application structure
&lt;/h1&gt;

&lt;p&gt;The first topic we'll tackle is how to organize your application. Many guides I've found put everything in the root project folder and it's done. Particularly I don't like this approach, I tend to take care on how to organize my projects in multiple subfolders, so, in a long-term, this organization can persist and avoid some headaches. In addition, since you may have several projects, keeping a similar structure will help you to find what you're looking for. If you don't care about it, feel free to jump this section.&lt;/p&gt;

&lt;p&gt;As far as I can see, there are three way to organize your application.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;A single project with all functions and a single serverless framework settings file&lt;/li&gt;
&lt;li&gt;Multiple projects, divided into application modules, each one with its own serverless framework settings file&lt;/li&gt;
&lt;li&gt;Multiple projects, one per function, each one with its own serverless framework settings file&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Particularly I choose the option 2. I believe the first option will result in a big single project, which may be a bit confusing to newcomer developers to start to contribute, however, may be the easiest option to build integration test across different functions. The third option, in the other hand, may turn these integration tests harder to implement, however, newcomer developers would have a smaller project to understand. The option 2 is a bit of both worlds.&lt;/p&gt;

&lt;p&gt;I decided this first module will be called "webhooks". Currently, I'm integrating my application with Github, but in the future, I may decide to integrate it with something else. That said, the Webhooks project has the following structure.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;├── app
    └── functions
        └── github.rb
    └── lib
        └── log.rb
    └── models
        └── github_event.rb
├── spec
    └── functions
        └── github_spec.rb
    └── support
        └── fixtures
            └── github
                └── events
                    └── push.json
    └── spec_helper.rb
├── serverless.yml
├── Gemfile and Gemfile.lock
├── Rakefile
├── Other files like .gitignore, .editorconfig, etc.
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;


&lt;p&gt;As you can see, I didn't lie about organizing my project in several subfolders. If you're a Rails developer, you may notice that I'm using a similar structure of Rails projects. I like the way Rails organize the projects and it's also familiar to me, which make it even easier for me to find something.&lt;/p&gt;

&lt;p&gt;As I mentioned before, most of Hello World examples hold all files in a single root project folder, which makes very easy to the Serverless Framework settings file (&lt;code&gt;serverless.yml&lt;/code&gt;) references the lambda function.&lt;br&gt;
&lt;/p&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;functions:
  myFunctionName:
    handler: &amp;lt;filename_without_extension&amp;gt;.&amp;lt;lambda_function_name&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;


&lt;p&gt;However, in my case, the file which contains my lambda function (&lt;code&gt;app/functions/github.rb&lt;/code&gt;) is inside multiple subfolders and, in addition, is a class method of &lt;code&gt;Webhooks::Github&lt;/code&gt;.&lt;/p&gt;


&lt;div class="ltag_gist-liquid-tag"&gt;
  
&lt;/div&gt;



&lt;p&gt;To reference the &lt;code&gt;handler&lt;/code&gt; class method inside &lt;code&gt;Webhooks::Github&lt;/code&gt;, I needed to set it this way:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;functions:
  github:
    handler: app/functions/github.Webhooks::Github.handler
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;


&lt;p&gt;Which corresponds to the following pattern: &lt;code&gt;path/to/&amp;lt;filename_without_extension&amp;gt;.&amp;lt;module_name&amp;gt;::&amp;lt;class_name&amp;gt;.&amp;lt;method_name&amp;gt;&lt;/code&gt;&lt;/p&gt;
&lt;h1&gt;
  
  
  Automated testing
&lt;/h1&gt;

&lt;p&gt;Next step: automated tests! Serverless is a new way of thinking about how to design applications, so, honestly, took me a while to really understand that a lambda function is as simple to test as a Ruby method. Once again, most of the blog post I found didn't tackle testing. In fact, I believe the only one I found discussing something about it was &lt;a href="https://serverless.com/blog/api-ruby-serverless-framework" rel="noopener noreferrer"&gt;this one&lt;/a&gt;. But here we'll be working with RSpec!&lt;/p&gt;


&lt;div class="ltag_gist-liquid-tag"&gt;
  
&lt;/div&gt;



&lt;p&gt;As you can see in the lines 23 and 29, I'm mocking the response from &lt;code&gt;Aws::DynamoDB::Client&lt;/code&gt;. This is needed because the &lt;code&gt;save!&lt;/code&gt; method of the &lt;code&gt;Webhooks::Github&lt;/code&gt; class is calling the DynamoDB client, and, because I don't have DynamoDB running locally, that's the easiest way to mock success and failure responses.&lt;/p&gt;

&lt;h1&gt;
  
  
  Building and deploying
&lt;/h1&gt;

&lt;p&gt;Ok, let's say your application is ready to be deployed and you're excited to use your lambda functions. Once you have your Serverless framework settings file properly configured, you can deploy your app running &lt;code&gt;sls deploy&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;But, let's be curious and take a look at the file built by the framework: it's a zip file inside the &lt;code&gt;.serverless&lt;/code&gt; folder with the name you set to &lt;code&gt;service&lt;/code&gt; in &lt;code&gt;serverless.yml&lt;/code&gt;. You will see that Serverless framework basically zip all the content of your project, including your tests, which are not needed in a production environment, and, since the dependencies of your project are not inside it, this zip file doesn't contain your project dependencies. So, basically, your lambda function will be successfully deployed but, won't work.&lt;/p&gt;

&lt;p&gt;So, before deploying our project, we need to execute &lt;code&gt;bundle install --deployment&lt;/code&gt; to switch Bundler to &lt;a href="https://bundler.io/man/bundle-install.1.html#DEPLOYMENT-MODE" rel="noopener noreferrer"&gt;deployment mode&lt;/a&gt;. This way, Bundler will create a &lt;code&gt;vendor&lt;/code&gt; folder inside your project with all dependencies. Great! Wait... All dependencies? We don't need development and test dependencies. No problem: &lt;code&gt;bundle install --deployment --without test development&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Great, thanks Bundler! Wait again. As soon as you try to perform changes in the &lt;code&gt;Gemfile&lt;/code&gt;, Bundler won't allow you to do it because you're in the deployment mode. So let's execute &lt;code&gt;bundle install --no-deployment&lt;/code&gt; to switch back to development mode. Once you try to execute &lt;code&gt;bundle install&lt;/code&gt;, you'll notice that Bundler is not taking care of the development and test dependencies anymore. Damn it Bundler!&lt;/p&gt;

&lt;p&gt;Instead of executing just &lt;code&gt;bundle install --no-deployment&lt;/code&gt;, we need to execute &lt;code&gt;bundle install --no-deployment --with test development&lt;/code&gt; to make Bundler take care of test and development dependencies again.&lt;/p&gt;

&lt;p&gt;Three commands to perform a single deploy. That's unacceptable! I really want to execute something similar to &lt;code&gt;app deploy&lt;/code&gt;, and this looks very much like a rake task!&lt;/p&gt;


&lt;div class="ltag_gist-liquid-tag"&gt;
  
&lt;/div&gt;


&lt;p&gt;Now I can simply execute &lt;code&gt;rake deploy&lt;/code&gt;. As you may notice, the first command of my deploy rake task is &lt;code&gt;rm -Rf vendor&lt;/code&gt;, and I'm doing this because I don't want gems that were removed from Gemfile to be there. For a brief moment I tried to use &lt;code&gt;--clean&lt;/code&gt;, but then Bundler started to warn me that's very dangerous, so it scared me a bit.&lt;/p&gt;

&lt;p&gt;Please leave a comment if you know a smarter way to do it. I really appreciate that! I had hope that Serverless framework team would take care of that, but, apparently, &lt;a href="https://github.com/serverless/serverless/issues/5567#issuecomment-444671106" rel="noopener noreferrer"&gt;they won't&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Last but not least, let's take care of the files that shouldn't be included in the deployment package. In this matter, Serverless framework team did a good job because, in the settings file (&lt;code&gt;serverless.yml&lt;/code&gt;), you can set the paths that should be included and excluded from the packaging process.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;package:
  exclude:
    - Gemfile
    - Gemfile.lock
    - Rakefile
    - spec/**
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;h1&gt;
  
  
  Logging
&lt;/h1&gt;

&lt;p&gt;Not a big deal here but I was getting too many logging outputs while testing my code using rspec, which was messing a bit my testing outputs: I just want to see green dots. So, I needed to build something that (a) is simple as logging should be, (b) I don't want to initialize it (&lt;code&gt;Logger.new(STDOUT)&lt;/code&gt;) every time I need to use it, (c) I want to silence it when running tests and (d) I want to see the logs in CloudWatch. That said, I built the following solution.&lt;/p&gt;


&lt;div class="ltag_gist-liquid-tag"&gt;
  
&lt;/div&gt;



&lt;p&gt;In order to log something, I just need to call &lt;code&gt;Log.info "Something to log"&lt;/code&gt;.&lt;/p&gt;

&lt;h1&gt;
  
  
  Next step
&lt;/h1&gt;

&lt;p&gt;Obviously, my next steps are to continue working in my lambda functions, however, I already know that I will need to share some code across different functions, and I want to work on that before building new functions. Fortunately, AWS also provided a solution for that: &lt;a href="https://aws.amazon.com/blogs/aws/new-for-aws-lambda-use-any-programming-language-and-share-common-components/" rel="noopener noreferrer"&gt;AWS Lambda Layers&lt;/a&gt;. But this topic will be the subject of a future post.&lt;/p&gt;

&lt;h1&gt;
  
  
  Looking for a job?
&lt;/h1&gt;

&lt;p&gt;If you're a &lt;a href="https://creditshelf-jobs.personio.de/job/26809" rel="noopener noreferrer"&gt;Ruby on Rails Developer&lt;/a&gt;, &lt;a href="https://creditshelf-jobs.personio.de/job/83994" rel="noopener noreferrer"&gt;DevOps Engineer&lt;/a&gt;, &lt;a href="https://creditshelf-jobs.personio.de/job/79886" rel="noopener noreferrer"&gt;Python Developer&lt;/a&gt; or a &lt;a href="https://creditshelf-jobs.personio.de/job/79886" rel="noopener noreferrer"&gt;Fullstack Java/Python Developer&lt;/a&gt; (&lt;strong&gt;all positions available for English speakers&lt;/strong&gt;), and you live around Frankfurt am Main or you're willing to move, we have positions available at &lt;a href="https://creditshelf.com" rel="noopener noreferrer"&gt;creditshelf&lt;/a&gt;.&lt;/p&gt;

</description>
      <category>ruby</category>
      <category>aws</category>
      <category>lambda</category>
      <category>serverless</category>
    </item>
  </channel>
</rss>
