diff --git a/src/interface/obsidian/src/main.ts b/src/interface/obsidian/src/main.ts index 1adc1eff..f5992061 100644 --- a/src/interface/obsidian/src/main.ts +++ b/src/interface/obsidian/src/main.ts @@ -24,7 +24,7 @@ export default class Khoj extends Plugin { // Add similar notes command. It can only be triggered from the editor this.addCommand({ id: 'similar', - name: 'Find Similar Notes', + name: 'Find similar notes', editorCheckCallback: (checking) => { if (!checking && this.settings.connectedToBackend) new KhojModal(this.app, this.settings, true).open(); @@ -49,11 +49,11 @@ export default class Khoj extends Plugin { this.settings = Object.assign({}, DEFAULT_SETTINGS, await this.loadData()); // Load, configure khoj server settings - await configureKhojBackend(this.settings); + await configureKhojBackend(this.app.vault, this.settings); } async saveSettings() { - await configureKhojBackend(this.settings, false) + await configureKhojBackend(this.app.vault, this.settings, false) .then(() => this.saveData(this.settings)); } } diff --git a/src/interface/obsidian/src/modal.ts b/src/interface/obsidian/src/modal.ts index d44da44a..0e46c047 100644 --- a/src/interface/obsidian/src/modal.ts +++ b/src/interface/obsidian/src/modal.ts @@ -10,9 +10,11 @@ export class KhojModal extends SuggestModal { setting: KhojSetting; rerank: boolean = false; find_similar_notes: boolean; + app: App; constructor(app: App, setting: KhojSetting, find_similar_notes: boolean = false) { super(app); + this.app = app; this.setting = setting; this.find_similar_notes = find_similar_notes; @@ -61,8 +63,9 @@ export class KhojModal extends SuggestModal { if (file && file.extension === 'md') { // Enable rerank of search results this.rerank = true - // Set contents of active markdown file to input element - this.inputEl.value = await this.app.vault.read(file); + // Set input element to contents of active markdown file + // truncate to first 8,000 characters to avoid hitting query size limits + this.inputEl.value = await this.app.vault.read(file).then(file_str => file_str.slice(0, 8000)); // Trigger search to get and render similar notes from khoj backend this.inputEl.dispatchEvent(new Event('input')); this.rerank = false @@ -76,12 +79,12 @@ export class KhojModal extends SuggestModal { async getSuggestions(query: string): Promise { // Query Khoj backend for search results let encodedQuery = encodeURIComponent(query); - let searchUrl = `${this.setting.khojUrl}/api/search?q=${encodedQuery}&n=${this.setting.resultsCount}&r=${this.rerank}&t=markdown` - let results = await request(searchUrl) - .then(response => JSON.parse(response)) - .then(data => data - .filter((result: any) => !this.find_similar_notes || !result.additional.file.endsWith(this.app.workspace.getActiveFile()?.path)) - .map((result: any) => { return { entry: result.entry, file: result.additional.file } as SearchResult; })); + let searchUrl = `${this.setting.khojUrl}/api/search?q=${encodedQuery}&n=${this.setting.resultsCount}&r=${this.rerank}&t=markdown`; + let response = await request(searchUrl); + let data = JSON.parse(response); + let results = data + .filter((result: any) => !this.find_similar_notes || !result.additional.file.endsWith(this.app.workspace.getActiveFile()?.path)) + .map((result: any) => { return { entry: result.entry, file: result.additional.file } as SearchResult; }); return results; } @@ -98,21 +101,21 @@ export class KhojModal extends SuggestModal { // Get all markdown files in vault const mdFiles = this.app.vault.getMarkdownFiles(); - // Find the vault file matching file of result. Open file at result heading - mdFiles + // Find the vault file matching file of chosen search result + let file_match = mdFiles // Sort by descending length of path // This finds longest path match when multiple files have same name .sort((a, b) => b.path.length - a.path.length) - .forEach((file) => { - // Find best file match across operating systems - // E.g Khoj Server on Linux, Obsidian Vault on Android - if (result.file.endsWith(file.path)) { - let resultHeading = result.entry.split('\n', 1)[0]; - let linkToEntry = `${file.path}${resultHeading}` - this.app.workspace.openLinkText(linkToEntry, ''); - console.log(`Link: ${linkToEntry}, File: ${file.path}, Heading: ${resultHeading}`); - return - } - }); + // The first match is the best file match across OS + // e.g Khoj server on Linux, Obsidian vault on Android + .find(file => result.file.endsWith(file.path)) + + // Open vault file at heading of chosen search result + if (file_match){ + let resultHeading = result.entry.split('\n', 1)[0]; + let linkToEntry = `${file_match.path}${resultHeading}` + this.app.workspace.openLinkText(linkToEntry, ''); + console.log(`Link: ${linkToEntry}, File: ${file_match.path}, Heading: ${resultHeading}`); + } } } diff --git a/src/interface/obsidian/src/settings.ts b/src/interface/obsidian/src/settings.ts index edfbb123..ce4f50f4 100644 --- a/src/interface/obsidian/src/settings.ts +++ b/src/interface/obsidian/src/settings.ts @@ -36,8 +36,8 @@ export class KhojSettingTab extends PluginSettingTab { .setValue(`${this.plugin.settings.khojUrl}`) .onChange(async (value) => { this.plugin.settings.khojUrl = value.trim(); - await this.plugin.saveSettings() - .finally(() => containerEl.firstElementChild?.setText(this.getBackendStatusMessage())); + await this.plugin.saveSettings(); + containerEl.firstElementChild?.setText(this.getBackendStatusMessage()); })); new Setting(containerEl) .setName('Results Count') @@ -60,15 +60,15 @@ export class KhojSettingTab extends PluginSettingTab { .onClick(async () => { // Disable button while updating index button.setButtonText('Updating...'); - button.removeCta() + button.removeCta(); indexVaultSetting = indexVaultSetting.setDisabled(true); - await request(`${this.plugin.settings.khojUrl}/api/update?t=markdown&force=true`) - .then(() => new Notice('✅ Updated Khoj index.')); + await request(`${this.plugin.settings.khojUrl}/api/update?t=markdown&force=true`); + new Notice('✅ Updated Khoj index.'); // Re-enable button once index is updated button.setButtonText('Update'); - button.setCta() + button.setCta(); indexVaultSetting = indexVaultSetting.setDisabled(false); }) ); diff --git a/src/interface/obsidian/src/utils.ts b/src/interface/obsidian/src/utils.ts index bc3ec598..b8142f6d 100644 --- a/src/interface/obsidian/src/utils.ts +++ b/src/interface/obsidian/src/utils.ts @@ -1,16 +1,16 @@ -import { FileSystemAdapter, Notice, RequestUrlParam, request } from 'obsidian'; +import { FileSystemAdapter, Notice, RequestUrlParam, request, Vault } from 'obsidian'; import { KhojSetting } from 'src/settings' -export function getVaultAbsolutePath(): string { - let adaptor = this.app.vault.adapter; +export function getVaultAbsolutePath(vault: Vault): string { + let adaptor = vault.adapter; if (adaptor instanceof FileSystemAdapter) { return adaptor.getBasePath(); } return ''; } -export async function configureKhojBackend(setting: KhojSetting, notify: boolean = true) { - let mdInVault = `${getVaultAbsolutePath()}/**/*.md`; +export async function configureKhojBackend(vault: Vault, setting: KhojSetting, notify: boolean = true) { + let mdInVault = `${getVaultAbsolutePath(vault)}/**/*.md`; let khojConfigUrl = `${setting.khojUrl}/api/config/data`; // Check if khoj backend is configured, note if cannot connect to backend @@ -28,7 +28,7 @@ export async function configureKhojBackend(setting: KhojSetting, notify: boolean if (!setting.connectedToBackend) return; // Set index name from the path of the current vault - let indexName = getVaultAbsolutePath().replace(/\//g, '_').replace(/ /g, '_'); + let indexName = getVaultAbsolutePath(vault).replace(/\//g, '_').replace(/ /g, '_'); // Get default index directory from khoj backend let khojDefaultIndexDirectory = await request(`${khojConfigUrl}/default`) .then(response => JSON.parse(response))