@@ -4,7 +4,7 @@ import { input } from "jsr:@denops/std@^7.0.0/helper/input";
44import { dirname } from "jsr:@std/path@^1.0.0/dirname" ;
55
66import type { IdItem } from "../../item.ts" ;
7- import type { Action , InvokeParams } from "../../action.ts" ;
7+ import { type Action , defineAction } from "../../action.ts" ;
88
99type Restriction = "file" | "directory" | "directory-or-parent" | "buffer" ;
1010
@@ -17,51 +17,39 @@ type Options<T> = {
1717 shellescape ?: boolean ;
1818} ;
1919
20- export class CmdAction < T > implements Action < T > {
21- #attrGetter: ( item : IdItem < T > ) => string | undefined ;
22- #immediate: boolean ;
23- #template: string ;
24- #restriction?: "file" | "directory" | "directory-or-parent" | "buffer" ;
25- #fnameescape: boolean ;
26- #shellescape: boolean ;
27-
28- constructor ( options : Options < T > = { } ) {
29- this . #attrGetter = options . attrGetter ?? ( ( item ) => item . value ) ;
30- this . #immediate = options . immediate ?? false ;
31- this . #template = options . template ?? "{}" ;
32- this . #restriction = options . restriction ;
33- this . #fnameescape = options . fnameescape ?? false ;
34- this . #shellescape = options . shellescape ?? false ;
35- }
36-
37- async invoke (
38- denops : Denops ,
39- { item, selectedItems } : InvokeParams < T > ,
40- { signal } : { signal ?: AbortSignal } ,
41- ) : Promise < void > {
42- const items = selectedItems ?? [ item ] ;
43- for ( const item of items . filter ( ( v ) => ! ! v ) ) {
44- signal ?. throwIfAborted ( ) ;
45- let value = this . #attrGetter( item ) ;
46- if ( value == undefined ) continue ;
47- if ( this . #restriction) {
48- value = await applyRestriction ( denops , value , this . #restriction) ;
20+ export function cmd < T > ( options : Options < T > = { } ) : Action < T > {
21+ const attrGetter = options . attrGetter ?? ( ( item ) => item . value ) ;
22+ const immediate = options . immediate ?? false ;
23+ const template = options . template ?? "{}" ;
24+ const restriction = options . restriction ;
25+ const fnameescape = options . fnameescape ?? false ;
26+ const shellescape = options . shellescape ?? false ;
27+ return defineAction < T > (
28+ async ( denops , { item, selectedItems } , { signal } ) => {
29+ const items = selectedItems ?? [ item ] ;
30+ for ( const item of items . filter ( ( v ) => ! ! v ) ) {
31+ signal ?. throwIfAborted ( ) ;
32+ let value = attrGetter ( item ) ;
4933 if ( value == undefined ) continue ;
34+ if ( restriction ) {
35+ value = await applyRestriction ( denops , value , restriction ) ;
36+ if ( value == undefined ) continue ;
37+ }
38+ if ( fnameescape ) {
39+ value = await fn . fnameescape ( denops , value ) ;
40+ }
41+ if ( shellescape ) {
42+ value = await fn . shellescape ( denops , value ) ;
43+ }
44+ const cmd = template . replaceAll ( "{}" , value ) ;
45+ try {
46+ await execute ( denops , cmd , immediate ) ;
47+ } catch ( err ) {
48+ console . warn ( `[fall] Failed to execute '${ cmd } ':` , err ) ;
49+ }
5050 }
51- if ( this . #fnameescape) {
52- value = await fn . fnameescape ( denops , value ) ;
53- }
54- if ( this . #shellescape) {
55- value = await fn . shellescape ( denops , value ) ;
56- }
57- const cmd = this . #template. replaceAll ( "{}" , value ) ;
58- try {
59- await execute ( denops , cmd , this . #immediate) ;
60- } catch ( err ) {
61- console . warn ( `[fall] Failed to execute '${ cmd } ':` , err ) ;
62- }
63- }
64- }
51+ } ,
52+ ) ;
6553}
6654
6755async function applyRestriction (
@@ -125,84 +113,8 @@ async function execute(
125113 await denops . cmd ( command ) ;
126114}
127115
128- export const cdAction : { cd : CmdAction < unknown > } = {
129- cd : new CmdAction ( {
130- immediate : true ,
131- template : "cd {}" ,
132- restriction : "directory-or-parent" ,
133- fnameescape : true ,
134- } ) ,
135- } ;
136-
137- export const lcdAction : { lcd : CmdAction < unknown > } = {
138- lcd : new CmdAction ( {
139- immediate : true ,
140- template : "lcd {}" ,
141- restriction : "directory-or-parent" ,
142- fnameescape : true ,
143- } ) ,
144- } ;
145-
146- export const tcdAction : { tcd : CmdAction < unknown > } = {
147- tcd : new CmdAction ( {
148- immediate : true ,
149- template : "tcd {}" ,
150- restriction : "directory-or-parent" ,
151- fnameescape : true ,
152- } ) ,
153- } ;
154-
155- export const cdActions = {
156- ...cdAction ,
157- ...lcdAction ,
158- ...tcdAction ,
159- } ;
160-
161- export const bunloadAction : { bunload : CmdAction < unknown > } = {
162- bunload : new CmdAction ( {
163- immediate : true ,
164- template : "bunload {}" ,
165- restriction : "buffer" ,
166- fnameescape : true ,
167- } ) ,
168- } ;
169-
170- export const bdeleteAction : { bdelete : CmdAction < unknown > } = {
171- bdelete : new CmdAction ( {
172- immediate : true ,
173- template : "bdelete {}" ,
174- restriction : "buffer" ,
175- fnameescape : true ,
176- } ) ,
177- } ;
178-
179- export const bwipeoutAction : { bwipeout : CmdAction < unknown > } = {
180- bwipeout : new CmdAction ( {
181- immediate : true ,
182- template : "bdelete {}" ,
183- restriction : "buffer" ,
184- fnameescape : true ,
185- } ) ,
186- } ;
187-
188- export const bufferActions = {
189- ...bunloadAction ,
190- ...bdeleteAction ,
191- ...bwipeoutAction ,
192- } ;
193-
194- export const helpAction : { help : CmdAction < unknown > } = {
195- help : new CmdAction ( {
196- immediate : true ,
197- template : "help {}" ,
198- } ) ,
199- } ;
200-
201- export const writeAction : { write : CmdAction < unknown > } = {
202- write : new CmdAction ( {
203- immediate : true ,
204- template : "tabedit {} | write | tabclose" ,
205- restriction : "buffer" ,
206- fnameescape : true ,
207- } ) ,
116+ export const defaultCmdActions : {
117+ cmd : Action < unknown > ;
118+ } = {
119+ cmd : cmd ( ) ,
208120} ;
0 commit comments