Jogusa
Jogusa

Reputation: 5691

How to save and restore multiple different sessions in Vim?

Depending on my task in Vim I have several tabs open.

How can I save different sessions for later use?

Upvotes: 428

Views: 120452

Answers (14)

oml
oml

Reputation: 175

Thanks mathielo. Following the example from them, I added this line to my .vimrc to save the active session (if any):

au VimLeave * if this_session != "" | exe "mksession! ".this_session

If you want to put more lines, use endif:

au VimLeave * if v:this_session != ""
au VimLeave *   exe "mksession! ".this_session
au VimLeave * endif

You only need to save a new session with:

:mks [Session filename]

Start Vim with:

$ vim -S [Session filename]

Vim will start the session and you don't need to worry about saving the session every time you close it. .vimrc won't do anything if you don't have an active session. As before.

That's what I was looking for! Thanks again mathielo!

Upvotes: 2

PMunch
PMunch

Reputation: 1734

Since this is the first hit on Google for me (and probably others) for how to work with sessions in Vim I've decided to add a little to @mathielo's answer on how to make this automatic.

I like his code, but the addition of the "only if without args" solution seemed to be a bit lacking. This is my modified version:

function! MakeSession(overwrite)
  let b:sessiondir = $HOME . "/.vim/sessions" . getcwd()
  if (filewritable(b:sessiondir) != 2)
    exe 'silent !mkdir -p ' b:sessiondir
    redraw!
  endif
  let b:filename = b:sessiondir . '/session.vim'
  if a:overwrite == 0 && !empty(glob(b:filename))
    return
  endif
  exe "mksession! " . b:filename
endfunction

function! LoadSession()
  let b:sessiondir = $HOME . "/.vim/sessions" . getcwd()
  let b:sessionfile = b:sessiondir . "/session.vim"
  if (filereadable(b:sessionfile))
    exe 'source ' b:sessionfile
  else
    echo "No session loaded."
  endif
endfunction

" Adding automatons for when entering or leaving Vim
if(argc() == 0)
  au VimEnter * nested :call LoadSession()
  au VimLeave * :call MakeSession(1)
else
  au VimLeave * :call MakeSession(0)
endif

The notable change here is the optional override. If you open Vim without options it will open any existing session and overwrite changes made when you leave. If Vim is opened with options it will only create a new session if none exist, this means that you can open single files in a directory that has a session without overwriting it. Then you can open Vim without options to run the session instead. If there doesn't exist a session then it creates a new one.

Upvotes: 12

jaybay
jaybay

Reputation: 31

For managing multiple sessions (on a per directory/repo basis), I've recently switched from the vim-session plugin to vim-workspace. Its session management is relatively simple and works pretty well.

Upvotes: 0

cute_ptr
cute_ptr

Reputation: 1203

If you plan having only 1 session for the project just do

:mks

which will create a Session.vim file in the current directory, and then to open the session (from the same directory):

vim -S

If you change the session and want to save it:

:mks!

This saves the session, not the files themselves!

If you plan having multiple sessions, I prefer to save them in hidden files in the project's directory:

:mks .session-name.vim

To open it (from the same directory):

vim -S .session-name.vim

Save session:

:mks! .session-name.vim

Since the sessions are saved in hidden files, to view them don't forget -a

ls -a

Upvotes: 26

archf
archf

Reputation: 201

Personally i just wrap over Tim Pope' s Obsession plugin to allow defining a sessiondir and avoid typing the path:

let g:sessiondir = $HOME . ".vim/sessions"

command! -nargs=1 MkSession call MkSession(<f-args>)
function! MkSession(sessionfile)
  if !isdirectory(g:sessiondir)
    call mkdir(g:sessiondir, "p")
  endif
  exe 'Obsession' g:sessiondir . '/' . a:sessionfile
endfunction

command! -nargs=1 LoadSession call LoadSession(<f-args>)
function! LoadSession(sessionfile)

  let a:sessionpath = g:sessiondir . a:sessionfile
  if (filereadable(a:sessionpath))
    exe 'source ' a:sessionpath
  else
    echo "No session loaded."
  endif
endfunction

Upvotes: 2

JohnTortugo
JohnTortugo

Reputation: 6625

Below is the only conf. that really worked for me. I took it from here, where you can also take a more complete/complex version.

set viewoptions+=cursor,folds,slash,unix
set viewoptions-=options

