4

Earlier, I had created some links to another folder using the following command.

sudo ln -s path_name link_name 

These links are looking similar to the folders. I am not able to differentiate between a folder and a link. Is there a way to find the difference between a folder and a link to another folder?

terdon
  • 100,812
mateen
  • 657

4 Answers4

6

There are many ways to see this. First of all, it is indicated in the output of ls -l. Note that the directory has a d at the beginning of the permissions field while the link has an l:

$ ls -l
drwxr-xr-x 2 terdon terdon 4096 Feb 13 14:12 bar
lrwxrwxrwx 1 terdon terdon    3 Feb 13 14:12 foo -> bar

You can also use file:

$ file bar foo 
bar: directory 
foo: symbolic link to `bar' 

Another choice is readlink which follows symbolic links to their targets:

$ readlink foo
bar

Running readlink bar will return no output (it fails, returning a non-0 exit code), so you can do something like:

readlink bar || echo "Not a link!"

or

readlink foo && "Echo this is a link"

Finally, you could also use find or the shell itself to list all links:

find . -type l

or

for f in *; do [ -L "$f" ] && echo "$f is a link"; done
terdon
  • 100,812
5

You could recognize a link by either a small arrow (->) in the output of ls -l:

enter image description here

or by the distinguished color, also appearing in the output of ls, as described in this answer (test2 is the link):

enter image description here

Jacob Vlijm
  • 83,767
2

Read man [ (or man test)and you will see you can do:

for theDir in path_name link_name ; do  
    if [ -L $theDir ] ; then  
        echo "$theDir exists and is a symbolic link"   
    elif [ -d $theDir ] ; then  
        echo "$theDir exists and is a directory"  
    fi  
done

I changed the order of the tests, so checking for a directory is done only if $theDir is not a link.

waltinator
  • 36,399
1

use ls -F .

this will make ls append characters to filenames

* for executable files

/ for directories

@ for symlinks**

| for FIFOs

> for doors (whatever this means)

= for sockets

regular files don't have classifier at the end. So in your case you'll see @ at the end of each symlink name and / at the end of real directory.

However if you use ls -l you won't see classifiers for symlinks and instead you'll see -> and link target after that.

You can also use stat and file to differentiate dirs/symlinks e.g:

$ file a                                                                                                                                                                                     
a: directory

$ file b                                                                                                                                                                                      
b: symbolic link to a

$ stat a                                                                                                                                                                                  
  File: 'a'
  Size: 40          Blocks: 0          IO Block: 4096   directory
 [...]

$ stat b                                                                                                                                                                                    
  File: 'b' -> 'a'
  Size: 1           Blocks: 0          IO Block: 4096   symbolic link
  [...]
suawek
  • 11