Spaces:
Running
Running
Commit
·
5cc0273
1
Parent(s):
4f0613d
back to basics with simplest installation possible
Browse files- .editorconfig +10 -0
- Dockerfile +12 -32
- README.md +311 -5
- README2.md +0 -306
- assets/screenshot.jpg +0 -0
- assets/screenshot_collection.png +0 -0
- assets/screenshot_desktop.png +0 -0
- assets/screenshot_desktop_02.png +0 -0
- assets/screenshot_extension.png +0 -0
- assets/screenshot_filemanager.png +0 -0
- assets/screenshot_nodes.png +0 -0
- assets/screenshot_omnillusion.png +0 -0
- assets/screenshot_omniwa.png +0 -0
- assets/screenshot_viewer.png +0 -0
- docker_build.sh +0 -4
- launch.js +0 -53
- omnitool_start.sh +29 -12
- packages/omni-server/scripts/huggingface.js +0 -309
- start.bat +37 -0
- start.sh +35 -1
- yarn.lock +0 -0
.editorconfig
ADDED
@@ -0,0 +1,10 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
root = true
|
2 |
+
|
3 |
+
[*]
|
4 |
+
end_of_line = lf
|
5 |
+
insert_final_newline = true
|
6 |
+
|
7 |
+
[*.{js,json,yml}]
|
8 |
+
charset = utf-8
|
9 |
+
indent_style = space
|
10 |
+
indent_size = 2
|
Dockerfile
CHANGED
@@ -1,42 +1,22 @@
|
|
1 |
FROM node:20.6.1
|
2 |
-
|
3 |
USER node
|
4 |
-
WORKDIR /app
|
5 |
-
|
6 |
-
RUN mkdir -p /app/node_modules
|
7 |
-
RUN chmod 777 /app
|
8 |
-
RUN chmod 777 /app/node_modules
|
9 |
|
10 |
-
COPY --chown=node
|
11 |
-
COPY --chown=node yarn.lock /app
|
12 |
-
COPY --chown=node . /app
|
13 |
-
|
14 |
-
# Get curl
|
15 |
-
#RUN apt-get update && apt-get install -y curl
|
16 |
-
# Download the file to a temporary location
|
17 |
RUN curl -L https://github.com/omnitool-ai/omnitool/raw/main/packages/omni-server/config.default/models/nsfwjs/mobilenet-v2-quant/group1-shard1of1 -o _tempfile.bin
|
|
|
|
|
|
|
|
|
18 |
|
19 |
-
|
20 |
-
RUN mkdir -p /app/packages/omni-server/config.default/models/nsfwjs/mobilenet-v2-quant/
|
21 |
-
RUN chmod 777 /app/packages/omni-server/config.default/models/nsfwjs/mobilenet-v2-quant/
|
22 |
-
|
23 |
-
# Move the file to the desired directory
|
24 |
-
RUN mv _tempfile.bin /app/packages/omni-server/config.default/models/nsfwjs/mobilenet-v2-quant/group1-shard1of1 && chown -R node /app/packages/omni-server/config.default/models/nsfwjs/mobilenet-v2-quant/group1-shard1of1
|
25 |
-
RUN chmod 777 /app/packages/omni-server/config.default/models/nsfwjs/mobilenet-v2-quant/group1-shard1of1
|
26 |
|
27 |
-
RUN
|
28 |
-
|
29 |
-
# Copy application source code along with main.py and run.sh
|
30 |
-
COPY --chown=node . /app
|
31 |
|
32 |
-
|
33 |
-
# RUN chmod +x $HOME/app/start.sh
|
34 |
|
35 |
-
|
36 |
|
37 |
-
# Create a new service container using the `yarn-app` image as a builder
|
38 |
-
EXPOSE 7860
|
39 |
|
40 |
-
|
41 |
-
#
|
42 |
-
# CMD ["/app/run.sh"]
|
|
|
1 |
FROM node:20.6.1
|
|
|
2 |
USER node
|
3 |
+
WORKDIR /home/node/app
|
|
|
|
|
|
|
|
|
4 |
|
5 |
+
COPY --chown=node ./requirements.txt /home/node/app/requirements.txt
|
|
|
|
|
|
|
|
|
|
|
|
|
6 |
RUN curl -L https://github.com/omnitool-ai/omnitool/raw/main/packages/omni-server/config.default/models/nsfwjs/mobilenet-v2-quant/group1-shard1of1 -o _tempfile.bin
|
7 |
+
RUN mkdir -p /home/node/app/packages/omni-server/config.default/models/nsfwjs/mobilenet-v2-quant/
|
8 |
+
RUN chmod 777 /home/node/app/packages/omni-server/config.default/models/nsfwjs/mobilenet-v2-quant/
|
9 |
+
RUN mv _tempfile.bin /home/node/app/packages/omni-server/config.default/models/nsfwjs/mobilenet-v2-quant/group1-shard1of1 && chown -R node /home/node/app/packages/omni-server/config.default/models/nsfwjs/mobilenet-v2-quant/group1-shard1of1
|
10 |
+
RUN chmod 777 /home/node/app/packages/omni-server/config.default/models/nsfwjs/mobilenet-v2-quant/group1-shard1of1
|
11 |
|
12 |
+
COPY --chown=node . /home/node/app
|
|
|
|
|
|
|
|
|
|
|
|
|
13 |
|
14 |
+
RUN yarn install
|
|
|
|
|
|
|
15 |
|
16 |
+
EXPOSE 1688
|
|
|
17 |
|
18 |
+
CMD [ "./omnitool_start.sh" ]
|
19 |
|
|
|
|
|
20 |
|
21 |
+
# ## docker build -t manusapiens/omnitool-test2b .
|
22 |
+
# ## docker run --name n10c -p 7860:7860 -d manusapiens/omnitool-test2b
|
|
README.md
CHANGED
@@ -1,8 +1,314 @@
|
|
1 |
---
|
2 |
-
title: O
|
3 |
emoji: 🐳
|
4 |
-
colorFrom:
|
5 |
-
colorTo:
|
6 |
sdk: docker
|
7 |
-
app_port:
|
8 |
-
---
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
---
|
2 |
+
title: O T 3
|
3 |
emoji: 🐳
|
4 |
+
colorFrom: yellow
|
5 |
+
colorTo: gray
|
6 |
sdk: docker
|
7 |
+
app_port: 1688
|
8 |
+
---
|
9 |
+
# Omnitool.ai - Your Open Source AI Desktop
|
10 |
+
|
11 |
+
*Discover, Learn, Evaluate and Build with thousands of Generative AI Models.*
|
12 |
+
|
13 |
+
Omnitool.ai is an open-source, downloadable "AI Lab in a box" built for learners, enthusiasts and anyone with interest in the current wave of AI innovation. It provides an extensible browser based desktop environment for streamlined, hands-on interacting with the latest AI models from OpenAI, replicate.com, Stable Diffusion, Google, or other leading providers through a single, unified interface.
|
14 |
+
|
15 |
+

