mirror of
https://github.com/logseq/logseq.git
synced 2026-05-24 20:54:09 +00:00
* refactor(shortcuts): simplify to build handler category map * fix(shortcuts): redundant re-mount for the pdf shortcuts * refactor(shortcuts): simplify names * refactor(shortcuts): simplify user keynames * fix(shortcuts): persist inited state for dev mode * refactor(shortcuts): simplify handlers installation * refactor(shortcuts): optimize shortcuts mixin * fix: incorrect function ref * refactor(shortcuts): shortcuts mixin * fix(shortcuts): incorrect initialization for the pdf shortcut handler * refactor(shortcuts): optimize binding keys map * refactor(shortcuts): optimize shortcuts conflicts detection * refactor(shortcuts): optimize binding ids map * refactor(shortcuts): WIP the new keymap page * refactor(shortcuts): WIP the new keymap related components * feat(shortcuts): WIP fuzzy search for the shortcuts * refactor(shortcuts): WIP the new keymap related components * feat(shortcuts): WIP the new shorcuts record component * feat(shortcuts): WIP the new shorcuts record component * feat(shortcuts): WIP check shortcut conflicts component * feat(shortcuts): WIP the new shorcuts record component * refactor(shortcuts): WIP persist user shortcuts * fix(shortcuts): detection for the conflicts * feat(shortcuts): WIP detection for the conflicts * feat(shortcuts): WIP persist user shortcuts * refactor(shortcuts): add unit tests * enhance(ux): search pane for the shortcuts * feat(shortcuts): remove the existent shortcut item * feat(shortcuts): fold/unfold categories * feat(shortcuts): add shortcuts filters * enhance(shortcuts): resove binding map description * enhance(shortcuts): reactive category shortcuts * enhance(shortcuts): register api for plugins * feat(shortcuts): add keyboard shortcuts filters * feat(shortcuts): impl keyboard shortcuts filters * enhance(shortcuts): leader keys for the shortcut conflicts detection * enhance(tests): leader keys conflicts for the shortucts * enhance(shortcuts): parse conflicts from current binding list * enhance(ui): polish the component of the restore shortcut action * enhance(shortcuts): get conflicts with specific handler id * enhance(shortcuts): polish the confilts component * enhance(shortcuts): polish keymap conflicts component * enhance(shortcuts): ux for handling shorcuts conflicts * enhance(ui): polish notifications cp * fix(shortcuts): remove reduplicate shortcuts for category * enhance(shortcuts): polish ux for handling shorcuts conflicts * chore(plugin): build libs core * enhance(plugin): support shortcut command lifecycle hooks * enhance(plugin): support shortcut command lifecycle hooks * chore(plugin): build libs core * enhance(shortcuts): support shortcuts saved to global config * enhance(shortcuts): support shortcuts be saved to global config * feat(shortcuts): support keymap manager to global settings * enhance(shortcuts): shortcut to open keymap settings * fix(units): tests * fix: lints * enhance(shortcuts): unlisten all shortcuts * fix: lints * fix: lints * fix(units): tests * fix(units): tests * fix(units): tests * enhance(shortcuts): unlisten/listen all shortcuts * enhance(shortcuts): polish conflicts component * fix(ui): modal size * fix(ui): modal panel container * enhance(shortcuts): i18n * enhance(ui): layout of the shortcuts recorder component * fix(lint): i18n * enhance(ui): keyboard icon for the keymap settings tab * fix(shortcuts): incorrect filters for the collaspsed shortcuts * enhance(ui): polish details for the keymap settings * enhance(ui): polish details for the keymap settings * fix(shortcuts): get shortcut description error when the associated handler-id not exist * fix(ui): the shortcut disabled label overlaps with section headers. * refactor(shortcuts): names * enhance(ui): filter icons
144 lines
3.1 KiB
TypeScript
144 lines
3.1 KiB
TypeScript
import { LSPluginUser, WithOptional } from '../LSPlugin.user'
|
|
import { EventEmitter } from 'eventemitter3'
|
|
|
|
export type IRequestOptions<R = any> = {
|
|
url: string
|
|
abortable: boolean
|
|
headers: Record<string, string>
|
|
method: 'GET' | 'POST' | 'PUT' | 'PATCH' | 'DELETE'
|
|
data: Object | ArrayBuffer
|
|
timeout: number
|
|
returnType: 'json' | 'text' | 'base64' | 'arraybuffer'
|
|
success: (result: R) => void
|
|
fail: (err: any) => void
|
|
final: () => void
|
|
}
|
|
|
|
export type RequestTaskID = string | number
|
|
|
|
const CLIENT_MSG_CALLBACK = '#lsp#request#callback'
|
|
const genTaskCallbackType = (id: RequestTaskID) => `task_callback_${id}`
|
|
|
|
/**
|
|
* Request task
|
|
*/
|
|
export class LSPluginRequestTask<R = any> {
|
|
private readonly _promise: Promise<R>
|
|
private _aborted: boolean = false
|
|
|
|
constructor(
|
|
private _client: LSPluginRequest,
|
|
private _requestId: RequestTaskID,
|
|
private _requestOptions: Partial<IRequestOptions> = {}
|
|
) {
|
|
this._promise = new Promise<any>((resolve, reject) => {
|
|
if (!this._requestId) {
|
|
return reject(null)
|
|
}
|
|
|
|
// task result listener
|
|
this._client.once(genTaskCallbackType(this._requestId), (e) => {
|
|
if (e && e instanceof Error) {
|
|
reject(e)
|
|
} else {
|
|
resolve(e)
|
|
}
|
|
})
|
|
})
|
|
|
|
const { success, fail, final } = this._requestOptions
|
|
|
|
this._promise
|
|
.then((res) => {
|
|
success?.(res)
|
|
})
|
|
.catch((e) => {
|
|
fail?.(e)
|
|
})
|
|
.finally(() => {
|
|
final?.()
|
|
})
|
|
}
|
|
|
|
abort() {
|
|
if (!this._requestOptions.abortable || this._aborted) return
|
|
|
|
this._client.ctx._execCallableAPI('http_request_abort', this._requestId)
|
|
|
|
this._aborted = true
|
|
}
|
|
|
|
get promise(): Promise<R> {
|
|
return this._promise
|
|
}
|
|
|
|
get client(): LSPluginRequest {
|
|
return this._client
|
|
}
|
|
|
|
get requestId(): RequestTaskID {
|
|
return this._requestId
|
|
}
|
|
}
|
|
|
|
/**
|
|
* A simple request client
|
|
*/
|
|
export class LSPluginRequest extends EventEmitter {
|
|
constructor(private _ctx: LSPluginUser) {
|
|
super()
|
|
|
|
// request callback listener
|
|
this.ctx.caller.on(CLIENT_MSG_CALLBACK, (e: any) => {
|
|
const reqId = e?.requestId
|
|
if (!reqId) return
|
|
|
|
this.emit(genTaskCallbackType(reqId), e?.payload)
|
|
})
|
|
}
|
|
|
|
static createRequestTask(
|
|
client: LSPluginRequest,
|
|
requestID: RequestTaskID,
|
|
requestOptions: Partial<IRequestOptions>
|
|
) {
|
|
return new LSPluginRequestTask(client, requestID, requestOptions)
|
|
}
|
|
|
|
async _request<
|
|
R extends {},
|
|
T extends WithOptional<
|
|
IRequestOptions<R>,
|
|
keyof Omit<IRequestOptions, 'url'>
|
|
>
|
|
>(
|
|
options: T
|
|
): Promise<
|
|
T extends Pick<IRequestOptions, 'abortable'> ? LSPluginRequestTask<R> : R
|
|
> {
|
|
const pid = this.ctx.baseInfo.id
|
|
const { success, fail, final, ...requestOptions } = options
|
|
const reqID = this.ctx.Experiments.invokeExperMethod(
|
|
'request',
|
|
pid,
|
|
requestOptions
|
|
)
|
|
|
|
const task = LSPluginRequest.createRequestTask(
|
|
this.ctx.Request,
|
|
reqID,
|
|
options
|
|
)
|
|
|
|
if (!requestOptions.abortable) {
|
|
return task.promise
|
|
}
|
|
|
|
return task as any
|
|
}
|
|
|
|
get ctx(): LSPluginUser {
|
|
return this._ctx
|
|
}
|
|
}
|