Sync local changes
This commit is contained in:
parent
74bfcc218b
commit
577ef68dad
18 changed files with 1584 additions and 6 deletions
135
.github/workflows/desktop-release.yml
vendored
Normal file
135
.github/workflows/desktop-release.yml
vendored
Normal file
|
|
@ -0,0 +1,135 @@
|
||||||
|
name: Build Desktop App
|
||||||
|
|
||||||
|
on:
|
||||||
|
push:
|
||||||
|
tags:
|
||||||
|
- 'v*'
|
||||||
|
workflow_dispatch:
|
||||||
|
inputs:
|
||||||
|
version:
|
||||||
|
description: 'Version to build (e.g., 0.1.0)'
|
||||||
|
required: false
|
||||||
|
default: ''
|
||||||
|
|
||||||
|
permissions:
|
||||||
|
contents: write
|
||||||
|
|
||||||
|
jobs:
|
||||||
|
build-windows:
|
||||||
|
runs-on: windows-latest
|
||||||
|
steps:
|
||||||
|
- name: Checkout code
|
||||||
|
uses: actions/checkout@v4
|
||||||
|
|
||||||
|
- name: Setup Node.js
|
||||||
|
uses: actions/setup-node@v4
|
||||||
|
with:
|
||||||
|
node-version: '20'
|
||||||
|
cache: 'npm'
|
||||||
|
|
||||||
|
- name: Install dependencies
|
||||||
|
run: npm ci
|
||||||
|
|
||||||
|
- name: Build desktop renderer
|
||||||
|
run: npm run build:desktop
|
||||||
|
|
||||||
|
- name: Build Windows installer
|
||||||
|
run: npx electron-builder --win --config electron-builder.yml
|
||||||
|
env:
|
||||||
|
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
||||||
|
|
||||||
|
- name: Upload Windows artifact
|
||||||
|
uses: actions/upload-artifact@v4
|
||||||
|
with:
|
||||||
|
name: windows-build
|
||||||
|
path: dist/*.exe
|
||||||
|
retention-days: 5
|
||||||
|
|
||||||
|
build-macos:
|
||||||
|
runs-on: macos-latest
|
||||||
|
steps:
|
||||||
|
- name: Checkout code
|
||||||
|
uses: actions/checkout@v4
|
||||||
|
|
||||||
|
- name: Setup Node.js
|
||||||
|
uses: actions/setup-node@v4
|
||||||
|
with:
|
||||||
|
node-version: '20'
|
||||||
|
cache: 'npm'
|
||||||
|
|
||||||
|
- name: Install dependencies
|
||||||
|
run: npm ci
|
||||||
|
|
||||||
|
- name: Build desktop renderer
|
||||||
|
run: npm run build:desktop
|
||||||
|
|
||||||
|
- name: Build macOS installer
|
||||||
|
run: npx electron-builder --mac --config electron-builder.yml
|
||||||
|
env:
|
||||||
|
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
||||||
|
|
||||||
|
- name: Upload macOS artifact
|
||||||
|
uses: actions/upload-artifact@v4
|
||||||
|
with:
|
||||||
|
name: macos-build
|
||||||
|
path: dist/*.dmg
|
||||||
|
retention-days: 5
|
||||||
|
|
||||||
|
build-linux:
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
steps:
|
||||||
|
- name: Checkout code
|
||||||
|
uses: actions/checkout@v4
|
||||||
|
|
||||||
|
- name: Setup Node.js
|
||||||
|
uses: actions/setup-node@v4
|
||||||
|
with:
|
||||||
|
node-version: '20'
|
||||||
|
cache: 'npm'
|
||||||
|
|
||||||
|
- name: Install dependencies
|
||||||
|
run: npm ci
|
||||||
|
|
||||||
|
- name: Build desktop renderer
|
||||||
|
run: npm run build:desktop
|
||||||
|
|
||||||
|
- name: Build Linux installers
|
||||||
|
run: npx electron-builder --linux --config electron-builder.yml
|
||||||
|
env:
|
||||||
|
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
||||||
|
|
||||||
|
- name: Upload Linux artifacts
|
||||||
|
uses: actions/upload-artifact@v4
|
||||||
|
with:
|
||||||
|
name: linux-build
|
||||||
|
path: |
|
||||||
|
dist/*.AppImage
|
||||||
|
dist/*.deb
|
||||||
|
retention-days: 5
|
||||||
|
|
||||||
|
release:
|
||||||
|
needs: [build-windows, build-macos, build-linux]
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
if: startsWith(github.ref, 'refs/tags/v')
|
||||||
|
steps:
|
||||||
|
- name: Download all artifacts
|
||||||
|
uses: actions/download-artifact@v4
|
||||||
|
with:
|
||||||
|
path: artifacts
|
||||||
|
|
||||||
|
- name: Display downloaded files
|
||||||
|
run: ls -R artifacts
|
||||||
|
|
||||||
|
- name: Create GitHub Release
|
||||||
|
uses: softprops/action-gh-release@v2
|
||||||
|
with:
|
||||||
|
draft: false
|
||||||
|
prerelease: ${{ contains(github.ref_name, 'beta') || contains(github.ref_name, 'alpha') }}
|
||||||
|
generate_release_notes: true
|
||||||
|
files: |
|
||||||
|
artifacts/windows-build/*.exe
|
||||||
|
artifacts/macos-build/*.dmg
|
||||||
|
artifacts/linux-build/*.AppImage
|
||||||
|
artifacts/linux-build/*.deb
|
||||||
|
env:
|
||||||
|
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
||||||
6
.replit
6
.replit
|
|
@ -5,6 +5,7 @@ integrations = ["javascript_gemini_ai_integrations:1.0.0"]
|
||||||
|
|
||||||
[nix]
|
[nix]
|
||||||
channel = "stable-25_05"
|
channel = "stable-25_05"
|
||||||
|
packages = ["imagemagick"]
|
||||||
|
|
||||||
[workflows]
|
[workflows]
|
||||||
runButton = "Project"
|
runButton = "Project"
|
||||||
|
|
@ -53,6 +54,10 @@ externalPort = 80
|
||||||
localPort = 8044
|
localPort = 8044
|
||||||
externalPort = 3003
|
externalPort = 3003
|
||||||
|
|
||||||
|
[[ports]]
|
||||||
|
localPort = 8080
|
||||||
|
externalPort = 8080
|
||||||
|
|
||||||
[[ports]]
|
[[ports]]
|
||||||
localPort = 38557
|
localPort = 38557
|
||||||
externalPort = 3000
|
externalPort = 3000
|
||||||
|
|
@ -70,3 +75,4 @@ build = ["npm", "run", "build"]
|
||||||
|
|
||||||
[userenv.shared]
|
[userenv.shared]
|
||||||
DISCORD_MAIN_CHAT_CHANNELS = "1425114041021497454"
|
DISCORD_MAIN_CHAT_CHANNELS = "1425114041021497454"
|
||||||
|
MAINTENANCE_MODE = "true"
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,95 @@
|
||||||
|
17s
|
||||||
|
12s
|
||||||
|
Run npx electron-builder --win --config electron-builder.yml
|
||||||
|
|
||||||
|
• electron-builder version=25.1.8 os=10.0.26100
|
||||||
|
• artifacts will be published reason=tag is defined tag=v0.1.1
|
||||||
|
• loaded configuration file=D:\a\aethex-forge\aethex-forge\electron-builder.yml
|
||||||
|
• skipped dependencies rebuild reason=npmRebuild is set to false
|
||||||
|
• packaging platform=win32 arch=x64 electron=32.3.3 appOutDir=dist\win-unpacked
|
||||||
|
• downloading url=https://github.com/electron/electron/releases/download/v32.3.3/electron-v32.3.3-win32-x64.zip size=113 MB parts=8
|
||||||
|
• downloaded url=https://github.com/electron/electron/releases/download/v32.3.3/electron-v32.3.3-win32-x64.zip duration=449ms
|
||||||
|
• updating asar integrity executable resource executablePath=dist\win-unpacked\AeThex Desktop Terminal.exe
|
||||||
|
⨯ icon directory D:\a\aethex-forge\aethex-forge\build\icons doesn't contain icons
|
||||||
|
github.com/develar/app-builder/pkg/icons.CollectIcons
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/collect-icons.go:73
|
||||||
|
github.com/develar/app-builder/pkg/icons.doConvertIcon
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:199
|
||||||
|
github.com/develar/app-builder/pkg/icons.ConvertIcon
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:56
|
||||||
|
github.com/develar/app-builder/pkg/icons.ConfigureCommand.func1
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:33
|
||||||
|
github.com/alecthomas/kingpin.(*actionMixin).applyActions
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/actions.go:28
|
||||||
|
github.com/alecthomas/kingpin.(*Application).applyActions
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:557
|
||||||
|
github.com/alecthomas/kingpin.(*Application).execute
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:390
|
||||||
|
github.com/alecthomas/kingpin.(*Application).Parse
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:222
|
||||||
|
main.main
|
||||||
|
/Users/runner/work/app-builder/app-builder/main.go:90
|
||||||
|
runtime.main
|
||||||
|
/Users/runner/hostedtoolcache/go/1.21.13/arm64/src/runtime/proc.go:267
|
||||||
|
runtime.goexit
|
||||||
|
/Users/runner/hostedtoolcache/go/1.21.13/arm64/src/runtime/asm_amd64.s:1650
|
||||||
|
github.com/develar/app-builder/pkg/icons.doConvertIcon
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:201
|
||||||
|
github.com/develar/app-builder/pkg/icons.ConvertIcon
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:56
|
||||||
|
github.com/develar/app-builder/pkg/icons.ConfigureCommand.func1
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:33
|
||||||
|
github.com/alecthomas/kingpin.(*actionMixin).applyActions
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/actions.go:28
|
||||||
|
github.com/alecthomas/kingpin.(*Application).applyActions
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:557
|
||||||
|
github.com/alecthomas/kingpin.(*Application).execute
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:390
|
||||||
|
github.com/alecthomas/kingpin.(*Application).Parse
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:222
|
||||||
|
main.main
|
||||||
|
/Users/runner/work/app-builder/app-builder/main.go:90
|
||||||
|
runtime.main
|
||||||
|
/Users/runner/hostedtoolcache/go/1.21.13/arm64/src/runtime/proc.go:267
|
||||||
|
runtime.goexit
|
||||||
|
/Users/runner/hostedtoolcache/go/1.21.13/arm64/src/runtime/asm_amd64.s:1650
|
||||||
|
⨯ D:\a\aethex-forge\aethex-forge\node_modules\app-builder-bin\win\x64\app-builder.exe process failed ERR_ELECTRON_BUILDER_CANNOT_EXECUTE
|
||||||
|
Exit code:
|
||||||
|
1 failedTask=build stackTrace=Error: D:\a\aethex-forge\aethex-forge\node_modules\app-builder-bin\win\x64\app-builder.exe process failed ERR_ELECTRON_BUILDER_CANNOT_EXECUTE
|
||||||
|
Exit code:
|
||||||
|
1
|
||||||
|
at ChildProcess.<anonymous> (D:\a\aethex-forge\aethex-forge\node_modules\builder-util\src\util.ts:255:14)
|
||||||
|
at Object.onceWrapper (node:events:639:26)
|
||||||
|
at ChildProcess.emit (node:events:524:28)
|
||||||
|
at ChildProcess.cp.emit (D:\a\aethex-forge\aethex-forge\node_modules\cross-spawn\lib\enoent.js:34:29)
|
||||||
|
at maybeClose (node:internal/child_process:1104:16)
|
||||||
|
at Process.ChildProcess._handle.onexit (node:internal/child_process:304:5)
|
||||||
|
From previous event:
|
||||||
|
at processImmediate (node:internal/timers:483:21)
|
||||||
|
From previous event:
|
||||||
|
at WinPackager.signApp (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\winPackager.ts:270:27)
|
||||||
|
at WinPackager.doSignAfterPack (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\platformPackager.ts:346:32)
|
||||||
|
at WinPackager.doPack (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\platformPackager.ts:331:7)
|
||||||
|
at WinPackager.pack (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\platformPackager.ts:138:5)
|
||||||
|
at Packager.doBuild (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\packager.ts:459:9)
|
||||||
|
at executeFinally (D:\a\aethex-forge\aethex-forge\node_modules\builder-util\src\promise.ts:12:14)
|
||||||
|
at Packager.build (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\packager.ts:393:31)
|
||||||
|
at executeFinally (D:\a\aethex-forge\aethex-forge\node_modules\builder-util\src\promise.ts:12:14)
|
||||||
|
Error: Process completed with exit code 1.
|
||||||
|
0s
|
||||||
|
0s
|
||||||
|
2s
|
||||||
|
Post job cleanup.
|
||||||
|
"C:\Program Files\Git\bin\git.exe" version
|
||||||
|
git version 2.52.0.windows.1
|
||||||
|
Temporarily overriding HOME='D:\a\_temp\4963c2ff-b212-40d1-906e-719e33666ab2' before making global git config changes
|
||||||
|
Adding repository directory to the temporary git global config as a safe directory
|
||||||
|
"C:\Program Files\Git\bin\git.exe" config --global --add safe.directory D:\a\aethex-forge\aethex-forge
|
||||||
|
"C:\Program Files\Git\bin\git.exe" config --local --name-only --get-regexp core\.sshCommand
|
||||||
|
"C:\Program Files\Git\bin\git.exe" submodule foreach --recursive "sh -c \"git config --local --name-only --get-regexp 'core\.sshCommand' && git config --local --unset-all 'core.sshCommand' || :\""
|
||||||
|
"C:\Program Files\Git\bin\git.exe" config --local --name-only --get-regexp http\.https\:\/\/github\.com\/\.extraheader
|
||||||
|
http.https://github.com/.extraheader
|
||||||
|
"C:\Program Files\Git\bin\git.exe" config --local --unset-all http.https://github.com/.extraheader
|
||||||
|
"C:\Program Files\Git\bin\git.exe" submodule foreach --recursive "sh -c \"git config --local --name-only --get-regexp 'http\.https\:\/\/github\.com\/\.extraheader' && git config --local --unset-all 'http.https://github.com/.extraheader' || :\""
|
||||||
|
"C:\Program Files\Git\bin\git.exe" config --local --name-only --get-regexp ^includeIf\.gitdir:
|
||||||
|
"C:\Program Files\Git\bin\git.exe" submodule foreach --recursive "git config --local --show-origin --name-only --get-regexp remote.origin.url"
|
||||||
|
|
@ -0,0 +1,95 @@
|
||||||
|
17s
|
||||||
|
12s
|
||||||
|
Run npx electron-builder --win --config electron-builder.yml
|
||||||
|
|
||||||
|
• electron-builder version=25.1.8 os=10.0.26100
|
||||||
|
• artifacts will be published reason=tag is defined tag=v0.1.1
|
||||||
|
• loaded configuration file=D:\a\aethex-forge\aethex-forge\electron-builder.yml
|
||||||
|
• skipped dependencies rebuild reason=npmRebuild is set to false
|
||||||
|
• packaging platform=win32 arch=x64 electron=32.3.3 appOutDir=dist\win-unpacked
|
||||||
|
• downloading url=https://github.com/electron/electron/releases/download/v32.3.3/electron-v32.3.3-win32-x64.zip size=113 MB parts=8
|
||||||
|
• downloaded url=https://github.com/electron/electron/releases/download/v32.3.3/electron-v32.3.3-win32-x64.zip duration=449ms
|
||||||
|
• updating asar integrity executable resource executablePath=dist\win-unpacked\AeThex Desktop Terminal.exe
|
||||||
|
⨯ icon directory D:\a\aethex-forge\aethex-forge\build\icons doesn't contain icons
|
||||||
|
github.com/develar/app-builder/pkg/icons.CollectIcons
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/collect-icons.go:73
|
||||||
|
github.com/develar/app-builder/pkg/icons.doConvertIcon
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:199
|
||||||
|
github.com/develar/app-builder/pkg/icons.ConvertIcon
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:56
|
||||||
|
github.com/develar/app-builder/pkg/icons.ConfigureCommand.func1
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:33
|
||||||
|
github.com/alecthomas/kingpin.(*actionMixin).applyActions
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/actions.go:28
|
||||||
|
github.com/alecthomas/kingpin.(*Application).applyActions
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:557
|
||||||
|
github.com/alecthomas/kingpin.(*Application).execute
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:390
|
||||||
|
github.com/alecthomas/kingpin.(*Application).Parse
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:222
|
||||||
|
main.main
|
||||||
|
/Users/runner/work/app-builder/app-builder/main.go:90
|
||||||
|
runtime.main
|
||||||
|
/Users/runner/hostedtoolcache/go/1.21.13/arm64/src/runtime/proc.go:267
|
||||||
|
runtime.goexit
|
||||||
|
/Users/runner/hostedtoolcache/go/1.21.13/arm64/src/runtime/asm_amd64.s:1650
|
||||||
|
github.com/develar/app-builder/pkg/icons.doConvertIcon
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:201
|
||||||
|
github.com/develar/app-builder/pkg/icons.ConvertIcon
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:56
|
||||||
|
github.com/develar/app-builder/pkg/icons.ConfigureCommand.func1
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:33
|
||||||
|
github.com/alecthomas/kingpin.(*actionMixin).applyActions
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/actions.go:28
|
||||||
|
github.com/alecthomas/kingpin.(*Application).applyActions
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:557
|
||||||
|
github.com/alecthomas/kingpin.(*Application).execute
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:390
|
||||||
|
github.com/alecthomas/kingpin.(*Application).Parse
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:222
|
||||||
|
main.main
|
||||||
|
/Users/runner/work/app-builder/app-builder/main.go:90
|
||||||
|
runtime.main
|
||||||
|
/Users/runner/hostedtoolcache/go/1.21.13/arm64/src/runtime/proc.go:267
|
||||||
|
runtime.goexit
|
||||||
|
/Users/runner/hostedtoolcache/go/1.21.13/arm64/src/runtime/asm_amd64.s:1650
|
||||||
|
⨯ D:\a\aethex-forge\aethex-forge\node_modules\app-builder-bin\win\x64\app-builder.exe process failed ERR_ELECTRON_BUILDER_CANNOT_EXECUTE
|
||||||
|
Exit code:
|
||||||
|
1 failedTask=build stackTrace=Error: D:\a\aethex-forge\aethex-forge\node_modules\app-builder-bin\win\x64\app-builder.exe process failed ERR_ELECTRON_BUILDER_CANNOT_EXECUTE
|
||||||
|
Exit code:
|
||||||
|
1
|
||||||
|
at ChildProcess.<anonymous> (D:\a\aethex-forge\aethex-forge\node_modules\builder-util\src\util.ts:255:14)
|
||||||
|
at Object.onceWrapper (node:events:639:26)
|
||||||
|
at ChildProcess.emit (node:events:524:28)
|
||||||
|
at ChildProcess.cp.emit (D:\a\aethex-forge\aethex-forge\node_modules\cross-spawn\lib\enoent.js:34:29)
|
||||||
|
at maybeClose (node:internal/child_process:1104:16)
|
||||||
|
at Process.ChildProcess._handle.onexit (node:internal/child_process:304:5)
|
||||||
|
From previous event:
|
||||||
|
at processImmediate (node:internal/timers:483:21)
|
||||||
|
From previous event:
|
||||||
|
at WinPackager.signApp (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\winPackager.ts:270:27)
|
||||||
|
at WinPackager.doSignAfterPack (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\platformPackager.ts:346:32)
|
||||||
|
at WinPackager.doPack (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\platformPackager.ts:331:7)
|
||||||
|
at WinPackager.pack (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\platformPackager.ts:138:5)
|
||||||
|
at Packager.doBuild (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\packager.ts:459:9)
|
||||||
|
at executeFinally (D:\a\aethex-forge\aethex-forge\node_modules\builder-util\src\promise.ts:12:14)
|
||||||
|
at Packager.build (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\packager.ts:393:31)
|
||||||
|
at executeFinally (D:\a\aethex-forge\aethex-forge\node_modules\builder-util\src\promise.ts:12:14)
|
||||||
|
Error: Process completed with exit code 1.
|
||||||
|
0s
|
||||||
|
0s
|
||||||
|
2s
|
||||||
|
Post job cleanup.
|
||||||
|
"C:\Program Files\Git\bin\git.exe" version
|
||||||
|
git version 2.52.0.windows.1
|
||||||
|
Temporarily overriding HOME='D:\a\_temp\4963c2ff-b212-40d1-906e-719e33666ab2' before making global git config changes
|
||||||
|
Adding repository directory to the temporary git global config as a safe directory
|
||||||
|
"C:\Program Files\Git\bin\git.exe" config --global --add safe.directory D:\a\aethex-forge\aethex-forge
|
||||||
|
"C:\Program Files\Git\bin\git.exe" config --local --name-only --get-regexp core\.sshCommand
|
||||||
|
"C:\Program Files\Git\bin\git.exe" submodule foreach --recursive "sh -c \"git config --local --name-only --get-regexp 'core\.sshCommand' && git config --local --unset-all 'core.sshCommand' || :\""
|
||||||
|
"C:\Program Files\Git\bin\git.exe" config --local --name-only --get-regexp http\.https\:\/\/github\.com\/\.extraheader
|
||||||
|
http.https://github.com/.extraheader
|
||||||
|
"C:\Program Files\Git\bin\git.exe" config --local --unset-all http.https://github.com/.extraheader
|
||||||
|
"C:\Program Files\Git\bin\git.exe" submodule foreach --recursive "sh -c \"git config --local --name-only --get-regexp 'http\.https\:\/\/github\.com\/\.extraheader' && git config --local --unset-all 'http.https://github.com/.extraheader' || :\""
|
||||||
|
"C:\Program Files\Git\bin\git.exe" config --local --name-only --get-regexp ^includeIf\.gitdir:
|
||||||
|
"C:\Program Files\Git\bin\git.exe" submodule foreach --recursive "git config --local --show-origin --name-only --get-regexp remote.origin.url"
|
||||||
|
|
@ -0,0 +1,75 @@
|
||||||
|
Run npx electron-builder --win --config electron-builder.yml
|
||||||
|
• electron-builder version=25.1.8 os=10.0.26100
|
||||||
|
• artifacts will be published reason=tag is defined tag=v0.1.0
|
||||||
|
• loaded configuration file=D:\a\aethex-forge\aethex-forge\electron-builder.yml
|
||||||
|
• skipped dependencies rebuild reason=npmRebuild is set to false
|
||||||
|
• packaging platform=win32 arch=x64 electron=32.3.3 appOutDir=dist\win-unpacked
|
||||||
|
• downloading url=https://github.com/electron/electron/releases/download/v32.3.3/electron-v32.3.3-win32-x64.zip size=113 MB parts=8
|
||||||
|
• downloaded url=https://github.com/electron/electron/releases/download/v32.3.3/electron-v32.3.3-win32-x64.zip duration=592ms
|
||||||
|
• updating asar integrity executable resource executablePath=dist\win-unpacked\AeThex Desktop Terminal.exe
|
||||||
|
⨯ icon directory D:\a\aethex-forge\aethex-forge\build\icons doesn't contain icons
|
||||||
|
github.com/develar/app-builder/pkg/icons.CollectIcons
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/collect-icons.go:73
|
||||||
|
github.com/develar/app-builder/pkg/icons.doConvertIcon
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:199
|
||||||
|
github.com/develar/app-builder/pkg/icons.ConvertIcon
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:56
|
||||||
|
github.com/develar/app-builder/pkg/icons.ConfigureCommand.func1
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:33
|
||||||
|
github.com/alecthomas/kingpin.(*actionMixin).applyActions
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/actions.go:28
|
||||||
|
github.com/alecthomas/kingpin.(*Application).applyActions
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:557
|
||||||
|
github.com/alecthomas/kingpin.(*Application).execute
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:390
|
||||||
|
github.com/alecthomas/kingpin.(*Application).Parse
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:222
|
||||||
|
main.main
|
||||||
|
/Users/runner/work/app-builder/app-builder/main.go:90
|
||||||
|
runtime.main
|
||||||
|
/Users/runner/hostedtoolcache/go/1.21.13/arm64/src/runtime/proc.go:267
|
||||||
|
runtime.goexit
|
||||||
|
/Users/runner/hostedtoolcache/go/1.21.13/arm64/src/runtime/asm_amd64.s:1650
|
||||||
|
github.com/develar/app-builder/pkg/icons.doConvertIcon
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:201
|
||||||
|
github.com/develar/app-builder/pkg/icons.ConvertIcon
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:56
|
||||||
|
github.com/develar/app-builder/pkg/icons.ConfigureCommand.func1
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:33
|
||||||
|
github.com/alecthomas/kingpin.(*actionMixin).applyActions
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/actions.go:28
|
||||||
|
github.com/alecthomas/kingpin.(*Application).applyActions
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:557
|
||||||
|
github.com/alecthomas/kingpin.(*Application).execute
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:390
|
||||||
|
github.com/alecthomas/kingpin.(*Application).Parse
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:222
|
||||||
|
main.main
|
||||||
|
/Users/runner/work/app-builder/app-builder/main.go:90
|
||||||
|
runtime.main
|
||||||
|
/Users/runner/hostedtoolcache/go/1.21.13/arm64/src/runtime/proc.go:267
|
||||||
|
runtime.goexit
|
||||||
|
/Users/runner/hostedtoolcache/go/1.21.13/arm64/src/runtime/asm_amd64.s:1650
|
||||||
|
⨯ D:\a\aethex-forge\aethex-forge\node_modules\app-builder-bin\win\x64\app-builder.exe process failed ERR_ELECTRON_BUILDER_CANNOT_EXECUTE
|
||||||
|
Exit code:
|
||||||
|
1 failedTask=build stackTrace=Error: D:\a\aethex-forge\aethex-forge\node_modules\app-builder-bin\win\x64\app-builder.exe process failed ERR_ELECTRON_BUILDER_CANNOT_EXECUTE
|
||||||
|
Exit code:
|
||||||
|
1
|
||||||
|
at ChildProcess.<anonymous> (D:\a\aethex-forge\aethex-forge\node_modules\builder-util\src\util.ts:255:14)
|
||||||
|
at Object.onceWrapper (node:events:639:26)
|
||||||
|
at ChildProcess.emit (node:events:524:28)
|
||||||
|
at ChildProcess.cp.emit (D:\a\aethex-forge\aethex-forge\node_modules\cross-spawn\lib\enoent.js:34:29)
|
||||||
|
at maybeClose (node:internal/child_process:1104:16)
|
||||||
|
at Process.ChildProcess._handle.onexit (node:internal/child_process:304:5)
|
||||||
|
From previous event:
|
||||||
|
at processImmediate (node:internal/timers:483:21)
|
||||||
|
From previous event:
|
||||||
|
at WinPackager.signApp (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\winPackager.ts:270:27)
|
||||||
|
at WinPackager.doSignAfterPack (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\platformPackager.ts:346:32)
|
||||||
|
at WinPackager.doPack (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\platformPackager.ts:331:7)
|
||||||
|
at WinPackager.pack (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\platformPackager.ts:138:5)
|
||||||
|
at Packager.doBuild (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\packager.ts:459:9)
|
||||||
|
at executeFinally (D:\a\aethex-forge\aethex-forge\node_modules\builder-util\src\promise.ts:12:14)
|
||||||
|
at Packager.build (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\packager.ts:393:31)
|
||||||
|
at executeFinally (D:\a\aethex-forge\aethex-forge\node_modules\builder-util\src\promise.ts:12:14)
|
||||||
|
Error: Process completed with exit code 1.
|
||||||
|
|
@ -0,0 +1,75 @@
|
||||||
|
Run npx electron-builder --win --config electron-builder.yml
|
||||||
|
• electron-builder version=25.1.8 os=10.0.26100
|
||||||
|
• artifacts will be published reason=tag is defined tag=v0.1.2
|
||||||
|
• loaded configuration file=D:\a\aethex-forge\aethex-forge\electron-builder.yml
|
||||||
|
• skipped dependencies rebuild reason=npmRebuild is set to false
|
||||||
|
• packaging platform=win32 arch=x64 electron=32.3.3 appOutDir=dist\win-unpacked
|
||||||
|
• downloading url=https://github.com/electron/electron/releases/download/v32.3.3/electron-v32.3.3-win32-x64.zip size=113 MB parts=8
|
||||||
|
• downloaded url=https://github.com/electron/electron/releases/download/v32.3.3/electron-v32.3.3-win32-x64.zip duration=732ms
|
||||||
|
• updating asar integrity executable resource executablePath=dist\win-unpacked\AeThex Desktop Terminal.exe
|
||||||
|
⨯ icon directory D:\a\aethex-forge\aethex-forge\build\icons doesn't contain icons
|
||||||
|
github.com/develar/app-builder/pkg/icons.CollectIcons
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/collect-icons.go:73
|
||||||
|
github.com/develar/app-builder/pkg/icons.doConvertIcon
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:199
|
||||||
|
github.com/develar/app-builder/pkg/icons.ConvertIcon
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:56
|
||||||
|
github.com/develar/app-builder/pkg/icons.ConfigureCommand.func1
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:33
|
||||||
|
github.com/alecthomas/kingpin.(*actionMixin).applyActions
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/actions.go:28
|
||||||
|
github.com/alecthomas/kingpin.(*Application).applyActions
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:557
|
||||||
|
github.com/alecthomas/kingpin.(*Application).execute
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:390
|
||||||
|
github.com/alecthomas/kingpin.(*Application).Parse
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:222
|
||||||
|
main.main
|
||||||
|
/Users/runner/work/app-builder/app-builder/main.go:90
|
||||||
|
runtime.main
|
||||||
|
/Users/runner/hostedtoolcache/go/1.21.13/arm64/src/runtime/proc.go:267
|
||||||
|
runtime.goexit
|
||||||
|
/Users/runner/hostedtoolcache/go/1.21.13/arm64/src/runtime/asm_amd64.s:1650
|
||||||
|
github.com/develar/app-builder/pkg/icons.doConvertIcon
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:201
|
||||||
|
github.com/develar/app-builder/pkg/icons.ConvertIcon
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:56
|
||||||
|
github.com/develar/app-builder/pkg/icons.ConfigureCommand.func1
|
||||||
|
/Users/runner/work/app-builder/app-builder/pkg/icons/icon-converter.go:33
|
||||||
|
github.com/alecthomas/kingpin.(*actionMixin).applyActions
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/actions.go:28
|
||||||
|
github.com/alecthomas/kingpin.(*Application).applyActions
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:557
|
||||||
|
github.com/alecthomas/kingpin.(*Application).execute
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:390
|
||||||
|
github.com/alecthomas/kingpin.(*Application).Parse
|
||||||
|
/Users/runner/go/pkg/mod/github.com/alecthomas/kingpin@v2.2.6+incompatible/app.go:222
|
||||||
|
main.main
|
||||||
|
/Users/runner/work/app-builder/app-builder/main.go:90
|
||||||
|
runtime.main
|
||||||
|
/Users/runner/hostedtoolcache/go/1.21.13/arm64/src/runtime/proc.go:267
|
||||||
|
runtime.goexit
|
||||||
|
/Users/runner/hostedtoolcache/go/1.21.13/arm64/src/runtime/asm_amd64.s:1650
|
||||||
|
⨯ D:\a\aethex-forge\aethex-forge\node_modules\app-builder-bin\win\x64\app-builder.exe process failed ERR_ELECTRON_BUILDER_CANNOT_EXECUTE
|
||||||
|
Exit code:
|
||||||
|
1 failedTask=build stackTrace=Error: D:\a\aethex-forge\aethex-forge\node_modules\app-builder-bin\win\x64\app-builder.exe process failed ERR_ELECTRON_BUILDER_CANNOT_EXECUTE
|
||||||
|
Exit code:
|
||||||
|
1
|
||||||
|
at ChildProcess.<anonymous> (D:\a\aethex-forge\aethex-forge\node_modules\builder-util\src\util.ts:255:14)
|
||||||
|
at Object.onceWrapper (node:events:639:26)
|
||||||
|
at ChildProcess.emit (node:events:524:28)
|
||||||
|
at ChildProcess.cp.emit (D:\a\aethex-forge\aethex-forge\node_modules\cross-spawn\lib\enoent.js:34:29)
|
||||||
|
at maybeClose (node:internal/child_process:1104:16)
|
||||||
|
at Process.ChildProcess._handle.onexit (node:internal/child_process:304:5)
|
||||||
|
From previous event:
|
||||||
|
at processImmediate (node:internal/timers:483:21)
|
||||||
|
From previous event:
|
||||||
|
at WinPackager.signApp (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\winPackager.ts:270:27)
|
||||||
|
at WinPackager.doSignAfterPack (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\platformPackager.ts:346:32)
|
||||||
|
at WinPackager.doPack (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\platformPackager.ts:331:7)
|
||||||
|
at WinPackager.pack (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\platformPackager.ts:138:5)
|
||||||
|
at Packager.doBuild (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\packager.ts:459:9)
|
||||||
|
at executeFinally (D:\a\aethex-forge\aethex-forge\node_modules\builder-util\src\promise.ts:12:14)
|
||||||
|
at Packager.build (D:\a\aethex-forge\aethex-forge\node_modules\app-builder-lib\src\packager.ts:393:31)
|
||||||
|
at executeFinally (D:\a\aethex-forge\aethex-forge\node_modules\builder-util\src\promise.ts:12:14)
|
||||||
|
Error: Process completed with exit code 1.
|
||||||
BIN
attached_assets/image_1765005879621.png
Normal file
BIN
attached_assets/image_1765005879621.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 51 KiB |
|
|
@ -10,6 +10,8 @@ import { AuthProvider } from "./contexts/AuthContext";
|
||||||
import { Web3Provider } from "./contexts/Web3Context";
|
import { Web3Provider } from "./contexts/Web3Context";
|
||||||
import { DocsThemeProvider } from "./contexts/DocsThemeContext";
|
import { DocsThemeProvider } from "./contexts/DocsThemeContext";
|
||||||
import { ArmThemeProvider } from "./contexts/ArmThemeContext";
|
import { ArmThemeProvider } from "./contexts/ArmThemeContext";
|
||||||
|
import { MaintenanceProvider } from "./contexts/MaintenanceContext";
|
||||||
|
import MaintenanceGuard from "./components/MaintenanceGuard";
|
||||||
import PageTransition from "./components/PageTransition";
|
import PageTransition from "./components/PageTransition";
|
||||||
import SkipAgentController from "./components/SkipAgentController";
|
import SkipAgentController from "./components/SkipAgentController";
|
||||||
import Index from "./pages/Index";
|
import Index from "./pages/Index";
|
||||||
|
|
@ -182,9 +184,11 @@ const App = () => (
|
||||||
<BrowserRouter>
|
<BrowserRouter>
|
||||||
<SubdomainPassportProvider>
|
<SubdomainPassportProvider>
|
||||||
<ArmThemeProvider>
|
<ArmThemeProvider>
|
||||||
<SkipAgentController />
|
<MaintenanceProvider>
|
||||||
<PageTransition>
|
<MaintenanceGuard>
|
||||||
<Routes>
|
<SkipAgentController />
|
||||||
|
<PageTransition>
|
||||||
|
<Routes>
|
||||||
{/* Subdomain Passport (aethex.me and aethex.space) handles its own redirect if not a subdomain */}
|
{/* Subdomain Passport (aethex.me and aethex.space) handles its own redirect if not a subdomain */}
|
||||||
<Route path="/" element={<SubdomainPassport />} />
|
<Route path="/" element={<SubdomainPassport />} />
|
||||||
<Route path="/onboarding" element={<Onboarding />} />
|
<Route path="/onboarding" element={<Onboarding />} />
|
||||||
|
|
@ -795,8 +799,10 @@ const App = () => (
|
||||||
<Route path="/404" element={<FourOhFourPage />} />
|
<Route path="/404" element={<FourOhFourPage />} />
|
||||||
{/* ADD ALL CUSTOM ROUTES ABOVE THE CATCH-ALL "*" ROUTE */}
|
{/* ADD ALL CUSTOM ROUTES ABOVE THE CATCH-ALL "*" ROUTE */}
|
||||||
<Route path="*" element={<FourOhFourPage />} />
|
<Route path="*" element={<FourOhFourPage />} />
|
||||||
</Routes>
|
</Routes>
|
||||||
</PageTransition>
|
</PageTransition>
|
||||||
|
</MaintenanceGuard>
|
||||||
|
</MaintenanceProvider>
|
||||||
</ArmThemeProvider>
|
</ArmThemeProvider>
|
||||||
</SubdomainPassportProvider>
|
</SubdomainPassportProvider>
|
||||||
</BrowserRouter>
|
</BrowserRouter>
|
||||||
|
|
|
||||||
33
client/components/MaintenanceGuard.tsx
Normal file
33
client/components/MaintenanceGuard.tsx
Normal file
|
|
@ -0,0 +1,33 @@
|
||||||
|
import React from "react";
|
||||||
|
import { useLocation } from "react-router-dom";
|
||||||
|
import { useMaintenance } from "@/contexts/MaintenanceContext";
|
||||||
|
import MaintenancePage from "@/pages/Maintenance";
|
||||||
|
|
||||||
|
const ALLOWED_PATHS = ["/login", "/staff/login", "/reset-password", "/health"];
|
||||||
|
|
||||||
|
interface MaintenanceGuardProps {
|
||||||
|
children: React.ReactNode;
|
||||||
|
}
|
||||||
|
|
||||||
|
export default function MaintenanceGuard({ children }: MaintenanceGuardProps) {
|
||||||
|
const { isMaintenanceMode, canBypass, loading } = useMaintenance();
|
||||||
|
const location = useLocation();
|
||||||
|
|
||||||
|
if (loading) {
|
||||||
|
return (
|
||||||
|
<div className="min-h-screen bg-gray-900 flex items-center justify-center">
|
||||||
|
<div className="w-8 h-8 border-2 border-purple-500 border-t-transparent rounded-full animate-spin" />
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
const isAllowedPath = ALLOWED_PATHS.some(path =>
|
||||||
|
location.pathname === path || location.pathname.startsWith(path)
|
||||||
|
);
|
||||||
|
|
||||||
|
if (isMaintenanceMode && !canBypass && !isAllowedPath) {
|
||||||
|
return <MaintenancePage />;
|
||||||
|
}
|
||||||
|
|
||||||
|
return <>{children}</>;
|
||||||
|
}
|
||||||
111
client/components/admin/MaintenanceToggle.tsx
Normal file
111
client/components/admin/MaintenanceToggle.tsx
Normal file
|
|
@ -0,0 +1,111 @@
|
||||||
|
import { Card, CardContent, CardDescription, CardHeader, CardTitle } from "@/components/ui/card";
|
||||||
|
import { Switch } from "@/components/ui/switch";
|
||||||
|
import { Badge } from "@/components/ui/badge";
|
||||||
|
import { useMaintenance } from "@/contexts/MaintenanceContext";
|
||||||
|
import { Construction, AlertTriangle, Loader2 } from "lucide-react";
|
||||||
|
import { useState } from "react";
|
||||||
|
import { aethexToast } from "@/lib/aethex-toast";
|
||||||
|
|
||||||
|
export default function MaintenanceToggle() {
|
||||||
|
const { isMaintenanceMode, canBypass, toggleMaintenanceMode, loading } = useMaintenance();
|
||||||
|
const [toggling, setToggling] = useState(false);
|
||||||
|
|
||||||
|
const handleToggle = async () => {
|
||||||
|
if (!canBypass) {
|
||||||
|
aethexToast.error("Only admins can toggle maintenance mode");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
setToggling(true);
|
||||||
|
try {
|
||||||
|
await toggleMaintenanceMode();
|
||||||
|
aethexToast.success(
|
||||||
|
isMaintenanceMode
|
||||||
|
? "Maintenance mode disabled - site is now live"
|
||||||
|
: "Maintenance mode enabled - visitors will see maintenance page"
|
||||||
|
);
|
||||||
|
} catch (error: any) {
|
||||||
|
aethexToast.error(error?.message || "Failed to toggle maintenance mode");
|
||||||
|
} finally {
|
||||||
|
setToggling(false);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
if (loading) {
|
||||||
|
return (
|
||||||
|
<Card className="bg-card/60 border-border/40 backdrop-blur">
|
||||||
|
<CardContent className="flex items-center justify-center py-8">
|
||||||
|
<Loader2 className="h-6 w-6 animate-spin text-muted-foreground" />
|
||||||
|
</CardContent>
|
||||||
|
</Card>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
return (
|
||||||
|
<Card className={`bg-card/60 border-border/40 backdrop-blur ${isMaintenanceMode ? 'border-yellow-500/30' : ''}`}>
|
||||||
|
<CardHeader className="pb-3">
|
||||||
|
<div className="flex items-center justify-between">
|
||||||
|
<div className="flex items-center gap-3">
|
||||||
|
<div className={`flex h-10 w-10 items-center justify-center rounded-full border ${
|
||||||
|
isMaintenanceMode
|
||||||
|
? 'border-yellow-500/30 bg-yellow-500/10'
|
||||||
|
: 'border-emerald-500/30 bg-emerald-500/10'
|
||||||
|
}`}>
|
||||||
|
{isMaintenanceMode ? (
|
||||||
|
<Construction className="h-5 w-5 text-yellow-400" />
|
||||||
|
) : (
|
||||||
|
<Construction className="h-5 w-5 text-emerald-400" />
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
<div>
|
||||||
|
<CardTitle className="text-lg">Maintenance Mode</CardTitle>
|
||||||
|
<CardDescription>
|
||||||
|
{isMaintenanceMode
|
||||||
|
? "Site is currently in maintenance mode"
|
||||||
|
: "Site is live and accessible"}
|
||||||
|
</CardDescription>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<Badge
|
||||||
|
variant="outline"
|
||||||
|
className={isMaintenanceMode
|
||||||
|
? "border-yellow-500/30 bg-yellow-500/10 text-yellow-200"
|
||||||
|
: "border-emerald-500/30 bg-emerald-500/10 text-emerald-200"
|
||||||
|
}
|
||||||
|
>
|
||||||
|
{isMaintenanceMode ? "Active" : "Off"}
|
||||||
|
</Badge>
|
||||||
|
</div>
|
||||||
|
</CardHeader>
|
||||||
|
<CardContent>
|
||||||
|
<div className="flex items-center justify-between rounded-lg border border-border/30 bg-background/40 p-4">
|
||||||
|
<div className="flex items-center gap-3">
|
||||||
|
{isMaintenanceMode && (
|
||||||
|
<AlertTriangle className="h-5 w-5 text-yellow-400" />
|
||||||
|
)}
|
||||||
|
<div>
|
||||||
|
<p className="font-medium text-sm">
|
||||||
|
{isMaintenanceMode
|
||||||
|
? "Visitors see maintenance page"
|
||||||
|
: "All visitors can access the site"}
|
||||||
|
</p>
|
||||||
|
<p className="text-xs text-muted-foreground mt-1">
|
||||||
|
{isMaintenanceMode
|
||||||
|
? "Only admins can view the site. Toggle off to go live."
|
||||||
|
: "Toggle on to show maintenance page to visitors."}
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div className="flex items-center gap-2">
|
||||||
|
{toggling && <Loader2 className="h-4 w-4 animate-spin" />}
|
||||||
|
<Switch
|
||||||
|
checked={isMaintenanceMode}
|
||||||
|
onCheckedChange={handleToggle}
|
||||||
|
disabled={toggling || !canBypass}
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</CardContent>
|
||||||
|
</Card>
|
||||||
|
);
|
||||||
|
}
|
||||||
104
client/contexts/MaintenanceContext.tsx
Normal file
104
client/contexts/MaintenanceContext.tsx
Normal file
|
|
@ -0,0 +1,104 @@
|
||||||
|
import React, { createContext, useContext, useState, useEffect, useCallback } from "react";
|
||||||
|
import { useAuth } from "./AuthContext";
|
||||||
|
import { supabase } from "@/lib/supabase";
|
||||||
|
|
||||||
|
interface MaintenanceContextType {
|
||||||
|
isMaintenanceMode: boolean;
|
||||||
|
canBypass: boolean;
|
||||||
|
loading: boolean;
|
||||||
|
toggleMaintenanceMode: () => Promise<void>;
|
||||||
|
refreshStatus: () => Promise<void>;
|
||||||
|
}
|
||||||
|
|
||||||
|
const MaintenanceContext = createContext<MaintenanceContextType | undefined>(undefined);
|
||||||
|
|
||||||
|
const ADMIN_ROLES = ["admin", "super_admin", "staff", "owner"];
|
||||||
|
|
||||||
|
export function MaintenanceProvider({ children }: { children: React.ReactNode }) {
|
||||||
|
const { user, roles, session, loading: authLoading } = useAuth();
|
||||||
|
const [isMaintenanceMode, setIsMaintenanceMode] = useState(false);
|
||||||
|
const [loading, setLoading] = useState(true);
|
||||||
|
|
||||||
|
const isAdmin = roles.some(role => ADMIN_ROLES.includes(role.toLowerCase()));
|
||||||
|
const canBypass = isAdmin && !!user;
|
||||||
|
|
||||||
|
const fetchMaintenanceStatus = useCallback(async () => {
|
||||||
|
try {
|
||||||
|
const response = await fetch("/api/admin/platform/maintenance");
|
||||||
|
if (response.ok) {
|
||||||
|
const data = await response.json();
|
||||||
|
setIsMaintenanceMode(data.maintenance_mode ?? false);
|
||||||
|
}
|
||||||
|
} catch (error) {
|
||||||
|
console.error("Failed to fetch maintenance status:", error);
|
||||||
|
} finally {
|
||||||
|
setLoading(false);
|
||||||
|
}
|
||||||
|
}, []);
|
||||||
|
|
||||||
|
const toggleMaintenanceMode = useCallback(async () => {
|
||||||
|
if (!canBypass) {
|
||||||
|
throw new Error("Only admins can toggle maintenance mode");
|
||||||
|
}
|
||||||
|
|
||||||
|
const { data: sessionData } = await supabase.auth.getSession();
|
||||||
|
const token = sessionData?.session?.access_token;
|
||||||
|
|
||||||
|
if (!token) {
|
||||||
|
throw new Error("No auth session");
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
const response = await fetch("/api/admin/platform/maintenance", {
|
||||||
|
method: "POST",
|
||||||
|
headers: {
|
||||||
|
"Content-Type": "application/json",
|
||||||
|
"Authorization": `Bearer ${token}`,
|
||||||
|
},
|
||||||
|
body: JSON.stringify({ maintenance_mode: !isMaintenanceMode }),
|
||||||
|
});
|
||||||
|
|
||||||
|
if (!response.ok) {
|
||||||
|
const errorData = await response.json();
|
||||||
|
throw new Error(errorData.error || "Failed to toggle maintenance mode");
|
||||||
|
}
|
||||||
|
|
||||||
|
const data = await response.json();
|
||||||
|
setIsMaintenanceMode(data.maintenance_mode);
|
||||||
|
} catch (error) {
|
||||||
|
console.error("Failed to toggle maintenance mode:", error);
|
||||||
|
throw error;
|
||||||
|
}
|
||||||
|
}, [canBypass, isMaintenanceMode]);
|
||||||
|
|
||||||
|
const refreshStatus = useCallback(async () => {
|
||||||
|
setLoading(true);
|
||||||
|
await fetchMaintenanceStatus();
|
||||||
|
}, [fetchMaintenanceStatus]);
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
fetchMaintenanceStatus();
|
||||||
|
}, [fetchMaintenanceStatus]);
|
||||||
|
|
||||||
|
return (
|
||||||
|
<MaintenanceContext.Provider
|
||||||
|
value={{
|
||||||
|
isMaintenanceMode,
|
||||||
|
canBypass,
|
||||||
|
loading: loading || authLoading,
|
||||||
|
toggleMaintenanceMode,
|
||||||
|
refreshStatus,
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
{children}
|
||||||
|
</MaintenanceContext.Provider>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
export function useMaintenance() {
|
||||||
|
const context = useContext(MaintenanceContext);
|
||||||
|
if (!context) {
|
||||||
|
throw new Error("useMaintenance must be used within MaintenanceProvider");
|
||||||
|
}
|
||||||
|
return context;
|
||||||
|
}
|
||||||
|
|
@ -40,6 +40,7 @@ import AdminStaffChat from "@/components/admin/AdminStaffChat";
|
||||||
import AdminStaffAdmin from "@/components/admin/AdminStaffAdmin";
|
import AdminStaffAdmin from "@/components/admin/AdminStaffAdmin";
|
||||||
import AdminStaffDocs from "@/components/admin/AdminStaffDocs";
|
import AdminStaffDocs from "@/components/admin/AdminStaffDocs";
|
||||||
import AdminStaffAchievements from "@/components/admin/AdminStaffAchievements";
|
import AdminStaffAchievements from "@/components/admin/AdminStaffAchievements";
|
||||||
|
import MaintenanceToggle from "@/components/admin/MaintenanceToggle";
|
||||||
import AdminSidebar from "@/components/admin/AdminSidebar";
|
import AdminSidebar from "@/components/admin/AdminSidebar";
|
||||||
import AdminEthosVerification from "@/pages/admin/AdminEthosVerification";
|
import AdminEthosVerification from "@/pages/admin/AdminEthosVerification";
|
||||||
import AdminGameForgeStudio from "@/components/admin/AdminGameForgeStudio";
|
import AdminGameForgeStudio from "@/components/admin/AdminGameForgeStudio";
|
||||||
|
|
@ -393,6 +394,8 @@ export default function Admin() {
|
||||||
</TabsList>
|
</TabsList>
|
||||||
|
|
||||||
<TabsContent value="overview" className="space-y-6">
|
<TabsContent value="overview" className="space-y-6">
|
||||||
|
<MaintenanceToggle />
|
||||||
|
|
||||||
<div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-4 gap-4">
|
<div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-4 gap-4">
|
||||||
<Card className="bg-card/60 border-border/40 backdrop-blur">
|
<Card className="bg-card/60 border-border/40 backdrop-blur">
|
||||||
<CardHeader className="pb-3">
|
<CardHeader className="pb-3">
|
||||||
|
|
|
||||||
159
client/pages/Maintenance.tsx
Normal file
159
client/pages/Maintenance.tsx
Normal file
|
|
@ -0,0 +1,159 @@
|
||||||
|
import { useState, useEffect } from "react";
|
||||||
|
import { Shield, Mail, Wrench, Clock, Zap } from "lucide-react";
|
||||||
|
import { Button } from "@/components/ui/button";
|
||||||
|
import { Badge } from "@/components/ui/badge";
|
||||||
|
import { Card, CardContent } from "@/components/ui/card";
|
||||||
|
import AeThexOSLogo from "@/components/AeThexOSLogo";
|
||||||
|
|
||||||
|
export default function MaintenancePage() {
|
||||||
|
const [currentMessage, setCurrentMessage] = useState(0);
|
||||||
|
const [dots, setDots] = useState("");
|
||||||
|
|
||||||
|
const messages = [
|
||||||
|
"Upgrading quantum processors...",
|
||||||
|
"Optimizing neural networks...",
|
||||||
|
"Synchronizing data streams...",
|
||||||
|
"Calibrating system modules...",
|
||||||
|
"Enhancing user experience...",
|
||||||
|
];
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
const messageInterval = setInterval(() => {
|
||||||
|
setCurrentMessage((prev) => (prev + 1) % messages.length);
|
||||||
|
}, 2500);
|
||||||
|
|
||||||
|
const dotsInterval = setInterval(() => {
|
||||||
|
setDots((prev) => (prev.length >= 3 ? "" : prev + "."));
|
||||||
|
}, 400);
|
||||||
|
|
||||||
|
return () => {
|
||||||
|
clearInterval(messageInterval);
|
||||||
|
clearInterval(dotsInterval);
|
||||||
|
};
|
||||||
|
}, [messages.length]);
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div className="min-h-screen bg-background overflow-hidden relative">
|
||||||
|
<div className="absolute inset-0 pointer-events-none overflow-hidden opacity-5">
|
||||||
|
{[...Array(20)].map((_, i) => (
|
||||||
|
<div
|
||||||
|
key={i}
|
||||||
|
className="absolute text-blue-400 animate-float font-mono"
|
||||||
|
style={{
|
||||||
|
left: `${Math.random() * 100}%`,
|
||||||
|
top: `${Math.random() * 100}%`,
|
||||||
|
animationDelay: `${Math.random() * 3}s`,
|
||||||
|
animationDuration: `${4 + Math.random() * 3}s`,
|
||||||
|
fontSize: `${10 + Math.random() * 6}px`,
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
{["01", "10", "//", "{ }", "< >", "=>"][Math.floor(Math.random() * 6)]}
|
||||||
|
</div>
|
||||||
|
))}
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div className="absolute top-1/4 left-1/4 w-96 h-96 bg-blue-500/5 rounded-full blur-3xl" />
|
||||||
|
<div className="absolute bottom-1/4 right-1/4 w-80 h-80 bg-cyan-500/5 rounded-full blur-3xl" />
|
||||||
|
|
||||||
|
<div className="relative z-10 flex items-center justify-center min-h-screen p-4">
|
||||||
|
<div className="max-w-xl w-full text-center space-y-8">
|
||||||
|
<div className="space-y-6">
|
||||||
|
<div className="relative inline-block">
|
||||||
|
<div className="absolute -inset-4 bg-gradient-to-r from-blue-500 to-cyan-500 opacity-20 blur-xl rounded-full animate-pulse" />
|
||||||
|
<div className="relative w-24 h-24 mx-auto bg-gradient-to-br from-blue-500/20 to-cyan-500/20 border border-blue-500/40 rounded-xl flex items-center justify-center shadow-lg shadow-blue-500/10">
|
||||||
|
<AeThexOSLogo size="lg" variant="default" animate />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div className="space-y-3">
|
||||||
|
<h1 className="text-4xl md:text-5xl font-bold bg-gradient-to-r from-blue-400 via-cyan-400 to-blue-400 bg-clip-text text-transparent">
|
||||||
|
System Maintenance
|
||||||
|
</h1>
|
||||||
|
<p className="text-lg text-muted-foreground max-w-md mx-auto">
|
||||||
|
We're upgrading AeThex to deliver a better experience.
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div className="flex justify-center gap-3 flex-wrap">
|
||||||
|
<Badge variant="outline" className="border-blue-500/50 text-blue-400 animate-pulse">
|
||||||
|
<Wrench className="h-3 w-3 mr-1" />
|
||||||
|
Maintenance Mode
|
||||||
|
</Badge>
|
||||||
|
<Badge variant="outline" className="border-cyan-500/50 text-cyan-400">
|
||||||
|
<Clock className="h-3 w-3 mr-1" />
|
||||||
|
Back Soon
|
||||||
|
</Badge>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<Card className="bg-card/50 border-border/50 backdrop-blur-sm">
|
||||||
|
<CardContent className="p-6 space-y-4">
|
||||||
|
<div className="flex items-center justify-center gap-3">
|
||||||
|
<div className="flex gap-1">
|
||||||
|
{[...Array(5)].map((_, i) => (
|
||||||
|
<div
|
||||||
|
key={i}
|
||||||
|
className="w-1.5 bg-gradient-to-t from-blue-500 to-cyan-400 rounded-full animate-pulse"
|
||||||
|
style={{
|
||||||
|
height: `${12 + i * 4}px`,
|
||||||
|
animationDelay: `${i * 0.15}s`,
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
))}
|
||||||
|
</div>
|
||||||
|
<span className="text-sm text-muted-foreground font-mono">
|
||||||
|
{messages[currentMessage]}{dots}
|
||||||
|
</span>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div className="h-px bg-border" />
|
||||||
|
|
||||||
|
<div className="grid grid-cols-3 gap-4 text-center text-xs">
|
||||||
|
<div className="space-y-1">
|
||||||
|
<div className="text-muted-foreground">STATUS</div>
|
||||||
|
<div className="text-blue-400 font-semibold flex items-center justify-center gap-1">
|
||||||
|
<Zap className="h-3 w-3" />
|
||||||
|
ACTIVE
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div className="space-y-1">
|
||||||
|
<div className="text-muted-foreground">SYSTEM</div>
|
||||||
|
<div className="text-foreground font-semibold">AeThex v2.0</div>
|
||||||
|
</div>
|
||||||
|
<div className="space-y-1">
|
||||||
|
<div className="text-muted-foreground">ETA</div>
|
||||||
|
<div className="text-cyan-400 font-semibold">~30 min</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</CardContent>
|
||||||
|
</Card>
|
||||||
|
|
||||||
|
<Card className="bg-background/30 border-border/30">
|
||||||
|
<CardContent className="p-4">
|
||||||
|
<div className="flex items-center justify-center gap-2 text-sm">
|
||||||
|
<Shield className="w-4 h-4 text-blue-400" />
|
||||||
|
<span className="text-muted-foreground">Questions?</span>
|
||||||
|
<Mail className="w-4 h-4 text-muted-foreground" />
|
||||||
|
<a
|
||||||
|
href="mailto:support@aethex.dev"
|
||||||
|
className="text-blue-400 hover:text-blue-300 transition-colors"
|
||||||
|
>
|
||||||
|
support@aethex.dev
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
</CardContent>
|
||||||
|
</Card>
|
||||||
|
|
||||||
|
<Button
|
||||||
|
variant="ghost"
|
||||||
|
size="sm"
|
||||||
|
asChild
|
||||||
|
className="text-muted-foreground hover:text-foreground hover:bg-blue-500/10"
|
||||||
|
>
|
||||||
|
<a href="/login">Staff Login</a>
|
||||||
|
</Button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
@ -311,7 +311,7 @@ async function registerDiscordCommands() {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Start HTTP health check server
|
// Start HTTP health check server
|
||||||
const healthPort = process.env.HEALTH_PORT || 8044;
|
const healthPort = process.env.HEALTH_PORT || 8080;
|
||||||
const ADMIN_TOKEN = process.env.DISCORD_ADMIN_TOKEN || "aethex-bot-admin";
|
const ADMIN_TOKEN = process.env.DISCORD_ADMIN_TOKEN || "aethex-bot-admin";
|
||||||
|
|
||||||
// Helper to check admin authentication
|
// Helper to check admin authentication
|
||||||
|
|
|
||||||
554
package-lock.json
generated
554
package-lock.json
generated
|
|
@ -19,6 +19,8 @@
|
||||||
"ethers": "^6.13.0",
|
"ethers": "^6.13.0",
|
||||||
"express": "^4.18.2",
|
"express": "^4.18.2",
|
||||||
"nodemailer": "^7.0.10",
|
"nodemailer": "^7.0.10",
|
||||||
|
"png-to-ico": "^3.0.1",
|
||||||
|
"sharp": "^0.34.5",
|
||||||
"stripe": "^15.12.0",
|
"stripe": "^15.12.0",
|
||||||
"zod": "^3.23.8"
|
"zod": "^3.23.8"
|
||||||
},
|
},
|
||||||
|
|
@ -1737,6 +1739,23 @@
|
||||||
"node": ">= 10.0.0"
|
"node": ">= 10.0.0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/@emnapi/runtime": {
|
||||||
|
"version": "1.7.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/@emnapi/runtime/-/runtime-1.7.1.tgz",
|
||||||
|
"integrity": "sha512-PVtJr5CmLwYAU9PZDMITZoR5iAOShYREoR45EyyLrbntV50mdePTgUn4AmOw90Ifcj+x2kRjdzr1HP3RrNiHGA==",
|
||||||
|
"license": "MIT",
|
||||||
|
"optional": true,
|
||||||
|
"dependencies": {
|
||||||
|
"tslib": "^2.4.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@emnapi/runtime/node_modules/tslib": {
|
||||||
|
"version": "2.8.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/tslib/-/tslib-2.8.1.tgz",
|
||||||
|
"integrity": "sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w==",
|
||||||
|
"license": "0BSD",
|
||||||
|
"optional": true
|
||||||
|
},
|
||||||
"node_modules/@emotion/cache": {
|
"node_modules/@emotion/cache": {
|
||||||
"version": "10.0.29",
|
"version": "10.0.29",
|
||||||
"resolved": "https://registry.npmjs.org/@emotion/cache/-/cache-10.0.29.tgz",
|
"resolved": "https://registry.npmjs.org/@emotion/cache/-/cache-10.0.29.tgz",
|
||||||
|
|
@ -2364,6 +2383,471 @@
|
||||||
"react-hook-form": "^7.0.0"
|
"react-hook-form": "^7.0.0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/@img/colour": {
|
||||||
|
"version": "1.0.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/colour/-/colour-1.0.0.tgz",
|
||||||
|
"integrity": "sha512-A5P/LfWGFSl6nsckYtjw9da+19jB8hkJ6ACTGcDfEJ0aE+l2n2El7dsVM7UVHZQ9s2lmYMWlrS21YLy2IR1LUw==",
|
||||||
|
"license": "MIT",
|
||||||
|
"engines": {
|
||||||
|
"node": ">=18"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-darwin-arm64": {
|
||||||
|
"version": "0.34.5",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-darwin-arm64/-/sharp-darwin-arm64-0.34.5.tgz",
|
||||||
|
"integrity": "sha512-imtQ3WMJXbMY4fxb/Ndp6HBTNVtWCUI0WdobyheGf5+ad6xX8VIDO8u2xE4qc/fr08CKG/7dDseFtn6M6g/r3w==",
|
||||||
|
"cpu": [
|
||||||
|
"arm64"
|
||||||
|
],
|
||||||
|
"license": "Apache-2.0",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"darwin"
|
||||||
|
],
|
||||||
|
"engines": {
|
||||||
|
"node": "^18.17.0 || ^20.3.0 || >=21.0.0"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
},
|
||||||
|
"optionalDependencies": {
|
||||||
|
"@img/sharp-libvips-darwin-arm64": "1.2.4"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-darwin-x64": {
|
||||||
|
"version": "0.34.5",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-darwin-x64/-/sharp-darwin-x64-0.34.5.tgz",
|
||||||
|
"integrity": "sha512-YNEFAF/4KQ/PeW0N+r+aVVsoIY0/qxxikF2SWdp+NRkmMB7y9LBZAVqQ4yhGCm/H3H270OSykqmQMKLBhBJDEw==",
|
||||||
|
"cpu": [
|
||||||
|
"x64"
|
||||||
|
],
|
||||||
|
"license": "Apache-2.0",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"darwin"
|
||||||
|
],
|
||||||
|
"engines": {
|
||||||
|
"node": "^18.17.0 || ^20.3.0 || >=21.0.0"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
},
|
||||||
|
"optionalDependencies": {
|
||||||
|
"@img/sharp-libvips-darwin-x64": "1.2.4"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-libvips-darwin-arm64": {
|
||||||
|
"version": "1.2.4",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-libvips-darwin-arm64/-/sharp-libvips-darwin-arm64-1.2.4.tgz",
|
||||||
|
"integrity": "sha512-zqjjo7RatFfFoP0MkQ51jfuFZBnVE2pRiaydKJ1G/rHZvnsrHAOcQALIi9sA5co5xenQdTugCvtb1cuf78Vf4g==",
|
||||||
|
"cpu": [
|
||||||
|
"arm64"
|
||||||
|
],
|
||||||
|
"license": "LGPL-3.0-or-later",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"darwin"
|
||||||
|
],
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-libvips-darwin-x64": {
|
||||||
|
"version": "1.2.4",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-libvips-darwin-x64/-/sharp-libvips-darwin-x64-1.2.4.tgz",
|
||||||
|
"integrity": "sha512-1IOd5xfVhlGwX+zXv2N93k0yMONvUlANylbJw1eTah8K/Jtpi15KC+WSiaX/nBmbm2HxRM1gZ0nSdjSsrZbGKg==",
|
||||||
|
"cpu": [
|
||||||
|
"x64"
|
||||||
|
],
|
||||||
|
"license": "LGPL-3.0-or-later",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"darwin"
|
||||||
|
],
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-libvips-linux-arm": {
|
||||||
|
"version": "1.2.4",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-libvips-linux-arm/-/sharp-libvips-linux-arm-1.2.4.tgz",
|
||||||
|
"integrity": "sha512-bFI7xcKFELdiNCVov8e44Ia4u2byA+l3XtsAj+Q8tfCwO6BQ8iDojYdvoPMqsKDkuoOo+X6HZA0s0q11ANMQ8A==",
|
||||||
|
"cpu": [
|
||||||
|
"arm"
|
||||||
|
],
|
||||||
|
"license": "LGPL-3.0-or-later",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"linux"
|
||||||
|
],
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-libvips-linux-arm64": {
|
||||||
|
"version": "1.2.4",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-libvips-linux-arm64/-/sharp-libvips-linux-arm64-1.2.4.tgz",
|
||||||
|
"integrity": "sha512-excjX8DfsIcJ10x1Kzr4RcWe1edC9PquDRRPx3YVCvQv+U5p7Yin2s32ftzikXojb1PIFc/9Mt28/y+iRklkrw==",
|
||||||
|
"cpu": [
|
||||||
|
"arm64"
|
||||||
|
],
|
||||||
|
"license": "LGPL-3.0-or-later",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"linux"
|
||||||
|
],
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-libvips-linux-ppc64": {
|
||||||
|
"version": "1.2.4",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-libvips-linux-ppc64/-/sharp-libvips-linux-ppc64-1.2.4.tgz",
|
||||||
|
"integrity": "sha512-FMuvGijLDYG6lW+b/UvyilUWu5Ayu+3r2d1S8notiGCIyYU/76eig1UfMmkZ7vwgOrzKzlQbFSuQfgm7GYUPpA==",
|
||||||
|
"cpu": [
|
||||||
|
"ppc64"
|
||||||
|
],
|
||||||
|
"license": "LGPL-3.0-or-later",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"linux"
|
||||||
|
],
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-libvips-linux-riscv64": {
|
||||||
|
"version": "1.2.4",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-libvips-linux-riscv64/-/sharp-libvips-linux-riscv64-1.2.4.tgz",
|
||||||
|
"integrity": "sha512-oVDbcR4zUC0ce82teubSm+x6ETixtKZBh/qbREIOcI3cULzDyb18Sr/Wcyx7NRQeQzOiHTNbZFF1UwPS2scyGA==",
|
||||||
|
"cpu": [
|
||||||
|
"riscv64"
|
||||||
|
],
|
||||||
|
"license": "LGPL-3.0-or-later",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"linux"
|
||||||
|
],
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-libvips-linux-s390x": {
|
||||||
|
"version": "1.2.4",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-libvips-linux-s390x/-/sharp-libvips-linux-s390x-1.2.4.tgz",
|
||||||
|
"integrity": "sha512-qmp9VrzgPgMoGZyPvrQHqk02uyjA0/QrTO26Tqk6l4ZV0MPWIW6LTkqOIov+J1yEu7MbFQaDpwdwJKhbJvuRxQ==",
|
||||||
|
"cpu": [
|
||||||
|
"s390x"
|
||||||
|
],
|
||||||
|
"license": "LGPL-3.0-or-later",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"linux"
|
||||||
|
],
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-libvips-linux-x64": {
|
||||||
|
"version": "1.2.4",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-libvips-linux-x64/-/sharp-libvips-linux-x64-1.2.4.tgz",
|
||||||
|
"integrity": "sha512-tJxiiLsmHc9Ax1bz3oaOYBURTXGIRDODBqhveVHonrHJ9/+k89qbLl0bcJns+e4t4rvaNBxaEZsFtSfAdquPrw==",
|
||||||
|
"cpu": [
|
||||||
|
"x64"
|
||||||
|
],
|
||||||
|
"license": "LGPL-3.0-or-later",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"linux"
|
||||||
|
],
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-libvips-linuxmusl-arm64": {
|
||||||
|
"version": "1.2.4",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-libvips-linuxmusl-arm64/-/sharp-libvips-linuxmusl-arm64-1.2.4.tgz",
|
||||||
|
"integrity": "sha512-FVQHuwx1IIuNow9QAbYUzJ+En8KcVm9Lk5+uGUQJHaZmMECZmOlix9HnH7n1TRkXMS0pGxIJokIVB9SuqZGGXw==",
|
||||||
|
"cpu": [
|
||||||
|
"arm64"
|
||||||
|
],
|
||||||
|
"license": "LGPL-3.0-or-later",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"linux"
|
||||||
|
],
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-libvips-linuxmusl-x64": {
|
||||||
|
"version": "1.2.4",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-libvips-linuxmusl-x64/-/sharp-libvips-linuxmusl-x64-1.2.4.tgz",
|
||||||
|
"integrity": "sha512-+LpyBk7L44ZIXwz/VYfglaX/okxezESc6UxDSoyo2Ks6Jxc4Y7sGjpgU9s4PMgqgjj1gZCylTieNamqA1MF7Dg==",
|
||||||
|
"cpu": [
|
||||||
|
"x64"
|
||||||
|
],
|
||||||
|
"license": "LGPL-3.0-or-later",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"linux"
|
||||||
|
],
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-linux-arm": {
|
||||||
|
"version": "0.34.5",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-linux-arm/-/sharp-linux-arm-0.34.5.tgz",
|
||||||
|
"integrity": "sha512-9dLqsvwtg1uuXBGZKsxem9595+ujv0sJ6Vi8wcTANSFpwV/GONat5eCkzQo/1O6zRIkh0m/8+5BjrRr7jDUSZw==",
|
||||||
|
"cpu": [
|
||||||
|
"arm"
|
||||||
|
],
|
||||||
|
"license": "Apache-2.0",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"linux"
|
||||||
|
],
|
||||||
|
"engines": {
|
||||||
|
"node": "^18.17.0 || ^20.3.0 || >=21.0.0"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
},
|
||||||
|
"optionalDependencies": {
|
||||||
|
"@img/sharp-libvips-linux-arm": "1.2.4"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-linux-arm64": {
|
||||||
|
"version": "0.34.5",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-linux-arm64/-/sharp-linux-arm64-0.34.5.tgz",
|
||||||
|
"integrity": "sha512-bKQzaJRY/bkPOXyKx5EVup7qkaojECG6NLYswgktOZjaXecSAeCWiZwwiFf3/Y+O1HrauiE3FVsGxFg8c24rZg==",
|
||||||
|
"cpu": [
|
||||||
|
"arm64"
|
||||||
|
],
|
||||||
|
"license": "Apache-2.0",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"linux"
|
||||||
|
],
|
||||||
|
"engines": {
|
||||||
|
"node": "^18.17.0 || ^20.3.0 || >=21.0.0"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
},
|
||||||
|
"optionalDependencies": {
|
||||||
|
"@img/sharp-libvips-linux-arm64": "1.2.4"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-linux-ppc64": {
|
||||||
|
"version": "0.34.5",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-linux-ppc64/-/sharp-linux-ppc64-0.34.5.tgz",
|
||||||
|
"integrity": "sha512-7zznwNaqW6YtsfrGGDA6BRkISKAAE1Jo0QdpNYXNMHu2+0dTrPflTLNkpc8l7MUP5M16ZJcUvysVWWrMefZquA==",
|
||||||
|
"cpu": [
|
||||||
|
"ppc64"
|
||||||
|
],
|
||||||
|
"license": "Apache-2.0",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"linux"
|
||||||
|
],
|
||||||
|
"engines": {
|
||||||
|
"node": "^18.17.0 || ^20.3.0 || >=21.0.0"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
},
|
||||||
|
"optionalDependencies": {
|
||||||
|
"@img/sharp-libvips-linux-ppc64": "1.2.4"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-linux-riscv64": {
|
||||||
|
"version": "0.34.5",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-linux-riscv64/-/sharp-linux-riscv64-0.34.5.tgz",
|
||||||
|
"integrity": "sha512-51gJuLPTKa7piYPaVs8GmByo7/U7/7TZOq+cnXJIHZKavIRHAP77e3N2HEl3dgiqdD/w0yUfiJnII77PuDDFdw==",
|
||||||
|
"cpu": [
|
||||||
|
"riscv64"
|
||||||
|
],
|
||||||
|
"license": "Apache-2.0",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"linux"
|
||||||
|
],
|
||||||
|
"engines": {
|
||||||
|
"node": "^18.17.0 || ^20.3.0 || >=21.0.0"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
},
|
||||||
|
"optionalDependencies": {
|
||||||
|
"@img/sharp-libvips-linux-riscv64": "1.2.4"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-linux-s390x": {
|
||||||
|
"version": "0.34.5",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-linux-s390x/-/sharp-linux-s390x-0.34.5.tgz",
|
||||||
|
"integrity": "sha512-nQtCk0PdKfho3eC5MrbQoigJ2gd1CgddUMkabUj+rBevs8tZ2cULOx46E7oyX+04WGfABgIwmMC0VqieTiR4jg==",
|
||||||
|
"cpu": [
|
||||||
|
"s390x"
|
||||||
|
],
|
||||||
|
"license": "Apache-2.0",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"linux"
|
||||||
|
],
|
||||||
|
"engines": {
|
||||||
|
"node": "^18.17.0 || ^20.3.0 || >=21.0.0"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
},
|
||||||
|
"optionalDependencies": {
|
||||||
|
"@img/sharp-libvips-linux-s390x": "1.2.4"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-linux-x64": {
|
||||||
|
"version": "0.34.5",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-linux-x64/-/sharp-linux-x64-0.34.5.tgz",
|
||||||
|
"integrity": "sha512-MEzd8HPKxVxVenwAa+JRPwEC7QFjoPWuS5NZnBt6B3pu7EG2Ge0id1oLHZpPJdn3OQK+BQDiw9zStiHBTJQQQQ==",
|
||||||
|
"cpu": [
|
||||||
|
"x64"
|
||||||
|
],
|
||||||
|
"license": "Apache-2.0",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"linux"
|
||||||
|
],
|
||||||
|
"engines": {
|
||||||
|
"node": "^18.17.0 || ^20.3.0 || >=21.0.0"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
},
|
||||||
|
"optionalDependencies": {
|
||||||
|
"@img/sharp-libvips-linux-x64": "1.2.4"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-linuxmusl-arm64": {
|
||||||
|
"version": "0.34.5",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-linuxmusl-arm64/-/sharp-linuxmusl-arm64-0.34.5.tgz",
|
||||||
|
"integrity": "sha512-fprJR6GtRsMt6Kyfq44IsChVZeGN97gTD331weR1ex1c1rypDEABN6Tm2xa1wE6lYb5DdEnk03NZPqA7Id21yg==",
|
||||||
|
"cpu": [
|
||||||
|
"arm64"
|
||||||
|
],
|
||||||
|
"license": "Apache-2.0",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"linux"
|
||||||
|
],
|
||||||
|
"engines": {
|
||||||
|
"node": "^18.17.0 || ^20.3.0 || >=21.0.0"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
},
|
||||||
|
"optionalDependencies": {
|
||||||
|
"@img/sharp-libvips-linuxmusl-arm64": "1.2.4"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-linuxmusl-x64": {
|
||||||
|
"version": "0.34.5",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-linuxmusl-x64/-/sharp-linuxmusl-x64-0.34.5.tgz",
|
||||||
|
"integrity": "sha512-Jg8wNT1MUzIvhBFxViqrEhWDGzqymo3sV7z7ZsaWbZNDLXRJZoRGrjulp60YYtV4wfY8VIKcWidjojlLcWrd8Q==",
|
||||||
|
"cpu": [
|
||||||
|
"x64"
|
||||||
|
],
|
||||||
|
"license": "Apache-2.0",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"linux"
|
||||||
|
],
|
||||||
|
"engines": {
|
||||||
|
"node": "^18.17.0 || ^20.3.0 || >=21.0.0"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
},
|
||||||
|
"optionalDependencies": {
|
||||||
|
"@img/sharp-libvips-linuxmusl-x64": "1.2.4"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-wasm32": {
|
||||||
|
"version": "0.34.5",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-wasm32/-/sharp-wasm32-0.34.5.tgz",
|
||||||
|
"integrity": "sha512-OdWTEiVkY2PHwqkbBI8frFxQQFekHaSSkUIJkwzclWZe64O1X4UlUjqqqLaPbUpMOQk6FBu/HtlGXNblIs0huw==",
|
||||||
|
"cpu": [
|
||||||
|
"wasm32"
|
||||||
|
],
|
||||||
|
"license": "Apache-2.0 AND LGPL-3.0-or-later AND MIT",
|
||||||
|
"optional": true,
|
||||||
|
"dependencies": {
|
||||||
|
"@emnapi/runtime": "^1.7.0"
|
||||||
|
},
|
||||||
|
"engines": {
|
||||||
|
"node": "^18.17.0 || ^20.3.0 || >=21.0.0"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-win32-arm64": {
|
||||||
|
"version": "0.34.5",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-win32-arm64/-/sharp-win32-arm64-0.34.5.tgz",
|
||||||
|
"integrity": "sha512-WQ3AgWCWYSb2yt+IG8mnC6Jdk9Whs7O0gxphblsLvdhSpSTtmu69ZG1Gkb6NuvxsNACwiPV6cNSZNzt0KPsw7g==",
|
||||||
|
"cpu": [
|
||||||
|
"arm64"
|
||||||
|
],
|
||||||
|
"license": "Apache-2.0 AND LGPL-3.0-or-later",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"win32"
|
||||||
|
],
|
||||||
|
"engines": {
|
||||||
|
"node": "^18.17.0 || ^20.3.0 || >=21.0.0"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-win32-ia32": {
|
||||||
|
"version": "0.34.5",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-win32-ia32/-/sharp-win32-ia32-0.34.5.tgz",
|
||||||
|
"integrity": "sha512-FV9m/7NmeCmSHDD5j4+4pNI8Cp3aW+JvLoXcTUo0IqyjSfAZJ8dIUmijx1qaJsIiU+Hosw6xM5KijAWRJCSgNg==",
|
||||||
|
"cpu": [
|
||||||
|
"ia32"
|
||||||
|
],
|
||||||
|
"license": "Apache-2.0 AND LGPL-3.0-or-later",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"win32"
|
||||||
|
],
|
||||||
|
"engines": {
|
||||||
|
"node": "^18.17.0 || ^20.3.0 || >=21.0.0"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@img/sharp-win32-x64": {
|
||||||
|
"version": "0.34.5",
|
||||||
|
"resolved": "https://registry.npmjs.org/@img/sharp-win32-x64/-/sharp-win32-x64-0.34.5.tgz",
|
||||||
|
"integrity": "sha512-+29YMsqY2/9eFEiW93eqWnuLcWcufowXewwSNIT6UwZdUUCrM3oFjMWH/Z6/TMmb4hlFenmfAVbpWeup2jryCw==",
|
||||||
|
"cpu": [
|
||||||
|
"x64"
|
||||||
|
],
|
||||||
|
"license": "Apache-2.0 AND LGPL-3.0-or-later",
|
||||||
|
"optional": true,
|
||||||
|
"os": [
|
||||||
|
"win32"
|
||||||
|
],
|
||||||
|
"engines": {
|
||||||
|
"node": "^18.17.0 || ^20.3.0 || >=21.0.0"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/@isaacs/balanced-match": {
|
"node_modules/@isaacs/balanced-match": {
|
||||||
"version": "4.0.1",
|
"version": "4.0.1",
|
||||||
"resolved": "https://registry.npmjs.org/@isaacs/balanced-match/-/balanced-match-4.0.1.tgz",
|
"resolved": "https://registry.npmjs.org/@isaacs/balanced-match/-/balanced-match-4.0.1.tgz",
|
||||||
|
|
@ -13370,6 +13854,32 @@
|
||||||
"node": ">=10.4.0"
|
"node": ">=10.4.0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/png-to-ico": {
|
||||||
|
"version": "3.0.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/png-to-ico/-/png-to-ico-3.0.1.tgz",
|
||||||
|
"integrity": "sha512-S8BOAoaGd9gT5uaemQ62arIY3Jzco7Uc7LwUTqRyqJDTsKqOAiyfyN4dSdT0D+Zf8XvgztgpRbM5wnQd7EgYwg==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"@types/node": "^22.10.3",
|
||||||
|
"minimist": "^1.2.8",
|
||||||
|
"pngjs": "^7.0.0"
|
||||||
|
},
|
||||||
|
"bin": {
|
||||||
|
"png-to-ico": "bin/cli.js"
|
||||||
|
},
|
||||||
|
"engines": {
|
||||||
|
"node": ">=20"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/pngjs": {
|
||||||
|
"version": "7.0.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/pngjs/-/pngjs-7.0.0.tgz",
|
||||||
|
"integrity": "sha512-LKWqWJRhstyYo9pGvgor/ivk2w94eSjE3RGVuzLGlr3NmD8bf7RcYGze1mNdEHRP6TRP6rMuDHk5t44hnTRyow==",
|
||||||
|
"license": "MIT",
|
||||||
|
"engines": {
|
||||||
|
"node": ">=14.19.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/postcss": {
|
"node_modules/postcss": {
|
||||||
"version": "8.5.6",
|
"version": "8.5.6",
|
||||||
"resolved": "https://registry.npmjs.org/postcss/-/postcss-8.5.6.tgz",
|
"resolved": "https://registry.npmjs.org/postcss/-/postcss-8.5.6.tgz",
|
||||||
|
|
@ -14698,6 +15208,50 @@
|
||||||
"integrity": "sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==",
|
"integrity": "sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==",
|
||||||
"license": "ISC"
|
"license": "ISC"
|
||||||
},
|
},
|
||||||
|
"node_modules/sharp": {
|
||||||
|
"version": "0.34.5",
|
||||||
|
"resolved": "https://registry.npmjs.org/sharp/-/sharp-0.34.5.tgz",
|
||||||
|
"integrity": "sha512-Ou9I5Ft9WNcCbXrU9cMgPBcCK8LiwLqcbywW3t4oDV37n1pzpuNLsYiAV8eODnjbtQlSDwZ2cUEeQz4E54Hltg==",
|
||||||
|
"hasInstallScript": true,
|
||||||
|
"license": "Apache-2.0",
|
||||||
|
"dependencies": {
|
||||||
|
"@img/colour": "^1.0.0",
|
||||||
|
"detect-libc": "^2.1.2",
|
||||||
|
"semver": "^7.7.3"
|
||||||
|
},
|
||||||
|
"engines": {
|
||||||
|
"node": "^18.17.0 || ^20.3.0 || >=21.0.0"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"url": "https://opencollective.com/libvips"
|
||||||
|
},
|
||||||
|
"optionalDependencies": {
|
||||||
|
"@img/sharp-darwin-arm64": "0.34.5",
|
||||||
|
"@img/sharp-darwin-x64": "0.34.5",
|
||||||
|
"@img/sharp-libvips-darwin-arm64": "1.2.4",
|
||||||
|
"@img/sharp-libvips-darwin-x64": "1.2.4",
|
||||||
|
"@img/sharp-libvips-linux-arm": "1.2.4",
|
||||||
|
"@img/sharp-libvips-linux-arm64": "1.2.4",
|
||||||
|
"@img/sharp-libvips-linux-ppc64": "1.2.4",
|
||||||
|
"@img/sharp-libvips-linux-riscv64": "1.2.4",
|
||||||
|
"@img/sharp-libvips-linux-s390x": "1.2.4",
|
||||||
|
"@img/sharp-libvips-linux-x64": "1.2.4",
|
||||||
|
"@img/sharp-libvips-linuxmusl-arm64": "1.2.4",
|
||||||
|
"@img/sharp-libvips-linuxmusl-x64": "1.2.4",
|
||||||
|
"@img/sharp-linux-arm": "0.34.5",
|
||||||
|
"@img/sharp-linux-arm64": "0.34.5",
|
||||||
|
"@img/sharp-linux-ppc64": "0.34.5",
|
||||||
|
"@img/sharp-linux-riscv64": "0.34.5",
|
||||||
|
"@img/sharp-linux-s390x": "0.34.5",
|
||||||
|
"@img/sharp-linux-x64": "0.34.5",
|
||||||
|
"@img/sharp-linuxmusl-arm64": "0.34.5",
|
||||||
|
"@img/sharp-linuxmusl-x64": "0.34.5",
|
||||||
|
"@img/sharp-wasm32": "0.34.5",
|
||||||
|
"@img/sharp-win32-arm64": "0.34.5",
|
||||||
|
"@img/sharp-win32-ia32": "0.34.5",
|
||||||
|
"@img/sharp-win32-x64": "0.34.5"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/shebang-command": {
|
"node_modules/shebang-command": {
|
||||||
"version": "2.0.0",
|
"version": "2.0.0",
|
||||||
"resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz",
|
"resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz",
|
||||||
|
|
|
||||||
|
|
@ -43,6 +43,8 @@
|
||||||
"ethers": "^6.13.0",
|
"ethers": "^6.13.0",
|
||||||
"express": "^4.18.2",
|
"express": "^4.18.2",
|
||||||
"nodemailer": "^7.0.10",
|
"nodemailer": "^7.0.10",
|
||||||
|
"png-to-ico": "^3.0.1",
|
||||||
|
"sharp": "^0.34.5",
|
||||||
"stripe": "^15.12.0",
|
"stripe": "^15.12.0",
|
||||||
"zod": "^3.23.8"
|
"zod": "^3.23.8"
|
||||||
},
|
},
|
||||||
|
|
|
||||||
|
|
@ -38,6 +38,8 @@ The monolith (`aethex.dev`) implements split routing to enforce legal separation
|
||||||
This ensures the Foundation's user-facing URLs display `aethex.foundation` in the browser, demonstrating operational independence per the Axiom Model.
|
This ensures the Foundation's user-facing URLs display `aethex.foundation` in the browser, demonstrating operational independence per the Axiom Model.
|
||||||
|
|
||||||
## Recent Changes (December 2025)
|
## Recent Changes (December 2025)
|
||||||
|
- **Maintenance Mode**: Site-wide maintenance mode with admin bypass. Admins can toggle via Admin Dashboard overview tab. Uses MAINTENANCE_MODE env var for initial state. Allowed paths during maintenance: /login, /staff/login, /reset-password, /health
|
||||||
|
- **Health Endpoint**: Added /health endpoint at aethex.dev/health that aggregates platform and Discord bot status
|
||||||
- **Axiom Model Routing**: Foundation and GameForge routes redirect to `aethex.foundation` domain for legal entity separation
|
- **Axiom Model Routing**: Foundation and GameForge routes redirect to `aethex.foundation` domain for legal entity separation
|
||||||
- **AI Intelligent Agent Integration**: Added global AI chat with 10 specialized personas (Network Agent, Forge Master, Ethics Sentinel, SBS Architect, Curriculum Weaver, QuantumLeap, Vapor, Apex, Ethos Producer, AeThex Archivist)
|
- **AI Intelligent Agent Integration**: Added global AI chat with 10 specialized personas (Network Agent, Forge Master, Ethics Sentinel, SBS Architect, Curriculum Weaver, QuantumLeap, Vapor, Apex, Ethos Producer, AeThex Archivist)
|
||||||
- **Tiered Access Control**: AI personas gated by user tier (Free/Architect/Council) based on roles
|
- **Tiered Access Control**: AI personas gated by user tier (Free/Architect/Council) based on roles
|
||||||
|
|
|
||||||
123
server/index.ts
123
server/index.ts
|
|
@ -457,6 +457,129 @@ export function createServer() {
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// Health check endpoint - proxies to Discord bot health
|
||||||
|
app.get("/health", async (_req, res) => {
|
||||||
|
try {
|
||||||
|
const botHealthPort = process.env.HEALTH_PORT || 8080;
|
||||||
|
const response = await fetch(`http://localhost:${botHealthPort}/health`);
|
||||||
|
const data = await response.json();
|
||||||
|
res.json({
|
||||||
|
status: "online",
|
||||||
|
platform: "aethex.dev",
|
||||||
|
bot: data,
|
||||||
|
timestamp: new Date().toISOString(),
|
||||||
|
});
|
||||||
|
} catch (error: any) {
|
||||||
|
res.json({
|
||||||
|
status: "online",
|
||||||
|
platform: "aethex.dev",
|
||||||
|
bot: { status: "offline", error: error?.message || "Bot unreachable" },
|
||||||
|
timestamp: new Date().toISOString(),
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
// Maintenance Mode API endpoints
|
||||||
|
const ADMIN_ROLES = ["admin", "super_admin", "staff", "owner"];
|
||||||
|
|
||||||
|
// In-memory maintenance state (fallback when DB table doesn't exist)
|
||||||
|
let maintenanceModeCache: boolean | null = null;
|
||||||
|
|
||||||
|
// Get maintenance status (public)
|
||||||
|
app.get("/api/admin/platform/maintenance", async (_req, res) => {
|
||||||
|
try {
|
||||||
|
// Try database first
|
||||||
|
const { data, error } = await adminSupabase
|
||||||
|
.from("platform_settings")
|
||||||
|
.select("value")
|
||||||
|
.eq("key", "maintenance_mode")
|
||||||
|
.single();
|
||||||
|
|
||||||
|
if (error) {
|
||||||
|
// If table doesn't exist, use env var or in-memory cache
|
||||||
|
if (error.code === "42P01" || error.message?.includes("does not exist")) {
|
||||||
|
const envMaintenance = process.env.MAINTENANCE_MODE === "true";
|
||||||
|
res.json({ maintenance_mode: maintenanceModeCache ?? envMaintenance });
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
// Row not found is OK, means maintenance is off
|
||||||
|
if (error.code !== "PGRST116") {
|
||||||
|
throw error;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const isActive = data?.value === "true" || data?.value === true;
|
||||||
|
maintenanceModeCache = isActive;
|
||||||
|
res.json({ maintenance_mode: isActive });
|
||||||
|
} catch (e: any) {
|
||||||
|
console.error("[Maintenance] Error fetching status:", e?.message);
|
||||||
|
// Fall back to env var or cache
|
||||||
|
const envMaintenance = process.env.MAINTENANCE_MODE === "true";
|
||||||
|
res.json({ maintenance_mode: maintenanceModeCache ?? envMaintenance });
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
// Toggle maintenance mode (admin only)
|
||||||
|
app.post("/api/admin/platform/maintenance", async (req, res) => {
|
||||||
|
try {
|
||||||
|
const authHeader = req.headers.authorization;
|
||||||
|
if (!authHeader?.startsWith("Bearer ")) {
|
||||||
|
return res.status(401).json({ error: "Unauthorized" });
|
||||||
|
}
|
||||||
|
|
||||||
|
const token = authHeader.substring(7);
|
||||||
|
const { data: { user }, error: authError } = await adminSupabase.auth.getUser(token);
|
||||||
|
|
||||||
|
if (authError || !user) {
|
||||||
|
return res.status(401).json({ error: "Invalid token" });
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check if user has admin role
|
||||||
|
const { data: roles } = await adminSupabase
|
||||||
|
.from("user_roles")
|
||||||
|
.select("role")
|
||||||
|
.eq("user_id", user.id);
|
||||||
|
|
||||||
|
const userRoles = roles?.map((r: any) => r.role?.toLowerCase()) || [];
|
||||||
|
const isAdmin = userRoles.some((role: string) => ADMIN_ROLES.includes(role));
|
||||||
|
|
||||||
|
if (!isAdmin) {
|
||||||
|
return res.status(403).json({ error: "Admin access required" });
|
||||||
|
}
|
||||||
|
|
||||||
|
const rawValue = req.body?.maintenance_mode;
|
||||||
|
const newMaintenanceMode = rawValue === true || rawValue === "true";
|
||||||
|
|
||||||
|
// Try to upsert in database
|
||||||
|
const { error } = await adminSupabase
|
||||||
|
.from("platform_settings")
|
||||||
|
.upsert({
|
||||||
|
key: "maintenance_mode",
|
||||||
|
value: String(newMaintenanceMode),
|
||||||
|
updated_at: new Date().toISOString(),
|
||||||
|
updated_by: user.id,
|
||||||
|
}, { onConflict: "key" });
|
||||||
|
|
||||||
|
if (error) {
|
||||||
|
// If table doesn't exist, just use in-memory cache
|
||||||
|
if (error.code === "42P01" || error.message?.includes("does not exist")) {
|
||||||
|
maintenanceModeCache = newMaintenanceMode;
|
||||||
|
console.log(`[Maintenance] Mode set to ${newMaintenanceMode} (in-memory) by ${user.email}`);
|
||||||
|
return res.json({ maintenance_mode: newMaintenanceMode });
|
||||||
|
}
|
||||||
|
throw error;
|
||||||
|
}
|
||||||
|
|
||||||
|
maintenanceModeCache = newMaintenanceMode;
|
||||||
|
console.log(`[Maintenance] Mode set to ${newMaintenanceMode} by ${user.email}`);
|
||||||
|
|
||||||
|
res.json({ maintenance_mode: newMaintenanceMode });
|
||||||
|
} catch (e: any) {
|
||||||
|
console.error("[Maintenance] Error toggling:", e?.message);
|
||||||
|
res.status(500).json({ error: e?.message || "Failed to toggle maintenance mode" });
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
// Example API routes
|
// Example API routes
|
||||||
app.get("/api/ping", (_req, res) => {
|
app.get("/api/ping", (_req, res) => {
|
||||||
const ping = process.env.PING_MESSAGE ?? "ping";
|
const ping = process.env.PING_MESSAGE ?? "ping";
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue