ivoryos 1.2.0b1__tar.gz → 1.2.2__tar.gz

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.

Potentially problematic release.


This version of ivoryos might be problematic. Click here for more details.

Files changed (118) hide show
  1. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/PKG-INFO +69 -35
  2. ivoryos-1.2.0b1/ivoryos.egg-info/PKG-INFO → ivoryos-1.2.2/README.md +51 -41
  3. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/__init__.py +22 -1
  4. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/config.py +1 -0
  5. ivoryos-1.2.2/ivoryos/optimizer/ax_optimizer.py +164 -0
  6. ivoryos-1.2.2/ivoryos/optimizer/base_optimizer.py +65 -0
  7. ivoryos-1.2.2/ivoryos/optimizer/baybe_optimizer.py +183 -0
  8. ivoryos-1.2.2/ivoryos/optimizer/registry.py +9 -0
  9. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/routes/auth/auth.py +3 -1
  10. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/routes/data/data.py +2 -0
  11. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/routes/design/design.py +4 -4
  12. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/routes/library/library.py +4 -4
  13. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/utils/script_runner.py +1 -1
  14. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/utils/serilize.py +4 -6
  15. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/utils/utils.py +2 -1
  16. ivoryos-1.2.2/ivoryos/version.py +1 -0
  17. ivoryos-1.2.0b1/README.md → ivoryos-1.2.2/ivoryos.egg-info/PKG-INFO +75 -30
  18. ivoryos-1.2.2/ivoryos.egg-info/SOURCES.txt +50 -0
  19. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos.egg-info/requires.txt +5 -1
  20. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos.egg-info/top_level.txt +0 -1
  21. ivoryos-1.2.2/pyproject.toml +38 -0
  22. ivoryos-1.2.0b1/MANIFEST.in +0 -8
  23. ivoryos-1.2.0b1/ivoryos/routes/auth/templates/login.html +0 -25
  24. ivoryos-1.2.0b1/ivoryos/routes/auth/templates/signup.html +0 -32
  25. ivoryos-1.2.0b1/ivoryos/routes/control/templates/controllers.html +0 -166
  26. ivoryos-1.2.0b1/ivoryos/routes/control/templates/controllers_new.html +0 -112
  27. ivoryos-1.2.0b1/ivoryos/routes/data/templates/components/step_card.html +0 -13
  28. ivoryos-1.2.0b1/ivoryos/routes/data/templates/workflow_database.html +0 -109
  29. ivoryos-1.2.0b1/ivoryos/routes/data/templates/workflow_view.html +0 -130
  30. ivoryos-1.2.0b1/ivoryos/routes/design/templates/components/action_form.html +0 -53
  31. ivoryos-1.2.0b1/ivoryos/routes/design/templates/components/actions_panel.html +0 -25
  32. ivoryos-1.2.0b1/ivoryos/routes/design/templates/components/autofill_toggle.html +0 -10
  33. ivoryos-1.2.0b1/ivoryos/routes/design/templates/components/canvas.html +0 -5
  34. ivoryos-1.2.0b1/ivoryos/routes/design/templates/components/canvas_footer.html +0 -9
  35. ivoryos-1.2.0b1/ivoryos/routes/design/templates/components/canvas_header.html +0 -75
  36. ivoryos-1.2.0b1/ivoryos/routes/design/templates/components/canvas_main.html +0 -34
  37. ivoryos-1.2.0b1/ivoryos/routes/design/templates/components/deck_selector.html +0 -10
  38. ivoryos-1.2.0b1/ivoryos/routes/design/templates/components/edit_action_form.html +0 -38
  39. ivoryos-1.2.0b1/ivoryos/routes/design/templates/components/instruments_panel.html +0 -66
  40. ivoryos-1.2.0b1/ivoryos/routes/design/templates/components/modals/drop_modal.html +0 -17
  41. ivoryos-1.2.0b1/ivoryos/routes/design/templates/components/modals/json_modal.html +0 -22
  42. ivoryos-1.2.0b1/ivoryos/routes/design/templates/components/modals/new_script_modal.html +0 -17
  43. ivoryos-1.2.0b1/ivoryos/routes/design/templates/components/modals/rename_modal.html +0 -23
  44. ivoryos-1.2.0b1/ivoryos/routes/design/templates/components/modals/saveas_modal.html +0 -27
  45. ivoryos-1.2.0b1/ivoryos/routes/design/templates/components/modals.html +0 -6
  46. ivoryos-1.2.0b1/ivoryos/routes/design/templates/components/python_code_overlay.html +0 -39
  47. ivoryos-1.2.0b1/ivoryos/routes/design/templates/components/sidebar.html +0 -15
  48. ivoryos-1.2.0b1/ivoryos/routes/design/templates/components/text_to_code_panel.html +0 -20
  49. ivoryos-1.2.0b1/ivoryos/routes/design/templates/experiment_builder.html +0 -41
  50. ivoryos-1.2.0b1/ivoryos/routes/execute/templates/components/error_modal.html +0 -20
  51. ivoryos-1.2.0b1/ivoryos/routes/execute/templates/components/logging_panel.html +0 -31
  52. ivoryos-1.2.0b1/ivoryos/routes/execute/templates/components/progress_panel.html +0 -27
  53. ivoryos-1.2.0b1/ivoryos/routes/execute/templates/components/run_panel.html +0 -9
  54. ivoryos-1.2.0b1/ivoryos/routes/execute/templates/components/run_tabs.html +0 -17
  55. ivoryos-1.2.0b1/ivoryos/routes/execute/templates/components/tab_bayesian.html +0 -399
  56. ivoryos-1.2.0b1/ivoryos/routes/execute/templates/components/tab_configuration.html +0 -98
  57. ivoryos-1.2.0b1/ivoryos/routes/execute/templates/components/tab_repeat.html +0 -14
  58. ivoryos-1.2.0b1/ivoryos/routes/execute/templates/experiment_run.html +0 -294
  59. ivoryos-1.2.0b1/ivoryos/routes/library/templates/library.html +0 -91
  60. ivoryos-1.2.0b1/ivoryos/routes/main/templates/help.html +0 -141
  61. ivoryos-1.2.0b1/ivoryos/routes/main/templates/home.html +0 -103
  62. ivoryos-1.2.0b1/ivoryos/static/favicon.ico +0 -0
  63. ivoryos-1.2.0b1/ivoryos/static/gui_annotation/Slide1.png +0 -0
  64. ivoryos-1.2.0b1/ivoryos/static/gui_annotation/Slide2.PNG +0 -0
  65. ivoryos-1.2.0b1/ivoryos/static/js/action_handlers.js +0 -213
  66. ivoryos-1.2.0b1/ivoryos/static/js/db_delete.js +0 -23
  67. ivoryos-1.2.0b1/ivoryos/static/js/overlay.js +0 -12
  68. ivoryos-1.2.0b1/ivoryos/static/js/script_metadata.js +0 -39
  69. ivoryos-1.2.0b1/ivoryos/static/js/socket_handler.js +0 -125
  70. ivoryos-1.2.0b1/ivoryos/static/js/sortable_card.js +0 -24
  71. ivoryos-1.2.0b1/ivoryos/static/js/sortable_design.js +0 -138
  72. ivoryos-1.2.0b1/ivoryos/static/js/ui_state.js +0 -113
  73. ivoryos-1.2.0b1/ivoryos/static/logo.webp +0 -0
  74. ivoryos-1.2.0b1/ivoryos/static/style.css +0 -211
  75. ivoryos-1.2.0b1/ivoryos/templates/base.html +0 -157
  76. ivoryos-1.2.0b1/ivoryos/version.py +0 -1
  77. ivoryos-1.2.0b1/ivoryos.egg-info/SOURCES.txt +0 -109
  78. ivoryos-1.2.0b1/setup.py +0 -38
  79. ivoryos-1.2.0b1/tests/__init__.py +0 -0
  80. ivoryos-1.2.0b1/tests/conftest.py +0 -133
  81. ivoryos-1.2.0b1/tests/integration/__init__.py +0 -0
  82. ivoryos-1.2.0b1/tests/integration/test_route_auth.py +0 -80
  83. ivoryos-1.2.0b1/tests/integration/test_route_control.py +0 -94
  84. ivoryos-1.2.0b1/tests/integration/test_route_database.py +0 -61
  85. ivoryos-1.2.0b1/tests/integration/test_route_design.py +0 -36
  86. ivoryos-1.2.0b1/tests/integration/test_route_main.py +0 -35
  87. ivoryos-1.2.0b1/tests/integration/test_sockets.py +0 -26
  88. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/LICENSE +0 -0
  89. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/routes/__init__.py +0 -0
  90. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/routes/api/api.py +0 -0
  91. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/routes/auth/__init__.py +0 -0
  92. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/routes/control/__init__.py +0 -0
  93. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/routes/control/control.py +0 -0
  94. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/routes/control/control_file.py +0 -0
  95. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/routes/control/control_new_device.py +0 -0
  96. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/routes/control/utils.py +0 -0
  97. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/routes/data/__init__.py +0 -0
  98. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/routes/design/__init__.py +0 -0
  99. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/routes/design/design_file.py +0 -0
  100. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/routes/design/design_step.py +0 -0
  101. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/routes/execute/__init__.py +0 -0
  102. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/routes/execute/execute.py +0 -0
  103. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/routes/execute/execute_file.py +0 -0
  104. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/routes/library/__init__.py +0 -0
  105. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/routes/main/__init__.py +0 -0
  106. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/routes/main/main.py +0 -0
  107. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/socket_handlers.py +0 -0
  108. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/utils/__init__.py +0 -0
  109. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/utils/bo_campaign.py +0 -0
  110. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/utils/client_proxy.py +0 -0
  111. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/utils/db_models.py +0 -0
  112. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/utils/form.py +0 -0
  113. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/utils/global_config.py +0 -0
  114. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/utils/llm_agent.py +0 -0
  115. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/utils/py_to_json.py +0 -0
  116. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos/utils/task_runner.py +0 -0
  117. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/ivoryos.egg-info/dependency_links.txt +0 -0
  118. {ivoryos-1.2.0b1 → ivoryos-1.2.2}/setup.cfg +0 -0
