Repository: rmagatti/auto-session (lua)

Issue:
[FEATURE] Purge/delete sessions with no open buffers
**Is your feature request related to a problem? Please describe.**

Sometimes after I'm done I end up closing all buffers but forget to session delete and I quit nvim. Some time later when I do session list I see more sessions than expected and a lot of them are empty with no open buffers.

**Describe the solution you'd like**

Delete the session automatically during auto save if there are no open buffers.

**Describe alternatives you've considered**

A custom function `SessionPurgeEmpty` which finds and deletes any empty sessions. Could possibly be hooked up to nvim exit or session save.

Pull request:
If there are only unnamed / empty listed buffers, delete the current session on
exit.

Listed as a breaking change because it's enabled by default (though the
change seems very minor)

Fixes: #426

Patch:
diff --git a/doc/auto-session.txt b/doc/auto-session.txt
index 30dc5848..9b38cff4 100644
--- a/doc/auto-session.txt
+++ b/doc/auto-session.txt
@@ -16,6 +16,7 @@ AutoSession.Config                                          *AutoSession.Config*
         {auto_save?}                    (boolean)           Enables/disables auto saving session on exit
         {auto_restore?}                 (boolean)           Enables/disables auto restoring session on start
         {auto_create?}                  (boolean|function)  Enables/disables auto creating new session files. Can take a function that should return true/false if a new session file should be created or not
+        {auto_delete_empty_sessions?}   (boolean)           Enables/disables deleting the session if there no named, non-empty buffers when auto-saving
         {suppressed_dirs?}              (table)             Suppress auto session for directories
         {allowed_dirs?}                 (table)             Allow auto session for directories, if empty then all directories are allowed except for suppressed ones
         {auto_restore_last_session?}    (boolean)           On startup, loads the last saved session if session for cwd does not exist
diff --git a/lua/auto-session/autocmds.lua b/lua/auto-session/autocmds.lua
index 54787d10..e8494333 100644
--- a/lua/auto-session/autocmds.lua
+++ b/lua/auto-session/autocmds.lua
@@ -112,7 +112,6 @@ local function setup_session_lens()
   local has_telescope, telescope = pcall(require, "telescope")
 
   if not has_telescope then
-    Lib.logger.info "Telescope.nvim is not installed. Session Lens cannot be setup!"
     return false
   end
 
diff --git a/lua/auto-session/config.lua b/lua/auto-session/config.lua
index ee990a4b..92ee91ea 100644
--- a/lua/auto-session/config.lua
+++ b/lua/auto-session/config.lua
@@ -12,6 +12,7 @@ local M = {}
 ---@field auto_save? boolean Enables/disables auto saving session on exit
 ---@field auto_restore? boolean Enables/disables auto restoring session on start
 ---@field auto_create? boolean|function Enables/disables auto creating new session files. Can take a function that should return true/false if a new session file should be created or not
+---@field auto_delete_empty_sessions? boolean Enables/disables deleting the session if there no named, non-empty buffers when auto-saving
 ---@field suppressed_dirs? table Suppress auto session for directories
 ---@field allowed_dirs? table Allow auto session for directories, if empty then all directories are allowed except for suppressed ones
 ---@field auto_restore_last_session? boolean On startup, loads the last saved session if session for cwd does not exist
