Aensert06 commited on
Commit
e00a36a
·
verified ·
1 Parent(s): 2db02bc

Upload entrypoint.sh

Browse files
Files changed (1) hide show
  1. entrypoint.sh +10 -331
entrypoint.sh CHANGED
@@ -1,336 +1,15 @@
1
  #!/bin/sh
 
2
  set -e
3
 
4
- CONFIG_FILE="${APP_HOME}/config.yaml"
 
5
 
6
- # Priority 1: Use USERNAME/PASSWORD if both are provided
7
- if [ -n "${USERNAME}" ] && [ -n "${PASSWORD}" ]; then
8
- echo "--- Basic auth enabled: Creating config.yaml with provided credentials. ---"
9
-
10
- cat <<EOT > ${CONFIG_FILE}
11
- dataRoot: ./data
12
- listen: true
13
- listenAddress:
14
- ipv4: 0.0.0.0
15
- ipv6: '[::]'
16
- protocol:
17
- ipv4: true
18
- ipv6: false
19
- dnsPreferIPv6: false
20
- autorunHostname: "auto"
21
- port: 8000
22
- autorunPortOverride: -1
23
- ssl:
24
- enabled: false
25
- certPath: "./certs/cert.pem"
26
- keyPath: "./certs/privkey.pem"
27
- whitelistMode: false
28
- enableForwardedWhitelist: false
29
- whitelist:
30
- - ::1
31
- - 127.0.0.1
32
- whitelistDockerHosts: true
33
- basicAuthMode: true
34
- basicAuthUser:
35
- username: "${USERNAME}"
36
- password: "${PASSWORD}"
37
- enableCorsProxy: false
38
- requestProxy:
39
- enabled: false
40
- url: "socks5://username:password@example.com:1080"
41
- bypass:
42
- - localhost
43
- - 127.0.0.1
44
- enableUserAccounts: false
45
- enableDiscreetLogin: false
46
- autheliaAuth: false
47
- perUserBasicAuth: false
48
- sessionTimeout: -1
49
- disableCsrfProtection: false
50
- securityOverride: false
51
- logging:
52
- enableAccessLog: true
53
- minLogLevel: 0
54
- rateLimiting:
55
- preferRealIpHeader: false
56
- autorun: false
57
- avoidLocalhost: false
58
- backups:
59
- common:
60
- numberOfBackups: 50
61
- chat:
62
- enabled: true
63
- checkIntegrity: true
64
- maxTotalBackups: -1
65
- throttleInterval: 10000
66
- thumbnails:
67
- enabled: true
68
- format: "jpg"
69
- quality: 95
70
- dimensions: { 'bg': [160, 90], 'avatar': [96, 144] }
71
- performance:
72
- lazyLoadCharacters: false
73
- memoryCacheCapacity: '100mb'
74
- useDiskCache: true
75
- allowKeysExposure: true
76
- skipContentCheck: false
77
- whitelistImportDomains:
78
- - localhost
79
- - cdn.discordapp.com
80
- - files.catbox.moe
81
- - raw.githubusercontent.com
82
- requestOverrides: []
83
- extensions:
84
- enabled: true
85
- autoUpdate: false
86
- models:
87
- autoDownload: true
88
- classification: Cohee/distilbert-base-uncased-go-emotions-onnx
89
- captioning: Xenova/vit-gpt2-image-captioning
90
- embedding: Cohee/jina-embeddings-v2-base-en
91
- speechToText: Xenova/whisper-small
92
- textToSpeech: Xenova/speecht5_tts
93
- enableDownloadableTokenizers: true
94
- promptPlaceholder: "[Start a new chat]"
95
- openai:
96
- randomizeUserId: false
97
- captionSystemPrompt: ""
98
- deepl:
99
- formality: default
100
- mistral:
101
- enablePrefix: false
102
- ollama:
103
- keepAlive: -1
104
- batchSize: -1
105
- claude:
106
- enableSystemPromptCache: false
107
- cachingAtDepth: -1
108
- enableServerPlugins: true
109
- enableServerPluginsAutoUpdate: false
110
- EOT
111
 