@@ -1,13 +1,26 @@
1
- Metadata-Version: 2.1
1
+ Metadata-Version: 2.4
2
2
  Name: ivoryos
3
- Version: 1.2.0b1
3
+ Version: 1.2.2
4
4
  Summary: an open-source Python package enabling Self-Driving Labs (SDLs) interoperability
5
- Home-page: https://gitlab.com/heingroup/ivoryos
6
- Author: Ivory Zhang
7
- Author-email: ivoryzhang@chem.ubc.ca
5
+ Author-email: Ivory Zhang <ivoryzhang@chem.ubc.ca>
8
6
  License: MIT
7
+ Project-URL: Homepage, https://gitlab.com/heingroup/ivoryos
8
+ Requires-Python: >=3.7
9
9
  Description-Content-Type: text/markdown
10
10
  License-File: LICENSE
11
+ Requires-Dist: bcrypt
12
+ Requires-Dist: Flask-Login
13
+ Requires-Dist: Flask-Session
14
+ Requires-Dist: Flask-SocketIO
15
+ Requires-Dist: Flask-SQLAlchemy
16
+ Requires-Dist: Flask-WTF
17
+ Requires-Dist: SQLAlchemy-Utils
18
+ Requires-Dist: python-dotenv
19
+ Requires-Dist: astor; python_version < "3.9"
20
+ Provides-Extra: optimizer
21
+ Requires-Dist: ax-platform; extra == "optimizer"
22
+ Requires-Dist: baybe; extra == "optimizer"
23
+ Dynamic: license-file
11
24
 