@@ -74,6 +75,7 @@ local defaults = {
   auto_save = true, -- Enables/disables auto saving session on exit
   auto_restore = true, -- Enables/disables auto restoring session on start
   auto_create = true, -- Enables/disables auto creating new session files. Can take a function that should return true/false if a new session file should be created or not
+  auto_delete_empty_sessions = true, -- Enables/disables deleting the session if there no named, non-empty buffers when auto-saving
   suppressed_dirs = nil, -- Suppress session restore/create in certain directories
   allowed_dirs = nil, -- Allow session restore/create in certain directories
   auto_restore_last_session = false, -- On startup, loads the last saved session if session for cwd does not exist
diff --git a/lua/auto-session/init.lua b/lua/auto-session/init.lua
index f1155d24..03214ad8 100644
--- a/lua/auto-session/init.lua
+++ b/lua/auto-session/init.lua
@@ -286,6 +286,11 @@ function AutoSession.AutoSaveSession()
     end
   end
 
+  if Config.auto_delete_empty_sessions and Lib.only_blank_buffers_left() then
+    AutoSession.DeleteSession(current_session)
+    return false
+  end
+
   if Config.close_unsupported_windows then
     -- Wrap in pcall in case there's an error while trying to close windows
     local success, result = pcall(Lib.close_unsupported_windows)
diff --git a/lua/auto-session/lib.lua b/lua/auto-session/lib.lua
index 544a92c5..3d7765c7 100644
--- a/lua/auto-session/lib.lua
+++ b/lua/auto-session/lib.lua
@@ -792,4 +792,26 @@ function Lib.purge_old_sessions(session_dir, purge_older_than_minutes)
   return vim.json.encode(out)
 end
 
+---Checks to see if there are only empty/unnamed buffers left
+---@return boolean # True if there are only empty/unnamed buffers left
+function Lib.only_blank_buffers_left()
+  local bufs = vim.api.nvim_list_bufs()
+  for _, bufnr in ipairs(bufs) do
+    -- Only consider listed buffers
+    if vim.fn.buflisted(bufnr) == 1 then
+      local lines = vim.api.nvim_buf_get_lines(bufnr, 0, -1, false)
+      local is_empty = #lines <= 1 and (lines[1] == nil or lines[1] == "")
+      -- Use deprecated version for 0.7 support
+      local is_modified = vim.api.nvim_buf_get_option(bufnr, "modified")
+      local has_name = vim.api.nvim_buf_get_name(bufnr) ~= ""
+
+      -- If buffer has a name, is modified, or has content, it's meaningful
+      if has_name or is_modified or not is_empty then
+        return false
+      end
+    end
+  end
+  return true
+end
+
 return Lib


Test patch:
diff --git a/tests/cmds_spec.lua b/tests/cmds_spec.lua
index 4f192f3f..2382e25c 100644
--- a/tests/cmds_spec.lua
+++ b/tests/cmds_spec.lua
@@ -104,7 +104,7 @@ describe("The default config", function()
     assert.True(vim.tbl_contains(sessions, TL.default_session_name))
     assert.True(vim.tbl_contains(sessions, TL.named_session_name))
 
-    print(vim.inspect(sessions))
+    -- print(vim.inspect(sessions))
     -- With my prefix, only named session should be present
     sessions = Lib.complete_session_for_dir(TL.session_dir, "my")
     assert.False(vim.tbl_contains(sessions, TL.default_session_name))
@@ -187,10 +187,31 @@ describe("The default config", function()
     as.DisableAutoSave()
 
     vim.cmd "SessionPurgeOrphaned"
-    print(TL.default_session_path)
+    -- print(TL.default_session_path)
 
     assert.equals(1, vim.fn.filereadable(TL.default_session_path))
     assert.equals(1, vim.fn.filereadable(TL.named_session_path))
     assert.equals(0, vim.fn.filereadable(TL.makeSessionPath(session_name)))
   end)
+
+  -- test that closes all buffers, calls autosave, checks to see if file is deleted
+  it("can auto-delete empty session on auto-save", function()
+    -- make sure auto-save is on (previous test disables it)
+    c.auto_save = true
+
+    -- make sure default session exists
+    assert.equals(1, vim.fn.bufexists(TL.test_file))
+    assert.True(as.SaveSession())
+
+    -- clear buffers so only an empty,unnamed buffer is left
+    vim.cmd "silent %bw"
+
+    -- Make sure session exists
+    assert.equals(1, vim.fn.filereadable(TL.default_session_path))
+
+    assert.False(as.AutoSaveSession())
+
+    -- Make sure session is now gone
+    assert.equals(0, vim.fn.filereadable(TL.default_session_path))
+  end)
 end)