{"id":37108270,"url":"https://github.com/minutelab/mless","last_synced_at":"2026-01-14T12:59:44.865Z","repository":{"id":57523952,"uuid":"104734635","full_name":"minutelab/mless","owner":"minutelab","description":"Mless - Run AWS Lambda triggered events locally","archived":false,"fork":false,"pushed_at":"2017-10-19T12:22:04.000Z","size":1617,"stargazers_count":17,"open_issues_count":0,"forks_count":3,"subscribers_count":3,"default_branch":"master","last_synced_at":"2024-06-20T01:28:37.974Z","etag":null,"topics":["lab-environment","lambda-functions","lambda-proxy"],"latest_commit_sha":null,"homepage":null,"language":"Go","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/minutelab.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2017-09-25T10:12:31.000Z","updated_at":"2019-03-26T16:47:35.000Z","dependencies_parsed_at":"2022-09-26T18:10:51.934Z","dependency_job_id":null,"html_url":"https://github.com/minutelab/mless","commit_stats":null,"previous_names":[],"tags_count":8,"template":false,"template_full_name":null,"purl":"pkg:github/minutelab/mless","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/minutelab%2Fmless","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/minutelab%2Fmless/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/minutelab%2Fmless/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/minutelab%2Fmless/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/minutelab","download_url":"https://codeload.github.com/minutelab/mless/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/minutelab%2Fmless/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":28420815,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-01-14T10:47:48.104Z","status":"ssl_error","status_checked_at":"2026-01-14T10:46:19.031Z","response_time":107,"last_error":"SSL_connect returned=1 errno=0 peeraddr=140.82.121.6:443 state=error: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["lab-environment","lambda-functions","lambda-proxy"],"created_at":"2026-01-14T12:59:44.271Z","updated_at":"2026-01-14T12:59:44.857Z","avatar_url":"https://github.com/minutelab.png","language":"Go","readme":"Mless - run serverless functions locally in real-life context\n=============================================================\n\nMless enables running AWS Lambda functions in a dev-accessible environment, using the full context (events and triggers) available in the Lambda framework. It is designed to greatly improve the development and testing process of serverless functions.\n\nUsing Mless you can execute Lambda functions in a lab environment optimized for development purposes, yet run the code in full context of the actual Lambda environment:\n\nWith mless the functions under test are triggered by actual AWS lambda events and triggers such as:\n\n * Calls from API gateway\n * Any AWS Lambda supported event sources such as\n   * Changes in S3 buckets\n   * Kinesis Streams events\n\nThis allows a full simulation of an application flow involving serverless functions, while allowing developers to have full access to the serverless code they work on.\n\nThe solution involves a small serverless proxy inside AWS lambda.\nIt enables redirection of events and triggers into an accessible lab environment where the code can be developed more easily and efficiently.\nOnce the Lambda function concludes it's processing, the flow of the application it is part of, continues as if the code runs in Lambda.\nA single test flow may include multiple simulated Lambda functions.\n\nRunning the function will use the role configured for the lambda function,\nand its configured environment. Yet using the [Minute Lab framework](http://minutelab.io) the lambda function itself will run in a preconfigured lab environment, that enables:\n\n * Using the latest code requiring no extra deployment steps of the new code\n   * For scripted languages (python, node) you can simply save the code in the IDE which will trigger the auto-deployment of the code\n * Enabling debugging of the serverless code using your local IDE\n\n Though handling the code will look and feel as if it runs locally, it will actually run in AWS,\n which grants it access to resources in the private VPC.\n\n## Proof Of Concept\n\nThe code is currently in a proof of concept stage.\n\n\nThe following limitations should be expected:\n * Limited environment support\n    * python - both 2.7 and 3.6 are supported\n    * nodejs6.10 partially supported\n      * You can proxy to nodeJS lambda functions running locally\n      * Currently we don't have proxy in nodejs, so the proxy must be in python\n      * Remote debugging available both with the legacy debugger and inspector protocols\n * No authentication/security is currently available for data transfer between the Lambda proxy and the lab environment where the code actually runs.\n\nOn the other hand -\n * Expect frequent updates and added features\n * We are eager to get feedback\n\n## Supported environment\n\n| Environment | Runtime | Debug | Proxy |\n| ----------- | ------- | ----- | ----- |\n| python 2.7  | :white_check_mark: |  :white_check_mark: pydevd, ptvsd | :white_check_mark: |\n| python 3.6  | :white_check_mark: |  :white_check_mark: pydevd, ptvsd | :white_check_mark: |\n| nodejs 6.10 | :white_check_mark: | :white_check_mark:                | :x:                |\n| nodejs 4.3  | :x:                | :x:                               | :x:                |\n| java        | :x:                | :x:                               | :x:                |\n| .net        | :x:                | :x:                               | :x:                |\n\n## Technology\n\nMless combines several technologies\n\n* a small mless proxy module inside the lambda function to allow execution of code in development in a controled or lab environment.\n  This proxy can be used in two ways:\n   * It can be the whole lambda function. A such it transfers all triggered events to the lab environment\n   * It can be used as library inside the real lambda function. This enables transfering only part of the events to the lab environment\n* The current Mless example utilizes the [Minute Lab](http://minutelab.io) technology to provide a lab environment optimized for development purposes, inculding the look \u0026 feel of a local lab environment for code that runs in the cloud as well as interactive troubleshooting, monitoring and automatic code deployment.\n\n\n## MLess vs SAM Local\n\nThere are many similarities between mless and [SAM local](https://aws.amazon.com/blogs/aws/new-aws-sam-local-beta-build-and-test-serverless-applications-locally/).\nBoth projects aim to run lambda function code in a local environment.\n\nIn fact mless shares some of the code base with SAM local.\n\nThere are several differences though:\n\n* Simulated VS actual triggers: SAM local runs and triggers the function locally and runs under the local user AWS role.\nTo trigger a function locally, SAM local enables you to simulate an event and similar to how it would run in Lambda. For example, SAM local enables you to simulate a trigger originating from a file change in S3.\n\nHowever SAM local won't allow you to react to real events or view a chain of events. Suppose a Lambda function that is triggered by a change in a S3 bucket and writes something into a Kinesis stream, which will then trigger another Lambda function.\n\nSAM local enables you to simulate each of the events independently.\n\nWith mless actual events and triggers are used to activate a Lambda function in test and the entire chain of event will roll out as it would in production.\n\n* Reuse of containers: SAM local runs each function in its own container, it doesn't reuse the same container to run several functions.\nTherefore it does not allow to test the side effects of container reuses (an inherent Lambda framework functionality). Both the positive effects (like preparing cache) and the negative ones are essential for a complete test scenario.\n\n## Usage\n\n### The demo Environment Overview\n\n\nThe environment includes the following components\n* An S3 bucket that will trigger the Lambda code into action\n* Mless proxy Lambda function: rediects triggers and events to a Minute Lab server, in which the Lambda code runs\n* A minute Lab environment to run the Lambda code in. This is an mless container running inside a Minute Lab host, running in AWS.\n\n### Prerequisites and setup\n\n#### Setting up Minute Lab\n\nTo best demonstrate the value of mless in the devlopment process, the current mless setup relies on a [MinuteLab](http://minutelab.io) lab environment. You will have to register and install the client to activate your private lab environment.\nThe [Quick Start Guide](http://docs.minutelab.io/user-guide/quickstart/) is a good starting point. Follow this guide to learn how to setup a Minute Lab domain, a host and a file share between your desktop and your host.\n\n\n**Note:** For the purpose of mless you will need to set up a self-hosted Minute Lab domain (all explained in the quickstart guide) to allow settings of security groups for inbound access from Lambda into your lab environment.\n\n#### Setting Inbound Access\n\nThe mless Lambda proxy would have to access the mless container running inside a Minute Lab host. For this you will have to configure a security group allowing inbound access to a designated port (by default 8000).\n\nYou will have to setup the security group in the EC2 console. You can attach it to the host either in the EC2 console or the Minute Lab console.\n\n#### Setting dynamic DNS\n\nTo access the container where the tested code runs, the proxy code would have to know its IP. The easiest way is by using a dynamic DNS service. You can use any service you like, but the mless code contains script templates to use [DYNU](https://www.dynu.com).\n\n\nRegister to such a service to obtain a DNS name (and credentials that allow you to register to it)\n\n### Setting up the examples\n\nCheckout this repository. The example directory includes several examples of lambda functions. All of them are built to get events from S3 (and write their results in there)\n\nThe example directory contains:\n\n* `mless.mlab` script - this script will start the mless container in Minute Lab\n* `ddns.dynu.sh` - this is a template for a script that will register to [dynu](https://www.dynu.com) dynamic DNS service. If this is what you are using copy it to `ddns.sh` and edit it to put your credentials and host name.\n  As `mless.mlab` starts it executes this script to register the updated IP.\n\n  If you are using another service you can put another script there.\n\n#### First example\n\nCreate a Lambda function to hold the first proxy:\n\n* Select either python 2.7 or python 3.6 as the environment\n* Copy the `procy/python\u003cver\u003e/python.py` as the function content\n* Set in the environment `MLESS_SERVER` to be `http://\u003cyour servername\u003e:8000`\n* Make the function call the appropriate local function\n  * The examples contain two function that does the same in different run time encironment\n    * python2.7 - `hashFile`\n    * python3.6 - `hash36`\n  * By default the proxy call a function with the same name as its own name.\n  * The default can be over ridden by configuring the environment variable `MLESS_FUNCNAME`.\n* Configure a trigger on creating an object in a S3 bucket of your choice\n  (it is advised to limit this to a specific folder only).\n* Make sure to configure the Lambda function with a role that allows it to read/write from/to this bucket.\n\nStart the test server by running the script `mlessd.mlab` (using the Minute Lab client) in the examples directory.\n\nNow upload a file to the S3 bucket to the specified folder. You will notice that:\n\n* The mlessd server will be invoked (twice)\n* In addition to the file that you uploaded there should be another file containing the sha1 of the original file\n\nWhat happened:\n\n* The file was uploaded to S3, which triggered the Lambda function\n* The mlessd proxy code invoked the mlessd with the details of the original file\n* The proxy was called, and executed the function from inside the lab environment.\n  This code computed the hash and wrote it back to S3\n* Writing the hash to the S3 bucket triggered the process again. AWS Lambda called the proxy\n  which called mlessd which executed the function.\n* This time the code determined (by the filename extension) that it doesn't need to write the hash,\n\n  and broke the loop.\n\n#### Modifying the example\n\nOpen your favorite IDE and edit your serverless code. To do that open the file `example/hash/lambda_function.py`(stored locally on your desktop) and cahnge it.\n\nFor example change the hashed file extension to be `.hash`\nThis is done by changing the line:\n\n```python\nnewkey = key+\".sha1\"\n```\n\nto:\n\n```python\nnewkey = key+\".hash\"\n```\n\nSave the file you just edited (locally). It will be uploaded to the running Minute Lab container automatically.\n\nNow upload another file to S3 (no need to stop/start mlessd).\nYou will notice that the NEW code is used:\n\n* The files are created with the `.hash` extension\n* The code fails to activate the \"loop protection\" (as the extention name was changed...), which results with `.hash.hash`, `.hash.hash.hash`, etc extensions (the \"loop\" will continue until the S3 file name length limit is reached)\n\n\n#### Running with a debugger\n\nThe instructions below are for running with [pydevd](http://www.pydev.org) (using [eclipse](https://www.eclipse.org/) or [LiClipse](http://www.liclipse.com)) as IDE.\n(It is also possible to debug using [Visual Studio Code](visual studio code) (`ptvsd`))\n\nUsing pydevd is technically non-trivial since the process under debugging opens a connection to the debugger running on the desktop. Minute Lab addresses the challenges quite efficiently.\n\nIn order to use it:\n\n* Prepare a pydevd capable IDE (for example eclipse with the pydev add-on).\n* Start the pydev server and set a breakpoint in the hashing function\n* Edit `examples/template.yaml`, in the section describing the hashFile function, remove the comment from the debbuger line (and save the file)\n\nUpload another file to S3 and watch the debugger in action.\n\n#### More examples\n\nThe examples directory contains more examples that are documented in those directories.\n","funding_links":[],"categories":[],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fminutelab%2Fmless","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fminutelab%2Fmless","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fminutelab%2Fmless/lists"}