Merge remote-tracking branch 'origin/main' into react/settings

; Conflicts:
;	apps/client/package.json
;	apps/client/src/translations/en/translation.json
;	apps/client/src/translations/tw/translation.json
;	pnpm-lock.yaml
This commit is contained in:
Elian Doran
2025-08-19 13:50:27 +03:00
53 changed files with 2330 additions and 972 deletions

View File

@@ -1,6 +1,6 @@
<p>Trilium supports configuration via a file named <code>config.ini</code> and
environment variables. Please review the file named <a href="https://github.com/TriliumNext/Trilium/blob/develop/apps/server/src/assets/config-sample.ini">config-sample.ini</a> in
the <a href="https://github.com/TriliumNext/Trilium">Notes</a> repository
environment variables. Please review the file named <a href="https://github.com/TriliumNext/Trilium/blob/main/apps/server/src/assets/config-sample.ini">config-sample.ini</a> in
the <a href="https://github.com/TriliumNext/Trilium">Trilium</a> repository
to see what values are supported.</p>
<p>You can provide the same values via environment variables instead of the <code>config.ini</code> file,
and these environment variables use the following format:</p>

View File

@@ -231,23 +231,17 @@
first, then adds fuzzy matching when needed.</p>
<h3>How Progressive Search Works</h3>
<ol>
<li>
<p><strong>Phase 1 - Exact Matching</strong>: When you search, Trilium first
looks for exact matches of your search terms. This handles the vast majority
of searches (90%+) and returns results almost instantly.</p>
</li>
<li>
<p><strong>Phase 2 - Fuzzy Fallback</strong>: If Phase 1 doesn't find enough
high-quality results (fewer than 5 results with good relevance scores),
Trilium automatically adds fuzzy matching to find results with typos or
spelling variations.</p>
</li>
<li>
<p><strong>Result Ordering</strong>: Exact matches always appear before fuzzy
matches, regardless of individual scores. This ensures that when you search
for "project", notes containing the exact word "project" will appear before
notes containing similar words like "projects" or "projection".</p>
</li>
<li><strong>Phase 1 - Exact Matching</strong>: When you search, Trilium first
looks for exact matches of your search terms. This handles the vast majority
of searches (90%+) and returns results almost instantly.</li>
<li><strong>Phase 2 - Fuzzy Fallback</strong>: If Phase 1 doesn't find enough
high-quality results (fewer than 5 results with good relevance scores),
Trilium automatically adds fuzzy matching to find results with typos or
spelling variations.</li>
<li><strong>Result Ordering</strong>: Exact matches always appear before fuzzy
matches, regardless of individual scores. This ensures that when you search
for "project", notes containing the exact word "project" will appear before
notes containing similar words like "projects" or "projection".</li>
</ol>
<h3>Progressive Search Behavior</h3>
<ul>

View File

@@ -2,9 +2,9 @@
<p>There are two types of error logs, both of which are useful when reporting
bugs.</p>
<ul>
<li data-list-item-id="e5d891396e04bcb9d78ea10421e8ee6be"><a class="reference-link" href="#root/pOsGYCXsbNQG/BgmBlOIl72jZ/qzNzp9LYQyPT/_help_bnyigUA2UK7s">Backend (server) logs</a>
<li><a class="reference-link" href="#root/_help_bnyigUA2UK7s">Backend (server) logs</a>
</li>
<li data-list-item-id="e94ecb76c9af944e47bf8b5c5dabf027a"><a class="reference-link" href="#root/pOsGYCXsbNQG/BgmBlOIl72jZ/qzNzp9LYQyPT/_help_9yEHzMyFirZR">Frontend logs</a>
<li><a class="reference-link" href="#root/_help_9yEHzMyFirZR">Frontend logs</a>
</li>
</ul>
<h2>Providing sensitive data</h2>

View File

