Skip to content

Commit

Permalink
0.2.2 - Patch (#54)
Browse files Browse the repository at this point in the history
* 🔨 Modified CMakeLists.txt check for CUDA installation. Fix for #10.

Signed-off-by: Bey Hao Yun <[email protected]>

* 🔨 Rectifying for failing lint_cmake test case in CI.

Signed-off-by: Bey Hao Yun <[email protected]>

* 📖 Updated easy_perception_deployment CHANGELOG.rst for v0.2.2 Patch.

Signed-off-by: Bey Hao Yun <[email protected]>

* 🔨 Set session_config.json to appropriate default values.

Signed-off-by: Bey Hao Yun <[email protected]>

* ➕ Added experimental config_epd.py python script within scripts folder. Unverified. Included TODOs within. Awaiting elaboration.

Signed-off-by: Bey Hao Yun <[email protected]>

* 🔨 Elaborated parser functions in config_epd.py python script.

Signed-off-by: Bey Hao Yun <[email protected]>

* 📖 Added TODOs for further elaboration in config_epd.py. Unit testing required.

Signed-off-by: Bey Hao Yun <[email protected]>

* ➕ Added experimental python_ci_action.yml GitHub Action file as well as linted config_epd.py python script.

Signed-off-by: Bey Hao Yun <[email protected]>

* 🔨 Renamed GitHub action CI to INDUSTRIAL_ROS_CI for better distinction from newly-added PYTHON_CI.

Signed-off-by: Bey Hao Yun <[email protected]>

* ➕ Added unit-testing for newly added EPDConfigurator python module for improved CLI operation. Modified PYTHON_CI to only run Python 3.8 and 3.9 according to Foxy and Humble dependencies.

Signed-off-by: Bey Hao Yun <[email protected]>

* 🔨 Rectifying to pass pycodestyle linting CI.

Signed-off-by: Bey Hao Yun <[email protected]>

* 🔨 Corrected python 3.9 to 3.10 to reflect Humble python dependency based on REP-2000.

Signed-off-by: Bey Hao Yun <[email protected]>

* 🔥 Removed 3.10 python in PYTHON_CI GitHub Action to prevent failing CI. Isolating PYTHON_CI to only reflect python present in a Ubuntu 20.04.

Signed-off-by: Bey Hao Yun <[email protected]>

* 🔥 Removed unused doxygen, wget and curl installation in PYTHON_CI GitHub Action.

Signed-off-by: Bey Hao Yun <[email protected]>

* 📖 Rectified CI badge on root README.md to link to official ros-industrial GitHub Action.

Signed-off-by: Bey Hao Yun <[email protected]>

* ➕ Elaborated on TODOs for usecase_config parsing and write-out in EPDConfigurator module. Verified on local python unit-testing.

Signed-off-by: Bey Hao Yun <[email protected]>

* ➕ Added test_set_Invalid_UseCase for config_epd unit_testing.

Signed-off-by: Bey Hao Yun <[email protected]>

* 📖 Updated CHANGELOG.rst for v0.2.2.

Signed-off-by: Bey Hao Yun <[email protected]>

* 🔨 Renaming GitHub Actions CI components to display appropriately on root README.md.

Signed-off-by: Bey Hao Yun <[email protected]>
  • Loading branch information
cardboardcode authored Aug 8, 2022
1 parent 0979965 commit 48d4c89
Show file tree
Hide file tree
Showing 8 changed files with 787 additions and 11 deletions.
34 changes: 34 additions & 0 deletions .github/workflows/cli_ci_action.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
name: CLI_CI

# Determines when this workflow is run
on: [push, pull_request]

jobs:
python_ci:
strategy:
matrix:
python-version: [3.8]
env:
QT_QPA_PLATFORM: "offscreen"
CODECOV_TOKEN: b56af58a-9b3b-49a9-800d-65746dbfb346

runs-on: ubuntu-20.04
steps:
- uses: actions/checkout@v2
- name: Set up Python ${{ matrix.python-version }}
uses: actions/setup-python@v2
with:
python-version: ${{ matrix.python-version }}
- name: Install dependencies
run: |
sudo apt-get update
sudo apt-get install -y python3-pip
sudo python -m pip install pycodestyle
- name: Static Analysis
run: |
pycodestyle --show-source easy_perception_deployment/scripts/test_config_epd.py easy_perception_deployment/scripts/cli/config_epd.py --count
- name: Dynamic Analysis
run: |
pip install pytest pytest-cov pytest-mock
cd easy_perception_deployment/scripts
pytest --capture=no -vv test_config_epd.py
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
![](img/epd_logo_long.png)

# **easy_perception_deployment**
[![CI](https://github.com/cardboardcode/easy_perception_deployment/actions/workflows/industrial_ci_action.yml/badge.svg)](https://github.com/cardboardcode/easy_perception_deployment/actions/workflows/industrial_ci_action.yml)
[![CI](https://github.com/ros-industrial/easy_perception_deployment/actions/workflows/industrial_ci_action.yml/badge.svg)](https://github.com/ros-industrial/easy_perception_deployment/actions/workflows/industrial_ci_action.yml)
[![codecov](https://codecov.io/gh/cardboardcode/easy_perception_deployment/branch/master/graph/badge.svg)](https://codecov.io/gh/cardboardcode/easy_perception_deployment)
[![License](https://img.shields.io/badge/License-Apache%202.0-blue.svg)](https://opensource.org/licenses/Apache-2.0)
[![Documentation Status](https://readthedocs.org/projects/epd-docs/badge/?version=latest)](https://epd-docs.readthedocs.io/en/latest/?badge=latest)
Expand Down
7 changes: 6 additions & 1 deletion easy_perception_deployment/CHANGELOG.rst
Original file line number Diff line number Diff line change
Expand Up @@ -40,4 +40,9 @@ Changelog for package easy_perception_deployment
* Abstracted instantiation of struct LocalizedObject in usecase_config.hpp. Reduced code verbosity for EPDObjectLocalization to EPDObjectTracking conversion in Localization Visualize workflow.
* Contributor(s): Bey Hao Yun


0.2.2 (2022-08-09)
-------------------
* Modified CMake-based check for CUDA installation to set USE_GPU flag.
* Included python script within scripts folder to allow for session and use-case configuration via commandline/terminal.
* Included unit-testing as well as additional Continuous Integration component as PYTHON_CI_ACTION.
* Contributor(s): Bey Hao Yun
9 changes: 4 additions & 5 deletions easy_perception_deployment/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -55,10 +55,6 @@ set(EPD_UTILS
include/ort_cpp_lib/p1_ort_base.cpp
)

# Check if CUDA is available in local onnxruntime build
include(CheckLanguage)
check_language(CUDA)

if(EXISTS "${CMAKE_CURRENT_LIST_DIR}/data/model/squeezenet1.1-7.onnx")
message(AUTHOR_WARNING "Pretrained models are downloaded.")
else()
Expand All @@ -74,7 +70,10 @@ else()
--directory-prefix=${CMAKE_CURRENT_LIST_DIR}/data/model/)
endif()

if(EXISTS ${CMAKE_CUDA_COMPILER})
# Check if CUDA is available in local onnxruntime build
find_package(CUDA)

if(CUDA_FOUND)
message(AUTHOR_WARNING "Using [-GPU-].")
add_definitions(-DUSE_GPU=true)
else()
Expand Down
8 changes: 4 additions & 4 deletions easy_perception_deployment/config/session_config.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"path_to_label_list" : "/home/cardboardvoice/epd_workspace/5_linting_epd_ws/src/easy_perception_deployment/easy_perception_deployment/data/label_list/imagenet_classes.txt",
"path_to_model" : "/home/cardboardvoice/epd_workspace/5_linting_epd_ws/src/easy_perception_deployment/easy_perception_deployment/data/model/squeezenet1.1-7.onnx",
"useCPU" : "CPU",
"visualizeFlag" : "robot"
"path_to_model": "./data/model/MaskRCNN-10.onnx",
"path_to_label_list": "./data/label_list/coco_classes.txt",
"visualizeFlag": "visualize",
"useCPU": "CPU"
}
Empty file.
296 changes: 296 additions & 0 deletions easy_perception_deployment/scripts/cli/config_epd.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,296 @@
#!/usr/bin/env bash

# Copyright 2022 Advanced Remanufacturing and Technology Centre
# Copyright 2022 ROS-Industrial Consortium Asia Pacific Team
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.


import os
import sys
import argparse
import getopt
import json


class EPDConfigurator():

def __init__(self, start_dirpath, args):

self.isInEPDPackageRoot(start_dirpath)

self._path_to_model = ''
self._path_to_label_list = ''
self._input_image_topic = ''
self.visualizeFlag = True
self.useCPU = True

self.usecase_mode = 0

self.count_class_list = []
self.path_to_color_template = ''
self.track_type = ''

# Check if session_config.json exits.
self.session_config_filepath = start_dirpath \
+ "/config/session_config.json"
if os.path.isfile(self.session_config_filepath):
print("[ config_epd ] - session_config.json detected.")
self.parse_session_config(self.session_config_filepath)
else:
print("[ config_epd ] - ERROR. session_config.json missing.")
sys.exit(1)
# Check if usecase_config.json exists.
self.usecase_config_filepath = start_dirpath \
+ "/config/usecase_config.json"
if os.path.isfile(self.usecase_config_filepath):
print("[ config_epd ] - usecase_config.txt detected.")
self.parse_usecase_config(self.usecase_config_filepath)
else:
print("[ config_epd ] - ERROR. usecase_config.json missing.")
sys.exit(1)

if len(args) < 2:
print('Please specify a configuration.')
self.print_help()
sys.exit(1)

opt_files = self.parse_args(args[1:])

self.write_out(
self.session_config_filepath,
self.usecase_config_filepath)

def print_help(self):
print('config_epd.py [--visualize ] [--action ] [--cpu ] [--gpu ] ' +
'[--model ] [--label ]')
print()
print('-v --visualize Sets EPD to Visualize Mode.')
print('-a --action Sets EPD to Action Mode.')
print('-g --gpu Sets EPD to GPU Mode.')
print('-c --cpu Sets EPD to CPU Mode.')
print('--model Sets new onnx model to be deployed via EPD.')
print('--label Sets new label list to be deployed via EPD.')
print('--use Sets usecase mode to be deployed via EPD. ' +
'Eg. [0,1,2,3,4].')

def isInEPDPackageRoot(self, start_dirpath):
if (os.path.isdir(start_dirpath + "/scripts") and
os.path.isdir(start_dirpath + "/launch") and
os.path.isdir(start_dirpath + "/data")):
print("[ config_epd ] - Executing in root of EPD package.")
else:
print("[ config_epd ] - ERROR. Not in root of EPD package")
print("[ config_epd ] - Please run in root of EPD package.")
print("[ config_epd ] - Exiting...")
sys.exit(1)

def parse_args(self, args):
# TODO(cardboardcode): Add options for usecase_config.json
# CLI configuration.
opts, opt_files = getopt.getopt(args, 'hvagc',
['visualize',
'action',
'gpu',
'cpu',
'model=',
'label=',
'use='])

for opt, arg in opts:
if opt == '-h':
self.print_help()
sys.exit(0)
elif opt in ('-v', '--visualize'):
print("[ session_config.json ] - Setting to Visualize Mode.")
self.visualizeFlag = True
elif opt in ('-a', '--action'):
print("[ session_config.json ] - Setting to Action Mode.")
self.visualizeFlag = False
elif opt in ('-g', '--gpu'):
print("[ session_config.json ] - Setting to GPU Mode.")
self.useCPU = False
elif opt in ('-c', '--cpu'):
print("[ session_config.json ] - Setting to CPU Mode.")
self.useCPU = True
elif opt in ('-m', '--model'):
if not os.path.isfile(os.getcwd() + "/" + arg):
print("[ config_epd ] - ERROR." +
" input model file does not exist.")
print("[ config_epd ] - Exiting.")
sys.exit(2)
self._path_to_model = arg
elif opt in ('-l', '--label'):
if not os.path.isfile(os.getcwd() + "/" + arg):
print("[ config_epd ] - ERROR." +
" input label list does not exist.")
print("[ config_epd ] - Exiting.")
sys.exit(2)
self._path_to_label_list = arg
elif opt in ('--use'):
self.set_use_case_from_cli(int(arg))

def parse_session_config(self, session_config_filepath):

f = open(session_config_filepath)
data = json.load(f)
self._path_to_model = data["path_to_model"]
self._path_to_label_list = data["path_to_label_list"]
if data["useCPU"] == "CPU":
self.useCPU = True
else:
self.useCPU = False
if data["visualizeFlag"] == "visualize":
self.visualizeFlag = True
else:
self.visualizeFlag = False
f.close()

def parse_usecase_config(self, usecase_config_filepath):

f = open(usecase_config_filepath)
data = json.load(f)
self.usecase_mode = data["usecase_mode"]
if self.usecase_mode == 0:
print("[ Use Case ] - CLASSIFICATION")
elif self.usecase_mode == 1:
print("[ Use Case ] - COUNTING")
self.count_class_list = data["class_list"]
# DEBUG
print("class_list =", self.count_class_list)
elif self.usecase_mode == 2:
print("[ Use Case ] - COLOR-MATCHING")
self.path_to_color_template = data["path_to_color_template"]
# DEBUG
print("path_to_color_template =", self.path_to_color_template)
elif self.usecase_mode == 3:
print("[ Use Case ] - LOCALIZATION")
elif self.usecase_mode == 4:
print("[ Use Case ] - TRACKING")
self.track_type = data["track_type"]
# DEBUG
print("track_type =", self.track_type)
else:
print("[ Use Case ] - INVALID. Please rectify" +
" usecase_config.json. Exiting...")
f.close()
sys.exit(1)
f.close()

def set_use_case_from_cli(self, usecase_mode):
self.usecase_mode = usecase_mode

if usecase_mode == 0:
print("[ session_config.json ] - " +
"Setting Use Case Mode to CLASSIFICATION.")
elif usecase_mode == 1:
print("[ session_config.json ] - " +
"Setting Use Case Mode to COUNTING.")
n = int(input("Please enter number of object class names : "))
self.count_class_list.clear()
for i in range(0, n):
ele = input("Please enter class name: ")
self.count_class_list.append(ele)
elif usecase_mode == 2:
print("[ session_config.json ] - " +
"Setting Use Case Mode to COLOR-MATCHING.")
self.path_to_color_template = input("Please enter \
Color Image File Path: ")
elif usecase_mode == 3:
print("[ session_config.json ] - " +
"Setting Use Case Mode to LOCALIZATION.")
elif usecase_mode == 4:
print("[ session_config.json ] - " +
"Setting Use Case Mode to TRACKING.")
self.track_type = input("Please enter Tracker Type \
[KCF, MEDIANFLOW, CSRT]: ")
else:
print("[ session_config.json ] - " +
"Invalid Use Case Mode provided. Exiting...")
sys.exit(1)

def write_out(self, session_config_filepath, usecase_config_filepath):

if self.visualizeFlag:
visualizeFlag_string = "visualize"
else:
visualizeFlag_string = "robot"

if self.useCPU:
useCPU_string = "CPU"
else:
useCPU_string = "GPU"

dict = {
"path_to_model": self._path_to_model,
"path_to_label_list": self._path_to_label_list,
"visualizeFlag": visualizeFlag_string,
"useCPU": useCPU_string
}
json_object_1 = json.dumps(dict, indent=4)

with open(session_config_filepath, 'w') as outfile_1:
outfile_1.write(json_object_1)

if self.usecase_mode == 0:
dict = {
"usecase_mode": self.usecase_mode
}
json_object_2 = json.dumps(dict, indent=4)
with open(usecase_config_filepath, 'w') as outfile_2:
outfile_2.write(json_object_2)
elif self.usecase_mode == 1:
dict = {
"usecase_mode": self.usecase_mode,
"class_list": self.count_class_list
}
json_object_2 = json.dumps(dict, indent=4)
with open(usecase_config_filepath, 'w') as outfile_2:
outfile_2.write(json_object_2)
elif self.usecase_mode == 2:
dict = {
"usecase_mode": self.usecase_mode,
"path_to_color_template": self.path_to_color_template
}
json_object_2 = json.dumps(dict, indent=4)
with open(usecase_config_filepath, 'w') as outfile_2:
outfile_2.write(json_object_2)
elif self.usecase_mode == 3:
dict = {
"usecase_mode": self.usecase_mode
}
json_object_2 = json.dumps(dict, indent=4)
with open(usecase_config_filepath, 'w') as outfile_2:
outfile_2.write(json_object_2)
elif self.usecase_mode == 4:
dict = {
"usecase_mode": self.usecase_mode,
"track_type": self.track_type
}
json_object_2 = json.dumps(dict, indent=4)
with open(usecase_config_filepath, 'w') as outfile_2:
outfile_2.write(json_object_2)


def main(args=None):
# Checks if this script is run in the root of the
# easy_perception_deployment ROS2 package.
start_dirpath = os.getcwd()
# Check if the following folders/files are in the directory
# when script is being executed:
# /data, /scripts, /launch, CMakeLists.txt and package.xml
configurator = EPDConfigurator(start_dirpath, args)


if __name__ == "__main__":
main(sys.argv)
Loading

0 comments on commit 48d4c89

Please sign in to comment.