Upload folder using huggingface_hub
Browse filesThis view is limited to 50 files because it contains too many changes. See raw diff
- .gitattributes +52 -0
- LICENSE +21 -0
- MANIFEST.in +9 -0
- MULTI_MODEL_README.md +339 -0
- README.md +139 -0
- build/lib/multi_model_orchestrator/__init__.py +27 -0
- build/lib/multi_model_orchestrator/demo_orchestrator.py +352 -0
- build/lib/multi_model_orchestrator/multi_model_orchestrator.py +497 -0
- build/lib/multi_model_orchestrator/simple_orchestrator.py +323 -0
- dist/multi_model_orchestrator-1.0.0-py3-none-any.whl +0 -0
- dist/multi_model_orchestrator-1.0.0.tar.gz +3 -0
- main.py +56 -0
- multi_model_env/.gitignore +2 -0
- multi_model_env/bin/Activate.ps1 +248 -0
- multi_model_env/bin/activate +76 -0
- multi_model_env/bin/activate.csh +27 -0
- multi_model_env/bin/activate.fish +69 -0
- multi_model_env/bin/diffusers-cli +8 -0
- multi_model_env/bin/f2py +8 -0
- multi_model_env/bin/hf +8 -0
- multi_model_env/bin/huggingface-cli +8 -0
- multi_model_env/bin/isympy +8 -0
- multi_model_env/bin/normalizer +8 -0
- multi_model_env/bin/numpy-config +8 -0
- multi_model_env/bin/pip +8 -0
- multi_model_env/bin/pip3 +8 -0
- multi_model_env/bin/pip3.13 +8 -0
- multi_model_env/bin/python +0 -0
- multi_model_env/bin/python3 +0 -0
- multi_model_env/bin/python3.13 +0 -0
- multi_model_env/bin/tiny-agents +8 -0
- multi_model_env/bin/torchfrtrace +8 -0
- multi_model_env/bin/torchrun +8 -0
- multi_model_env/bin/tqdm +8 -0
- multi_model_env/bin/transformers +8 -0
- multi_model_env/bin/transformers-cli +8 -0
- multi_model_env/lib/python3.13/site-packages/MarkupSafe-3.0.2.dist-info/INSTALLER +1 -0
- multi_model_env/lib/python3.13/site-packages/MarkupSafe-3.0.2.dist-info/LICENSE.txt +28 -0
- multi_model_env/lib/python3.13/site-packages/MarkupSafe-3.0.2.dist-info/METADATA +92 -0
- multi_model_env/lib/python3.13/site-packages/MarkupSafe-3.0.2.dist-info/RECORD +14 -0
- multi_model_env/lib/python3.13/site-packages/MarkupSafe-3.0.2.dist-info/WHEEL +5 -0
- multi_model_env/lib/python3.13/site-packages/MarkupSafe-3.0.2.dist-info/top_level.txt +1 -0
- multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libXau.6.dylib +0 -0
- multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libavif.16.3.0.dylib +3 -0
- multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libbrotlicommon.1.1.0.dylib +3 -0
- multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libbrotlidec.1.1.0.dylib +3 -0
- multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libfreetype.6.dylib +3 -0
- multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libharfbuzz.0.dylib +3 -0
- multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libjpeg.62.4.0.dylib +3 -0
- multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/liblcms2.2.dylib +3 -0
.gitattributes
CHANGED
|
@@ -33,3 +33,55 @@ saved_model/**/* filter=lfs diff=lfs merge=lfs -text
|
|
| 33 |
*.zip filter=lfs diff=lfs merge=lfs -text
|
| 34 |
*.zst filter=lfs diff=lfs merge=lfs -text
|
| 35 |
*tfevents* filter=lfs diff=lfs merge=lfs -text
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 33 |
*.zip filter=lfs diff=lfs merge=lfs -text
|
| 34 |
*.zst filter=lfs diff=lfs merge=lfs -text
|
| 35 |
*tfevents* filter=lfs diff=lfs merge=lfs -text
|
| 36 |
+
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libavif.16.3.0.dylib filter=lfs diff=lfs merge=lfs -text
|
| 37 |
+
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libbrotlicommon.1.1.0.dylib filter=lfs diff=lfs merge=lfs -text
|
| 38 |
+
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libbrotlidec.1.1.0.dylib filter=lfs diff=lfs merge=lfs -text
|
| 39 |
+
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libfreetype.6.dylib filter=lfs diff=lfs merge=lfs -text
|
| 40 |
+
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libharfbuzz.0.dylib filter=lfs diff=lfs merge=lfs -text
|
| 41 |
+
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libjpeg.62.4.0.dylib filter=lfs diff=lfs merge=lfs -text
|
| 42 |
+
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/liblcms2.2.dylib filter=lfs diff=lfs merge=lfs -text
|
| 43 |
+
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/liblzma.5.dylib filter=lfs diff=lfs merge=lfs -text
|
| 44 |
+
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libopenjp2.2.5.3.dylib filter=lfs diff=lfs merge=lfs -text
|
| 45 |
+
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libpng16.16.dylib filter=lfs diff=lfs merge=lfs -text
|
| 46 |
+
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libtiff.6.dylib filter=lfs diff=lfs merge=lfs -text
|
| 47 |
+
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libwebp.7.dylib filter=lfs diff=lfs merge=lfs -text
|
| 48 |
+
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libwebpmux.3.dylib filter=lfs diff=lfs merge=lfs -text
|
| 49 |
+
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libxcb.1.1.0.dylib filter=lfs diff=lfs merge=lfs -text
|
| 50 |
+
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libz.1.3.1.zlib-ng.dylib filter=lfs diff=lfs merge=lfs -text
|
| 51 |
+
multi_model_env/lib/python3.13/site-packages/PIL/_imaging.cpython-313-darwin.so filter=lfs diff=lfs merge=lfs -text
|
| 52 |
+
multi_model_env/lib/python3.13/site-packages/PIL/_imagingft.cpython-313-darwin.so filter=lfs diff=lfs merge=lfs -text
|
| 53 |
+
multi_model_env/lib/python3.13/site-packages/charset_normalizer/md.cpython-313-darwin.so filter=lfs diff=lfs merge=lfs -text
|
| 54 |
+
multi_model_env/lib/python3.13/site-packages/charset_normalizer/md__mypyc.cpython-313-darwin.so filter=lfs diff=lfs merge=lfs -text
|
| 55 |
+
multi_model_env/lib/python3.13/site-packages/functorch/_C.cpython-313-darwin.so filter=lfs diff=lfs merge=lfs -text
|
| 56 |
+
multi_model_env/lib/python3.13/site-packages/hf_xet/hf_xet.abi3.so filter=lfs diff=lfs merge=lfs -text
|
| 57 |
+
multi_model_env/lib/python3.13/site-packages/numpy/.dylibs/libgcc_s.1.1.dylib filter=lfs diff=lfs merge=lfs -text
|
| 58 |
+
multi_model_env/lib/python3.13/site-packages/numpy/.dylibs/libgfortran.5.dylib filter=lfs diff=lfs merge=lfs -text
|
| 59 |
+
multi_model_env/lib/python3.13/site-packages/numpy/.dylibs/libquadmath.0.dylib filter=lfs diff=lfs merge=lfs -text
|
| 60 |
+
multi_model_env/lib/python3.13/site-packages/numpy/.dylibs/libscipy_openblas64_.dylib filter=lfs diff=lfs merge=lfs -text
|
| 61 |
+
multi_model_env/lib/python3.13/site-packages/numpy/_core/_multiarray_tests.cpython-313-darwin.so filter=lfs diff=lfs merge=lfs -text
|
| 62 |
+
multi_model_env/lib/python3.13/site-packages/numpy/_core/_multiarray_umath.cpython-313-darwin.so filter=lfs diff=lfs merge=lfs -text
|
| 63 |
+
multi_model_env/lib/python3.13/site-packages/numpy/_core/_simd.cpython-313-darwin.so filter=lfs diff=lfs merge=lfs -text
|
| 64 |
+
multi_model_env/lib/python3.13/site-packages/numpy/fft/_pocketfft_umath.cpython-313-darwin.so filter=lfs diff=lfs merge=lfs -text
|
| 65 |
+
multi_model_env/lib/python3.13/site-packages/numpy/linalg/_umath_linalg.cpython-313-darwin.so filter=lfs diff=lfs merge=lfs -text
|
| 66 |
+
multi_model_env/lib/python3.13/site-packages/numpy/random/_bounded_integers.cpython-313-darwin.so filter=lfs diff=lfs merge=lfs -text
|
| 67 |
+
multi_model_env/lib/python3.13/site-packages/numpy/random/_common.cpython-313-darwin.so filter=lfs diff=lfs merge=lfs -text
|
| 68 |
+
multi_model_env/lib/python3.13/site-packages/numpy/random/_generator.cpython-313-darwin.so filter=lfs diff=lfs merge=lfs -text
|
| 69 |
+
multi_model_env/lib/python3.13/site-packages/numpy/random/_mt19937.cpython-313-darwin.so filter=lfs diff=lfs merge=lfs -text
|
| 70 |
+
multi_model_env/lib/python3.13/site-packages/numpy/random/_pcg64.cpython-313-darwin.so filter=lfs diff=lfs merge=lfs -text
|
| 71 |
+
multi_model_env/lib/python3.13/site-packages/numpy/random/_philox.cpython-313-darwin.so filter=lfs diff=lfs merge=lfs -text
|
| 72 |
+
multi_model_env/lib/python3.13/site-packages/numpy/random/bit_generator.cpython-313-darwin.so filter=lfs diff=lfs merge=lfs -text
|
| 73 |
+
multi_model_env/lib/python3.13/site-packages/numpy/random/mtrand.cpython-313-darwin.so filter=lfs diff=lfs merge=lfs -text
|
| 74 |
+
multi_model_env/lib/python3.13/site-packages/pip/_vendor/distlib/t64-arm.exe filter=lfs diff=lfs merge=lfs -text
|
| 75 |
+
multi_model_env/lib/python3.13/site-packages/pip/_vendor/distlib/t64.exe filter=lfs diff=lfs merge=lfs -text
|
| 76 |
+
multi_model_env/lib/python3.13/site-packages/pip/_vendor/distlib/w64-arm.exe filter=lfs diff=lfs merge=lfs -text
|
| 77 |
+
multi_model_env/lib/python3.13/site-packages/pip/_vendor/distlib/w64.exe filter=lfs diff=lfs merge=lfs -text
|
| 78 |
+
multi_model_env/lib/python3.13/site-packages/regex/_regex.cpython-313-darwin.so filter=lfs diff=lfs merge=lfs -text
|
| 79 |
+
multi_model_env/lib/python3.13/site-packages/safetensors/_safetensors_rust.abi3.so filter=lfs diff=lfs merge=lfs -text
|
| 80 |
+
multi_model_env/lib/python3.13/site-packages/tokenizers/tokenizers.abi3.so filter=lfs diff=lfs merge=lfs -text
|
| 81 |
+
multi_model_env/lib/python3.13/site-packages/torch/bin/protoc filter=lfs diff=lfs merge=lfs -text
|
| 82 |
+
multi_model_env/lib/python3.13/site-packages/torch/bin/protoc-3.13.0.0 filter=lfs diff=lfs merge=lfs -text
|
| 83 |
+
multi_model_env/lib/python3.13/site-packages/torch/lib/libc10.dylib filter=lfs diff=lfs merge=lfs -text
|
| 84 |
+
multi_model_env/lib/python3.13/site-packages/torch/lib/libomp.dylib filter=lfs diff=lfs merge=lfs -text
|
| 85 |
+
multi_model_env/lib/python3.13/site-packages/torch/lib/libtorch_cpu.dylib filter=lfs diff=lfs merge=lfs -text
|
| 86 |
+
multi_model_env/lib/python3.13/site-packages/torch/lib/libtorch_python.dylib filter=lfs diff=lfs merge=lfs -text
|
| 87 |
+
multi_model_env/lib/python3.13/site-packages/yaml/_yaml.cpython-313-darwin.so filter=lfs diff=lfs merge=lfs -text
|
LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
MIT License
|
| 2 |
+
|
| 3 |
+
Copyright (c) 2024 Kunal Dhanda
|
| 4 |
+
|
| 5 |
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
| 6 |
+
of this software and associated documentation files (the "Software"), to deal
|
| 7 |
+
in the Software without restriction, including without limitation the rights
|
| 8 |
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
| 9 |
+
copies of the Software, and to permit persons to whom the Software is
|
| 10 |
+
furnished to do so, subject to the following conditions:
|
| 11 |
+
|
| 12 |
+
The above copyright notice and this permission notice shall be included in all
|
| 13 |
+
copies or substantial portions of the Software.
|
| 14 |
+
|
| 15 |
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
| 16 |
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
| 17 |
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
| 18 |
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
| 19 |
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
| 20 |
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
| 21 |
+
SOFTWARE.
|
MANIFEST.in
ADDED
|
@@ -0,0 +1,9 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
include README.md
|
| 2 |
+
include MULTI_MODEL_README.md
|
| 3 |
+
include requirements.txt
|
| 4 |
+
include multi_model_requirements.txt
|
| 5 |
+
include LICENSE
|
| 6 |
+
include *.json
|
| 7 |
+
include *.py
|
| 8 |
+
recursive-exclude * __pycache__
|
| 9 |
+
recursive-exclude * *.py[co]
|
MULTI_MODEL_README.md
ADDED
|
@@ -0,0 +1,339 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
# Multi-Model Orchestrator: Parent-Child LLM System
|
| 2 |
+
|
| 3 |
+
A sophisticated multi-model orchestration system that manages parent-child LLM relationships, specifically integrating the [CLIP-GPT2 Image Captioner](https://huggingface.co/kunaliitkgp09/clip-gpt2-image-captioner) and [Flickr30k Text-to-Image](https://huggingface.co/kunaliitkgp09/flickr30k-text-to-image) models.
|
| 4 |
+
|
| 5 |
+
## 🚀 Features
|
| 6 |
+
|
| 7 |
+
### **Parent Orchestrator**
|
| 8 |
+
- **Intelligent Task Routing**: Automatically routes tasks to appropriate child models
|
| 9 |
+
- **Model Management**: Handles loading, caching, and lifecycle of child models
|
| 10 |
+
- **Error Handling**: Robust error handling and recovery mechanisms
|
| 11 |
+
- **Task History**: Comprehensive logging and monitoring of all operations
|
| 12 |
+
- **Async Support**: Both synchronous and asynchronous processing modes
|
| 13 |
+
|
| 14 |
+
### **Child Models**
|
| 15 |
+
- **CLIP-GPT2 Image Captioner**: Converts images to descriptive text captions
|
| 16 |
+
- **Flickr30k Text-to-Image**: Generates images from text descriptions
|
| 17 |
+
- **Extensible Architecture**: Easy to add new child models
|
| 18 |
+
|
| 19 |
+
### **Advanced Capabilities**
|
| 20 |
+
- **Multimodal Processing**: Combines multiple child models for complex tasks
|
| 21 |
+
- **Batch Processing**: Handle multiple tasks efficiently
|
| 22 |
+
- **Performance Monitoring**: Track processing times and success rates
|
| 23 |
+
- **Memory Management**: Efficient GPU/CPU memory usage
|
| 24 |
+
|
| 25 |
+
## 📁 Project Structure
|
| 26 |
+
|
| 27 |
+
```
|
| 28 |
+
├── multi_model_orchestrator.py # Advanced orchestrator with full features
|
| 29 |
+
├── simple_orchestrator.py # Simplified interface matching original code
|
| 30 |
+
├── multi_model_example.py # Comprehensive examples and demonstrations
|
| 31 |
+
├── multi_model_requirements.txt # Dependencies for multi-model system
|
| 32 |
+
└── MULTI_MODEL_README.md # This file
|
| 33 |
+
```
|
| 34 |
+
|
| 35 |
+
## 🛠️ Installation
|
| 36 |
+
|
| 37 |
+
1. **Install dependencies:**
|
| 38 |
+
```bash
|
| 39 |
+
pip install -r multi_model_requirements.txt
|
| 40 |
+
```
|
| 41 |
+
|
| 42 |
+
2. **Verify installation:**
|
| 43 |
+
```python
|
| 44 |
+
import torch
|
| 45 |
+
from transformers import CLIPProcessor
|
| 46 |
+
from diffusers import StableDiffusionPipeline
|
| 47 |
+
print("All dependencies installed successfully!")
|
| 48 |
+
```
|
| 49 |
+
|
| 50 |
+
## 🎯 Quick Start
|
| 51 |
+
|
| 52 |
+
### **Basic Usage (Matching Original Code)**
|
| 53 |
+
|
| 54 |
+
```python
|
| 55 |
+
from simple_orchestrator import SimpleMultiModelOrchestrator
|
| 56 |
+
|
| 57 |
+
# Initialize orchestrator
|
| 58 |
+
orchestrator = SimpleMultiModelOrchestrator()
|
| 59 |
+
orchestrator.initialize_models()
|
| 60 |
+
|
| 61 |
+
# Generate caption from image
|
| 62 |
+
caption = orchestrator.generate_caption("sample_image.jpg")
|
| 63 |
+
print(f"Caption: {caption}")
|
| 64 |
+
|
| 65 |
+
# Generate image from text
|
| 66 |
+
image_path = orchestrator.generate_image("A beautiful sunset over mountains")
|
| 67 |
+
print(f"Generated image: {image_path}")
|
| 68 |
+
|
| 69 |
+
# Route tasks
|
| 70 |
+
caption = orchestrator.route_task("caption", "sample_image.jpg")
|
| 71 |
+
image_path = orchestrator.route_task("generate_image", "A cat on a windowsill")
|
| 72 |
+
```
|
| 73 |
+
|
| 74 |
+
### **Advanced Usage**
|
| 75 |
+
|
| 76 |
+
```python
|
| 77 |
+
from multi_model_orchestrator import MultiModelOrchestrator
|
| 78 |
+
import asyncio
|
| 79 |
+
|
| 80 |
+
async def main():
|
| 81 |
+
# Initialize advanced orchestrator
|
| 82 |
+
orchestrator = MultiModelOrchestrator()
|
| 83 |
+
await orchestrator.initialize()
|
| 84 |
+
|
| 85 |
+
# Multimodal processing
|
| 86 |
+
results = await orchestrator.process_multimodal(
|
| 87 |
+
image_path="sample_image.jpg",
|
| 88 |
+
text_prompt="A serene landscape with mountains"
|
| 89 |
+
)
|
| 90 |
+
|
| 91 |
+
print("Results:", results)
|
| 92 |
+
|
| 93 |
+
asyncio.run(main())
|
| 94 |
+
```
|
| 95 |
+
|
| 96 |
+
## 🔧 Model Integration
|
| 97 |
+
|
| 98 |
+
### **Child Model 1: CLIP-GPT2 Image Captioner**
|
| 99 |
+
- **Model**: `kunaliitkgp09/clip-gpt2-image-captioner`
|
| 100 |
+
- **Task**: Image-to-text captioning
|
| 101 |
+
- **Input**: Image file path
|
| 102 |
+
- **Output**: Descriptive text caption
|
| 103 |
+
- **Performance**: ~40% accuracy on test samples
|
| 104 |
+
|
| 105 |
+
### **Child Model 2: Flickr30k Text-to-Image**
|
| 106 |
+
- **Model**: `kunaliitkgp09/flickr30k-text-to-image`
|
| 107 |
+
- **Task**: Text-to-image generation
|
| 108 |
+
- **Input**: Text prompt
|
| 109 |
+
- **Output**: Generated image file
|
| 110 |
+
- **Performance**: Fine-tuned on Flickr30k dataset
|
| 111 |
+
|
| 112 |
+
## 📊 Usage Examples
|
| 113 |
+
|
| 114 |
+
### **1. Image Captioning**
|
| 115 |
+
```python
|
| 116 |
+
# Generate caption from image
|
| 117 |
+
caption = orchestrator.generate_caption("path/to/image.jpg")
|
| 118 |
+
print(f"Generated Caption: {caption}")
|
| 119 |
+
```
|
| 120 |
+
|
| 121 |
+
### **2. Text-to-Image Generation**
|
| 122 |
+
```python
|
| 123 |
+
# Generate image from text
|
| 124 |
+
image_path = orchestrator.generate_image("A majestic eagle soaring over mountains")
|
| 125 |
+
print(f"Generated Image: {image_path}")
|
| 126 |
+
```
|
| 127 |
+
|
| 128 |
+
### **3. Multimodal Processing**
|
| 129 |
+
```python
|
| 130 |
+
# Process both image and text together
|
| 131 |
+
results = orchestrator.process_multimodal_task(
|
| 132 |
+
image_path="sample_image.jpg",
|
| 133 |
+
text_prompt="A serene landscape with mountains"
|
| 134 |
+
)
|
| 135 |
+
|
| 136 |
+
print("Caption:", results["caption"])
|
| 137 |
+
print("Generated Image:", results["generated_image"])
|
| 138 |
+
print("Analysis:", results["analysis_prompt"])
|
| 139 |
+
```
|
| 140 |
+
|
| 141 |
+
### **4. Async Processing**
|
| 142 |
+
```python
|
| 143 |
+
# Async version for better performance
|
| 144 |
+
async def async_example():
|
| 145 |
+
results = await orchestrator.process_multimodal_async(
|
| 146 |
+
image_path="sample_image.jpg",
|
| 147 |
+
text_prompt="A futuristic cityscape"
|
| 148 |
+
)
|
| 149 |
+
return results
|
| 150 |
+
```
|
| 151 |
+
|
| 152 |
+
### **5. Batch Processing**
|
| 153 |
+
```python
|
| 154 |
+
# Process multiple tasks
|
| 155 |
+
image_tasks = [
|
| 156 |
+
"A beautiful sunset",
|
| 157 |
+
"A cozy coffee shop",
|
| 158 |
+
"A vibrant garden"
|
| 159 |
+
]
|
| 160 |
+
|
| 161 |
+
for prompt in image_tasks:
|
| 162 |
+
image_path = orchestrator.generate_image(prompt)
|
| 163 |
+
print(f"Generated: {image_path}")
|
| 164 |
+
```
|
| 165 |
+
|
| 166 |
+
## 🔍 Task History and Monitoring
|
| 167 |
+
|
| 168 |
+
```python
|
| 169 |
+
# Get orchestrator status
|
| 170 |
+
status = orchestrator.get_status()
|
| 171 |
+
print(f"Status: {status}")
|
| 172 |
+
|
| 173 |
+
# Get task history
|
| 174 |
+
history = orchestrator.get_task_history()
|
| 175 |
+
for task in history:
|
| 176 |
+
print(f"Task: {task['task_type']}, Time: {task['processing_time']:.2f}s")
|
| 177 |
+
|
| 178 |
+
# Save task history
|
| 179 |
+
orchestrator.save_task_history("my_tasks.json")
|
| 180 |
+
```
|
| 181 |
+
|
| 182 |
+
## ⚙️ Configuration Options
|
| 183 |
+
|
| 184 |
+
### **Model Configuration**
|
| 185 |
+
```python
|
| 186 |
+
# Custom model parameters
|
| 187 |
+
orchestrator = SimpleMultiModelOrchestrator(device="cuda") # or "cpu"
|
| 188 |
+
|
| 189 |
+
# Custom generation parameters
|
| 190 |
+
image_path = orchestrator.generate_image(
|
| 191 |
+
"A beautiful landscape",
|
| 192 |
+
output_path="custom_output.png"
|
| 193 |
+
)
|
| 194 |
+
```
|
| 195 |
+
|
| 196 |
+
### **Async Configuration**
|
| 197 |
+
```python
|
| 198 |
+
# Async orchestrator with concurrent processing
|
| 199 |
+
async_orchestrator = AsyncMultiModelOrchestrator()
|
| 200 |
+
|
| 201 |
+
# Process tasks concurrently
|
| 202 |
+
results = await async_orchestrator.process_multimodal_async(
|
| 203 |
+
image_path="image.jpg",
|
| 204 |
+
text_prompt="prompt"
|
| 205 |
+
)
|
| 206 |
+
```
|
| 207 |
+
|
| 208 |
+
## 🎯 Use Cases
|
| 209 |
+
|
| 210 |
+
### **1. Content Creation**
|
| 211 |
+
- Generate captions for social media images
|
| 212 |
+
- Create images from text descriptions
|
| 213 |
+
- Multimodal content analysis
|
| 214 |
+
|
| 215 |
+
### **2. Research and Development**
|
| 216 |
+
- Model performance comparison
|
| 217 |
+
- Multimodal AI research
|
| 218 |
+
- Prototype development
|
| 219 |
+
|
| 220 |
+
### **3. Production Systems**
|
| 221 |
+
- Automated content generation
|
| 222 |
+
- Image analysis pipelines
|
| 223 |
+
- Text-to-image applications
|
| 224 |
+
|
| 225 |
+
### **4. Educational Applications**
|
| 226 |
+
- AI model demonstration
|
| 227 |
+
- Multimodal learning systems
|
| 228 |
+
- Research toolkits
|
| 229 |
+
|
| 230 |
+
## 🔧 Advanced Features
|
| 231 |
+
|
| 232 |
+
### **Error Handling**
|
| 233 |
+
```python
|
| 234 |
+
try:
|
| 235 |
+
caption = orchestrator.generate_caption("image.jpg")
|
| 236 |
+
except Exception as e:
|
| 237 |
+
print(f"Error: {e}")
|
| 238 |
+
# Handle error gracefully
|
| 239 |
+
```
|
| 240 |
+
|
| 241 |
+
### **Performance Optimization**
|
| 242 |
+
```python
|
| 243 |
+
# Use async for better performance
|
| 244 |
+
async def optimized_processing():
|
| 245 |
+
tasks = [
|
| 246 |
+
orchestrator.generate_caption_async("image1.jpg"),
|
| 247 |
+
orchestrator.generate_caption_async("image2.jpg"),
|
| 248 |
+
orchestrator.generate_image_async("prompt1"),
|
| 249 |
+
orchestrator.generate_image_async("prompt2")
|
| 250 |
+
]
|
| 251 |
+
|
| 252 |
+
results = await asyncio.gather(*tasks)
|
| 253 |
+
return results
|
| 254 |
+
```
|
| 255 |
+
|
| 256 |
+
### **Custom Model Integration**
|
| 257 |
+
```python
|
| 258 |
+
# Add new child models
|
| 259 |
+
class CustomChildModel:
|
| 260 |
+
def __init__(self, model_name):
|
| 261 |
+
self.model = load_model(model_name)
|
| 262 |
+
|
| 263 |
+
def process(self, input_data):
|
| 264 |
+
# Custom processing logic
|
| 265 |
+
return result
|
| 266 |
+
|
| 267 |
+
# Integrate with orchestrator
|
| 268 |
+
orchestrator.add_child_model("custom_model", CustomChildModel("model_name"))
|
| 269 |
+
```
|
| 270 |
+
|
| 271 |
+
## 📈 Performance Metrics
|
| 272 |
+
|
| 273 |
+
The orchestrator tracks various performance metrics:
|
| 274 |
+
|
| 275 |
+
- **Processing Time**: Time taken for each task
|
| 276 |
+
- **Success Rate**: Percentage of successful operations
|
| 277 |
+
- **Memory Usage**: GPU/CPU memory consumption
|
| 278 |
+
- **Model Load Times**: Time to initialize each child model
|
| 279 |
+
- **Task Throughput**: Number of tasks processed per second
|
| 280 |
+
|
| 281 |
+
## 🚨 Important Notes
|
| 282 |
+
|
| 283 |
+
### **System Requirements**
|
| 284 |
+
- **GPU**: Recommended for optimal performance (CUDA compatible)
|
| 285 |
+
- **RAM**: 8GB+ for smooth operation
|
| 286 |
+
- **Storage**: 5GB+ for model downloads and generated content
|
| 287 |
+
- **Python**: 3.8+ required
|
| 288 |
+
|
| 289 |
+
### **Model Downloads**
|
| 290 |
+
- Models are downloaded automatically on first use
|
| 291 |
+
- CLIP-GPT2: ~500MB
|
| 292 |
+
- Stable Diffusion: ~4GB
|
| 293 |
+
- Total initial download: ~5GB
|
| 294 |
+
|
| 295 |
+
### **Memory Management**
|
| 296 |
+
- Models are loaded into GPU memory when available
|
| 297 |
+
- CPU fallback available for systems without GPU
|
| 298 |
+
- Memory usage scales with batch size and model complexity
|
| 299 |
+
|
| 300 |
+
## 🤝 Contributing
|
| 301 |
+
|
| 302 |
+
Contributions are welcome! Please feel free to submit pull requests or open issues for:
|
| 303 |
+
|
| 304 |
+
- New child model integrations
|
| 305 |
+
- Performance improvements
|
| 306 |
+
- Bug fixes
|
| 307 |
+
- Documentation enhancements
|
| 308 |
+
- Feature requests
|
| 309 |
+
|
| 310 |
+
## 📄 License
|
| 311 |
+
|
| 312 |
+
This project is licensed under the MIT License - see the LICENSE file for details.
|
| 313 |
+
|
| 314 |
+
## 🙏 Acknowledgments
|
| 315 |
+
|
| 316 |
+
- **CLIP-GPT2 Model**: [kunaliitkgp09/clip-gpt2-image-captioner](https://huggingface.co/kunaliitkgp09/clip-gpt2-image-captioner)
|
| 317 |
+
- **Stable Diffusion Model**: [kunaliitkgp09/flickr30k-text-to-image](https://huggingface.co/kunaliitkgp09/flickr30k-text-to-image)
|
| 318 |
+
- **Hugging Face**: For providing the model hosting platform
|
| 319 |
+
- **PyTorch**: For the deep learning framework
|
| 320 |
+
- **Transformers**: For the model loading and processing utilities
|
| 321 |
+
|
| 322 |
+
## 📚 References
|
| 323 |
+
|
| 324 |
+
1. **CLIP**: "Learning Transferable Visual Representations" (Radford et al., 2021)
|
| 325 |
+
2. **GPT-2**: "Language Models are Unsupervised Multitask Learners" (Radford et al., 2019)
|
| 326 |
+
3. **Stable Diffusion**: "High-Resolution Image Synthesis with Latent Diffusion Models" (Rombach et al., 2022)
|
| 327 |
+
4. **Flickr30k**: "From Image Descriptions to Visual Denotations" (Young et al., 2014)
|
| 328 |
+
|
| 329 |
+
## 🔗 Links
|
| 330 |
+
|
| 331 |
+
- **CLIP-GPT2 Model**: https://huggingface.co/kunaliitkgp09/clip-gpt2-image-captioner
|
| 332 |
+
- **Flickr30k Text-to-Image**: https://huggingface.co/kunaliitkgp09/flickr30k-text-to-image
|
| 333 |
+
- **Hugging Face Hub**: https://huggingface.co/
|
| 334 |
+
- **PyTorch**: https://pytorch.org/
|
| 335 |
+
- **Transformers**: https://huggingface.co/docs/transformers/
|
| 336 |
+
|
| 337 |
+
---
|
| 338 |
+
|
| 339 |
+
**Happy Orchestrating! 🚀**
|
README.md
ADDED
|
@@ -0,0 +1,139 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
---
|
| 2 |
+
language:
|
| 3 |
+
- en
|
| 4 |
+
license: mit
|
| 5 |
+
library_name: multi-model-orchestrator
|
| 6 |
+
tags:
|
| 7 |
+
- ai
|
| 8 |
+
- machine-learning
|
| 9 |
+
- multimodal
|
| 10 |
+
- image-captioning
|
| 11 |
+
- text-to-image
|
| 12 |
+
- orchestration
|
| 13 |
+
- transformers
|
| 14 |
+
- pytorch
|
| 15 |
+
---
|
| 16 |
+
|
| 17 |
+
# Multi-Model Orchestrator
|
| 18 |
+
|
| 19 |
+
A sophisticated multi-model orchestration system that manages parent-child LLM relationships, specifically integrating CLIP-GPT2 image captioner and Flickr30k text-to-image models.
|
| 20 |
+
|
| 21 |
+
## 🚀 Features
|
| 22 |
+
|
| 23 |
+
### **Parent Orchestrator**
|
| 24 |
+
- **Intelligent Task Routing**: Automatically routes tasks to appropriate child models
|
| 25 |
+
- **Model Management**: Handles loading, caching, and lifecycle of child models
|
| 26 |
+
- **Error Handling**: Robust error handling and recovery mechanisms
|
| 27 |
+
- **Task History**: Comprehensive logging and monitoring of all operations
|
| 28 |
+
- **Async Support**: Both synchronous and asynchronous processing modes
|
| 29 |
+
|
| 30 |
+
### **Child Models**
|
| 31 |
+
- **CLIP-GPT2 Image Captioner**: Converts images to descriptive text captions
|
| 32 |
+
- **Flickr30k Text-to-Image**: Generates images from text descriptions
|
| 33 |
+
- **Extensible Architecture**: Easy to add new child models
|
| 34 |
+
|
| 35 |
+
## 📦 Installation
|
| 36 |
+
|
| 37 |
+
```bash
|
| 38 |
+
pip install git+https://huggingface.co/kunaliitkgp09/multi-model-orchestrator
|
| 39 |
+
```
|
| 40 |
+
|
| 41 |
+
## 🎯 Quick Start
|
| 42 |
+
|
| 43 |
+
```python
|
| 44 |
+
from multi_model_orchestrator import SimpleMultiModelOrchestrator
|
| 45 |
+
|
| 46 |
+
# Initialize orchestrator
|
| 47 |
+
orchestrator = SimpleMultiModelOrchestrator()
|
| 48 |
+
orchestrator.initialize_models()
|
| 49 |
+
|
| 50 |
+
# Generate caption from image
|
| 51 |
+
caption = orchestrator.generate_caption("sample_image.jpg")
|
| 52 |
+
print(f"Caption: {caption}")
|
| 53 |
+
|
| 54 |
+
# Generate image from text
|
| 55 |
+
image_path = orchestrator.generate_image("A beautiful sunset over mountains")
|
| 56 |
+
print(f"Generated image: {image_path}")
|
| 57 |
+
```
|
| 58 |
+
|
| 59 |
+
## 🔗 Model Integration
|
| 60 |
+
|
| 61 |
+
### **Child Model 1: CLIP-GPT2 Image Captioner**
|
| 62 |
+
- **Model**: `kunaliitkgp09/clip-gpt2-image-captioner`
|
| 63 |
+
- **Task**: Image-to-text captioning
|
| 64 |
+
- **Performance**: ~40% accuracy on test samples
|
| 65 |
+
|
| 66 |
+
### **Child Model 2: Flickr30k Text-to-Image**
|
| 67 |
+
- **Model**: `kunaliitkgp09/flickr30k-text-to-image`
|
| 68 |
+
- **Task**: Text-to-image generation
|
| 69 |
+
- **Performance**: Fine-tuned on Flickr30k dataset
|
| 70 |
+
|
| 71 |
+
## 📊 Usage Examples
|
| 72 |
+
|
| 73 |
+
### **Multimodal Processing**
|
| 74 |
+
```python
|
| 75 |
+
# Process both image and text together
|
| 76 |
+
results = orchestrator.process_multimodal_task(
|
| 77 |
+
image_path="sample_image.jpg",
|
| 78 |
+
text_prompt="A serene landscape with mountains"
|
| 79 |
+
)
|
| 80 |
+
|
| 81 |
+
print("Caption:", results["caption"])
|
| 82 |
+
print("Generated Image:", results["generated_image"])
|
| 83 |
+
```
|
| 84 |
+
|
| 85 |
+
### **Async Processing**
|
| 86 |
+
```python
|
| 87 |
+
from multi_model_orchestrator import AsyncMultiModelOrchestrator
|
| 88 |
+
import asyncio
|
| 89 |
+
|
| 90 |
+
async def async_example():
|
| 91 |
+
orchestrator = AsyncMultiModelOrchestrator()
|
| 92 |
+
orchestrator.initialize_models()
|
| 93 |
+
|
| 94 |
+
results = await orchestrator.process_multimodal_async(
|
| 95 |
+
image_path="sample_image.jpg",
|
| 96 |
+
text_prompt="A futuristic cityscape"
|
| 97 |
+
)
|
| 98 |
+
return results
|
| 99 |
+
|
| 100 |
+
asyncio.run(async_example())
|
| 101 |
+
```
|
| 102 |
+
|
| 103 |
+
## 🎯 Use Cases
|
| 104 |
+
|
| 105 |
+
- **Content Creation**: Generate captions and images for social media
|
| 106 |
+
- **Research and Development**: Model performance comparison and prototyping
|
| 107 |
+
- **Production Systems**: Automated content generation pipelines
|
| 108 |
+
- **Educational Applications**: AI model demonstration and learning
|
| 109 |
+
|
| 110 |
+
## 📈 Performance Metrics
|
| 111 |
+
|
| 112 |
+
- **Processing Time**: Optimized for real-time applications
|
| 113 |
+
- **Memory Usage**: Efficient GPU/CPU memory management
|
| 114 |
+
- **Success Rate**: Robust error handling and recovery
|
| 115 |
+
- **Extensibility**: Easy integration of new child models
|
| 116 |
+
|
| 117 |
+
## 🤝 Contributing
|
| 118 |
+
|
| 119 |
+
Contributions are welcome! Please feel free to submit pull requests or open issues for:
|
| 120 |
+
- New child model integrations
|
| 121 |
+
- Performance improvements
|
| 122 |
+
- Bug fixes
|
| 123 |
+
- Documentation enhancements
|
| 124 |
+
|
| 125 |
+
## 📄 License
|
| 126 |
+
|
| 127 |
+
This project is licensed under the MIT License.
|
| 128 |
+
|
| 129 |
+
## 🙏 Acknowledgments
|
| 130 |
+
|
| 131 |
+
- **CLIP-GPT2 Model**: [kunaliitkgp09/clip-gpt2-image-captioner](https://huggingface.co/kunaliitkgp09/clip-gpt2-image-captioner)
|
| 132 |
+
- **Stable Diffusion Model**: [kunaliitkgp09/flickr30k-text-to-image](https://huggingface.co/kunaliitkgp09/flickr30k-text-to-image)
|
| 133 |
+
- **Hugging Face**: For providing the model hosting platform
|
| 134 |
+
- **PyTorch**: For the deep learning framework
|
| 135 |
+
- **Transformers**: For the model loading and processing utilities
|
| 136 |
+
|
| 137 |
+
---
|
| 138 |
+
|
| 139 |
+
**Happy Orchestrating! 🚀**
|
build/lib/multi_model_orchestrator/__init__.py
ADDED
|
@@ -0,0 +1,27 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
"""
|
| 2 |
+
Multi-Model Orchestrator: Parent-Child LLM System
|
| 3 |
+
|
| 4 |
+
A sophisticated multi-model orchestration system that manages parent-child LLM relationships,
|
| 5 |
+
specifically integrating CLIP-GPT2 image captioner and Flickr30k text-to-image models.
|
| 6 |
+
|
| 7 |
+
Author: Kunal Dhanda
|
| 8 |
+
Version: 1.0.0
|
| 9 |
+
"""
|
| 10 |
+
|
| 11 |
+
from .simple_orchestrator import SimpleMultiModelOrchestrator, AsyncMultiModelOrchestrator
|
| 12 |
+
from .multi_model_orchestrator import MultiModelOrchestrator, ParentOrchestrator, ChildModel, ModelManager
|
| 13 |
+
from .demo_orchestrator import DemoMultiModelOrchestrator
|
| 14 |
+
|
| 15 |
+
__version__ = "1.0.0"
|
| 16 |
+
__author__ = "Kunal Dhanda"
|
| 17 |
+
__email__ = "kunaldhanda@example.com"
|
| 18 |
+
|
| 19 |
+
__all__ = [
|
| 20 |
+
"SimpleMultiModelOrchestrator",
|
| 21 |
+
"AsyncMultiModelOrchestrator",
|
| 22 |
+
"MultiModelOrchestrator",
|
| 23 |
+
"ParentOrchestrator",
|
| 24 |
+
"ChildModel",
|
| 25 |
+
"ModelManager",
|
| 26 |
+
"DemoMultiModelOrchestrator"
|
| 27 |
+
]
|
build/lib/multi_model_orchestrator/demo_orchestrator.py
ADDED
|
@@ -0,0 +1,352 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/usr/bin/env python3
|
| 2 |
+
"""
|
| 3 |
+
Demo Multi-Model Orchestrator
|
| 4 |
+
Shows the structure and functionality without downloading large models
|
| 5 |
+
"""
|
| 6 |
+
|
| 7 |
+
import time
|
| 8 |
+
import json
|
| 9 |
+
from typing import Dict, Any, Optional
|
| 10 |
+
|
| 11 |
+
class DemoMultiModelOrchestrator:
|
| 12 |
+
"""Demo orchestrator that simulates the multi-model system"""
|
| 13 |
+
|
| 14 |
+
def __init__(self, device: str = "cpu"):
|
| 15 |
+
self.device = device
|
| 16 |
+
self.caption_model_name = "kunaliitkgp09/clip-gpt2-image-captioner"
|
| 17 |
+
self.text2img_model_name = "kunaliitkgp09/flickr30k-text-to-image"
|
| 18 |
+
|
| 19 |
+
# Simulated model instances
|
| 20 |
+
self.caption_processor = None
|
| 21 |
+
self.caption_model = None
|
| 22 |
+
self.text2img_pipeline = None
|
| 23 |
+
self.tokenizer = None
|
| 24 |
+
|
| 25 |
+
# Task history
|
| 26 |
+
self.task_history = []
|
| 27 |
+
|
| 28 |
+
def initialize_models(self):
|
| 29 |
+
"""Simulate model initialization"""
|
| 30 |
+
print("🔧 Initializing child models...")
|
| 31 |
+
|
| 32 |
+
try:
|
| 33 |
+
# Simulate loading captioning model
|
| 34 |
+
print("📥 Loading CLIP-GPT2 captioning model...")
|
| 35 |
+
time.sleep(1) # Simulate loading time
|
| 36 |
+
self.caption_processor = "CLIPProcessor"
|
| 37 |
+
self.caption_model = "CLIP-GPT2-Model"
|
| 38 |
+
self.tokenizer = "GPT2Tokenizer"
|
| 39 |
+
print("✅ Captioning model loaded")
|
| 40 |
+
|
| 41 |
+
# Simulate loading text-to-image model
|
| 42 |
+
print("📥 Loading Stable Diffusion text-to-image model...")
|
| 43 |
+
time.sleep(1) # Simulate loading time
|
| 44 |
+
self.text2img_pipeline = "StableDiffusionPipeline"
|
| 45 |
+
print("✅ Text-to-image model loaded")
|
| 46 |
+
|
| 47 |
+
print("🎉 All models initialized successfully!")
|
| 48 |
+
return True
|
| 49 |
+
|
| 50 |
+
except Exception as e:
|
| 51 |
+
print(f"❌ Error initializing models: {e}")
|
| 52 |
+
return False
|
| 53 |
+
|
| 54 |
+
def generate_caption(self, image_path: str) -> str:
|
| 55 |
+
"""Simulate image captioning"""
|
| 56 |
+
start_time = time.time()
|
| 57 |
+
|
| 58 |
+
try:
|
| 59 |
+
print(f"🖼️ Processing image: {image_path}")
|
| 60 |
+
time.sleep(0.5) # Simulate processing time
|
| 61 |
+
|
| 62 |
+
# Simulate caption generation
|
| 63 |
+
sample_captions = [
|
| 64 |
+
"A beautiful landscape with mountains and trees",
|
| 65 |
+
"A person standing in front of a scenic view",
|
| 66 |
+
"A colorful sunset over the ocean",
|
| 67 |
+
"A cozy room with warm lighting",
|
| 68 |
+
"A busy street in a modern city"
|
| 69 |
+
]
|
| 70 |
+
|
| 71 |
+
import random
|
| 72 |
+
caption = random.choice(sample_captions)
|
| 73 |
+
|
| 74 |
+
# Log task
|
| 75 |
+
self._log_task("caption", image_path, caption, time.time() - start_time)
|
| 76 |
+
|
| 77 |
+
return caption
|
| 78 |
+
|
| 79 |
+
except Exception as e:
|
| 80 |
+
print(f"❌ Error generating caption: {e}")
|
| 81 |
+
self._log_task("caption", image_path, None, time.time() - start_time, str(e))
|
| 82 |
+
raise
|
| 83 |
+
|
| 84 |
+
def generate_image(self, text_prompt: str, output_path: Optional[str] = None) -> str:
|
| 85 |
+
"""Simulate text-to-image generation"""
|
| 86 |
+
start_time = time.time()
|
| 87 |
+
|
| 88 |
+
try:
|
| 89 |
+
print(f"🎨 Generating image from prompt: '{text_prompt}'")
|
| 90 |
+
time.sleep(1) # Simulate generation time
|
| 91 |
+
|
| 92 |
+
# Generate unique output path if not provided
|
| 93 |
+
if output_path is None:
|
| 94 |
+
timestamp = int(time.time())
|
| 95 |
+
output_path = f"generated_image_{timestamp}.png"
|
| 96 |
+
|
| 97 |
+
# Simulate image generation
|
| 98 |
+
print(f"💾 Saving generated image to: {output_path}")
|
| 99 |
+
|
| 100 |
+
# Log task
|
| 101 |
+
self._log_task("generate_image", text_prompt, output_path, time.time() - start_time)
|
| 102 |
+
|
| 103 |
+
return output_path
|
| 104 |
+
|
| 105 |
+
except Exception as e:
|
| 106 |
+
print(f"❌ Error generating image: {e}")
|
| 107 |
+
self._log_task("generate_image", text_prompt, None, time.time() - start_time, str(e))
|
| 108 |
+
raise
|
| 109 |
+
|
| 110 |
+
def route_task(self, task_type: str, input_data: str) -> str:
|
| 111 |
+
"""Parent model decides which child to call"""
|
| 112 |
+
print(f"🎯 Parent orchestrator routing task: {task_type}")
|
| 113 |
+
|
| 114 |
+
if task_type == "caption":
|
| 115 |
+
return self.generate_caption(input_data)
|
| 116 |
+
elif task_type == "generate_image":
|
| 117 |
+
return self.generate_image(input_data)
|
| 118 |
+
else:
|
| 119 |
+
raise ValueError("Invalid task type: choose 'caption' or 'generate_image'")
|
| 120 |
+
|
| 121 |
+
def process_multimodal_task(self, image_path: str, text_prompt: str) -> Dict[str, str]:
|
| 122 |
+
"""Process a multimodal task using both child models"""
|
| 123 |
+
print("🔄 Processing multimodal task...")
|
| 124 |
+
results = {}
|
| 125 |
+
|
| 126 |
+
# Step 1: Generate caption from image
|
| 127 |
+
try:
|
| 128 |
+
print("📝 Step 1: Generating caption from image...")
|
| 129 |
+
caption = self.generate_caption(image_path)
|
| 130 |
+
results["caption"] = caption
|
| 131 |
+
except Exception as e:
|
| 132 |
+
results["caption"] = f"Error: {str(e)}"
|
| 133 |
+
|
| 134 |
+
# Step 2: Generate image from text prompt
|
| 135 |
+
try:
|
| 136 |
+
print("🎨 Step 2: Generating image from text...")
|
| 137 |
+
generated_image_path = self.generate_image(text_prompt)
|
| 138 |
+
results["generated_image"] = generated_image_path
|
| 139 |
+
except Exception as e:
|
| 140 |
+
results["generated_image"] = f"Error: {str(e)}"
|
| 141 |
+
|
| 142 |
+
# Step 3: Create analysis prompt
|
| 143 |
+
if results["caption"] and not results["caption"].startswith("Error"):
|
| 144 |
+
analysis_prompt = f"Analyze this image caption: {results['caption']}"
|
| 145 |
+
results["analysis_prompt"] = analysis_prompt
|
| 146 |
+
|
| 147 |
+
return results
|
| 148 |
+
|
| 149 |
+
def _log_task(self, task_type: str, input_data: str, output: Any,
|
| 150 |
+
processing_time: float, error: Optional[str] = None):
|
| 151 |
+
"""Log task execution"""
|
| 152 |
+
self.task_history.append({
|
| 153 |
+
"task_type": task_type,
|
| 154 |
+
"input_data": str(input_data)[:100], # Truncate for logging
|
| 155 |
+
"output": str(output)[:200] if output else None,
|
| 156 |
+
"processing_time": processing_time,
|
| 157 |
+
"timestamp": time.time(),
|
| 158 |
+
"error": error
|
| 159 |
+
})
|
| 160 |
+
|
| 161 |
+
def get_task_history(self) -> list:
|
| 162 |
+
"""Get task execution history"""
|
| 163 |
+
return self.task_history
|
| 164 |
+
|
| 165 |
+
def save_task_history(self, filepath: str = "demo_task_history.json"):
|
| 166 |
+
"""Save task history to file"""
|
| 167 |
+
with open(filepath, 'w') as f:
|
| 168 |
+
json.dump(self.task_history, f, indent=2)
|
| 169 |
+
print(f"📄 Task history saved to {filepath}")
|
| 170 |
+
|
| 171 |
+
def get_status(self) -> Dict[str, Any]:
|
| 172 |
+
"""Get orchestrator status"""
|
| 173 |
+
return {
|
| 174 |
+
"models_loaded": {
|
| 175 |
+
"caption_model": self.caption_model is not None,
|
| 176 |
+
"text2img_pipeline": self.text2img_pipeline is not None
|
| 177 |
+
},
|
| 178 |
+
"total_tasks": len(self.task_history),
|
| 179 |
+
"device": self.device,
|
| 180 |
+
"child_models": {
|
| 181 |
+
"clip_gpt2_captioner": "kunaliitkgp09/clip-gpt2-image-captioner",
|
| 182 |
+
"flickr30k_text2img": "kunaliitkgp09/flickr30k-text-to-image"
|
| 183 |
+
}
|
| 184 |
+
}
|
| 185 |
+
|
| 186 |
+
def demo_basic_usage():
|
| 187 |
+
"""Demo 1: Basic usage of the orchestrator"""
|
| 188 |
+
print("="*60)
|
| 189 |
+
print("DEMO 1: BASIC USAGE")
|
| 190 |
+
print("="*60)
|
| 191 |
+
|
| 192 |
+
# Initialize orchestrator
|
| 193 |
+
orchestrator = DemoMultiModelOrchestrator()
|
| 194 |
+
|
| 195 |
+
# Initialize models
|
| 196 |
+
print("🚀 Initializing orchestrator...")
|
| 197 |
+
if not orchestrator.initialize_models():
|
| 198 |
+
print("❌ Failed to initialize models. Exiting.")
|
| 199 |
+
return
|
| 200 |
+
|
| 201 |
+
# Get status
|
| 202 |
+
status = orchestrator.get_status()
|
| 203 |
+
print(f"\n📊 Orchestrator Status:")
|
| 204 |
+
print(json.dumps(status, indent=2))
|
| 205 |
+
|
| 206 |
+
# Example 1: Image captioning
|
| 207 |
+
print("\n" + "-"*40)
|
| 208 |
+
print("🖼️ IMAGE CAPTIONING")
|
| 209 |
+
print("-"*40)
|
| 210 |
+
try:
|
| 211 |
+
caption = orchestrator.generate_caption("sample_image.jpg")
|
| 212 |
+
print(f"📝 Generated Caption: {caption}")
|
| 213 |
+
except Exception as e:
|
| 214 |
+
print(f"❌ Caption generation failed: {e}")
|
| 215 |
+
|
| 216 |
+
# Example 2: Text-to-image generation
|
| 217 |
+
print("\n" + "-"*40)
|
| 218 |
+
print("🎨 TEXT-TO-IMAGE GENERATION")
|
| 219 |
+
print("-"*40)
|
| 220 |
+
try:
|
| 221 |
+
image_path = orchestrator.generate_image("A beautiful sunset over mountains with a lake")
|
| 222 |
+
print(f"🖼️ Generated Image: {image_path}")
|
| 223 |
+
except Exception as e:
|
| 224 |
+
print(f"❌ Image generation failed: {e}")
|
| 225 |
+
|
| 226 |
+
# Example 3: Task routing
|
| 227 |
+
print("\n" + "-"*40)
|
| 228 |
+
print("🎯 TASK ROUTING")
|
| 229 |
+
print("-"*40)
|
| 230 |
+
try:
|
| 231 |
+
# Route caption task
|
| 232 |
+
caption = orchestrator.route_task("caption", "sample_image.jpg")
|
| 233 |
+
print(f"📝 Routed Caption: {caption}")
|
| 234 |
+
|
| 235 |
+
# Route image generation task
|
| 236 |
+
image_path = orchestrator.route_task("generate_image", "A cat sitting on a windowsill")
|
| 237 |
+
print(f"🖼️ Routed Image: {image_path}")
|
| 238 |
+
except Exception as e:
|
| 239 |
+
print(f"❌ Task routing failed: {e}")
|
| 240 |
+
|
| 241 |
+
def demo_multimodal_processing():
|
| 242 |
+
"""Demo 2: Multimodal processing"""
|
| 243 |
+
print("\n" + "="*60)
|
| 244 |
+
print("DEMO 2: MULTIMODAL PROCESSING")
|
| 245 |
+
print("="*60)
|
| 246 |
+
|
| 247 |
+
orchestrator = DemoMultiModelOrchestrator()
|
| 248 |
+
|
| 249 |
+
if not orchestrator.initialize_models():
|
| 250 |
+
print("❌ Failed to initialize models. Exiting.")
|
| 251 |
+
return
|
| 252 |
+
|
| 253 |
+
# Process multimodal task
|
| 254 |
+
print("🔄 Processing multimodal task...")
|
| 255 |
+
try:
|
| 256 |
+
results = orchestrator.process_multimodal_task(
|
| 257 |
+
image_path="sample_image.jpg",
|
| 258 |
+
text_prompt="A serene landscape with mountains and a flowing river"
|
| 259 |
+
)
|
| 260 |
+
|
| 261 |
+
print("\n📊 Multimodal Results:")
|
| 262 |
+
for key, value in results.items():
|
| 263 |
+
print(f" {key}: {value}")
|
| 264 |
+
|
| 265 |
+
except Exception as e:
|
| 266 |
+
print(f"❌ Multimodal processing failed: {e}")
|
| 267 |
+
|
| 268 |
+
def demo_task_history():
|
| 269 |
+
"""Demo 3: Task history and monitoring"""
|
| 270 |
+
print("\n" + "="*60)
|
| 271 |
+
print("DEMO 3: TASK HISTORY")
|
| 272 |
+
print("="*60)
|
| 273 |
+
|
| 274 |
+
orchestrator = DemoMultiModelOrchestrator()
|
| 275 |
+
|
| 276 |
+
if not orchestrator.initialize_models():
|
| 277 |
+
print("❌ Failed to initialize models. Exiting.")
|
| 278 |
+
return
|
| 279 |
+
|
| 280 |
+
# Perform some tasks
|
| 281 |
+
print("🔄 Performing tasks to build history...")
|
| 282 |
+
|
| 283 |
+
try:
|
| 284 |
+
# Task 1
|
| 285 |
+
caption1 = orchestrator.generate_caption("image1.jpg")
|
| 286 |
+
print(f"📝 Task 1 - Caption: {caption1}")
|
| 287 |
+
|
| 288 |
+
# Task 2
|
| 289 |
+
image1 = orchestrator.generate_image("A peaceful forest scene")
|
| 290 |
+
print(f"🖼️ Task 2 - Image: {image1}")
|
| 291 |
+
|
| 292 |
+
# Task 3
|
| 293 |
+
caption2 = orchestrator.generate_caption("image2.jpg")
|
| 294 |
+
print(f"📝 Task 3 - Caption: {caption2}")
|
| 295 |
+
|
| 296 |
+
except Exception as e:
|
| 297 |
+
print(f"❌ Task execution failed: {e}")
|
| 298 |
+
|
| 299 |
+
# Display task history
|
| 300 |
+
print("\n" + "-"*40)
|
| 301 |
+
print("📋 TASK HISTORY")
|
| 302 |
+
print("-"*40)
|
| 303 |
+
history = orchestrator.get_task_history()
|
| 304 |
+
|
| 305 |
+
for i, task in enumerate(history):
|
| 306 |
+
print(f"\n📊 Task {i+1}:")
|
| 307 |
+
print(f" Type: {task['task_type']}")
|
| 308 |
+
print(f" Input: {task['input_data']}")
|
| 309 |
+
print(f" Output: {task['output']}")
|
| 310 |
+
print(f" Processing Time: {task['processing_time']:.2f}s")
|
| 311 |
+
print(f" Success: {task.get('error') is None}")
|
| 312 |
+
if task.get('error'):
|
| 313 |
+
print(f" Error: {task['error']}")
|
| 314 |
+
|
| 315 |
+
# Save task history
|
| 316 |
+
orchestrator.save_task_history("demo_task_history.json")
|
| 317 |
+
print(f"\n💾 Task history saved to demo_task_history.json")
|
| 318 |
+
|
| 319 |
+
def main():
|
| 320 |
+
"""Run all demos"""
|
| 321 |
+
print("🎭 Multi-Model Orchestrator Demo")
|
| 322 |
+
print("This demo shows the structure and functionality of the orchestrator.")
|
| 323 |
+
print("Note: This is a simulation - actual models would be downloaded and used.")
|
| 324 |
+
|
| 325 |
+
try:
|
| 326 |
+
# Run demos
|
| 327 |
+
demo_basic_usage()
|
| 328 |
+
demo_multimodal_processing()
|
| 329 |
+
demo_task_history()
|
| 330 |
+
|
| 331 |
+
print("\n" + "="*60)
|
| 332 |
+
print("🎉 ALL DEMOS COMPLETED SUCCESSFULLY!")
|
| 333 |
+
print("="*60)
|
| 334 |
+
|
| 335 |
+
print("\n📁 Generated files:")
|
| 336 |
+
print(" - demo_task_history.json (task history)")
|
| 337 |
+
|
| 338 |
+
print("\n🔗 Real Model Links:")
|
| 339 |
+
print(" - CLIP-GPT2 Captioner: https://huggingface.co/kunaliitkgp09/clip-gpt2-image-captioner")
|
| 340 |
+
print(" - Flickr30k Text-to-Image: https://huggingface.co/kunaliitkgp09/flickr30k-text-to-image")
|
| 341 |
+
|
| 342 |
+
print("\n🚀 Next steps:")
|
| 343 |
+
print("1. Install dependencies: pip install -r multi_model_requirements.txt")
|
| 344 |
+
print("2. Run with real models: python multi_model_example.py")
|
| 345 |
+
print("3. Integrate into your applications")
|
| 346 |
+
print("4. Add more child models to the system")
|
| 347 |
+
|
| 348 |
+
except Exception as e:
|
| 349 |
+
print(f"\n❌ Error during execution: {e}")
|
| 350 |
+
|
| 351 |
+
if __name__ == "__main__":
|
| 352 |
+
main()
|
build/lib/multi_model_orchestrator/multi_model_orchestrator.py
ADDED
|
@@ -0,0 +1,497 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
import torch
|
| 2 |
+
import asyncio
|
| 3 |
+
import logging
|
| 4 |
+
import json
|
| 5 |
+
import time
|
| 6 |
+
from typing import Dict, List, Optional, Union, Any
|
| 7 |
+
from dataclasses import dataclass
|
| 8 |
+
from enum import Enum
|
| 9 |
+
from pathlib import Path
|
| 10 |
+
import traceback
|
| 11 |
+
|
| 12 |
+
from transformers import AutoProcessor, AutoModelForCausalLM, CLIPProcessor, GPT2Tokenizer
|
| 13 |
+
from diffusers import StableDiffusionPipeline
|
| 14 |
+
from PIL import Image
|
| 15 |
+
import numpy as np
|
| 16 |
+
|
| 17 |
+
# Configure logging
|
| 18 |
+
logging.basicConfig(level=logging.INFO)
|
| 19 |
+
logger = logging.getLogger(__name__)
|
| 20 |
+
|
| 21 |
+
class TaskType(Enum):
|
| 22 |
+
"""Enumeration of supported task types"""
|
| 23 |
+
IMAGE_TO_TEXT = "image_to_text"
|
| 24 |
+
TEXT_TO_IMAGE = "text_to_image"
|
| 25 |
+
IMAGE_ANALYSIS = "image_analysis"
|
| 26 |
+
TEXT_GENERATION = "text_generation"
|
| 27 |
+
MULTIMODAL_GENERATION = "multimodal_generation"
|
| 28 |
+
|
| 29 |
+
@dataclass
|
| 30 |
+
class ModelConfig:
|
| 31 |
+
"""Configuration for child models"""
|
| 32 |
+
name: str
|
| 33 |
+
model_type: str
|
| 34 |
+
device: str = "cuda"
|
| 35 |
+
max_length: int = 50
|
| 36 |
+
temperature: float = 0.7
|
| 37 |
+
top_p: float = 0.9
|
| 38 |
+
batch_size: int = 1
|
| 39 |
+
|
| 40 |
+
@dataclass
|
| 41 |
+
class TaskResult:
|
| 42 |
+
"""Result from a child model task"""
|
| 43 |
+
success: bool
|
| 44 |
+
output: Any
|
| 45 |
+
model_used: str
|
| 46 |
+
processing_time: float
|
| 47 |
+
error_message: Optional[str] = None
|
| 48 |
+
metadata: Optional[Dict] = None
|
| 49 |
+
|
| 50 |
+
class ModelManager:
|
| 51 |
+
"""Manages loading and caching of child models"""
|
| 52 |
+
|
| 53 |
+
def __init__(self, device: str = "cuda"):
|
| 54 |
+
self.device = device if torch.cuda.is_available() else "cpu"
|
| 55 |
+
self.models = {}
|
| 56 |
+
self.processors = {}
|
| 57 |
+
self.pipelines = {}
|
| 58 |
+
self.model_configs = {}
|
| 59 |
+
|
| 60 |
+
def register_model(self, name: str, config: ModelConfig):
|
| 61 |
+
"""Register a model configuration"""
|
| 62 |
+
self.model_configs[name] = config
|
| 63 |
+
|
| 64 |
+
def load_model(self, name: str) -> bool:
|
| 65 |
+
"""Load a specific model"""
|
| 66 |
+
if name not in self.model_configs:
|
| 67 |
+
logger.error(f"Model {name} not registered")
|
| 68 |
+
return False
|
| 69 |
+
|
| 70 |
+
config = self.model_configs[name]
|
| 71 |
+
|
| 72 |
+
try:
|
| 73 |
+
logger.info(f"Loading model: {name}")
|
| 74 |
+
start_time = time.time()
|
| 75 |
+
|
| 76 |
+
if config.model_type == "caption":
|
| 77 |
+
# Load CLIP-GPT2 captioning model
|
| 78 |
+
self.processors[name] = CLIPProcessor.from_pretrained("openai/clip-vit-base-patch16")
|
| 79 |
+
self.models[name] = AutoModelForCausalLM.from_pretrained(config.name).to(self.device)
|
| 80 |
+
|
| 81 |
+
elif config.model_type == "text2img":
|
| 82 |
+
# Load Stable Diffusion text-to-image model
|
| 83 |
+
self.pipelines[name] = StableDiffusionPipeline.from_pretrained(
|
| 84 |
+
config.name,
|
| 85 |
+
torch_dtype=torch.float16 if self.device == "cuda" else torch.float32
|
| 86 |
+
).to(self.device)
|
| 87 |
+
|
| 88 |
+
elif config.model_type == "llm":
|
| 89 |
+
# Load general language model
|
| 90 |
+
self.processors[name] = AutoProcessor.from_pretrained(config.name)
|
| 91 |
+
self.models[name] = AutoModelForCausalLM.from_pretrained(config.name).to(self.device)
|
| 92 |
+
|
| 93 |
+
load_time = time.time() - start_time
|
| 94 |
+
logger.info(f"Model {name} loaded successfully in {load_time:.2f}s")
|
| 95 |
+
return True
|
| 96 |
+
|
| 97 |
+
except Exception as e:
|
| 98 |
+
logger.error(f"Failed to load model {name}: {str(e)}")
|
| 99 |
+
return False
|
| 100 |
+
|
| 101 |
+
def get_model(self, name: str):
|
| 102 |
+
"""Get a loaded model"""
|
| 103 |
+
if name in self.models:
|
| 104 |
+
return self.models[name]
|
| 105 |
+
elif name in self.pipelines:
|
| 106 |
+
return self.pipelines[name]
|
| 107 |
+
else:
|
| 108 |
+
raise ValueError(f"Model {name} not loaded")
|
| 109 |
+
|
| 110 |
+
def get_processor(self, name: str):
|
| 111 |
+
"""Get a model processor"""
|
| 112 |
+
if name in self.processors:
|
| 113 |
+
return self.processors[name]
|
| 114 |
+
else:
|
| 115 |
+
raise ValueError(f"Processor for {name} not loaded")
|
| 116 |
+
|
| 117 |
+
class ChildModel:
|
| 118 |
+
"""Base class for child models"""
|
| 119 |
+
|
| 120 |
+
def __init__(self, name: str, model_manager: ModelManager):
|
| 121 |
+
self.name = name
|
| 122 |
+
self.model_manager = model_manager
|
| 123 |
+
self.config = model_manager.model_configs[name]
|
| 124 |
+
|
| 125 |
+
async def process(self, input_data: Any) -> TaskResult:
|
| 126 |
+
"""Process input data and return result"""
|
| 127 |
+
start_time = time.time()
|
| 128 |
+
|
| 129 |
+
try:
|
| 130 |
+
if self.config.model_type == "caption":
|
| 131 |
+
result = await self._process_caption(input_data)
|
| 132 |
+
elif self.config.model_type == "text2img":
|
| 133 |
+
result = await self._process_text2img(input_data)
|
| 134 |
+
elif self.config.model_type == "llm":
|
| 135 |
+
result = await self._process_llm(input_data)
|
| 136 |
+
else:
|
| 137 |
+
raise ValueError(f"Unknown model type: {self.config.model_type}")
|
| 138 |
+
|
| 139 |
+
processing_time = time.time() - start_time
|
| 140 |
+
|
| 141 |
+
return TaskResult(
|
| 142 |
+
success=True,
|
| 143 |
+
output=result,
|
| 144 |
+
model_used=self.name,
|
| 145 |
+
processing_time=processing_time,
|
| 146 |
+
metadata={"model_type": self.config.model_type}
|
| 147 |
+
)
|
| 148 |
+
|
| 149 |
+
except Exception as e:
|
| 150 |
+
processing_time = time.time() - start_time
|
| 151 |
+
logger.error(f"Error in model {self.name}: {str(e)}")
|
| 152 |
+
|
| 153 |
+
return TaskResult(
|
| 154 |
+
success=False,
|
| 155 |
+
output=None,
|
| 156 |
+
model_used=self.name,
|
| 157 |
+
processing_time=processing_time,
|
| 158 |
+
error_message=str(e)
|
| 159 |
+
)
|
| 160 |
+
|
| 161 |
+
async def _process_caption(self, image_path: str) -> str:
|
| 162 |
+
"""Process image captioning task"""
|
| 163 |
+
# Run in thread pool to avoid blocking
|
| 164 |
+
loop = asyncio.get_event_loop()
|
| 165 |
+
return await loop.run_in_executor(None, self._caption_sync, image_path)
|
| 166 |
+
|
| 167 |
+
def _caption_sync(self, image_path: str) -> str:
|
| 168 |
+
"""Synchronous image captioning"""
|
| 169 |
+
image = Image.open(image_path).convert("RGB")
|
| 170 |
+
processor = self.model_manager.get_processor(self.name)
|
| 171 |
+
model = self.model_manager.get_model(self.name)
|
| 172 |
+
|
| 173 |
+
inputs = processor(images=image, return_tensors="pt").to(self.device)
|
| 174 |
+
|
| 175 |
+
with torch.no_grad():
|
| 176 |
+
output = model.generate(
|
| 177 |
+
**inputs,
|
| 178 |
+
max_length=self.config.max_length,
|
| 179 |
+
temperature=self.config.temperature,
|
| 180 |
+
top_p=self.config.top_p,
|
| 181 |
+
do_sample=True,
|
| 182 |
+
pad_token_id=processor.tokenizer.eos_token_id
|
| 183 |
+
)
|
| 184 |
+
|
| 185 |
+
caption = processor.tokenizer.batch_decode(output, skip_special_tokens=True)[0]
|
| 186 |
+
return caption
|
| 187 |
+
|
| 188 |
+
async def _process_text2img(self, prompt: str) -> str:
|
| 189 |
+
"""Process text-to-image generation task"""
|
| 190 |
+
loop = asyncio.get_event_loop()
|
| 191 |
+
return await loop.run_in_executor(None, self._text2img_sync, prompt)
|
| 192 |
+
|
| 193 |
+
def _text2img_sync(self, prompt: str) -> str:
|
| 194 |
+
"""Synchronous text-to-image generation"""
|
| 195 |
+
pipeline = self.model_manager.get_model(self.name)
|
| 196 |
+
|
| 197 |
+
# Generate unique output path
|
| 198 |
+
timestamp = int(time.time())
|
| 199 |
+
output_path = f"generated_image_{timestamp}.png"
|
| 200 |
+
|
| 201 |
+
with torch.no_grad():
|
| 202 |
+
image = pipeline(
|
| 203 |
+
prompt,
|
| 204 |
+
num_inference_steps=20,
|
| 205 |
+
guidance_scale=7.5,
|
| 206 |
+
width=512,
|
| 207 |
+
height=512
|
| 208 |
+
).images[0]
|
| 209 |
+
|
| 210 |
+
image.save(output_path)
|
| 211 |
+
return output_path
|
| 212 |
+
|
| 213 |
+
async def _process_llm(self, text: str) -> str:
|
| 214 |
+
"""Process general language model task"""
|
| 215 |
+
loop = asyncio.get_event_loop()
|
| 216 |
+
return await loop.run_in_executor(None, self._llm_sync, text)
|
| 217 |
+
|
| 218 |
+
def _llm_sync(self, text: str) -> str:
|
| 219 |
+
"""Synchronous language model processing"""
|
| 220 |
+
processor = self.model_manager.get_processor(self.name)
|
| 221 |
+
model = self.model_manager.get_model(self.name)
|
| 222 |
+
|
| 223 |
+
inputs = processor(text, return_tensors="pt").to(self.device)
|
| 224 |
+
|
| 225 |
+
with torch.no_grad():
|
| 226 |
+
output = model.generate(
|
| 227 |
+
**inputs,
|
| 228 |
+
max_length=self.config.max_length,
|
| 229 |
+
temperature=self.config.temperature,
|
| 230 |
+
top_p=self.config.top_p,
|
| 231 |
+
do_sample=True,
|
| 232 |
+
pad_token_id=processor.tokenizer.eos_token_id
|
| 233 |
+
)
|
| 234 |
+
|
| 235 |
+
result = processor.tokenizer.batch_decode(output, skip_special_tokens=True)[0]
|
| 236 |
+
return result
|
| 237 |
+
|
| 238 |
+
class ParentOrchestrator:
|
| 239 |
+
"""Parent model that orchestrates child models"""
|
| 240 |
+
|
| 241 |
+
def __init__(self, device: str = "cuda"):
|
| 242 |
+
self.device = device if torch.cuda.is_available() else "cpu"
|
| 243 |
+
self.model_manager = ModelManager(device)
|
| 244 |
+
self.child_models = {}
|
| 245 |
+
self.task_history = []
|
| 246 |
+
|
| 247 |
+
# Register child models
|
| 248 |
+
self._register_child_models()
|
| 249 |
+
|
| 250 |
+
def _register_child_models(self):
|
| 251 |
+
"""Register all child models"""
|
| 252 |
+
# CLIP-GPT2 Image Captioner
|
| 253 |
+
self.model_manager.register_model(
|
| 254 |
+
"clip_gpt2_captioner",
|
| 255 |
+
ModelConfig(
|
| 256 |
+
name="kunaliitkgp09/clip-gpt2-image-captioner",
|
| 257 |
+
model_type="caption",
|
| 258 |
+
device=self.device,
|
| 259 |
+
max_length=50,
|
| 260 |
+
temperature=0.7
|
| 261 |
+
)
|
| 262 |
+
)
|
| 263 |
+
|
| 264 |
+
# Flickr30k Text-to-Image
|
| 265 |
+
self.model_manager.register_model(
|
| 266 |
+
"flickr30k_text2img",
|
| 267 |
+
ModelConfig(
|
| 268 |
+
name="kunaliitkgp09/flickr30k-text-to-image",
|
| 269 |
+
model_type="text2img",
|
| 270 |
+
device=self.device,
|
| 271 |
+
temperature=0.8
|
| 272 |
+
)
|
| 273 |
+
)
|
| 274 |
+
|
| 275 |
+
# Optional: Add a general LLM for text processing
|
| 276 |
+
self.model_manager.register_model(
|
| 277 |
+
"gpt2_text",
|
| 278 |
+
ModelConfig(
|
| 279 |
+
name="gpt2",
|
| 280 |
+
model_type="llm",
|
| 281 |
+
device=self.device,
|
| 282 |
+
max_length=100,
|
| 283 |
+
temperature=0.8
|
| 284 |
+
)
|
| 285 |
+
)
|
| 286 |
+
|
| 287 |
+
async def initialize_models(self):
|
| 288 |
+
"""Initialize all child models"""
|
| 289 |
+
logger.info("Initializing child models...")
|
| 290 |
+
|
| 291 |
+
for model_name in self.model_manager.model_configs:
|
| 292 |
+
success = self.model_manager.load_model(model_name)
|
| 293 |
+
if success:
|
| 294 |
+
self.child_models[model_name] = ChildModel(model_name, self.model_manager)
|
| 295 |
+
logger.info(f"Child model {model_name} initialized successfully")
|
| 296 |
+
else:
|
| 297 |
+
logger.error(f"Failed to initialize child model {model_name}")
|
| 298 |
+
|
| 299 |
+
async def route_task(self, task_type: TaskType, input_data: Any,
|
| 300 |
+
model_name: Optional[str] = None) -> TaskResult:
|
| 301 |
+
"""Route task to appropriate child model"""
|
| 302 |
+
|
| 303 |
+
# Determine which model to use
|
| 304 |
+
if model_name is None:
|
| 305 |
+
model_name = self._select_model_for_task(task_type)
|
| 306 |
+
|
| 307 |
+
if model_name not in self.child_models:
|
| 308 |
+
return TaskResult(
|
| 309 |
+
success=False,
|
| 310 |
+
output=None,
|
| 311 |
+
model_used=model_name,
|
| 312 |
+
processing_time=0.0,
|
| 313 |
+
error_message=f"Model {model_name} not available"
|
| 314 |
+
)
|
| 315 |
+
|
| 316 |
+
# Process task
|
| 317 |
+
child_model = self.child_models[model_name]
|
| 318 |
+
result = await child_model.process(input_data)
|
| 319 |
+
|
| 320 |
+
# Log task
|
| 321 |
+
self.task_history.append({
|
| 322 |
+
"task_type": task_type.value,
|
| 323 |
+
"model_used": model_name,
|
| 324 |
+
"input_data": str(input_data)[:100], # Truncate for logging
|
| 325 |
+
"success": result.success,
|
| 326 |
+
"processing_time": result.processing_time,
|
| 327 |
+
"timestamp": time.time()
|
| 328 |
+
})
|
| 329 |
+
|
| 330 |
+
return result
|
| 331 |
+
|
| 332 |
+
def _select_model_for_task(self, task_type: TaskType) -> str:
|
| 333 |
+
"""Select appropriate model for task type"""
|
| 334 |
+
if task_type == TaskType.IMAGE_TO_TEXT:
|
| 335 |
+
return "clip_gpt2_captioner"
|
| 336 |
+
elif task_type == TaskType.TEXT_TO_IMAGE:
|
| 337 |
+
return "flickr30k_text2img"
|
| 338 |
+
elif task_type == TaskType.TEXT_GENERATION:
|
| 339 |
+
return "gpt2_text"
|
| 340 |
+
else:
|
| 341 |
+
raise ValueError(f"No model available for task type: {task_type}")
|
| 342 |
+
|
| 343 |
+
async def process_multimodal_task(self, image_path: str, text_prompt: str) -> Dict[str, TaskResult]:
|
| 344 |
+
"""Process a multimodal task using multiple child models"""
|
| 345 |
+
results = {}
|
| 346 |
+
|
| 347 |
+
# Step 1: Generate caption from image
|
| 348 |
+
caption_result = await self.route_task(
|
| 349 |
+
TaskType.IMAGE_TO_TEXT,
|
| 350 |
+
image_path,
|
| 351 |
+
"clip_gpt2_captioner"
|
| 352 |
+
)
|
| 353 |
+
results["caption"] = caption_result
|
| 354 |
+
|
| 355 |
+
# Step 2: Generate image from text prompt
|
| 356 |
+
image_result = await self.route_task(
|
| 357 |
+
TaskType.TEXT_TO_IMAGE,
|
| 358 |
+
text_prompt,
|
| 359 |
+
"flickr30k_text2img"
|
| 360 |
+
)
|
| 361 |
+
results["generated_image"] = image_result
|
| 362 |
+
|
| 363 |
+
# Step 3: Generate text analysis using LLM
|
| 364 |
+
if caption_result.success:
|
| 365 |
+
analysis_prompt = f"Analyze this image caption: {caption_result.output}"
|
| 366 |
+
analysis_result = await self.route_task(
|
| 367 |
+
TaskType.TEXT_GENERATION,
|
| 368 |
+
analysis_prompt,
|
| 369 |
+
"gpt2_text"
|
| 370 |
+
)
|
| 371 |
+
results["analysis"] = analysis_result
|
| 372 |
+
|
| 373 |
+
return results
|
| 374 |
+
|
| 375 |
+
def get_task_history(self) -> List[Dict]:
|
| 376 |
+
"""Get task execution history"""
|
| 377 |
+
return self.task_history
|
| 378 |
+
|
| 379 |
+
def get_model_status(self) -> Dict[str, bool]:
|
| 380 |
+
"""Get status of all child models"""
|
| 381 |
+
return {
|
| 382 |
+
name: name in self.child_models
|
| 383 |
+
for name in self.model_manager.model_configs
|
| 384 |
+
}
|
| 385 |
+
|
| 386 |
+
def save_task_history(self, filepath: str):
|
| 387 |
+
"""Save task history to file"""
|
| 388 |
+
with open(filepath, 'w') as f:
|
| 389 |
+
json.dump(self.task_history, f, indent=2)
|
| 390 |
+
logger.info(f"Task history saved to {filepath}")
|
| 391 |
+
|
| 392 |
+
class MultiModelOrchestrator:
|
| 393 |
+
"""Main orchestrator class with simplified interface"""
|
| 394 |
+
|
| 395 |
+
def __init__(self, device: str = "cuda"):
|
| 396 |
+
self.parent = ParentOrchestrator(device)
|
| 397 |
+
self.initialized = False
|
| 398 |
+
|
| 399 |
+
async def initialize(self):
|
| 400 |
+
"""Initialize the orchestrator"""
|
| 401 |
+
await self.parent.initialize_models()
|
| 402 |
+
self.initialized = True
|
| 403 |
+
logger.info("Multi-model orchestrator initialized successfully")
|
| 404 |
+
|
| 405 |
+
async def generate_caption(self, image_path: str) -> str:
|
| 406 |
+
"""Generate caption from image"""
|
| 407 |
+
if not self.initialized:
|
| 408 |
+
await self.initialize()
|
| 409 |
+
|
| 410 |
+
result = await self.parent.route_task(TaskType.IMAGE_TO_TEXT, image_path)
|
| 411 |
+
|
| 412 |
+
if result.success:
|
| 413 |
+
return result.output
|
| 414 |
+
else:
|
| 415 |
+
raise RuntimeError(f"Caption generation failed: {result.error_message}")
|
| 416 |
+
|
| 417 |
+
async def generate_image(self, text_prompt: str) -> str:
|
| 418 |
+
"""Generate image from text"""
|
| 419 |
+
if not self.initialized:
|
| 420 |
+
await self.initialize()
|
| 421 |
+
|
| 422 |
+
result = await self.parent.route_task(TaskType.TEXT_TO_IMAGE, text_prompt)
|
| 423 |
+
|
| 424 |
+
if result.success:
|
| 425 |
+
return result.output
|
| 426 |
+
else:
|
| 427 |
+
raise RuntimeError(f"Image generation failed: {result.error_message}")
|
| 428 |
+
|
| 429 |
+
async def process_multimodal(self, image_path: str, text_prompt: str) -> Dict[str, Any]:
|
| 430 |
+
"""Process multimodal task"""
|
| 431 |
+
if not self.initialized:
|
| 432 |
+
await self.initialize()
|
| 433 |
+
|
| 434 |
+
results = await self.parent.process_multimodal_task(image_path, text_prompt)
|
| 435 |
+
|
| 436 |
+
# Extract outputs
|
| 437 |
+
output = {}
|
| 438 |
+
for key, result in results.items():
|
| 439 |
+
if result.success:
|
| 440 |
+
output[key] = result.output
|
| 441 |
+
else:
|
| 442 |
+
output[key] = f"Error: {result.error_message}"
|
| 443 |
+
|
| 444 |
+
return output
|
| 445 |
+
|
| 446 |
+
def get_status(self) -> Dict[str, Any]:
|
| 447 |
+
"""Get orchestrator status"""
|
| 448 |
+
return {
|
| 449 |
+
"initialized": self.initialized,
|
| 450 |
+
"model_status": self.parent.get_model_status(),
|
| 451 |
+
"total_tasks": len(self.parent.get_task_history())
|
| 452 |
+
}
|
| 453 |
+
|
| 454 |
+
# Usage examples
|
| 455 |
+
async def main():
|
| 456 |
+
"""Example usage of the multi-model orchestrator"""
|
| 457 |
+
|
| 458 |
+
# Initialize orchestrator
|
| 459 |
+
orchestrator = MultiModelOrchestrator()
|
| 460 |
+
await orchestrator.initialize()
|
| 461 |
+
|
| 462 |
+
print("Multi-Model Orchestrator Status:")
|
| 463 |
+
print(json.dumps(orchestrator.get_status(), indent=2))
|
| 464 |
+
|
| 465 |
+
# Example 1: Image captioning
|
| 466 |
+
try:
|
| 467 |
+
# Note: Replace with actual image path
|
| 468 |
+
caption = await orchestrator.generate_caption("sample_image.jpg")
|
| 469 |
+
print(f"\nGenerated Caption: {caption}")
|
| 470 |
+
except Exception as e:
|
| 471 |
+
print(f"Caption generation error: {e}")
|
| 472 |
+
|
| 473 |
+
# Example 2: Text-to-image generation
|
| 474 |
+
try:
|
| 475 |
+
image_path = await orchestrator.generate_image("A beautiful sunset over mountains")
|
| 476 |
+
print(f"\nGenerated Image saved at: {image_path}")
|
| 477 |
+
except Exception as e:
|
| 478 |
+
print(f"Image generation error: {e}")
|
| 479 |
+
|
| 480 |
+
# Example 3: Multimodal processing
|
| 481 |
+
try:
|
| 482 |
+
multimodal_result = await orchestrator.process_multimodal(
|
| 483 |
+
"sample_image.jpg",
|
| 484 |
+
"A serene landscape with mountains"
|
| 485 |
+
)
|
| 486 |
+
print(f"\nMultimodal Results:")
|
| 487 |
+
for key, value in multimodal_result.items():
|
| 488 |
+
print(f" {key}: {value}")
|
| 489 |
+
except Exception as e:
|
| 490 |
+
print(f"Multimodal processing error: {e}")
|
| 491 |
+
|
| 492 |
+
# Save task history
|
| 493 |
+
orchestrator.parent.save_task_history("task_history.json")
|
| 494 |
+
|
| 495 |
+
if __name__ == "__main__":
|
| 496 |
+
# Run the example
|
| 497 |
+
asyncio.run(main())
|
build/lib/multi_model_orchestrator/simple_orchestrator.py
ADDED
|
@@ -0,0 +1,323 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/usr/bin/env python3
|
| 2 |
+
"""
|
| 3 |
+
Simplified Multi-Model Orchestrator
|
| 4 |
+
Based on the original code structure with enhanced functionality
|
| 5 |
+
"""
|
| 6 |
+
|
| 7 |
+
import asyncio
|
| 8 |
+
import torch
|
| 9 |
+
from transformers import CLIPProcessor, GPT2Tokenizer
|
| 10 |
+
from diffusers import StableDiffusionPipeline
|
| 11 |
+
from PIL import Image
|
| 12 |
+
import time
|
| 13 |
+
import json
|
| 14 |
+
from typing import Dict, Any, Optional
|
| 15 |
+
|
| 16 |
+
class SimpleMultiModelOrchestrator:
|
| 17 |
+
"""Simplified orchestrator matching the original code structure"""
|
| 18 |
+
|
| 19 |
+
def __init__(self, device: str = "cuda"):
|
| 20 |
+
self.device = device if torch.cuda.is_available() else "cpu"
|
| 21 |
+
self.caption_model_name = "kunaliitkgp09/clip-gpt2-image-captioner"
|
| 22 |
+
self.text2img_model_name = "kunaliitkgp09/flickr30k-text-to-image"
|
| 23 |
+
|
| 24 |
+
# Model instances
|
| 25 |
+
self.caption_processor = None
|
| 26 |
+
self.caption_model = None
|
| 27 |
+
self.text2img_pipeline = None
|
| 28 |
+
self.tokenizer = None
|
| 29 |
+
|
| 30 |
+
# Task history
|
| 31 |
+
self.task_history = []
|
| 32 |
+
|
| 33 |
+
def initialize_models(self):
|
| 34 |
+
"""Initialize all child models"""
|
| 35 |
+
print("Initializing child models...")
|
| 36 |
+
|
| 37 |
+
try:
|
| 38 |
+
# Load captioning model
|
| 39 |
+
print("Loading CLIP-GPT2 captioning model...")
|
| 40 |
+
self.caption_processor = CLIPProcessor.from_pretrained("openai/clip-vit-base-patch16")
|
| 41 |
+
self.caption_model = torch.hub.load('huggingface/pytorch-transformers', 'model',
|
| 42 |
+
self.caption_model_name).to(self.device)
|
| 43 |
+
self.tokenizer = GPT2Tokenizer.from_pretrained("gpt2")
|
| 44 |
+
self.tokenizer.pad_token = self.tokenizer.eos_token
|
| 45 |
+
print("✓ Captioning model loaded")
|
| 46 |
+
|
| 47 |
+
# Load text-to-image model
|
| 48 |
+
print("Loading Stable Diffusion text-to-image model...")
|
| 49 |
+
self.text2img_pipeline = StableDiffusionPipeline.from_pretrained(
|
| 50 |
+
self.text2img_model_name,
|
| 51 |
+
torch_dtype=torch.float16 if self.device == "cuda" else torch.float32
|
| 52 |
+
).to(self.device)
|
| 53 |
+
print("✓ Text-to-image model loaded")
|
| 54 |
+
|
| 55 |
+
print("All models initialized successfully!")
|
| 56 |
+
return True
|
| 57 |
+
|
| 58 |
+
except Exception as e:
|
| 59 |
+
print(f"Error initializing models: {e}")
|
| 60 |
+
return False
|
| 61 |
+
|
| 62 |
+
def generate_caption(self, image_path: str) -> str:
|
| 63 |
+
"""Child Model 1 - Image Captioning"""
|
| 64 |
+
start_time = time.time()
|
| 65 |
+
|
| 66 |
+
try:
|
| 67 |
+
image = Image.open(image_path).convert("RGB")
|
| 68 |
+
|
| 69 |
+
# Process image with CLIP
|
| 70 |
+
inputs = self.caption_processor(images=image, return_tensors="pt").to(self.device)
|
| 71 |
+
|
| 72 |
+
# Generate caption
|
| 73 |
+
with torch.no_grad():
|
| 74 |
+
output = self.caption_model.generate(
|
| 75 |
+
**inputs,
|
| 76 |
+
max_length=50,
|
| 77 |
+
temperature=0.7,
|
| 78 |
+
do_sample=True,
|
| 79 |
+
pad_token_id=self.tokenizer.eos_token_id
|
| 80 |
+
)
|
| 81 |
+
|
| 82 |
+
caption = self.tokenizer.batch_decode(output, skip_special_tokens=True)[0]
|
| 83 |
+
|
| 84 |
+
# Log task
|
| 85 |
+
self._log_task("caption", image_path, caption, time.time() - start_time)
|
| 86 |
+
|
| 87 |
+
return caption
|
| 88 |
+
|
| 89 |
+
except Exception as e:
|
| 90 |
+
print(f"Error generating caption: {e}")
|
| 91 |
+
self._log_task("caption", image_path, None, time.time() - start_time, str(e))
|
| 92 |
+
raise
|
| 93 |
+
|
| 94 |
+
def generate_image(self, text_prompt: str, output_path: Optional[str] = None) -> str:
|
| 95 |
+
"""Child Model 2 - Text-to-Image"""
|
| 96 |
+
start_time = time.time()
|
| 97 |
+
|
| 98 |
+
try:
|
| 99 |
+
# Generate unique output path if not provided
|
| 100 |
+
if output_path is None:
|
| 101 |
+
timestamp = int(time.time())
|
| 102 |
+
output_path = f"generated_image_{timestamp}.png"
|
| 103 |
+
|
| 104 |
+
# Generate image
|
| 105 |
+
with torch.no_grad():
|
| 106 |
+
image = self.text2img_pipeline(
|
| 107 |
+
text_prompt,
|
| 108 |
+
num_inference_steps=20,
|
| 109 |
+
guidance_scale=7.5,
|
| 110 |
+
width=512,
|
| 111 |
+
height=512
|
| 112 |
+
).images[0]
|
| 113 |
+
|
| 114 |
+
# Save image
|
| 115 |
+
image.save(output_path)
|
| 116 |
+
|
| 117 |
+
# Log task
|
| 118 |
+
self._log_task("generate_image", text_prompt, output_path, time.time() - start_time)
|
| 119 |
+
|
| 120 |
+
return output_path
|
| 121 |
+
|
| 122 |
+
except Exception as e:
|
| 123 |
+
print(f"Error generating image: {e}")
|
| 124 |
+
self._log_task("generate_image", text_prompt, None, time.time() - start_time, str(e))
|
| 125 |
+
raise
|
| 126 |
+
|
| 127 |
+
def route_task(self, task_type: str, input_data: str) -> str:
|
| 128 |
+
"""Parent model decides which child to call"""
|
| 129 |
+
if task_type == "caption":
|
| 130 |
+
return self.generate_caption(input_data)
|
| 131 |
+
elif task_type == "generate_image":
|
| 132 |
+
return self.generate_image(input_data)
|
| 133 |
+
else:
|
| 134 |
+
raise ValueError("Invalid task type: choose 'caption' or 'generate_image'")
|
| 135 |
+
|
| 136 |
+
def process_multimodal_task(self, image_path: str, text_prompt: str) -> Dict[str, str]:
|
| 137 |
+
"""Process a multimodal task using both child models"""
|
| 138 |
+
results = {}
|
| 139 |
+
|
| 140 |
+
# Step 1: Generate caption from image
|
| 141 |
+
try:
|
| 142 |
+
caption = self.generate_caption(image_path)
|
| 143 |
+
results["caption"] = caption
|
| 144 |
+
except Exception as e:
|
| 145 |
+
results["caption"] = f"Error: {str(e)}"
|
| 146 |
+
|
| 147 |
+
# Step 2: Generate image from text prompt
|
| 148 |
+
try:
|
| 149 |
+
generated_image_path = self.generate_image(text_prompt)
|
| 150 |
+
results["generated_image"] = generated_image_path
|
| 151 |
+
except Exception as e:
|
| 152 |
+
results["generated_image"] = f"Error: {str(e)}"
|
| 153 |
+
|
| 154 |
+
# Step 3: Create analysis prompt
|
| 155 |
+
if results["caption"] and not results["caption"].startswith("Error"):
|
| 156 |
+
analysis_prompt = f"Analyze this image caption: {results['caption']}"
|
| 157 |
+
results["analysis_prompt"] = analysis_prompt
|
| 158 |
+
|
| 159 |
+
return results
|
| 160 |
+
|
| 161 |
+
def _log_task(self, task_type: str, input_data: str, output: Any,
|
| 162 |
+
processing_time: float, error: Optional[str] = None):
|
| 163 |
+
"""Log task execution"""
|
| 164 |
+
self.task_history.append({
|
| 165 |
+
"task_type": task_type,
|
| 166 |
+
"input_data": str(input_data)[:100], # Truncate for logging
|
| 167 |
+
"output": str(output)[:200] if output else None,
|
| 168 |
+
"processing_time": processing_time,
|
| 169 |
+
"timestamp": time.time(),
|
| 170 |
+
"error": error
|
| 171 |
+
})
|
| 172 |
+
|
| 173 |
+
def get_task_history(self) -> list:
|
| 174 |
+
"""Get task execution history"""
|
| 175 |
+
return self.task_history
|
| 176 |
+
|
| 177 |
+
def save_task_history(self, filepath: str = "task_history.json"):
|
| 178 |
+
"""Save task history to file"""
|
| 179 |
+
with open(filepath, 'w') as f:
|
| 180 |
+
json.dump(self.task_history, f, indent=2)
|
| 181 |
+
print(f"Task history saved to {filepath}")
|
| 182 |
+
|
| 183 |
+
def get_status(self) -> Dict[str, Any]:
|
| 184 |
+
"""Get orchestrator status"""
|
| 185 |
+
return {
|
| 186 |
+
"models_loaded": {
|
| 187 |
+
"caption_model": self.caption_model is not None,
|
| 188 |
+
"text2img_pipeline": self.text2img_pipeline is not None
|
| 189 |
+
},
|
| 190 |
+
"total_tasks": len(self.task_history),
|
| 191 |
+
"device": self.device
|
| 192 |
+
}
|
| 193 |
+
|
| 194 |
+
# Async version for better performance
|
| 195 |
+
class AsyncMultiModelOrchestrator(SimpleMultiModelOrchestrator):
|
| 196 |
+
"""Async version of the orchestrator"""
|
| 197 |
+
|
| 198 |
+
async def generate_caption_async(self, image_path: str) -> str:
|
| 199 |
+
"""Async image captioning"""
|
| 200 |
+
loop = asyncio.get_event_loop()
|
| 201 |
+
return await loop.run_in_executor(None, self.generate_caption, image_path)
|
| 202 |
+
|
| 203 |
+
async def generate_image_async(self, text_prompt: str, output_path: Optional[str] = None) -> str:
|
| 204 |
+
"""Async text-to-image generation"""
|
| 205 |
+
loop = asyncio.get_event_loop()
|
| 206 |
+
return await loop.run_in_executor(None, self.generate_image, text_prompt, output_path)
|
| 207 |
+
|
| 208 |
+
async def process_multimodal_async(self, image_path: str, text_prompt: str) -> Dict[str, str]:
|
| 209 |
+
"""Async multimodal processing"""
|
| 210 |
+
# Run both tasks concurrently
|
| 211 |
+
caption_task = self.generate_caption_async(image_path)
|
| 212 |
+
image_task = self.generate_image_async(text_prompt)
|
| 213 |
+
|
| 214 |
+
results = {}
|
| 215 |
+
|
| 216 |
+
try:
|
| 217 |
+
# Wait for both tasks to complete
|
| 218 |
+
caption, generated_image_path = await asyncio.gather(
|
| 219 |
+
caption_task, image_task, return_exceptions=True
|
| 220 |
+
)
|
| 221 |
+
|
| 222 |
+
# Handle results
|
| 223 |
+
if isinstance(caption, Exception):
|
| 224 |
+
results["caption"] = f"Error: {str(caption)}"
|
| 225 |
+
else:
|
| 226 |
+
results["caption"] = caption
|
| 227 |
+
|
| 228 |
+
if isinstance(generated_image_path, Exception):
|
| 229 |
+
results["generated_image"] = f"Error: {str(generated_image_path)}"
|
| 230 |
+
else:
|
| 231 |
+
results["generated_image"] = generated_image_path
|
| 232 |
+
|
| 233 |
+
# Create analysis prompt
|
| 234 |
+
if results["caption"] and not results["caption"].startswith("Error"):
|
| 235 |
+
analysis_prompt = f"Analyze this image caption: {results['caption']}"
|
| 236 |
+
results["analysis_prompt"] = analysis_prompt
|
| 237 |
+
|
| 238 |
+
except Exception as e:
|
| 239 |
+
results["error"] = f"Multimodal processing failed: {str(e)}"
|
| 240 |
+
|
| 241 |
+
return results
|
| 242 |
+
|
| 243 |
+
# Usage examples
|
| 244 |
+
def main():
|
| 245 |
+
"""Example usage of the multi-model orchestrator"""
|
| 246 |
+
|
| 247 |
+
# Initialize orchestrator
|
| 248 |
+
orchestrator = SimpleMultiModelOrchestrator()
|
| 249 |
+
|
| 250 |
+
# Initialize models
|
| 251 |
+
if not orchestrator.initialize_models():
|
| 252 |
+
print("Failed to initialize models. Exiting.")
|
| 253 |
+
return
|
| 254 |
+
|
| 255 |
+
print("\nMulti-Model Orchestrator Status:")
|
| 256 |
+
print(json.dumps(orchestrator.get_status(), indent=2))
|
| 257 |
+
|
| 258 |
+
# Example 1: Image captioning
|
| 259 |
+
try:
|
| 260 |
+
# Note: Replace with actual image path
|
| 261 |
+
caption = orchestrator.route_task("caption", "sample_image.jpg")
|
| 262 |
+
print(f"\nGenerated Caption: {caption}")
|
| 263 |
+
except Exception as e:
|
| 264 |
+
print(f"Caption generation error: {e}")
|
| 265 |
+
|
| 266 |
+
# Example 2: Text-to-image generation
|
| 267 |
+
try:
|
| 268 |
+
image_path = orchestrator.route_task("generate_image", "A beautiful sunset over mountains")
|
| 269 |
+
print(f"\nGenerated Image saved at: {image_path}")
|
| 270 |
+
except Exception as e:
|
| 271 |
+
print(f"Image generation error: {e}")
|
| 272 |
+
|
| 273 |
+
# Example 3: Multimodal processing
|
| 274 |
+
try:
|
| 275 |
+
multimodal_result = orchestrator.process_multimodal_task(
|
| 276 |
+
"sample_image.jpg",
|
| 277 |
+
"A serene landscape with mountains"
|
| 278 |
+
)
|
| 279 |
+
print(f"\nMultimodal Results:")
|
| 280 |
+
for key, value in multimodal_result.items():
|
| 281 |
+
print(f" {key}: {value}")
|
| 282 |
+
except Exception as e:
|
| 283 |
+
print(f"Multimodal processing error: {e}")
|
| 284 |
+
|
| 285 |
+
# Save task history
|
| 286 |
+
orchestrator.save_task_history()
|
| 287 |
+
|
| 288 |
+
async def async_main():
|
| 289 |
+
"""Async example usage"""
|
| 290 |
+
|
| 291 |
+
# Initialize async orchestrator
|
| 292 |
+
orchestrator = AsyncMultiModelOrchestrator()
|
| 293 |
+
|
| 294 |
+
# Initialize models
|
| 295 |
+
if not orchestrator.initialize_models():
|
| 296 |
+
print("Failed to initialize models. Exiting.")
|
| 297 |
+
return
|
| 298 |
+
|
| 299 |
+
print("\nAsync Multi-Model Orchestrator Status:")
|
| 300 |
+
print(json.dumps(orchestrator.get_status(), indent=2))
|
| 301 |
+
|
| 302 |
+
# Example: Concurrent multimodal processing
|
| 303 |
+
try:
|
| 304 |
+
multimodal_result = await orchestrator.process_multimodal_async(
|
| 305 |
+
"sample_image.jpg",
|
| 306 |
+
"A beautiful sunset over mountains"
|
| 307 |
+
)
|
| 308 |
+
print(f"\nAsync Multimodal Results:")
|
| 309 |
+
for key, value in multimodal_result.items():
|
| 310 |
+
print(f" {key}: {value}")
|
| 311 |
+
except Exception as e:
|
| 312 |
+
print(f"Async multimodal processing error: {e}")
|
| 313 |
+
|
| 314 |
+
# Save task history
|
| 315 |
+
orchestrator.save_task_history("async_task_history.json")
|
| 316 |
+
|
| 317 |
+
if __name__ == "__main__":
|
| 318 |
+
print("Running synchronous example...")
|
| 319 |
+
main()
|
| 320 |
+
|
| 321 |
+
print("\n" + "="*50)
|
| 322 |
+
print("Running async example...")
|
| 323 |
+
asyncio.run(async_main())
|
dist/multi_model_orchestrator-1.0.0-py3-none-any.whl
ADDED
|
Binary file (16.1 kB). View file
|
|
|
dist/multi_model_orchestrator-1.0.0.tar.gz
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:49e6ac00733a0b80bddbc4b49c8785b73b7d9741094e5ec11e56bb8ffd014015
|
| 3 |
+
size 20248
|
main.py
ADDED
|
@@ -0,0 +1,56 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/usr/bin/env python3
|
| 2 |
+
"""
|
| 3 |
+
Main entry point for Multi-Model Orchestrator
|
| 4 |
+
"""
|
| 5 |
+
|
| 6 |
+
import sys
|
| 7 |
+
import argparse
|
| 8 |
+
from multi_model_orchestrator import DemoMultiModelOrchestrator, SimpleMultiModelOrchestrator
|
| 9 |
+
|
| 10 |
+
def main():
|
| 11 |
+
parser = argparse.ArgumentParser(description="Multi-Model Orchestrator")
|
| 12 |
+
parser.add_argument("--demo", action="store_true", help="Run demo mode")
|
| 13 |
+
parser.add_argument("--real", action="store_true", help="Run with real models")
|
| 14 |
+
parser.add_argument("--caption", type=str, help="Generate caption for image")
|
| 15 |
+
parser.add_argument("--generate-image", type=str, help="Generate image from text")
|
| 16 |
+
parser.add_argument("--multimodal", nargs=2, metavar=("IMAGE", "TEXT"),
|
| 17 |
+
help="Process multimodal task (image_path text_prompt)")
|
| 18 |
+
|
| 19 |
+
args = parser.parse_args()
|
| 20 |
+
|
| 21 |
+
if args.demo:
|
| 22 |
+
# Run demo
|
| 23 |
+
from multi_model_orchestrator.demo_orchestrator import main as demo_main
|
| 24 |
+
demo_main()
|
| 25 |
+
elif args.real:
|
| 26 |
+
# Run with real models
|
| 27 |
+
print("Real model mode - requires model downloads")
|
| 28 |
+
print("Use: python -m multi_model_orchestrator.multi_model_example")
|
| 29 |
+
elif args.caption:
|
| 30 |
+
# Generate caption
|
| 31 |
+
orchestrator = DemoMultiModelOrchestrator()
|
| 32 |
+
orchestrator.initialize_models()
|
| 33 |
+
caption = orchestrator.generate_caption(args.caption)
|
| 34 |
+
print(f"Caption: {caption}")
|
| 35 |
+
elif args.generate_image:
|
| 36 |
+
# Generate image
|
| 37 |
+
orchestrator = DemoMultiModelOrchestrator()
|
| 38 |
+
orchestrator.initialize_models()
|
| 39 |
+
image_path = orchestrator.generate_image(args.generate_image)
|
| 40 |
+
print(f"Generated image: {image_path}")
|
| 41 |
+
elif args.multimodal:
|
| 42 |
+
# Multimodal processing
|
| 43 |
+
image_path, text_prompt = args.multimodal
|
| 44 |
+
orchestrator = DemoMultiModelOrchestrator()
|
| 45 |
+
orchestrator.initialize_models()
|
| 46 |
+
results = orchestrator.process_multimodal_task(image_path, text_prompt)
|
| 47 |
+
print("Results:")
|
| 48 |
+
for key, value in results.items():
|
| 49 |
+
print(f" {key}: {value}")
|
| 50 |
+
else:
|
| 51 |
+
# Default: run demo
|
| 52 |
+
from multi_model_orchestrator.demo_orchestrator import main as demo_main
|
| 53 |
+
demo_main()
|
| 54 |
+
|
| 55 |
+
if __name__ == "__main__":
|
| 56 |
+
main()
|
multi_model_env/.gitignore
ADDED
|
@@ -0,0 +1,2 @@
|
|
|
|
|
|
|
|
|
|
| 1 |
+
# Created by venv; see https://docs.python.org/3/library/venv.html
|
| 2 |
+
*
|
multi_model_env/bin/Activate.ps1
ADDED
|
@@ -0,0 +1,248 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
<#
|
| 2 |
+
.Synopsis
|
| 3 |
+
Activate a Python virtual environment for the current PowerShell session.
|
| 4 |
+
|
| 5 |
+
.Description
|
| 6 |
+
Pushes the python executable for a virtual environment to the front of the
|
| 7 |
+
$Env:PATH environment variable and sets the prompt to signify that you are
|
| 8 |
+
in a Python virtual environment. Makes use of the command line switches as
|
| 9 |
+
well as the `pyvenv.cfg` file values present in the virtual environment.
|
| 10 |
+
|
| 11 |
+
.Parameter VenvDir
|
| 12 |
+
Path to the directory that contains the virtual environment to activate. The
|
| 13 |
+
default value for this is the parent of the directory that the Activate.ps1
|
| 14 |
+
script is located within.
|
| 15 |
+
|
| 16 |
+
.Parameter Prompt
|
| 17 |
+
The prompt prefix to display when this virtual environment is activated. By
|
| 18 |
+
default, this prompt is the name of the virtual environment folder (VenvDir)
|
| 19 |
+
surrounded by parentheses and followed by a single space (ie. '(.venv) ').
|
| 20 |
+
|
| 21 |
+
.Example
|
| 22 |
+
Activate.ps1
|
| 23 |
+
Activates the Python virtual environment that contains the Activate.ps1 script.
|
| 24 |
+
|
| 25 |
+
.Example
|
| 26 |
+
Activate.ps1 -Verbose
|
| 27 |
+
Activates the Python virtual environment that contains the Activate.ps1 script,
|
| 28 |
+
and shows extra information about the activation as it executes.
|
| 29 |
+
|
| 30 |
+
.Example
|
| 31 |
+
Activate.ps1 -VenvDir C:\Users\MyUser\Common\.venv
|
| 32 |
+
Activates the Python virtual environment located in the specified location.
|
| 33 |
+
|
| 34 |
+
.Example
|
| 35 |
+
Activate.ps1 -Prompt "MyPython"
|
| 36 |
+
Activates the Python virtual environment that contains the Activate.ps1 script,
|
| 37 |
+
and prefixes the current prompt with the specified string (surrounded in
|
| 38 |
+
parentheses) while the virtual environment is active.
|
| 39 |
+
|
| 40 |
+
.Notes
|
| 41 |
+
On Windows, it may be required to enable this Activate.ps1 script by setting the
|
| 42 |
+
execution policy for the user. You can do this by issuing the following PowerShell
|
| 43 |
+
command:
|
| 44 |
+
|
| 45 |
+
PS C:\> Set-ExecutionPolicy -ExecutionPolicy RemoteSigned -Scope CurrentUser
|
| 46 |
+
|
| 47 |
+
For more information on Execution Policies:
|
| 48 |
+
https://go.microsoft.com/fwlink/?LinkID=135170
|
| 49 |
+
|
| 50 |
+
#>
|
| 51 |
+
Param(
|
| 52 |
+
[Parameter(Mandatory = $false)]
|
| 53 |
+
[String]
|
| 54 |
+
$VenvDir,
|
| 55 |
+
[Parameter(Mandatory = $false)]
|
| 56 |
+
[String]
|
| 57 |
+
$Prompt
|
| 58 |
+
)
|
| 59 |
+
|
| 60 |
+
<# Function declarations --------------------------------------------------- #>
|
| 61 |
+
|
| 62 |
+
<#
|
| 63 |
+
.Synopsis
|
| 64 |
+
Remove all shell session elements added by the Activate script, including the
|
| 65 |
+
addition of the virtual environment's Python executable from the beginning of
|
| 66 |
+
the PATH variable.
|
| 67 |
+
|
| 68 |
+
.Parameter NonDestructive
|
| 69 |
+
If present, do not remove this function from the global namespace for the
|
| 70 |
+
session.
|
| 71 |
+
|
| 72 |
+
#>
|
| 73 |
+
function global:deactivate ([switch]$NonDestructive) {
|
| 74 |
+
# Revert to original values
|
| 75 |
+
|
| 76 |
+
# The prior prompt:
|
| 77 |
+
if (Test-Path -Path Function:_OLD_VIRTUAL_PROMPT) {
|
| 78 |
+
Copy-Item -Path Function:_OLD_VIRTUAL_PROMPT -Destination Function:prompt
|
| 79 |
+
Remove-Item -Path Function:_OLD_VIRTUAL_PROMPT
|
| 80 |
+
}
|
| 81 |
+
|
| 82 |
+
# The prior PYTHONHOME:
|
| 83 |
+
if (Test-Path -Path Env:_OLD_VIRTUAL_PYTHONHOME) {
|
| 84 |
+
Copy-Item -Path Env:_OLD_VIRTUAL_PYTHONHOME -Destination Env:PYTHONHOME
|
| 85 |
+
Remove-Item -Path Env:_OLD_VIRTUAL_PYTHONHOME
|
| 86 |
+
}
|
| 87 |
+
|
| 88 |
+
# The prior PATH:
|
| 89 |
+
if (Test-Path -Path Env:_OLD_VIRTUAL_PATH) {
|
| 90 |
+
Copy-Item -Path Env:_OLD_VIRTUAL_PATH -Destination Env:PATH
|
| 91 |
+
Remove-Item -Path Env:_OLD_VIRTUAL_PATH
|
| 92 |
+
}
|
| 93 |
+
|
| 94 |
+
# Just remove the VIRTUAL_ENV altogether:
|
| 95 |
+
if (Test-Path -Path Env:VIRTUAL_ENV) {
|
| 96 |
+
Remove-Item -Path env:VIRTUAL_ENV
|
| 97 |
+
}
|
| 98 |
+
|
| 99 |
+
# Just remove VIRTUAL_ENV_PROMPT altogether.
|
| 100 |
+
if (Test-Path -Path Env:VIRTUAL_ENV_PROMPT) {
|
| 101 |
+
Remove-Item -Path env:VIRTUAL_ENV_PROMPT
|
| 102 |
+
}
|
| 103 |
+
|
| 104 |
+
# Just remove the _PYTHON_VENV_PROMPT_PREFIX altogether:
|
| 105 |
+
if (Get-Variable -Name "_PYTHON_VENV_PROMPT_PREFIX" -ErrorAction SilentlyContinue) {
|
| 106 |
+
Remove-Variable -Name _PYTHON_VENV_PROMPT_PREFIX -Scope Global -Force
|
| 107 |
+
}
|
| 108 |
+
|
| 109 |
+
# Leave deactivate function in the global namespace if requested:
|
| 110 |
+
if (-not $NonDestructive) {
|
| 111 |
+
Remove-Item -Path function:deactivate
|
| 112 |
+
}
|
| 113 |
+
}
|
| 114 |
+
|
| 115 |
+
<#
|
| 116 |
+
.Description
|
| 117 |
+
Get-PyVenvConfig parses the values from the pyvenv.cfg file located in the
|
| 118 |
+
given folder, and returns them in a map.
|
| 119 |
+
|
| 120 |
+
For each line in the pyvenv.cfg file, if that line can be parsed into exactly
|
| 121 |
+
two strings separated by `=` (with any amount of whitespace surrounding the =)
|
| 122 |
+
then it is considered a `key = value` line. The left hand string is the key,
|
| 123 |
+
the right hand is the value.
|
| 124 |
+
|
| 125 |
+
If the value starts with a `'` or a `"` then the first and last character is
|
| 126 |
+
stripped from the value before being captured.
|
| 127 |
+
|
| 128 |
+
.Parameter ConfigDir
|
| 129 |
+
Path to the directory that contains the `pyvenv.cfg` file.
|
| 130 |
+
#>
|
| 131 |
+
function Get-PyVenvConfig(
|
| 132 |
+
[String]
|
| 133 |
+
$ConfigDir
|
| 134 |
+
) {
|
| 135 |
+
Write-Verbose "Given ConfigDir=$ConfigDir, obtain values in pyvenv.cfg"
|
| 136 |
+
|
| 137 |
+
# Ensure the file exists, and issue a warning if it doesn't (but still allow the function to continue).
|
| 138 |
+
$pyvenvConfigPath = Join-Path -Resolve -Path $ConfigDir -ChildPath 'pyvenv.cfg' -ErrorAction Continue
|
| 139 |
+
|
| 140 |
+
# An empty map will be returned if no config file is found.
|
| 141 |
+
$pyvenvConfig = @{ }
|
| 142 |
+
|
| 143 |
+
if ($pyvenvConfigPath) {
|
| 144 |
+
|
| 145 |
+
Write-Verbose "File exists, parse `key = value` lines"
|
| 146 |
+
$pyvenvConfigContent = Get-Content -Path $pyvenvConfigPath
|
| 147 |
+
|
| 148 |
+
$pyvenvConfigContent | ForEach-Object {
|
| 149 |
+
$keyval = $PSItem -split "\s*=\s*", 2
|
| 150 |
+
if ($keyval[0] -and $keyval[1]) {
|
| 151 |
+
$val = $keyval[1]
|
| 152 |
+
|
| 153 |
+
# Remove extraneous quotations around a string value.
|
| 154 |
+
if ("'""".Contains($val.Substring(0, 1))) {
|
| 155 |
+
$val = $val.Substring(1, $val.Length - 2)
|
| 156 |
+
}
|
| 157 |
+
|
| 158 |
+
$pyvenvConfig[$keyval[0]] = $val
|
| 159 |
+
Write-Verbose "Adding Key: '$($keyval[0])'='$val'"
|
| 160 |
+
}
|
| 161 |
+
}
|
| 162 |
+
}
|
| 163 |
+
return $pyvenvConfig
|
| 164 |
+
}
|
| 165 |
+
|
| 166 |
+
|
| 167 |
+
<# Begin Activate script --------------------------------------------------- #>
|
| 168 |
+
|
| 169 |
+
# Determine the containing directory of this script
|
| 170 |
+
$VenvExecPath = Split-Path -Parent $MyInvocation.MyCommand.Definition
|
| 171 |
+
$VenvExecDir = Get-Item -Path $VenvExecPath
|
| 172 |
+
|
| 173 |
+
Write-Verbose "Activation script is located in path: '$VenvExecPath'"
|
| 174 |
+
Write-Verbose "VenvExecDir Fullname: '$($VenvExecDir.FullName)"
|
| 175 |
+
Write-Verbose "VenvExecDir Name: '$($VenvExecDir.Name)"
|
| 176 |
+
|
| 177 |
+
# Set values required in priority: CmdLine, ConfigFile, Default
|
| 178 |
+
# First, get the location of the virtual environment, it might not be
|
| 179 |
+
# VenvExecDir if specified on the command line.
|
| 180 |
+
if ($VenvDir) {
|
| 181 |
+
Write-Verbose "VenvDir given as parameter, using '$VenvDir' to determine values"
|
| 182 |
+
}
|
| 183 |
+
else {
|
| 184 |
+
Write-Verbose "VenvDir not given as a parameter, using parent directory name as VenvDir."
|
| 185 |
+
$VenvDir = $VenvExecDir.Parent.FullName.TrimEnd("\\/")
|
| 186 |
+
Write-Verbose "VenvDir=$VenvDir"
|
| 187 |
+
}
|
| 188 |
+
|
| 189 |
+
# Next, read the `pyvenv.cfg` file to determine any required value such
|
| 190 |
+
# as `prompt`.
|
| 191 |
+
$pyvenvCfg = Get-PyVenvConfig -ConfigDir $VenvDir
|
| 192 |
+
|
| 193 |
+
# Next, set the prompt from the command line, or the config file, or
|
| 194 |
+
# just use the name of the virtual environment folder.
|
| 195 |
+
if ($Prompt) {
|
| 196 |
+
Write-Verbose "Prompt specified as argument, using '$Prompt'"
|
| 197 |
+
}
|
| 198 |
+
else {
|
| 199 |
+
Write-Verbose "Prompt not specified as argument to script, checking pyvenv.cfg value"
|
| 200 |
+
if ($pyvenvCfg -and $pyvenvCfg['prompt']) {
|
| 201 |
+
Write-Verbose " Setting based on value in pyvenv.cfg='$($pyvenvCfg['prompt'])'"
|
| 202 |
+
$Prompt = $pyvenvCfg['prompt'];
|
| 203 |
+
}
|
| 204 |
+
else {
|
| 205 |
+
Write-Verbose " Setting prompt based on parent's directory's name. (Is the directory name passed to venv module when creating the virtual environment)"
|
| 206 |
+
Write-Verbose " Got leaf-name of $VenvDir='$(Split-Path -Path $venvDir -Leaf)'"
|
| 207 |
+
$Prompt = Split-Path -Path $venvDir -Leaf
|
| 208 |
+
}
|
| 209 |
+
}
|
| 210 |
+
|
| 211 |
+
Write-Verbose "Prompt = '$Prompt'"
|
| 212 |
+
Write-Verbose "VenvDir='$VenvDir'"
|
| 213 |
+
|
| 214 |
+
# Deactivate any currently active virtual environment, but leave the
|
| 215 |
+
# deactivate function in place.
|
| 216 |
+
deactivate -nondestructive
|
| 217 |
+
|
| 218 |
+
# Now set the environment variable VIRTUAL_ENV, used by many tools to determine
|
| 219 |
+
# that there is an activated venv.
|
| 220 |
+
$env:VIRTUAL_ENV = $VenvDir
|
| 221 |
+
|
| 222 |
+
$env:VIRTUAL_ENV_PROMPT = $Prompt
|
| 223 |
+
|
| 224 |
+
if (-not $Env:VIRTUAL_ENV_DISABLE_PROMPT) {
|
| 225 |
+
|
| 226 |
+
Write-Verbose "Setting prompt to '$Prompt'"
|
| 227 |
+
|
| 228 |
+
# Set the prompt to include the env name
|
| 229 |
+
# Make sure _OLD_VIRTUAL_PROMPT is global
|
| 230 |
+
function global:_OLD_VIRTUAL_PROMPT { "" }
|
| 231 |
+
Copy-Item -Path function:prompt -Destination function:_OLD_VIRTUAL_PROMPT
|
| 232 |
+
New-Variable -Name _PYTHON_VENV_PROMPT_PREFIX -Description "Python virtual environment prompt prefix" -Scope Global -Option ReadOnly -Visibility Public -Value $Prompt
|
| 233 |
+
|
| 234 |
+
function global:prompt {
|
| 235 |
+
Write-Host -NoNewline -ForegroundColor Green "($_PYTHON_VENV_PROMPT_PREFIX) "
|
| 236 |
+
_OLD_VIRTUAL_PROMPT
|
| 237 |
+
}
|
| 238 |
+
}
|
| 239 |
+
|
| 240 |
+
# Clear PYTHONHOME
|
| 241 |
+
if (Test-Path -Path Env:PYTHONHOME) {
|
| 242 |
+
Copy-Item -Path Env:PYTHONHOME -Destination Env:_OLD_VIRTUAL_PYTHONHOME
|
| 243 |
+
Remove-Item -Path Env:PYTHONHOME
|
| 244 |
+
}
|
| 245 |
+
|
| 246 |
+
# Add the venv to the PATH
|
| 247 |
+
Copy-Item -Path Env:PATH -Destination Env:_OLD_VIRTUAL_PATH
|
| 248 |
+
$Env:PATH = "$VenvExecDir$([System.IO.Path]::PathSeparator)$Env:PATH"
|
multi_model_env/bin/activate
ADDED
|
@@ -0,0 +1,76 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
# This file must be used with "source bin/activate" *from bash*
|
| 2 |
+
# You cannot run it directly
|
| 3 |
+
|
| 4 |
+
deactivate () {
|
| 5 |
+
# reset old environment variables
|
| 6 |
+
if [ -n "${_OLD_VIRTUAL_PATH:-}" ] ; then
|
| 7 |
+
PATH="${_OLD_VIRTUAL_PATH:-}"
|
| 8 |
+
export PATH
|
| 9 |
+
unset _OLD_VIRTUAL_PATH
|
| 10 |
+
fi
|
| 11 |
+
if [ -n "${_OLD_VIRTUAL_PYTHONHOME:-}" ] ; then
|
| 12 |
+
PYTHONHOME="${_OLD_VIRTUAL_PYTHONHOME:-}"
|
| 13 |
+
export PYTHONHOME
|
| 14 |
+
unset _OLD_VIRTUAL_PYTHONHOME
|
| 15 |
+
fi
|
| 16 |
+
|
| 17 |
+
# Call hash to forget past locations. Without forgetting
|
| 18 |
+
# past locations the $PATH changes we made may not be respected.
|
| 19 |
+
# See "man bash" for more details. hash is usually a builtin of your shell
|
| 20 |
+
hash -r 2> /dev/null
|
| 21 |
+
|
| 22 |
+
if [ -n "${_OLD_VIRTUAL_PS1:-}" ] ; then
|
| 23 |
+
PS1="${_OLD_VIRTUAL_PS1:-}"
|
| 24 |
+
export PS1
|
| 25 |
+
unset _OLD_VIRTUAL_PS1
|
| 26 |
+
fi
|
| 27 |
+
|
| 28 |
+
unset VIRTUAL_ENV
|
| 29 |
+
unset VIRTUAL_ENV_PROMPT
|
| 30 |
+
if [ ! "${1:-}" = "nondestructive" ] ; then
|
| 31 |
+
# Self destruct!
|
| 32 |
+
unset -f deactivate
|
| 33 |
+
fi
|
| 34 |
+
}
|
| 35 |
+
|
| 36 |
+
# unset irrelevant variables
|
| 37 |
+
deactivate nondestructive
|
| 38 |
+
|
| 39 |
+
# on Windows, a path can contain colons and backslashes and has to be converted:
|
| 40 |
+
case "$(uname)" in
|
| 41 |
+
CYGWIN*|MSYS*|MINGW*)
|
| 42 |
+
# transform D:\path\to\venv to /d/path/to/venv on MSYS and MINGW
|
| 43 |
+
# and to /cygdrive/d/path/to/venv on Cygwin
|
| 44 |
+
VIRTUAL_ENV=$(cygpath /Users/kunaldhanda/DeepSeek/multi_model_env)
|
| 45 |
+
export VIRTUAL_ENV
|
| 46 |
+
;;
|
| 47 |
+
*)
|
| 48 |
+
# use the path as-is
|
| 49 |
+
export VIRTUAL_ENV=/Users/kunaldhanda/DeepSeek/multi_model_env
|
| 50 |
+
;;
|
| 51 |
+
esac
|
| 52 |
+
|
| 53 |
+
_OLD_VIRTUAL_PATH="$PATH"
|
| 54 |
+
PATH="$VIRTUAL_ENV/"bin":$PATH"
|
| 55 |
+
export PATH
|
| 56 |
+
|
| 57 |
+
VIRTUAL_ENV_PROMPT=multi_model_env
|
| 58 |
+
export VIRTUAL_ENV_PROMPT
|
| 59 |
+
|
| 60 |
+
# unset PYTHONHOME if set
|
| 61 |
+
# this will fail if PYTHONHOME is set to the empty string (which is bad anyway)
|
| 62 |
+
# could use `if (set -u; : $PYTHONHOME) ;` in bash
|
| 63 |
+
if [ -n "${PYTHONHOME:-}" ] ; then
|
| 64 |
+
_OLD_VIRTUAL_PYTHONHOME="${PYTHONHOME:-}"
|
| 65 |
+
unset PYTHONHOME
|
| 66 |
+
fi
|
| 67 |
+
|
| 68 |
+
if [ -z "${VIRTUAL_ENV_DISABLE_PROMPT:-}" ] ; then
|
| 69 |
+
_OLD_VIRTUAL_PS1="${PS1:-}"
|
| 70 |
+
PS1="("multi_model_env") ${PS1:-}"
|
| 71 |
+
export PS1
|
| 72 |
+
fi
|
| 73 |
+
|
| 74 |
+
# Call hash to forget past commands. Without forgetting
|
| 75 |
+
# past commands the $PATH changes we made may not be respected
|
| 76 |
+
hash -r 2> /dev/null
|
multi_model_env/bin/activate.csh
ADDED
|
@@ -0,0 +1,27 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
# This file must be used with "source bin/activate.csh" *from csh*.
|
| 2 |
+
# You cannot run it directly.
|
| 3 |
+
|
| 4 |
+
# Created by Davide Di Blasi <davidedb@gmail.com>.
|
| 5 |
+
# Ported to Python 3.3 venv by Andrew Svetlov <andrew.svetlov@gmail.com>
|
| 6 |
+
|
| 7 |
+
alias deactivate 'test $?_OLD_VIRTUAL_PATH != 0 && setenv PATH "$_OLD_VIRTUAL_PATH" && unset _OLD_VIRTUAL_PATH; rehash; test $?_OLD_VIRTUAL_PROMPT != 0 && set prompt="$_OLD_VIRTUAL_PROMPT" && unset _OLD_VIRTUAL_PROMPT; unsetenv VIRTUAL_ENV; unsetenv VIRTUAL_ENV_PROMPT; test "\!:*" != "nondestructive" && unalias deactivate'
|
| 8 |
+
|
| 9 |
+
# Unset irrelevant variables.
|
| 10 |
+
deactivate nondestructive
|
| 11 |
+
|
| 12 |
+
setenv VIRTUAL_ENV /Users/kunaldhanda/DeepSeek/multi_model_env
|
| 13 |
+
|
| 14 |
+
set _OLD_VIRTUAL_PATH="$PATH"
|
| 15 |
+
setenv PATH "$VIRTUAL_ENV/"bin":$PATH"
|
| 16 |
+
setenv VIRTUAL_ENV_PROMPT multi_model_env
|
| 17 |
+
|
| 18 |
+
|
| 19 |
+
set _OLD_VIRTUAL_PROMPT="$prompt"
|
| 20 |
+
|
| 21 |
+
if (! "$?VIRTUAL_ENV_DISABLE_PROMPT") then
|
| 22 |
+
set prompt = "("multi_model_env") $prompt:q"
|
| 23 |
+
endif
|
| 24 |
+
|
| 25 |
+
alias pydoc python -m pydoc
|
| 26 |
+
|
| 27 |
+
rehash
|
multi_model_env/bin/activate.fish
ADDED
|
@@ -0,0 +1,69 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
# This file must be used with "source <venv>/bin/activate.fish" *from fish*
|
| 2 |
+
# (https://fishshell.com/). You cannot run it directly.
|
| 3 |
+
|
| 4 |
+
function deactivate -d "Exit virtual environment and return to normal shell environment"
|
| 5 |
+
# reset old environment variables
|
| 6 |
+
if test -n "$_OLD_VIRTUAL_PATH"
|
| 7 |
+
set -gx PATH $_OLD_VIRTUAL_PATH
|
| 8 |
+
set -e _OLD_VIRTUAL_PATH
|
| 9 |
+
end
|
| 10 |
+
if test -n "$_OLD_VIRTUAL_PYTHONHOME"
|
| 11 |
+
set -gx PYTHONHOME $_OLD_VIRTUAL_PYTHONHOME
|
| 12 |
+
set -e _OLD_VIRTUAL_PYTHONHOME
|
| 13 |
+
end
|
| 14 |
+
|
| 15 |
+
if test -n "$_OLD_FISH_PROMPT_OVERRIDE"
|
| 16 |
+
set -e _OLD_FISH_PROMPT_OVERRIDE
|
| 17 |
+
# prevents error when using nested fish instances (Issue #93858)
|
| 18 |
+
if functions -q _old_fish_prompt
|
| 19 |
+
functions -e fish_prompt
|
| 20 |
+
functions -c _old_fish_prompt fish_prompt
|
| 21 |
+
functions -e _old_fish_prompt
|
| 22 |
+
end
|
| 23 |
+
end
|
| 24 |
+
|
| 25 |
+
set -e VIRTUAL_ENV
|
| 26 |
+
set -e VIRTUAL_ENV_PROMPT
|
| 27 |
+
if test "$argv[1]" != "nondestructive"
|
| 28 |
+
# Self-destruct!
|
| 29 |
+
functions -e deactivate
|
| 30 |
+
end
|
| 31 |
+
end
|
| 32 |
+
|
| 33 |
+
# Unset irrelevant variables.
|
| 34 |
+
deactivate nondestructive
|
| 35 |
+
|
| 36 |
+
set -gx VIRTUAL_ENV /Users/kunaldhanda/DeepSeek/multi_model_env
|
| 37 |
+
|
| 38 |
+
set -gx _OLD_VIRTUAL_PATH $PATH
|
| 39 |
+
set -gx PATH "$VIRTUAL_ENV/"bin $PATH
|
| 40 |
+
set -gx VIRTUAL_ENV_PROMPT multi_model_env
|
| 41 |
+
|
| 42 |
+
# Unset PYTHONHOME if set.
|
| 43 |
+
if set -q PYTHONHOME
|
| 44 |
+
set -gx _OLD_VIRTUAL_PYTHONHOME $PYTHONHOME
|
| 45 |
+
set -e PYTHONHOME
|
| 46 |
+
end
|
| 47 |
+
|
| 48 |
+
if test -z "$VIRTUAL_ENV_DISABLE_PROMPT"
|
| 49 |
+
# fish uses a function instead of an env var to generate the prompt.
|
| 50 |
+
|
| 51 |
+
# Save the current fish_prompt function as the function _old_fish_prompt.
|
| 52 |
+
functions -c fish_prompt _old_fish_prompt
|
| 53 |
+
|
| 54 |
+
# With the original prompt function renamed, we can override with our own.
|
| 55 |
+
function fish_prompt
|
| 56 |
+
# Save the return status of the last command.
|
| 57 |
+
set -l old_status $status
|
| 58 |
+
|
| 59 |
+
# Output the venv prompt; color taken from the blue of the Python logo.
|
| 60 |
+
printf "%s(%s)%s " (set_color 4B8BBE) multi_model_env (set_color normal)
|
| 61 |
+
|
| 62 |
+
# Restore the return status of the previous command.
|
| 63 |
+
echo "exit $old_status" | .
|
| 64 |
+
# Output the original/"old" prompt.
|
| 65 |
+
_old_fish_prompt
|
| 66 |
+
end
|
| 67 |
+
|
| 68 |
+
set -gx _OLD_FISH_PROMPT_OVERRIDE "$VIRTUAL_ENV"
|
| 69 |
+
end
|
multi_model_env/bin/diffusers-cli
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/Users/kunaldhanda/DeepSeek/multi_model_env/bin/python3.13
|
| 2 |
+
# -*- coding: utf-8 -*-
|
| 3 |
+
import re
|
| 4 |
+
import sys
|
| 5 |
+
from diffusers.commands.diffusers_cli import main
|
| 6 |
+
if __name__ == '__main__':
|
| 7 |
+
sys.argv[0] = re.sub(r'(-script\.pyw|\.exe)?$', '', sys.argv[0])
|
| 8 |
+
sys.exit(main())
|
multi_model_env/bin/f2py
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/Users/kunaldhanda/DeepSeek/multi_model_env/bin/python3.13
|
| 2 |
+
# -*- coding: utf-8 -*-
|
| 3 |
+
import re
|
| 4 |
+
import sys
|
| 5 |
+
from numpy.f2py.f2py2e import main
|
| 6 |
+
if __name__ == '__main__':
|
| 7 |
+
sys.argv[0] = re.sub(r'(-script\.pyw|\.exe)?$', '', sys.argv[0])
|
| 8 |
+
sys.exit(main())
|
multi_model_env/bin/hf
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/Users/kunaldhanda/DeepSeek/multi_model_env/bin/python3.13
|
| 2 |
+
# -*- coding: utf-8 -*-
|
| 3 |
+
import re
|
| 4 |
+
import sys
|
| 5 |
+
from huggingface_hub.cli.hf import main
|
| 6 |
+
if __name__ == '__main__':
|
| 7 |
+
sys.argv[0] = re.sub(r'(-script\.pyw|\.exe)?$', '', sys.argv[0])
|
| 8 |
+
sys.exit(main())
|
multi_model_env/bin/huggingface-cli
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/Users/kunaldhanda/DeepSeek/multi_model_env/bin/python3.13
|
| 2 |
+
# -*- coding: utf-8 -*-
|
| 3 |
+
import re
|
| 4 |
+
import sys
|
| 5 |
+
from huggingface_hub.commands.huggingface_cli import main
|
| 6 |
+
if __name__ == '__main__':
|
| 7 |
+
sys.argv[0] = re.sub(r'(-script\.pyw|\.exe)?$', '', sys.argv[0])
|
| 8 |
+
sys.exit(main())
|
multi_model_env/bin/isympy
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/Users/kunaldhanda/DeepSeek/multi_model_env/bin/python3.13
|
| 2 |
+
# -*- coding: utf-8 -*-
|
| 3 |
+
import re
|
| 4 |
+
import sys
|
| 5 |
+
from isympy import main
|
| 6 |
+
if __name__ == '__main__':
|
| 7 |
+
sys.argv[0] = re.sub(r'(-script\.pyw|\.exe)?$', '', sys.argv[0])
|
| 8 |
+
sys.exit(main())
|
multi_model_env/bin/normalizer
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/Users/kunaldhanda/DeepSeek/multi_model_env/bin/python3.13
|
| 2 |
+
# -*- coding: utf-8 -*-
|
| 3 |
+
import re
|
| 4 |
+
import sys
|
| 5 |
+
from charset_normalizer import cli
|
| 6 |
+
if __name__ == '__main__':
|
| 7 |
+
sys.argv[0] = re.sub(r'(-script\.pyw|\.exe)?$', '', sys.argv[0])
|
| 8 |
+
sys.exit(cli.cli_detect())
|
multi_model_env/bin/numpy-config
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/Users/kunaldhanda/DeepSeek/multi_model_env/bin/python3.13
|
| 2 |
+
# -*- coding: utf-8 -*-
|
| 3 |
+
import re
|
| 4 |
+
import sys
|
| 5 |
+
from numpy._configtool import main
|
| 6 |
+
if __name__ == '__main__':
|
| 7 |
+
sys.argv[0] = re.sub(r'(-script\.pyw|\.exe)?$', '', sys.argv[0])
|
| 8 |
+
sys.exit(main())
|
multi_model_env/bin/pip
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/Users/kunaldhanda/DeepSeek/multi_model_env/bin/python3.13
|
| 2 |
+
# -*- coding: utf-8 -*-
|
| 3 |
+
import re
|
| 4 |
+
import sys
|
| 5 |
+
from pip._internal.cli.main import main
|
| 6 |
+
if __name__ == '__main__':
|
| 7 |
+
sys.argv[0] = re.sub(r'(-script\.pyw|\.exe)?$', '', sys.argv[0])
|
| 8 |
+
sys.exit(main())
|
multi_model_env/bin/pip3
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/Users/kunaldhanda/DeepSeek/multi_model_env/bin/python3.13
|
| 2 |
+
# -*- coding: utf-8 -*-
|
| 3 |
+
import re
|
| 4 |
+
import sys
|
| 5 |
+
from pip._internal.cli.main import main
|
| 6 |
+
if __name__ == '__main__':
|
| 7 |
+
sys.argv[0] = re.sub(r'(-script\.pyw|\.exe)?$', '', sys.argv[0])
|
| 8 |
+
sys.exit(main())
|
multi_model_env/bin/pip3.13
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/Users/kunaldhanda/DeepSeek/multi_model_env/bin/python3.13
|
| 2 |
+
# -*- coding: utf-8 -*-
|
| 3 |
+
import re
|
| 4 |
+
import sys
|
| 5 |
+
from pip._internal.cli.main import main
|
| 6 |
+
if __name__ == '__main__':
|
| 7 |
+
sys.argv[0] = re.sub(r'(-script\.pyw|\.exe)?$', '', sys.argv[0])
|
| 8 |
+
sys.exit(main())
|
multi_model_env/bin/python
ADDED
|
Binary file (52.6 kB). View file
|
|
|
multi_model_env/bin/python3
ADDED
|
Binary file (52.6 kB). View file
|
|
|
multi_model_env/bin/python3.13
ADDED
|
Binary file (52.6 kB). View file
|
|
|
multi_model_env/bin/tiny-agents
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/Users/kunaldhanda/DeepSeek/multi_model_env/bin/python3.13
|
| 2 |
+
# -*- coding: utf-8 -*-
|
| 3 |
+
import re
|
| 4 |
+
import sys
|
| 5 |
+
from huggingface_hub.inference._mcp.cli import app
|
| 6 |
+
if __name__ == '__main__':
|
| 7 |
+
sys.argv[0] = re.sub(r'(-script\.pyw|\.exe)?$', '', sys.argv[0])
|
| 8 |
+
sys.exit(app())
|
multi_model_env/bin/torchfrtrace
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/Users/kunaldhanda/DeepSeek/multi_model_env/bin/python3.13
|
| 2 |
+
# -*- coding: utf-8 -*-
|
| 3 |
+
import re
|
| 4 |
+
import sys
|
| 5 |
+
from tools.flight_recorder.fr_trace import main
|
| 6 |
+
if __name__ == '__main__':
|
| 7 |
+
sys.argv[0] = re.sub(r'(-script\.pyw|\.exe)?$', '', sys.argv[0])
|
| 8 |
+
sys.exit(main())
|
multi_model_env/bin/torchrun
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/Users/kunaldhanda/DeepSeek/multi_model_env/bin/python3.13
|
| 2 |
+
# -*- coding: utf-8 -*-
|
| 3 |
+
import re
|
| 4 |
+
import sys
|
| 5 |
+
from torch.distributed.run import main
|
| 6 |
+
if __name__ == '__main__':
|
| 7 |
+
sys.argv[0] = re.sub(r'(-script\.pyw|\.exe)?$', '', sys.argv[0])
|
| 8 |
+
sys.exit(main())
|
multi_model_env/bin/tqdm
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/Users/kunaldhanda/DeepSeek/multi_model_env/bin/python3.13
|
| 2 |
+
# -*- coding: utf-8 -*-
|
| 3 |
+
import re
|
| 4 |
+
import sys
|
| 5 |
+
from tqdm.cli import main
|
| 6 |
+
if __name__ == '__main__':
|
| 7 |
+
sys.argv[0] = re.sub(r'(-script\.pyw|\.exe)?$', '', sys.argv[0])
|
| 8 |
+
sys.exit(main())
|
multi_model_env/bin/transformers
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/Users/kunaldhanda/DeepSeek/multi_model_env/bin/python3.13
|
| 2 |
+
# -*- coding: utf-8 -*-
|
| 3 |
+
import re
|
| 4 |
+
import sys
|
| 5 |
+
from transformers.commands.transformers_cli import main
|
| 6 |
+
if __name__ == '__main__':
|
| 7 |
+
sys.argv[0] = re.sub(r'(-script\.pyw|\.exe)?$', '', sys.argv[0])
|
| 8 |
+
sys.exit(main())
|
multi_model_env/bin/transformers-cli
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/Users/kunaldhanda/DeepSeek/multi_model_env/bin/python3.13
|
| 2 |
+
# -*- coding: utf-8 -*-
|
| 3 |
+
import re
|
| 4 |
+
import sys
|
| 5 |
+
from transformers.commands.transformers_cli import main_cli
|
| 6 |
+
if __name__ == '__main__':
|
| 7 |
+
sys.argv[0] = re.sub(r'(-script\.pyw|\.exe)?$', '', sys.argv[0])
|
| 8 |
+
sys.exit(main_cli())
|
multi_model_env/lib/python3.13/site-packages/MarkupSafe-3.0.2.dist-info/INSTALLER
ADDED
|
@@ -0,0 +1 @@
|
|
|
|
|
|
|
| 1 |
+
pip
|
multi_model_env/lib/python3.13/site-packages/MarkupSafe-3.0.2.dist-info/LICENSE.txt
ADDED
|
@@ -0,0 +1,28 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
Copyright 2010 Pallets
|
| 2 |
+
|
| 3 |
+
Redistribution and use in source and binary forms, with or without
|
| 4 |
+
modification, are permitted provided that the following conditions are
|
| 5 |
+
met:
|
| 6 |
+
|
| 7 |
+
1. Redistributions of source code must retain the above copyright
|
| 8 |
+
notice, this list of conditions and the following disclaimer.
|
| 9 |
+
|
| 10 |
+
2. Redistributions in binary form must reproduce the above copyright
|
| 11 |
+
notice, this list of conditions and the following disclaimer in the
|
| 12 |
+
documentation and/or other materials provided with the distribution.
|
| 13 |
+
|
| 14 |
+
3. Neither the name of the copyright holder nor the names of its
|
| 15 |
+
contributors may be used to endorse or promote products derived from
|
| 16 |
+
this software without specific prior written permission.
|
| 17 |
+
|
| 18 |
+
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
| 19 |
+
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
| 20 |
+
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
|
| 21 |
+
PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
| 22 |
+
HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
| 23 |
+
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
|
| 24 |
+
TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
|
| 25 |
+
PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
| 26 |
+
LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
|
| 27 |
+
NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
| 28 |
+
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
multi_model_env/lib/python3.13/site-packages/MarkupSafe-3.0.2.dist-info/METADATA
ADDED
|
@@ -0,0 +1,92 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
Metadata-Version: 2.1
|
| 2 |
+
Name: MarkupSafe
|
| 3 |
+
Version: 3.0.2
|
| 4 |
+
Summary: Safely add untrusted strings to HTML/XML markup.
|
| 5 |
+
Maintainer-email: Pallets <contact@palletsprojects.com>
|
| 6 |
+
License: Copyright 2010 Pallets
|
| 7 |
+
|
| 8 |
+
Redistribution and use in source and binary forms, with or without
|
| 9 |
+
modification, are permitted provided that the following conditions are
|
| 10 |
+
met:
|
| 11 |
+
|
| 12 |
+
1. Redistributions of source code must retain the above copyright
|
| 13 |
+
notice, this list of conditions and the following disclaimer.
|
| 14 |
+
|
| 15 |
+
2. Redistributions in binary form must reproduce the above copyright
|
| 16 |
+
notice, this list of conditions and the following disclaimer in the
|
| 17 |
+
documentation and/or other materials provided with the distribution.
|
| 18 |
+
|
| 19 |
+
3. Neither the name of the copyright holder nor the names of its
|
| 20 |
+
contributors may be used to endorse or promote products derived from
|
| 21 |
+
this software without specific prior written permission.
|
| 22 |
+
|
| 23 |
+
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
| 24 |
+
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
| 25 |
+
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
|
| 26 |
+
PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
| 27 |
+
HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
| 28 |
+
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
|
| 29 |
+
TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
|
| 30 |
+
PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
| 31 |
+
LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
|
| 32 |
+
NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
| 33 |
+
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
| 34 |
+
|
| 35 |
+
Project-URL: Donate, https://palletsprojects.com/donate
|
| 36 |
+
Project-URL: Documentation, https://markupsafe.palletsprojects.com/
|
| 37 |
+
Project-URL: Changes, https://markupsafe.palletsprojects.com/changes/
|
| 38 |
+
Project-URL: Source, https://github.com/pallets/markupsafe/
|
| 39 |
+
Project-URL: Chat, https://discord.gg/pallets
|
| 40 |
+
Classifier: Development Status :: 5 - Production/Stable
|
| 41 |
+
Classifier: Environment :: Web Environment
|
| 42 |
+
Classifier: Intended Audience :: Developers
|
| 43 |
+
Classifier: License :: OSI Approved :: BSD License
|
| 44 |
+
Classifier: Operating System :: OS Independent
|
| 45 |
+
Classifier: Programming Language :: Python
|
| 46 |
+
Classifier: Topic :: Internet :: WWW/HTTP :: Dynamic Content
|
| 47 |
+
Classifier: Topic :: Text Processing :: Markup :: HTML
|
| 48 |
+
Classifier: Typing :: Typed
|
| 49 |
+
Requires-Python: >=3.9
|
| 50 |
+
Description-Content-Type: text/markdown
|
| 51 |
+
License-File: LICENSE.txt
|
| 52 |
+
|
| 53 |
+
# MarkupSafe
|
| 54 |
+
|
| 55 |
+
MarkupSafe implements a text object that escapes characters so it is
|
| 56 |
+
safe to use in HTML and XML. Characters that have special meanings are
|
| 57 |
+
replaced so that they display as the actual characters. This mitigates
|
| 58 |
+
injection attacks, meaning untrusted user input can safely be displayed
|
| 59 |
+
on a page.
|
| 60 |
+
|
| 61 |
+
|
| 62 |
+
## Examples
|
| 63 |
+
|
| 64 |
+
```pycon
|
| 65 |
+
>>> from markupsafe import Markup, escape
|
| 66 |
+
|
| 67 |
+
>>> # escape replaces special characters and wraps in Markup
|
| 68 |
+
>>> escape("<script>alert(document.cookie);</script>")
|
| 69 |
+
Markup('<script>alert(document.cookie);</script>')
|
| 70 |
+
|
| 71 |
+
>>> # wrap in Markup to mark text "safe" and prevent escaping
|
| 72 |
+
>>> Markup("<strong>Hello</strong>")
|
| 73 |
+
Markup('<strong>hello</strong>')
|
| 74 |
+
|
| 75 |
+
>>> escape(Markup("<strong>Hello</strong>"))
|
| 76 |
+
Markup('<strong>hello</strong>')
|
| 77 |
+
|
| 78 |
+
>>> # Markup is a str subclass
|
| 79 |
+
>>> # methods and operators escape their arguments
|
| 80 |
+
>>> template = Markup("Hello <em>{name}</em>")
|
| 81 |
+
>>> template.format(name='"World"')
|
| 82 |
+
Markup('Hello <em>"World"</em>')
|
| 83 |
+
```
|
| 84 |
+
|
| 85 |
+
## Donate
|
| 86 |
+
|
| 87 |
+
The Pallets organization develops and supports MarkupSafe and other
|
| 88 |
+
popular packages. In order to grow the community of contributors and
|
| 89 |
+
users, and allow the maintainers to devote more time to the projects,
|
| 90 |
+
[please donate today][].
|
| 91 |
+
|
| 92 |
+
[please donate today]: https://palletsprojects.com/donate
|
multi_model_env/lib/python3.13/site-packages/MarkupSafe-3.0.2.dist-info/RECORD
ADDED
|
@@ -0,0 +1,14 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
MarkupSafe-3.0.2.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4
|
| 2 |
+
MarkupSafe-3.0.2.dist-info/LICENSE.txt,sha256=SJqOEQhQntmKN7uYPhHg9-HTHwvY-Zp5yESOf_N9B-o,1475
|
| 3 |
+
MarkupSafe-3.0.2.dist-info/METADATA,sha256=aAwbZhSmXdfFuMM-rEHpeiHRkBOGESyVLJIuwzHP-nw,3975
|
| 4 |
+
MarkupSafe-3.0.2.dist-info/RECORD,,
|
| 5 |
+
MarkupSafe-3.0.2.dist-info/WHEEL,sha256=EhaGmhgTZV8uqhZxBmQmxqlBexDOCFpUXsFLjK8lF9g,109
|
| 6 |
+
MarkupSafe-3.0.2.dist-info/top_level.txt,sha256=qy0Plje5IJuvsCBjejJyhDCjEAdcDLK_2agVcex8Z6U,11
|
| 7 |
+
markupsafe/__init__.py,sha256=sr-U6_27DfaSrj5jnHYxWN-pvhM27sjlDplMDPZKm7k,13214
|
| 8 |
+
markupsafe/__pycache__/__init__.cpython-313.pyc,,
|
| 9 |
+
markupsafe/__pycache__/_native.cpython-313.pyc,,
|
| 10 |
+
markupsafe/_native.py,sha256=hSLs8Jmz5aqayuengJJ3kdT5PwNpBWpKrmQSdipndC8,210
|
| 11 |
+
markupsafe/_speedups.c,sha256=O7XulmTo-epI6n2FtMVOrJXl8EAaIwD2iNYmBI5SEoQ,4149
|
| 12 |
+
markupsafe/_speedups.cpython-313-darwin.so,sha256=zqa2NWhnDkGCuJVPBpLRKADVKQXphH3cRvm6rY8Hvds,50624
|
| 13 |
+
markupsafe/_speedups.pyi,sha256=ENd1bYe7gbBUf2ywyYWOGUpnXOHNJ-cgTNqetlW8h5k,41
|
| 14 |
+
markupsafe/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
multi_model_env/lib/python3.13/site-packages/MarkupSafe-3.0.2.dist-info/WHEEL
ADDED
|
@@ -0,0 +1,5 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
Wheel-Version: 1.0
|
| 2 |
+
Generator: setuptools (75.2.0)
|
| 3 |
+
Root-Is-Purelib: false
|
| 4 |
+
Tag: cp313-cp313-macosx_11_0_arm64
|
| 5 |
+
|
multi_model_env/lib/python3.13/site-packages/MarkupSafe-3.0.2.dist-info/top_level.txt
ADDED
|
@@ -0,0 +1 @@
|
|
|
|
|
|
|
| 1 |
+
markupsafe
|
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libXau.6.dylib
ADDED
|
Binary file (70 kB). View file
|
|
|
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libavif.16.3.0.dylib
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:173bc240d1d7ba7cc6fbd4769a942e5743dfe3d5c60f5d1cdf6bfac1c23e3b5b
|
| 3 |
+
size 2999728
|
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libbrotlicommon.1.1.0.dylib
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:9de349e2275ea9702e3f69ee5bae2645e91f69c0474d6674e0b126ebe3a6d305
|
| 3 |
+
size 201200
|
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libbrotlidec.1.1.0.dylib
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:296c21f63059fbe2c426b4abfe7ed9274797a5bff875bd58dd75e362c1121c56
|
| 3 |
+
size 104576
|
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libfreetype.6.dylib
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:25662cfcc8b01db700126023a5e4e032a06d3f08c863899a53eda73d0e37dd65
|
| 3 |
+
size 1208336
|
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libharfbuzz.0.dylib
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:74be7efca5f46967668a99acc7eb2b52f4d7d769b5e96d3a70242ae90bddb50e
|
| 3 |
+
size 1772960
|
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/libjpeg.62.4.0.dylib
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:3738d4c83621823e877e389de5c311e3923cef2ed6faf8af613b9c1ab1908ac9
|
| 3 |
+
size 637088
|
multi_model_env/lib/python3.13/site-packages/PIL/.dylibs/liblcms2.2.dylib
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:b42c5cb99e069f860382cebe75034b23d5e8dfe979c1b3715790872d0395b2f8
|
| 3 |
+
size 557776
|