@@ -1,10 +1,10 @@
<h2>Accessing via the backend log</h2>
<p>In the&nbsp;<a class="reference-link" href="#root/pOsGYCXsbNQG/gh7bpGYxajRS/Vc8PjrjAGuOp/_help_x3i7MxGccDuM">Global menu</a>,
<p>In the&nbsp;<a class="reference-link" href="#root/_help_x3i7MxGccDuM">Global menu</a>,
go to Advanced → Show backend log</p>
<h2>Location on the disk</h2>
<p>Backend logs are stored on the file system. To find them, open the&nbsp;
<a
class="reference-link" href="#root/pOsGYCXsbNQG/Otzi9La2YAUX/_help_tAassRL4RSQL">Data directory</a>, go to the <code>log</code> subdirectory and find the
class="reference-link" href="#root/_help_tAassRL4RSQL">Data directory</a>, go to the <code>log</code> subdirectory and find the
latest log file, e.g. <code>trilium-2022-12-14.log</code>.&nbsp;</p>
<h2>Reporting backend bugs</h2>
<p>You can attach the whole file to the bug report (preferable) or open it
@@ -15,12 +15,18 @@
in order to reduce the space consumption.</p>
<p>It's possible to change the retention period by modifying the&nbsp;
<a
class="reference-link" href="#root/pOsGYCXsbNQG/tC7s2alapj8V/_help_Gzjqa934BdH4">Configuration (config.ini or environment variables)</a>&nbsp;via the <code>.ini</code> file:</p><pre><code class="language-text-x-trilium-auto">[Logging]
class="reference-link" href="#root/_help_Gzjqa934BdH4">Configuration (config.ini or environment variables)</a>&nbsp;via the <code>.ini</code> file:</p><pre><code class="language-text-x-trilium-auto">[Logging]
retentionDays=7</code></pre>
<p>Or via the environment variable <code>TRILIUM_LOGGING_RETENTION_DAYS</code>.</p>
<aside
class="admonition note">
<p>Special cases:</p>
<ul>
<li>Positive values indicate the number of days worth of logs to keep</li>
<li>A value of 0 results with the default value (90 days) to be used</li>
<li>Negative values (e.g. <code>-1</code>) result with all logs to be kept,
irrespective how ancient and numerous (and</li>
</ul>
<aside class="admonition note">
<p>If you set the retention days to a low number, you might notice that not
all the log files are being deleted. This is because a minimum number of
logs (7 at the time of writing) is maintained at all times.</p>
</aside>
</aside>

View File

@@ -5,9 +5,9 @@
console is cleared on app restart.</p>
<p>If that doesn't work, then:</p>
<ul>
<li data-list-item-id="e1f836ac8425c0d56072614c40c996bbd">in Trilium desktop app, go to top-left menu button -&gt; Advanced -&gt;
<li>in Trilium desktop app, go to top-left menu button -&gt; Advanced -&gt;
Open Dev Tools</li>
<li data-list-item-id="e8bd27605bedefe884b826a1899413a6d">In Firefox/Chrome right-click anywhere in the page and click Inspect:</li>
<li>In Firefox/Chrome right-click anywhere in the page and click Inspect:</li>
</ul>
<p>
<img src="Frontend logs_error-logs-f.png">

View File

@@ -0,0 +1,14 @@
{
"keyboard_actions": {
"back-in-note-history": "به یادداشت قبلی در تاریخچه",
"forward-in-note-history": "به یادداشت بعدی در تاریخچه برو",
"open-jump-to-note-dialog": "باز کردن پنجرهٔ «پرش به یادداشت»",
"open-command-palette": "باز کردن پالت دستورات",
"scroll-to-active-note": "پیمایش درخت یادداشت به یادداشت جاری",
"quick-search": "فعال‌سازی نوار جستجوی سریع",
"search-in-subtree": "‪جستجوی یادداشت‌ها در زیردرخت یادداشت فعال",
"expand-subtree": "باز کردن زیردرخت یادداشت جاری",
"collapse-tree": "بستن کامل درخت یادداشت‌ها",
"collapse-subtree": "بستن زیرشاخه‌های یادداشت فعلی"
}
}

View File

@@ -0,0 +1,10 @@
{
"keyboard_actions": {
"quick-search": "Aktivoi pikahakupalkki",
"collapse-tree": "Kutista valmis muistiinpanopuu",
"creating-and-moving-notes": "Luo ja siirrä muistioita",
"delete-note": "Poista muistio",
"move-note-up": "Siirrä muistio ylös",
"open-command-palette": "Avaa komentovalikko"
}
}

View File

@@ -134,7 +134,7 @@
},
"setup_sync-from-desktop": {
"heading": "Synchroniser depuis une application de bureau",
"description": "Cette procédure doit être réalisée depuis l'application de bureau:",
"description": "Cette procédure doit être réalisée depuis l'application de bureau :",
"step1": "Ouvrez l'application Trilium Notes.",
"step2": "Dans le menu Trilium, cliquez sur Options.",
"step3": "Cliquez sur la catégorie Synchroniser.",
@@ -310,6 +310,46 @@
"clone-notes-to": "Cloner les notes vers",
"move-notes-to": "Déplacer les notes vers",
"copy-notes-to-clipboard": "Copier les notes dans le presse-papiers",
"paste-notes-from-clipboard": "Coller les notes depuis le presse-papiers"
"paste-notes-from-clipboard": "Coller les notes depuis le presse-papiers",
"cut-notes-to-clipboard": "Couper les notes vers le presse-papier",
"select-all-notes-in-parent": "Selectionner toutes les notes dans le parent",
"add-note-above-to-selection": "Ajouter la note au-dessus à la selection",
"add-note-below-to-selection": "Ajouter la note dessous à la selection",
"duplicate-subtree": "Dupliquer la sous-arborescence",
"open-new-tab": "Ouvrir un nouvel onglet",
"close-active-tab": "Fermer l'onglet actif",
"reopen-last-tab": "Réouvrir le dernier onglet",
"activate-next-tab": "Activer l'onglet suivant",
"activate-previous-tab": "Activer l'onglet précédent",
"open-new-window": "Ouvrir une nouvelle fenêtre",
"toggle-system-tray-icon": "Activer/Désactiver l'icone de la barre d'état",
"toggle-zen-mode": "Activer/Désactiver le mode Zen",
"switch-to-first-tab": "Aller au premier onglet",
"switch-to-second-tab": "Aller au second onglet",
"switch-to-third-tab": "Aller au troisième onglet",
"switch-to-fourth-tab": "Aller au quatrième onglet",
"switch-to-fifth-tab": "Aller au cinquième onglet",
"switch-to-sixth-tab": "Aller au sixième onglet",
"switch-to-seventh-tab": "Aller au septième onglet",
"switch-to-eighth-tab": "Aller au huitième onglet",
"switch-to-ninth-tab": "Aller au neuvième onglet",
"switch-to-last-tab": "Aller au dernier onglet",
"show-note-source": "Afficher la source de la note",
"show-options": "Afficher les options",
"show-revisions": "Afficher les révisions",
"show-recent-changes": "Afficher les changements récents",
"show-sql-console": "Afficher la console SQL",
"show-backend-log": "Afficher le journal du backend",
"show-help": "Afficher l'aide",
"show-cheatsheet": "Afficher la fiche de triche",
"add-link-to-text": "Ajouter un lien au texte",
"follow-link-under-cursor": "Suivre le lien en dessous du curseur",
"insert-date-and-time-to-text": "Insérer la date et l'heure dans le texte",
"paste-markdown-into-text": "Coller du Markdown dans le texte",
"cut-into-note": "Couper dans une note",
"add-include-note-to-text": "Ajouter une note inclusion au texte",
"edit-read-only-note": "Modifier une note en lecture seule",
"add-new-label": "Ajouter une nouvelle étiquette",
"add-new-relation": "Ajouter une nouvelle relation"
}
}

