Skip to content

Commit 1d74ea9

Browse files
committed
fixes and analytics for web
1 parent b6ce764 commit 1d74ea9

23 files changed

Lines changed: 751 additions & 74 deletions

.github/workflows/android.yml

Lines changed: 4 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -6,9 +6,6 @@ on:
66
- 'v*.*.*'
77
workflow_dispatch:
88

9-
env:
10-
FORCE_JAVASCRIPT_ACTIONS_TO_NODE24: true
11-
129
jobs:
1310
build-android:
1411
runs-on: ubuntu-latest
@@ -37,7 +34,7 @@ jobs:
3734
npx cap sync android
3835
3936
- name: Setup Java
40-
uses: actions/setup-java@v4
37+
uses: actions/setup-java@v5
4138
with:
4239
distribution: temurin
4340
java-version: '17'
@@ -51,7 +48,7 @@ jobs:
5148
run: ./gradlew assembleDebug
5249

5350
- name: Upload Debug APK
54-
uses: actions/upload-artifact@v5
51+
uses: actions/upload-artifact@v6
5552
with:
5653
name: app-debug-apk
5754
path: android/app/build/outputs/apk/debug/*.apk
@@ -93,14 +90,14 @@ jobs:
9390
fi
9491
9592
- name: Upload Release AAB
96-
uses: actions/upload-artifact@v5
93+
uses: actions/upload-artifact@v6
9794
with:
9895
name: app-release-aab
9996
path: android/app/build/outputs/bundle/release/*.aab
10097
if-no-files-found: ignore
10198

10299
- name: Upload Release APK
103-
uses: actions/upload-artifact@v5
100+
uses: actions/upload-artifact@v6
104101
with:
105102
name: app-release-apk
106103
path: android/app/build/outputs/apk/release/*.apk

.github/workflows/publish-aur.yml

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -19,9 +19,6 @@ on:
1919
permissions:
2020
contents: read
2121

22-
env:
23-
FORCE_JAVASCRIPT_ACTIONS_TO_NODE24: true
24-
2522
jobs:
2623
aur:
2724
runs-on: ubuntu-latest

.github/workflows/release.yml

Lines changed: 11 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,6 @@ permissions:
1414
contents: write
1515

1616
env:
17-
FORCE_JAVASCRIPT_ACTIONS_TO_NODE24: true
1817
APP_ID: io.streambooru.StreamBooru
1918
APP_NAME: StreamBooru
2019

@@ -60,7 +59,7 @@ jobs:
6059
cp dist/*.tar.gz release-linux/ || true
6160
cp dist/INSTALL.md release-linux/ || true
6261
ls -la release-linux
63-
- uses: actions/upload-artifact@v5
62+
- uses: actions/upload-artifact@v6
6463
with:
6564
name: linux
6665
path: release-linux
@@ -69,7 +68,7 @@ jobs:
6968
if: startsWith(github.ref, 'refs/tags/')
7069
continue-on-error: true
7170
needs: prep
72-
runs-on: windows-latest
71+
runs-on: windows-2025
7372
steps:
7473
- uses: actions/checkout@v5
7574
- name: Setup Node
@@ -91,7 +90,7 @@ jobs:
9190
cp dist/*.exe release-win/ || true
9291
cp docs/INSTALL.md release-win/INSTALL.md || true
9392
ls -la release-win
94-
- uses: actions/upload-artifact@v5
93+
- uses: actions/upload-artifact@v6
9594
with:
9695
name: windows
9796
path: release-win
@@ -134,7 +133,7 @@ jobs:
134133
ls -la release-flatpak
135134
test "$(find release-flatpak -maxdepth 1 -name '*.flatpak' | wc -l)" -gt 0
136135
137-
- uses: actions/upload-artifact@v5
136+
- uses: actions/upload-artifact@v6
138137
with:
139138
name: flatpak
140139
path: release-flatpak
@@ -169,7 +168,7 @@ jobs:
169168
npx cap sync android
170169
171170
- name: Setup Java
172-
uses: actions/setup-java@v4
171+
uses: actions/setup-java@v5
173172
with:
174173
distribution: temurin
175174
java-version: '17'
@@ -236,7 +235,7 @@ jobs:
236235
237236
- name: Upload APK artifact (for Release attachment)
238237
if: hashFiles('out-apk/*.apk') != ''
239-
uses: actions/upload-artifact@v5
238+
uses: actions/upload-artifact@v6
240239
with:
241240
name: android-apk
242241
path: out-apk/*.apk
@@ -248,7 +247,7 @@ jobs:
248247

249248
- name: Upload AAB artifact (private to Actions; not attached to Release)
250249
if: hashFiles('out-aab/*.aab') != ''
251-
uses: actions/upload-artifact@v5
250+
uses: actions/upload-artifact@v6
252251
with:
253252
name: android-aab
254253
path: out-aab/*.aab
@@ -266,7 +265,7 @@ jobs:
266265
fetch-depth: 0
267266

268267
- name: Download all artifacts
269-
uses: actions/download-artifact@v5
268+
uses: actions/download-artifact@v7
270269
with:
271270
path: ./artifacts
272271

@@ -336,7 +335,7 @@ jobs:
336335
337336
- name: Upload release notes (debug)
338337
if: always()
339-
uses: actions/upload-artifact@v5
338+
uses: actions/upload-artifact@v6
340339
with:
341340
name: release-notes-${{ github.ref_name }}
342341
path: |
@@ -348,7 +347,7 @@ jobs:
348347

349348
- name: Create/Update GitHub Release
350349
if: steps.body.outputs.found == 'true'
351-
uses: softprops/action-gh-release@v2
350+
uses: softprops/action-gh-release@v3
352351
with:
353352
tag_name: ${{ github.ref_name }}
354353
name: ${{ github.ref_name }}
@@ -366,7 +365,7 @@ jobs:
366365
367366
- name: Create/Update GitHub Release (auto-generated notes only)
368367
if: steps.body.outputs.found != 'true'
369-
uses: softprops/action-gh-release@v2
368+
uses: softprops/action-gh-release@v3
370369
with:
371370
tag_name: ${{ github.ref_name }}
372371
name: ${{ github.ref_name }}

.gitignore

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -134,6 +134,7 @@ dist
134134
!.yarn/sdks
135135
!.yarn/versions
136136

137-
# Vite logs files
138-
vite.config.js.timestamp-*
139-
vite.config.ts.timestamp-*
137+
# Proprietary AtlasAnalytics bundle (maintained outside the public OSS tree)
138+
/private/
139+
/renderer/analytics-private/
140+
/server/src/_analytics_private/

nixpacks.toml

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,13 @@ cmds = [
1414
cmds = ['cd server && bun install --ignore-scripts']
1515

1616
[phases.build]
17-
cmds = ['rm -rf server/webapp && cp -r renderer server/webapp']
17+
cmds = [
18+
'if [ -n "$ATLAS_ANALYTICS_REPO" ]; then rm -rf private/atlas-analytics && git clone --depth 1 "$ATLAS_ANALYTICS_REPO" private/atlas-analytics; fi',
19+
'node scripts/merge-private-analytics.mjs',
20+
'if [ -d private/atlas-analytics/client ]; then cd server && bun add @openpanel/sdk@^1.3.1 @swetrix/node@^3.2.0 swetrix@^4.2.0; fi',
21+
'node scripts/vendor-analytics.mjs || true',
22+
'rm -rf server/webapp && cp -r renderer server/webapp'
23+
]
1824

1925
[start]
2026
cmd = 'cd server && bun run start:prod'

renderer/index.html

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,11 +4,12 @@
44
<meta charset="utf-8" />
55
<title>StreamBooru</title>
66
<meta name="viewport" content="width=device-width, initial-scale=1, viewport-fit=cover" />
7-
<meta http-equiv="Content-Security-Policy" content="default-src 'self'; img-src 'self' data: blob: https: http:; media-src 'self' data: blob: https: http:; style-src 'self' 'unsafe-inline'; script-src 'self'; connect-src https: http:;">
7+
<meta http-equiv="Content-Security-Policy" content="default-src 'self'; img-src 'self' data: blob: https: http:; media-src 'self' data: blob: https: http:; style-src 'self' 'unsafe-inline'; script-src 'self' https://insights.atlastechsolutions.co.uk; connect-src https: http:;">
88
<link rel="stylesheet" href="./styles.css" />
99
<link rel="stylesheet" href="./mobile.css" media="(max-width: 900px)" />
1010
</head>
1111
<body>
12+
<script src="./js/analytics-loader.js"></script>
1213
<script src="./js/platform.js"></script>
1314

1415
<header class="topbar">

renderer/js/account.js

Lines changed: 27 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,8 @@
11
(function () {
2+
const isWebHostedAnalytics = () => window.SBWebAnalytics?.enabled?.() !== false
3+
&& !navigator.userAgent.includes('Electron')
4+
&& !(window.Capacitor?.getPlatform?.() === 'android');
5+
26
// elements
37
function h(tag, attrs = {}, children = []) {
48
const el = document.createElement(tag);
@@ -110,6 +114,13 @@
110114

111115
// local login
112116
const rowLocal = h('div', { className: 'fields-row' });
117+
const loginAnalyticsNotice = isWebHostedAnalytics()
118+
? (() => {
119+
const notice = h('p', { className: 'login-analytics-notice', hidden: '' });
120+
notice.setAttribute('data-login-analytics-disclosure', '');
121+
return notice;
122+
})()
123+
: null;
113124
const userInput = mkInput('Username', 'text');
114125
const passInput = mkInput('Password', 'password');
115126
const btnLoginLocal = h('button', { className: 'link-btn', text: 'Login (Local)' });
@@ -136,6 +147,7 @@
136147
card.appendChild(status);
137148
card.appendChild(serverRow);
138149
card.appendChild(rowRegister);
150+
if (loginAnalyticsNotice) card.appendChild(loginAnalyticsNotice);
139151
card.appendChild(rowLocal);
140152
card.appendChild(rowDiscord);
141153
card.appendChild(rowInfo);
@@ -206,15 +218,18 @@
206218
await window.api.accountSetServer?.(origin || serverSelect.value);
207219
}
208220

209-
const who = a.user ? `${a.user.name || a.user.id}` : 'Not logged in';
210-
status.textContent = `Server: ${serverSelect.value}${a.loggedIn ? 'Logged in as ' + who : 'Not logged in'}`;
221+
const who = a.user ? (a.user.name || a.user.id) : null;
222+
status.textContent = a.loggedIn
223+
? `Server: ${serverSelect.value} • Logged in${who ? ' as ' + who : ''}`
224+
: `Server: ${serverSelect.value} • Not logged in`;
211225

212226
const linked = !!a?.user?.discord_id;
213-
linkBadge.textContent = linked ? 'Discord linked' : 'Discord not linked';
214-
linkBadge.className = 'badge ' + (linked ? 'ok' : 'muted');
227+
linkBadge.textContent = linked ? 'Discord linked' : (a.loggedIn ? 'Signed in' : 'Discord not linked');
228+
linkBadge.className = 'badge ' + (linked ? 'ok' : (a.loggedIn ? 'ok' : 'muted'));
215229

216230
btnLinkDiscord.disabled = !a.loggedIn || linked;
217231
btnLoginDiscord.disabled = !serverSelect.value || a.loggedIn;
232+
btnLoginDiscord.title = a.loggedIn ? 'You are already logged in' : 'Sign in with Discord';
218233
btnUnlinkDiscord.disabled = !a.loggedIn || !linked;
219234
btnLoginLocal.disabled = !serverSelect.value || a.loggedIn;
220235
btnRegister.disabled = !serverSelect.value || a.loggedIn;
@@ -252,6 +267,7 @@
252267
btnRegister.addEventListener('click', async () => {
253268
try {
254269
btnRegister.disabled = true;
270+
if (isWebHostedAnalytics()) window.SBAnalytics?.trackEvent?.('register_form_started', { form: 'account_modal' });
255271
const u = regUser.value.trim();
256272
const p = regPass.value;
257273
if (!u || !p) { alert('Enter username and password'); return; }
@@ -265,6 +281,7 @@
265281
btnLoginLocal.addEventListener('click', async () => {
266282
try {
267283
btnLoginLocal.disabled = true;
284+
if (isWebHostedAnalytics()) window.SBAnalytics?.trackEvent?.('login_form_started', { form: 'account_modal' });
268285
const u = userInput.value.trim();
269286
const p = passInput.value;
270287
if (!u || !p) { alert('Enter username and password'); return; }
@@ -305,6 +322,7 @@
305322
btnLoginDiscord.addEventListener('click', (e) => {
306323
e.preventDefault();
307324
e.stopPropagation();
325+
if (btnLoginDiscord.disabled) return;
308326
btnLoginDiscord.disabled = true;
309327
try {
310328
const onWeb = typeof window !== 'undefined'
@@ -357,6 +375,11 @@
357375
});
358376

359377
await refresh();
378+
if (loginAnalyticsNotice) {
379+
const syncLoginDisclosure = () => window.SBAnalytics?.updateLoginDisclosure?.(loginAnalyticsNotice);
380+
syncLoginDisclosure();
381+
window.SBConsent?.onConsentChange?.(syncLoginDisclosure);
382+
}
360383
setTimeout(() => panel.focus(), 0);
361384
}
362385

0 commit comments

Comments
 (0)