112
- # Priority 2: Use CONFIG_YAML if provided (and username/password are not)
113
- elif [ -n "${CONFIG_YAML}" ]; then
114
- echo "--- Found CONFIG_YAML, creating config.yaml from environment variable. ---"
115
- printf '%s\n' "${CONFIG_YAML}" > ${CONFIG_FILE}
116
-
117
- # Priority 3: No config provided, let the app use its defaults
118
- else
119
- echo "--- No user/pass or CONFIG_YAML provided. App will use its default settings. ---"
120
- fi
121
-
122
- # --- BEGIN: Update SillyTavern Core at Runtime ---
123
- echo '--- Attempting to update SillyTavern Core from GitHub (staging branch) ---'
124
- if [ -d ".git" ] && [ "$(git rev-parse --abbrev-ref HEAD)" = "staging" ]; then
125
- echo 'Existing staging branch found. Resetting and pulling latest changes...'
126
- git reset --hard HEAD && \
127
- git pull origin staging || echo 'WARN: git pull failed, continuing with code from build time.'
128
- echo '--- SillyTavern Core update check finished. ---'
129
- else
130
- echo 'WARN: .git directory not found or not on staging branch. Skipping runtime update. Code from build time will be used.'
131
- fi
132
- # --- END: Update SillyTavern Core at Runtime ---
133
-
134
- # --- BEGIN: Configure Git default identity at Runtime ---
135
- echo '--- Configuring Git default user identity at runtime ---'
136
- git config --global user.name "SillyTavern Sync" && \
137
- git config --global user.email "sillytavern-sync@example.com" && \
138
- git config --global --add safe.directory "${APP_HOME}/data"
139
- echo '--- Git identity configured for runtime user. ---'
140
- # --- END: Configure Git default identity at Runtime ---
141
-
142
- # --- BEGIN: Dynamically Install Plugins at Runtime ---
143
- echo '--- Checking for PLUGINS environment variable ---'
144
- if [ -n "$PLUGINS" ]; then
145
- echo "*** Installing Plugins specified in PLUGINS environment variable: $PLUGINS ***"
146
- # Ensure plugins directory exists
147
- mkdir -p ./plugins && chown node:node ./plugins
148
- # Set comma as delimiter
149
- IFS=','
150
- # Loop through each plugin URL
151
- for plugin_url in $PLUGINS; do
152
- # Trim leading/trailing whitespace
153
- plugin_url=$(echo "$plugin_url" | sed 's/^[[:space:]]*//;s/[[:space:]]*$//')
154
- if [ -z "$plugin_url" ]; then continue; fi
155
- # Extract plugin name
156
- plugin_name_git=$(basename "$plugin_url")
157
- plugin_name=${plugin_name_git%.git}
158
- plugin_dir="./plugins/$plugin_name"
159
- echo "--- Installing plugin: $plugin_name from $plugin_url into $plugin_dir ---"
160
- # Remove existing dir if it exists
161
- rm -rf "$plugin_dir"
162
- # Clone the plugin (run as root, fix perms later)
163
- git clone --depth 1 "$plugin_url" "$plugin_dir"
164
- if [ -f "$plugin_dir/package.json" ]; then
165
- echo "--- Installing dependencies for $plugin_name ---"
166
- (cd "$plugin_dir" && npm install --no-audit --no-fund --loglevel=error --no-progress --omit=dev --force && npm cache clean --force) || echo "WARN: Failed to install dependencies for $plugin_name"
167
- else
168
- echo "--- No package.json found for $plugin_name, skipping dependency install. ---"
169
- fi || echo "WARN: Failed to clone $plugin_name from $plugin_url, skipping..."
170
-
171
- # Configure cloud-saves plugin if this is the cloud-saves plugin
172
- if [ "$plugin_name" = "cloud-saves" ]; then
173
- echo "--- Detected cloud-saves plugin, checking for configuration environment variables ---"
174
-
175
- # Set default values
176
- REPO_URL_VALUE=${REPO_URL:-"https://github.com/fuwei99/sillytravern"}
177
- GITHUB_TOKEN_VALUE=${GITHUB_TOKEN:-""}
178
- AUTOSAVE_INTERVAL_VALUE=${AUTOSAVE_INTERVAL:-30}
179
- AUTOSAVE_TARGET_TAG_VALUE=${AUTOSAVE_TARGET_TAG:-""}
180
-
181
- # Always set autosave to false as required
182
- AUTOSAVE_ENABLED="false"
183
-
184
- echo "--- Creating cloud-saves plugin configuration file ---"
185
- CONFIG_JSON_FILE="$plugin_dir/config.json"
186
-
187
- # Generate config.json file
188
- cat <<EOT > ${CONFIG_JSON_FILE}
189
- {
190
- "repo_url": "${REPO_URL_VALUE}",
191
- "branch": "main",
192
- "username": "cloud-saves",
193
- "github_token": "${GITHUB_TOKEN_VALUE}",
194
- "display_name": "",
195
- "is_authorized": true,
196
- "last_save": null,
197
- "current_save": null,
198
- "has_temp_stash": false,
199
- "autoSaveEnabled": ${AUTOSAVE_ENABLED},
200
- "autoSaveInterval": ${AUTOSAVE_INTERVAL_VALUE},
201
- "autoSaveTargetTag": "${AUTOSAVE_TARGET_TAG_VALUE}"
202
- }
203
- EOT
204
-
205
- # Set correct permissions for config file
206
- chown node:node ${CONFIG_JSON_FILE}
207
-
208
- echo "--- cloud-saves plugin configuration file created at: ${CONFIG_JSON_FILE} ---"
209
- fi
210
- done
211
- # Reset IFS
212
- unset IFS
213
- # Fix permissions for plugins directory after installation
214
- echo "--- Setting permissions for plugins directory ---"
215
- chown -R node:node ./plugins
216
- echo "*** Plugin installation finished. ***"
217
- else
218
- echo 'PLUGINS environment variable is not set or empty, skipping runtime plugin installation.'
219
- fi
220
- # --- END: Dynamically Install Plugins at Runtime ---
221
-
222
- echo "*** Starting SillyTavern... ***"
223
- node ${APP_HOME}/server.js &
224
- SERVER_PID=$!
225
-
226
- echo "SillyTavern server started with PID ${SERVER_PID}. Waiting for it to become responsive..."
227
-
228
- # --- Health Check Logic ---
229
- HEALTH_CHECK_URL="http://localhost:8000/"
230
- CURL_COMMAND="curl -sf"
231
-
232
- # If basic auth is enabled, provide credentials to curl for health checks
233
- if [ -n "${USERNAME}" ] && [ -n "${PASSWORD}" ]; then
234
- echo "--- Health check will use basic auth credentials. ---"
235
- # The -u flag provides user:password for basic auth
236
- CURL_COMMAND="curl -sf -u \"${USERNAME}:${PASSWORD}\""
237
- fi
238
-
239
- # Health check loop
240
- RETRY_COUNT=0
241
- MAX_RETRIES=12 # Wait for 60 seconds max
242
- # Use eval to correctly execute the command string with quotes
243
- while ! eval "${CURL_COMMAND} ${HEALTH_CHECK_URL}" > /dev/null; do
244
- RETRY_COUNT=$((RETRY_COUNT+1))
245
- if [ ${RETRY_COUNT} -ge ${MAX_RETRIES} ]; then
246
- echo "SillyTavern failed to start. Exiting."
247
- kill ${SERVER_PID}
248
- exit 1
249
- fi
250
- echo "SillyTavern is still starting or not responsive on port 8000, waiting 5 seconds..."
251
- sleep 5
252
- done
253
-
254
- echo "SillyTavern started successfully! Beginning periodic keep-alive..."
255
-
256
- # --- BEGIN: Install Extensions after SillyTavern startup ---
257
- install_extensions() {
258
- echo "--- Waiting 40 seconds before installing extensions... ---"
259
- sleep 40
260
-
261
- echo "--- Checking for EXTENSIONS environment variable ---"
262
- if [ -n "$EXTENSIONS" ]; then
263
- echo "*** Installing Extensions specified in EXTENSIONS environment variable: $EXTENSIONS ***"
264
-
265
- # Determine installation directory based on INSTALL_FOR_ALL_USERS
266
- if [ "$INSTALL_FOR_ALL_USERS" = "true" ]; then
267
- # System-level installation (for all users)
268
- EXTENSIONS_DIR="./public/scripts/extensions/third-party"
269
- echo "Installing extensions for all users in: $EXTENSIONS_DIR"
270
- else
271
- # User-level installation (for default user only)
272
- EXTENSIONS_DIR="./data/default-user/extensions"
273
- echo "Installing extensions for default user in: $EXTENSIONS_DIR"
274
- fi
275
-
276
- # Ensure extensions directory exists
277
- mkdir -p "$EXTENSIONS_DIR" && chown node:node "$EXTENSIONS_DIR"
278
-
279
- # Set comma as delimiter
280
- IFS=','
281
-
282
- # Loop through each extension URL
283
- for extension_url in $EXTENSIONS; do
284
- # Trim leading/trailing whitespace
285
- extension_url=$(echo "$extension_url" | sed 's/^[[:space:]]*//;s/[[:space:]]*$//')
286
- if [ -z "$extension_url" ]; then continue; fi
287
-
288
- # Extract extension name
289
- extension_name_git=$(basename "$extension_url")
290
- extension_name=${extension_name_git%.git}
291
- extension_dir="$EXTENSIONS_DIR/$extension_name"
292
-
293
- echo "--- Installing extension: $extension_name from $extension_url into $extension_dir ---"
294
-
295
- # Remove existing dir if it exists
296
- rm -rf "$extension_dir"
297
-
298
- # Clone the extension
299
- git clone --depth 1 "$extension_url" "$extension_dir"
300
-
301
- # Check if extension has package.json and install dependencies if needed
302
- if [ -f "$extension_dir/package.json" ]; then
303
- echo "--- Installing dependencies for $extension_name ---"
304
- (cd "$extension_dir" && npm install --no-audit --no-fund --loglevel=error --no-progress --omit=dev --force && npm cache clean --force) || echo "WARN: Failed to install dependencies for $extension_name"
305
- else
306
- echo "--- No package.json found for $extension_name, skipping dependency install. ---"
307
- fi || echo "WARN: Failed to clone $extension_name from $extension_url, skipping..."
308
- done
309
-
310
- # Reset IFS
311
- unset IFS
312
-
313
- # Fix permissions for extensions directory after installation
314
- echo "--- Setting permissions for extensions directory ---"
315
- chown -R node:node "$EXTENSIONS_DIR"
316
-
317
- echo "*** Extensions installation finished. ***"
318
- else
319
- echo 'EXTENSIONS environment variable is not set or empty, skipping extensions installation.'
320
- fi
321
- }
322
-
323
- # Run the extension installation in the background
324
- install_extensions &
325
- # --- END: Install Extensions after SillyTavern startup ---
326
-
327
- # Keep-alive loop
328
- while kill -0 ${SERVER_PID} 2>/dev/null; do
329
- echo "Sending keep-alive request to ${HEALTH_CHECK_URL}"
330
- # Use eval here as well for the keep-alive command
331
- eval "${CURL_COMMAND} ${HEALTH_CHECK_URL}" > /dev/null || echo "Keep-alive request failed."
332
- echo "Keep-alive request sent. Sleeping for 30 minutes."
333
- sleep 1800
334
- done &
335
-
336
- wait ${SERVER_PID}
 
1
  #!/bin/sh
2
+ # This script runs inside the container when it starts.
3
  set -e
4
 
5
+ # 1. Generate the initial config.yaml from the template and environment variables (Secrets).
6
+ envsubst < /home/node/app/config.template.yaml > /home/node/app/config.yaml
7
 
8
+ # 2. Forcibly set all necessary plugin-related configurations.
9
+ sed -i 's/^ *whitelistMode:.*$/whitelistMode: false/' /home/node/app/config.yaml
10
+ sed -i 's/^ *enableServerPlugins:.*$/enableServerPlugins: true/' /home/node/app/config.yaml
11
+ sed -i 's/^ *enableServerPluginsAutoUpdate:.*$/enableServerPluginsAutoUpdate: false/' /home/node/app/config.yaml
12
+ sed -i 's/^ *extensions\.enabled:.*$/extensions.enabled: true/' /home/node/app/config.yaml
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
13
 
14
+ # 3. Start the main application.
15
+ exec node server.js