Skip to content

Commit

Permalink
Optionally run specified rocoto task as part of the ctests (#1121)
Browse files Browse the repository at this point in the history
Only tested with the coupled UFS and the marine DA tasks:
```
Test project /scratch1/NCEPDEV/stmp2/Guillaume.Vernieres/runs/prs/global-workflow/sorc/gdas.cd/build/gdas/test/gw-ci
  Test  #1: C48mx500_3DVarAOWCDA
  Test  #2: C96_atmaerosnowDA
  Test  #3: C96C48_ufs_hybatmDA
  Test  #4: C48mx500_3DVarAOWCDA_gdasfcst_202103241200
  Test  #5: C48mx500_3DVarAOWCDA_gdasprepoceanobs_202103241800
  Test  #6: C48mx500_3DVarAOWCDA_gdasocnanalprep_202103241800
  Test  #7: C48mx500_3DVarAOWCDA_gdasocnanalbmat_202103241800
  Test  #8: C48mx500_3DVarAOWCDA_gdasocnanalrun_202103241800
  Test  #9: C48mx500_3DVarAOWCDA_gdasocnanalchkpt_202103241800
  Test #10: C48mx500_3DVarAOWCDA_gdasocnanalpost_202103241800

Total Tests: 10
```
  • Loading branch information
guillaumevernieres authored May 23, 2024
1 parent 52dfb5f commit af7fb73
Show file tree
Hide file tree
Showing 4 changed files with 136 additions and 7 deletions.
53 changes: 50 additions & 3 deletions test/gw-ci/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -3,13 +3,60 @@ set(HOMEgfs ${CMAKE_SOURCE_DIR}/../../..)
set(RUNTESTS ${CMAKE_CURRENT_BINARY_DIR}/../../test/gw-ci)

# List of g-w ci test to create
# -----------------------------
set(cycling_tests "C48mx500_3DVarAOWCDA" "C96_atmaerosnowDA" "C96C48_ufs_hybatmDA")

# Prepare the cycling ctests
# List of tasks to run for each test
# ----------------------------------
set(C48mx500_3DVarAOWCDA_tasks
"gdasprepoceanobs"
"gdasocnanalprep"
"gdasocnanalbmat"
"gdasocnanalrun"
"gdasocnanalchkpt"
"gdasocnanalpost")
set(C96_atmaerosnowDA_tasks) # empty list for now
set(C96C48_ufs_hybatmDA_tasks) # empty list for now

# Iterate through the list of cycling test
# ----------------------------------------
foreach(pslot ${cycling_tests})
message(STATUS "preparing ${pslot} ctest")
# Prepare the COMROOT and EXPDIR for the cycling ctests
set(YAML ${HOMEgfs}/ci/cases/pr/${pslot}.yaml)
add_test(NAME ${pslot}
COMMAND /bin/bash -c "${PROJECT_SOURCE_DIR}/test/gw-ci/create_exp.sh ${YAML} ${pslot} ${HOMEgfs} ${RUNTESTS}"
WORKING_DIRECTORY ${RUNTESTS})
COMMAND /bin/bash -c "${PROJECT_SOURCE_DIR}/test/gw-ci/create_exp.sh ${YAML} ${pslot} ${HOMEgfs} ${RUNTESTS}"
WORKING_DIRECTORY ${RUNTESTS})
set_tests_properties(${pslot} PROPERTIES LABELS "manual")

# Get the 1/2 cycle and full cycle's dates
execute_process(
COMMAND ${CMAKE_COMMAND} -E env python ${PROJECT_SOURCE_DIR}/test/gw-ci/get_cycles.py ${YAML}
OUTPUT_VARIABLE SCRIPT_OUTPUT
RESULT_VARIABLE SCRIPT_RESULT
OUTPUT_STRIP_TRAILING_WHITESPACE
)
string(REPLACE "," ";" DATES_LIST ${SCRIPT_OUTPUT})
list(GET DATES_LIST 0 HALF_CYCLE)
list(GET DATES_LIST 1 FULL_CYCLE)

# 1/2 cycle gdasfcst
message(STATUS "preparing 1/2 cycle gdasfcst for ${pslot} ctest")
add_test(NAME ${pslot}_gdasfcst_${HALF_CYCLE}
COMMAND /bin/bash -c "${PROJECT_SOURCE_DIR}/test/gw-ci/run_exp.sh ${pslot} gdasfcst ${HALF_CYCLE}"
WORKING_DIRECTORY ${RUNTESTS})
set_tests_properties(${pslot}_gdasfcst_${HALF_CYCLE} PROPERTIES LABELS "manual")