augroup vimrc
    autocmd BufWritePost *
    \   if expand('%') != '' && &buftype !~ 'nofile'
    \|      mkview
    \|  endif
    autocmd BufRead *
    \   if expand('%') != '' && &buftype !~ 'nofile'
    \|      silent loadview
    \|  endif
augroup END

Upvotes: 0

Sagar Jain
Sagar Jain

Reputation: 7941

You can store session wherever you want.

Ex:

:mksession! D:/session.ses

This stores the session in D drive.

This can be opened by typing

:so D:/session.ses

in any of the vim files.

Upvotes: 0

mathielo
mathielo

Reputation: 6795

If you want to automate the process without using any plugins, you could use Go away and come back from Vim Tips Wiki.

Each time you exit Vim it will save the current session under ~/.vim/sessions and load it back again once Vim is opened. It's also based on you current path, so if you open Vim from different directories you will have different sessions, which is quite useful when working on different projects.

Just edit your ~/.vimrc file and add the following:

function! MakeSession()
  let b:sessiondir = $HOME . "/.vim/sessions" . getcwd()
  if (filewritable(b:sessiondir) != 2)
    exe 'silent !mkdir -p ' b:sessiondir
    redraw!
  endif
  let b:filename = b:sessiondir . '/session.vim'
  exe "mksession! " . b:filename
endfunction

function! LoadSession()
  let b:sessiondir = $HOME . "/.vim/sessions" . getcwd()
  let b:sessionfile = b:sessiondir . "/session.vim"
  if (filereadable(b:sessionfile))
    exe 'source ' b:sessionfile
  else
    echo "No session loaded."
  endif
endfunction

" Adding automatons for when entering or leaving Vim
au VimEnter * nested :call LoadSession()
au VimLeave * :call MakeSession()

Even for a beginner this script is somewhat easy to understand and customize.

Please note this script will only work properly for Unix systems (MacOS/Linux), it needs to be adapted to work on Windows.


UPDATE: Adding 0xc0de's suggestion, you may replace the VimEnter line for these ones if you want Vim to load session only if no arguments are provided:

if(argc() == 0)
  au VimEnter * nested :call LoadSession()
endif

Upvotes: 31

WALID BELRHALMIA
WALID BELRHALMIA

Reputation: 441

There is this wonderful plugin call vim-session. It's very powerful. To install it:

cd ~/.vim/bundle
git clone https://github.com/xolox/vim-session.git

I have mapped its functionality in my .vimrc file like this:

nnoremap <leader>so :OpenSession 
nnoremap <leader>ss :SaveSession 
nnoremap <leader>sd :DeleteSession<CR>
nnoremap <leader>sc :CloseSession<CR>

Now in normal mode just type <leader>ss and you will see a command like this

:SaveSession 

Now add the name of your session

 :SaveSession namesession

and that's all.

When you close Vim and reopen it just do

 :OpenSession

and you will see your session open.

There is a lot of other configuration to add in your .vimrc file see the documentation for examples:

let g:session_directory = "~/.vim/tmp/session"  // the directory must be created before the sessions will be saved there
let g:session_autoload = "no"                   // automatic reload sessions
let g:session_autosave = "no"                   // autosave
let g:session_command_aliases = 1

There is a good tutorial on YouTube.

Upvotes: 3

vivek
vivek

Reputation: 2857

There is a very useful plugin for this task vim-startify which handles many other things like recently opened files etc, it has a very easy interface too.

I am using it since couple of days and till now its working perfectly. Hope it helps you.

Upvotes: 7

Jan Christoph
Jan Christoph

Reputation: 751

You might want to set these session options in your vimrc. Especially options is annoying when you've changed your vimrc after you've saved the session.

set ssop-=options    " do not store global and local values in a session
set ssop-=folds      " do not store folds

Upvotes: 75

gdso
gdso

Reputation: 1911

If you use NERDTree as your file explorer/dash, I would recommend xolox/vim-session plugin instead of the built-in :mksession command. For some reason, :mksession fails to restore NERDTree buffers. Your mileage may vary, but thought I'd share my experience.

Upvotes: 36

Deepanshu
Deepanshu

Reputation: 826

Note that :mksession will not save the changes to any files that you've made. I made this mistake of closing vim after saving the session assuming that I'll take up from there. But next time I opened the session, the changes I had made to the files were gone.

Upvotes: 45

Benj
Benj

Reputation: 32418

You want something like

:mksession ~/mysession.vim

Then later you can source that vim file and you'll have your old session back:

:source ~/mysession.vim

or open vim with the -S option:

$ vim -S ~/mysession.vim

Upvotes: 583

Related Questions