idmtools-platform-comps 0.0.0.dev0__py3-none-any.whl → 0.0.2__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (64) hide show
  1. idmtools_platform_comps/__init__.py +25 -8
  2. idmtools_platform_comps/cli/__init__.py +4 -0
  3. idmtools_platform_comps/cli/cli_functions.py +50 -0
  4. idmtools_platform_comps/cli/comps.py +492 -0
  5. idmtools_platform_comps/comps_cli.py +48 -0
  6. idmtools_platform_comps/comps_operations/__init__.py +6 -0
  7. idmtools_platform_comps/comps_operations/asset_collection_operations.py +263 -0
  8. idmtools_platform_comps/comps_operations/experiment_operations.py +569 -0
  9. idmtools_platform_comps/comps_operations/simulation_operations.py +678 -0
  10. idmtools_platform_comps/comps_operations/suite_operations.py +228 -0
  11. idmtools_platform_comps/comps_operations/workflow_item_operations.py +269 -0
  12. idmtools_platform_comps/comps_platform.py +309 -0
  13. idmtools_platform_comps/plugin_info.py +168 -0
  14. idmtools_platform_comps/ssmt_operations/__init__.py +6 -0
  15. idmtools_platform_comps/ssmt_operations/simulation_operations.py +77 -0
  16. idmtools_platform_comps/ssmt_operations/workflow_item_operations.py +73 -0
  17. idmtools_platform_comps/ssmt_platform.py +44 -0
  18. idmtools_platform_comps/ssmt_work_items/__init__.py +4 -0
  19. idmtools_platform_comps/ssmt_work_items/comps_work_order_task.py +29 -0
  20. idmtools_platform_comps/ssmt_work_items/comps_workitems.py +113 -0
  21. idmtools_platform_comps/ssmt_work_items/icomps_workflowitem.py +71 -0
  22. idmtools_platform_comps/ssmt_work_items/work_order.py +54 -0
  23. idmtools_platform_comps/utils/__init__.py +4 -0
  24. idmtools_platform_comps/utils/assetize_output/__init__.py +4 -0
  25. idmtools_platform_comps/utils/assetize_output/assetize_output.py +125 -0
  26. idmtools_platform_comps/utils/assetize_output/assetize_ssmt_script.py +144 -0
  27. idmtools_platform_comps/utils/base_singularity_work_order.json +6 -0
  28. idmtools_platform_comps/utils/download/__init__.py +4 -0
  29. idmtools_platform_comps/utils/download/download.py +178 -0
  30. idmtools_platform_comps/utils/download/download_ssmt.py +81 -0
  31. idmtools_platform_comps/utils/download_experiment.py +116 -0
  32. idmtools_platform_comps/utils/file_filter_workitem.py +519 -0
  33. idmtools_platform_comps/utils/general.py +358 -0
  34. idmtools_platform_comps/utils/linux_mounts.py +73 -0
  35. idmtools_platform_comps/utils/lookups.py +123 -0
  36. idmtools_platform_comps/utils/package_version.py +489 -0
  37. idmtools_platform_comps/utils/python_requirements_ac/__init__.py +4 -0
  38. idmtools_platform_comps/utils/python_requirements_ac/create_asset_collection.py +155 -0
  39. idmtools_platform_comps/utils/python_requirements_ac/install_requirements.py +109 -0
  40. idmtools_platform_comps/utils/python_requirements_ac/requirements_to_asset_collection.py +374 -0
  41. idmtools_platform_comps/utils/python_version.py +40 -0
  42. idmtools_platform_comps/utils/scheduling.py +154 -0
  43. idmtools_platform_comps/utils/singularity_build.py +491 -0
  44. idmtools_platform_comps/utils/spatial_output.py +76 -0
  45. idmtools_platform_comps/utils/ssmt_utils/__init__.py +6 -0
  46. idmtools_platform_comps/utils/ssmt_utils/common.py +70 -0
  47. idmtools_platform_comps/utils/ssmt_utils/file_filter.py +568 -0
  48. idmtools_platform_comps/utils/sweeping.py +162 -0
  49. idmtools_platform_comps-0.0.2.dist-info/METADATA +100 -0
  50. idmtools_platform_comps-0.0.2.dist-info/RECORD +62 -0
  51. idmtools_platform_comps-0.0.2.dist-info/entry_points.txt +9 -0
  52. idmtools_platform_comps-0.0.2.dist-info/licenses/LICENSE.TXT +3 -0
  53. {idmtools_platform_comps-0.0.0.dev0.dist-info → idmtools_platform_comps-0.0.2.dist-info}/top_level.txt +1 -0
  54. ssmt_image/Dockerfile +52 -0
  55. ssmt_image/Makefile +21 -0
  56. ssmt_image/__init__.py +6 -0
  57. ssmt_image/bootstrap.sh +30 -0
  58. ssmt_image/build_docker_image.py +161 -0
  59. ssmt_image/pip.conf +3 -0
  60. ssmt_image/push_docker_image.py +49 -0
  61. ssmt_image/requirements.txt +9 -0
  62. idmtools_platform_comps-0.0.0.dev0.dist-info/METADATA +0 -41
  63. idmtools_platform_comps-0.0.0.dev0.dist-info/RECORD +0 -5
  64. {idmtools_platform_comps-0.0.0.dev0.dist-info → idmtools_platform_comps-0.0.2.dist-info}/WHEEL +0 -0