View File

@@ -0,0 +1 @@
{}

View File

@@ -6,20 +6,20 @@
"open-command-palette": "コマンドパレットを開く",
"scroll-to-active-note": "ノートツリーをアクティブなノートまでスクロールする",
"search-in-subtree": "アクティブなノートのサブツリー内でノートを検索する",
"expand-subtree": "現在のノートのサブツリーを展開する",
"expand-subtree": "現在のノートのサブツリーを展開",
"collapse-tree": "ノートツリー全体を折りたたむ",
"collapse-subtree": "現在のノートのサブツリーを折りたたむ",
"creating-and-moving-notes": "ノートの作成と移動",
"create-note-after": "アクティブなノートの後にノートを作成する",
"create-note-into": "アクティブなノートの子ノートを作成する",
"delete-note": "ノートを削除する",
"move-note-up": "ノートを上に移動する",
"move-note-down": "ノートを下に移動する",
"move-note-up-in-hierarchy": "ノートを上の階層に移動する",
"move-note-down-in-hierarchy": "ノートを下の階層に移動する",
"delete-note": "ノートを削除",
"move-note-up": "ノートを上に移動",
"move-note-down": "ノートを下に移動",
"move-note-up-in-hierarchy": "ノートを上の階層に移動",
"move-note-down-in-hierarchy": "ノートを下の階層に移動",
"edit-note-title": "ツリーからノートの詳細にジャンプして、タイトルを編集",
"clone-notes-to": "選択したノートを複製する",
"move-notes-to": "選択したノートを移動する",
"clone-notes-to": "選択したノートを複製",
"move-notes-to": "選択したノートを移動",
"copy-notes-to-clipboard": "選択したノートをクリップボードにコピー",
"paste-notes-from-clipboard": "クリップボードからアクティブなノートにノートを貼り付け",
"cut-notes-to-clipboard": "選択したノートをクリップボードにカット",

View File

