Prasenjit Kumar Nag a.k.a Joy

A Developers Adventure in Coding

Lets Build a Terminal One-liner to Add All New Files Into a Subversion Repository

Those who of you have been working with subversion for a while may have noticed that when you add a number of files in different directories into an existing subversion repository you have to add each one of them from command line which is a pain.

Though the following command adds all new files recursively into the repo but it also add svn:ignored files back into the tree which is bad.

1
svn add --force *

So I was searching for a good solution today and found What I needed. In this tutorial I will to walking through the steps with explanation and finally we will have a ready-to-use one-liner, running which will add all new(untracked) files into a svn repo.

Using svn stat(or st) to check the status:  If you run the

1
2
3
4
5
svn status

#or

svn st

command from within your repo directory it will show you a list of new and modified files, I ran the command in one of my repo and the output was like this

1
2
3
4
5
?  .idea
?  application/models/book_model.php
?  application/views/find-books.php
M application/views/splash.php
?  application/controllers/books.php

The entries which have ? mark at the start are new files yet to be added into the svn repo. Lines starting with M means there are changes to be committed but the file is already in the repo. We are interested with the lines which start with ? So let’s filter the output of svn stat to find the lines which start with ? .We can use grep to do this using syntax like

1
svn status | grep "^?"

Which is telling grep to find lines which start with the character ?.  So this will out something like this for my repo

1
2
3
4
?  .idea
?  application/models/book_model.php
?  application/views/find-books.php
?  application/controllers/books.php

Now we have got the list of new files which we can add to svn repo using svn add command. But we need to remove the ? from the starting of these lines to use them as arguments of svn add . We can do this easily using the command line scripting language awk using the following  syntax

1
svn status | grep "^?" | awk '{print $2}'

we saw after using grep we had lines of this structure

1
?  application/models/book_model.php

As we are using | awk, so awk is getting two arguments first one is ? and second one is file path. So as awk is printing $2 which means the second argument, the file path. So after adding awk block we will have the following output

1
2
3
application/models/book_model.php
application/views/find-books.php
application/controllers/books.php

Which is exactly what we need to pass to svn add. Now using xarg we can pass this argument set into svn add command with this syntax

1
svn status | grep "^?" | awk '{print $2}' | xargs svn add

If you run this in your terminal all new files will be added to svn you can check that using svn stat again. Which will show that the files has been added for inclusion in remote repo in next commit.

We can make it a bit better though. Most of us use some kind of IDE’s and those IDE’s leave hidden files  for indexing and saving project specific settings. Or we may have hidden system files which we dont want to include in the repo. We can filter out the hidden files using another grep, the syntax is something like

1
svn status | grep -v "^.[ \t]*\..*"

So what is grep -v “^.[ \t]..doing here. The pattern “^.[ \t].. is matching svn status entries which have hidden files in it. If you have some idea about regular expression you can figure that out yourself, if you cant you can comment in this post and I will explain in details. And the -v option is an invert-match switch which tells grep to output non-matching files, that means files which are not hidden.

So we have got this by far

1
svn status | grep -v "^.[ \t]*\..*" | grep "^?" | awk '{print $2}' | xargs svn add

After that you can use svn stat again to make sure you are not committing anything you dont want to. Because it will add any non-hidden files in the repo. If you see that you have added a file you dont want to you can user the following command to remove that from next commit list

1
2
3
4
5
svn revert filename

#or this if you wan to remove a directory

svn revert --recursive path/to/directory/

And if you want to add any hidden file like a .htaccess then after running this command you can always use another svn add command to add that specific file or if you want you can even remove the hidden file removing grep block from the command chain.

So the one-liner you can use from now on is

1
svn status | grep -v "^.[ \t]*\..*" | grep "^?" | awk '{print $2}' | xargs svn add

This comes in handy When you add a lot of file in different directories and saves you time.

I am not very good at terminal things yet and found this snippet here.

This post is just an effort to better understand whats magic is going on in that one line.

Hope you enjoyed it. :)

Comments