# Select the list of tasks to run for the full cycle
set(TASK_LIST_NAME "${pslot}_tasks")
set(TASK_LIST "${${TASK_LIST_NAME}}")
message(STATUS "Tasks for ${EXPERIMENT}: ${TASK_LIST}")

foreach(task ${TASK_LIST})
message(STATUS "preparing the full cycle ${task} for ${pslot} ctest")
add_test(NAME ${pslot}_${task}_${FULL_CYCLE}
COMMAND /bin/bash -c "${PROJECT_SOURCE_DIR}/test/gw-ci/run_exp.sh ${pslot} ${task} ${FULL_CYCLE}"
WORKING_DIRECTORY ${RUNTESTS})
set_tests_properties(${pslot}_${task}_${FULL_CYCLE} PROPERTIES LABELS "manual")
endforeach()
endforeach()
13 changes: 9 additions & 4 deletions test/gw-ci/create_exp.sh
Original file line number Diff line number Diff line change
@@ -1,14 +1,19 @@
#!/bin/bash
expyaml="$1"
export pslot="$2"
expyaml_ctest="$1"
pslot_ctest="$2"
HOMEgfs="$3"
export RUNTESTS="$4"/${pslot}
export SLURM_ACCOUNT="da-cpu"
exp_path=$4

# Get ICSDIR_ROOT
source "${HOMEgfs}/ush/detect_machine.sh"
source "${HOMEgfs}/ci/platforms/config.${MACHINE_ID}"

# Arguments for the exp setup
expyaml=${expyaml_ctest}
export pslot=${pslot_ctest}
export RUNTESTS=${exp_path}/${pslot}
export SLURM_ACCOUNT="da-cpu"

# Source the gw environement
source ${HOMEgfs}/workflow/gw_setup.sh

Expand Down
38 changes: 38 additions & 0 deletions test/gw-ci/get_cycles.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
import re
import argparse
from datetime import datetime, timedelta


def read_idate_from_yaml(file_path):
idate_value = None
with open(file_path, 'r') as file:
for line in file:
match = re.search(r'^\s*idate:\s*(.*)', line)

if match:
idate_value = match.group(1).strip()
break
return idate_value


def format_dates(idate_str):
date_obj = datetime.strptime(idate_str, '%Y%m%d%H')
half_cycle = date_obj.strftime('%Y%m%d%H%M')
new_date_obj = date_obj + timedelta(hours=6)
full_cycle = new_date_obj.strftime('%Y%m%d%H%M')

return half_cycle, full_cycle


def main():
parser = argparse.ArgumentParser(description="Extract and format idate.")
parser.add_argument('yaml_file', help="Path to exp.yaml file")
args = parser.parse_args()

idate_value = read_idate_from_yaml(args.yaml_file)
half_cycle, full_cycle = format_dates(idate_value)
print(f"{half_cycle},{full_cycle}")


if __name__ == "__main__":
main()
39 changes: 39 additions & 0 deletions test/gw-ci/run_exp.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
#!/bin/bash

pslot=$1
TASK_NAME=$2
CYCLE=$3

# Define the workflow XML and database files
WORKFLOW_XML=${pslot}/EXPDIR/${pslot}/${pslot}.xml
WORKFLOW_DB=${pslot}/EXPDIR/${pslot}/${pslot}.db

# Boot the task
echo "booting $TASK_NAME for cycle $CYCLE"
if [[ ! -e "$WORKFLOW_DB" ]]; then
rocotorun -w "$WORKFLOW_XML" -d "$WORKFLOW_DB" -t "$TASK_NAME" -c "$CYCLE"
fi
rocotoboot -w "$WORKFLOW_XML" -d "$WORKFLOW_DB" -t "$TASK_NAME" -c "$CYCLE"

while true; do
# Update the status of the task
rocotorun -w "$WORKFLOW_XML" -d "$WORKFLOW_DB" -t "$TASK_NAME" -c "$CYCLE"

# Check the task status
OUTPUT=$(rocotostat -w "$WORKFLOW_XML" -d "$WORKFLOW_DB" -t "$TASK_NAME" -c "$CYCLE")
STATUS=$(echo "$OUTPUT" | awk '$2 == task {print $4}' task="$TASK_NAME")

if [[ "$STATUS" == "SUCCEEDED" ]]; then
echo "The task succeeded."
exit 0
elif [[ "$STATUS" == "FAILED" ]]; then
echo "The task failed."
exit 1
elif [[ "$STATUS" == "DEAD" ]]; then
echo "The task is dead."
exit 1
else
echo "The task is in state: $STATUS"
fi
sleep 10
done

0 comments on commit af7fb73

Please sign in to comment.