mirror of
https://github.com/logseq/logseq.git
synced 2026-02-01 22:47:36 +00:00
Added
1. All configurations of current graph.
App.getCurrentGraphConfigs: () => Promise<any>
2. All favorite pages list of current graph.
App.getCurrentGraphFavorites: () => Promise<Array<string> | null>
3. All recent pages list of current graph.
App.getCurrentGraphRecent: () => Promise<Array<string> | null>
4. Clear right sidebar blocks.
App.clearRightSidebarBlocks: (opts?: { close: boolean }) => void
5. Support register CodeMirror enhancer. #Experiment feature
Experiments.registerExtensionsEnhancer<T = any>(type: 'katex' | 'codemirror', enhancer: (v: T) => Promise<any>)
6. Support hooks for app search service. #Alpha stage
App.registerSearchService<T extends IPluginSearchServiceHooks>(s: T): void
7. Support focus option for App.insertBlock. Credit to [[tennox]] #PR
Fixed
1. Adjust build script to be compatible for shadow-cljs bundler.
How to set up a clojurescript project with shadow-cljs?
https://github.com/rlhk/logseq-url-plus/blob/main/doc/dev-notes.md
82 lines
2.3 KiB
TypeScript
82 lines
2.3 KiB
TypeScript
import { IPluginSearchServiceHooks } from '../LSPlugin'
|
|
import { LSPluginUser } from '../LSPlugin.user'
|
|
import { isArray, isFunction, mapKeys } from 'lodash-es'
|
|
|
|
export class LSPluginSearchService {
|
|
|
|
/**
|
|
* @param ctx
|
|
* @param serviceHooks
|
|
*/
|
|
constructor(
|
|
private ctx: LSPluginUser,
|
|
private serviceHooks: IPluginSearchServiceHooks
|
|
) {
|
|
ctx._execCallableAPI(
|
|
'register-search-service',
|
|
ctx.baseInfo.id,
|
|
serviceHooks.name,
|
|
serviceHooks.options
|
|
)
|
|
|
|
// hook events TODO: remove listeners
|
|
const wrapHookEvent = (k) => `service:search:${k}:${serviceHooks.name}`
|
|
|
|
Object.entries(
|
|
{
|
|
query: {
|
|
f: 'onQuery', args: ['graph', 'q', true], reply: true,
|
|
transformOutput: (data: any) => {
|
|
// TODO: transform keys?
|
|
if (isArray(data?.blocks)) {
|
|
data.blocks = data.blocks.map(it => {
|
|
return it && mapKeys(it, (_, k) => `block/${k}`)
|
|
})
|
|
}
|
|
|
|
return data
|
|
}
|
|
},
|
|
rebuildBlocksIndice: { f: 'onIndiceInit', args: ['graph', 'blocks'] },
|
|
transactBlocks: { f: 'onBlocksChanged', args: ['graph', 'data'] },
|
|
truncateBlocks: { f: 'onIndiceReset', args: ['graph'] },
|
|
removeDb: { f: 'onGraph', args: ['graph'] }
|
|
}
|
|
).forEach(
|
|
([k, v]) => {
|
|
const hookEvent = wrapHookEvent(k)
|
|
ctx.caller.on(hookEvent, async (payload: any) => {
|
|
if (isFunction(serviceHooks?.[v.f])) {
|
|
let ret = null
|
|
|
|
try {
|
|
ret = await serviceHooks[v.f].apply(
|
|
serviceHooks, (v.args || []).map((prop: any) => {
|
|
if (!payload) return
|
|
if (prop === true) return payload
|
|
if (payload.hasOwnProperty(prop)) {
|
|
const ret = payload[prop]
|
|
delete payload[prop]
|
|
return ret
|
|
}
|
|
})
|
|
)
|
|
|
|
if (v.transformOutput) {
|
|
ret = v.transformOutput(ret)
|
|
}
|
|
} catch (e) {
|
|
console.error('[SearchService] ', e)
|
|
ret = e
|
|
} finally {
|
|
if (v.reply) {
|
|
ctx.caller.call(
|
|
`${hookEvent}:reply`, ret
|
|
)
|
|
}
|
|
}
|
|
}
|
|
})
|
|
})
|
|
}
|
|
} |