Live debug your AWS Lambda functions in Java

The SLAppForge Debugger for Java consists of two end-user visible components. The first is an AWS Lambda Layer, and the second is a user agent, which executes on the local machine where the favorite IDE runs. The Lambda function connects with the IDE through the SLAppForge Debug Server, and both communication ends are secured with challenge-response based authentication to ensure that only authorized developers can debug a function.

For large enterprises such as financial services or Government organizations that are extremely security-sensitive, SLAppForge shall offer a distribution of its debug server for deployment within a VPC or internal network, which can be further secured with SSL encryption, IP based access filtering and any other forms of additional security.

 

Getting Started

Let’s start with the basic Lambda function in Java with a POJO request and response as used by the AWS Lambda example documentation.

https://docs.aws.amazon.com/lambda/latest/dg/java-handler-io-type-pojo.html

package com.slappforge.samples.aws.java;

import com.amazonaws.services.lambda.runtime.Context;
import com.amazonaws.services.lambda.runtime.RequestHandler;

public class HelloPojo implements RequestHandler<HelloPojo.RequestClass, HelloPojo.ResponseClass> {

   public ResponseClass handleRequest(RequestClass request, Context context){
       String greetingString = String.format("Hello %s %s.", request.firstName, request.lastName);
       return new ResponseClass(greetingString);
   }

   public static class ResponseClass {
       private String greetings;

       public String getGreetings() {
           return greetings;
       }

       public void setGreetings(String greetings) {
           this.greetings = greetings;
       }

       public ResponseClass(String greetings) {
           this.greetings = greetings;
       }

       public ResponseClass() {}
   }

   public static class RequestClass {
       private String firstName;
       private String lastName;

       public String getFirstName() {
           return firstName;
       }

       public void setFirstName(String firstName) {
           this.firstName = firstName;
       }

       public String getLastName() {
           return lastName;
       }

       public void setLastName(String lastName) {
           this.lastName = lastName;
       }

       public RequestClass(String firstName, String lastName) {
           this.firstName = firstName;
           this.lastName = lastName;
       }

       public RequestClass() {}
   }
}

Use a basic maven configuration with the maven shade plugin, to include the necessary AWS dependencies, and create the deployable artifact. Next, go to the AWS Lambda console and define your function as usual. We will name our function “live-debug-demo” and use Java 8 as shown below.

 

 

Next upload the JAR file built by maven, and set the handler method as follows “com.slappforge.samples.aws.java.HelloPojo::handleRequest”. Finally create a test event with the following JSON payload, and invoke the function with the test payload created.

{
"firstName": "Asankha",
"lastName": "Perera"
}

You should see the following output on your Lambda console.

 

AWS Lambda function

 

Debugging the function live on AWS

SLAppForge Debug for Java uses a challenge response method of authentication to secure access for debugging. To create your access keys, visit https://www.slappforge.com/java-debug and login with your SLAppForge account credentials. If you do not already have an account with SLAppForge, you will be directed to the registration page.

 

 

If you are new to the Sigma IDE – be aware that now you can always use the SLAppForge credentials to login to it. The Sigma IDE is the first browser based IDE custom built for developing Serverless applications with NodeJS and Python, for both Amazon Web Services (AWS) and the Google Cloud Platform (GCP). It supports drag-and-drop code generation, about 3 second updates for function re-deployment – which really saves time during iterative development, and also supports live debugging of Lambda functions on AWS. Read more about the Sigma IDE, or watch the quick introduction video.

You will be presented with a set of credentials for live debugging as follows, and you can re-generate a new secret again at any time.

 

 

Lambda Function preparation for debugging

To set your function for live debugging, go to “Layers” for your function and add select to add a layer. Specify the ARN of the layer provided by SLAppForge.

 

 

Note: SLAppForge Debug for Java will be Generally Available (GA) from early January 2020. Until the GA, SLAppForge will provide early access to the beta version for customers who sign up through the following form. After the product is becomes GA, the layer will be published for use by any eligible AWS user.