@@ -0,0 +1,66 @@
{
"keyboard_actions": {
"back-in-note-history": "Nawigacja do poprzedniej notatki w historii",
"forward-in-note-history": "Nawigacja do następnej notatki w historii",
"open-jump-to-note-dialog": "Otwórz dialog \"Skocz do notatki\"",
"open-command-palette": "Otwórz paletę komend",
"scroll-to-active-note": "Przewiń drzewo notatek do aktywnej notatki",
"quick-search": "Aktywuj szybki pasek wyszukiwania",
"search-in-subtree": "Szukaj notatek w sub-drzewie aktywnej notatki",
"expand-subtree": "Rozszerz sub-drzewo obecnej notatki",
"collapse-tree": "Schowaj kompletne drzewo notatek",
"collapse-subtree": "Schowaj sub-drzewo aktualnej notatki",
"sort-child-notes": "Sortuj podnotatki",
"creating-and-moving-notes": "Tworzenie oraz przestawianie notatek",
"create-note-after": "Utwórz notatkę po aktywnej notatce",
"create-note-into": "Utwórz notatkę jako podnotatka aktywnej notatki",
"create-note-into-inbox": "Utwórz notatkę w skrzyncę (jeśli zdefiniowana) lub jako notatka dnia",
"delete-note": "Usuń notatkę",
"move-note-up": "Przestaw notatkę wyżej",
"move-note-down": "Przestaw notatkę niżej",
"move-note-up-in-hierarchy": "Przestaw notatkę wyżej w hierarchii",
"move-note-down-in-hierarchy": "Przestaw notatkę niżej w hierarchii",
"edit-note-title": "Przeskocz z drzewa do detali notatki i edytuj tytuł",
"edit-branch-prefix": "Pokaż dialog \"Edytuj prefiks gałęzi\"",
"clone-notes-to": "Sklonuj zaznaczone notatki",
"move-notes-to": "Przestaw zaznaczone notatki",
"note-clipboard": "Schowek notatki",
"copy-notes-to-clipboard": "Skopiuj zaznaczone notatki do schowka",
"paste-notes-from-clipboard": "Wklej notatki ze schowka do aktywnej notatki",
"cut-notes-to-clipboard": "Wytnij zaznaczone notatki do schowka",
"select-all-notes-in-parent": "Zaznacz wszystkie notatki z poziomu aktualnej notatki",
"add-note-above-to-the-selection": "Dodaj notatkę nad zaznaczeniem",
"add-note-below-to-selection": "Dodaj notatkę pod zaznaczeniem",
"duplicate-subtree": "Duplikuj sub-drzewo",
"tabs-and-windows": "Karty i Okna",
"open-new-tab": "Otwórz nową kartę",
"close-active-tab": "Zamknij aktywną kartę",
"reopen-last-tab": "Otwórz ponownie ostatnio zamkniętą kartę",
"activate-next-tab": "Aktywuj kartę po prawej",
"activate-previous-tab": "Aktywuj kartę po lewej",
"open-new-window": "Otwórz nowe puste okno",
"toggle-tray": "Pokaż/schowaj aplikację z zasobnika systemowego",
"first-tab": "Aktywuj piewszą kartę z listy",
"second-tab": "Aktywuj drugą kartę z listy",
"third-tab": "Aktywuj trzecią kartę z listy",
"fourth-tab": "Aktywuj czwartą kartę z listy",
"fifth-tab": "Aktywuj piątą kartę z listy",
"sixth-tab": "Aktywuj szóstą kartę z listy",
"seventh-tab": "Aktywuj siódmą kartę z listy",
"eight-tab": "Aktywuj ósmą kartę z listy",
"ninth-tab": "Aktywuj dziewiątą kartę z listy",
"last-tab": "Aktywuj ostatnią kartę z listy",
"dialogs": "Okna dialogowe",
"show-note-source": "Pokaż dialog \"Źródło notatki\"",
"show-options": "Pokaż stronę \"Opcje\"",
"show-revisions": "Pokaż dialog \"Rewizje notatki\"",
"show-recent-changes": "Pokaż dialog \"Ostatnie zmiany\"",
"show-sql-console": "Pokaż stronę \"Konsola SQL\"",
"show-backend-log": "Pokaż stronę \"Logi Backendu\"",
"show-help": "Pokaż wbudowany poradnik użytkownika",
"show-cheatsheet": "Pokaż dialog z częstymi operacjami klawiatury",
"text-note-operations": "Operacje tekstowe notatki",
"add-link-to-text": "Otwórz dialog dodawania linku do tekstu",
"follow-link-under-cursor": "Podążaj za linkiem, w którym znajduje się kursor"
}
}

View File

@@ -1 +1,34 @@
{}
{
"keyboard_actions": {
"open-command-palette": "Открыть палитру команд",
"quick-search": "Активировать панель быстрого поиска",
"move-note-up": "Переместить заметку вверх",
"move-note-down": "Переместить заметку вниз",
"move-note-up-in-hierarchy": "Переместить заметку вверх в иерархии",
"move-note-down-in-hierarchy": "Переместить заметку вниз в иерархии",
"delete-note": "Удалить заметку",
"back-in-note-history": "Перейти к предыдущей заметке в истории",
"forward-in-note-history": "Перейти к следующей заметке в истории",
"scroll-to-active-note": "Прокрутить дерево заметок до активной заметки",
"search-in-subtree": "Искать заметки в поддереве активной заметки",
"expand-subtree": "Развернуть поддерево текущей заметки",
"collapse-tree": "Свернуть дерево заметок полностью",
"collapse-subtree": "Свернуть поддерево текущей заметки",
"sort-child-notes": "Сортировка дочерних заметок",
"creating-and-moving-notes": "Создание и перемещение заметок",
"create-note-after": "Создать заметку после активной заметки",
"create-note-into": "Создать заметку как дочернюю для активной заметки",
"edit-note-title": "Перейти от дерева к деталям заметки и отредактировать заголовок",
"clone-notes-to": "Клонировать выбранные заметки",
"move-notes-to": "Переместить выбранные заметки",
"note-clipboard": "Буфер обмена заметок",
"copy-notes-to-clipboard": "Скопировать выбранные заметки в буфер обмена",
"paste-notes-from-clipboard": "Вставить заметки из буфера обмена в активную заметку",
"cut-notes-to-clipboard": "Вырезать выбранные заметки в буфер обмена",
"duplicate-subtree": "Дублировать поддерево",
"tabs-and-windows": "Вкладки и окна",
"open-new-tab": "Открыть новую вкладку",
"close-active-tab": "Закрыть активную вкладку",
"reopen-last-tab": "Повторно открыть последнюю закрытую вкладку"
}
}

View File

