Closed. This question does not meet Stack Overflow guidelines. It is not currently accepting answers.
This question does not appear to be about a specific programming problem, a software algorithm, or software tools primarily used by programmers. If you believe the question would be on-topic on another Stack Exchange site, you can leave a comment to explain where the question may be able to be answered.
Closed 6 years ago.
Improve this question
I'm trying to symlink all files in a directory to a target directory, by doing:
ln -s /directory/* /target-directory
Problem is when I go into the target-directory, I'm seeing this '*', an asterisk in quotes, instead of all the files in the first directory. What am I doing wrong? Thanks.
Normally, what'd happen when you run ln -s /directory/* /target-directory is that the shell would expand /directory/* into a list of the (currently existing, visible) files in /directory/, and then pass that to ln in its argument list. The result would be equivalent to something like ln -s /directory/file1.txt /directory/file3.pdf /directory/file3.c /target-directory. Note that the ln command would not see the "*", and so would not include it in either the link source or target name.
Since "*" is being used as the link name, it's not getting expanded. There are a couple of reasons this might happen:
You might have the noglob shell option set. But you said in the comments that's not the case.
The shell expansion might not have matched any files, in which case the shell will simply pass it unchanged to ln, giving the result you describe. You said you created a file in the source directory, but did you re-test after doing that? Another possibility is that there's a typo in the directory path, so it's not finding a matching directory (let alone any files in it).
Oh, one more note: you said when you go to the target directory, you see an asterisk in quotes. Exactly how are you looking? Because if you're just using ls, it should not include quotes in the listing unless they're actually part of the filename. [Edit: Mark Plotnick pointed out that some versions of GNU ls do add quotes to some filenames.] I have no idea how the command you gave could add quotes to the filename.
Do not create the destination directory and do
ln -sd ./source ./destination
If you set the failglob option, you will get an error message if expansion of * is not possible.
shopt -s failglob
Related
Closed. This question is not about programming or software development. It is not currently accepting answers.
This question does not appear to be about a specific programming problem, a software algorithm, or software tools primarily used by programmers. If you believe the question would be on-topic on another Stack Exchange site, you can leave a comment to explain where the question may be able to be answered.
Closed 6 months ago.
Improve this question
ln -s $(ls ../*.txt)
When I do the command above it replay with an error message saying : "ln: target '../foo.txt' is not a directory".
foo.txt is the first file that ls command has found in the parent dir.
I am trying to make symbolic links for all the files in the parent directory which ends with ".txt".
Can you please explain why my command did not work ?
You forgot the directory name to put all the links into. If you want them put into the current directory, use ..
There's also no need to use ls, and you'll get the wrong results if any of the filenames contain whitespace or wildcard characters, because those will be processed in the $(...) output. Just use the wildcard directly.
ln -s ../*.txt .
Closed. This question does not meet Stack Overflow guidelines. It is not currently accepting answers.
This question does not appear to be about a specific programming problem, a software algorithm, or software tools primarily used by programmers. If you believe the question would be on-topic on another Stack Exchange site, you can leave a comment to explain where the question may be able to be answered.
Closed 1 year ago.
Improve this question
As far as you know, - has different usages for in combination with different commands in Linux. For example in combination with cd command, it means "Change directory to the previous location" and in combination mv or cat command it means stdin or stdout.
Unfortunately I wrongly used this character with mv command. I wanted to move my file to the previous location which I have been before the change directory but I moved it to stdin instead.
Is there any way to recover my file?
I run this command:
# mv myfile -
I moved it to stdin instead.
No, you moved to a file literally named by a dash (you'll use /dev/stdin or /proc/self/fd/0 to refer to the stdin, i.e. the file descriptor 0).
You want to
mv -i ./- myfile
this is usual practice (to prefix by ./ a strange path). The -i interactively asks for confirmation.
Sometimes it is not even easy to type a path for a weird file (e.g. for a file name containing a single newline character). You could use globbing (read about shell expansion), e.g. mv -i ./? file.
See mv(1) and path_resolution(7) and glob(7) and proc(5)
The good habit is to avoid strange characters in file paths.
Closed. This question does not meet Stack Overflow guidelines. It is not currently accepting answers.
This question does not appear to be about a specific programming problem, a software algorithm, or software tools primarily used by programmers. If you believe the question would be on-topic on another Stack Exchange site, you can leave a comment to explain where the question may be able to be answered.
Closed 5 years ago.
Improve this question
I want to rename files in a folder on UNIX using a script.
The format of the original file is:
abc.txt.temp
and I want to rename it to:
abc.txt
Many files use this format and I want to remove .temp from the original file name.
The answer Ciprian gave is certainly an option but I feel it's limiting.
The solution below is much more flexible as you don't have to actually count anything and you can remove text from any position rather than just the end.
The following command (1 line) will remove any mention of .temp in all the files:
for filename in *; do mv "$filename" "${filename//.temp/}"; done
Note The "*" means all files in current folder. You can use *.temp to achieve exactly the same result as Ciprian's method. (that is, only removing .temp from files ending with .temp)
I don't know about UNIX, but since the question also have the Linux tag it may just be a UNIX/Linux confusion.
Most GNU/Linux distributions have a rename command. Depending on the rename version, to replace foo with bar in files names the syntax may either be as simple as
rename foo bar files
or follow sed's regexp syntax :
rename 's/foo/bar/' files
In your case, you want to replace .temp with an empty string ('') in all files ending with .temp, so depending on your rename version one of these commands should work :
rename .temp '' *.temp
or
rename 's/\.temp$//' *.temp
Create the following script with a name like 'rename.sh':
#!/bin/bash
TARGET_DIR=$1
TARGET_FILES="$TARGET_DIR/*.temp"
for fileName in $TARGET_FILES
do
newFileName=${fileName::-5}
mv -v "${fileName}" "${newFileName}"
done
note The ${var:offset:length} expansion requires bash version 4 or higher.
Give it execution rights:
chmod a+x rename.sh
You need to call it and pass the name of the directory of the .temp files as a parameter. Call it like this:
./rename.sh /path/to/the/temp-files
The script loops over all the *.temp files in the target folder, extracts the last 5 chars from the file path ('.temp' is 5 chars) and moves the original file to the new file that doesn't contain .temp as the extension.
EDIT: tested on a CentOS 7
Closed. This question does not meet Stack Overflow guidelines. It is not currently accepting answers.
This question does not appear to be about a specific programming problem, a software algorithm, or software tools primarily used by programmers. If you believe the question would be on-topic on another Stack Exchange site, you can leave a comment to explain where the question may be able to be answered.
Closed 7 years ago.
Improve this question
I have found that if I have a .sh file in a certain directory then I can run it (using sh) from that folder with or without dot forward slash. So why even bother adding it?
Please check http://www.linfo.org/dot_slash.html as well.
Basically this is a safety mechanism to indicate the program to execute is in the current directory and NOT a built-in command, a command in some other folder specified in the PATH etc.
From the link:
Files in the current directory can be accessed for reading and writing by merely entering the command name (e.g., cat or vi) followed by the name of the file. That is, no absolute path is necessary. However, when execution is desired, either an absolute path (or its dot slash equivalent) or the inclusion of the directory containing the command's executable file in the PATH variable is necessary. This is a built-in safety mechanism.
If your script is running without ./ then it means the specific location is in the path or . is in the path as mentioned in comments.
Hope it helps.
Your PATH is a list of directories which is searched to find files to execute. If your command is in one of those directories it will be executed. If it is in a different directory, then you need to indicate to the shell what directory it is in. . means the current directory, so
./prog
will run the prog file found in the current directory
/some/other/path/prog
will run the file in the directort /some/other/path
and
subdir/prog
will run prog in subdir relative to your current directory.
To see what your path is set to type echo $PATH.
Closed. This question does not meet Stack Overflow guidelines. It is not currently accepting answers.
This question does not appear to be about a specific programming problem, a software algorithm, or software tools primarily used by programmers. If you believe the question would be on-topic on another Stack Exchange site, you can leave a comment to explain where the question may be able to be answered.
Closed 2 years ago.
Improve this question
How do you add any current directory './' to the search path for executables in Linux?
I know this is an old answer, but if anyone else stumbles across this question via Google like I did, here's a more detailed explanation.
If you want to make it so that search path contains the value of pwd at the time you set the search path, do:
export PATH=$PATH:$(pwd)
So, if pwd is /home/me/tmp, PATH will be set to $PATH:/home/me/tmp
However, If you want it so that whatever your present working directory is at the time you execute a command (ex; the value of pwd at any given time is in the search path), do:
export PATH=$PATH:.
So, if pwd is /home/me/tmp, PATH will be set to $PATH:.. If your present working directory contains a script called foo, then it would be fount in your PATH. If you change directories to one that does not contain foo, "foo" will not be found in the PATH any more.
You should note that having your present working directory in your PATH is a potential security risk, however.
If you want to permanently add the directory you're currently in to the PATH variable you can use
$ echo "export PATH=\$PATH:$(pwd)" >> ~/.bashrc
which will expand $(pwd) to the string literal of your current directory and append the quoted line to your bashrc which is loaded when you start your terminal. Note the \ in \$PATH is needed to escape the expansion of $PATH to its current value.
$ pwd
/path/to/suuuuuuuuuuuuuuuuuuuuper/long/foo/directory/bin
$ echo "export PATH=\$PATH:$(pwd)" >> ~/.bashrc
$ tail ~/.bashrc -n 1
export PATH=$PATH:/path/to/suuuuuuuuuuuuuuuuuuuuper/long/foo/directory/bin
For the current directory, you can just use a zero-length (null) directory name. You can use an initial or trailing colon, or a double colon. This is from the bash manpage, man bash:
PATH The search path for commands. It is a colon-separated list of
directories in which the shell looks for commands (see COMMAND EXECUTION
below). A zero-length (null) directory name in the value of PATH
indicates the current directory. A null directory name may appear as two
adjacent colons, or as an initial or trailing colon. The default path
is system-dependent, and is set by the administrator who installs bash.
A common value is
``/usr/local/bin:/usr/local/sbin:/usr/bin:/usr/sbin:/bin:/sbin''.
Um...that didn't work for me. I would do
export PATH=$(pwd):$PATH
The command previously posted literally just adds the dot.
export PATH=$PATH:$PWD
works with bash 4.3.48
This is an old question, but I thought I'd add to it for those using the CSH or TCSH.
Adding the following to your .cshrc or .tcshrc will add the current directory to the environment path variable.
setenv PATH {$PATH}:.