Unix search ignore caps - linux

I want to search for a specific file by name in Solaris.
But I don't know whether the file has caps in the name or not, so I want to ignore the caps.
If i use:
find . -name 'word'
it won't find me file that is named WoRd.
I know I have to use -i somehow, but I just can't manage to find the correct syntax.
Thanks.

Please try this one. It will be solved your problem
$find . -iname 'word'
Where i for ignore case sensitive

Try this, -type f matches files only, you were correct to assume using the -i flag
find . -type f -print | grep -i "word"
Also check out this answer that goes deeper: https://unix.stackexchange.com/questions/40766/help-understanding-find-syntax-on-solaris

Related

How to recursively delete all files in folder that dont match a given pattern

I would like to delete all files in a given folder that dont match the pattern ^transactions_[0-9]+
Let's say I have these files in the folder
file_list
transactions_010116.csv
transactions_020116.csv
transactions_check_010116.csv
transactions_check_020116.csv
I would like to delete transactions_check_010116.csv and transactions_check_020116.csv and leave the first two as they are using ^transactions_[0-9]+
I've been trying to use find something like below, but this expression deletes everything in the folder not just the files that dont match the pattern:
find /my_file_location -type f ! -regex '^transactions_[0-9]+' -delete
What i'm trying to do here is using regex find all files in folder that dont start with ^transactions_[0-9]+ and delete them.
Depending on your implementation, you could have to use option -E to allow the use of full regexes. An other problem is that -regex gives you an almost full path starting with the directory you passed.
So the correct command should be:
find -E /my_file_location ! -regex '.*/transactions_[0-9]+$' -type f -delete
But you should first issue the same with -print to be sure...
grep has -v option to grep everything not matching the provided regex:
find . | grep -v '^transactions_[0-9]+' | xargs rm -f

Using Perl-based rename command with find in Bash

I just stumbled upon Perl today while playing around with Bash scripting. When I tried to remove blank spaces in multiple file names, I found this post, which helped me a lot.
After a lot of struggling, I finally understand the rename and substitution commands and their syntax. I wanted to try to replace all "_(x)" at the end of file names with "x", due to duplicate files. But when I try to do it myself, it just does not seem to work. I have three questions with the following code:
Why is nothing executed when I run it?
I used redirection to show me the success note as an error, so I know what happened. What did I do wrong about that?
After a lot of research, I still do not entirely understand file descriptors and redirection in Bash as well as the syntax for the substitute function in Perl. Can somebody give give me a link for a good tutorial?
find -name "*_(*)." -type f | \
rename 's/)././g' && \
find -name "*_(*." -type f | \
rename 's/_(//g' 2>&1
You either need to use xargs or you need to use find's ability to execute commands:
find -name "*_(*)." -type f | xargs rename 's/)././g'
find -name "*_(*." -type f | xargs rename 's/_(//g'
Or:
find -name "*_(*)." -type f -exec rename 's/)././g' {} +
find -name "*_(*." -type f -exec rename 's/_(//g' {} +
In both cases, the file names are added to the command line of rename. As it was, rename would have to read its standard input to discover the file names — and it doesn't.
Does the first find find the files you want? Is the dot at the end of the pattern needed? Do the regexes do what you expect? OK, let's debug some of those too.
You could do it all in one command with a more complex regex:
find . -name "*_(*)" -type f -exec rename 's/_\((\d+)\)$/$1/' {} +
The find pattern is corrected to lose the requirement of a trailing .. If the _(x) is inserted before the extension, then you'd need "*_(*).*" as the pattern for find (and you'll need to revise the Perl regexes).
The Perl substitute needs dissection:
The \( matches an open parenthesis.
The ( starts a capture group.
The \d+ looks for 'one or more digits'.
The ) stops the capture group. It is the first and only, so it is given the number 1.
The \) matches a close parenthesis.
The $ matches the end of the file name.
The $1 in the replacement puts the value of capture group 1 into the replacement text.
In your code, the 2>&1 sent the error messages from the second rename command to standard output instead of standard error. That really doesn't help much here.
You need two separate tutorials; you are not going to find one tutorial that covers I/O redirection in Bash and regular expressions in Perl.
The 'official' Perl regular expression tutorial is:
perlretut, also available as perldoc perlretut on your machine.
The Bash manual covers I/O redirection, but it is somewhat terse:
I/O Redirections.

Replace a part of statement with another in whole source code

I am trying to find the whole source code for occurrences of, say, "MY_NAME" and want to replace it with, say, "YOUR_NAME". I already know the files and the line numbers where they occur and i want to make a patch for the same so that anyone running the patch can do the same. Can anyone please help?
You can do it by console. Just use find to locate destination files, and then you can declare what you want to replace with what sentence. In example:
find -name '*' | xargs perl -pi -e 's/MY_NAME/YOUR_NAME/g'
It might be easier to do a sed command, and then generate a patch.
sed -e '12s/MY_NAME/YOUR_NAME/g;32s/MY_NAME/YOUR_NAME/g' file > file2
This will replace MY_NAME with YOUR_NAME on lines 12 and 32, and save the output into file2.
You can also generate a sed script if there are many changes:
#!/bin/sed -f
12s/MY_NAME/YOUR_NAME/g
32s/MY_NAME/YOUR_NAME/g
Then, for applying to many files, you should use find:
find -type f '(' -iname "*.c" -or -iname "*.h" ')' -exec "./script.sed" '{}' \;
Hope this helps =)
Use the command diff to create a patch-file that can then be distributed and applied with the patch-command.
man diff Will give you a lot of information on the process.

Find in Linux combined with a search to return a particular line

I'm trying to return a particular line from files found from this search:
find . -name "database.php"
Each of these files contains a database name, next to a php variable like $dname=
I've been trying to use -exec to execute a grep search on this file with no success
-exec "grep {\}\ dbname"
Can anyone provide me with some understanding of how to accomplish this task?
I'm running CentOS 5, and there are about 100 database.php files stored in subdirectories on my server.
Thanks
Jason
You have the arguments to grep inverted, and you need them as separate arguments:
find . -name "database.php" -exec grep '$dbname' /dev/null {} +
The presence of /dev/null ensures that the file name(s) that match are listed as well as the lines that match.
I think this will do it. Not sure if you need to make any adjustments for CentOS.
find . -name "database.php" -exec grep dbname {} \;
I worked it out using xargs
find . -name "database.php" -print | xargs grep \'database\'\=\> > list_of_databases
Feel free to post a better way if you find one (or what some rep for a good answer)
I tend to habitually avoid find because I've never learned how to use it properly, so the way I'd accomplish your task would be:
grep dbname **/database.php
Edit: This command won't be viable in all cases because it can potentially generate a very long argument list, whereas find executes its command on found files one by one like xargs. And, as I noted in my comment, it's possibly not very portable. But it's damn short ;)

Ignore case when trying to match file names using find command in Linux

Right now, all I know to use is:
find / -name string.*
that is case sensitive and it won't find files named:
1string.x
STRing.x
string1.x
How can I search so that all the above would be returned in the search to a case-insensitive matching?
Use the -iname option instead of -name.
Or you could use find / | grep -i string
This works as well, if you want to avoid the single quotes:
find . -iname \*string\*
Use -iname in find for case insensitive file name matches.
If the system you are in does not have the find command provided by the GNU utils package, you can use the -name tag alone with POSIX bracket expressions as
find . -name '*[Ss][Tt][Rr]ing*'

Resources