12
25
  [![Documentation Status](https://readthedocs.org/projects/ivoryos/badge/?version=latest)](https://ivoryos.readthedocs.io/en/latest/?badge=latest)
13
26
  [![PyPI version](https://img.shields.io/pypi/v/ivoryos)](https://pypi.org/project/ivoryos/)
@@ -39,7 +52,7 @@ With the least modification of the current workflow, user can design, manage and
39
52
  This software is developed and tested using Windows. This software and its dependencies are compatible across major platforms: Linux, macOS, and Windows. Some dependencies (Flask-SQLAlchemy) may require additional setup.
40
53
 
41
54
  ### Python Version
42
- Python >=3.10 for best compatibility. Python >=3.7 without Ax.
55
+ Python >=3.10 for the best compatibility. Python >=3.7 without Ax.
43
56
  ### Python dependencies
44
57
  This software is compatible with the latest versions of all dependencies.
45
58
  - bcrypt~=4.0
@@ -50,7 +63,9 @@ This software is compatible with the latest versions of all dependencies.
50
63
  - SQLAlchemy-Utils~=0.41
51
64
  - Flask-WTF~=1.2
52
65
  - python-dotenv==1.0.1
53
- - ax-platform (optional ~=0.4 for Python>=3.9)
66
+ - ax-platform (optional 1.0 for Python>=3.10)
67
+ - baybe (optional)
68
+
54
69
 
55
70
  ## Installation
56
71
  ```bash
@@ -74,43 +89,60 @@ import ivoryos
74
89
  ivoryos.run(__name__)
75
90
  ```
76
91
  ### Login
77
- Create an account and login (local database)
92
+ Create an account and login (local database with bcrypt password)
78
93
  ### Features
79
- - **Direct control**: direct function calling _Device_ tab
80
- - **Workflow design and iteration**:
81
- - **Design**: add function to canvas in _Design_ tab. click `Compile and Run` button to go to the execution page
82
- - **Execution**: configure iteration methods and parameters in _Compile/Run_ tab.
83
- - **Database**: manage workflows in _Library_ tab.
84
- - **Info page**: additional info in _About_ tab.
94
+ - **Direct control**: direct function calling _Devices_ tab
95
+ - **Workflows**:
96
+ - **Design Editor**: drag/add function to canvas in _Design_ tab. click `Compile and Run` button to go to the execution configuration page
97
+ - **Execution Config**: configure iteration methods and parameters in _Compile/Run_ tab.
98
+ - **Design Library**: manage workflow scripts in _Library_ tab.
99
+ - **Workflow Data**: Execution records are in _Data_ tab.
85
100
 
86
101
  [//]: # (![Discord]&#40;https://img.shields.io/discord/1313641159356059770&#41;)
87
102
 
88
103
  [//]: # (![PyPI - Downloads]&#40;https://img.shields.io/pypi/dm/ivoryos&#41;)
89
104
 
90
105
 
91
- ### Additional settings (not actively maintained)
92
- #### AI assistant
93
- To streamline the experimental design on SDLs, we also integrate Large Language Models (LLMs) to interpret the inspected functions and generate code according to task descriptions.
106
+ ### Additional settings
107
+ [//]: # (#### AI assistant)
94
108
 
95
- #### Enable LLMs with [OpenAI API](https://github.com/openai/openai-python)
96
- 1. Create a `.env` file for `OPENAI_API_KEY`
97
- ```
98
- OPENAI_API_KEY="Your API Key"
99
- ```
100
- 2. In your SDL script, define model, you can use any GPT models.
109
+ [//]: # (To streamline the experimental design on SDLs, we also integrate Large Language Models &#40;LLMs&#41; to interpret the inspected functions and generate code according to task descriptions.)
101
110
 
102
- ```python
103
- ivoryos.run(__name__, model="gpt-3.5-turbo")
104
- ```
111
+ [//]: # ()
112
+ [//]: # (#### Enable LLMs with [OpenAI API]&#40;https://github.com/openai/openai-python&#41;)
105
113
 
106
- #### Enable local LLMs with [Ollama](https://ollama.com/)
107
- 1. Download Ollama.
108
- 2. pull models from Ollama
109
- 3. In your SDL script, define LLM server and model, you can use any models available on Ollama.
114
+ [//]: # (1. Create a `.env` file for `OPENAI_API_KEY`)
110
115
 
111
- ```python
112
- ivoryos.run(__name__, llm_server="localhost", model="llama3.1")
113
- ```
116
+ [//]: # (```)
117
+
118
+ [//]: # (OPENAI_API_KEY="Your API Key")
119
+
120
+ [//]: # (```)
121
+
122
+ [//]: # (2. In your SDL script, define model, you can use any GPT models.)
123
+
124
+ [//]: # ()
125
+ [//]: # (```python)
126
+
127
+ [//]: # (ivoryos.run&#40;__name__, model="gpt-3.5-turbo"&#41;)
128
+
129
+ [//]: # (```)
130
+
131
+ [//]: # ()
132
+ [//]: # (#### Enable local LLMs with [Ollama]&#40;https://ollama.com/&#41;)
133
+
134
+ [//]: # (1. Download Ollama.)
135
+
136
+ [//]: # (2. pull models from Ollama)
137
+
138
+ [//]: # (3. In your SDL script, define LLM server and model, you can use any models available on Ollama.)
139
+
140
+ [//]: # ()
141
+ [//]: # (```python)
142
+
143
+ [//]: # (ivoryos.run&#40;__name__, llm_server="localhost", model="llama3.1"&#41;)
144
+
145
+ [//]: # (```)
114
146
 
115
147
  #### Add additional logger(s)
116
148
  ```python
@@ -135,7 +167,7 @@ ivoryos.run(__name__)
135
167
 
136
168
  * Running on all addresses (0.0.0.0)
137
169
  * Running on http://127.0.0.1:8000
138
- * Running on http://xxx.xx.xx.xxx:8000
170
+ * Running on http://0.0.0.0:8000
139
171
 
140
172
  ### Deck function and web form
141
173
  ![](https://gitlab.com/heingroup/ivoryos/raw/main/docs/source/_static/demo.gif)
@@ -163,6 +195,8 @@ When you run the application for the first time, it will automatically create th
163
195
  - [x] dropdown input ✅
164
196
  - [x] show line number option ✅
165
197
  - [ ] snapshot version control
198
+ - [ ] optimizer-agnostic
199
+ - [ ] check batch-config file compatibility
166
200
 
167
201
  ## Citing
168
202
 
@@ -203,4 +237,4 @@ For an additional perspective related to the development of the tool, please see
203
237
  ## Authors and Acknowledgement
204
238
  Ivory Zhang, Lucy Hao
205
239
 
206
- Authors acknowledge all former and current Hein Lab members for their valuable suggestions.
240
+ Authors acknowledge Telescope Innovations, Hein Lab members for their valuable suggestions and contributions.
@@ -1,14 +1,3 @@
1
- Metadata-Version: 2.1
2
- Name: ivoryos
3
- Version: 1.2.0b1
4
- Summary: an open-source Python package enabling Self-Driving Labs (SDLs) interoperability
5
- Home-page: https://gitlab.com/heingroup/ivoryos
6
- Author: Ivory Zhang
7
- Author-email: ivoryzhang@chem.ubc.ca
8
- License: MIT
9
- Description-Content-Type: text/markdown
10
- License-File: LICENSE
11
-
12
1
  [![Documentation Status](https://readthedocs.org/projects/ivoryos/badge/?version=latest)](https://ivoryos.readthedocs.io/en/latest/?badge=latest)
13
2
  [![PyPI version](https://img.shields.io/pypi/v/ivoryos)](https://pypi.org/project/ivoryos/)
14
3
  ![License](https://img.shields.io/pypi/l/ivoryos)
@@ -39,7 +28,7 @@ With the least modification of the current workflow, user can design, manage and
39
28
  This software is developed and tested using Windows. This software and its dependencies are compatible across major platforms: Linux, macOS, and Windows. Some dependencies (Flask-SQLAlchemy) may require additional setup.
40
29
 
41
30
  ### Python Version
42
- Python >=3.10 for best compatibility. Python >=3.7 without Ax.
31
+ Python >=3.10 for the best compatibility. Python >=3.7 without Ax.
43
32
  ### Python dependencies
44
33
  This software is compatible with the latest versions of all dependencies.
45
34
  - bcrypt~=4.0
@@ -50,7 +39,9 @@ This software is compatible with the latest versions of all dependencies.
50
39
  - SQLAlchemy-Utils~=0.41
51
40
  - Flask-WTF~=1.2
52
41
  - python-dotenv==1.0.1
53
- - ax-platform (optional ~=0.4 for Python>=3.9)
42
+ - ax-platform (optional 1.0 for Python>=3.10)
43
+ - baybe (optional)
44
+
54
45
 
55
46
  ## Installation
56
47
  ```bash
@@ -74,43 +65,60 @@ import ivoryos
74
65
  ivoryos.run(__name__)
75
66
  ```
76
67
  ### Login
77
- Create an account and login (local database)
68
+ Create an account and login (local database with bcrypt password)
78
69
  ### Features
79
- - **Direct control**: direct function calling _Device_ tab
80
- - **Workflow design and iteration**:
81
- - **Design**: add function to canvas in _Design_ tab. click `Compile and Run` button to go to the execution page
82
- - **Execution**: configure iteration methods and parameters in _Compile/Run_ tab.
83
- - **Database**: manage workflows in _Library_ tab.
84
- - **Info page**: additional info in _About_ tab.
70
+ - **Direct control**: direct function calling _Devices_ tab
71
+ - **Workflows**:
72
+ - **Design Editor**: drag/add function to canvas in _Design_ tab. click `Compile and Run` button to go to the execution configuration page
73
+ - **Execution Config**: configure iteration methods and parameters in _Compile/Run_ tab.
74
+ - **Design Library**: manage workflow scripts in _Library_ tab.
75
+ - **Workflow Data**: Execution records are in _Data_ tab.
85
76
 
86
77
  [//]: # (![Discord]&#40;https://img.shields.io/discord/1313641159356059770&#41;)
87
78
 
88
79
  [//]: # (![PyPI - Downloads]&#40;https://img.shields.io/pypi/dm/ivoryos&#41;)
89
80
 
90
81
 
91
- ### Additional settings (not actively maintained)
92
- #### AI assistant
93
- To streamline the experimental design on SDLs, we also integrate Large Language Models (LLMs) to interpret the inspected functions and generate code according to task descriptions.
82
+ ### Additional settings
83
+ [//]: # (#### AI assistant)
94
84
 
95
- #### Enable LLMs with [OpenAI API](https://github.com/openai/openai-python)
96
- 1. Create a `.env` file for `OPENAI_API_KEY`
97
- ```
98
- OPENAI_API_KEY="Your API Key"
99
- ```
100
- 2. In your SDL script, define model, you can use any GPT models.
85
+ [//]: # (To streamline the experimental design on SDLs, we also integrate Large Language Models &#40;LLMs&#41; to interpret the inspected functions and generate code according to task descriptions.)
101
86
 
102
- ```python
103
- ivoryos.run(__name__, model="gpt-3.5-turbo")
104
- ```
87
+ [//]: # ()
88
+ [//]: # (#### Enable LLMs with [OpenAI API]&#40;https://github.com/openai/openai-python&#41;)
105
89
 
106
- #### Enable local LLMs with [Ollama](https://ollama.com/)
107
- 1. Download Ollama.
108
- 2. pull models from Ollama
109
- 3. In your SDL script, define LLM server and model, you can use any models available on Ollama.
90
+ [//]: # (1. Create a `.env` file for `OPENAI_API_KEY`)
110
91
 
111
- ```python
112
- ivoryos.run(__name__, llm_server="localhost", model="llama3.1")
113
- ```
92
+ [//]: # (```)
93
+
94
+ [//]: # (OPENAI_API_KEY="Your API Key")
95
+
96
+ [//]: # (```)
97
+
98
+ [//]: # (2. In your SDL script, define model, you can use any GPT models.)
99
+
100
+ [//]: # ()
101
+ [//]: # (```python)
102
+
103
+ [//]: # (ivoryos.run&#40;__name__, model="gpt-3.5-turbo"&#41;)
104
+
105
+ [//]: # (```)
106
+
107
+ [//]: # ()
108
+ [//]: # (#### Enable local LLMs with [Ollama]&#40;https://ollama.com/&#41;)
109
+
110
+ [//]: # (1. Download Ollama.)
111
+
112
+ [//]: # (2. pull models from Ollama)
113
+
114
+ [//]: # (3. In your SDL script, define LLM server and model, you can use any models available on Ollama.)
115
+
116
+ [//]: # ()
117
+ [//]: # (```python)
118
+
119
+ [//]: # (ivoryos.run&#40;__name__, llm_server="localhost", model="llama3.1"&#41;)
120
+
121
+ [//]: # (```)
114
122
 
115
123
  #### Add additional logger(s)
116
124
  ```python
@@ -135,7 +143,7 @@ ivoryos.run(__name__)
135
143
 
136
144
  * Running on all addresses (0.0.0.0)
137
145
  * Running on http://127.0.0.1:8000
138
- * Running on http://xxx.xx.xx.xxx:8000
146
+ * Running on http://0.0.0.0:8000
139
147
 
140
148
  ### Deck function and web form
141
149
  ![](https://gitlab.com/heingroup/ivoryos/raw/main/docs/source/_static/demo.gif)
@@ -163,6 +171,8 @@ When you run the application for the first time, it will automatically create th
163
171
  - [x] dropdown input ✅
164
172
  - [x] show line number option ✅
165
173
  - [ ] snapshot version control
174
+ - [ ] optimizer-agnostic
175
+ - [ ] check batch-config file compatibility
166
176
 
167
177
  ## Citing
168
178
 
@@ -203,4 +213,4 @@ For an additional perspective related to the development of the tool, please see
203
213
  ## Authors and Acknowledgement
204
214
  Ivory Zhang, Lucy Hao
205
215
 
206
- Authors acknowledge all former and current Hein Lab members for their valuable suggestions.
216
+ Authors acknowledge Telescope Innovations, Hein Lab members for their valuable suggestions and contributions.
@@ -1,8 +1,11 @@
1
1
  import os
2
2
  import sys
3
+ import uuid
3
4
  from typing import Union
4
5
 
5
- from flask import Flask, redirect, url_for, g, Blueprint
6
+ from flask import Flask, redirect, url_for, g, Blueprint, session
7
+ from flask_login import AnonymousUserMixin
8
+
6
9
  sys.path.insert(0, os.path.abspath(os.path.join(os.path.dirname(__file__), '..')))
7
10
 
8
11
  from ivoryos.config import Config, get_config
@@ -90,6 +93,23 @@ def create_app(config_class=None):
90
93
  """
91
94
  g.logger = logger
92
95
  g.socketio = socketio
96
+ session.permanent = False
97
+ # DEMO_MODE: Simulate logged-in user per session
98
+ if app.config.get("DEMO_MODE", False):
99
+ if "demo_user_id" not in session:
100
+ session["demo_user_id"] = f"demo_{str(uuid.uuid4())[:8]}"
101
+
102
+ class SessionDemoUser(AnonymousUserMixin):
103
+ @property
104
+ def is_authenticated(self):
105
+ return True
106
+
107
+ def get_id(self):
108
+ return session.get("demo_user_id")
109
+
110
+ login_manager.anonymous_user = SessionDemoUser
111
+
112
+
93
113
 
94
114
  @app.route('/')
95
115
  def redirect_to_prefix():
@@ -101,6 +121,7 @@ def create_app(config_class=None):
101
121
  text = ' '.join(word for word in name.split('_'))
102
122
  return text.capitalize()
103
123
 
124
+ # app.config.setdefault("DEMO_MODE", False)
104
125
  return app
105
126
 
106
127
 
@@ -43,6 +43,7 @@ class TestingConfig(Config):
43
43
 
44
44
  class DemoConfig(Config):
45
45
  DEBUG = False
46
+ DEMO_MODE = True
46
47
  SQLALCHEMY_DATABASE_URI = 'sqlite:///:memory:'
47
48
  OUTPUT_FOLDER = os.path.join(os.path.abspath(os.curdir), '/tmp/ivoryos_data')
48
49
  CSV_FOLDER = os.path.join(OUTPUT_FOLDER, 'config_csv/')
@@ -0,0 +1,164 @@
1
+ # optimizers/ax_optimizer.py
2
+ from typing import Dict
3
+
4
+
5
+
6
+ from ivoryos.optimizer.base_optimizer import OptimizerBase
7
+ from ivoryos.utils.utils import install_and_import
8
+
9
+ class AxOptimizer(OptimizerBase):
10
+ def __init__(self, experiment_name, parameter_space, objective_config, optimizer_config=None):
11
+ try:
12
+ from ax.api.client import Client
13
+ except ImportError as e:
14
+ install_and_import("ax", "ax-platform")
15
+ raise ImportError("Please install Ax with pip install ax-platform to use AxOptimizer. Attempting to install Ax...")
16
+ super().__init__(experiment_name, parameter_space, objective_config, optimizer_config)
17
+
18
+ self.client = Client()
19
+ # 2. Configure where Ax will search.
20
+ self.client.configure_experiment(
21
+ name=experiment_name,
22
+ parameters=self._convert_parameter_to_ax_format(parameter_space)
23
+ )
24
+ # 3. Configure the objective function.
25
+ self.client.configure_optimization(objective=self._convert_objective_to_ax_format(objective_config))
26
+ if optimizer_config:
27
+ self.client.set_generation_strategy(self._convert_generator_to_ax_format(optimizer_config))
28
+ self.generators = self._create_generator_mapping()
29
+
30
+ @staticmethod
31
+ def _create_generator_mapping():
32
+ """Create a mapping from string values to Generator enum members."""
33
+ from ax.modelbridge import Generators
34
+ return {member.value: member for member in Generators}
35
+
36
+ def _convert_parameter_to_ax_format(self, parameter_space):
37
+ """
38
+ Converts the parameter space configuration to Baybe format.
39
+ :param parameter_space: The parameter space configuration.
40
+ [
41
+ {"name": "param_1", "type": "range", "bounds": [1.0, 2.0], "value_type": "float"},
42
+ {"name": "param_2", "type": "choice", "bounds": ["a", "b", "c"], "value_type": "str"},
43
+ {"name": "param_3", "type": "range", "bounds": [0 10], "value_type": "int"},
44
+ ]
45
+ :return: A list of Baybe parameters.
46
+ """
47
+ from ax import RangeParameterConfig, ChoiceParameterConfig
48
+ ax_params = []
49
+ for p in parameter_space:
50
+ if p["type"] == "range":
51
+ ax_params.append(
52
+ RangeParameterConfig(
53
+ name=p["name"],
54
+ bounds=tuple(p["bounds"]),
55
+ parameter_type=p["value_type"]
56
+ ))
57
+ elif p["type"] == "choice":
58
+ ax_params.append(
59
+ ChoiceParameterConfig(
60
+ name=p["name"],
61
+ values=p["bounds"],
62
+ parameter_type=p["value_type"],
63
+ )
64
+ )
65
+ return ax_params
66
+
67
+ def _convert_objective_to_ax_format(self, objective_config: list):
68
+ """
69
+ Converts the objective configuration to Baybe format.
70
+ :param parameter_space: The parameter space configuration.
71
+ [
72
+ {"name": "obj_1", "minimize": True, "weight": 1},
73
+ {"name": "obj_2", "minimize": False, "weight": 2}
74
+ ]
75
+ :return: Ax objective configuration. "-cost, utility"
76
+ """
77
+ objectives = []
78
+ for obj in objective_config:
79
+ obj_name = obj.get("name")
80
+ minimize = obj.get("minimize", True)
81
+ weight = obj.get("weight", 1)
82
+ sign = "-" if minimize else ""
83
+ objectives.append(f"{sign}{weight} * {obj_name}")
84
+ return ", ".join(objectives)
85
+
86
+ def _convert_generator_to_ax_format(self, optimizer_config):
87
+ """
88
+ Converts the optimizer configuration to Ax format.
89
+ :param optimizer_config: The optimizer configuration.
90
+ :return: Ax generator configuration.
91
+ """
92
+ from ax.generation_strategy.generation_node import GenerationStep
93
+ from ax.generation_strategy.generation_strategy import GenerationStrategy
94
+ generators = self._create_generator_mapping()
95
+ step_1 = optimizer_config.get("step_1", {})
96
+ step_2 = optimizer_config.get("step_2", {})
97
+ step_1_generator = step_1.get("model", "Sobol")
98
+ step_2_generator = step_2.get("model", "BOTorch")
99
+ generator_1 = GenerationStep(model=generators.get(step_1_generator), num_trials=step_1.get("num_samples", 5))
100
+ generator_2 = GenerationStep(model=generators.get(step_2_generator), num_trials=step_2.get("num_samples", -1))
101
+ return GenerationStrategy(steps=[generator_1, generator_2])
102
+
103
+ def suggest(self, n=1):
104
+ trial_index, params = self.client.get_next_trials(1).popitem()
105
+ self.trial_index = trial_index
106
+ return params
107
+
108
+ def observe(self, results):
109
+ self.client.complete_trial(
110
+ trial_index=self.trial_index,
111
+ raw_data=results
112
+ )
113
+
114
+ @staticmethod
115
+ def get_schema():
116
+ return {
117
+ "parameter_types": ["range", "choice"],
118
+ "multiple_objectives": True,
119
+ # "objective_weights": True,
120
+ "optimizer_config": {
121
+ "step_1": {"model": ["Sobol", "Uniform", "Factorial", "Thompson"], "num_samples": 5},
122
+ "step_2": {"model": ["BoTorch", "SAASBO", "SAAS_MTGP", "Legacy_GPEI", "EB", "EB_Ashr", "ST_MTGP", "BO_MIXED", "Contextual_SACBO"]}
123
+ },
124
+ }
125
+
126
+ def append_existing_data(self, existing_data):
127
+ """
128
+ Append existing data to the Ax experiment.
129
+ :param existing_data: A dictionary containing existing data.
130
+ """
131
+ from pandas import DataFrame
132
+ if not existing_data:
133
+ return
134
+ if isinstance(existing_data, DataFrame):
135
+ existing_data = existing_data.to_dict(orient="records")
136
+ parameter_names = [i.get("name") for i in self.parameter_space]
137
+ objective_names = [i.get("name") for i in self.objective_config]
138
+ for name, value in existing_data.items():
139
+ # First attach the trial and note the trial index
140
+ parameters = {name: value for name in existing_data if name in parameter_names}
141
+ trial_index = self.client.attach_trial(parameters=parameters)
142
+ raw_data = {name: value for name in existing_data if name in objective_names}
143
+ # Then complete the trial with the existing data
144
+ self.client.complete_trial(trial_index=trial_index, raw_data=raw_data)
145
+
146
+
147
+ if __name__ == "__main__":
148
+ # Example usage
149
+ optimizer = AxOptimizer(
150
+ experiment_name="example_experiment",
151
+ parameter_space=[
152
+ {"name": "param_1", "type": "range", "bounds": [0.0, 1.0], "value_type": "float"},
153
+ {"name": "param_2", "type": "choice", "bounds": ["a", "b", "c"], "value_type": "str"}
154
+ ],
155
+ objective_config=[
156
+ {"name": "objective_1", "minimize": True},
157
+ {"name": "objective_2", "minimize": False}
158
+ ],
159
+ optimizer_config={
160
+ "step_1": {"model": "Sobol", "num_samples": 5},
161
+ "step_2": {"model": "BoTorch"}
162
+ }
163
+ )
164
+ print(optimizer._create_generator_mapping())
@@ -0,0 +1,65 @@
1
+ ### ivoryos/optimizers/base.py
2
+
3
+ from abc import ABC, abstractmethod
4
+
5
+
6
+
7
+ class OptimizerBase(ABC):
8
+ def __init__(self, experiment_name:str, parameter_space: list, objective_config: dict, optimizer_config: dict):
9
+ """
10
+ :param experiment_name: arbitrary name
11
+ :param parameter_space: list of parameter names
12
+ [
13
+ {"name": "param_1", "type": "range", "bounds": [1.0, 2.0], "value_type": "float"},
14
+ {"name": "param_2", "type": "choice", "bounds": ["a", "b", "c"], "value_type": "str"},
15
+ {"name": "param_3", "type": "range", "bounds": [0 10], "value_type": "int"},
16
+ ]
17
+ :param objective_config: objective configuration
18
+ [
19
+ {"name": "obj_1", "minimize": True, "weight": 1},
20
+ {"name": "obj_2", "minimize": False, "weight": 1}
21
+ ]
22
+ :param optimizer_config: optimizer configuration
23
+ optimizer_config={
24
+ "step_1": {"model": "Random", "num_samples": 10},
25
+ "step_2": {"model": "BOTorch"}
26
+ }
27
+ """
28
+ self.experiment_name = experiment_name
29
+ self.parameter_space = parameter_space
30
+ self.objective_config = objective_config
31
+ self.optimizer_config = optimizer_config
32
+
33
+ @abstractmethod
34
+ def suggest(self, n=1):
35
+ pass
36
+
37
+ @abstractmethod
38
+ def observe(self, results: dict):
39
+ """
40
+ observe
41
+ :param results: {"objective_name": "value"}
42
+ """
43
+ pass
44
+
45
+ @abstractmethod
46
+ def append_existing_data(self, existing_data):
47
+ pass
48
+
49
+ @staticmethod
50
+ def get_schema():
51
+ """
52
+ Returns a template for the optimizer configuration.
53
+ """
54
+ return {
55
+ "parameter_types": ["range", "choice"],
56
+ "multiple_objectives": True,
57
+ # "objective_weights": True,
58
+ "optimizer_config": {
59
+ "step_1": {"model": [], "num_samples": 10},
60
+ "step_2": {"model": []}
61
+ },
62
+ }
63
+
64
+
65
+