@@ -304,6 +304,88 @@ export const backupCellExecutorPlugin: JupyterFrontEndPlugin<INotebookCellExecut
304304 }
305305 } ;
306306
307+ /**
308+ * The command IDs for docmanager save operations to disable
309+ */
310+ const SAVE_COMMANDS = {
311+ save : 'docmanager:save' ,
312+ saveAs : 'docmanager:save-as' ,
313+ saveAll : 'docmanager:save-all' ,
314+ toggleAutosave : 'docmanager:toggle-autosave'
315+ } as const ;
316+
317+ /**
318+ * Plugin to disable save commands
319+ */
320+ const disableSavePlugin : JupyterFrontEndPlugin < void > = {
321+ id : 'disable-save:plugin' ,
322+ description : 'Disables save commands and removes their keyboard shortcuts since documents are autosaved' ,
323+ autoStart : true ,
324+ activate : ( app : JupyterFrontEnd ) : void => {
325+
326+ /**
327+ * Override save commands and remove keyboard shortcuts after app is fully loaded
328+ */
329+ app . restored . then ( ( ) => {
330+
331+ // Helper function to remove existing command and add new one
332+ const overrideCommand = ( commandId : string , options : any ) => {
333+ if ( app . commands . hasCommand ( commandId ) ) {
334+ // Remove existing command using private API
335+ const commandRegistry = app . commands as any ;
336+ if ( commandRegistry . _commands && commandRegistry . _commands . delete ) {
337+ commandRegistry . _commands . delete ( commandId ) ;
338+ }
339+ app . commands . addCommand ( commandId , options ) ;
340+ }
341+ } ;
342+
343+ // Override main save command (Ctrl/Cmd+S)
344+ overrideCommand ( SAVE_COMMANDS . save , {
345+ label : 'Save (Autosaving)' ,
346+ caption : 'Save operations are disabled - documents are autosaved' ,
347+ isEnabled : ( ) => true ,
348+ execute : ( ) => {
349+ return Promise . resolve ( ) ;
350+ }
351+ } ) ;
352+
353+ // Override save-as command (Ctrl/Cmd+Shift+S)
354+ overrideCommand ( SAVE_COMMANDS . saveAs , {
355+ label : 'Save As… (Autosaving)' ,
356+ caption : 'Save operations are disabled - documents are autosaved' ,
357+ isEnabled : ( ) => true ,
358+ execute : ( ) => {
359+ return Promise . resolve ( ) ;
360+ }
361+ } ) ;
362+
363+ // Override save-all command
364+ overrideCommand ( SAVE_COMMANDS . saveAll , {
365+ label : 'Save All (Autosaving)' ,
366+ caption : 'Save operations are disabled - documents are autosaved' ,
367+ isEnabled : ( ) => true ,
368+ execute : ( ) => {
369+ return Promise . resolve ( ) ;
370+ }
371+ } ) ;
372+
373+ // Override toggle autosave command
374+ overrideCommand ( SAVE_COMMANDS . toggleAutosave , {
375+ label : 'Autosave Documents (Autosaving)' ,
376+ caption : 'Autosave toggle is disabled - documents are always autosaved' ,
377+ isEnabled : ( ) => true ,
378+ isToggled : ( ) => true ,
379+ execute : ( ) => {
380+ return Promise . resolve ( ) ;
381+ }
382+ } ) ;
383+
384+ console . log ( 'Full autosave enabled, save commands disabled' ) ;
385+ } ) ;
386+ }
387+ } ;
388+
307389const plugins : JupyterFrontEndPlugin < unknown > [ ] = [
308390 rtcContentProvider ,
309391 yfile ,
@@ -315,7 +397,8 @@ const plugins: JupyterFrontEndPlugin<unknown>[] = [
315397 kernelStatus ,
316398 notebookFactoryPlugin ,
317399 codemirrorYjsPlugin ,
318- backupCellExecutorPlugin
400+ backupCellExecutorPlugin ,
401+ disableSavePlugin
319402] ;
320403
321404export default plugins ;
0 commit comments