Code repository author: Alexandre Harano
This project provides a small DigitalOcean Function
using Python to validate blocking=false functionality.
This project uses the twelve-factor app methodology.
Environment variables in this project can be stored using a .env (dot env) file.
For initial setup, a sample is provided as .env.sample.
A description of each of the variables is provided as the following list.
FUNCTION_URL: the DigitalOcean Function URL to be calledAUTHORIZATION_TOKEN: a string value to be used as the Functions REST API Authorization token
First, clone this repo:
$ git clone https://github.com/ayharano/do-function-tester.gitAfter cloning the repository, change the directory to the project root. All instructions below, including configuring the virtual environment and running the project, depend on being in the project root directory.
To maintain consistency between individual commits,
this repo is adopting the use of pre-commit.
The recommended way to install it for this repo is by installing via pipx.
After installing pipx, issue the following commands:
$ pipx install pre-commit
$ pre-commit install --install-hooks --overwritepre-commit is configured to also run per push and pull requests in GitHub workflow.
This project was tested by using CPython 3.10. In order to keep multiple versions of the Python interpreter, we recommend the use of pyenv.
Once it is installed, we can use the same version as the one used during this project development, which was CPython 3.12.1.
Run the following:
$ pyenv install 3.10.3 # install CPython 3.10.3
$ pyenv local 3.10.3 # select CPython 3.10.3 as the local interpreterAs a directory name for the virtual env, for this tutorial we will use it as virtualenvironment.
If you prefer another name, just replace all the occurrences from here.
To install a virtual env, run the following:
$ python -m venv virtualenvironmentThis way, a directory named virtualenvironment will be created at the project root to store the Python project dependencies.
Regarding the installation and the use of virtual envs, more details can be found at the venv module documentation.
To use the virutal env, the instructions depend on the target operating system:
- venv for Linux or macOS
$ source virtualenvironment/bin/activate- venv for Windows (PowerShell)
virtualenvironment\Scripts\Activate.ps1Once the virtual env is activated, run:
python -m pip install --upgrade pip && python -m pip install --editable '.[local]' && python -m pip install --upgrade tzdataThis command is a chained call of 3 executions, being
- upgrading the local
pipto its most recent version - installing all the project dependencies, including the ones for local dev use, and installing the project as an editable install, and
- enforce the most recent version of
tzdata, which is used by Python to manage timezone data without relying on the data from the target operating system (more details at thezoneinfomodule documentation)
To deploy this function, a DigitalOcean account is required.
For this tutorial, we rely on doctl CLI (installation instructions).
Following the Functions Quickstart, we must create a namespace before deploying a Function. Two parameters are required:
label: an arbitrary label for the namespaceregion: one of the available DigitalOcean's datacenter - list for Functions
For this example, we used functions-ns as its label and nyc as its region:
$ doctl serverless namespaces create --label functions-ns --region nycIf it is correctly configured, an output similar to the following should be displayed
Connected to functions namespace 'fn-01234567-89ab-cdef-0123-456789abcdef' on API host 'https://faas-nyc1-abcdef01.doserverless.co'
To deploy the function(s), run:
$ doctl serverless deploy . # yes, it is a dot after deployIf it is correctly runs, an output such as the following should be displayed
Deploying '/home/user/projects/do-function-tester'
to namespace 'fn-01234567-89ab-cdef-0123-456789abcdef'
on host 'https://faas-nyc1-abcdef01.doserverless.co'
Deployed functions ('doctl sls fn get <funcName> --url' for URL):
- tester/blocking_false_handler
To test the Function, we need to populate the environmental variables:
As we will need the Function URL, we should run the suggested command:
$ doctl sls fn get tester/blocking_false_handler --urlThe output is a URL similar to this
https://faas-nyc1-abcdef01.doserverless.co/api/v1/web/fn-01234567-89ab-cdef-0123-456789abcdef/tester/blocking_false_handler
We can set that value in the .env file as FUNCTION_URL:
FUNCTION_URL=https://faas-nyc1-abcdef01.doserverless.co/api/v1/web/fn-01234567-89ab-cdef-0123-456789abcdef/tester/blocking_false_handler
Follow the instructions described in Call a Function Asynchronously using curl and the REST API to retrieve the token.
Having its full value (everything after Authorization:), set it in the .env file as AUTHORIZATION_TOKEN:
AUTORIZATION_TOKEN=Basic VeryBase64EncodedValue=
If the project was correctly installed as described in the Project Installation section, we can just test the Function by running
$ python -m tester issue any value here after issue will be grouped as a listExample output:
{'after_request': '2024-02-16T18:46:24.745284+00:00',
'before_request': '2024-02-16T18:46:24.319217+00:00',
'body': {'activationId': 'abcdef0123456789abcdef0123456789'},
'status_code': 202,
'time_diff': 0.426067}As described in Retrieve Activation Records Using curl and the REST API, we can retrieve the actual values using the activationId.
If the project was correctly installed as described in the Project Installation section, we can just test the Function by running
$ python -m tester retrieve abcdef0123456789abcdef0123456789where abcdef0123456789abcdef0123456789 would be the activationId value.
Example output:
{'after_request': '2024-02-16T18:47:09.740636+00:00',
'before_request': '2024-02-16T18:47:09.255087+00:00',
'body': {'activationId': 'abcdef0123456789abcdef0123456789',
'annotations': [{'key': 'path',
'value': 'fn-01234567-89ab-cdef-0123-456789abcdef/tester/blocking_false_handler'},
{'key': 'waitTime', 'value': 769},
{'key': 'uuid',
'value': 'fedcba98-7654-3210-0123-456789abcdef'},
{'key': 'entry', 'value': 'main'},
{'key': 'user_id', 'value': '12345678'},
{'key': 'gbs', 'value': 0.0125},
{'key': 'kind', 'value': 'python:3.9'},
{'key': 'timeout', 'value': False},
{'key': 'limits',
'value': {'logs': 5,
'memory': 128,
'timeout': 1000}},
{'key': 'initTime', 'value': 10}],
'duration': 2,
'end': 1708109185446,
'logs': [],
'name': 'blocking_false_handler',
'namespace': 'fn-01234567-89ab-cdef-0123-456789abcdef',
'publish': False,
'response': {'result': {'body': {'list_args': ['any',
'value',
'here',
'after',
'issue',
'will',
'be',
'grouped',
'as',
'a',
'list'],
'received_at': '2024-02-16T18:46:25.445336+00:00',
'sent_at_arg': '2024-02-16T18:46:24.319205+00:00'},
'statusCode': 202},
'size': 232,
'status': 'success',
'success': True},
'start': 1708109185444,
'subject': '01234567-89ab-cdef-0123-456789abcdef',
'version': '0.0.1'},
'status_code': 200,
'time_diff': 0.485549}