To register for early access beta program, please register through the form by providing your AWS Account or Organization ID, for which access is desired. Once your request is approved, your AWS account will be granted permission to use the layer used during the beta program.

Under the Function Code section, select “Custom runtime” for your function as follows

 

 

Next, go to the environment variable section of your Lambda function and define three variables, SLAPP_KEY, SLAPP_SECRET and SLAPP_SESSION as follows, using the credentials generated earlier. The SLAPP_SESSION is any string which can uniquely identify a debugging session – when you have multiple sessions under your account. This String can be anything, but you need to have the same key in the function and your IDE to initiate a debugging session.

 

 

Finally, under the basic settings of your Lambda function, set the timeout value to a reasonable amount to allow your debugging session. It’s recommended that this be set to a value around 2 to 5 minutes. Setting a larger number might hold your executions for longer durations causing your billing to increase, especially in the case of any abrupt failures.

 

Setting up of your IDE

We will use IntelliJ IDEA IDE for this article, but the same settings will be applicable even if you use Eclipse, NetBeans or the command line jdb debugger! The client side agent also takes in the same three environment variables you defined earlier.

#!/bin/sh
export SLAPP_KEY=69ad3415-4b1a-444b-9187-e7bfe2bdbdca
export SLAPP_SECRET=zjZaw5VG0Ok4EtpIZ2cvIxuRHPetDkbS
export SLAPP_SESSION=asankha-12345
java -cp java-debug-runtime-1.0.0-beta-1.jar com.slappforge.aws.IDEProxy

Once you start the local agent, it establishes a connection to the SLAppForge Debug server, authenticates your credentials, and opens up port 5005 on your local machine for your IDE to connect.

user@HOST:~/example$ ./ide-proxy
03 Dec 2019 13:01:09,464 IDEProxy : SLAppForge Live Debug for AWS - Java
03 Dec 2019 13:01:15,589 Connected to Server on port 9090!

Finally configure your IDE to connect to “localhost” on port “5005” for your remote debugging session (see below for the settings for IntelliJ IDEA), and set a breakpoint in your Lambda function where you expect the debugger to stop, and fire your test request!

 

 

Once the breakpoint is hit, your IDE will be able to debug your function as a normal Java process. You can set the variables, step through or do anything else as you would normally do while investigating and debugging a Java process. Only thing you need to keep in mind is that each function will have a maximum time limit as set for its timeout. While at present you can increase the timeout for upto 15 minutes, we do not think you should need a debug session as long as that. Hence, somewhere between two to 5 minutes should be generally adequate for most scenarios.

 

 

You can now change local variables and resume execution after any step-through debugging, and see the result in the Lambda console. You can also inspect the Context variable being passed in to see the live attributes of the function, and also monitor any logging in parallel through CloudWatch.

 

Avoiding Surprises

Here are a few tips to ensure you have a great debugging experience while you debug your Lambda functions live on AWS as they execute.

  • To quickly disable debugging, set an environment variable “SLAPP_DISABLE=true”. This allows you to let the function run without waiting for the debugger to attach. Without this being set, be aware that the function will not execute but timeout – if your debugger does not connect.
  • Make sure the following settings are appropriate for your debugging session
    • Adequate memory allocated for the function – depending on your function and its dependencies
    • Timeout – adequate for a debugging session, but not too much to avoid having to wait too long for a function to timeout, incase the debugger does not connect, or you run into any other issue
    • Concurrency – If you can set this to one, this is recommended

 

Whats Next

The SLAppForge Debug for Java is scheduled to be Generally Available (GA) from early January 2020, when SLAppForge announces a few other exciting updates about the company and its future.

Event triggered function debugging is not available as of this announcement date, but SLAppForge is finalizing the feature to become available during December, in time for our GA release.

SLAppForge Debugger for Java

Debug Lambda functions live as they execute on AWS

Now you can test and debug your serverless applications locally. Perform step-through debugging of your Lambda functions with SLAppForge Debugger for Java.

Download