|
16 |
+
|
17 |
+
Watch the [demo](https://tinyurl.com/omnitool-demo)! and see more [videos](https://www.youtube.com/@OmnitoolAI/videos) on our Youtube channel.
|
18 |
+
|
19 |
+
## Why Omnitool?
|
20 |
+
|
21 |
+
With thousands of preprints and countless "AI tools" released each week, it is incredibly challenging to stay on top of the rapidly evolving AI ecosystem, to separate hype and facts and to extract durable long term skills and learning. PapersWithCode and GitHub repositories attached to arXiv papers provide ability to hands-on validate and apply the latest discoveries, but the fragile nature of the Python ecosystem and often steep hardware requirments dramatically limits accessibility. Likewise implementing and testing cloud based models requires delving deep into API documentation and wrestling with connecting code.
|
22 |
+
|
23 |
+
We believe that is a serious problem. AI may represent the first large scale technological disruption unbounded by logistical challenges, scaling along existing wires, API infastructure and app delivery platforms. Meanwhile, market pressure to adopt AI is felt by many businesses and teams.
|
24 |
+
|
25 |
+
Without educated decision makers and technical experts, businesses and public organisations alike are at high risk of falling for hype and magical narratives and expensive misadventures.
|
26 |
+
|
27 |
+
Omnitool is our attempt to improve this situation: A **single, unified interface** capable of connecting with as many AI models as possible and to **reduce the "time to hands on AI" to an absolute minimum**.
|
28 |
+
|
29 |
+
Omnitool is **highly extensible and interoperable**. Most OpenAPI3 based services can be connected and turned into "blocks" without writing code. It's extension framework enables deeper integrations of anything from custom UIs (Like Stability Dream Studio) to Game Engines (like BabyonJS or Phaser) to [Image manipulation libraries](https://github.com/georgzoeller/omni-extension-sharp/blob/master/README.md).
|
30 |
+
|
31 |
+
|
32 |
+
## What Omnitool is NOT
|
33 |
+
|
34 |
+
- Omnitool is **not a multi-user cloud SaaS product**. It's a downloadable, locally installed product.
|
35 |
+
- Omnitool is **NOT a no-code solution** meant to replace coding or enable non engineers to code. It's focused on interacting with AI use cases, not writing general purpose software.
|
36 |
+
- Omnitool is **not production/enterprise software**. (Yet.) It's a lab optimizing for access to the latest technologies over stability and, as with any lab, things may blow up from time to time.
|
37 |
+
|
38 |
+
|
39 |
+
## Table of Contents
|
40 |
+
|
41 |
+
- [Key Features](#key-features)
|
42 |
+
- [Quickstart](#quickstart-guide)
|
43 |
+
- [Manual Install](#manual-install)
|
44 |
+
- [PocketBase DB Admin (ADVANCED)](#pocketbase-db-admin-advanced)
|
45 |
+
- [Next Steps](#next-steps)
|
46 |
+
- [Changelist](#changelist)
|
47 |
+
|
48 |
+
## Key Features
|
49 |
+
|
50 |
+
### Self-hosted and Open Source
|
51 |
+
|
52 |
+
* Omnitool is local self-hosted software that turns your machine into a powerful AI Lab.
|
53 |
+
|
54 |
+
* You install Omnitool and it runs on your Mac, Windows or Linux notebook, desktop or server, not cloud servers.
|
55 |
+
* Data stores it's data locally on your machine and is only transmitted to the third party provider APIs you choose to access. Updates are managed via github.
|
56 |
+
* A Docker Image is forthcoming.
|
57 |
+
* If you are interested in running Omnitool in the cloud, please get in touch with us at [email protected]
|
58 |
+
|
59 |
+
* Open Source and Open Standards
|
60 |
+
* Omnitool is licensed as open source software and heavily leverages open standards, such as OpenAPI, making it interoperable and extensible.
|
61 |
+
|
62 |
+
### Rapid Access to the world of generative AI without GPU, Managing Python installations and learning dozens of APIs and interfaces
|
63 |
+
|
64 |
+
* Minimal Time-to-AI: It allows you to try out models and services in minutes without having to study API docs, write boilerplate code, manage python venvs or figuring out new user interfaces. Because of it's integration of many leading AI platforms, the lag time between "paper with code" to hands on experimentation often is cut down to days.
|
65 |
+
|
66 |
+
* It presents the vast world of generative AI - image, video, audio, text, and classification APIS - through a single, unified user interface without oversimplifying or hiding the power of the APIs.
|
67 |
+
|
68 |
+
### Comprehensive AI Provider Support
|
69 |
+
* Seamlessly provides access to 1000s of AI model and utility APIs from an rapidly growing list leading AI providers and aggregators, exposing them all via interoperable blocks.
|
70 |
+
|
71 |
+
Currently supported (v. 0.5.3) :
|
72 |
+
* [Civitai.com](https://civitai.com) (Model metadata access)
|
73 |
+
* [Deepl.com](https://deepl.com) (Document translation)
|
74 |
+
* [ElevenLabs.io](https://elevenlabs.io) (Multilingual voice generation)
|
75 |
+
* Getimg.ai (Image generation and manipulation APIs)
|
76 |
+
* Github.com (Various)
|
77 |
+
* Google.com
|
78 |
+
* Gmail
|
79 |
+
* Vertex (AI)
|
80 |
+
* Google Translate
|
81 |
+
* Google TTS (Text to Speech)
|
82 |
+
* Google Vision (Computer Vision)
|
83 |
+
* [Huggingface.com](https://huggingface.com) (1000's of models, including free inference models)
|
84 |
+
* [OpenAI.com](https://openai.com) (Image/Text/Audio Generation including GPT3/4/Visual, Whisper, Dall-e 2, Dall-e 3, Moderation APIs and more)
|
85 |
+
* [OpenRouter.ai](https://OpenRouter.ai) (100s of LLM APIs)
|
86 |
+
* [Perplexity.ai](https://perplexity.ai) (Text Generation)
|
87 |
+
* [Stability.ai](https://stability.ai) (Image Generation and Manipulation APIs)
|
88 |
+
* [TextSynth.com](https://textsynth.com) (LLM, translation, and classification APIs)
|
89 |
+
* [Replicate.com](https://replicate.com/explore) (1000s of models across all modalities)
|
90 |
+
* [Uberduck.com](https://uberduck.com) (Voice Generation, Music centric offerings)
|
91 |
+
* [Unsplash.com](https://unsplash.com) (Stock imagery)
|
92 |
+
* with many more APIs in testing...
|
93 |
+
|
94 |
+
* Support for the following Open Source APIs is in the final stages of testing:
|
95 |
+
* Automatic1111/SDNext API
|
96 |
+
* Oobabooga Text Generation API
|
97 |
+
* Ollama API
|
98 |
+
|
99 |
+
* Omnitool is able to generate blocks from any openapi.json definitions via URL or directly supplied file. We support a number of custom x- annotations that can be added to openapi definitions to allow omnitool to guide the block generation. It also supports creating "patches" on top of existing APIs to create customized blocks. With integrated JSONATA support, it is possible to build powerful data processing blocks using pure data.
|
100 |
+
|
101 |
+
|
102 |
+
### Extensible Architecture
|
103 |
+
|
104 |
+
* Inspired by the common modding architecture found in video game toolsets, Omnitool is built, from the ground up, to be extensible via multiple mechanisms:
|
105 |
+
* Simple **Client and Server scripts** allowing addition of /commands that are hot-reloaded, so editing and building is a breeze.
|
106 |
+
* **Client Extensions** - any web-app/webpage can be turned into an extension and integrated directly on Omnitool's desktop via it's window system. Omnitool's client SDK exposes the full range of platform functionality to extensions, allowing you to write apps or tools using every API or recipe enabled in Omnitool.
|
107 |
+
* **Server Extensions** - Server extensions written in javascript that can add new blocks, API and core functionality.
|
108 |
+
|
109 |
+
* Some examples of currently available extensions:
|
110 |
+
* omni-core-replicate, a core extensions that allows import of any AI model on [replicate.com](https://replicate.com) into a ready to use block in Omnitool
|
111 |
+
* [omni-extension-sharp](https://github.com/omnitool-community/omni-extension-sharp), an extension adding an array of Image Manipulation blocks such as format conversion, masking, composition and more based on the powerful [sharp](https://github.com/lovell/sharp) image processing library.
|
112 |
+
* omni-extension-minipaint, a powerful [photo editing tool](https://github.com/viliusle/miniPaint) useful for quickly creating and editing images without switching out of the app.
|
113 |
+
* omni-extension-openpose, a [OpenPose based](https://github.com/CMU-Perceptual-Computing-Lab/openpose) pose estimation and generation toolkit useful for creating guidance images for controlnet/diffusion models.
|
114 |
+
* omni-extension-tldraw, a whiteboarding/sketching extension built on [TLDraw](https://github.com/tldraw/tldraw), useful for generating input for visual transformers and diffusion models
|
115 |
+
* omni-extension-wavacity, a [full wasm implementation](https://wavacity.com/) of Audacity, a state of the art audio recorder/editor useful for generating and editing audio content.
|
116 |
+
|
117 |
+
* Visit the Extension tab in app or see our [Omnitool Community Github](https://github.com/orgs/omnitool-community/repositories) for a list of currently available extensions
|
118 |
+
|
119 |
+
|
120 |
+
## Quickstart Guide
|
121 |
+
|
122 |
+
We are currently testing installers for Windows and macOS. Until those are publicly available, please follow the manual installation steps.
|
123 |
+
|
124 |
+
## Manual Install
|
125 |
+
|
126 |
+
This guide will help you download the Omnitool software, and then build and start the Omnitool server in a directory running from your local machine.
|
127 |
+
|
128 |
+
You can then access the Omnitool software from a web browser on your local machine.
|
129 |
+
|
130 |
+
1. **Prerequisites**
|
131 |
+
|
132 |
+
Ensure you have the latest versions of the following sofware installed:
|
133 |
+
|
134 |
+
* [Node.js](https://nodejs.org/en)
|
135 |
+
* [Yarn](https://yarnpkg.com)
|
136 |
+
* [Git](https://en.wikipedia.org/wiki/Git)
|
137 |
+
|
138 |
+
|
139 |
+
2. **Get the Source Code**
|
140 |
+
- Open a terminal
|
141 |
+
- Navigate to where you want Omnitool to be installed
|
142 |
+
- Use the following command:
|
143 |
+
```
|
144 |
+
git clone https://github.com/omnitool-ai/omnitool
|
145 |
+
```
|
146 |
+
|
147 |
+
This will create the `omnitool` folder.
|
148 |
+
|
149 |
+
- Now navigate inside Omnitool's folder. By default:
|
150 |
+
```
|
151 |
+
cd omnitool
|
152 |
+
```
|
153 |
+
|
154 |
+
3. **Install Source Dependencies**
|
155 |
+
|
156 |
+
Run the following command in the root of the repository to install the necessary dependencies:
|
157 |
+
```
|
158 |
+
yarn install
|
159 |
+
```
|
160 |
+
**Troubleshooting**
|
161 |
+
|
162 |
+
* **PYTHON 3.12** - some users are reporting a yarn install failure due to **a missing python module 'distutils'**. To resolve this, we recommend running our fix script to detect and autofix any potential issues and try again. Or you can manually pip install 'setuptools' from the terminal.
|
163 |
+
```
|
164 |
+
node setup\fix.js
|
165 |
+
```
|
166 |
+
|
167 |
+
4. **Build and Start the Server**
|
168 |
+
|
169 |
+
Now we will use `yarn` and `Node.js` to build the server software locally on your machine and then start it running.
|
170 |
+
|
171 |
+
Windows:
|
172 |
+
```
|
173 |
+
start.bat
|
174 |
+
```
|
175 |
+
|
176 |
+
MacOS/Linux:
|
177 |
+
```
|
178 |
+
./start.sh
|
179 |
+
```
|
180 |
+
|
181 |
+
When successful, you will see the following message:
|
182 |
+
|
183 |
+
```
|
184 |
+
◐ Booting Server
|
185 |
+
✔ Server has started and is ready to accept connections on http://127.0.0.1:1688.
|
186 |
+
✔ Ctrl-C to quit.
|
187 |
+
```
|
188 |
+
|
189 |
+
5. **Open Omnitool in a Web Browser**
|
190 |
+
|
191 |
+
Omnitool.ai can now be accessed from:
|
192 |
+
[127.0.0.1:1688](http://127.0.0.1:1688)
|
193 |
+
|
194 |
+
---
|
195 |
+
6. **Explore the Sample Recipes**
|
196 |
+
Use the "Load Recipe" button in the menu to explore different functionality of the platform.
|
197 |
+
|
198 |
+
---
|
199 |
+
7. **Explore the Code**
|
200 |
+
For a list of scripts we use internally, try running:
|
201 |
+
```
|
202 |
+
yarn run
|
203 |
+
```
|
204 |
+
|
205 |
+
## PocketBase DB Admin (ADVANCED)
|
206 |
+
Recipes and various cache data are stored in a [PocketBase](https://pocketbase.io) database.
|
207 |
+
|
208 |
+
If the database is currently running, you can access the default PocketBase admin interface by navigating to [127.0.0.1:8090/_](http://127.0.0.1:8090/_)
|
209 |
+
|
210 |
+
Alternatively, the admin interface can be accessed directly within omnitool. From the main menu, choose the `Database Admin` option and the same interface will open inside the omnitool browser window.
|
211 |
+
|
212 |
+
o log in to the database, use the credentials
|
213 |
+
* Email: **[email protected]**
|
214 |
+
* Password: **[email protected]**
|
215 |
+
|
216 |
+
Once logged in, you can directly modify records using the PocketBase admin interface. This is particularly useful for advanced configurations and troubleshooting.
|
217 |
+
|
218 |
+
### Reset Local PocketBase Storage (ADVANCED)
|
219 |
+
|
220 |
+
There may be occasions when you need to reset your local database, either to recover from an invalid state or to start with a fresh install.
|
221 |
+
|
222 |
+
For Linux:
|
223 |
+
```bash
|
224 |
+
rm -rf ./local.bin
|
225 |
+
yarn start
|
226 |
+
```
|
227 |
+
For Windows:
|
228 |
+
```cmd
|
229 |
+
rmdir /s /q .\local.bin
|
230 |
+
yarn start
|
231 |
+
```
|
232 |
+
|
233 |
+
- **Warning**:
|
234 |
+
- **ALL YOUR LOCAL RECIPES, GENERATED IMAGES, DOCUMENTS, AUDIO ETC, WILL BE PERMANENTLY ERASED**
|
235 |
+
|
236 |
+
## Generating a JWT Token
|
237 |
+
|
238 |
+
Our service allows you to generate a JWT by running a specific script designed for this purpose. The script's signature is as follows:
|
239 |
+
|
240 |
+
```
|
241 |
+
/generateJwtToken <action> <subject> <expires_in>
|
242 |
+
```
|
243 |
+
|
244 |
+
**Parameters**
|
245 |
+
|
246 |
+
- `<action>`: This is a string parameter identifying the intended action to be performed. In the context of running recipes, this should be set to exec.
|
247 |
+
- `<subject>`: This is a string parameter that specifies the subject of the JWT. This could be the recipe that you intend to execute.
|
248 |
+
- `<expires_in>`: This is an integer parameter that determines the token's validity period in milliseconds.
|
249 |
+
|
250 |
+
**Example**
|
251 |
+
|
252 |
+
To generate a JWT for executing a recipe with a validity of 30,000 milliseconds (or 30 seconds), you would run the following script:
|
253 |
+
|
254 |
+
```
|
255 |
+
/generateJwtToken exec Workflow 30000
|
256 |
+
```
|
257 |
+
|
258 |
+
**Output**
|
259 |
+
|
260 |
+
The script will output a JWT, which is a token string to be used in the authorization header for your API requests.
|
261 |
+
|
262 |
+
### Executing a recipe with JWT Authentication
|
263 |
+
|
264 |
+
Once you have your JWT, you can execute a recipe by making a POST request to the recipe execution API. This request must include the JWT in the Authorization header.
|
265 |
+
|
266 |
+
**Endpoint**
|
267 |
+
|
268 |
+
```
|
269 |
+
POST http://127.0.0.1:1688/api/v1/workflow/exec
|
270 |
+
```
|
271 |
+
|
272 |
+
**Header**
|
273 |
+
|
274 |
+
```
|
275 |
+
Authorization: Bearer <token>
|
276 |
+
```
|
277 |
+
|
278 |
+
`<token>` is the JWT acquired from the /generateJwtToken script.
|
279 |
+
|
280 |
+
**Curl Example**
|
281 |
+
|
282 |
+
To make the request using curl, you would use the following command, replacing <token> with your actual JWT:
|
283 |
+
|
284 |
+
```
|
285 |
+
curl -X POST http://127.0.0.1:1688/api/v1/workflow/exec -H "Authorization: Bearer <token>"
|
286 |
+
```
|
287 |
+
|
288 |
+
**Response**
|
289 |
+
|
290 |
+
Upon success, the API will initiate the specified recipe. You will receive a JSON response containing details about the recipe's execution status, including any outputs or errors.
|
291 |
+
|
292 |
+
**Security Considerations**
|
293 |
+
|
294 |
+
- Keep your JWT secure to prevent unauthorized access to your recipes.
|
295 |
+
- Always use a secure connection to interact with the APIs.
|
296 |
+
- Regularly rotate your tokens and use a short expiration time to minimize the impact of potential leaks.
|
297 |
+
|
298 |
+
**Troubleshooting**
|
299 |
+
|
300 |
+
* If you encounter authorization errors, ensure the JWT has not expired, is correctly set in the header, and was generated with the proper parameters.
|
301 |
+
|
302 |
+
## Next Steps
|
303 |
+
|
304 |
+
1. Join the Omnitool.ai Discord Community
|
305 |
+
|
306 |
+
Interact with fellow users, share your experiences, ask questions, and be a part of our active and growing community on [Discord](https://tinyurl.com/omnitool-discord).
|
307 |
+
|
308 |
+
2. Contribute to Omnitool.ai
|
309 |
+
|
310 |
+
As an open-source platform, we welcome contributions from users like you. Whether it's improving documentation, adding new features, or simply sharing your unique use cases, your input is invaluable to us. Simply send us a pull-request and we'll be in contact.
|
311 |
+
|
312 |
+
3. Feedback and Suggestions
|
313 |
+
|
314 |
+
Your feedback helps shape the future of Omnitool.ai. Send your feedback and suggestions to [[email protected]](mailto:[email protected]), or share them directly in our [Discord #feedback channel](https://tinyurl.com/omnitool-feedback).
|
README2.md
DELETED
@@ -1,306 +0,0 @@
|
|
1 |
-
# Omnitool.ai - Your Open Source AI Desktop
|
2 |
-
|
3 |
-
*Discover, Learn, Evaluate and Build with thousands of Generative AI Models.*
|
4 |
-
|
5 |
-
Omnitool.ai is an open-source, downloadable "AI Lab in a box" built for learners, enthusiasts and anyone with interest in the current wave of AI innovation. It provides an extensible browser based desktop environment for streamlined, hands-on interacting with the latest AI models from OpenAI, replicate.com, Stable Diffusion, Google, or other leading providers through a single, unified interface.
|
6 |
-
|
7 |
-

|
8 |
-
|
9 |
-
Watch the [demo](https://tinyurl.com/omnitool-demo)! and see more [videos](https://www.youtube.com/@OmnitoolAI/videos) on our Youtube channel.
|
10 |
-
|
11 |
-
## Why Omnitool?
|
12 |
-
|
13 |
-
With thousands of preprints and countless "AI tools" released each week, it is incredibly challenging to stay on top of the rapidly evolving AI ecosystem, to separate hype and facts and to extract durable long term skills and learning. PapersWithCode and GitHub repositories attached to arXiv papers provide ability to hands-on validate and apply the latest discoveries, but the fragile nature of the Python ecosystem and often steep hardware requirments dramatically limits accessibility. Likewise implementing and testing cloud based models requires delving deep into API documentation and wrestling with connecting code.
|
14 |
-
|
15 |
-
We believe that is a serious problem. AI may represent the first large scale technological disruption unbounded by logistical challenges, scaling along existing wires, API infastructure and app delivery platforms. Meanwhile, market pressure to adopt AI is felt by many businesses and teams.
|
16 |
-
|
17 |
-
Without educated decision makers and technical experts, businesses and public organisations alike are at high risk of falling for hype and magical narratives and expensive misadventures.
|
18 |
-
|
19 |
-
Omnitool is our attempt to improve this situation: A **single, unified interface** capable of connecting with as many AI models as possible and to **reduce the "time to hands on AI" to an absolute minimum**.
|
20 |
-
|
21 |
-
Omnitool is **highly extensible and interoperable**. Most OpenAPI3 based services can be connected and turned into "blocks" without writing code. It's extension framework enables deeper integrations of anything from custom UIs (Like Stability Dream Studio) to Game Engines (like BabyonJS or Phaser) to [Image manipulation libraries](https://github.com/georgzoeller/omni-extension-sharp/blob/master/README.md).
|
22 |
-
|
23 |
-
|
24 |
-
## What Omnitool is NOT
|
25 |
-
|
26 |
-
- Omnitool is **not a multi-user cloud SaaS product**. It's a downloadable, locally installed product.
|
27 |
-
- Omnitool is **NOT a no-code solution** meant to replace coding or enable non engineers to code. It's focused on interacting with AI use cases, not writing general purpose software.
|
28 |
-
- Omnitool is **not production/enterprise software**. (Yet.) It's a lab optimizing for access to the latest technologies over stability and, as with any lab, things may blow up from time to time.
|
29 |
-
|
30 |
-
|
31 |
-
## Table of Contents
|
32 |
-
|
33 |
-
- [Key Features](#key-features)
|
34 |
-
- [Quickstart](#quickstart-guide)
|
35 |
-
- [Manual Install](#manual-install)
|
36 |
-
- [PocketBase DB Admin (ADVANCED)](#pocketbase-db-admin-advanced)
|
37 |
-
- [Next Steps](#next-steps)
|
38 |
-
- [Changelist](#changelist)
|
39 |
-
|
40 |
-
## Key Features
|
41 |
-
|
42 |
-
### Self-hosted and Open Source
|
43 |
-
|
44 |
-
* Omnitool is local self-hosted software that turns your machine into a powerful AI Lab.
|
45 |
-
|
46 |
-
* You install Omnitool and it runs on your Mac, Windows or Linux notebook, desktop or server, not cloud servers.
|
47 |
-
* Data stores it's data locally on your machine and is only transmitted to the third party provider APIs you choose to access. Updates are managed via github.
|
48 |
-
* A Docker Image is forthcoming.
|
49 |
-
* If you are interested in running Omnitool in the cloud, please get in touch with us at [email protected]
|
50 |
-
|
51 |
-
* Open Source and Open Standards
|
52 |
-
* Omnitool is licensed as open source software and heavily leverages open standards, such as OpenAPI, making it interoperable and extensible.
|
53 |
-
|
54 |
-
### Rapid Access to the world of generative AI without GPU, Managing Python installations and learning dozens of APIs and interfaces
|
55 |
-
|
56 |
-
* Minimal Time-to-AI: It allows you to try out models and services in minutes without having to study API docs, write boilerplate code, manage python venvs or figuring out new user interfaces. Because of it's integration of many leading AI platforms, the lag time between "paper with code" to hands on experimentation often is cut down to days.
|
57 |
-
|
58 |
-
* It presents the vast world of generative AI - image, video, audio, text, and classification APIS - through a single, unified user interface without oversimplifying or hiding the power of the APIs.
|
59 |
-
|
60 |
-
### Comprehensive AI Provider Support
|
61 |
-
* Seamlessly provides access to 1000s of AI model and utility APIs from an rapidly growing list leading AI providers and aggregators, exposing them all via interoperable blocks.
|
62 |
-
|
63 |
-
Currently supported (v. 0.5.3) :
|
64 |
-
* [Civitai.com](https://civitai.com) (Model metadata access)
|
65 |
-
* [Deepl.com](https://deepl.com) (Document translation)
|
66 |
-
* [ElevenLabs.io](https://elevenlabs.io) (Multilingual voice generation)
|
67 |
-
* Getimg.ai (Image generation and manipulation APIs)
|
68 |
-
* Github.com (Various)
|
69 |
-
* Google.com
|
70 |
-
* Gmail
|
71 |
-
* Vertex (AI)
|
72 |
-
* Google Translate
|
73 |
-
* Google TTS (Text to Speech)
|
74 |
-
* Google Vision (Computer Vision)
|
75 |
-
* [Huggingface.com](https://huggingface.com) (1000's of models, including free inference models)
|
76 |
-
* [OpenAI.com](https://openai.com) (Image/Text/Audio Generation including GPT3/4/Visual, Whisper, Dall-e 2, Dall-e 3, Moderation APIs and more)
|
77 |
-
* [OpenRouter.ai](https://OpenRouter.ai) (100s of LLM APIs)
|
78 |
-
* [Perplexity.ai](https://perplexity.ai) (Text Generation)
|
79 |
-
* [Stability.ai](https://stability.ai) (Image Generation and Manipulation APIs)
|
80 |
-
* [TextSynth.com](https://textsynth.com) (LLM, translation, and classification APIs)
|
81 |
-
* [Replicate.com](https://replicate.com/explore) (1000s of models across all modalities)
|
82 |
-
* [Uberduck.com](https://uberduck.com) (Voice Generation, Music centric offerings)
|
83 |
-
* [Unsplash.com](https://unsplash.com) (Stock imagery)
|
84 |
-
* with many more APIs in testing...
|
85 |
-
|
86 |
-
* Support for the following Open Source APIs is in the final stages of testing:
|
87 |
-
* Automatic1111/SDNext API
|
88 |
-
* Oobabooga Text Generation API
|
89 |
-
* Ollama API
|
90 |
-
|
91 |
-
* Omnitool is able to generate blocks from any openapi.json definitions via URL or directly supplied file. We support a number of custom x- annotations that can be added to openapi definitions to allow omnitool to guide the block generation. It also supports creating "patches" on top of existing APIs to create customized blocks. With integrated JSONATA support, it is possible to build powerful data processing blocks using pure data.
|
92 |
-
|
93 |
-
|
94 |
-
### Extensible Architecture
|
95 |
-
|
96 |
-
* Inspired by the common modding architecture found in video game toolsets, Omnitool is built, from the ground up, to be extensible via multiple mechanisms:
|
97 |
-
* Simple **Client and Server scripts** allowing addition of /commands that are hot-reloaded, so editing and building is a breeze.
|
98 |
-
* **Client Extensions** - any web-app/webpage can be turned into an extension and integrated directly on Omnitool's desktop via it's window system. Omnitool's client SDK exposes the full range of platform functionality to extensions, allowing you to write apps or tools using every API or recipe enabled in Omnitool.
|
99 |
-
* **Server Extensions** - Server extensions written in javascript that can add new blocks, API and core functionality.
|
100 |
-
|
101 |
-
* Some examples of currently available extensions:
|
102 |
-
* omni-core-replicate, a core extensions that allows import of any AI model on [replicate.com](https://replicate.com) into a ready to use block in Omnitool
|
103 |
-
* [omni-extension-sharp](https://github.com/omnitool-community/omni-extension-sharp), an extension adding an array of Image Manipulation blocks such as format conversion, masking, composition and more based on the powerful [sharp](https://github.com/lovell/sharp) image processing library.
|
104 |
-
* omni-extension-minipaint, a powerful [photo editing tool](https://github.com/viliusle/miniPaint) useful for quickly creating and editing images without switching out of the app.
|
105 |
-
* omni-extension-openpose, a [OpenPose based](https://github.com/CMU-Perceptual-Computing-Lab/openpose) pose estimation and generation toolkit useful for creating guidance images for controlnet/diffusion models.
|
106 |
-
* omni-extension-tldraw, a whiteboarding/sketching extension built on [TLDraw](https://github.com/tldraw/tldraw), useful for generating input for visual transformers and diffusion models
|
107 |
-
* omni-extension-wavacity, a [full wasm implementation](https://wavacity.com/) of Audacity, a state of the art audio recorder/editor useful for generating and editing audio content.
|
108 |
-
|
109 |
-
* Visit the Extension tab in app or see our [Omnitool Community Github](https://github.com/orgs/omnitool-community/repositories) for a list of currently available extensions
|
110 |
-
|
111 |
-
|
112 |
-
## Quickstart Guide
|
113 |
-
|
114 |
-
We are currently testing installers for Windows and macOS. Until those are publicly available, please follow the manual installation steps.
|
115 |
-
|
116 |
-
## Manual Install
|
117 |
-
|
118 |
-
This guide will help you download the Omnitool software, and then build and start the Omnitool server in a directory running from your local machine.
|
119 |
-
|
120 |
-
You can then access the Omnitool software from a web browser on your local machine.
|
121 |
-
|
122 |
-
1. **Prerequisites**
|
123 |
-
|
124 |
-
Ensure you have the latest versions of the following sofware installed:
|
125 |
-
|
126 |
-
* [Node.js](https://nodejs.org/en)
|
127 |
-
* [Yarn](https://yarnpkg.com)
|
128 |
-
* [Git](https://en.wikipedia.org/wiki/Git)
|
129 |
-
|
130 |
-
|
131 |
-
2. **Get the Source Code**
|
132 |
-
- Open a terminal
|
133 |
-
- Navigate to where you want Omnitool to be installed
|
134 |
-
- Use the following command:
|
135 |
-
```
|
136 |
-
git clone https://github.com/omnitool-ai/omnitool
|
137 |
-
```
|
138 |
-
|
139 |
-
This will create the `omnitool` folder.
|
140 |
-
|
141 |
-
- Now navigate inside Omnitool's folder. By default:
|
142 |
-
```
|
143 |
-
cd omnitool
|
144 |
-
```
|
145 |
-
|
146 |
-
3. **Install Source Dependencies**
|
147 |
-
|
148 |
-
Run the following command in the root of the repository to install the necessary dependencies:
|
149 |
-
```
|
150 |
-
yarn install
|
151 |
-
```
|
152 |
-
**Troubleshooting**
|
153 |
-
|
154 |
-
* **PYTHON 3.12** - some users are reporting a yarn install failure due to **a missing python module 'distutils'**. To resolve this, we recommend running our fix script to detect and autofix any potential issues and try again. Or you can manually pip install 'setuptools' from the terminal.
|
155 |
-
```
|
156 |
-
node setup\fix.js
|
157 |
-
```
|
158 |
-
|
159 |
-
4. **Build and Start the Server**
|
160 |
-
|
161 |
-
Now we will use `yarn` and `Node.js` to build the server software locally on your machine and then start it running.
|
162 |
-
|
163 |
-
Windows:
|
164 |
-
```
|
165 |
-
start.bat
|
166 |
-
```
|
167 |
-
|
168 |
-
MacOS/Linux:
|
169 |
-
```
|
170 |
-
./start.sh
|
171 |
-
```
|
172 |
-
|
173 |
-
When successful, you will see the following message:
|
174 |
-
|
175 |
-
```
|
176 |
-
◐ Booting Server
|
177 |
-
✔ Server has started and is ready to accept connections on http://127.0.0.1:1688.
|
178 |
-
✔ Ctrl-C to quit.
|
179 |
-
```
|
180 |
-
|
181 |
-
5. **Open Omnitool in a Web Browser**
|
182 |
-
|
183 |
-
Omnitool.ai can now be accessed from:
|
184 |
-
[127.0.0.1:1688](http://127.0.0.1:1688)
|
185 |
-
|
186 |
-
---
|
187 |
-
6. **Explore the Sample Recipes**
|
188 |
-
Use the "Load Recipe" button in the menu to explore different functionality of the platform.
|
189 |
-
|
190 |
-
---
|
191 |
-
7. **Explore the Code**
|
192 |
-
For a list of scripts we use internally, try running:
|
193 |
-
```
|
194 |
-
yarn run
|
195 |
-
```
|
196 |
-
|
197 |
-
## PocketBase DB Admin (ADVANCED)
|
198 |
-
Recipes and various cache data are stored in a [PocketBase](https://pocketbase.io) database.
|
199 |
-
|
200 |
-
If the database is currently running, you can access the default PocketBase admin interface by navigating to [127.0.0.1:8090/_](http://127.0.0.1:8090/_)
|
201 |
-
|
202 |
-
Alternatively, the admin interface can be accessed directly within omnitool. From the main menu, choose the `Database Admin` option and the same interface will open inside the omnitool browser window.
|
203 |
-
|
204 |
-
o log in to the database, use the credentials
|
205 |
-
* Email: **[email protected]**
|
206 |
-
* Password: **[email protected]**
|
207 |
-
|
208 |
-
Once logged in, you can directly modify records using the PocketBase admin interface. This is particularly useful for advanced configurations and troubleshooting.
|
209 |
-
|
210 |
-
### Reset Local PocketBase Storage (ADVANCED)
|
211 |
-
|
212 |
-
There may be occasions when you need to reset your local database, either to recover from an invalid state or to start with a fresh install.
|
213 |
-
|
214 |
-
For Linux:
|
215 |
-
```bash
|
216 |
-
rm -rf ./local.bin
|
217 |
-
yarn start
|
218 |
-
```
|
219 |
-
For Windows:
|
220 |
-
```cmd
|
221 |
-
rmdir /s /q .\local.bin
|
222 |
-
yarn start
|
223 |
-
```
|
224 |
-
|
225 |
-
- **Warning**:
|
226 |
-
- **ALL YOUR LOCAL RECIPES, GENERATED IMAGES, DOCUMENTS, AUDIO ETC, WILL BE PERMANENTLY ERASED**
|
227 |
-
|
228 |
-
## Generating a JWT Token
|
229 |
-
|
230 |
-
Our service allows you to generate a JWT by running a specific script designed for this purpose. The script's signature is as follows:
|
231 |
-
|
232 |
-
```
|
233 |
-
/generateJwtToken <action> <subject> <expires_in>
|
234 |
-
```
|
235 |
-
|
236 |
-
**Parameters**
|
237 |
-
|
238 |
-
- `<action>`: This is a string parameter identifying the intended action to be performed. In the context of running recipes, this should be set to exec.
|
239 |
-
- `<subject>`: This is a string parameter that specifies the subject of the JWT. This could be the recipe that you intend to execute.
|
240 |
-
- `<expires_in>`: This is an integer parameter that determines the token's validity period in milliseconds.
|
241 |
-
|
242 |
-
**Example**
|
243 |
-
|
244 |
-
To generate a JWT for executing a recipe with a validity of 30,000 milliseconds (or 30 seconds), you would run the following script:
|
245 |
-
|
246 |
-
```
|
247 |
-
/generateJwtToken exec Workflow 30000
|
248 |
-
```
|
249 |
-
|
250 |
-
**Output**
|
251 |
-
|
252 |
-
The script will output a JWT, which is a token string to be used in the authorization header for your API requests.
|
253 |
-
|
254 |
-
### Executing a recipe with JWT Authentication
|
255 |
-
|
256 |
-
Once you have your JWT, you can execute a recipe by making a POST request to the recipe execution API. This request must include the JWT in the Authorization header.
|
257 |
-
|
258 |
-
**Endpoint**
|
259 |
-
|
260 |
-
```
|
261 |
-
POST http://127.0.0.1:1688/api/v1/workflow/exec
|
262 |
-
```
|
263 |
-
|
264 |
-
**Header**
|
265 |
-
|
266 |
-
```
|
267 |
-
Authorization: Bearer <token>
|
268 |
-
```
|
269 |
-
|
270 |
-
`<token>` is the JWT acquired from the /generateJwtToken script.
|
271 |
-
|
272 |
-
**Curl Example**
|
273 |
-
|
274 |
-
To make the request using curl, you would use the following command, replacing <token> with your actual JWT:
|
275 |
-
|
276 |
-
```
|
277 |
-
curl -X POST http://127.0.0.1:1688/api/v1/workflow/exec -H "Authorization: Bearer <token>"
|
278 |
-
```
|
279 |
-
|
280 |
-
**Response**
|
281 |
-
|
282 |
-
Upon success, the API will initiate the specified recipe. You will receive a JSON response containing details about the recipe's execution status, including any outputs or errors.
|
283 |
-
|
284 |
-
**Security Considerations**
|
285 |
-
|
286 |
-
- Keep your JWT secure to prevent unauthorized access to your recipes.
|
287 |
-
- Always use a secure connection to interact with the APIs.
|
288 |
-
- Regularly rotate your tokens and use a short expiration time to minimize the impact of potential leaks.
|
289 |
-
|
290 |
-
**Troubleshooting**
|
291 |
-
|
292 |
-
* If you encounter authorization errors, ensure the JWT has not expired, is correctly set in the header, and was generated with the proper parameters.
|
293 |
-
|
294 |
-
## Next Steps
|
295 |
-
|
296 |
-
1. Join the Omnitool.ai Discord Community
|
297 |
-
|
298 |
-
Interact with fellow users, share your experiences, ask questions, and be a part of our active and growing community on [Discord](https://tinyurl.com/omnitool-discord).
|
299 |
-
|
300 |
-
2. Contribute to Omnitool.ai
|
301 |
-
|
302 |
-
As an open-source platform, we welcome contributions from users like you. Whether it's improving documentation, adding new features, or simply sharing your unique use cases, your input is invaluable to us. Simply send us a pull-request and we'll be in contact.
|
303 |
-
|
304 |
-
3. Feedback and Suggestions
|
305 |
-
|
306 |
-
Your feedback helps shape the future of Omnitool.ai. Send your feedback and suggestions to [[email protected]](mailto:[email protected]), or share them directly in our [Discord #feedback channel](https://tinyurl.com/omnitool-feedback).
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
assets/screenshot.jpg
ADDED
![]() |
assets/screenshot_collection.png
ADDED
![]() |
assets/screenshot_desktop.png
ADDED
![]() |
assets/screenshot_desktop_02.png
ADDED
![]() |
assets/screenshot_extension.png
ADDED
![]() |
assets/screenshot_filemanager.png
ADDED
![]() |
assets/screenshot_nodes.png
ADDED
![]() |
assets/screenshot_omnillusion.png
ADDED
![]() |
assets/screenshot_omniwa.png
ADDED
![]() |
assets/screenshot_viewer.png
ADDED
![]() |
docker_build.sh
DELETED
@@ -1,4 +0,0 @@
|
|
1 |
-
#!/bin/bash
|
2 |
-
|
3 |
-
docker build -t fastapi .
|
4 |
-
docker run -it -p 7860:7860 fastapi
|
|
|
|
|
|
|
|
|
|
launch.js
DELETED
@@ -1,53 +0,0 @@
|
|
1 |
-
const fastify = require('fastify')({ logger: true });
|
2 |
-
const http = require('http');
|
3 |
-
const { spawn } = require('child_process');
|
4 |
-
|
5 |
-
const PROXY_PORT = 7860; // Change this to a port different from 1688
|
6 |
-
const TARGET_HOST = '127.0.0.1';
|
7 |
-
const TARGET_PORT = 1688;
|
8 |
-
|
9 |
-
// Function to start the request forwarding server
|
10 |
-
async function startRequestForwardingServer() {
|
11 |
-
const server = http.createServer((req, res) => {
|
12 |
-
const options = {
|
13 |
-
hostname: TARGET_HOST,
|
14 |
-
port: TARGET_PORT,
|
15 |
-
path: req.url,
|
16 |
-
method: req.method,
|
17 |
-
headers: req.headers,
|
18 |
-
};
|
19 |
-
|
20 |
-
const proxy = http.request(options, (proxyRes) => {
|
21 |
-
res.writeHead(proxyRes.statusCode, proxyRes.headers);
|
22 |
-
proxyRes.pipe(res, { end: true });
|
23 |
-
});
|
24 |
-
|
25 |
-
req.pipe(proxy, { end: true });
|
26 |
-
});
|
27 |
-
|
28 |
-
server.listen(PROXY_PORT, '0.0.0.0');
|
29 |
-
console.log(`Request forwarding server listening on port ${PROXY_PORT}`);
|
30 |
-
}
|
31 |
-
|
32 |
-
// Function to start the background process
|
33 |
-
function startYarnStartProcess() {
|
34 |
-
const child = spawn('yarn', ['start'], {
|
35 |
-
detached: true,
|
36 |
-
stdio: 'ignore'
|
37 |
-
});
|
38 |
-
|
39 |
-
child.unref();
|
40 |
-
}
|
41 |
-
|
42 |
-
// Main function to start everything
|
43 |
-
async function startServers() {
|
44 |
-
try {
|
45 |
-
startYarnStartProcess();
|
46 |
-
await startRequestForwardingServer();
|
47 |
-
} catch (error) {
|
48 |
-
console.error('Failed to start servers:', error);
|
49 |
-
}
|
50 |
-
}
|
51 |
-
|
52 |
-
// Start the servers
|
53 |
-
startServers();
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
omnitool_start.sh
CHANGED
@@ -1,18 +1,35 @@
|
|
1 |
#!/bin/bash
|
|
|
2 |
|
3 |
-
|
4 |
-
|
5 |
-
echo "
|
6 |
-
/usr/local/bin/node -v
|
7 |
|
8 |
-
|
9 |
-
|
|
|
10 |
|
11 |
-
#
|
12 |
-
echo "
|
13 |
-
printenv
|
14 |
|
15 |
-
|
16 |
|
17 |
-
#
|
18 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
#!/bin/bash
|
2 |
+
echo "--- YARN START ---"
|
3 |
|
4 |
+
if [ -d "/data" ] && [ ! -L "/home/node/app/packages/omni-server/data.local" ]; then
|
5 |
+
# Backup the existing data.local directory
|
6 |
+
echo "--- Backup the existing data.local directory ---"
|
|
|
7 |
|
8 |
+
if [ -d "/home/node/app/packages/omni-server/data.local" ]; then
|
9 |
+
mv /home/node/app/packages/omni-server/data.local /home/node/app/packages/omni-server/data.local.org
|
10 |
+
fi
|
11 |
|
12 |
+
# Create the symlink
|
13 |
+
echo "--- Create the symlink ---"
|
|
|
14 |
|
15 |
+
ln -s /data /home/node/app/packages/omni-server/data.local
|
16 |
|
17 |
+
# Copy data from backup to symlink if backup exists
|
18 |
+
echo "--- Copy data from backup to symlink if backup exists ---"
|
19 |
+
|
20 |
+
if [ -d "/home/node/app/packages/omni-server/data.local.org" ]; then
|
21 |
+
cp -a /home/node/app/packages/omni-server/data.local.org/. /home/node/app/packages/omni-server/data.local/
|
22 |
+
# Cleanup
|
23 |
+
rm -rf /home/node/app/packages/omni-server/data.local.org
|
24 |
+
echo "--- Cleanup done ---"
|
25 |
+
|
26 |
+
fi
|
27 |
+
else
|
28 |
+
echo "--- NO /data folder DETECTED, SKIPPING symlink creation ---"
|
29 |
+
fi
|
30 |
+
|
31 |
+
echo "--- YARN INSTALL ---"
|
32 |
+
yarn
|
33 |
+
|
34 |
+
echo "--- YARN START ---"
|
35 |
+
yarn start -u -rb -R blocks
|
packages/omni-server/scripts/huggingface.js
DELETED
@@ -1,309 +0,0 @@
|
|
1 |
-
//@ts-check
|
2 |
-
debugger;
|
3 |
-
import { client as gradio } from "@gradio/client";
|
4 |
-
|
5 |
-
const app_reference = 'manu-sapiens/gradio-api-test'; //'tomsoderlund/rest-api-with-gradio';
|
6 |
-
const options = { "hf_token": "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" };//{hf_token} Not needed for a public space, which is the case here.
|
7 |
-
|
8 |
-
//@ts-ignore
|
9 |
-
const app = await gradio(app_reference, options);
|
10 |
-
const config = app.config;
|
11 |
-
const root = app.config.root;
|
12 |
-
const root_url = app.config.root_url;
|
13 |
-
const app_id = app.config.app_id;
|
14 |
-
const skip_queue = !app.config.enable_queue;
|
15 |
-
const space_id = app.config.space_id;
|
16 |
-
const jwt = app.config.jwt;
|
17 |
-
|
18 |
-
debugger;
|
19 |
-
const view_api = await app.view_api();
|
20 |
-
console.warn(`huggingface API returned:\n ${JSON.stringify(view_api)}`);
|
21 |
-
|
22 |
-
const result = await predict("/predict", ["This is a test"]);
|
23 |
-
console.warn(result);
|
24 |
-
|
25 |
-
async function predict(endpoint, data, event_data = null)
|
26 |
-
{
|
27 |
-
debugger;
|
28 |
-
if (endpoint != '/predict')
|
29 |
-
{
|
30 |
-
throw new Error('endpoint must be /predict');
|
31 |
-
}
|
32 |
-
|
33 |
-
|
34 |
-
const app = await submit(data, event_data, jwt, skip_queue);
|
35 |
-
|
36 |
-
try
|
37 |
-
{
|
38 |
-
const result = await new Promise((resolve, reject) =>
|
39 |
-
{
|
40 |
-
app
|
41 |
-
.on("data", (d) =>
|
42 |
-
{
|
43 |
-
resolve(d);
|
44 |
-
})
|
45 |
-
.on("status", (status) =>
|
46 |
-
{
|
47 |
-
if (status.stage === "error")
|
48 |
-
{
|
49 |
-
reject(status);
|
50 |
-
}
|
51 |
-
});
|
52 |
-
});
|
53 |
-
|
54 |
-
app.destroy();
|
55 |
-
return result;
|
56 |
-
} catch (error)
|
57 |
-
{
|
58 |
-
app.destroy();
|
59 |
-
throw error;
|
60 |
-
}
|
61 |
-
}
|
62 |
-
|
63 |
-
|
64 |
-
async function submit(data, event_data, jwt, skip_queue = false)
|
65 |
-
{
|
66 |
-
let payload;
|
67 |
-
let complete = false;
|
68 |
-
const listener_map = {};
|
69 |
-
|
70 |
-
const _endpoint = "/predict";
|
71 |
-
|
72 |
-
const _payload = await handleBlob(_endpoint, data);
|
73 |
-
|
74 |
-
let websocket;
|
75 |
-
|
76 |
-
payload = { data: _payload || [], event_data };
|
77 |
-
|
78 |
-
|
79 |
-
if (skip_queue)
|
80 |
-
{
|
81 |
-
await processImmediateCall(_endpoint, payload);
|
82 |
-
} else
|
83 |
-
{
|
84 |
-
await processQueueCall(_endpoint, payload, "wss", jwt);
|
85 |
-
}
|
86 |
-
|
87 |
-
|
88 |
-
return {
|
89 |
-
on(eventType, listener)
|
90 |
-
{
|
91 |
-
const listeners = listener_map[eventType] || [];
|
92 |
-
listener_map[eventType] = listeners;
|
93 |
-
listeners.push(listener);
|
94 |
-
return this;
|
95 |
-
},
|
96 |
-
off(eventType, listener)
|
97 |
-
{
|
98 |
-
let listeners = listener_map[eventType] || [];
|
99 |
-
listeners = listeners.filter((l) => l !== listener);
|
100 |
-
listener_map[eventType] = listeners;
|
101 |
-
return this;
|
102 |
-
},
|
103 |
-
async cancel()
|
104 |
-
{
|
105 |
-
const _status = { stage: "complete", queue: false };
|
106 |
-
|
107 |
-
//@ts-ignore
|
108 |
-
complete = _status;
|
109 |
-
fireEvent("status", { ..._status });
|
110 |
-
if (websocket && websocket.readyState === 0)
|
111 |
-
{
|
112 |
-
websocket.addEventListener("open", () =>
|
113 |
-
{
|
114 |
-
websocket.close();
|
115 |
-
});
|
116 |
-
} else
|
117 |
-
{
|
118 |
-
websocket.close();
|
119 |
-
}
|
120 |
-
try
|
121 |
-
{
|
122 |
-
await fetch(
|
123 |
-
`${http_protocol}//${host + config.path}/reset`,
|
124 |
-
{
|
125 |
-
headers: { "Content-Type": "application/json" },
|
126 |
-
method: "POST",
|
127 |
-
body: JSON.stringify({ session_hash }),
|
128 |
-
}
|
129 |
-
);
|
130 |
-
} catch (e)
|
131 |
-
{
|
132 |
-
console.warn(
|
133 |
-
"The `/reset` endpoint could not be called. Subsequent endpoint results may be unreliable."
|
134 |
-
);
|
135 |
-
}
|
136 |
-
},
|
137 |
-
destroy()
|
138 |
-
{
|
139 |
-
for (const eventType in listener_map)
|
140 |
-
{
|
141 |
-
listener_map[eventType].forEach((fn) =>
|
142 |
-
{
|
143 |
-
this.off(eventType, fn);
|
144 |
-
});
|
145 |
-
}
|
146 |
-
},
|
147 |
-
};
|
148 |
-
|
149 |
-
}
|
150 |
-
|
151 |
-
async function handleBlob(_endpoint, data)
|
152 |
-
{
|
153 |
-
const response = await handle_blob(
|
154 |
-
`${http_protocol}//${host + config.path}`,
|
155 |
-
data,
|
156 |
-
api.unnamed_endpoints[0],
|
157 |
-
hf_token
|
158 |
-
);
|
159 |
-
return transform_files
|
160 |
-
? transform_output(response.data, api.unnamed_endpoints[0], config.root, config.root_url)
|
161 |
-
: response.data;
|
162 |
-
}
|
163 |
-
|
164 |
-
async function processImmediateCall(_endpoint, payload)
|
165 |
-
{
|
166 |
-
fireEvent("status", { stage: "pending", queue: false });
|
167 |
-
const [output, status_code] = await post_data(
|
168 |
-
`${http_protocol}//${host + config.path}/run${_endpoint}`,
|
169 |
-
{ ...payload, session_hash },
|
170 |
-
hf_token
|
171 |
-
);
|
172 |
-
if (status_code == 200)
|
173 |
-
{
|
174 |
-
fireEvent("data", { data: output.data });
|
175 |
-
fireEvent("status", {
|
176 |
-
stage: "complete",
|
177 |
-
eta: output.average_duration,
|
178 |
-
queue: false,
|
179 |
-
});
|
180 |
-
} else
|
181 |
-
{
|
182 |
-
fireEvent("status", { stage: "error", message: output.error, queue: false });
|
183 |
-
}
|
184 |
-
}
|
185 |
-
|
186 |
-
async function processQueueCall(_endpoint, payload, ws_protocol = "wss", jwt = null)
|
187 |
-
{
|
188 |
-
fireEvent("status", { stage: "pending", queue: true });
|
189 |
-
const url = new URL(`${ws_protocol}://${host}${config.path}/queue/join`);
|
190 |
-
if (jwt)
|
191 |
-
{
|
192 |
-
url.searchParams.set("__sign", jwt);
|
193 |
-
}
|
194 |
-
const websocket = new WebSocket(url);
|
195 |
-
websocket.onclose = (evt) =>
|
196 |
-
{
|
197 |
-
if (!evt.wasClean)
|
198 |
-
{
|
199 |
-
fireEvent("status", {
|
200 |
-
stage: "error",
|
201 |
-
message: BROKEN_CONNECTION_MSG,
|
202 |
-
queue: true,
|
203 |
-
});
|
204 |
-
}
|
205 |
-
};
|
206 |
-
websocket.onmessage = function (event)
|
207 |
-
{
|
208 |
-
const _data = JSON.parse(event.data);
|
209 |
-
const { type, status, data } = handle_message(
|
210 |
-
_data,
|
211 |
-
last_status[0]
|
212 |
-
);
|
213 |
-
if (type === "update" && status && !complete)
|
214 |
-
{
|
215 |
-
fireEvent("status", { ...status });
|
216 |
-
if (status.stage === "error")
|
217 |
-
{
|
218 |
-
websocket.close();
|
219 |
-
}
|
220 |
-
} else if (type === "hash")
|
221 |
-
{
|
222 |
-
websocket.send(JSON.stringify({ session_hash }));
|
223 |
-
} else if (type === "data")
|
224 |
-
{
|
225 |
-
websocket.send(JSON.stringify({ ...payload, session_hash }));
|
226 |
-
} else if (type === "complete")
|
227 |
-
{
|
228 |
-
complete = status;
|
229 |
-
} else if (type === "generating")
|
230 |
-
{
|
231 |
-
fireEvent("status", { ...status, stage: status.stage, queue: true });
|
232 |
-
}
|
233 |
-
if (data)
|
234 |
-
{
|
235 |
-
fireEvent("data", {
|
236 |
-
data: transform_files
|
237 |
-
? transform_output(data.data, api.unnamed_endpoints[0], config.root, config.root_url)
|
238 |
-
: data.data,
|
239 |
-
});
|
240 |
-
if (complete)
|
241 |
-
{
|
242 |
-
fireEvent("status", { ...complete, stage: status.stage, queue: true });
|
243 |
-
websocket.close();
|
244 |
-
}
|
245 |
-
}
|
246 |
-
};
|
247 |
-
if (semiver(config.version || "2.0.0", "3.6") < 0)
|
248 |
-
{
|
249 |
-
addEventListener("open", () =>
|
250 |
-
websocket.send(JSON.stringify({ hash: session_hash }))
|
251 |
-
);
|
252 |
-
}
|
253 |
-
}
|
254 |
-
|
255 |
-
function fireEvent(eventType, eventData)
|
256 |
-
{
|
257 |
-
const listeners = listener_map[eventType] || [];
|
258 |
-
listeners.forEach((listener) => listener(eventData));
|
259 |
-
}
|
260 |
-
|
261 |
-
async function handle_blob(endpoint, data, api_info, token)
|
262 |
-
{
|
263 |
-
const blob_refs = await walk_and_store_blobs(data, undefined, [], true, api_info);
|
264 |
-
|
265 |
-
const processedData = await Promise.all(
|
266 |
-
blob_refs.map(async ({ path, blob, data, type }) =>
|
267 |
-
{
|
268 |
-
if (blob)
|
269 |
-
{
|
270 |
-
const file_url = (await upload_files(endpoint, [blob], token)).files[0];
|
271 |
-
return { path, file_url, type };
|
272 |
-
} else
|
273 |
-
{
|
274 |
-
return { path, base64: data, type };
|
275 |
-
}
|
276 |
-
})
|
277 |
-
);
|
278 |
-
|
279 |
-
processedData.forEach(({ path, file_url, base64, type }) =>
|
280 |
-
{
|
281 |
-
if (base64)
|
282 |
-
{
|
283 |
-
update_object(data, base64, path);
|
284 |
-
} else if (type === "Gallery")
|
285 |
-
{
|
286 |
-
update_object(data, file_url, path);
|
287 |
-
} else if (file_url)
|
288 |
-
{
|
289 |
-
const o = {
|
290 |
-
is_file: true,
|
291 |
-
name: `${file_url}`,
|
292 |
-
data: null
|
293 |
-
// orig_name: "file.csv"
|
294 |
-
};
|
295 |
-
update_object(data, o, path);
|
296 |
-
}
|
297 |
-
});
|
298 |
-
|
299 |
-
return data;
|
300 |
-
}
|
301 |
-
|
302 |
-
function skipQueue(id, config)
|
303 |
-
{
|
304 |
-
return (
|
305 |
-
!(config?.dependencies?.[id]?.queue === null
|
306 |
-
? config.enable_queue
|
307 |
-
: config?.dependencies?.[id]?.queue) || false
|
308 |
-
);
|
309 |
-
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
start.bat
ADDED
@@ -0,0 +1,37 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
@echo off
|
2 |
+
|
3 |
+
:: Check if node is installed
|
4 |
+
where node >nul 2>&1
|
5 |
+
if %errorlevel% neq 0 (
|
6 |
+
echo Node.js is not installed. Please install it from https://nodejs.org/
|
7 |
+
exit /b
|
8 |
+
)
|
9 |
+
|
10 |
+
:: Check if yarn is installed
|
11 |
+
where yarn >nul 2>&1
|
12 |
+
if %errorlevel% neq 0 (
|
13 |
+
echo yarn is not installed. After installing Node.js, please install yarn from https://classic.yarnpkg.com/en/docs/install/
|
14 |
+
exit /b
|
15 |
+
)
|
16 |
+
|
17 |
+
:: Check if git is installed
|
18 |
+
where git >nul 2>&1
|
19 |
+
if %errorlevel% neq 0 (
|
20 |
+
echo git is not installed. Please install it from https://git-scm.com/downloads
|
21 |
+
exit /b
|
22 |
+
)
|
23 |
+
|
24 |
+
:: Prompt user to update
|
25 |
+
set /p update="Before running Omnitool, do you want to update the project from Github first? (y/n) "
|
26 |
+
if /I "%update%"=="y" (
|
27 |
+
:: Pull latest changes from git
|
28 |
+
git pull
|
29 |
+
if %errorlevel% neq 0 (
|
30 |
+
echo Error occurred during git pull. Exiting.
|
31 |
+
exit /b
|
32 |
+
)
|
33 |
+
)
|
34 |
+
|
35 |
+
:: Run yarn commands
|
36 |
+
call yarn
|
37 |
+
call yarn start -u -rb %*
|
start.sh
CHANGED
@@ -1,3 +1,37 @@
|
|
1 |
#!/bin/bash
|
2 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
3 |
yarn start -u -rb "$@" # Pass all arguments to yarn start
|
|
|
1 |
#!/bin/bash
|
2 |
+
|
3 |
+
|
4 |
+
# Check if node is installed
|
5 |
+
if ! command -v node &> /dev/null; then
|
6 |
+
echo "Node.js is not installed. Please install it from https://nodejs.org/"
|
7 |
+
exit 1
|
8 |
+
fi
|
9 |
+
|
10 |
+
# Check if yarn is installed
|
11 |
+
if ! command -v yarn &> /dev/null; then
|
12 |
+
echo "yarn is not installed. After installing Node.js, please install yarn from https://classic.yarnpkg.com/en/docs/install/"
|
13 |
+
exit 1
|
14 |
+
fi
|
15 |
+
|
16 |
+
# Check if git is installed
|
17 |
+
if ! command -v git &> /dev/null; then
|
18 |
+
echo "git is not installed. Please install it from https://git-scm.com/downloads"
|
19 |
+
exit 1
|
20 |
+
fi
|
21 |
+
|
22 |
+
# Prompt user to update
|
23 |
+
read -p "Before running Omnitool, do you want to update the project from Github first? (y/n) " -n 1 -r
|
24 |
+
echo # move to a new line
|
25 |
+
|
26 |
+
if [[ $REPLY =~ ^[Yy]$ ]]; then
|
27 |
+
# Pull latest changes from git
|
28 |
+
git pull
|
29 |
+
if [ $? -ne 0 ]; then
|
30 |
+
echo "Error occurred during git pull. Exiting."
|
31 |
+
exit 1
|
32 |
+
fi
|
33 |
+
fi
|
34 |
+
|
35 |
+
# Run yarn commands
|
36 |
+
yarn
|
37 |
yarn start -u -rb "$@" # Pass all arguments to yarn start
|
yarn.lock
CHANGED
The diff for this file is too large to render.
See raw diff
|
|