Skip to main content

GDD APS

Disclaimer

The example Python source code is meant merely as a starting point to quickly interact and retrieve insights from ADMA. It is in no way intended for production workloads.

Overview

Once you have successfully created a Party, Farm and Field, you are ready to execute the additional provided examples.

Now that we have the needed entities created, we can use the GDD service. This is a four-step process. These four steps have been captured and automated in tutorial/example/gdd.py included in the downloadable tutorial zipfile.

Background

This example calculates growing degree days (GDD). GDD is an indicator of crop development based on weather conditions. Specifically, it accounts for heat accumulation.

The GDD service supports the following crops: canola, corn, cotton, sugar beet, soybean, and winter wheat.

The example assumes not all HTTP calls are successful and performs up to five retries for the following HTTP status codes: 429, 502, 503, 504.

GDD Processing

Approach

The example, tutorial.example.gdd, uses the following approach. Note that this approach is for demonstration purposes only.

  1. Given a Party, Field, starting date, a range of days, and crop, attempt to generate GDD for each day while keeping a cumulative sum.

Logging

Due to the nature of this example, logging was enabled. The logging is configured to log to stdout in JSON format, ensure that the timestamp is in ISO 8601 using the UTC time zone, and is backed by a queue. The log configuration file is resource/logging.yml and all logging code exists in tutorial/util/logging.py.

Job IDs

In this example, job ids are generated using the following snippet. While this is sufficient for a first run, each separate request to the GDD service must have a unique job id, or you will receive an error like the one below the snippet.

job_id = f'{gdd_date.isoformat()}-{crop}'
Error for 2023-08-01-canola 
{ "error": {
"code": "Conflict",
"message": "GDD-04103: Job JobId [https://dfs-fb-prod-instance.farmbeats.azure.net/, 2023-08-01-canola] already exists."
},
"traceId": "4c1add25c8075d86e9b09cb73405fed3"
}

So a potential workaround for this issue is to provide a suffix to the generated job ids, but this may not be sufficient for your use case.

job_id = f'{gdd_date.isoformat()}-{crop}-{number:03d}'

Whatever your use case, keep in mind that you will need to keep track of these job ids for subsequent requests to the GDD service and for retrieving the generated insight(s).

Additional Details

Before we execute the command, a little explanation is in order. A new directory will be created in the root of the adma directory named output. Within the output directory, the following directory structure will be created: party_id/resource_id/solution_id. This directory will hold log files of submitted requests and subsequent responses. In the following example the log file is named 2023-08-01-canola.txt. This directory will also hold the generated insight(s). In the following example, the calculated GDD values are included in the file name GDD-2023-08-01-2023-08-31-canola.json.

Output Directory Structure

output
└── 551c7fb3-8b9c-4b5c-8ecc-d6830325ce12
└── b159f824-4d12-4b40-aa38-b98f0c876edf
└── bayerAgPowered.gdd
├── GDD-2023-08-01-2023-08-31-canola.json
├── GDD-2023-08-01-canola.txt
├── ...
└── GDD-2023-08-31-canola.txt
Sample Output Download

A sample output from this example may be downloaded as gdd-output.

E.g.

{
"temperature_unit": "C",
"gdd_measurements": [
{
"date": "2023-08-01",
"daily_contribution": 16.0,
"cumulative_sum": 16.0
},
{
"date": "2023-08-02",
"daily_contribution": 17.0,
"cumulative_sum": 33.0
}
]
}

Generate GDD

Note that you will need to modify lines 172-176 in tutorial/example/gdd.py to change the number_of_days, start_date, crop, and add the UUID of the Party and Field in order to generate and retrieve the insights.

Note this command will take a while to complete. You may want to limit the number of days for it to complete sooner.

Note there is a secondary Python file tutorial/example/concurrent/gdd.py that works very similarly but executes GDD in a concurrent manner. This will execute in a much more timely manner.

python -m tutorial.example.gdd