memi-board 0.45.1 → 0.46.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +20 -6
- package/dist/composables/boardLookup.d.ts +2 -0
- package/dist/composables/useMemiBoardAuth.d.ts +5 -1
- package/dist/config.d.ts +2 -0
- package/dist/{en-DxkqyZq2.js → en-CaPfPNDy.js} +7 -2
- package/dist/en-CaPfPNDy.js.map +1 -0
- package/dist/index.js +375 -347
- package/dist/index.js.map +1 -1
- package/dist/runtime/components/CategorySettings.vue +12 -5
- package/dist/runtime/components/Settings.vue +8 -1
- package/dist/runtime/components/Users.vue +4 -3
- package/dist/{slugify-BuOMFLxN.js → slugify-DJ82ifCd.js} +13 -5
- package/dist/slugify-DJ82ifCd.js.map +1 -0
- package/dist/storage.js +1 -1
- package/dist/types.d.ts +3 -1
- package/dist/utils/boardAccess.d.ts +3 -0
- package/dist/utils/section.d.ts +1 -1
- package/docs/firebase-setup.md +30 -2
- package/docs/firestore.rules.example +24 -8
- package/docs/roles-migration.md +32 -0
- package/docs/storage.rules.example +4 -4
- package/package.json +1 -1
- package/dist/en-DxkqyZq2.js.map +0 -1
- package/dist/slugify-BuOMFLxN.js.map +0 -1
package/dist/index.js
CHANGED
|
@@ -1,10 +1,10 @@
|
|
|
1
|
-
import { A as e, B as t, C as n, D as r, E as i, F as a, G as o, H as s, I as c, L as l, M as u, N as d, O as f, P as p, R as m, S as h, T as g, U as _, V as v, W as y, _ as b, a as x, b as S, c as C, d as w, f as T, g as E, h as D, i as O, j as k, k as ee, l as
|
|
2
|
-
import { computed as
|
|
3
|
-
import { deleteDoc as
|
|
4
|
-
import { useCollection as
|
|
5
|
-
import { GoogleAuthProvider as
|
|
6
|
-
import { deleteObject as
|
|
7
|
-
import { GoogleAIBackend as
|
|
1
|
+
import { A as e, B as t, C as n, D as r, E as i, F as a, G as o, H as s, I as c, L as l, M as u, N as d, O as f, P as p, R as m, S as h, T as g, U as _, V as v, W as y, _ as b, a as x, b as S, c as C, d as w, f as T, g as E, h as D, i as O, j as k, k as ee, l as A, m as j, n as te, o as ne, p as re, r as ie, s as ae, u as oe, v as M, w as se, x as ce, y as le, z as N } from "./slugify-DJ82ifCd.js";
|
|
2
|
+
import { computed as P, onScopeDispose as F, reactive as ue, ref as I, toValue as L, watch as R } from "vue";
|
|
3
|
+
import { deleteDoc as de, deleteField as fe, doc as pe, documentId as z, endAt as me, endBefore as he, getDoc as B, getDocs as V, increment as H, limit as U, limitToLast as ge, onSnapshot as W, orderBy as G, query as K, runTransaction as _e, serverTimestamp as q, setDoc as J, startAfter as Y, updateDoc as X, where as Z, writeBatch as ve } from "firebase/firestore";
|
|
4
|
+
import { useCollection as ye, useCurrentUser as be, useDocument as xe, useFirebaseApp as Se, useFirebaseAuth as Ce, useFirestore as Q } from "vuefire";
|
|
5
|
+
import { GoogleAuthProvider as we, OAuthProvider as Te, createUserWithEmailAndPassword as Ee, signInWithEmailAndPassword as De, signInWithPopup as Oe, signOut as ke, updateProfile as Ae } from "firebase/auth";
|
|
6
|
+
import { deleteObject as je, getStorage as Me, listAll as Ne, ref as Pe } from "firebase/storage";
|
|
7
|
+
import { GoogleAIBackend as Fe, Schema as Ie, getAI as Le, getGenerativeModel as Re } from "firebase/ai";
|
|
8
8
|
//#region src/utils/boardSeo.ts
|
|
9
9
|
function ze(e, t) {
|
|
10
10
|
return !e || e === "전체" || e === w(t, "seo.allCategory");
|
|
@@ -64,13 +64,13 @@ function qe(e) {
|
|
|
64
64
|
//#region src/composables/fetchPublicSeo.ts
|
|
65
65
|
function Je() {
|
|
66
66
|
return {
|
|
67
|
-
db:
|
|
68
|
-
paths:
|
|
67
|
+
db: Q(),
|
|
68
|
+
paths: M()
|
|
69
69
|
};
|
|
70
70
|
}
|
|
71
71
|
async function Ye(e, t) {
|
|
72
72
|
try {
|
|
73
|
-
let n = await
|
|
73
|
+
let n = await B(o(e.db, e.paths, t));
|
|
74
74
|
if (!n.exists()) return {
|
|
75
75
|
label: t,
|
|
76
76
|
description: "",
|
|
@@ -107,7 +107,7 @@ async function Ze(e, t, n) {
|
|
|
107
107
|
let o = await Ye(a, r);
|
|
108
108
|
if (o.hidden) return null;
|
|
109
109
|
try {
|
|
110
|
-
let e = (await
|
|
110
|
+
let e = (await V(K(N(a.db, a.paths), Z("boardId", "==", r), Z("slug", "==", i), Z("listed", "==", !0), Z("isPublished", "==", !0), U(1)))).docs[0];
|
|
111
111
|
if (!e) return null;
|
|
112
112
|
let t = e.data() ?? {}, n = typeof t.title == "string" ? t.title.trim() : "";
|
|
113
113
|
return n ? {
|
|
@@ -126,7 +126,7 @@ async function Ze(e, t, n) {
|
|
|
126
126
|
}
|
|
127
127
|
}
|
|
128
128
|
async function Qe(e, t, n) {
|
|
129
|
-
n && await
|
|
129
|
+
n && await oe(n);
|
|
130
130
|
let r = e?.trim() || null, i = t ?? Je();
|
|
131
131
|
if (i.paths = _(i.paths), r) {
|
|
132
132
|
let e = await Ye(i, r);
|
|
@@ -160,7 +160,7 @@ async function Qe(e, t, n) {
|
|
|
160
160
|
async function $e(e, t) {
|
|
161
161
|
let n = [], r = null;
|
|
162
162
|
try {
|
|
163
|
-
let i = await
|
|
163
|
+
let i = await V(K(N(e.db, e.paths), Z("boardId", "==", t), Z("listed", "==", !0), Z("isPublished", "==", !0), G("createdAt", "desc"), U(12)));
|
|
164
164
|
for (let e of i.docs) {
|
|
165
165
|
let t = e.data() ?? {}, i = typeof t.title == "string" ? t.title.trim() : "";
|
|
166
166
|
i && n.length < 5 && n.push(i), r ||= Ve(t.previewImage);
|
|
@@ -176,7 +176,7 @@ async function $e(e, t) {
|
|
|
176
176
|
//#endregion
|
|
177
177
|
//#region src/utils/boardAccess.ts
|
|
178
178
|
function et(e, t) {
|
|
179
|
-
return !e || !t ? !1 :
|
|
179
|
+
return !e || !t ? !1 : [...t.allowedStaffUids ?? [], ...t.allowedManagerUids ?? []].includes(e);
|
|
180
180
|
}
|
|
181
181
|
function tt(e, t, n, r) {
|
|
182
182
|
return e ? t ? !0 : n ? et(e, r) : !1 : !1;
|
|
@@ -244,15 +244,15 @@ var pt = "__MEMI_BOARD_AUTH_STATE__";
|
|
|
244
244
|
function mt() {
|
|
245
245
|
let e = globalThis;
|
|
246
246
|
return e[pt] || (e[pt] = {
|
|
247
|
-
role:
|
|
248
|
-
rolePending:
|
|
249
|
-
rawBlockCount:
|
|
250
|
-
blockAtMs:
|
|
247
|
+
role: I("user"),
|
|
248
|
+
rolePending: I(!0),
|
|
249
|
+
rawBlockCount: I(0),
|
|
250
|
+
blockAtMs: I(null),
|
|
251
251
|
watchStarted: !1
|
|
252
252
|
}), e[pt];
|
|
253
253
|
}
|
|
254
254
|
function ht() {
|
|
255
|
-
let e =
|
|
255
|
+
let e = le(), { t, locale: n } = O(), r = mt(), i = Q(), a = Ce(), o = be(), { role: s, rolePending: c, rawBlockCount: l, blockAtMs: u } = r;
|
|
256
256
|
function d() {
|
|
257
257
|
let t = e.moderation?.blockBanThreshold;
|
|
258
258
|
return t === 0 ? 0 : typeof t == "number" && t > 0 ? Math.floor(t) : 10;
|
|
@@ -262,33 +262,41 @@ function ht() {
|
|
|
262
262
|
return typeof t == "number" && t > 0 ? t : st;
|
|
263
263
|
}
|
|
264
264
|
function m(e) {
|
|
265
|
-
return f(i,
|
|
265
|
+
return f(i, M(), e);
|
|
266
266
|
}
|
|
267
267
|
function h(e) {
|
|
268
|
-
if (
|
|
268
|
+
if (s.value = [
|
|
269
|
+
"owner",
|
|
270
|
+
"admin",
|
|
271
|
+
"manager",
|
|
272
|
+
"staff",
|
|
273
|
+
"user"
|
|
274
|
+
].includes(String(e?.role)) ? e?.role : "user", !e) {
|
|
269
275
|
l.value = 0, u.value = null;
|
|
270
276
|
return;
|
|
271
277
|
}
|
|
272
278
|
l.value = Math.max(0, Math.floor(Number(e.moderationBlockCount) || 0)), u.value = ft(e.moderationBlockAt);
|
|
273
279
|
}
|
|
274
280
|
async function g(e) {
|
|
275
|
-
let t = m(e.uid), n = ee(i,
|
|
276
|
-
if (!r.exists()) return await Promise.all([
|
|
281
|
+
let t = m(e.uid), n = ee(i, M(), e.uid), r = await B(t);
|
|
282
|
+
if (!r.exists()) return await Promise.all([J(t, {
|
|
277
283
|
role: "user",
|
|
278
284
|
displayName: e.displayName,
|
|
279
285
|
photoURL: e.photoURL,
|
|
280
|
-
joinedAt:
|
|
281
|
-
lastVisitAt:
|
|
282
|
-
updatedAt:
|
|
283
|
-
}),
|
|
286
|
+
joinedAt: q(),
|
|
287
|
+
lastVisitAt: q(),
|
|
288
|
+
updatedAt: q()
|
|
289
|
+
}), J(n, { email: e.email })]), h({ moderationBlockCount: 0 }), "user";
|
|
284
290
|
let a = r.data();
|
|
285
291
|
h(a);
|
|
286
292
|
let o = typeof a.displayName == "string" && a.displayName.trim(), s = typeof a.photoURL == "string" && a.photoURL.trim(), c = {
|
|
287
|
-
lastVisitAt:
|
|
288
|
-
updatedAt:
|
|
293
|
+
lastVisitAt: q(),
|
|
294
|
+
updatedAt: q()
|
|
289
295
|
};
|
|
290
|
-
return !o && e.displayName && (c.displayName = e.displayName), !s && e.photoURL && (c.photoURL = e.photoURL), await Promise.all([
|
|
296
|
+
return !o && e.displayName && (c.displayName = e.displayName), !s && e.photoURL && (c.photoURL = e.photoURL), await Promise.all([X(t, c), J(n, { email: e.email }, { merge: !0 })]), [
|
|
297
|
+
"owner",
|
|
291
298
|
"admin",
|
|
299
|
+
"manager",
|
|
292
300
|
"staff",
|
|
293
301
|
"user"
|
|
294
302
|
].includes(String(a.role)) ? a.role : "user";
|
|
@@ -299,10 +307,10 @@ function ht() {
|
|
|
299
307
|
h(void 0);
|
|
300
308
|
return;
|
|
301
309
|
}
|
|
302
|
-
let t = await
|
|
310
|
+
let t = await B(m(e));
|
|
303
311
|
h(t.exists() ? t.data() : void 0);
|
|
304
312
|
}
|
|
305
|
-
r.watchStarted || (r.watchStarted = !0,
|
|
313
|
+
r.watchStarted || (r.watchStarted = !0, R(o, async (e) => {
|
|
306
314
|
if (c.value = !0, !e) {
|
|
307
315
|
s.value = "user", h(void 0), c.value = !1;
|
|
308
316
|
return;
|
|
@@ -315,37 +323,37 @@ function ht() {
|
|
|
315
323
|
c.value = !1;
|
|
316
324
|
}
|
|
317
325
|
}, { immediate: !0 }));
|
|
318
|
-
let v =
|
|
326
|
+
let v = P(() => !!o.value), y = P(() => s.value === "owner"), b = P(() => s.value === "manager"), x = P(() => y.value || s.value === "admin"), S = P(() => b.value || s.value === "staff"), C = P(() => x.value || S.value), w = P(() => ct(l.value, u.value, Date.now(), p())), T = P(() => {
|
|
319
327
|
let e = d();
|
|
320
328
|
return e <= 0 ? !1 : ut(l.value, u.value, Date.now(), e, p());
|
|
321
|
-
}),
|
|
329
|
+
}), E = P(() => {
|
|
322
330
|
let e = d();
|
|
323
331
|
if (e <= 0) return null;
|
|
324
332
|
let t = lt(l.value, u.value, Date.now(), e, p());
|
|
325
333
|
return t == null ? null : dt(t, Date.now(), n.value);
|
|
326
|
-
}),
|
|
327
|
-
if (!
|
|
328
|
-
let e =
|
|
334
|
+
}), D = P(() => {
|
|
335
|
+
if (!T.value) return null;
|
|
336
|
+
let e = E.value;
|
|
329
337
|
return e ? t("auth.writeRestrictedUntil", { until: e }) : t("auth.writeRestricted");
|
|
330
338
|
});
|
|
331
|
-
async function
|
|
339
|
+
async function k() {
|
|
332
340
|
let e = o.value?.uid, r = d();
|
|
333
341
|
if (!e || r <= 0) return {
|
|
334
342
|
effectiveCount: 0,
|
|
335
343
|
restricted: !1,
|
|
336
344
|
messageSuffix: ""
|
|
337
345
|
};
|
|
338
|
-
let i = m(e), a = await
|
|
339
|
-
a.exists() ? await
|
|
340
|
-
moderationBlockCount:
|
|
341
|
-
moderationBlockAt:
|
|
342
|
-
updatedAt:
|
|
343
|
-
}) : await
|
|
346
|
+
let i = m(e), a = await B(i);
|
|
347
|
+
a.exists() ? await X(i, {
|
|
348
|
+
moderationBlockCount: H(1),
|
|
349
|
+
moderationBlockAt: q(),
|
|
350
|
+
updatedAt: q()
|
|
351
|
+
}) : await J(i, {
|
|
344
352
|
role: "user",
|
|
345
353
|
displayName: o.value?.displayName ?? null,
|
|
346
354
|
moderationBlockCount: 1,
|
|
347
|
-
moderationBlockAt:
|
|
348
|
-
updatedAt:
|
|
355
|
+
moderationBlockAt: q(),
|
|
356
|
+
updatedAt: q()
|
|
349
357
|
});
|
|
350
358
|
let s = (a.exists() ? Math.max(0, Math.floor(Number(a.data().moderationBlockCount) || 0)) : 0) + 1, c = Date.now();
|
|
351
359
|
l.value = s, u.value = c;
|
|
@@ -366,61 +374,68 @@ function ht() {
|
|
|
366
374
|
messageSuffix: g
|
|
367
375
|
};
|
|
368
376
|
}
|
|
369
|
-
function
|
|
377
|
+
function A() {
|
|
370
378
|
if (!a) throw Error(t("auth.notInitialized"));
|
|
371
379
|
return a;
|
|
372
380
|
}
|
|
373
|
-
async function
|
|
374
|
-
return
|
|
381
|
+
async function j() {
|
|
382
|
+
return Oe(A(), new we());
|
|
375
383
|
}
|
|
376
384
|
async function te() {
|
|
377
|
-
let e = new
|
|
378
|
-
return e.addScope("email"), e.addScope("name"),
|
|
385
|
+
let e = new Te("apple.com");
|
|
386
|
+
return e.addScope("email"), e.addScope("name"), Oe(A(), e);
|
|
379
387
|
}
|
|
380
|
-
async function
|
|
381
|
-
return
|
|
382
|
-
}
|
|
383
|
-
async function ne(e, t, n) {
|
|
384
|
-
let r = await De(D(), e, t);
|
|
385
|
-
return n && await je(r.user, { displayName: n }), r;
|
|
388
|
+
async function ne(e, t) {
|
|
389
|
+
return De(A(), e, t);
|
|
386
390
|
}
|
|
387
|
-
async function re() {
|
|
388
|
-
await
|
|
391
|
+
async function re(e, t, n) {
|
|
392
|
+
let r = await Ee(A(), e, t);
|
|
393
|
+
return n && await Ae(r.user, { displayName: n }), r;
|
|
389
394
|
}
|
|
390
|
-
function ie(
|
|
391
|
-
|
|
395
|
+
async function ie() {
|
|
396
|
+
await ke(A());
|
|
392
397
|
}
|
|
393
398
|
function ae(e) {
|
|
394
|
-
return
|
|
399
|
+
return tt(o.value?.uid, x.value, S.value, e ? at(e) : void 0);
|
|
395
400
|
}
|
|
396
401
|
function oe(e) {
|
|
397
|
-
return
|
|
402
|
+
return o.value ? x.value ? !0 : b.value && !!e && (at(e)?.allowedManagerUids ?? []).includes(o.value.uid) : !1;
|
|
398
403
|
}
|
|
399
404
|
function se(e) {
|
|
400
|
-
return v.value && (o.value?.uid === e.authorUid ||
|
|
405
|
+
return v.value && (o.value?.uid === e.authorUid || ae(e.boardId));
|
|
406
|
+
}
|
|
407
|
+
function ce(e) {
|
|
408
|
+
return v.value && o.value?.uid === e.authorUid;
|
|
409
|
+
}
|
|
410
|
+
function N(e) {
|
|
411
|
+
return v.value && (o.value?.uid === e.authorUid || ae(e.boardId));
|
|
401
412
|
}
|
|
402
413
|
return {
|
|
403
414
|
user: o,
|
|
415
|
+
role: s,
|
|
416
|
+
isOwner: y,
|
|
417
|
+
isManager: b,
|
|
418
|
+
canConfigureBoard: oe,
|
|
404
419
|
isSignedIn: v,
|
|
405
|
-
isAdmin:
|
|
406
|
-
isStaff:
|
|
407
|
-
canManageContent:
|
|
408
|
-
canManageBoard:
|
|
420
|
+
isAdmin: x,
|
|
421
|
+
isStaff: S,
|
|
422
|
+
canManageContent: C,
|
|
423
|
+
canManageBoard: ae,
|
|
409
424
|
rolePending: c,
|
|
410
|
-
moderationBlockCount:
|
|
411
|
-
isWriteRestricted:
|
|
412
|
-
restrictedUntilLabel:
|
|
413
|
-
restrictedMessage:
|
|
414
|
-
signInWithGoogle:
|
|
425
|
+
moderationBlockCount: w,
|
|
426
|
+
isWriteRestricted: T,
|
|
427
|
+
restrictedUntilLabel: E,
|
|
428
|
+
restrictedMessage: D,
|
|
429
|
+
signInWithGoogle: j,
|
|
415
430
|
signInWithApple: te,
|
|
416
|
-
signInWithEmail:
|
|
417
|
-
signUpWithEmail:
|
|
418
|
-
signOut:
|
|
419
|
-
canEdit:
|
|
420
|
-
canDelete:
|
|
421
|
-
canEditComment:
|
|
422
|
-
canDeleteComment:
|
|
423
|
-
recordContentModerationBlock:
|
|
431
|
+
signInWithEmail: ne,
|
|
432
|
+
signUpWithEmail: re,
|
|
433
|
+
signOut: ie,
|
|
434
|
+
canEdit: se,
|
|
435
|
+
canDelete: se,
|
|
436
|
+
canEditComment: ce,
|
|
437
|
+
canDeleteComment: N,
|
|
438
|
+
recordContentModerationBlock: k,
|
|
424
439
|
refreshBoardUser: _
|
|
425
440
|
};
|
|
426
441
|
}
|
|
@@ -448,8 +463,8 @@ function yt(e) {
|
|
|
448
463
|
//#endregion
|
|
449
464
|
//#region src/utils/findReadablePost.ts
|
|
450
465
|
async function bt(e, t, n, r, i, a) {
|
|
451
|
-
let o = [
|
|
452
|
-
return a ? (await
|
|
466
|
+
let o = [Z("boardId", "==", n), Z("slug", "==", r)];
|
|
467
|
+
return a ? (await V(K(N(e, t), ...o, U(1)))).docs[0] : (await Promise.all([V(K(N(e, t), ...o, Z("listed", "==", !0), Z("isPublished", "==", !0), U(1))), ...i ? [V(K(N(e, t), ...o, Z("authorUid", "==", i), U(1)))] : []])).flatMap((e) => e.docs)[0];
|
|
453
468
|
}
|
|
454
469
|
//#endregion
|
|
455
470
|
//#region src/utils/extractEditorImageUrls.ts
|
|
@@ -479,36 +494,36 @@ function Ct(e) {
|
|
|
479
494
|
//#region src/utils/deletePostCascade.ts
|
|
480
495
|
async function wt(e) {
|
|
481
496
|
try {
|
|
482
|
-
let t = await
|
|
483
|
-
await Promise.all([...t.items.map((e) =>
|
|
497
|
+
let t = await Ne(e);
|
|
498
|
+
await Promise.all([...t.items.map((e) => je(e).catch(() => {})), ...t.prefixes.map((e) => wt(e))]);
|
|
484
499
|
} catch {}
|
|
485
500
|
}
|
|
486
501
|
async function Tt(e, t) {
|
|
487
|
-
await wt(
|
|
502
|
+
await wt(Pe(e, `${t}/images`)), await wt(Pe(e, `${t}/attachments`));
|
|
488
503
|
}
|
|
489
504
|
async function Et(e, t) {
|
|
490
505
|
let n = [...new Set([...t].filter(Boolean))];
|
|
491
|
-
await Promise.all(n.map((t) =>
|
|
506
|
+
await Promise.all(n.map((t) => je(Pe(e, t)).catch(() => {})));
|
|
492
507
|
}
|
|
493
508
|
var Dt = 450;
|
|
494
509
|
async function Ot(e, t) {
|
|
495
|
-
let n = await
|
|
510
|
+
let n = await V(t);
|
|
496
511
|
for (let t = 0; t < n.docs.length; t += Dt) {
|
|
497
|
-
let r =
|
|
512
|
+
let r = ve(e);
|
|
498
513
|
n.docs.slice(t, t + Dt).forEach((e) => r.delete(e.ref)), await r.commit();
|
|
499
514
|
}
|
|
500
515
|
}
|
|
501
516
|
async function kt(e, t, n) {
|
|
502
|
-
await Ot(e,
|
|
517
|
+
await Ot(e, K(a(e, t), Z("postId", "==", n)));
|
|
503
518
|
}
|
|
504
519
|
async function At(e, t, n) {
|
|
505
|
-
await Ot(e,
|
|
520
|
+
await Ot(e, K(a(e, t), Z("commentId", "==", n), Z("target", "==", "comment")));
|
|
506
521
|
}
|
|
507
522
|
async function jt(e, t, n, r) {
|
|
508
|
-
let i = l(e, n, r), a = c(e, n, r), [o, s] = await Promise.all([
|
|
523
|
+
let i = l(e, n, r), a = c(e, n, r), [o, s] = await Promise.all([B(i), B(a)]);
|
|
509
524
|
if (!o.exists()) return;
|
|
510
525
|
let d = o.data(), f = s.exists() ? String(s.data().content ?? "") : "";
|
|
511
|
-
await Ot(e,
|
|
526
|
+
await Ot(e, K(u(e, n), Z("postId", "==", r))), await kt(e, n, r);
|
|
512
527
|
let p = /* @__PURE__ */ new Set(), h = /* @__PURE__ */ new Set();
|
|
513
528
|
for (let e of d.attachments ?? []) {
|
|
514
529
|
if (!e?.path) continue;
|
|
@@ -527,9 +542,9 @@ async function jt(e, t, n, r) {
|
|
|
527
542
|
let a = Ct(t);
|
|
528
543
|
a && a !== r && h.add(a);
|
|
529
544
|
}
|
|
530
|
-
await
|
|
545
|
+
await de(a), await Tt(t, m(n, r));
|
|
531
546
|
for (let e of h) await Tt(t, m(n, e));
|
|
532
|
-
await Et(t, p), await
|
|
547
|
+
await Et(t, p), await de(i);
|
|
533
548
|
}
|
|
534
549
|
//#endregion
|
|
535
550
|
//#region src/utils/postBody.ts
|
|
@@ -586,19 +601,19 @@ function Vt(e) {
|
|
|
586
601
|
async function Ht(e, t, n, r) {
|
|
587
602
|
let i;
|
|
588
603
|
for (;;) {
|
|
589
|
-
let a = await
|
|
604
|
+
let a = await V(K(t, Z("boardId", "==", n), G("__name__"), ...i ? [Y(i)] : [], U(400)));
|
|
590
605
|
if (a.empty) break;
|
|
591
|
-
let o =
|
|
606
|
+
let o = ve(e), s = 0;
|
|
592
607
|
for (let e of a.docs) e.data().listed !== r && (o.update(e.ref, { listed: r }), s++);
|
|
593
608
|
if (s && await o.commit(), i = a.docs[a.docs.length - 1], a.docs.length < 400) break;
|
|
594
609
|
}
|
|
595
610
|
}
|
|
596
611
|
async function Ut(e, t, n, r) {
|
|
597
|
-
await Ht(e,
|
|
612
|
+
await Ht(e, N(e, t), n, r), await Ht(e, u(e, t), n, r);
|
|
598
613
|
}
|
|
599
614
|
async function Wt(e, t, n, r) {
|
|
600
615
|
let i = o(e, t, n), a = Vt(r.visibility);
|
|
601
|
-
await
|
|
616
|
+
await _e(e, async (e) => {
|
|
602
617
|
let t = await e.get(i), n = t.data(), o = n?.visibilityTransition || "";
|
|
603
618
|
if (o && o !== a) throw Error("Finish the pending visibility change before changing it again.");
|
|
604
619
|
return !t.exists() || !o && Vt(n?.visibility) === a ? (e.set(i, r, { merge: !0 }), !1) : (e.set(i, {
|
|
@@ -606,12 +621,12 @@ async function Wt(e, t, n, r) {
|
|
|
606
621
|
visibility: a === "public" ? "public" : Vt(n?.visibility),
|
|
607
622
|
visibilityTransition: a
|
|
608
623
|
}, { merge: !0 }), !0);
|
|
609
|
-
}) && (await Ut(e, t, n, a !== "hidden"), await
|
|
624
|
+
}) && (await Ut(e, t, n, a !== "hidden"), await _e(e, async (e) => {
|
|
610
625
|
if ((await e.get(i)).data()?.visibilityTransition !== a) throw Error("The visibility transition changed. Reload and retry.");
|
|
611
626
|
e.update(i, {
|
|
612
627
|
visibility: a,
|
|
613
628
|
visibilityTransition: "",
|
|
614
|
-
updatedAt:
|
|
629
|
+
updatedAt: q()
|
|
615
630
|
});
|
|
616
631
|
}));
|
|
617
632
|
}
|
|
@@ -662,11 +677,12 @@ function Jt(e, t, n) {
|
|
|
662
677
|
writeRole: t.writeRole ?? "user",
|
|
663
678
|
commentWriteRole: t.commentWriteRole ?? "user",
|
|
664
679
|
allowedStaffUids: Array.isArray(t.allowedStaffUids) ? t.allowedStaffUids : [],
|
|
680
|
+
allowedManagerUids: Array.isArray(t.allowedManagerUids) ? t.allowedManagerUids : [],
|
|
665
681
|
locale: E(t.locale) ?? ""
|
|
666
682
|
};
|
|
667
683
|
}
|
|
668
684
|
function Yt() {
|
|
669
|
-
let e = () =>
|
|
685
|
+
let e = () => M(), t = Q(), n = Se(), { isSignedIn: i, isAdmin: a, isStaff: s, user: c } = ht(), { t: l } = O(), u = P(() => K(y(t, e()), G("order", "asc"))), { data: d, pending: f } = ye(u, { ssrKey: r(e(), "boards") }), p = P(() => d.value.map((e, t) => Jt(e.id, e, t))), m = p, h = P(() => p.value.filter((e) => e.visibility !== "hidden")), g = h;
|
|
670
686
|
function _(e) {
|
|
671
687
|
if (e) return p.value.find((t) => t.id === e)?.label ?? e;
|
|
672
688
|
}
|
|
@@ -690,8 +706,8 @@ function Yt() {
|
|
|
690
706
|
function k(e) {
|
|
691
707
|
return tt(c.value?.uid, a.value, s.value, e ? D(e) : void 0);
|
|
692
708
|
}
|
|
693
|
-
let ee =
|
|
694
|
-
function
|
|
709
|
+
let ee = P(() => p.value.filter((e) => k(e.id)));
|
|
710
|
+
function A(e, t) {
|
|
695
711
|
return {
|
|
696
712
|
label: e.label.trim(),
|
|
697
713
|
description: (e.description ?? "").trim(),
|
|
@@ -701,53 +717,54 @@ function Yt() {
|
|
|
701
717
|
writeRole: e.writeRole ?? "user",
|
|
702
718
|
commentWriteRole: e.commentWriteRole ?? "user",
|
|
703
719
|
allowedStaffUids: e.allowedStaffUids ?? [],
|
|
720
|
+
allowedManagerUids: e.allowedManagerUids ?? [],
|
|
704
721
|
locale: E(e.locale) ?? "",
|
|
705
722
|
order: t,
|
|
706
|
-
updatedAt:
|
|
723
|
+
updatedAt: q()
|
|
707
724
|
};
|
|
708
725
|
}
|
|
709
|
-
async function
|
|
726
|
+
async function j(n, r = n.order ?? 0) {
|
|
710
727
|
if (!i.value) throw Error(l("boardSettings.signInRequired"));
|
|
711
728
|
let a = n.id.trim(), o = n.label.trim();
|
|
712
729
|
if (!a || !o) throw Error(l("boardSettings.idAndNameRequired"));
|
|
713
|
-
let s = qt(n.visibility), c =
|
|
730
|
+
let s = qt(n.visibility), c = A({
|
|
714
731
|
...n,
|
|
715
732
|
label: o,
|
|
716
733
|
visibility: s
|
|
717
734
|
}, r);
|
|
718
735
|
await Wt(t, e(), a, c);
|
|
719
736
|
}
|
|
720
|
-
let
|
|
721
|
-
async function
|
|
737
|
+
let ne = j;
|
|
738
|
+
async function re(e) {
|
|
722
739
|
if (!i.value) throw Error(l("boardSettings.signInRequired"));
|
|
723
740
|
for (let t of e) if (!t.id.trim() || !t.label.trim()) throw Error(l("boardSettings.idAndNameRequired"));
|
|
724
|
-
for (let [t, n] of e.entries()) await
|
|
741
|
+
for (let [t, n] of e.entries()) await j(n, t);
|
|
725
742
|
}
|
|
726
|
-
let
|
|
727
|
-
async function
|
|
743
|
+
let ie = re;
|
|
744
|
+
async function ae(r) {
|
|
728
745
|
if (!i.value) throw Error(l("boardSettings.signInRequired"));
|
|
729
746
|
let a = r.trim();
|
|
730
747
|
if (!a) throw Error(l("boardSettings.deleteIdRequired"));
|
|
731
748
|
for (;;) {
|
|
732
|
-
let r = await
|
|
749
|
+
let r = await V(K(N(t, e()), Z("boardId", "==", a), U(25)));
|
|
733
750
|
if (r.empty) break;
|
|
734
|
-
for (let i of r.docs) await jt(t,
|
|
751
|
+
for (let i of r.docs) await jt(t, Me(n), e(), i.id);
|
|
735
752
|
}
|
|
736
|
-
await
|
|
753
|
+
await de(o(t, e(), r));
|
|
737
754
|
}
|
|
738
|
-
let
|
|
739
|
-
async function
|
|
755
|
+
let oe = ae;
|
|
756
|
+
async function se() {
|
|
740
757
|
return Promise.resolve();
|
|
741
758
|
}
|
|
742
|
-
async function
|
|
759
|
+
async function ce(e) {
|
|
743
760
|
let t = e.trim();
|
|
744
761
|
if (!t) throw Error(l("boardSettings.nameRequired"));
|
|
745
762
|
if (!i.value) throw Error(l("boardSettings.signInRequired"));
|
|
746
763
|
let n = p.value.find((e) => e.label === t);
|
|
747
764
|
if (n) return n.id;
|
|
748
|
-
let r =
|
|
765
|
+
let r = te(t) || `board-${Date.now()}`, a = r, o = 2, s = new Set(p.value.map((e) => e.id));
|
|
749
766
|
for (; s.has(a);) a = `${r}-${o++}`;
|
|
750
|
-
return await
|
|
767
|
+
return await j({
|
|
751
768
|
id: a,
|
|
752
769
|
label: t,
|
|
753
770
|
visibility: "public",
|
|
@@ -775,15 +792,15 @@ function Yt() {
|
|
|
775
792
|
categoryVisibility: C,
|
|
776
793
|
isCategoryHidden: T,
|
|
777
794
|
settingsPending: f,
|
|
778
|
-
ensureSettings:
|
|
779
|
-
addBoard:
|
|
780
|
-
addCategory:
|
|
781
|
-
saveBoard:
|
|
782
|
-
saveCategory:
|
|
783
|
-
saveBoards:
|
|
784
|
-
saveCategories:
|
|
785
|
-
deleteBoard:
|
|
786
|
-
deleteCategory:
|
|
795
|
+
ensureSettings: se,
|
|
796
|
+
addBoard: ce,
|
|
797
|
+
addCategory: ce,
|
|
798
|
+
saveBoard: j,
|
|
799
|
+
saveCategory: ne,
|
|
800
|
+
saveBoards: re,
|
|
801
|
+
saveCategories: ie,
|
|
802
|
+
deleteBoard: ae,
|
|
803
|
+
deleteCategory: oe,
|
|
787
804
|
DEFAULT_BOARDS: Gt,
|
|
788
805
|
DEFAULT_CATEGORIES: Kt
|
|
789
806
|
};
|
|
@@ -797,12 +814,12 @@ function Zt(e) {
|
|
|
797
814
|
return t === "permission-denied" || t === "firestore/permission-denied";
|
|
798
815
|
}
|
|
799
816
|
function Qt(e, t) {
|
|
800
|
-
let n =
|
|
817
|
+
let n = L(e)?.trim();
|
|
801
818
|
if (!n) throw Error(w(t, "posts.boardIdRequired"));
|
|
802
819
|
return n;
|
|
803
820
|
}
|
|
804
821
|
function $t(e) {
|
|
805
|
-
let t =
|
|
822
|
+
let t = Q(), n = Se(), { isBoardHidden: r, getBoard: i } = Yt(), { user: a, canManageBoard: o } = ht(), { t: s, locale: u } = O(), d = () => M(), f = () => Qt(e, u.value), p = () => N(t, d()), m = (e) => l(t, d(), e), h = (e) => c(t, d(), e);
|
|
806
823
|
function g() {
|
|
807
824
|
return !r(f());
|
|
808
825
|
}
|
|
@@ -819,15 +836,15 @@ function $t(e) {
|
|
|
819
836
|
if (!e.title?.trim()) throw Error(s("posts.titleRequired"));
|
|
820
837
|
}
|
|
821
838
|
function y() {
|
|
822
|
-
return
|
|
839
|
+
return pe(p()).id;
|
|
823
840
|
}
|
|
824
841
|
function b(e) {
|
|
825
842
|
return bt(t, d(), f(), e, a.value?.uid, o(f()));
|
|
826
843
|
}
|
|
827
844
|
async function x(e = {}) {
|
|
828
|
-
let t = e.pageSize ?? 20, n = [
|
|
829
|
-
e.publicOnly !== !1 && n.push(
|
|
830
|
-
let r = await
|
|
845
|
+
let t = e.pageSize ?? 20, n = [Z("boardId", "==", f()), Z("isPublished", "==", !0)];
|
|
846
|
+
e.publicOnly !== !1 && n.push(Z("listed", "==", !0)), n.push(G("createdAt", "desc")), e.cursor && n.push(Y(e.cursor)), n.push(U(t + 1));
|
|
847
|
+
let r = await V(K(p(), ...n)), i = r.docs.slice(0, t);
|
|
831
848
|
return {
|
|
832
849
|
posts: i.map((e) => ({
|
|
833
850
|
id: e.id,
|
|
@@ -838,7 +855,7 @@ function $t(e) {
|
|
|
838
855
|
};
|
|
839
856
|
}
|
|
840
857
|
async function S(e) {
|
|
841
|
-
let [t, n] = await Promise.all([
|
|
858
|
+
let [t, n] = await Promise.all([B(m(e)), B(h(e))]);
|
|
842
859
|
return t.exists() ? {
|
|
843
860
|
id: t.id,
|
|
844
861
|
...t.data(),
|
|
@@ -888,7 +905,7 @@ function $t(e) {
|
|
|
888
905
|
}
|
|
889
906
|
}
|
|
890
907
|
async function T(e) {
|
|
891
|
-
return `${
|
|
908
|
+
return `${te(e.trim()) || "post"}-${y()}`;
|
|
892
909
|
}
|
|
893
910
|
async function E(e) {
|
|
894
911
|
if (!e.createdAt) return {
|
|
@@ -897,11 +914,11 @@ function $t(e) {
|
|
|
897
914
|
};
|
|
898
915
|
try {
|
|
899
916
|
let t = [
|
|
900
|
-
|
|
901
|
-
|
|
902
|
-
...e.listed === !1 ? [] : [
|
|
903
|
-
|
|
904
|
-
], [n, r] = await Promise.all([
|
|
917
|
+
Z("boardId", "==", f()),
|
|
918
|
+
Z("isPublished", "==", !0),
|
|
919
|
+
...e.listed === !1 ? [] : [Z("listed", "==", !0)],
|
|
920
|
+
G("createdAt", "desc")
|
|
921
|
+
], [n, r] = await Promise.all([V(K(p(), ...t, Y(e.createdAt), U(1))), V(K(p(), ...t, he(e.createdAt), ge(1)))]), i = (e) => {
|
|
905
922
|
let t = e.docs[0];
|
|
906
923
|
return t ? {
|
|
907
924
|
id: t.id,
|
|
@@ -923,7 +940,7 @@ function $t(e) {
|
|
|
923
940
|
v(e);
|
|
924
941
|
let n = e.postId || y(), r = _(), i, a;
|
|
925
942
|
r ? (i = n, a = Nt(e.content)) : (a = e.title.trim(), i = e.slug?.trim() || await T(a));
|
|
926
|
-
let o = Bt(e.content, e.attachments), s = g(), c =
|
|
943
|
+
let o = Bt(e.content, e.attachments), s = g(), c = ve(t);
|
|
927
944
|
return c.set(m(n), {
|
|
928
945
|
boardId: f(),
|
|
929
946
|
slug: i,
|
|
@@ -941,33 +958,33 @@ function $t(e) {
|
|
|
941
958
|
authorPhoto: e.authorPhoto,
|
|
942
959
|
moderationStatus: "approved",
|
|
943
960
|
moderationModel: e.moderationModel ?? null,
|
|
944
|
-
createdAt:
|
|
945
|
-
updatedAt:
|
|
961
|
+
createdAt: q(),
|
|
962
|
+
updatedAt: q()
|
|
946
963
|
}), c.set(h(n), { content: e.content }), await c.commit(), Xt.set(`${f()}/${i}`, n), i;
|
|
947
964
|
}
|
|
948
965
|
async function k(e, t) {
|
|
949
966
|
v(t);
|
|
950
967
|
let n = _() ? Nt(t.content) : t.title.trim(), r = Bt(t.content, t.attachments), i = g();
|
|
951
|
-
await Promise.all([
|
|
968
|
+
await Promise.all([X(m(e), {
|
|
952
969
|
title: n,
|
|
953
970
|
...r,
|
|
954
|
-
previewImage: r.previewImage ? r.previewImage :
|
|
955
|
-
videoUrl: r.videoUrl ? r.videoUrl :
|
|
971
|
+
previewImage: r.previewImage ? r.previewImage : fe(),
|
|
972
|
+
videoUrl: r.videoUrl ? r.videoUrl : fe(),
|
|
956
973
|
tags: t.tags ?? [],
|
|
957
974
|
listed: i,
|
|
958
975
|
attachments: t.attachments ?? [],
|
|
959
|
-
updatedAt:
|
|
960
|
-
}),
|
|
976
|
+
updatedAt: q()
|
|
977
|
+
}), J(h(e), { content: t.content }, { merge: !0 })]);
|
|
961
978
|
}
|
|
962
979
|
async function ee(e) {
|
|
963
|
-
await
|
|
980
|
+
await X(m(e), {
|
|
964
981
|
isPublished: !0,
|
|
965
|
-
publishedAt:
|
|
966
|
-
updatedAt:
|
|
982
|
+
publishedAt: q(),
|
|
983
|
+
updatedAt: q()
|
|
967
984
|
});
|
|
968
985
|
}
|
|
969
|
-
async function
|
|
970
|
-
await jt(t,
|
|
986
|
+
async function A(e) {
|
|
987
|
+
await jt(t, Me(n), d(), e);
|
|
971
988
|
for (let [t, n] of Xt) n === e && Xt.delete(t);
|
|
972
989
|
}
|
|
973
990
|
return {
|
|
@@ -981,16 +998,16 @@ function $t(e) {
|
|
|
981
998
|
createPost: D,
|
|
982
999
|
updatePost: k,
|
|
983
1000
|
publishPost: ee,
|
|
984
|
-
deletePost:
|
|
1001
|
+
deletePost: A
|
|
985
1002
|
};
|
|
986
1003
|
}
|
|
987
1004
|
var en = 10;
|
|
988
1005
|
function tn(e, t = {}) {
|
|
989
|
-
let n =
|
|
1006
|
+
let n = Q(), { isAdmin: r, user: i, canManageBoard: a } = ht(), o = () => M(), s = t.pageSize ?? en, c = P(() => i.value?.uid ?? ""), l = P(() => Qt(e)), u = () => N(n, o()), d = P(() => t.publicOnly === void 0 ? !(r.value || a(l.value)) : typeof t.publicOnly == "boolean" ? t.publicOnly : t.publicOnly.value), f = I([]), p = I([]), m = I([]), h = I(!0), g = I(!0), _ = I(!1), v = I(""), y = null, b = null, x, S;
|
|
990
1007
|
function C(e) {
|
|
991
1008
|
return e.createdAt?.toMillis?.() ?? 0;
|
|
992
1009
|
}
|
|
993
|
-
let w =
|
|
1010
|
+
let w = P(() => {
|
|
994
1011
|
let e = /* @__PURE__ */ new Map();
|
|
995
1012
|
for (let t of [
|
|
996
1013
|
...p.value,
|
|
@@ -1000,11 +1017,11 @@ function tn(e, t = {}) {
|
|
|
1000
1017
|
return [...e.values()].sort((e, t) => C(t) - C(e) || String(t.id).localeCompare(String(e.id)));
|
|
1001
1018
|
});
|
|
1002
1019
|
function T() {
|
|
1003
|
-
let e = [
|
|
1004
|
-
return d.value && e.push(
|
|
1020
|
+
let e = [Z("boardId", "==", l.value), Z("isPublished", "==", !0)];
|
|
1021
|
+
return d.value && e.push(Z("listed", "==", !0)), e;
|
|
1005
1022
|
}
|
|
1006
1023
|
function E() {
|
|
1007
|
-
x?.(), x =
|
|
1024
|
+
x?.(), x = W(K(u(), ...T(), G("createdAt", "desc"), G(z(), "desc"), U(s)), (e) => {
|
|
1008
1025
|
f.value = e.docs.map((e) => ({
|
|
1009
1026
|
id: e.id,
|
|
1010
1027
|
...e.data()
|
|
@@ -1020,7 +1037,7 @@ function tn(e, t = {}) {
|
|
|
1020
1037
|
m.value = [];
|
|
1021
1038
|
return;
|
|
1022
1039
|
}
|
|
1023
|
-
S =
|
|
1040
|
+
S = W(K(u(), Z("boardId", "==", l.value), Z("authorUid", "==", e), Z("isPublished", "==", !1), G("createdAt", "desc"), U(20)), (e) => {
|
|
1024
1041
|
m.value = e.docs.map((e) => ({
|
|
1025
1042
|
id: e.id,
|
|
1026
1043
|
...e.data()
|
|
@@ -1035,11 +1052,11 @@ function tn(e, t = {}) {
|
|
|
1035
1052
|
try {
|
|
1036
1053
|
let e = b ?? y, t = [
|
|
1037
1054
|
...T(),
|
|
1038
|
-
|
|
1039
|
-
|
|
1040
|
-
...e ? [
|
|
1041
|
-
|
|
1042
|
-
], n = await
|
|
1055
|
+
G("createdAt", "desc"),
|
|
1056
|
+
G(z(), "desc"),
|
|
1057
|
+
...e ? [Y(e)] : [],
|
|
1058
|
+
U(s + 1)
|
|
1059
|
+
], n = await V(K(u(), ...t)), r = n.docs.slice(0, s), i = r.map((e) => ({
|
|
1043
1060
|
id: e.id,
|
|
1044
1061
|
...e.data()
|
|
1045
1062
|
})), a = new Set([...p.value, ...f.value].map((e) => e.id));
|
|
@@ -1054,11 +1071,11 @@ function tn(e, t = {}) {
|
|
|
1054
1071
|
function k() {
|
|
1055
1072
|
x?.(), f.value = [], p.value = [], y = null, b = null, g.value = !0, v.value = "", h.value = !0, E(), D();
|
|
1056
1073
|
}
|
|
1057
|
-
return
|
|
1074
|
+
return R([
|
|
1058
1075
|
l,
|
|
1059
1076
|
d,
|
|
1060
1077
|
c
|
|
1061
|
-
], k, { immediate: !0 }),
|
|
1078
|
+
], k, { immediate: !0 }), F(() => {
|
|
1062
1079
|
x?.(), S?.();
|
|
1063
1080
|
}), {
|
|
1064
1081
|
posts: w,
|
|
@@ -1070,21 +1087,21 @@ function tn(e, t = {}) {
|
|
|
1070
1087
|
};
|
|
1071
1088
|
}
|
|
1072
1089
|
function nn(e, t) {
|
|
1073
|
-
let n =
|
|
1090
|
+
let n = Q(), r = () => M(), i = P(() => Qt(e)), a = P(() => typeof t == "string" ? t : t.value), o = P(() => l(n, r(), a.value)), s = P(() => c(n, r(), a.value)), { data: u, pending: d } = xe(o), { data: f, pending: p } = xe(s);
|
|
1074
1091
|
return {
|
|
1075
|
-
post:
|
|
1092
|
+
post: P(() => !u.value || u.value.boardId !== i.value ? null : {
|
|
1076
1093
|
...u.value,
|
|
1077
1094
|
id: a.value,
|
|
1078
1095
|
content: f.value?.content ?? ""
|
|
1079
1096
|
}),
|
|
1080
|
-
pending:
|
|
1097
|
+
pending: P(() => d.value || p.value)
|
|
1081
1098
|
};
|
|
1082
1099
|
}
|
|
1083
1100
|
//#endregion
|
|
1084
1101
|
//#region src/composables/useMemiBoardUserPosts.ts
|
|
1085
1102
|
var rn = 10;
|
|
1086
1103
|
function an(e, t = {}) {
|
|
1087
|
-
let n =
|
|
1104
|
+
let n = Q(), r = () => M(), i = () => N(n, r()), a = t.pageSize ?? rn, o = P(() => L(e)?.trim() || ""), s = I([]), c = I([]), l = I(!0), u = I(!0), d = I(!1), f = I(""), p = null, m = null, h;
|
|
1088
1105
|
function g(e) {
|
|
1089
1106
|
return {
|
|
1090
1107
|
id: e.id,
|
|
@@ -1094,16 +1111,16 @@ function an(e, t = {}) {
|
|
|
1094
1111
|
function _(e) {
|
|
1095
1112
|
return e.createdAt?.toMillis?.() ?? 0;
|
|
1096
1113
|
}
|
|
1097
|
-
let v =
|
|
1114
|
+
let v = P(() => {
|
|
1098
1115
|
let e = /* @__PURE__ */ new Map();
|
|
1099
1116
|
for (let t of [...c.value, ...s.value]) t.id && e.set(t.id, t);
|
|
1100
1117
|
return [...e.values()].sort((e, t) => _(t) - _(e) || String(t.id).localeCompare(String(e.id)));
|
|
1101
1118
|
});
|
|
1102
1119
|
function y() {
|
|
1103
1120
|
return [
|
|
1104
|
-
|
|
1105
|
-
|
|
1106
|
-
|
|
1121
|
+
Z("authorUid", "==", o.value),
|
|
1122
|
+
Z("isPublished", "==", !0),
|
|
1123
|
+
Z("listed", "==", !0)
|
|
1107
1124
|
];
|
|
1108
1125
|
}
|
|
1109
1126
|
function b() {
|
|
@@ -1111,7 +1128,7 @@ function an(e, t = {}) {
|
|
|
1111
1128
|
l.value = !1;
|
|
1112
1129
|
return;
|
|
1113
1130
|
}
|
|
1114
|
-
h =
|
|
1131
|
+
h = W(K(i(), ...y(), G("createdAt", "desc"), G(z(), "desc"), U(a)), (e) => {
|
|
1115
1132
|
s.value = e.docs.map(g), p = e.docs.at(-1) ?? null, m || (u.value = e.docs.length >= a), l.value = !1;
|
|
1116
1133
|
}, (e) => {
|
|
1117
1134
|
console.error("[memi-board:userPosts] onSnapshot failed", e), f.value = e.message || String(e), l.value = !1;
|
|
@@ -1123,11 +1140,11 @@ function an(e, t = {}) {
|
|
|
1123
1140
|
try {
|
|
1124
1141
|
let e = m ?? p, t = [
|
|
1125
1142
|
...y(),
|
|
1126
|
-
|
|
1127
|
-
|
|
1128
|
-
...e ? [
|
|
1129
|
-
|
|
1130
|
-
], n = await
|
|
1143
|
+
G("createdAt", "desc"),
|
|
1144
|
+
G(z(), "desc"),
|
|
1145
|
+
...e ? [Y(e)] : [],
|
|
1146
|
+
U(a + 1)
|
|
1147
|
+
], n = await V(K(i(), ...t)), r = n.docs.slice(0, a), o = r.map(g), l = new Set([...c.value, ...s.value].map((e) => e.id));
|
|
1131
1148
|
c.value.push(...o.filter((e) => !l.has(e.id))), m = r.at(-1) ?? m, u.value = n.docs.length > a;
|
|
1132
1149
|
} catch (e) {
|
|
1133
1150
|
f.value = e.message || String(e), console.error("[memi-board:userPosts] loadMore failed", e);
|
|
@@ -1139,7 +1156,7 @@ function an(e, t = {}) {
|
|
|
1139
1156
|
function S() {
|
|
1140
1157
|
h?.(), s.value = [], c.value = [], p = null, m = null, u.value = !0, f.value = "", l.value = !0, b();
|
|
1141
1158
|
}
|
|
1142
|
-
return
|
|
1159
|
+
return R(o, S, { immediate: !0 }), F(() => h?.()), {
|
|
1143
1160
|
posts: v,
|
|
1144
1161
|
postsPending: l,
|
|
1145
1162
|
hasMore: u,
|
|
@@ -1152,7 +1169,7 @@ function an(e, t = {}) {
|
|
|
1152
1169
|
//#region src/composables/useMemiBoardUserComments.ts
|
|
1153
1170
|
var on = 10;
|
|
1154
1171
|
function sn(e, t = {}) {
|
|
1155
|
-
let n =
|
|
1172
|
+
let n = Q(), r = () => M(), i = () => u(n, r()), a = t.pageSize ?? on, o = P(() => L(e)?.trim() || ""), s = I([]), c = I([]), l = I(!0), d = I(!0), f = I(!1), p = I(""), m = null, h = null, g;
|
|
1156
1173
|
function _(e) {
|
|
1157
1174
|
return {
|
|
1158
1175
|
id: e.id,
|
|
@@ -1162,20 +1179,20 @@ function sn(e, t = {}) {
|
|
|
1162
1179
|
function v(e) {
|
|
1163
1180
|
return e.createdAt?.toMillis?.() ?? 0;
|
|
1164
1181
|
}
|
|
1165
|
-
let y =
|
|
1182
|
+
let y = P(() => {
|
|
1166
1183
|
let e = /* @__PURE__ */ new Map();
|
|
1167
1184
|
for (let t of [...c.value, ...s.value]) t.id && e.set(t.id, t);
|
|
1168
1185
|
return [...e.values()].sort((e, t) => v(t) - v(e) || String(t.id).localeCompare(String(e.id)));
|
|
1169
1186
|
});
|
|
1170
1187
|
function b() {
|
|
1171
|
-
return [
|
|
1188
|
+
return [Z("authorUid", "==", o.value), Z("listed", "==", !0)];
|
|
1172
1189
|
}
|
|
1173
1190
|
function x() {
|
|
1174
1191
|
if (g?.(), !o.value) {
|
|
1175
1192
|
l.value = !1;
|
|
1176
1193
|
return;
|
|
1177
1194
|
}
|
|
1178
|
-
g =
|
|
1195
|
+
g = W(K(i(), ...b(), G("createdAt", "desc"), G(z(), "desc"), U(a)), (e) => {
|
|
1179
1196
|
s.value = e.docs.map(_), m = e.docs.at(-1) ?? null, h || (d.value = e.docs.length >= a), l.value = !1;
|
|
1180
1197
|
}, (e) => {
|
|
1181
1198
|
console.error("[memi-board:userComments] onSnapshot failed", e), p.value = e.message || String(e), l.value = !1;
|
|
@@ -1187,11 +1204,11 @@ function sn(e, t = {}) {
|
|
|
1187
1204
|
try {
|
|
1188
1205
|
let e = h ?? m, t = [
|
|
1189
1206
|
...b(),
|
|
1190
|
-
|
|
1191
|
-
|
|
1192
|
-
...e ? [
|
|
1193
|
-
|
|
1194
|
-
], n = await
|
|
1207
|
+
G("createdAt", "desc"),
|
|
1208
|
+
G(z(), "desc"),
|
|
1209
|
+
...e ? [Y(e)] : [],
|
|
1210
|
+
U(a + 1)
|
|
1211
|
+
], n = await V(K(i(), ...t)), r = n.docs.slice(0, a), o = r.map(_), l = new Set([...c.value, ...s.value].map((e) => e.id));
|
|
1195
1212
|
c.value.push(...o.filter((e) => !l.has(e.id))), h = r.at(-1) ?? h, d.value = n.docs.length > a;
|
|
1196
1213
|
} catch (e) {
|
|
1197
1214
|
p.value = e.message || String(e), console.error("[memi-board:userComments] loadMore failed", e);
|
|
@@ -1203,7 +1220,7 @@ function sn(e, t = {}) {
|
|
|
1203
1220
|
function C() {
|
|
1204
1221
|
g?.(), s.value = [], c.value = [], m = null, h = null, d.value = !0, p.value = "", l.value = !0, x();
|
|
1205
1222
|
}
|
|
1206
|
-
return
|
|
1223
|
+
return R(o, C, { immediate: !0 }), F(() => g?.()), {
|
|
1207
1224
|
comments: y,
|
|
1208
1225
|
commentsPending: l,
|
|
1209
1226
|
hasMore: d,
|
|
@@ -1216,10 +1233,10 @@ function sn(e, t = {}) {
|
|
|
1216
1233
|
//#region src/composables/useMemiBoardCommentFeed.ts
|
|
1217
1234
|
var cn = 10;
|
|
1218
1235
|
function ln(e = "latest", t = {}) {
|
|
1219
|
-
let n =
|
|
1220
|
-
let e = Math.floor(Number(
|
|
1236
|
+
let n = Q(), r = () => M(), i = () => u(n, r()), a = P(() => {
|
|
1237
|
+
let e = Math.floor(Number(L(t.pageSize)));
|
|
1221
1238
|
return Number.isFinite(e) && e > 0 ? e : cn;
|
|
1222
|
-
}), o =
|
|
1239
|
+
}), o = P(() => L(e) === "likes" ? "likes" : "latest"), s = I([]), c = I([]), l = I(!0), d = I(!0), f = I(!1), p = I(""), m = null, h = null, g;
|
|
1223
1240
|
function _(e) {
|
|
1224
1241
|
return {
|
|
1225
1242
|
id: e.id,
|
|
@@ -1236,25 +1253,25 @@ function ln(e = "latest", t = {}) {
|
|
|
1236
1253
|
}
|
|
1237
1254
|
return v(t) - v(e) || String(t.id).localeCompare(String(e.id));
|
|
1238
1255
|
}
|
|
1239
|
-
let b =
|
|
1256
|
+
let b = P(() => {
|
|
1240
1257
|
let e = /* @__PURE__ */ new Map();
|
|
1241
1258
|
for (let t of [...c.value, ...s.value]) t.id && e.set(t.id, t);
|
|
1242
1259
|
return [...e.values()].sort(y);
|
|
1243
1260
|
});
|
|
1244
1261
|
function x() {
|
|
1245
1262
|
return o.value === "likes" ? [
|
|
1246
|
-
|
|
1247
|
-
|
|
1248
|
-
|
|
1249
|
-
|
|
1263
|
+
Z("listed", "==", !0),
|
|
1264
|
+
G("likeCount", "desc"),
|
|
1265
|
+
G("createdAt", "desc"),
|
|
1266
|
+
G(z(), "desc")
|
|
1250
1267
|
] : [
|
|
1251
|
-
|
|
1252
|
-
|
|
1253
|
-
|
|
1268
|
+
Z("listed", "==", !0),
|
|
1269
|
+
G("createdAt", "desc"),
|
|
1270
|
+
G(z(), "desc")
|
|
1254
1271
|
];
|
|
1255
1272
|
}
|
|
1256
1273
|
function S() {
|
|
1257
|
-
g?.(), g =
|
|
1274
|
+
g?.(), g = W(K(i(), ...x(), U(a.value)), (e) => {
|
|
1258
1275
|
s.value = e.docs.map(_), m = e.docs.at(-1) ?? null, h || (d.value = e.docs.length >= a.value), l.value = !1;
|
|
1259
1276
|
}, (e) => {
|
|
1260
1277
|
console.error("[memi-board:commentFeed] onSnapshot failed", e), p.value = e.message || String(e), l.value = !1;
|
|
@@ -1264,7 +1281,7 @@ function ln(e = "latest", t = {}) {
|
|
|
1264
1281
|
if (!(f.value || !d.value || l.value)) {
|
|
1265
1282
|
f.value = !0, p.value = "";
|
|
1266
1283
|
try {
|
|
1267
|
-
let e = h ?? m, t = await
|
|
1284
|
+
let e = h ?? m, t = await V(K(i(), ...x(), ...e ? [Y(e)] : [], U(a.value + 1))), n = t.docs.slice(0, a.value), r = n.map(_), o = new Set([...c.value, ...s.value].map((e) => e.id));
|
|
1268
1285
|
c.value.push(...r.filter((e) => !o.has(e.id))), h = n.at(-1) ?? h, d.value = t.docs.length > a.value;
|
|
1269
1286
|
} catch (e) {
|
|
1270
1287
|
p.value = e.message || String(e), console.error("[memi-board:commentFeed] loadMore failed", e);
|
|
@@ -1276,7 +1293,7 @@ function ln(e = "latest", t = {}) {
|
|
|
1276
1293
|
function w() {
|
|
1277
1294
|
g?.(), s.value = [], c.value = [], m = null, h = null, d.value = !0, p.value = "", l.value = !0, S();
|
|
1278
1295
|
}
|
|
1279
|
-
return
|
|
1296
|
+
return R([o, a], w, { immediate: !0 }), F(() => g?.()), {
|
|
1280
1297
|
comments: b,
|
|
1281
1298
|
commentsPending: l,
|
|
1282
1299
|
hasMore: d,
|
|
@@ -1291,7 +1308,7 @@ function ln(e = "latest", t = {}) {
|
|
|
1291
1308
|
var un = 100, dn = /* @__PURE__ */ new Map();
|
|
1292
1309
|
function $(e) {
|
|
1293
1310
|
let t = dn.get(e);
|
|
1294
|
-
return t || (t =
|
|
1311
|
+
return t || (t = ue({
|
|
1295
1312
|
text: "",
|
|
1296
1313
|
sentiment: null,
|
|
1297
1314
|
loaded: !1,
|
|
@@ -1301,22 +1318,22 @@ function $(e) {
|
|
|
1301
1318
|
}), dn.set(e, t)), t;
|
|
1302
1319
|
}
|
|
1303
1320
|
function fn(e) {
|
|
1304
|
-
let t =
|
|
1321
|
+
let t = Q(), n = () => M(), { user: r } = ht(), { t: a, formatNumber: o } = O(), s = P(() => L(e)), c = P(() => `${r.value?.uid ?? ""}:${s.value}`), l = P(() => {
|
|
1305
1322
|
let e = r.value?.uid, a = s.value;
|
|
1306
1323
|
return !e || !a ? null : i(t, n(), e, a);
|
|
1307
|
-
}), u =
|
|
1324
|
+
}), u = P({
|
|
1308
1325
|
get: () => $(c.value).text,
|
|
1309
1326
|
set: (e) => {
|
|
1310
1327
|
$(c.value).text = e;
|
|
1311
1328
|
}
|
|
1312
|
-
}), d =
|
|
1329
|
+
}), d = P(() => $(c.value).sentiment), f = P(() => $(c.value).loaded), p = P(() => $(c.value).pending), m = P(() => $(c.value).saving), h = P(() => $(c.value).error);
|
|
1313
1330
|
async function g() {
|
|
1314
1331
|
let e = l.value;
|
|
1315
1332
|
if (!e) return;
|
|
1316
1333
|
let t = $(c.value);
|
|
1317
1334
|
t.pending = !0, t.error = "";
|
|
1318
1335
|
try {
|
|
1319
|
-
let n = (await
|
|
1336
|
+
let n = (await B(e)).data();
|
|
1320
1337
|
t.text = n ? n.text ?? "" : "", t.sentiment = n ? n.sentiment ?? null : null, t.loaded = !0;
|
|
1321
1338
|
} catch (e) {
|
|
1322
1339
|
t.error = e.message || String(e), console.error("[memi-board:authorMemo] load failed", e);
|
|
@@ -1332,10 +1349,10 @@ function fn(e) {
|
|
|
1332
1349
|
let i = $(c.value);
|
|
1333
1350
|
i.saving = !0, i.error = "";
|
|
1334
1351
|
try {
|
|
1335
|
-
await
|
|
1352
|
+
await J(n, {
|
|
1336
1353
|
text: r,
|
|
1337
1354
|
sentiment: t,
|
|
1338
|
-
updatedAt:
|
|
1355
|
+
updatedAt: q()
|
|
1339
1356
|
}), i.text = r, i.sentiment = t, i.loaded = !0;
|
|
1340
1357
|
} catch (e) {
|
|
1341
1358
|
throw i.error = e.message || String(e), console.error("[memi-board:authorMemo] save failed", e), e;
|
|
@@ -1349,7 +1366,7 @@ function fn(e) {
|
|
|
1349
1366
|
let t = $(c.value);
|
|
1350
1367
|
t.saving = !0, t.error = "";
|
|
1351
1368
|
try {
|
|
1352
|
-
await
|
|
1369
|
+
await de(e), t.text = "", t.sentiment = null, t.loaded = !0;
|
|
1353
1370
|
} catch (e) {
|
|
1354
1371
|
throw t.error = e.message || String(e), console.error("[memi-board:authorMemo] remove failed", e), e;
|
|
1355
1372
|
} finally {
|
|
@@ -1371,7 +1388,7 @@ function fn(e) {
|
|
|
1371
1388
|
//#endregion
|
|
1372
1389
|
//#region src/utils/subscribeCommentRange.ts
|
|
1373
1390
|
function pn(e, t, n, r, i, a) {
|
|
1374
|
-
return
|
|
1391
|
+
return W(K(u(e, t), Z("postId", "==", n), ...r.rootId ? [Z("rootId", "==", r.rootId), Z("isReply", "==", !0)] : [Z("parentId", "==", null)], G("createdAt", "asc"), G(z(), "asc"), ...r.hasMore && r.cursor ? [me(r.cursor)] : []), (e) => i(e.docs.map((e) => ({
|
|
1375
1392
|
...e.data(),
|
|
1376
1393
|
id: e.id
|
|
1377
1394
|
}))), a);
|
|
@@ -1386,21 +1403,21 @@ function _n(e, { t, formatNumber: n }) {
|
|
|
1386
1403
|
return r;
|
|
1387
1404
|
}
|
|
1388
1405
|
function vn(e, t, n = {}) {
|
|
1389
|
-
let r =
|
|
1406
|
+
let r = Q(), i = () => M(), { isBoardHidden: a } = Yt(), o = O(), { t: s } = o, c = () => u(r, i()), d = P(() => L(e)), f = P(() => L(t)), p = () => !a(d.value), m = I([]), h = I(n.subscribe !== !1), g = I([]), _ = I(!1), v = I(n.subscribe !== !1), y = I(n.subscribe !== !1), b = null, x = 0, S = 0, C;
|
|
1390
1407
|
function w(e) {
|
|
1391
1408
|
return e.createdAt?.toMillis?.() ?? 0;
|
|
1392
1409
|
}
|
|
1393
|
-
let T =
|
|
1410
|
+
let T = P(() => {
|
|
1394
1411
|
let e = /* @__PURE__ */ new Map();
|
|
1395
1412
|
for (let t of [...m.value, ...g.value]) t.id && e.set(t.id, t);
|
|
1396
1413
|
return [...e.values()].sort((e, t) => w(e) - w(t) || String(e.id).localeCompare(String(t.id)));
|
|
1397
1414
|
});
|
|
1398
|
-
|
|
1415
|
+
R([f, d], async ([e]) => {
|
|
1399
1416
|
let t = ++x;
|
|
1400
1417
|
if (S++, _.value = !1, g.value = [], m.value = [], b = null, C?.(), C = void 0, v.value = n.subscribe !== !1, n.subscribe !== !1) {
|
|
1401
1418
|
h.value = !0, y.value = !0;
|
|
1402
1419
|
try {
|
|
1403
|
-
let n =
|
|
1420
|
+
let n = V(K(c(), Z("postId", "==", e), G("createdAt", "desc"), G(z(), "desc")));
|
|
1404
1421
|
if (await Promise.all([n.then((e) => {
|
|
1405
1422
|
if (t !== x) return;
|
|
1406
1423
|
let n = e.docs.map((e) => ({
|
|
@@ -1432,13 +1449,13 @@ function vn(e, t, n = {}) {
|
|
|
1432
1449
|
_.value = !0;
|
|
1433
1450
|
try {
|
|
1434
1451
|
let t = [
|
|
1435
|
-
|
|
1436
|
-
|
|
1437
|
-
|
|
1438
|
-
|
|
1439
|
-
...b ? [
|
|
1440
|
-
|
|
1441
|
-
], n = await
|
|
1452
|
+
Z("postId", "==", f.value),
|
|
1453
|
+
Z("parentId", "==", null),
|
|
1454
|
+
G("createdAt", "asc"),
|
|
1455
|
+
G(z(), "asc"),
|
|
1456
|
+
...b ? [Y(b)] : [],
|
|
1457
|
+
U(11)
|
|
1458
|
+
], n = await V(K(c(), ...t));
|
|
1442
1459
|
if (e !== x) return;
|
|
1443
1460
|
let r = n.docs.slice(0, mn), i = r.map((e) => ({
|
|
1444
1461
|
id: e.id,
|
|
@@ -1449,11 +1466,11 @@ function vn(e, t, n = {}) {
|
|
|
1449
1466
|
e === x && (_.value = !1);
|
|
1450
1467
|
}
|
|
1451
1468
|
}
|
|
1452
|
-
|
|
1469
|
+
F(() => {
|
|
1453
1470
|
x++, S++, C?.();
|
|
1454
1471
|
});
|
|
1455
1472
|
async function ee(e) {
|
|
1456
|
-
let t = _n(e.body, o), n =
|
|
1473
|
+
let t = _n(e.body, o), n = ve(r), a = pe(c());
|
|
1457
1474
|
n.set(a, {
|
|
1458
1475
|
postId: f.value,
|
|
1459
1476
|
boardId: d.value,
|
|
@@ -1471,14 +1488,14 @@ function vn(e, t, n = {}) {
|
|
|
1471
1488
|
replyCount: 0,
|
|
1472
1489
|
likeCount: 0,
|
|
1473
1490
|
isReply: !1,
|
|
1474
|
-
createdAt:
|
|
1475
|
-
updatedAt:
|
|
1476
|
-
}), n.update(l(r, i(), f.value), { commentCount:
|
|
1491
|
+
createdAt: q(),
|
|
1492
|
+
updatedAt: q()
|
|
1493
|
+
}), n.update(l(r, i(), f.value), { commentCount: H(1) }), await n.commit();
|
|
1477
1494
|
}
|
|
1478
|
-
async function
|
|
1495
|
+
async function A(e) {
|
|
1479
1496
|
let t = _n(e.body, o);
|
|
1480
1497
|
if (!e.parent.id) throw Error(s("comments.replyTargetNotFound"));
|
|
1481
|
-
let n =
|
|
1498
|
+
let n = ve(r), a = pe(c()), u = e.parent.parentId == null ? e.parent.id : e.parent.rootId;
|
|
1482
1499
|
if (!u) throw Error(s("comments.threadNotFound"));
|
|
1483
1500
|
let m = Math.min((e.parent.depth ?? 0) + 1, 2);
|
|
1484
1501
|
n.set(a, {
|
|
@@ -1498,46 +1515,46 @@ function vn(e, t, n = {}) {
|
|
|
1498
1515
|
replyCount: 0,
|
|
1499
1516
|
likeCount: 0,
|
|
1500
1517
|
isReply: !0,
|
|
1501
|
-
createdAt:
|
|
1502
|
-
updatedAt:
|
|
1503
|
-
}), n.update(k(r, i(), u), { replyCount:
|
|
1518
|
+
createdAt: q(),
|
|
1519
|
+
updatedAt: q()
|
|
1520
|
+
}), n.update(k(r, i(), u), { replyCount: H(1) }), n.update(l(r, i(), f.value), { commentCount: H(1) }), await n.commit();
|
|
1504
1521
|
}
|
|
1505
|
-
async function
|
|
1522
|
+
async function j(e) {
|
|
1506
1523
|
if (!e.id) return;
|
|
1507
1524
|
if (e.parentId == null && (e.replyCount ?? 0) > 0) throw Error(s("comments.hasRepliesCannotDelete"));
|
|
1508
1525
|
await At(r, i(), e.id);
|
|
1509
|
-
let t =
|
|
1510
|
-
t.delete(k(r, i(), e.id)), e.parentId && e.rootId && t.update(k(r, i(), e.rootId), { replyCount:
|
|
1526
|
+
let t = ve(r);
|
|
1527
|
+
t.delete(k(r, i(), e.id)), e.parentId && e.rootId && t.update(k(r, i(), e.rootId), { replyCount: H(-1) }), t.update(l(r, i(), f.value), { commentCount: H(-1) }), await t.commit(), g.value = g.value.filter((t) => t.id !== e.id), m.value = m.value.filter((t) => t.id !== e.id);
|
|
1511
1528
|
}
|
|
1512
|
-
async function
|
|
1529
|
+
async function te(e, t) {
|
|
1513
1530
|
let n = _n(t, o);
|
|
1514
|
-
await
|
|
1531
|
+
await X(k(r, i(), e), {
|
|
1515
1532
|
body: n,
|
|
1516
|
-
updatedAt:
|
|
1533
|
+
updatedAt: q()
|
|
1517
1534
|
});
|
|
1518
1535
|
}
|
|
1519
|
-
async function
|
|
1520
|
-
await
|
|
1536
|
+
async function ne(e, t, n) {
|
|
1537
|
+
await X(k(r, i(), e), {
|
|
1521
1538
|
isBlinded: t,
|
|
1522
|
-
moderatedAt:
|
|
1539
|
+
moderatedAt: q(),
|
|
1523
1540
|
moderatedBy: n
|
|
1524
1541
|
});
|
|
1525
1542
|
}
|
|
1526
1543
|
return {
|
|
1527
1544
|
comments: T,
|
|
1528
|
-
commentsPending:
|
|
1545
|
+
commentsPending: P(() => y.value || h.value),
|
|
1529
1546
|
hasMore: v,
|
|
1530
1547
|
loadingMore: _,
|
|
1531
1548
|
loadMore: D,
|
|
1532
1549
|
addComment: ee,
|
|
1533
|
-
addReply:
|
|
1534
|
-
updateComment:
|
|
1535
|
-
setCommentBlinded:
|
|
1536
|
-
deleteComment:
|
|
1550
|
+
addReply: A,
|
|
1551
|
+
updateComment: te,
|
|
1552
|
+
setCommentBlinded: ne,
|
|
1553
|
+
deleteComment: j
|
|
1537
1554
|
};
|
|
1538
1555
|
}
|
|
1539
1556
|
function yn(e, t, n) {
|
|
1540
|
-
let r =
|
|
1557
|
+
let r = Q(), i = () => M(), a = () => u(r, i()), o = t.trim(), s = I([]), c = I(!1), l = I(!1), d = I(!0), f = null, p, m = 0, h = 0;
|
|
1541
1558
|
function g(e) {
|
|
1542
1559
|
return e.sort((e, t) => (e.createdAt?.toMillis?.() ?? 0) - (t.createdAt?.toMillis?.() ?? 0) || String(e.id).localeCompare(String(t.id)));
|
|
1543
1560
|
}
|
|
@@ -1560,14 +1577,14 @@ function yn(e, t, n) {
|
|
|
1560
1577
|
c.value = !0;
|
|
1561
1578
|
try {
|
|
1562
1579
|
let t = [
|
|
1563
|
-
|
|
1564
|
-
|
|
1565
|
-
|
|
1566
|
-
|
|
1567
|
-
|
|
1568
|
-
...f ? [
|
|
1569
|
-
|
|
1570
|
-
], r = await
|
|
1580
|
+
Z("postId", "==", o),
|
|
1581
|
+
Z("rootId", "==", n),
|
|
1582
|
+
Z("isReply", "==", !0),
|
|
1583
|
+
G("createdAt", "asc"),
|
|
1584
|
+
G(z(), "asc"),
|
|
1585
|
+
...f ? [Y(f)] : [],
|
|
1586
|
+
U(6)
|
|
1587
|
+
], r = await V(K(a(), ...t));
|
|
1571
1588
|
if (e !== m) return;
|
|
1572
1589
|
let i = new Set(s.value.map((e) => e.id)), c = r.docs.slice(0, hn), u = c.map((e) => ({
|
|
1573
1590
|
id: e.id,
|
|
@@ -1584,7 +1601,7 @@ function yn(e, t, n) {
|
|
|
1584
1601
|
async function b() {
|
|
1585
1602
|
y(), await v();
|
|
1586
1603
|
}
|
|
1587
|
-
return
|
|
1604
|
+
return F(() => {
|
|
1588
1605
|
m++, h++, p?.();
|
|
1589
1606
|
}), {
|
|
1590
1607
|
replies: s,
|
|
@@ -1598,21 +1615,21 @@ function yn(e, t, n) {
|
|
|
1598
1615
|
//#endregion
|
|
1599
1616
|
//#region src/composables/useMemiBoardLikes.ts
|
|
1600
1617
|
function bn(e, t) {
|
|
1601
|
-
let n = () =>
|
|
1618
|
+
let n = () => M(), r = Q(), i = be(), { t: a } = O(), o = I(!1), s = I(!1), c;
|
|
1602
1619
|
function u(e) {
|
|
1603
1620
|
return d(r, n(), t, e);
|
|
1604
1621
|
}
|
|
1605
|
-
|
|
1622
|
+
R(i, (e) => {
|
|
1606
1623
|
if (c?.(), c = void 0, !e) {
|
|
1607
1624
|
o.value = !1;
|
|
1608
1625
|
return;
|
|
1609
1626
|
}
|
|
1610
|
-
c =
|
|
1627
|
+
c = W(u(e.uid), (e) => {
|
|
1611
1628
|
o.value = e.exists();
|
|
1612
1629
|
}, (e) => {
|
|
1613
1630
|
console.error("[memi-board:likes] onSnapshot failed", e);
|
|
1614
1631
|
});
|
|
1615
|
-
}, { immediate: !0 }),
|
|
1632
|
+
}, { immediate: !0 }), F(() => c?.());
|
|
1616
1633
|
async function f() {
|
|
1617
1634
|
let c = i.value?.uid;
|
|
1618
1635
|
if (!c) throw Error(a("likes.signInRequired"));
|
|
@@ -1620,12 +1637,12 @@ function bn(e, t) {
|
|
|
1620
1637
|
s.value = !0;
|
|
1621
1638
|
try {
|
|
1622
1639
|
let i = u(c), a = l(r, n(), t);
|
|
1623
|
-
return await
|
|
1640
|
+
return await _e(r, async (n) => (await n.get(i)).exists() ? (n.delete(i), n.update(a, { likeCount: H(-1) }), !1) : (n.set(i, {
|
|
1624
1641
|
uid: c,
|
|
1625
1642
|
postId: t,
|
|
1626
1643
|
boardId: e,
|
|
1627
|
-
createdAt:
|
|
1628
|
-
}), n.update(a, { likeCount:
|
|
1644
|
+
createdAt: q()
|
|
1645
|
+
}), n.update(a, { likeCount: H(1) }), !0));
|
|
1629
1646
|
} finally {
|
|
1630
1647
|
s.value = !1;
|
|
1631
1648
|
}
|
|
@@ -1638,9 +1655,9 @@ function bn(e, t) {
|
|
|
1638
1655
|
}
|
|
1639
1656
|
var xn = Symbol.for("memi-board:comment-likes");
|
|
1640
1657
|
function Sn(e, t) {
|
|
1641
|
-
let n = () =>
|
|
1642
|
-
|
|
1643
|
-
f?.(), f = void 0, l.value = /* @__PURE__ */ new Set(), e && t && (f =
|
|
1658
|
+
let n = () => M(), r = Q(), i = be(), { t: o } = O(), s = P(() => L(e)), c = P(() => L(t)), l = I(/* @__PURE__ */ new Set()), u = I(null), f;
|
|
1659
|
+
R([i, c], ([e, t]) => {
|
|
1660
|
+
f?.(), f = void 0, l.value = /* @__PURE__ */ new Set(), e && t && (f = W(K(a(r, n()), Z("uid", "==", e.uid), Z("postId", "==", t), Z("target", "==", "comment")), (e) => {
|
|
1644
1661
|
let t = /* @__PURE__ */ new Set();
|
|
1645
1662
|
for (let n of e.docs) {
|
|
1646
1663
|
let e = n.data().commentId;
|
|
@@ -1650,7 +1667,7 @@ function Sn(e, t) {
|
|
|
1650
1667
|
}, (e) => {
|
|
1651
1668
|
console.error("[memi-board:comment-likes] onSnapshot failed", e);
|
|
1652
1669
|
}));
|
|
1653
|
-
}, { immediate: !0 }),
|
|
1670
|
+
}, { immediate: !0 }), F(() => f?.());
|
|
1654
1671
|
function p(e) {
|
|
1655
1672
|
return !!e && l.value.has(e);
|
|
1656
1673
|
}
|
|
@@ -1664,7 +1681,7 @@ function Sn(e, t) {
|
|
|
1664
1681
|
if (u.value) return p(e);
|
|
1665
1682
|
u.value = e;
|
|
1666
1683
|
try {
|
|
1667
|
-
let i = d(r, n(), e, t), a = k(r, n(), e), u = await
|
|
1684
|
+
let i = d(r, n(), e, t), a = k(r, n(), e), u = await _e(r, async (n) => {
|
|
1668
1685
|
let r = await n.get(i), l = await n.get(a);
|
|
1669
1686
|
if (!l.exists()) throw Error(o("likes.commentNotFound"));
|
|
1670
1687
|
let u = Number(l.data()?.likeCount ?? 0);
|
|
@@ -1674,7 +1691,7 @@ function Sn(e, t) {
|
|
|
1674
1691
|
boardId: s.value,
|
|
1675
1692
|
commentId: e,
|
|
1676
1693
|
target: "comment",
|
|
1677
|
-
createdAt:
|
|
1694
|
+
createdAt: q()
|
|
1678
1695
|
}), n.update(a, { likeCount: u + 1 }), !0);
|
|
1679
1696
|
}), f = new Set(l.value);
|
|
1680
1697
|
return u ? f.add(e) : f.delete(e), l.value = f, u;
|
|
@@ -1716,18 +1733,18 @@ function Tn(e, t) {
|
|
|
1716
1733
|
return wn.some((t) => t.value === e) ? w(t, `reports.reason.${e}`) : e || w(t, "reports.fallbackLabel");
|
|
1717
1734
|
}
|
|
1718
1735
|
function En(e, n) {
|
|
1719
|
-
let r = () =>
|
|
1720
|
-
|
|
1736
|
+
let r = () => M(), i = Q(), a = be(), { t: o } = O(), s = I(!1), c = I(!1), l;
|
|
1737
|
+
R(a, (e) => {
|
|
1721
1738
|
if (l?.(), l = void 0, !e) {
|
|
1722
1739
|
s.value = !1;
|
|
1723
1740
|
return;
|
|
1724
1741
|
}
|
|
1725
|
-
l =
|
|
1742
|
+
l = W(t(i, r(), n, e.uid), (e) => {
|
|
1726
1743
|
s.value = e.exists();
|
|
1727
1744
|
}, (e) => {
|
|
1728
1745
|
console.error("[memi-board:reports] onSnapshot failed", e);
|
|
1729
1746
|
});
|
|
1730
|
-
}, { immediate: !0 }),
|
|
1747
|
+
}, { immediate: !0 }), F(() => l?.());
|
|
1731
1748
|
async function u(l) {
|
|
1732
1749
|
let u = a.value?.uid;
|
|
1733
1750
|
if (!u) throw Error(o("reports.signInRequired"));
|
|
@@ -1739,7 +1756,7 @@ function En(e, n) {
|
|
|
1739
1756
|
if (f.length > 200) throw Error(o("reports.detailTooLong", { max: 200 }));
|
|
1740
1757
|
c.value = !0;
|
|
1741
1758
|
try {
|
|
1742
|
-
await
|
|
1759
|
+
await J(t(i, r(), n, u), {
|
|
1743
1760
|
uid: u,
|
|
1744
1761
|
target: "post",
|
|
1745
1762
|
postId: n,
|
|
@@ -1750,7 +1767,7 @@ function En(e, n) {
|
|
|
1750
1767
|
postTitle: (l.postTitle || "").trim().slice(0, 200),
|
|
1751
1768
|
authorUid: l.authorUid || "",
|
|
1752
1769
|
authorName: l.authorName ?? null,
|
|
1753
|
-
createdAt:
|
|
1770
|
+
createdAt: q()
|
|
1754
1771
|
}), s.value = !0;
|
|
1755
1772
|
} finally {
|
|
1756
1773
|
c.value = !1;
|
|
@@ -1764,62 +1781,62 @@ function En(e, n) {
|
|
|
1764
1781
|
}
|
|
1765
1782
|
var Dn = 20;
|
|
1766
1783
|
function On(e = {}) {
|
|
1767
|
-
let n = () =>
|
|
1768
|
-
function
|
|
1784
|
+
let n = () => M(), r = Q(), { isAdmin: i, canManageContent: a, canManageBoard: o } = ht(), c = e.pageSize ?? Dn, l = P(() => L(e.boardId)?.trim() || ""), u = I([]), d = I(!0), f = I(!1), p = I(!1), m = I(""), h = null, g;
|
|
1785
|
+
function _(e) {
|
|
1769
1786
|
return {
|
|
1770
1787
|
id: e.id,
|
|
1771
1788
|
...e.data()
|
|
1772
1789
|
};
|
|
1773
1790
|
}
|
|
1774
|
-
function
|
|
1775
|
-
if (
|
|
1776
|
-
|
|
1791
|
+
function v() {
|
|
1792
|
+
if (g?.(), !a.value || !i.value && !l.value) {
|
|
1793
|
+
u.value = [], d.value = !1;
|
|
1777
1794
|
return;
|
|
1778
1795
|
}
|
|
1779
|
-
|
|
1780
|
-
let e =
|
|
1781
|
-
|
|
1782
|
-
|
|
1796
|
+
d.value = !0;
|
|
1797
|
+
let e = l.value ? [Z("status", "==", "open"), Z("boardId", "==", l.value)] : [Z("status", "==", "open"), Z("target", "==", "post")];
|
|
1798
|
+
g = W(K(s(r, n()), ...e, G("createdAt", "desc"), G(z(), "desc"), U(c)), (e) => {
|
|
1799
|
+
u.value = e.docs.map(_).filter((e) => o(e.boardId)), h = e.docs.at(-1) ?? null, p.value = e.docs.length >= c, d.value = !1;
|
|
1783
1800
|
}, (e) => {
|
|
1784
|
-
console.error("[memi-board:report-queue] onSnapshot failed", e),
|
|
1801
|
+
console.error("[memi-board:report-queue] onSnapshot failed", e), m.value = e.message || String(e), d.value = !1;
|
|
1785
1802
|
});
|
|
1786
1803
|
}
|
|
1787
|
-
|
|
1788
|
-
async function
|
|
1789
|
-
if (!
|
|
1790
|
-
|
|
1804
|
+
R([a, l], v, { immediate: !0 }), F(() => g?.());
|
|
1805
|
+
async function y() {
|
|
1806
|
+
if (!f.value && p.value && h && a.value) {
|
|
1807
|
+
f.value = !0, m.value = "";
|
|
1791
1808
|
try {
|
|
1792
|
-
let e =
|
|
1793
|
-
|
|
1809
|
+
let e = l.value ? [Z("status", "==", "open"), Z("boardId", "==", l.value)] : [Z("status", "==", "open"), Z("target", "==", "post")], t = await V(K(s(r, n()), ...e, G("createdAt", "desc"), G(z(), "desc"), Y(h), U(c + 1))), i = t.docs.slice(0, c), a = new Set(u.value.map((e) => e.id));
|
|
1810
|
+
u.value.push(...i.map(_).filter((e) => !a.has(e.id) && o(e.boardId))), h = i.at(-1) ?? h, p.value = t.docs.length > c;
|
|
1794
1811
|
} catch (e) {
|
|
1795
|
-
|
|
1812
|
+
m.value = e.message || String(e);
|
|
1796
1813
|
} finally {
|
|
1797
|
-
|
|
1814
|
+
f.value = !1;
|
|
1798
1815
|
}
|
|
1799
1816
|
}
|
|
1800
1817
|
}
|
|
1801
|
-
async function
|
|
1802
|
-
e.id &&
|
|
1818
|
+
async function b(e, i) {
|
|
1819
|
+
e.id && o(e.boardId) && await X(t(r, n(), e.postId, e.uid), {
|
|
1803
1820
|
status: i,
|
|
1804
|
-
reviewedAt:
|
|
1805
|
-
reviewedBy:
|
|
1821
|
+
reviewedAt: q(),
|
|
1822
|
+
reviewedBy: be().value?.uid || ""
|
|
1806
1823
|
});
|
|
1807
1824
|
}
|
|
1808
1825
|
return {
|
|
1809
|
-
reports:
|
|
1810
|
-
pending:
|
|
1811
|
-
loadingMore:
|
|
1812
|
-
hasMore:
|
|
1813
|
-
loadError:
|
|
1814
|
-
loadMore:
|
|
1815
|
-
dismissReport: (e) =>
|
|
1816
|
-
actionReport: (e) =>
|
|
1826
|
+
reports: u,
|
|
1827
|
+
pending: d,
|
|
1828
|
+
loadingMore: f,
|
|
1829
|
+
hasMore: p,
|
|
1830
|
+
loadError: m,
|
|
1831
|
+
loadMore: y,
|
|
1832
|
+
dismissReport: (e) => b(e, "dismissed"),
|
|
1833
|
+
actionReport: (e) => b(e, "actioned")
|
|
1817
1834
|
};
|
|
1818
1835
|
}
|
|
1819
1836
|
//#endregion
|
|
1820
1837
|
//#region src/composables/useMemiBoardViews.ts
|
|
1821
1838
|
function kn() {
|
|
1822
|
-
let e = () =>
|
|
1839
|
+
let e = () => M(), t = Q();
|
|
1823
1840
|
function n(t, n) {
|
|
1824
1841
|
let { postsCollection: r } = e();
|
|
1825
1842
|
return `memi-board:viewed:${r}:${t}:${n}`;
|
|
@@ -1842,7 +1859,7 @@ function kn() {
|
|
|
1842
1859
|
if (s && c && !r(s, c)) {
|
|
1843
1860
|
i(s, c);
|
|
1844
1861
|
try {
|
|
1845
|
-
await
|
|
1862
|
+
await X(l(t, e(), c), { viewCount: H(1) });
|
|
1846
1863
|
} catch (e) {
|
|
1847
1864
|
try {
|
|
1848
1865
|
sessionStorage.removeItem(n(s, c));
|
|
@@ -2005,7 +2022,7 @@ var Wn = {
|
|
|
2005
2022
|
via: "empty"
|
|
2006
2023
|
};
|
|
2007
2024
|
function Gn(e = {}) {
|
|
2008
|
-
let t = O(), n =
|
|
2025
|
+
let t = O(), n = P(() => E(L(e.locale)) ?? t.locale.value), r = le().moderation ?? {}, i = Se(), a = (e) => w(n.value, e), { isWriteRestricted: o, restrictedMessage: s, recordContentModerationBlock: c } = ht(), l = Vn([...Bn, ...r.localBlocklist ?? []]);
|
|
2009
2026
|
function u(e) {
|
|
2010
2027
|
let t = e.match(l);
|
|
2011
2028
|
return t ? {
|
|
@@ -2021,7 +2038,7 @@ function Gn(e = {}) {
|
|
|
2021
2038
|
}
|
|
2022
2039
|
function d() {
|
|
2023
2040
|
let e = r.model ?? "gemini-3.5-flash-lite", t = r.useLimitedUseAppCheckTokens !== !1, a = Le(i, {
|
|
2024
|
-
backend: new
|
|
2041
|
+
backend: new Fe(),
|
|
2025
2042
|
useLimitedUseAppCheckTokens: t
|
|
2026
2043
|
});
|
|
2027
2044
|
return Re(a, {
|
|
@@ -2031,10 +2048,10 @@ function Gn(e = {}) {
|
|
|
2031
2048
|
temperature: 0,
|
|
2032
2049
|
maxOutputTokens: 256,
|
|
2033
2050
|
responseMimeType: "application/json",
|
|
2034
|
-
responseSchema:
|
|
2035
|
-
flagged:
|
|
2036
|
-
category:
|
|
2037
|
-
reason:
|
|
2051
|
+
responseSchema: Ie.object({ properties: {
|
|
2052
|
+
flagged: Ie.boolean(),
|
|
2053
|
+
category: Ie.string(),
|
|
2054
|
+
reason: Ie.string()
|
|
2038
2055
|
} })
|
|
2039
2056
|
}
|
|
2040
2057
|
});
|
|
@@ -2157,7 +2174,9 @@ function Gn(e = {}) {
|
|
|
2157
2174
|
//#endregion
|
|
2158
2175
|
//#region src/composables/useMemiBoardUsers.ts
|
|
2159
2176
|
var Kn = [
|
|
2177
|
+
"owner",
|
|
2160
2178
|
"admin",
|
|
2179
|
+
"manager",
|
|
2161
2180
|
"staff",
|
|
2162
2181
|
"user"
|
|
2163
2182
|
].map((e) => ({
|
|
@@ -2166,12 +2185,12 @@ var Kn = [
|
|
|
2166
2185
|
description: w("ko", `boardUsers.roleDescription.${e}`)
|
|
2167
2186
|
}));
|
|
2168
2187
|
function qn(t = {}) {
|
|
2169
|
-
let n = () =>
|
|
2188
|
+
let n = () => M(), i = Q(), { t: a } = O(), o = P(() => L(t.enabled) ?? !0 ? e(i, n()) : null), s = ye(o, { ssrKey: r(n(), "users-management") });
|
|
2170
2189
|
async function c(e, t) {
|
|
2171
2190
|
if (!Kn.some((e) => e.value === t)) throw Error(a("boardUsers.unsupportedRole"));
|
|
2172
|
-
await
|
|
2191
|
+
await X(f(i, n(), e), {
|
|
2173
2192
|
role: t,
|
|
2174
|
-
updatedAt:
|
|
2193
|
+
updatedAt: q()
|
|
2175
2194
|
});
|
|
2176
2195
|
}
|
|
2177
2196
|
return {
|
|
@@ -2183,10 +2202,10 @@ function qn(t = {}) {
|
|
|
2183
2202
|
//#endregion
|
|
2184
2203
|
//#region src/composables/useMemiBoardUserProfile.ts
|
|
2185
2204
|
function Jn(e) {
|
|
2186
|
-
let t =
|
|
2205
|
+
let t = Q(), n = () => M(), r = P(() => L(e)), i = P(() => {
|
|
2187
2206
|
let e = r.value;
|
|
2188
2207
|
return e ? f(t, n(), e) : null;
|
|
2189
|
-
}), { data: a, pending: o } =
|
|
2208
|
+
}), { data: a, pending: o } = xe(i);
|
|
2190
2209
|
return {
|
|
2191
2210
|
profile: a,
|
|
2192
2211
|
profilePending: o
|
|
@@ -2337,9 +2356,9 @@ function Sr(e, t, n) {
|
|
|
2337
2356
|
};
|
|
2338
2357
|
}
|
|
2339
2358
|
function Cr() {
|
|
2340
|
-
let { locale: e } = O(), t =
|
|
2359
|
+
let { locale: e } = O(), t = Q(), n = pe(t, "settings", "homeLayout"), { data: r, pending: i } = xe(n), a = P(() => (Array.isArray(r.value?.blocks) ? r.value.blocks : mr).map((t, n) => Sr(t, n, e.value)));
|
|
2341
2360
|
async function o(t) {
|
|
2342
|
-
await
|
|
2361
|
+
await J(n, {
|
|
2343
2362
|
columns: 12,
|
|
2344
2363
|
blocks: t.map((t, n) => {
|
|
2345
2364
|
let r = t, i = _r(r), a = tr(i, t.count);
|
|
@@ -2357,7 +2376,7 @@ function Cr() {
|
|
|
2357
2376
|
order: n
|
|
2358
2377
|
};
|
|
2359
2378
|
}),
|
|
2360
|
-
updatedAt:
|
|
2379
|
+
updatedAt: q()
|
|
2361
2380
|
});
|
|
2362
2381
|
}
|
|
2363
2382
|
return {
|
|
@@ -2365,7 +2384,7 @@ function Cr() {
|
|
|
2365
2384
|
pending: i,
|
|
2366
2385
|
sections: a,
|
|
2367
2386
|
blocks: a,
|
|
2368
|
-
hasSavedLayout:
|
|
2387
|
+
hasSavedLayout: P(() => Array.isArray(r.value?.blocks)),
|
|
2369
2388
|
saveSections: o,
|
|
2370
2389
|
saveBlocks: o
|
|
2371
2390
|
};
|
|
@@ -2373,20 +2392,20 @@ function Cr() {
|
|
|
2373
2392
|
//#endregion
|
|
2374
2393
|
//#region src/composables/useMemiBoardMiniPosts.ts
|
|
2375
2394
|
function wr(e, t) {
|
|
2376
|
-
let n =
|
|
2377
|
-
let r = Math.max(1, Math.floor(Number(
|
|
2378
|
-
return a && o.unshift(
|
|
2379
|
-
}), { data: s, pending: c, error: l } =
|
|
2395
|
+
let n = Q(), i = () => M(), a = L(e)?.trim() || "all", o = P(() => {
|
|
2396
|
+
let r = Math.max(1, Math.floor(Number(L(t)) || 5)), a = L(e)?.trim() || "", o = [Z("isPublished", "==", !0), Z("listed", "==", !0)];
|
|
2397
|
+
return a && o.unshift(Z("boardId", "==", a)), K(N(n, i()), ...o, G("createdAt", "desc"), U(r));
|
|
2398
|
+
}), { data: s, pending: c, error: l } = ye(o, { ssrKey: r(i(), `mini-list/${a}`) });
|
|
2380
2399
|
return {
|
|
2381
|
-
posts:
|
|
2400
|
+
posts: P(() => s.value ?? []),
|
|
2382
2401
|
pending: c,
|
|
2383
2402
|
error: l
|
|
2384
2403
|
};
|
|
2385
2404
|
}
|
|
2386
2405
|
function Tr(e) {
|
|
2387
|
-
let t =
|
|
2406
|
+
let t = Q(), n = () => M(), i = P(() => [...new Set(L(e).map((e) => e.trim()).filter(Boolean))].slice(0, 10)), a = i.value.join(",") || "none", o = P(() => i.value.length ? K(N(t, n()), Z(z(), "in", i.value)) : null), { data: s, pending: c, error: l } = ye(o, { ssrKey: r(n(), `mini-picked/${a}`) });
|
|
2388
2407
|
return {
|
|
2389
|
-
posts:
|
|
2408
|
+
posts: P(() => {
|
|
2390
2409
|
let e = new Map((s.value ?? []).map((e) => [e.id, e])), t = [];
|
|
2391
2410
|
for (let n of i.value) {
|
|
2392
2411
|
let r = e.get(n);
|
|
@@ -2401,6 +2420,15 @@ function Tr(e) {
|
|
|
2401
2420
|
//#endregion
|
|
2402
2421
|
//#region src/data/versionHistory.ts
|
|
2403
2422
|
var Er = [
|
|
2423
|
+
{
|
|
2424
|
+
version: "0.46.0",
|
|
2425
|
+
date: "2026-10-21",
|
|
2426
|
+
highlights: [
|
|
2427
|
+
"일반 사용자·스태프·매니저·관리자·최고 관리자, 다섯 가지 역할을 지원해요",
|
|
2428
|
+
"게시판별 매니저가 설정과 스태프 배정을 관리할 수 있어요",
|
|
2429
|
+
"서비스에 맞게 역할 이름을 바꿀 수 있어요"
|
|
2430
|
+
]
|
|
2431
|
+
},
|
|
2404
2432
|
{
|
|
2405
2433
|
version: "0.45.1",
|
|
2406
2434
|
date: "2026-10-15",
|
|
@@ -2732,12 +2760,12 @@ function Pr(e) {
|
|
|
2732
2760
|
return !e || typeof e != "object" ? null : "toMillis" in e && typeof e.toMillis == "function" ? e.toMillis() : null;
|
|
2733
2761
|
}
|
|
2734
2762
|
function Fr(e = {}) {
|
|
2735
|
-
let t = O(), n =
|
|
2763
|
+
let t = O(), n = P(() => E(L(e.locale)) ?? t.locale.value), r = (e, t) => w(n.value, e, t), i = Se(), a = Q(), o = be(), s = le();
|
|
2736
2764
|
async function c() {
|
|
2737
2765
|
let e = o.value?.uid;
|
|
2738
2766
|
if (!e) throw Error(r("writingAssistant.loginRequired"));
|
|
2739
|
-
await
|
|
2740
|
-
let n = f(a,
|
|
2767
|
+
await _e(a, async (t) => {
|
|
2768
|
+
let n = f(a, M(), e), i = await t.get(n);
|
|
2741
2769
|
if (!i.exists()) throw Error(r("writingAssistant.userMissing"));
|
|
2742
2770
|
let o = i.data(), s = Pr(o.aiWritingWindowAt), c = Math.max(0, Math.floor(Number(o.aiWritingCount) || 0)), l = Date.now(), u = s != null && l - s < Or;
|
|
2743
2771
|
if (u && c >= 10) {
|
|
@@ -2749,8 +2777,8 @@ function Fr(e = {}) {
|
|
|
2749
2777
|
}
|
|
2750
2778
|
t.update(n, {
|
|
2751
2779
|
aiWritingCount: u ? c + 1 : 1,
|
|
2752
|
-
aiWritingWindowAt: u ? o.aiWritingWindowAt :
|
|
2753
|
-
updatedAt:
|
|
2780
|
+
aiWritingWindowAt: u ? o.aiWritingWindowAt : q(),
|
|
2781
|
+
updatedAt: q()
|
|
2754
2782
|
});
|
|
2755
2783
|
});
|
|
2756
2784
|
}
|
|
@@ -2759,7 +2787,7 @@ function Fr(e = {}) {
|
|
|
2759
2787
|
if (!e.content.trim()) throw Error(r("writingAssistant.contentRequired"));
|
|
2760
2788
|
await c();
|
|
2761
2789
|
let l = s.moderation ?? {}, u = Le(i, {
|
|
2762
|
-
backend: new
|
|
2790
|
+
backend: new Fe(),
|
|
2763
2791
|
useLimitedUseAppCheckTokens: l.useLimitedUseAppCheckTokens !== !1
|
|
2764
2792
|
}), d = Re(u, {
|
|
2765
2793
|
model: l.model ?? "gemini-3.5-flash-lite",
|
|
@@ -2804,12 +2832,12 @@ function Lr(e, t) {
|
|
|
2804
2832
|
});
|
|
2805
2833
|
}
|
|
2806
2834
|
function Rr() {
|
|
2807
|
-
let e =
|
|
2835
|
+
let e = Se(), { moderation: t } = le();
|
|
2808
2836
|
function n(n, r) {
|
|
2809
2837
|
let i = Le(e, {
|
|
2810
|
-
backend: new
|
|
2838
|
+
backend: new Fe(),
|
|
2811
2839
|
useLimitedUseAppCheckTokens: t.useLimitedUseAppCheckTokens !== !1
|
|
2812
|
-
}), a =
|
|
2840
|
+
}), a = Ie.object({ properties: Object.fromEntries(r.map((e) => [e, Ie.string()])) });
|
|
2813
2841
|
return Re(i, {
|
|
2814
2842
|
model: t.model ?? "gemini-3.5-flash-lite",
|
|
2815
2843
|
systemInstruction: [
|
|
@@ -2822,7 +2850,7 @@ function Rr() {
|
|
|
2822
2850
|
temperature: .2,
|
|
2823
2851
|
maxOutputTokens: 2048,
|
|
2824
2852
|
responseMimeType: "application/json",
|
|
2825
|
-
responseSchema:
|
|
2853
|
+
responseSchema: Ie.object({ properties: Object.fromEntries(n.map((e) => [e, a])) })
|
|
2826
2854
|
}
|
|
2827
2855
|
});
|
|
2828
2856
|
}
|
|
@@ -2848,7 +2876,7 @@ function Rr() {
|
|
|
2848
2876
|
return l;
|
|
2849
2877
|
}
|
|
2850
2878
|
async function i(e, t = {}) {
|
|
2851
|
-
let n = t.source ?? "ko", i = (t.targets ??
|
|
2879
|
+
let n = t.source ?? "ko", i = (t.targets ?? j.map((e) => e.code)).filter((e) => e !== n), a = t.purpose ?? "website UI labels", o = e.map((e) => ({
|
|
2852
2880
|
...e,
|
|
2853
2881
|
fields: Object.fromEntries(Object.entries(e.fields).map(([e, t]) => [e, t.trim()]).filter(([, e]) => e))
|
|
2854
2882
|
})).filter((e) => Object.keys(e.fields).length);
|
|
@@ -2936,6 +2964,6 @@ function Hr(e) {
|
|
|
2936
2964
|
return c(), i && a.length && n.push(`<pre class="overflow-x-auto rounded-lg bg-muted p-3 text-sm"><code>${a.join("\n")}</code></pre>`), n.join("\n");
|
|
2937
2965
|
}
|
|
2938
2966
|
//#endregion
|
|
2939
|
-
export { un as AUTHOR_MEMO_MAX_LENGTH, Yn as BOARD_SECTION_COLS, Qn as BOARD_SECTION_KINDS, $n as BOARD_SECTION_SORTS, Kn as BOARD_USER_ROLES, gn as COMMENT_BODY_MAX_LENGTH, st as DEFAULT_BLOCK_BAN_DECAY_MS, ot as DEFAULT_BLOCK_BAN_THRESHOLD, Gt as DEFAULT_BOARDS, Kt as DEFAULT_CATEGORIES, S as DEFAULT_COMMENTS_COLLECTION,
|
|
2967
|
+
export { un as AUTHOR_MEMO_MAX_LENGTH, Yn as BOARD_SECTION_COLS, Qn as BOARD_SECTION_KINDS, $n as BOARD_SECTION_SORTS, Kn as BOARD_USER_ROLES, gn as COMMENT_BODY_MAX_LENGTH, st as DEFAULT_BLOCK_BAN_DECAY_MS, ot as DEFAULT_BLOCK_BAN_THRESHOLD, Gt as DEFAULT_BOARDS, Kt as DEFAULT_CATEGORIES, S as DEFAULT_COMMENTS_COLLECTION, ce as DEFAULT_LIKES_COLLECTION, T as DEFAULT_MEMI_BOARD_LOCALE, h as DEFAULT_POSTS_COLLECTION, n as DEFAULT_REPORTS_COLLECTION, se as DEFAULT_SETTINGS_COLLECTION, g as DEFAULT_USERS_COLLECTION, re as FALLBACK_MEMI_BOARD_LOCALE, j as MEMI_BOARD_LOCALES, Cn as REPORT_DETAIL_MAX_LENGTH, wn as REPORT_REASONS, Dr as WRITING_ASSISTANT_DAILY_LIMIT, Be as asHttpUrl, Ke as boardListOgDescription, Ge as boardListOgTitle, We as boardPostOgDescription, Ue as boardPostOgTitle, Xn as boardSectionKinds, Zn as boardSectionSorts, r as boardSsrKey, f as boardUserDoc, e as boardUsersCol, Bt as buildPostPreview, tt as canManageBoardByRole, nt as canWriteCommentByRole, tr as clampSectionCount, k as commentDoc, u as commentsCol, b as configureMemiBoard, er as defaultSectionCount, ct as effectiveModerationBlockCount, xt as extractEditorImageUrls, Qe as fetchPublicListForSeo, Ze as fetchPublicPostForSeo, x as formatDate, ne as formatFullDate, ae as formatRelativeDate, dt as formatRestrictedUntilLabel, C as formatTimestampDetails, Ft as hasBodyImage, Pt as hasBodyText, yt as imeSafeSubmitClick, vt as imeSafeSubmitPointerDown, et as isAssignedStaff, It as isContentEmpty, Zt as isFirestorePermissionDenied, A as isMemiBoardLocaleLoaded, ut as isModerationWriteRestricted, d as likeDoc, p as likeDocId, a as likesCol, oe as loadMemiBoardLocale, zr as localizedText, xn as memiBoardCommentLikesKey, ie as memiBoardHostLocaleKey, D as memiBoardLocaleInfo, fr as miniBoardView, sr as miniCommentLink, or as miniMoreLink, cr as miniPostImage, ar as miniPostLink, lr as miniPostTitle, pr as miniPostsView, ur as miniViewGroup, dr as miniViewLabel, lt as moderationWriteRestrictedUntilMs, qe as normalizeBasePath, Sr as normalizeBoardSection, E as normalizeMemiBoardLocale, nr as pairSectionCols, Mt as plainTextFromHtml, c as postBodyDoc, l as postDoc, Ct as postNamespaceFromStoragePath, m as postStorageFolder, N as postsCol, Hr as renderMarkdownToHtml, t as reportDoc, v as reportDocId, Tn as reportReasonLabel, s as reportsCol, _ as resolveBoardPathConfig, Je as resolvePublicSeoDb, rr as sectionColClass, ir as sectionMinHeight, y as settingsCol, o as settingsDoc, te as slugify, St as storagePathFromDownloadUrl, Nt as titleFromBody, He as toAbsoluteUrl, Ve as toBoardOgImageUrl, w as translate, M as useBoardPathConfig, ht as useMemiBoardAuth, fn as useMemiBoardAuthorMemo, Rr as useMemiBoardAutoTranslate, ln as useMemiBoardCommentFeed, Sn as useMemiBoardCommentLikes, vn as useMemiBoardComments, le as useMemiBoardConfig, O as useMemiBoardI18n, bn as useMemiBoardLikes, wr as useMemiBoardMiniLatest, Tr as useMemiBoardMiniPicked, Gn as useMemiBoardModeration, nn as useMemiBoardPost, tn as useMemiBoardPostList, $t as useMemiBoardPosts, yn as useMemiBoardReplies, On as useMemiBoardReportQueue, En as useMemiBoardReports, Cr as useMemiBoardSections, Yt as useMemiBoardSettings, sn as useMemiBoardUserComments, an as useMemiBoardUserPosts, Jn as useMemiBoardUserProfile, qn as useMemiBoardUsers, kn as useMemiBoardViews, Fr as useMemiBoardWritingAssistant, Er as versionHistory, zt as videoListCoverUrl, Rt as youtubeId };
|
|
2940
2968
|
|
|
2941
2969
|
//# sourceMappingURL=index.js.map
|