@@ -0,0 +1,162 @@
1
+ """
2
+ idmtools utility.
3
+
4
+ Copyright 2025, Gates Foundation. All rights reserved.
5
+ """
6
+ import numpy as np
7
+ from typing import Dict, Any, List
8
+ from idmtools.entities.simulation import Simulation
9
+ from logging import getLogger, DEBUG
10
+
11
+ logger = getLogger()
12
+
13
+
14
+ ##################################################
15
+ # Sweeping utility functions
16
+ ##################################################
17
+ def set_param(simulation: Simulation, param: str, value: Any) -> Dict[str, Any]:
18
+ """
19
+ Set a specific parameter value on the simulation task config.
20
+
21
+ Args:
22
+ simulation (Simulation): idmtools Simulation object.
23
+ param (str): Name of the parameter to modify.
24
+ value (Any): New value to set.
25
+
26
+ Returns:
27
+ Dict[str, Any]: A dictionary containing the parameter name and value.
28
+ """
29
+ try:
30
+ return simulation.task.set_parameter(param, value)
31
+ except ValueError:
32
+ if "parameters" in simulation.task.config:
33
+ config = simulation.task.config.parameters
34
+ else:
35
+ config = simulation.task.config
36
+
37
+ config[param] = value
38
+ return {param: value}
39
+
40
+
41
+ def sweep_functions(simulation: Simulation, func_list: List) -> Dict[str, Any]:
42
+ """
43
+ Apply a list of sweep functions to a simulation.
44
+
45
+ Args:
46
+ simulation (Simulation): The simulation to update.
47
+ func_list (List[Callable]): List of functions that apply sweeps to the simulation.
48
+
49
+ Returns:
50
+ Dict[str, Any]: A dictionary of aggregated metadata from each sweep function.
51
+ """
52
+ tags_updated = {}
53
+ for func in func_list:
54
+ tags = func(simulation)
55
+ if tags:
56
+ tags_updated.update(tags)
57
+ return tags_updated
58
+
59
+
60
+ class ItvFn:
61
+ """
62
+ Sweeping utility for modifying interventions (campaign layer) during sweeps.
63
+
64
+ Requirements:
65
+ - func must accept an emod-api campaign object as its first argument.
66
+ - func must return a dictionary of metadata (i.e: tags).
67
+
68
+ Returns:
69
+ Dict[str, Any]: Metadata returned by the intervention function, with numpy types cast to Python types.
70
+ """
71
+ def __init__(self, func, *args, **kwargs): # noqa: D107
72
+ self.func = func
73
+ self.args = args
74
+ self.kwargs = kwargs
75
+
76
+ def __call__(self, simulation: Simulation): # noqa: D102
77
+ import emod_api.campaign as campaign
78
+ campaign.reset()
79
+
80
+ matadata = self.func(campaign, *self.args, **self.kwargs)
81
+
82
+ # Add new campaign events
83
+ events = campaign.campaign_dict["Events"]
84
+ simulation.task.campaign.add_events(events)
85
+
86
+ # Handle adhoc (custom) individual events
87
+ adhoc_events = campaign.get_adhocs()
88
+ if len(adhoc_events) > 0:
89
+ if logger.isEnabledFor(DEBUG):
90
+ logger.debug("Found adhoc events in campaign. Needs some special processing behind the scenes.")
91
+ if "Custom_Individual_Events" in simulation.task.config.parameters:
92
+ ev_exist = set(simulation.task.config.parameters.Custom_Individual_Events)
93
+ ev_addhoc = set(adhoc_events.keys())
94
+ simulation.task.config.parameters.Custom_Individual_Events = list(ev_exist.union(ev_addhoc))
95
+ else:
96
+ simulation.task.config.parameters.Report_Event_Recorder_Events.extend(list(set(adhoc_events.keys())))
97
+
98
+ # Convert numpy types
99
+ if matadata:
100
+ for k, v in matadata.items():
101
+ if isinstance(v, (np.int64, np.float64, np.float32, np.uint32, np.int16, np.int32)):
102
+ matadata[k] = v.item()
103
+
104
+ return matadata
105
+
106
+
107
+ class CfgFn:
108
+ """
109
+ Sweeping utility for modifying simulation configuration parameters.
110
+
111
+ Requirements:
112
+ - func must accept simulation.task.config as the first parameter.
113
+ - func must return a dictionary for tagging.
114
+
115
+ Returns:
116
+ Dict[str, Any]: Metadata dictionary with Python-native types.
117
+ """
118
+
119
+ def __init__(self, func, *args, **kwargs): # noqa: D107
120
+ self.func = func
121
+ self.args = args
122
+ self.kwargs = kwargs
123
+
124
+ def __call__(self, simulation: Simulation): # noqa: D102
125
+ matadata = self.func(simulation.task.config, *self.args, **self.kwargs)
126
+
127
+ # Make sure we cast numpy types into normal system types
128
+ if matadata:
129
+ for k, v in matadata.items():
130
+ if isinstance(v, (np.int64, np.float64, np.float32, np.uint32, np.int16, np.int32)):
131
+ matadata[k] = v.item()
132
+
133
+ return matadata
134
+
135
+
136
+ class SwpFn:
137
+ """
138
+ Sweeping utility for modifying task-level elements (e.g., reports, demographics, climate).
139
+
140
+ Requirements:
141
+ - func must accept simulation.task as the first parameter.
142
+ - func must return a metadata dictionary (tags).
143
+
144
+ Returns:
145
+ Dict[str, Any]: Metadata with numpy types cast to Python-native types.
146
+ """
147
+
148
+ def __init__(self, func, *args, **kwargs): # noqa: D107
149
+ self.func = func
150
+ self.args = args
151
+ self.kwargs = kwargs
152
+
153
+ def __call__(self, simulation: Simulation): # noqa: D102
154
+ matadata = self.func(simulation.task, *self.args, **self.kwargs)
155
+
156
+ # Make sure we cast numpy types into normal system types
157
+ if matadata:
158
+ for k, v in matadata.items():
159
+ if isinstance(v, (np.int64, np.float64, np.float32, np.uint32, np.int16, np.int32)):
160
+ matadata[k] = v.item()
161
+
162
+ return matadata
@@ -0,0 +1,100 @@
1
+ Metadata-Version: 2.4
2
+ Name: idmtools_platform_comps
3
+ Version: 0.0.2
4
+ Summary: Comps platform for IDM-Tools
5
+ Author-email: Zhaowei Du <zdu@idmod.org>, Sharon Chen <shchen@idmod.org>, Clinton Collins <ccollins@idmod.org>, Benoit Raybaud <braybaud@idmod.org>, Clark Kirkman IV <ckirkman@idmod.org>, Ye Chen <yechen@idmod.org>, Mary Fisher <mafisher@idmod.org>, Mandy Izzo <mizzo@idmod.org>, Jen Schripsema <jschripsema@idmod.org>, Ross Carter <rcarter@idmod.org>
6
+ Project-URL: Homepage, https://github.com/InstituteforDiseaseModeling/idmtools
7
+ Keywords: modeling,IDM
8
+ Classifier: Programming Language :: Python :: 3.8
9
+ Classifier: Programming Language :: Python :: 3.9
10
+ Classifier: Programming Language :: Python :: 3.10
11
+ Classifier: Programming Language :: Python :: 3.11
12
+ Classifier: Programming Language :: Python :: 3.12
13
+ Requires-Python: >=3.8
14
+ Description-Content-Type: text/markdown
15
+ License-File: LICENSE.TXT
16
+ Requires-Dist: idmtools<1.0.0,>=0.0.0
17
+ Requires-Dist: pyCOMPS~=2.11
18
+ Requires-Dist: natsort~=8.4.0
19
+ Provides-Extra: test
20
+ Requires-Dist: idmtools[test]; extra == "test"
21
+ Requires-Dist: idmtools_test; extra == "test"
22
+ Requires-Dist: idmtools_models; extra == "test"
23
+ Provides-Extra: packaging
24
+ Requires-Dist: flake8; extra == "packaging"
25
+ Requires-Dist: coverage; extra == "packaging"
26
+ Requires-Dist: bump2version; extra == "packaging"
27
+ Requires-Dist: twine; extra == "packaging"
28
+ Requires-Dist: natsort; extra == "packaging"
29
+ Dynamic: license-file
30
+
31
+ ![Staging: idmtools-platform-comps](https://github.com/InstituteforDiseaseModeling/idmtools/workflows/Staging:%20idmtools-platform-comps/badge.svg?branch=dev)
32
+
33
+ # idmtools-platform-comps
34
+
35
+ <!-- START doctoc generated TOC please keep comment here to allow auto update -->
36
+ <!-- DON'T EDIT THIS SECTION, INSTEAD RE-RUN doctoc TO UPDATE -->
37
+ **Table of Contents**
38
+
39
+ - [Installing](#installing)
40
+ - [Development Tips](#development-tips)
41
+ - [Building SSMT Docker Image](#building-ssmt-docker-image)
42
+ - [Choose SSMT Docker Image to use in test/script](#choose-ssmt-docker-image-to-use-in-testscript)
43
+
44
+ <!-- END doctoc generated TOC please keep comment here to allow auto update -->
45
+
46
+ ## Installing
47
+
48
+ ```bash
49
+ pip install idmtools-platform-comps --index-url=https://packages.idmod.org/api/pypi/pypi-production/simple
50
+ ```
51
+
52
+ # Development Tips
53
+
54
+ There is a Makefile file available for most common development tasks. Here is a list of commands
55
+ ```bash
56
+ clean - Clean up temproary files
57
+ lint - Lint package and tests
58
+ test - Run All tests
59
+ coverage - Run tests and generate coverage report that is shown in browser
60
+ ```
61
+ On Windows, you can use `pymake` instead of `make`
62
+
63
+ # Building SSMT Docker Image
64
+
65
+ To build the SSMT Docker image, follow these steps
66
+
67
+ 1. ```bash
68
+ docker login docker-production.packages.idmod.org
69
+ ```
70
+ 2. ```bash
71
+ make ssmt-image
72
+ ```
73
+ 3. When prompted, enter your idm username and password
74
+
75
+ # Choose SSMT Docker Image to use in test/script
76
+
77
+ There are three ways to choose which ssmt docker image to use in your script:
78
+
79
+ 1. specify docker_image in SSMTWorkItem creation, for example,
80
+ ```bash
81
+ wi = SSMTWorkItem(name=wi_name, command=command, docker_image='my_test_ssmt_docker_image')
82
+ ```
83
+ 2. define docker_image in your idmtools.ini, for example:
84
+ ```bash
85
+ [COMPS2]
86
+ type = COMPS
87
+ endpoint = https://comps.idmod.org
88
+ environment = Calculon
89
+ ......
90
+ docker_image = my_test_ssmt_docker_image
91
+ ```
92
+
93
+ 3. if not above two cases, idomtools system will determine the default ssmt docker image from platform for you:
94
+
95
+ if endpoint = https://comps.idmod.org, it will use production docker image
96
+
97
+ for all other cases, it will use the staging docker image
98
+
99
+ Note: if user overrode docker image in wi (case #1) and also defined docker image in idmtools.ini (case #2),
100
+ it will take #1 as higher priority
@@ -0,0 +1,62 @@
1
+ idmtools_platform_comps/__init__.py,sha256=q761fnOdJ5dHMHpppTworPXdxYXPL8F05yBSCYEbtn0,829
2
+ idmtools_platform_comps/comps_cli.py,sha256=WdeC7Z1-J1-l5FKu0g5SYlYjQQhOTtrPIP-UDGYRrag,1688
3
+ idmtools_platform_comps/comps_platform.py,sha256=ZMyEzDXnGi4-8Tewam0a0jyDL46P4C0DLZ_oLQ8uMQ4,14762
4
+ idmtools_platform_comps/plugin_info.py,sha256=NBKl8cPNzxy185x5XgVbm92Yl8DZl7pL_OWWHutCQds,5751
5
+ idmtools_platform_comps/ssmt_platform.py,sha256=Yp8FTT8bKjmnRC7Cdz5PmOBvGvy5Oif27hSSlAtlxdc,1808
6
+ idmtools_platform_comps/cli/__init__.py,sha256=YSMg0oRXQjJME5sfJqZ4AK2LTtcK4vng8IIQfztNNhQ,105
7
+ idmtools_platform_comps/cli/cli_functions.py,sha256=ajLR0OmRFvSImAn7tBXy63ul5nt4w5VzztQ8mmIC95k,1561
8
+ idmtools_platform_comps/cli/comps.py,sha256=GFIhCfq_IskHEP8VDKAbiCglRvW-J1mkYqw6KBZX1tM,25676
9
+ idmtools_platform_comps/comps_operations/__init__.py,sha256=nbpywJN29X4gFDmU__MbBAiSra03h0xMmL-HbSt0RIs,177
10
+ idmtools_platform_comps/comps_operations/asset_collection_operations.py,sha256=tx_O_CJoW8S04AWL9D6sY3KDd8Bo1aLWt5E2o943pXg,11555
11
+ idmtools_platform_comps/comps_operations/experiment_operations.py,sha256=kpM7bSKvBNnhmHNwcHpz2X5XuMFJVT45aMx4MIV0cms,23756
12
+ idmtools_platform_comps/comps_operations/simulation_operations.py,sha256=uBagWIBSqbWkxyJlkuxRPfPsQGy_PpdFnIPn-iLv2wk,29951
13
+ idmtools_platform_comps/comps_operations/suite_operations.py,sha256=KcjoK1rL6y3wPBU1PHfYBU20Y1Y1Iar5fzjknDh8sf8,7573
14
+ idmtools_platform_comps/comps_operations/workflow_item_operations.py,sha256=zMXjTYc3oNWDvFHv2v4UdIRfzpPTa56qWEjrjzkjgzE,9989
15
+ idmtools_platform_comps/ssmt_operations/__init__.py,sha256=cBNIFW7ml6eFxEMoagrNUAg5-zBpsYgI8O_WcRenITw,218
16
+ idmtools_platform_comps/ssmt_operations/simulation_operations.py,sha256=447SRVUiQMatCwSd5XLwb12ZOylkXU8-ZU-Mi00VJGg,2991
17
+ idmtools_platform_comps/ssmt_operations/workflow_item_operations.py,sha256=T-V__FTFFlGzrEvYVa5XSemI2dhECNx16SCdTXg1WjY,2801
18
+ idmtools_platform_comps/ssmt_work_items/__init__.py,sha256=0OknVYmNvKuidiudz3I8z8Kf8vtL5QF_vcoccqAODQM,104
19
+ idmtools_platform_comps/ssmt_work_items/comps_work_order_task.py,sha256=caGz5oFZkiDhSHBdn4XYkmFHWAPVK6BRybQ-9TrrYUM,873
20
+ idmtools_platform_comps/ssmt_work_items/comps_workitems.py,sha256=7nMsv-L4_A-ugSFM6qcM82fy3pYP8P95j-33BFupFwg,3717
21
+ idmtools_platform_comps/ssmt_work_items/icomps_workflowitem.py,sha256=yUpETmG4geXJAIrtVHh7mUFqSpdfYsjKnmtH-2c6qYs,1897
22
+ idmtools_platform_comps/ssmt_work_items/work_order.py,sha256=G6kcqZb-OLzykbNLtIDDFyS4fhiU-OPbgnmOnfmMImo,1653
23
+ idmtools_platform_comps/utils/__init__.py,sha256=eerSmYyuqPdwpt6aHUEsPjhNcYGaSfQOQdLJ-8rhBDo,100
24
+ idmtools_platform_comps/utils/base_singularity_work_order.json,sha256=YCrJSkhiX5igP_VYjMNlunUs0Y9jueWCPj5L5eGZYYA,87
25
+ idmtools_platform_comps/utils/download_experiment.py,sha256=5hkrYD90tMDjM9Vgw3YjNyCMe4qUt9LVUJCbRH0qMFw,3333
26
+ idmtools_platform_comps/utils/file_filter_workitem.py,sha256=0d1ApTZQGVP-9EaJhYB8h88yjZRZ1nACvz6rN5foxY4,21074
27
+ idmtools_platform_comps/utils/general.py,sha256=Xp8au0JSK_E5cIOMkQSJ0ppGMWhirxODoZVOWYlSe_o,12366
28
+ idmtools_platform_comps/utils/linux_mounts.py,sha256=xai-RUIm6dPnjYamgEjc4lYiJBpZqyupbSVNinB_XmQ,2605
29
+ idmtools_platform_comps/utils/lookups.py,sha256=PBMuRaENuJEYxYkd1PA7aFDBDIOM7IX2Xqi5sEc3OHY,4378
30
+ idmtools_platform_comps/utils/package_version.py,sha256=r1UyATqvMCOMKCbwHCUMniGHv8RJGrd68jc28Yt7UMo,16149
31
+ idmtools_platform_comps/utils/python_version.py,sha256=15DxlGjo4lrKm2w43dD2_Vf7p5oKfOoF9g8W7qp9zlI,1290
32
+ idmtools_platform_comps/utils/scheduling.py,sha256=-hkNSXtHzd1BT_InbGq5CUB-ChN0L1K6Bd9oai91N3g,6173
33
+ idmtools_platform_comps/utils/singularity_build.py,sha256=TzbabKEbsP6rlADF7hZ6C4TyOEVMP7bNKIi9FSTeoh8,20569
34
+ idmtools_platform_comps/utils/spatial_output.py,sha256=bNSwjb957D0L3BKo-wOPmTAg5lGMEVTIz6ypA12C6fQ,2334
35
+ idmtools_platform_comps/utils/sweeping.py,sha256=8GofrbofLrJu9POQNl09lNoZk1d6nWlPaIjgEaajcxw,5434
36
+ idmtools_platform_comps/utils/assetize_output/__init__.py,sha256=hRdtgRQ4EQNTXZQXJ4_Ym9dG7Bn49cCsum3JEdHa3pA,104
37
+ idmtools_platform_comps/utils/assetize_output/assetize_output.py,sha256=HhZCbdb29UFwhMYofupzsLPtt2bqE_oMHWZs17fztZM,5314
38
+ idmtools_platform_comps/utils/assetize_output/assetize_ssmt_script.py,sha256=nUSvFEFeuLLaXttM9NgguiLKtdjULCzYoAhfcd7IuN0,4844
39
+ idmtools_platform_comps/utils/download/__init__.py,sha256=y9lZ4H9k0MbHS70b02BUnpF4lSoTDKrjDnWM67nrpQU,106
40
+ idmtools_platform_comps/utils/download/download.py,sha256=VFJALnMJtUz39xRaqyLcXOz1gimwcn3iZE6vsB6oJPo,6871
41
+ idmtools_platform_comps/utils/download/download_ssmt.py,sha256=Iu2ggZlLbq5nBQi2Fh4dKjscqXK_tE_d-oLET3_FADU,3194
42
+ idmtools_platform_comps/utils/python_requirements_ac/__init__.py,sha256=5SB84oji6LJ9TD_c_WT8OXgvonDuGfSW6joe3PHQJec,117
43
+ idmtools_platform_comps/utils/python_requirements_ac/create_asset_collection.py,sha256=14xYbrfc5pew4hI0iTN_wb5wq0T3SUlbLbxri8WkQJY,5042
44
+ idmtools_platform_comps/utils/python_requirements_ac/install_requirements.py,sha256=0Oo1SEbBoC8EDvNwmWz1s2xp3w62zExGd0oEmJp6RmU,3515
45
+ idmtools_platform_comps/utils/python_requirements_ac/requirements_to_asset_collection.py,sha256=aMgmlgqcB0_eYe3bdhKyjgXhe2b2LWedOYowB6xZOOk,13632
46
+ idmtools_platform_comps/utils/ssmt_utils/__init__.py,sha256=9p8SmJ5g21Tk2dOAkfc3Kh8MZ3uWEMWo-ysdk4Wllak,158
47
+ idmtools_platform_comps/utils/ssmt_utils/common.py,sha256=67-sGWOBnJaR31BE6SvtZ2ajFF57lc_jsmvH3eJ_wDY,2272
48
+ idmtools_platform_comps/utils/ssmt_utils/file_filter.py,sha256=Nx2_OF4kXDMgO48BhbIcglNJgUim-tdcZ7gsTJMCbfI,26810
49
+ idmtools_platform_comps-0.0.2.dist-info/licenses/LICENSE.TXT,sha256=l9S8Ydr_LcejxKoqK8191ZAOsmVX-nJLSPoLKZDUgcg,197
50
+ ssmt_image/Dockerfile,sha256=5cENyIiv8hnmmGHxEW1vCGgsJsQ2T-sq4Nvdbjz3k_Q,1787
51
+ ssmt_image/Makefile,sha256=kq4BufedyACnD9Z96ypNXsuNI__UEhH73IILuSoOaOk,620
52
+ ssmt_image/__init__.py,sha256=tKN1Oxn8Y7VjaLoKeOviyb_MNrdyTru1NRkxaKWRyM8,130
53
+ ssmt_image/bootstrap.sh,sha256=V0psR_4rJ-sWcmsy-XDnNrbqkgpAXu1rrwVUlRpHgNQ,755
54
+ ssmt_image/build_docker_image.py,sha256=v1zlLTn8TU0HlClUGvmAdcUUMHa0vZcI2uvqK22cq4E,6671
55
+ ssmt_image/pip.conf,sha256=hKl-m_qBXwyQ3QU_lq5tber-7MVizUomo9Kxw5Snb-I,157
56
+ ssmt_image/push_docker_image.py,sha256=GshSewoKZAibWh32YKFWTv9nu78HSXJD6FOY1HcIVvE,1806
57
+ ssmt_image/requirements.txt,sha256=1jO8Nl0sU0fqOdVwIf0bXHK8DiVjRezbTKZUug4Bmn4,135
58
+ idmtools_platform_comps-0.0.2.dist-info/METADATA,sha256=dSWkDTi2ERgazHwdW9iNb2pXnMIlMS_8ozlJBPb1HTA,3793
59
+ idmtools_platform_comps-0.0.2.dist-info/WHEEL,sha256=wUyA8OaulRlbfwMtmQsvNngGrxQHAvkKcvRmdizlJi0,92
60
+ idmtools_platform_comps-0.0.2.dist-info/entry_points.txt,sha256=y9ye9nY5E2wjFygMgGnvW9pLyZG4a8FW_0vVjgyH06Q,354
61
+ idmtools_platform_comps-0.0.2.dist-info/top_level.txt,sha256=JGCUUIm6XvUKwv2sqP1HMROi7fMhZxD5q5uhiILd0C0,35
62
+ idmtools_platform_comps-0.0.2.dist-info/RECORD,,
@@ -0,0 +1,9 @@
1
+ [console_scripts]
2
+ comps-cli = idmtools_platform_comps.cli.comps:comps
3
+
4
+ [idmtools_cli.cli_plugins]
5
+ comps_subcommand = idmtools_platform_comps.cli.comps:comps
6
+
7
+ [idmtools_platform]
8
+ idmtools_platform_comps = idmtools_platform_comps.plugin_info:COMPSPlatformSpecification
9
+ idmtools_platform_ssmt = idmtools_platform_comps.plugin_info:SSMTPlatformSpecification
@@ -0,0 +1,3 @@
1
+ idmtools is licensed under the Creative Commons Attribution-Noncommercial-ShareAlike 4.0 License.
2
+
3
+ To view a copy of this license, visit https://creativecommons.org/licenses/by-nc-sa/4.0/legalcode
ssmt_image/Dockerfile ADDED
@@ -0,0 +1,52 @@
1
+ FROM ubuntu:20.04
2
+
3
+ # Install dependencies
4
+ RUN apt-get update
5
+
6
+ ENV PYTHONPATH=./Assets/:./Assets/site-packages/:.
7
+ # set the timezone - do this before installing python
8
+ RUN export DEBIAN_FRONTEND=noninteractive && \
9
+ apt-get update && \
10
+ apt-get install -y tzdata
11
+ RUN ln -fs /usr/share/zoneinfo/America/Los_Angeles /etc/localtime
12
+ RUN dpkg-reconfigure --frontend noninteractive tzdata
13
+
14
+ # install Python3
15
+ RUN apt-get install -y python3-pip
16
+ RUN apt-get install -y python3-dev
17
+ RUN pip install --upgrade pip setuptools
18
+
19
+ # r packages to support analysis in R
20
+ RUN apt-get install -y xz-utils llvm r-base \
21
+ # clean up temporary data
22
+ && mkdir -p /root/.pip
23
+
24
+ # && apt-get clean && \ <--- We do this at the end of this file
25
+ # mkdir -p /root/.pip && \
26
+ # rm -rf /var/lib/apt/lists/* <--- We do this at the end of this file
27
+
28
+ # add requirements file
29
+ ADD requirements.txt /tmp/
30
+ # set default index to IDM Pip Prod(Caching and internal packages IDMTools may depend on like pyComps
31
+ ADD pip.conf /etc/pip.conf
32
+
33
+ COPY .depends/* /tmp/
34
+
35
+ RUN pip3 install -U pip && \
36
+ pip install pygit2
37
+
38
+ RUN bash -c "pip3 install /tmp/*.gz --index-url=https://packages.idmod.org/api/pypi/pypi-production/simple"
39
+
40
+ # make the PIP index configurable so we can build against staging, production, or a local PyPI server
41
+ ARG SSMT_VERSION
42
+
43
+ # Install the packages
44
+ RUN pip3 install --upgrade pip --index-url=https://pypi.python.org/simple && \
45
+ pip3 install dataclasses && \
46
+ pip3 install -r /tmp/requirements.txt && \
47
+ rm -rf /root/.cache
48
+ # To make this effective, we need to collapse this to one layer....... so don't do it for now
49
+ # remove stuff we needed for pip but don't want in our final image
50
+ # apt-get remove build-essential
51
+
52
+ RUN apt-get clean && rm -rf /var/lib/apt/lists/*
ssmt_image/Makefile ADDED
@@ -0,0 +1,21 @@
1
+ .PHONY: help clean clean-all docker docker-release-staging
2
+ IPY=python -c
3
+ PY?=python
4
+ PDS=$(PY) ../../dev_scripts/
5
+ PDR=$(PDS)run.py
6
+
7
+ help:
8
+ help-from-makefile -f ./Makefile
9
+
10
+ clean-all: clean ## Deleting package info hides plugins so we only want to do that for packaging
11
+ $(CLDIR) --dir-patterns "**/*.egg-info/"
12
+ docker rmi idmtools_comps_ssmt_worker
13
+
14
+ docker: ## Build our docker image using the local pypi
15
+ $(MAKE) -C ../../idmtools_core dist
16
+ $(MAKE) -C ../../idmtools_models dist
17
+ $(MAKE) -C ../../idmtools_platform_comps dist
18
+ python build_docker_image.py
19
+
20
+ docker-release-staging: docker
21
+ python push_docker_image.py
ssmt_image/__init__.py ADDED
@@ -0,0 +1,6 @@
1
+ """idmtools comps platform.
2
+
3
+ Build docker image.
4
+
5
+ Copyright 2021, Bill & Melinda Gates Foundation. All rights reserved.
6
+ """
@@ -0,0 +1,30 @@
1
+ #!/bin/bash
2
+ #
3
+ echo "---> bootstrap.sh: Starting"
4
+ cd $COMPS_WORKING_DIR
5
+ echo "---> bootstrap.sh: Environment variables:"
6
+ env
7
+ echo "---> bootstrap.sh: End of environment variables."
8
+
9
+ if [[ $COMPS_WORKING_DIR != $PWD ]]; then
10
+ exit 254
11
+ fi
12
+ EXITCODE=255
13
+ if [[ -z "${COMPS_STARTUP_CMD// }" ]]; then
14
+ echo "---> bootstrap.sh: COMPS_STARTUP_CMD environment variable not specified."
15
+ else
16
+ echo Executing system command: $COMPS_STARTUP_CMD
17
+ eval "$COMPS_STARTUP_CMD"
18
+ EXITCODE=$?
19
+ fi
20
+
21
+ if [[ -z "${COMPS_USER_CMD// }" ]]; then
22
+ echo "---> bootstrap.sh: COMPS_USER_CMD environment variable not specified."
23
+ else
24
+ echo Executing user command: $COMPS_USER_CMD
25
+ eval "$COMPS_USER_CMD"
26
+ EXITCODE=$?
27
+ fi
28
+
29
+ echo "---> bootstrap.sh: Finished ($EXITCODE)"
30
+ exit $EXITCODE
@@ -0,0 +1,161 @@
1
+ """This script is currently a workaround so that we can use bump2version with docker since the nightly versions doesn't work with docker registry.
2
+
3
+ Notes:
4
+ If you are using this script locally, you need to set the environment variables *PYPI_STAGING_USERNAME* and *PYPI_STAGING_PASSWORD*.
5
+ These can be set to your idm email/password
6
+
7
+ Copyright 2021, Bill & Melinda Gates Foundation. All rights reserved.
8
+ """
9
+ import argparse
10
+ import glob
11
+ import os
12
+ import shutil
13
+ import subprocess
14
+ from logging import getLogger, basicConfig, DEBUG, INFO
15
+ import sys
16
+ from getpass import getpass
17
+ import requests
18
+ from requests.auth import HTTPBasicAuth
19
+ import keyring
20
+ from natsort import natsorted
21
+
22
+
23
+ logger = getLogger(__name__)
24
+ # Global Configurations
25
+ KEYRING_NAME = "idmtools_ssmt_builder"
26
+ BASE_REPO = 'packages.idmod.org'
27
+ REPO_KEY = 'idm-docker-staging'
28
+ DOCKER_REPO = f'{REPO_KEY}.{BASE_REPO}'
29
+ IMAGE_NAME = 'idmtools/comps_ssmt_worker'
30
+ BASE_IMAGE_NAME = f'{DOCKER_REPO}/{IMAGE_NAME}'
31
+ CURRENT_DIRECTORY = os.path.dirname(__file__)
32
+ BASE_VERSION = open(os.path.join(CURRENT_DIRECTORY, '..', 'VERSION')).read().strip()
33
+
34
+ logger.info("Please be sure you are logged into the docker-production.packages.idmod.org Docker Repo")
35
+ BASE_DIR = os.path.abspath(os.path.join(CURRENT_DIRECTORY, '..', '..'))
36
+ LOCAL_PACKAGE_DIR = os.path.join(BASE_DIR, 'idmtools_platform_comps/ssmt_image')
37
+
38
+
39
+ def get_dependency_packages():
40
+ """
41
+ Get python packages required to build image.
42
+
43
+ Returns:
44
+ None
45
+ """
46
+ os.makedirs(os.path.abspath('.depends'), exist_ok=True)
47
+ for root, _dirs, files in os.walk(os.path.join(LOCAL_PACKAGE_DIR, '.depends')):
48
+ for file in files:
49
+ os.remove(os.path.join(root, file))
50
+ for package in ['idmtools_core', 'idmtools_models', 'idmtools_platform_comps']:
51
+ for file in glob.glob(os.path.join(BASE_DIR, package, 'dist', '**.gz')):
52
+ shutil.copy(file, os.path.join(LOCAL_PACKAGE_DIR, '.depends', os.path.basename(file)))
53
+
54
+
55
+ def get_username_and_password(disable_keyring_load=False, disable_keyring_save=False):
56
+ """
57
+ Try to get username.
58
+
59
+ It first attempts loading from environment vars, then keyring if not disabled, then lastly prompts.
60
+
61
+ Args:
62
+ disable_keyring_load: Disable loading credentials from keyring
63
+ disable_keyring_save: Disable keyring save
64
+
65
+ Returns:
66
+ Username password
67
+ """
68
+ if 'PYPI_STAGING_USERNAME' in os.environ:
69
+ logger.info("Loading Credentials from environment")
70
+ if 'PYPI_STAGING_PASSWORD' not in os.environ:
71
+ logger.error("When specifying username from environment variable, you must also specify password")
72
+ sys.exit(-1)
73
+ username = os.environ['PYPI_STAGING_USERNAME']
74
+ password = os.environ['PYPI_STAGING_PASSWORD']
75
+ elif not disable_keyring_load and keyring.get_credential(KEYRING_NAME, "username"):
76
+ username = keyring.get_password(KEYRING_NAME, "username")
77
+ password = keyring.get_password(KEYRING_NAME, "password")
78
+ else:
79
+ username = input('Username:')
80
+ password = getpass(prompt='Password:')
81
+ if not disable_keyring_save:
82
+ logger.info("Saving Credentials")
83
+ keyring.set_password(KEYRING_NAME, "username", username)
84
+ keyring.set_password(KEYRING_NAME, "password", password)
85
+ return username, password
86
+
87
+
88
+ def get_latest_image_version_from_registry(username, password):
89
+ """
90
+ Fetch the latest image version from repo.
91
+
92
+ Returns:
93
+ Latest version published in the registry
94
+ """
95
+ url = f'https://{BASE_REPO}/artifactory/api/docker/{REPO_KEY}/v2/{IMAGE_NAME}/tags/list'
96
+ auth = HTTPBasicAuth(username=username, password=password)
97
+ logger.info(f"Loading Credentials from {url}")
98
+ response = requests.get(url, auth=auth)
99
+ logger.debug(f"Return Code: {response.status_code}")
100
+ if response.status_code != 200:
101
+ print(response.status_code)
102
+ print(response.content)
103
+ raise Exception('Could not load images')
104
+ else:
105
+ images = natsorted(response.json()['tags'], reverse=True)
106
+ images = [i for i in images if len(i) > 6]
107
+ logger.debug(f"Images: {images}")
108
+ last_version = images[0]
109
+ logger.info(f"Last Version {url}")
110
+ version_parts = last_version.split('.')
111
+ base_part = '.'.join(version_parts[:-1])
112
+ if BASE_VERSION in base_part:
113
+ version_parts[-1] = str(int(version_parts[-1]) + 1)
114
+ version = '.'.join(version_parts)
115
+ else:
116
+ version = f'{BASE_VERSION}.0'
117
+ logger.info(f"Next Version: {version}")
118
+ return version
119
+
120
+
121
+ def build_image(username, password, disable_keyring_load, disable_keyring_save):
122
+ """
123
+ Run the docker build command.
124
+
125
+ Args:
126
+ username: Username to use with registry
127
+ password: Password to use with registry
128
+ disable_keyring_load: Disable keyring which caches passwords
129
+ disable_keyring_save: Disable caching password to the keyring
130
+
131
+ Returns:
132
+ None
133
+ """
134
+ if username is None or password is None:
135
+ username, password = get_username_and_password(disable_keyring_load, disable_keyring_save)
136
+ get_dependency_packages()
137
+ version = get_latest_image_version_from_registry(username, password)
138
+ cmd = ['docker', 'build', '--network=host', '--build-arg', f'SSMT_VERSION={version}', '--tag',
139
+ f'{DOCKER_REPO}/{IMAGE_NAME}:{version}', '.']
140
+ logger.info(f'Running: {" ".join(cmd)}')
141
+ p = subprocess.Popen(" ".join(cmd), cwd=os.path.abspath(os.path.dirname(__file__)), shell=True)
142
+ p.wait()
143
+
144
+ if p.returncode == 0:
145
+ logger.info("Tagging image")
146
+ os.system(f'docker tag {DOCKER_REPO}/{IMAGE_NAME}:{version} {DOCKER_REPO}/{IMAGE_NAME}:{version[:-2]}')
147
+ sys.exit(p.returncode)
148
+
149
+
150
+ if __name__ == "__main__":
151
+ parser = argparse.ArgumentParser("Build SSMT Image")
152
+ parser.add_argument("--username", default=None, help="Docker Production Username")
153
+ parser.add_argument("--password", default=None, help="Docker Production Password")
154
+ parser.add_argument("--disable-keyring-load", default=False, help="Disable loading password from keyring")
155
+ parser.add_argument("--disable-keyring-save", default=False, help="Disable saving password to keyring after user prompts")
156
+ parser.add_argument("--verbose", default=False, help="Enable Debug logging")
157
+ parser.add_argument("--debug", default=False, help="Enable Debug logging")
158
+ args = parser.parse_args()
159
+
160
+ basicConfig(filename="build.log", level=DEBUG if any([args.verbose, args.debug]) else INFO)
161
+ build_image(args.username, args.password, args.disable_keyring_load, args.disable_keyring_save)
ssmt_image/pip.conf ADDED
@@ -0,0 +1,3 @@
1
+ [global]
2
+ index-url = https://packages.idmod.org/api/pypi/pypi-production/simple
3
+ extra-index-url = https://packages.idmod.org/api/pypi/pypi-production/simple