@@ -13,24 +13,24 @@
"move-note-down": "下移筆記",
"move-note-up-in-hierarchy": "將筆記層級上移",
"move-note-down-in-hierarchy": "將筆記層級下移",
"edit-note-title": "從筆記樹跳轉至筆記詳情並編輯標題",
"edit-note-title": "從筆記樹跳轉至筆記內容並編輯標題",
"edit-branch-prefix": "顯示編輯分支前綴對話方塊",
"note-clipboard": "筆記剪貼簿",
"copy-notes-to-clipboard": "複製選的筆記至剪貼簿",
"copy-notes-to-clipboard": "複製選的筆記至剪貼簿",
"paste-notes-from-clipboard": "從剪貼簿貼上筆記至目前筆記中",
"cut-notes-to-clipboard": "剪下選的筆記至剪貼簿",
"select-all-notes-in-parent": "選擇前筆記級別的所有筆記",
"cut-notes-to-clipboard": "剪下選的筆記至剪貼簿",
"select-all-notes-in-parent": "選擇前筆記級別的所有筆記",
"add-note-above-to-the-selection": "加入上方筆記至選擇中",
"add-note-below-to-selection": "加入下方筆記至選擇中",
"duplicate-subtree": "複製子階層",
"tabs-and-windows": "分頁和視窗",
"open-new-tab": "打開新分頁",
"close-active-tab": "關閉活動分頁",
"close-active-tab": "關閉使用中分頁",
"reopen-last-tab": "重新打開最後關閉的分頁",
"activate-next-tab": "切換至右側分頁",
"activate-previous-tab": "切換至左側分頁",
"open-new-window": "打開新空白視窗",
"toggle-tray": "從系統匣顯示/隱藏應用程式",
"toggle-tray": "從系統匣顯示 / 隱藏應用程式",
"first-tab": "切換至列表中第一個分頁",
"second-tab": "切換至列表中第二個分頁",
"third-tab": "切換至列表中第三個分頁",
@@ -44,7 +44,7 @@
"dialogs": "對話方塊",
"show-note-source": "顯示筆記來源對話方塊",
"show-options": "打開選項頁面",
"show-revisions": "顯示筆記修改歷史對話方塊",
"show-revisions": "顯示筆記歷史版本對話方塊",
"show-recent-changes": "顯示最近更改對話方塊",
"show-sql-console": "打開 SQL 控制台頁面",
"show-backend-log": "打開後端日誌頁面",
@@ -54,18 +54,18 @@
"insert-date-and-time-to-text": "插入目前日期和時間",
"paste-markdown-into-text": "將剪貼簿中的 Markdown 文字貼上",
"cut-into-note": "從目前筆記剪下選擇的部分並新增至子筆記",
"add-include-note-to-text": "打開對話方塊以包含筆記",
"add-include-note-to-text": "打開對話方塊以內嵌筆記",
"edit-readonly-note": "編輯唯讀筆記",
"attributes-labels-and-relations": "屬性(標籤和關係)",
"add-new-label": "新增新標籤",
"create-new-relation": "新增新關聯",
"ribbon-tabs": "功能區分頁",
"toggle-basic-properties": "顯示基本屬性",
"toggle-file-properties": "顯示文件屬性",
"toggle-file-properties": "顯示檔案屬性",
"toggle-image-properties": "顯示圖像屬性",
"toggle-owned-attributes": "顯示擁有的屬性",
"toggle-inherited-attributes": "顯示繼承屬性",
"toggle-promoted-attributes": "顯示升的屬性",
"toggle-owned-attributes": "顯示自有屬性",
"toggle-inherited-attributes": "顯示繼承屬性",
"toggle-promoted-attributes": "顯示升的屬性",
"toggle-link-map": "顯示連結地圖",
"toggle-note-info": "顯示筆記資訊",
"toggle-note-paths": "顯示筆記路徑",
@@ -73,9 +73,9 @@
"other": "其他",
"toggle-right-pane": "切換右側面板的顯示,包括目錄和高亮",
"print-active-note": "列印目前筆記",
"open-note-externally": "以預設應用程式打開筆記文件",
"open-note-externally": "以預設應用程式打開筆記檔案",
"render-active-note": "渲染(重新渲染)目前筆記",
"run-active-note": "執行目前的 JavaScript前端/後端)程式碼筆記",
"run-active-note": "執行目前的 JavaScript前端 / 後端)程式碼筆記",
"toggle-note-hoisting": "聚焦目前筆記",
"unhoist": "取消任何聚焦",
"reload-frontend-app": "重新載入前端應用",
@@ -86,24 +86,24 @@
"zoom-in": "放大",
"note-navigation": "筆記導航",
"reset-zoom-level": "重設縮放比例",
"copy-without-formatting": "以純文字複製選文字",
"force-save-revision": "強制新增/儲存目前筆記的新版本",
"copy-without-formatting": "以純文字複製選文字",
"force-save-revision": "強制新增 / 儲存目前筆記的新版本",
"show-help": "顯示用戶說明",
"toggle-book-properties": "顯示集合屬性",
"back-in-note-history": "跳轉至歷史記錄中的上一個筆記",
"forward-in-note-history": "跳轉至歷史記錄中的下一個筆記",
"open-command-palette": "打開命令面板",
"scroll-to-active-note": "動筆記樹至目前筆記",
"scroll-to-active-note": "動筆記樹至目前筆記",
"quick-search": "開啟快速搜尋列",
"create-note-after": "新增筆記於目前筆記之後",
"create-note-into": "新增目前筆記的子筆記",
"clone-notes-to": "克隆選的筆記至",
"move-notes-to": "移動選的筆記至",
"clone-notes-to": "克隆選的筆記至",
"move-notes-to": "移動選的筆記至",
"show-cheatsheet": "顯示常用鍵盤快捷鍵",
"find-in-text": "顯示搜尋面板",
"toggle-classic-editor-toolbar": "顯示固定工具列編輯器的格式分頁",
"export-as-pdf": "匯出目前筆記為 PDF",
"toggle-zen-mode": "啟用/禁用禪模式(極簡界面以專注編輯)"
"toggle-zen-mode": "啟用 / 禁用禪模式(極簡界面以專注編輯)"
},
"login": {
"title": "登入",
@@ -214,7 +214,7 @@
"back-in-note-history": "返回筆記歷史",
"forward-in-note-history": "前進筆記歷史",
"jump-to-note": "跳轉至…",
"scroll-to-active-note": "動至目前筆記",
"scroll-to-active-note": "動至目前筆記",
"quick-search": "快速搜尋",
"search-in-subtree": "在子階層中搜尋",
"expand-subtree": "展開子階層",
@@ -246,8 +246,8 @@
"activate-next-tab": "切換至下一分頁",
"activate-previous-tab": "切換至上一分頁",
"open-new-window": "打開新視窗",
"toggle-system-tray-icon": "顯示/隱藏系統匣圖示",
"toggle-zen-mode": "啟用/禁用禪模式",
"toggle-system-tray-icon": "顯示 / 隱藏系統匣圖示",
"toggle-zen-mode": "啟用 / 禁用禪模式",
"switch-to-first-tab": "切換至第一個分頁",
"switch-to-second-tab": "切換至第二個分頁",
"switch-to-third-tab": "切換至第三個分頁",
@@ -260,7 +260,7 @@
"switch-to-last-tab": "切換至第最後一個分頁",
"show-note-source": "顯示筆記原始碼",
"show-options": "顯示選項",
"show-revisions": "顯示修改歷史",
"show-revisions": "顯示歷史版本",
"show-recent-changes": "顯示最近更改",
"show-sql-console": "顯示 SQL 控制台",
"show-backend-log": "顯示後端日誌",
@@ -271,18 +271,18 @@
"insert-date-and-time-to-text": "插入日期和時間",
"paste-markdown-into-text": "貼上 Markdown 文字",
"cut-into-note": "剪下至筆記",
"add-include-note-to-text": "新增包含筆記",
"add-include-note-to-text": "新增內嵌筆記",
"edit-read-only-note": "編輯唯讀筆記",
"add-new-label": "新增標籤",
"add-new-relation": "新增關聯",
"toggle-ribbon-tab-classic-editor": "顯示功能區分頁:經典編輯器",
"toggle-ribbon-tab-basic-properties": "顯示功能區分頁:基本屬性",
"toggle-ribbon-tab-book-properties": "顯示功能區分頁:書籍屬性",
"toggle-ribbon-tab-file-properties": "顯示功能區分頁:文件屬性",
"toggle-ribbon-tab-file-properties": "顯示功能區分頁:檔案屬性",
"toggle-ribbon-tab-image-properties": "顯示功能區分頁:圖片屬性",
"toggle-ribbon-tab-owned-attributes": "顯示功能區分頁:自有屬性",
"toggle-ribbon-tab-inherited-attributes": "顯示功能區分頁:繼承屬性",
"toggle-ribbon-tab-promoted-attributes": "顯示功能區分頁:升屬性",
"toggle-ribbon-tab-promoted-attributes": "顯示功能區分頁:升屬性",
"toggle-ribbon-tab-note-map": "顯示功能區分頁:筆記地圖",
"toggle-ribbon-tab-note-info": "顯示功能區分頁:筆記資訊",
"toggle-ribbon-tab-note-paths": "顯示功能區分頁:筆記路徑",
@@ -313,15 +313,15 @@
"bulk-action-title": "批次操作",
"backend-log-title": "後端日誌",
"user-hidden-title": "隱藏的用戶",
"launch-bar-templates-title": "啟動模版",
"launch-bar-templates-title": "啟動模版",
"base-abstract-launcher-title": "基礎摘要啟動器",
"command-launcher-title": "命令啟動器",
"note-launcher-title": "筆記啟動器",
"script-launcher-title": "腳本啟動器",
"built-in-widget-title": "內建小工具",
"spacer-title": "空白占位",
"custom-widget-title": "自訂小工具",
"launch-bar-title": "啟動",
"built-in-widget-title": "內建元件",
"spacer-title": "分隔元件",
"custom-widget-title": "自訂元件",
"launch-bar-title": "啟動",
"available-launchers-title": "可用啟動器",
"go-to-previous-note-title": "跳轉至前一筆記",
"go-to-next-note-title": "跳轉至後一筆記",
@@ -349,7 +349,7 @@
"etapi-title": "ETAPI",
"backup-title": "備份",
"sync-title": "同步",
"ai-llm-title": "AI/LLM",
"ai-llm-title": "AI / LLM",
"other": "其他",
"advanced-title": "進階",
"visible-launchers-title": "可見啟動器",
@@ -373,7 +373,7 @@
"export_filter": "PDF 文件 (*.pdf)",
"unable-to-export-message": "目前筆記無法被匯出為 PDF 。",
"unable-to-export-title": "無法匯出為 PDF",
"unable-to-save-message": "選定文件無法被寫入。請重試或選擇其他路徑。"
"unable-to-save-message": "所選檔案無法被寫入。請重試或選擇其他路徑。"
},
"tray": {
"tooltip": "Trilium 筆記",

View File

@@ -0,0 +1,12 @@
{
"keyboard_actions": {
"back-in-note-history": "Перейти до минулої нотатки в історії",
"forward-in-note-history": "Перейти до наступної нотатки в історії",
"open-command-palette": "Відкрити палітру команд",
"scroll-to-active-note": "Прокрутити дерево нотаток до активної нотатки",
"quick-search": "Показати панель швидкого пошуку",
"search-in-subtree": "Пошук нотаток в піддереві активної нотатки",
"expand-subtree": "Розкрити піддерево поточної нотатки",
"collapse-tree": "Згорнути все дерево нотаток"
}
}

View File

@@ -35,6 +35,8 @@ class SearchResult {
highlightedNotePathTitle?: string;
contentSnippet?: string;
highlightedContentSnippet?: string;
attributeSnippet?: string;
highlightedAttributeSnippet?: string;
private fuzzyScore: number; // Track fuzzy score separately
constructor(notePathArray: string[]) {

View File

@@ -468,8 +468,13 @@ function extractContentSnippet(noteId: string, searchTokens: string[], maxLength
content = striptags(content);
}
// Normalize whitespace
content = content.replace(/\s+/g, " ").trim();
// Normalize whitespace while preserving paragraph breaks
// First, normalize multiple newlines to double newlines (paragraph breaks)
content = content.replace(/\n\s*\n/g, "\n\n");
// Then normalize spaces within lines
content = content.split('\n').map(line => line.replace(/\s+/g, " ").trim()).join('\n');
// Finally trim the whole content
content = content.trim();
if (!content) {
return "";
@@ -495,21 +500,36 @@ function extractContentSnippet(noteId: string, searchTokens: string[], maxLength
// Extract snippet
let snippet = content.substring(snippetStart, snippetStart + maxLength);
// Try to start/end at word boundaries
if (snippetStart > 0) {
const firstSpace = snippet.indexOf(" ");
if (firstSpace > 0 && firstSpace < 20) {
snippet = snippet.substring(firstSpace + 1);
}
snippet = "..." + snippet;
}
if (snippetStart + maxLength < content.length) {
const lastSpace = snippet.lastIndexOf(" ");
if (lastSpace > snippet.length - 20) {
snippet = snippet.substring(0, lastSpace);
}
// If snippet contains linebreaks, limit to max 4 lines and override character limit
const lines = snippet.split('\n');
if (lines.length > 4) {
snippet = lines.slice(0, 4).join('\n');
// Add ellipsis if we truncated lines
snippet = snippet + "...";
} else if (lines.length > 1) {
// For multi-line snippets, just limit to 4 lines (keep existing snippet)
snippet = lines.slice(0, 4).join('\n');
if (lines.length > 4) {
snippet = snippet + "...";
}
} else {
// Single line content - apply original word boundary logic
// Try to start/end at word boundaries
if (snippetStart > 0) {
const firstSpace = snippet.search(/\s/);
if (firstSpace > 0 && firstSpace < 20) {
snippet = snippet.substring(firstSpace + 1);
}
snippet = "..." + snippet;
}
if (snippetStart + maxLength < content.length) {
const lastSpace = snippet.search(/\s[^\s]*$/);
if (lastSpace > snippet.length - 20 && lastSpace > 0) {
snippet = snippet.substring(0, lastSpace);
}
snippet = snippet + "...";
}
}
return snippet;
@@ -519,6 +539,90 @@ function extractContentSnippet(noteId: string, searchTokens: string[], maxLength
}
}
function extractAttributeSnippet(noteId: string, searchTokens: string[], maxLength: number = 200): string {
const note = becca.notes[noteId];
if (!note) {
return "";
}
try {
// Get all attributes for this note
const attributes = note.getAttributes();
if (!attributes || attributes.length === 0) {
return "";
}
let matchingAttributes: Array<{name: string, value: string, type: string}> = [];
// Look for attributes that match the search tokens
for (const attr of attributes) {
const attrName = attr.name?.toLowerCase() || "";
const attrValue = attr.value?.toLowerCase() || "";
const attrType = attr.type || "";
// Check if any search token matches the attribute name or value
const hasMatch = searchTokens.some(token => {
const normalizedToken = normalizeString(token.toLowerCase());
return attrName.includes(normalizedToken) || attrValue.includes(normalizedToken);
});
if (hasMatch) {
matchingAttributes.push({
name: attr.name || "",
value: attr.value || "",
type: attrType
});
}
}
if (matchingAttributes.length === 0) {
return "";
}
// Limit to 4 lines maximum, similar to content snippet logic
const lines: string[] = [];
for (const attr of matchingAttributes.slice(0, 4)) {
let line = "";
if (attr.type === "label") {
line = attr.value ? `#${attr.name}="${attr.value}"` : `#${attr.name}`;
} else if (attr.type === "relation") {
// For relations, show the target note title if possible
const targetNote = attr.value ? becca.notes[attr.value] : null;
const targetTitle = targetNote ? targetNote.title : attr.value;
line = `~${attr.name}="${targetTitle}"`;
}
if (line) {
lines.push(line);
}
}
let snippet = lines.join('\n');
// Apply length limit while preserving line structure
if (snippet.length > maxLength) {
// Try to truncate at word boundaries but keep lines intact
const truncated = snippet.substring(0, maxLength);
const lastNewline = truncated.lastIndexOf('\n');
if (lastNewline > maxLength / 2) {
// If we can keep most content by truncating to last complete line
snippet = truncated.substring(0, lastNewline);
} else {
// Otherwise just truncate and add ellipsis
const lastSpace = truncated.lastIndexOf(' ');
snippet = truncated.substring(0, lastSpace > maxLength / 2 ? lastSpace : maxLength - 3);
snippet = snippet + "...";
}
}
return snippet;
} catch (e) {
log.error(`Error extracting attribute snippet for note ${noteId}: ${e}`);
return "";
}
}
function searchNotesForAutocomplete(query: string, fastSearch: boolean = true) {
const searchContext = new SearchContext({
fastSearch: fastSearch,
@@ -533,9 +637,10 @@ function searchNotesForAutocomplete(query: string, fastSearch: boolean = true) {
const trimmed = allSearchResults.slice(0, 200);
// Extract content snippets
// Extract content and attribute snippets
for (const result of trimmed) {
result.contentSnippet = extractContentSnippet(result.noteId, searchContext.highlightedTokens);
result.attributeSnippet = extractAttributeSnippet(result.noteId, searchContext.highlightedTokens);
}
highlightSearchResults(trimmed, searchContext.highlightedTokens, searchContext.ignoreInternalAttributes);
@@ -549,6 +654,8 @@ function searchNotesForAutocomplete(query: string, fastSearch: boolean = true) {
highlightedNotePathTitle: result.highlightedNotePathTitle,
contentSnippet: result.contentSnippet,
highlightedContentSnippet: result.highlightedContentSnippet,
attributeSnippet: result.attributeSnippet,
highlightedAttributeSnippet: result.highlightedAttributeSnippet,
icon: icon ?? "bx bx-note"
};
});
@@ -574,7 +681,18 @@ function highlightSearchResults(searchResults: SearchResult[], highlightedTokens
// Initialize highlighted content snippet
if (result.contentSnippet) {
result.highlightedContentSnippet = escapeHtml(result.contentSnippet).replace(/[<{}]/g, "");
// Escape HTML but preserve newlines for later conversion to <br>
result.highlightedContentSnippet = escapeHtml(result.contentSnippet);
// Remove any stray < { } that might interfere with our highlighting markers
result.highlightedContentSnippet = result.highlightedContentSnippet.replace(/[<{}]/g, "");
}
// Initialize highlighted attribute snippet
if (result.attributeSnippet) {
// Escape HTML but preserve newlines for later conversion to <br>
result.highlightedAttributeSnippet = escapeHtml(result.attributeSnippet);
// Remove any stray < { } that might interfere with our highlighting markers
result.highlightedAttributeSnippet = result.highlightedAttributeSnippet.replace(/[<{}]/g, "");
}
}
@@ -612,6 +730,16 @@ function highlightSearchResults(searchResults: SearchResult[], highlightedTokens
contentRegex.lastIndex += 2;
}
}
// Highlight in attribute snippet
if (result.highlightedAttributeSnippet) {
const attributeRegex = new RegExp(escapeRegExp(token), "gi");
while ((match = attributeRegex.exec(normalizeString(result.highlightedAttributeSnippet))) !== null) {
result.highlightedAttributeSnippet = wrapText(result.highlightedAttributeSnippet, match.index, token.length, "{", "}");
// 2 characters are added, so we need to adjust the index
attributeRegex.lastIndex += 2;
}
}
}
}
@@ -621,7 +749,17 @@ function highlightSearchResults(searchResults: SearchResult[], highlightedTokens
}
if (result.highlightedContentSnippet) {
// Replace highlighting markers with HTML tags
result.highlightedContentSnippet = result.highlightedContentSnippet.replace(/{/g, "<b>").replace(/}/g, "</b>");
// Convert newlines to <br> tags for HTML display
result.highlightedContentSnippet = result.highlightedContentSnippet.replace(/\n/g, "<br>");
}
if (result.highlightedAttributeSnippet) {
// Replace highlighting markers with HTML tags
result.highlightedAttributeSnippet = result.highlightedAttributeSnippet.replace(/{/g, "<b>").replace(/}/g, "</b>");
// Convert newlines to <br> tags for HTML display
result.highlightedAttributeSnippet = result.highlightedAttributeSnippet.replace(/\n/g, "<br>");
}
}
}