@brftech/filex-core 0.5.0 → 0.7.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/dist/{ArchiveViewer-DKW-HyXT.js → ArchiveViewer-w6GDJJt9.js} +2 -2
- package/dist/{ArchiveViewer-DKW-HyXT.js.map → ArchiveViewer-w6GDJJt9.js.map} +1 -1
- package/dist/{CsvViewer-D2HmP2yr.js → CsvViewer-Ci5-mke8.js} +2 -2
- package/dist/{CsvViewer-D2HmP2yr.js.map → CsvViewer-Ci5-mke8.js.map} +1 -1
- package/dist/{DrawioViewer-DPNvOFCs.js → DrawioViewer-D2iMuQfD.js} +2 -2
- package/dist/{DrawioViewer-DPNvOFCs.js.map → DrawioViewer-D2iMuQfD.js.map} +1 -1
- package/dist/{EpubViewer-ByqjNuNL.js → EpubViewer-D4ydsa9X.js} +2 -2
- package/dist/{EpubViewer-ByqjNuNL.js.map → EpubViewer-D4ydsa9X.js.map} +1 -1
- package/dist/{IpynbViewer-2iONhbuJ.js → IpynbViewer-CWBwiFKX.js} +2 -2
- package/dist/{IpynbViewer-2iONhbuJ.js.map → IpynbViewer-CWBwiFKX.js.map} +1 -1
- package/dist/{MermaidViewer-CmiU7hIT.js → MermaidViewer-CDhuqQli.js} +2 -2
- package/dist/{MermaidViewer-CmiU7hIT.js.map → MermaidViewer-CDhuqQli.js.map} +1 -1
- package/dist/{PsdViewer-Inhl2yN9.js → PsdViewer-C_TkFb2H.js} +2 -2
- package/dist/{PsdViewer-Inhl2yN9.js.map → PsdViewer-C_TkFb2H.js.map} +1 -1
- package/dist/{TiffViewer-C2AFFEze.js → TiffViewer-BmWCXR7e.js} +2 -2
- package/dist/{TiffViewer-C2AFFEze.js.map → TiffViewer-BmWCXR7e.js.map} +1 -1
- package/dist/{Viewer3D-YdW14q_n.js → Viewer3D-5kPT1QsY.js} +2 -2
- package/dist/{Viewer3D-YdW14q_n.js.map → Viewer3D-5kPT1QsY.js.map} +1 -1
- package/dist/filex-core.js +66 -47
- package/dist/filex-core.umd.cjs +41 -40
- package/dist/filex-core.umd.cjs.map +1 -1
- package/dist/index-nc0-oI_l.js +11723 -0
- package/dist/index-nc0-oI_l.js.map +1 -0
- package/dist/index.d.ts +364 -1
- package/dist/style.css +1 -1
- package/package.json +1 -1
- package/src/FileExplorer.vue +756 -23
- package/src/components/CommandPalette.vue +12 -1
- package/src/components/EncryptedFolderModal.vue +125 -0
- package/src/components/GalleryView.vue +215 -0
- package/src/components/GridView.vue +2 -0
- package/src/components/InspectorPanel.vue +170 -0
- package/src/components/ListView.vue +2 -0
- package/src/components/SecondaryPane.vue +411 -0
- package/src/components/TabBar.vue +174 -0
- package/src/components/Toolbar.vue +23 -5
- package/src/composables/useFileApi.ts +60 -0
- package/src/composables/useKeyboardShortcuts.ts +19 -0
- package/src/composables/useTabs.ts +222 -0
- package/src/index.ts +27 -0
- package/src/lib/e2ecrypto.ts +299 -0
- package/src/locales/en.ts +67 -0
- package/src/locales/tr.ts +67 -0
- package/src/modals/NewFolderModal.vue +18 -0
- package/src/modals/PreviewModal.vue +7 -2
- package/src/styles/base.css +631 -0
- package/src/types/FileNode.ts +4 -1
- package/dist/index-eARevpz0.js +0 -9952
- package/dist/index-eARevpz0.js.map +0 -1
package/src/locales/en.ts
CHANGED
|
@@ -332,4 +332,71 @@ export const en: Record<string, string> = {
|
|
|
332
332
|
'toolbar.view_label': 'View',
|
|
333
333
|
'list.aria': 'File list',
|
|
334
334
|
'grid.aria': 'File grid',
|
|
335
|
+
|
|
336
|
+
/* === wiring:d1 — tabs + split pane === */
|
|
337
|
+
'tabs.strip': 'Tabs',
|
|
338
|
+
'tabs.new': 'New tab',
|
|
339
|
+
'tabs.close': 'Close tab',
|
|
340
|
+
'tabs.split': 'Split view',
|
|
341
|
+
'tabs.split_off': 'Close split',
|
|
342
|
+
'ctx.open_new_tab': 'Open in new tab',
|
|
343
|
+
'shortcuts.group.tabs': 'Tabs',
|
|
344
|
+
'shortcuts.tab_new': 'New tab',
|
|
345
|
+
'shortcuts.tab_close': 'Close tab',
|
|
346
|
+
'shortcuts.tab_next': 'Next tab',
|
|
347
|
+
'shortcuts.tab_prev': 'Previous tab',
|
|
348
|
+
'cmd.tab_new': 'Open a new tab',
|
|
349
|
+
'cmd.split_toggle': 'Toggle split view',
|
|
350
|
+
'split.pane': 'Secondary pane',
|
|
351
|
+
'split.close': 'Close the side pane',
|
|
352
|
+
'split.error': 'Could not load the listing',
|
|
353
|
+
'split.retry': 'Retry',
|
|
354
|
+
'split.copy_queued': 'Copy queued',
|
|
355
|
+
'split.cross_copy': 'Different storages — copy queued instead',
|
|
356
|
+
'split.cross_failed': 'Cross-storage copy is not supported by this server',
|
|
357
|
+
/* === /wiring:d1 === */
|
|
358
|
+
/* wiring:d2 — gallery view */
|
|
359
|
+
'toolbar.view.gallery': 'Gallery',
|
|
360
|
+
'gallery.aria': 'File gallery',
|
|
361
|
+
/* /wiring:d2 */
|
|
362
|
+
/* wiring:d3 — inspector node comments */
|
|
363
|
+
'inspector.section.comments': 'Comments',
|
|
364
|
+
'inspector.comments.empty': 'No comments yet.',
|
|
365
|
+
'inspector.comments.placeholder': 'Write a comment…',
|
|
366
|
+
'inspector.comments.send': 'Send',
|
|
367
|
+
'inspector.comments.delete': 'Delete comment',
|
|
368
|
+
/* wiring:e2 — end-to-end encrypted folders */
|
|
369
|
+
'e2e.create.title': 'Create encrypted folder',
|
|
370
|
+
'e2e.create.option': 'Create encrypted folder…',
|
|
371
|
+
'e2e.create.pw_placeholder': 'Folder password (min 8 characters)',
|
|
372
|
+
'e2e.create.pw2_placeholder': 'Repeat the password',
|
|
373
|
+
'e2e.create.warn_title': 'NO WAY BACK',
|
|
374
|
+
'e2e.create.warn_body':
|
|
375
|
+
'Files open ONLY with this password. The password is NEVER stored on the server; if you forget it the content is lost forever. There is no recovery — not even an admin can open it.',
|
|
376
|
+
'e2e.create.ack': 'I understand: if I lose the password my data cannot be recovered.',
|
|
377
|
+
'e2e.create.ack_required': 'Please confirm the warning to continue.',
|
|
378
|
+
'e2e.create.pw_short': 'Password must be at least 8 characters.',
|
|
379
|
+
'e2e.create.pw_mismatch': 'Passwords do not match.',
|
|
380
|
+
'e2e.create.bad_name': 'Invalid folder name.',
|
|
381
|
+
'e2e.create.create': 'Create encrypted folder',
|
|
382
|
+
'e2e.create.busy': 'Creating…',
|
|
383
|
+
'e2e.create.done': 'Encrypted folder created',
|
|
384
|
+
'e2e.create.failed': 'Could not create the encrypted folder',
|
|
385
|
+
'e2e.create.nested': 'You cannot create an encrypted folder inside another one.',
|
|
386
|
+
'e2e.locked.title': 'This folder is end-to-end encrypted',
|
|
387
|
+
'e2e.locked.hint': 'Enter the folder password to see its contents. The password stays in this tab’s memory only.',
|
|
388
|
+
'e2e.locked.pw_placeholder': 'Folder password',
|
|
389
|
+
'e2e.locked.unlock': 'Unlock',
|
|
390
|
+
'e2e.locked.busy': 'Verifying…',
|
|
391
|
+
'e2e.unlock.wrong': 'Wrong password.',
|
|
392
|
+
'e2e.unlock.marker_missing': 'Could not read the key file (.filex-e2e.json).',
|
|
393
|
+
'e2e.strip.label': 'Encrypted folder — unlocked',
|
|
394
|
+
'e2e.strip.lock': 'Lock',
|
|
395
|
+
'e2e.locked_toast': 'Folder locked',
|
|
396
|
+
'e2e.upload.too_big': 'Files over 200 MB cannot be uploaded to an encrypted folder (MVP limit)',
|
|
397
|
+
'e2e.upload.locked': 'Unlock the folder first',
|
|
398
|
+
'e2e.decrypting': 'Decrypting…',
|
|
399
|
+
'e2e.decrypt_failed': 'Could not decrypt the file (password changed or file corrupted).',
|
|
400
|
+
'e2e.download.failed': 'Could not download the encrypted file.',
|
|
401
|
+
/* /wiring:e2 */
|
|
335
402
|
};
|
package/src/locales/tr.ts
CHANGED
|
@@ -332,4 +332,71 @@ export const tr: Record<string, string> = {
|
|
|
332
332
|
'toolbar.view_label': 'Görünüm',
|
|
333
333
|
'list.aria': 'Dosya listesi',
|
|
334
334
|
'grid.aria': 'Dosya ızgarası',
|
|
335
|
+
|
|
336
|
+
/* === wiring:d1 — sekmeler + split panel === */
|
|
337
|
+
'tabs.strip': 'Sekmeler',
|
|
338
|
+
'tabs.new': 'Yeni sekme',
|
|
339
|
+
'tabs.close': 'Sekmeyi kapat',
|
|
340
|
+
'tabs.split': 'Görünümü böl',
|
|
341
|
+
'tabs.split_off': 'Bölmeyi kapat',
|
|
342
|
+
'ctx.open_new_tab': 'Yeni sekmede aç',
|
|
343
|
+
'shortcuts.group.tabs': 'Sekmeler',
|
|
344
|
+
'shortcuts.tab_new': 'Yeni sekme',
|
|
345
|
+
'shortcuts.tab_close': 'Sekmeyi kapat',
|
|
346
|
+
'shortcuts.tab_next': 'Sonraki sekme',
|
|
347
|
+
'shortcuts.tab_prev': 'Önceki sekme',
|
|
348
|
+
'cmd.tab_new': 'Yeni sekme aç',
|
|
349
|
+
'cmd.split_toggle': 'Görünümü böl / birleştir',
|
|
350
|
+
'split.pane': 'İkincil panel',
|
|
351
|
+
'split.close': 'Yan paneli kapat',
|
|
352
|
+
'split.error': 'Liste yüklenemedi',
|
|
353
|
+
'split.retry': 'Yeniden dene',
|
|
354
|
+
'split.copy_queued': 'Kopyalama kuyruğa alındı',
|
|
355
|
+
'split.cross_copy': 'Depolar farklı — kopyalama kuyruğa alındı',
|
|
356
|
+
'split.cross_failed': 'Depolar arası kopyalama bu sunucuda desteklenmiyor',
|
|
357
|
+
/* === /wiring:d1 === */
|
|
358
|
+
/* wiring:d2 — galeri görünümü */
|
|
359
|
+
'toolbar.view.gallery': 'Galeri',
|
|
360
|
+
'gallery.aria': 'Dosya galerisi',
|
|
361
|
+
/* /wiring:d2 */
|
|
362
|
+
/* wiring:d3 — Yorumlar (inspector node comments) */
|
|
363
|
+
'inspector.section.comments': 'Yorumlar',
|
|
364
|
+
'inspector.comments.empty': 'Henüz yorum yok.',
|
|
365
|
+
'inspector.comments.placeholder': 'Yorum yaz…',
|
|
366
|
+
'inspector.comments.send': 'Gönder',
|
|
367
|
+
'inspector.comments.delete': 'Yorumu sil',
|
|
368
|
+
/* wiring:e2 — uçtan uca şifreli klasörler */
|
|
369
|
+
'e2e.create.title': 'Şifreli klasör oluştur',
|
|
370
|
+
'e2e.create.option': 'Şifreli klasör oluştur…',
|
|
371
|
+
'e2e.create.pw_placeholder': 'Klasör parolası (en az 8 karakter)',
|
|
372
|
+
'e2e.create.pw2_placeholder': 'Parolayı tekrar girin',
|
|
373
|
+
'e2e.create.warn_title': 'GERİ DÖNÜŞÜ YOK',
|
|
374
|
+
'e2e.create.warn_body':
|
|
375
|
+
'Dosyalar yalnız bu parolayla açılır. Parola sunucuda TUTULMAZ; unutursanız içerik sonsuza dek kaybolur. Kurtarma yolu yoktur — yönetici dahil kimse açamaz.',
|
|
376
|
+
'e2e.create.ack': 'Anladım: parolayı kaybedersem verilerim kurtarılamaz.',
|
|
377
|
+
'e2e.create.ack_required': 'Devam etmek için uyarıyı onaylayın.',
|
|
378
|
+
'e2e.create.pw_short': 'Parola en az 8 karakter olmalı.',
|
|
379
|
+
'e2e.create.pw_mismatch': 'Parolalar birbirini tutmuyor.',
|
|
380
|
+
'e2e.create.bad_name': 'Geçersiz klasör adı.',
|
|
381
|
+
'e2e.create.create': 'Şifreli klasörü oluştur',
|
|
382
|
+
'e2e.create.busy': 'Oluşturuluyor…',
|
|
383
|
+
'e2e.create.done': 'Şifreli klasör oluşturuldu',
|
|
384
|
+
'e2e.create.failed': 'Şifreli klasör oluşturulamadı',
|
|
385
|
+
'e2e.create.nested': 'Şifreli klasörün içine ikinci bir şifreli klasör açılamaz.',
|
|
386
|
+
'e2e.locked.title': 'Bu klasör uçtan uca şifreli',
|
|
387
|
+
'e2e.locked.hint': 'İçeriği görmek için klasör parolasını girin. Parola yalnız bu sekmede, bellekte tutulur.',
|
|
388
|
+
'e2e.locked.pw_placeholder': 'Klasör parolası',
|
|
389
|
+
'e2e.locked.unlock': 'Kilidi aç',
|
|
390
|
+
'e2e.locked.busy': 'Doğrulanıyor…',
|
|
391
|
+
'e2e.unlock.wrong': 'Parola yanlış.',
|
|
392
|
+
'e2e.unlock.marker_missing': 'Şifre dosyası (.filex-e2e.json) okunamadı.',
|
|
393
|
+
'e2e.strip.label': 'Şifreli klasör — kilit açık',
|
|
394
|
+
'e2e.strip.lock': 'Kilitle',
|
|
395
|
+
'e2e.locked_toast': 'Klasör kilitlendi',
|
|
396
|
+
'e2e.upload.too_big': '200 MB üstü dosyalar şifreli klasöre yüklenemez (MVP sınırı)',
|
|
397
|
+
'e2e.upload.locked': 'Önce klasörün kilidini açın',
|
|
398
|
+
'e2e.decrypting': 'Çözülüyor…',
|
|
399
|
+
'e2e.decrypt_failed': 'Dosya çözülemedi (parola değişmiş ya da dosya bozulmuş olabilir).',
|
|
400
|
+
'e2e.download.failed': 'Şifreli dosya indirilemedi.',
|
|
401
|
+
/* /wiring:e2 */
|
|
335
402
|
};
|
|
@@ -7,11 +7,17 @@ import Modal from './Modal.vue';
|
|
|
7
7
|
const props = defineProps<{
|
|
8
8
|
open: boolean;
|
|
9
9
|
locale: LocaleCode;
|
|
10
|
+
/* wiring:e2 — hosts hide the encrypted option (e.g. already inside an
|
|
11
|
+
* encrypted folder / feature-gated embeds). Default: shown. */
|
|
12
|
+
encryptedOption?: boolean;
|
|
10
13
|
}>();
|
|
11
14
|
|
|
12
15
|
const emit = defineEmits<{
|
|
13
16
|
(e: 'close'): void;
|
|
14
17
|
(e: 'submit', name: string): void;
|
|
18
|
+
/* wiring:e2 — user picked "Create encrypted folder…" — the parent swaps
|
|
19
|
+
* this modal for EncryptedFolderModal. */
|
|
20
|
+
(e: 'encrypted'): void;
|
|
15
21
|
}>();
|
|
16
22
|
|
|
17
23
|
const { t } = useLocale(() => props.locale);
|
|
@@ -51,6 +57,18 @@ function submit() {
|
|
|
51
57
|
@keydown.enter.prevent="submit"
|
|
52
58
|
/>
|
|
53
59
|
<p v-if="err" class="fe-form__error">{{ err }}</p>
|
|
60
|
+
<!-- wiring:e2 — encrypted-folder entry point lives inside the normal
|
|
61
|
+
new-folder flow so every trigger (toolbar / context menu / palette)
|
|
62
|
+
reaches it without extra wiring. -->
|
|
63
|
+
<button
|
|
64
|
+
v-if="encryptedOption !== false"
|
|
65
|
+
type="button"
|
|
66
|
+
class="fe-e2e-optlink"
|
|
67
|
+
@click="emit('encrypted')"
|
|
68
|
+
>
|
|
69
|
+
🔒 {{ t('e2e.create.option') }}
|
|
70
|
+
</button>
|
|
71
|
+
<!-- /wiring:e2 -->
|
|
54
72
|
</form>
|
|
55
73
|
<template #actions>
|
|
56
74
|
<button type="button" class="fe-btn" @click="emit('close')">
|
|
@@ -46,6 +46,11 @@ const props = defineProps<{
|
|
|
46
46
|
pdfSaveUrl?: string | null;
|
|
47
47
|
/** Standalone full-screen viewer route — `?path=…&storage=…&type=…`. */
|
|
48
48
|
viewerBaseUrl?: string | null;
|
|
49
|
+
/* wiring:e2 — false hides the "Düzenle" / "Yeni Sekmede Aç" buttons.
|
|
50
|
+
* The standalone route fetches RAW server bytes, which inside an
|
|
51
|
+
* E2E-encrypted folder is ciphertext (and its save path could clobber
|
|
52
|
+
* the encrypted blob) — the host disables the escape hatches there. */
|
|
53
|
+
newTabEnabled?: boolean;
|
|
49
54
|
/** Drop the dialog chrome (backdrop tint, header bar, footer actions)
|
|
50
55
|
* so the viewer fills the full viewport. Used by the standalone
|
|
51
56
|
* /files/edit route where the browser tab IS the container — a
|
|
@@ -1020,13 +1025,13 @@ function loadOnlyOfficeScript(base: string): Promise<void> {
|
|
|
1020
1025
|
</div>
|
|
1021
1026
|
<template #actions>
|
|
1022
1027
|
<button
|
|
1023
|
-
v-if="file && openMode === 'view' && canEditKind"
|
|
1028
|
+
v-if="file && openMode === 'view' && canEditKind && newTabEnabled !== false /* wiring:e2 */"
|
|
1024
1029
|
type="button"
|
|
1025
1030
|
class="fe-btn fe-btn--primary"
|
|
1026
1031
|
@click="openEditInNewTab"
|
|
1027
1032
|
>✏ {{ t('viewer.edit') }}</button>
|
|
1028
1033
|
<button
|
|
1029
|
-
v-if="file"
|
|
1034
|
+
v-if="file && newTabEnabled !== false /* wiring:e2 */"
|
|
1030
1035
|
type="button"
|
|
1031
1036
|
class="fe-btn"
|
|
1032
1037
|
@click="openInNewTab"
|