How to make vim SpellCheck *not* code aware? - vim

By default, vim spell checker is code aware, so it doesn't spell-check code parts of the file. In effect, in markdown it considers (pandoc multiline) tables to be codes and thus doesn't spell-check their contents.
Is it possible to override this? Or enable spell-check for the entire file including code.

As far as I'm able to determine, there is no way to tell Vim to ignore the
spellcheck suggestions in the syntax file and to just "check everything".
A fairly heavy-handed workaround is to disable syntax entirely with :syn off;
you can re-enable this with :syn on.
Specifically for Markdown, you can disable highlighting of code blocks with
:syn clear markdownCodeBlock; you can reset this with :syn on as well.

Use syntax spell
:syntax spell toplevel
See:
http://usevim.com/2013/05/10/synspell/

In that case I would contact the maintainer of the markdown syntax file and ask him/she if (s)he could fix this issue.

I created bash script fixing syntax files. IT IS NOT PERFECT BUT IT IS GOOD. It can be reversed by running it again. It adds contains=#Spell to syn match and syn region definitions in all files in given directory.
To use it:
Save the script as fix_syntax_files.sh
Give it permissions
Change path at the bottom of the script to one corresponding to your vim plugins location
Run the script
(OPTIONAL) Run script again to revert the changes
The script makes backup of all files before modification so you can assume it is safe to run it. I anyway do not take any responsibility for potential problems caused by the script.
Edit:
You can leave feedback to the script in the following repository:
https://github.com/dominikduda/config_files/blob/master/bin/fix_vim_syntax_files.sh
#!/bin/bash
function fix_file {
sed -i -e '/exe/! {s/contains=/contains=#Spell,/g}' $1
sed -i -e 's/contains=#Spell,ALL/contains=ALL/g' $1
sed -i -e 's/contains=#Spell,ALLBUT/contains=ALLBUT/g' $1
sed -i -e 's/contains=#Spell,TOP/contains=TOP/g' $1
sed -i -e 's/contains=#Spell,CONTAINED/contains=CONTAINED/g' $1
sed -i -e 's/contains=#Spell,NONE/contains=#Spell/g' $1
sed -i -e '/^ *syn match/ {/contains=/! s/$/ contains=#Spell/g}' $1
sed -i -e '/^ *syn region/ {/contains=/! s/$/ contains=#Spell/g}' $1
return 0
}
function revert_file {
mv "$1/$2.spellfix-backup" "$1/$2"
return 0
}
function fix_recursively_in_catalog {
syntax_catalogs_paths="$(find $1 -type d ! -name '*.*' -not -path '*git*' -print)"
syntax_catalogs_count="$(echo "${syntax_catalogs_paths}" | wc -l)"
echo "${syntax_catalogs_count} syntax catalogs found and will be scanned for files"
echo "${syntax_catalogs_paths}" | while read -r catalog_path ; do
echo " Scanning $catalog_path"
ls -p "${catalog_path}" | grep -v / | grep -v .spellfix-backup | grep .vim | while read -r file_name ; do
cp "${catalog_path}/${file_name}" "${catalog_path}/${file_name}.spellfix-backup"
fix_file "${catalog_path}/${file_name}"
echo " Fixing ${file_name} (backup created as ${file_name}.spellfix-backup)"
done
done
echo 'Fix done.'
echo 'Remember to REVERT FIX before updating vim plugins'
return 0
}
function revert_recursively_in_catalog {
syntax_catalogs_paths="$(find $1 -type d ! -name '*.*' -not -path '*git*' -print)"
syntax_catalogs_count="$(echo "${syntax_catalogs_paths}" | wc -l)"
echo "${syntax_catalogs_count} syntax catalogs found and will be scanned for spellfix-backup files"
echo "${syntax_catalogs_paths}" | while read -r catalog_path ; do
echo " Scanning $catalog_path"
ls -p "${catalog_path}" | grep -v / | grep -v .spellfix-backup | grep .vim | while read -r file_name ; do
revert_file "${catalog_path}" "${file_name}"
echo " Reverting ${file_name} (from file ${file_name}.spellfix-backup)"
done
done
echo 'Revert done.'
echo 'Remember to FIX AGAIN after plugins update (or set it as a post update hook)'
return 0
}
function main {
syntax_catalogs_paths="$(find $1 -type d ! -name '*.*' -not -path '*git*' -print)"
while read -r catalog_path ; do
if ls -p "${catalog_path}" | grep -v / | grep .spellfix-backup; then
echo ".spellfix-backup files found, reverting fix!"
echo "--------------------------------------------"
revert_recursively_in_catalog $1
return 0
fi
done < <(echo "${syntax_catalogs_paths}")
echo ".spellfix-backup files NOT found, fixing!"
echo "-----------------------------------------"
fix_recursively_in_catalog $1
}
main ~/PATH/TO/VIM/PLUGINS/

Related

How do I search for a file based on what is output by a command running on that file

I am working on a project for one of my professors and he asked me to sort a couple hundred .fits images based on their header files (specifically what star they are images of) I think that grep would be the best way to do this however I can't seam to figure out how to use grep based on the header.
I am entering:
ls | imhead *.fits | grep -E -r "PG\ 1104+243" *
to just list them out for now, once they are listed I know how to copy them into a directory.
I am new to using grep so I am unsure as to where my error lies? any help would be greatly appreciated! Thanks!
Assuming that imghead will extract the headers of the .fits as txt, you can use a simple shell script to do it:
script.sh
#!/bin/bash
grep "$1" "$2" > /dev/null 2>&1 && echo "$2"
Note that the + is a special character if you use extended regular expression, meaning if you pass the -E as in the question. A simple grep without any options should do the trick here.
Use find to exec the script on every *.fits file in the current folder:
find -maxdepth 1 -name '*.fits' -exec ./script.sh 'PG 1104+243' {} \;
If you are going to copy/move/alter or do something with the files you find, you might be better off, in terms of complexity and ease of quoting, using a loop like this:
#!/bin/bash
find . -name \*.fits -print0 | while read -d '' -r file; do
echo Checking file: $file
imhead "$file" | grep -q 'PG 1104+243'
if [ $? -eq 0 ]; then
echo Object matches: $file
fi
done

sed with variable as argument in bash script

I am trying to write a bash script to scan for authorized_keys files and remove the keys of a couple previous employees if found. I am having one heck of a time figuring out the escaping for the sed command at the end. I am using commas instead of / since / can show up in the ssh-key. Any help would be appreciated
#!/bin/bash
declare -A keys
keys["employee1"]='AAAAB3NzaC1yc2EAAAABJQAAAIEAxoZ7ZdpJkL98n8cSTkFBwaAeSNK0m/tOWtF1mu5NAzMM/+1SDO6rJH/ruyyqBJo9s+AHWZLGRHfXT2XBg2SRaUnubAKp0w6qNIbej0MsA/ifAs8AfVGdj0pUPLtKpo6XVZkB8vEZSIQ+xNk1n5HJrGJnFGWKWeY3z1/KOLxcLHU='
keys["employee2"]='AAAAB3NzaC1yc2EAAAABIwAAAQEAwHYNAVhb319OBVXPhYF8cSTkFBwaAekr7UcKjfLPCHMpz19W0L/C0g+75Hn8COxOQILDUhIPhYHXOduQjGD/6NXgJDWxgyT00Azg5BREUnBd58WqZPlEvTZYlAgmdMIbnWPPGdJwzqKH/k7/STK6vTKxL6rxBo4lSNK0m/tOWtF1mu5NAzMM/+1SDO6rJH/ruyyqBJo9s+NIbej0MsA/ifAs8AfAkfO2JjgeQpJMyZ7B02XVN5iSLAyC3Cb5FXIjJuk4LPhcApuVyszH2lgve0r5bt/nFgVujJTvJTHPlGrqkYDcDJVUtfbjoLqGPrnpijp6rGIC7aFDDe7bk0ygHYMXDFWcjJBerfLGUWTYWFFLY3bfiO/h/9oEycmQHyB2co4a0IyyDnaYn9OY6xsRRATVlk4Q=='
files=`find / -name authorized_keys`
echo "Checking Authorized_Keys files on: " `hostname`
echo ""
echo "Located files: "
for file in $files; do
echo " $file"
done
echo""
for file in $files; do
for key in "${!keys[#]}"; do
if grep -q ${keys[$key]} $file; then
echo " *** Removing $key from $file"
sed "s,${keys[$key]},d" $file
fi
done
done
You've made it a bit complicated I think.
You can do this using grep -vf and process substitution:
# array to hold the value you want to remove
keys=(
'AAAAB3NzaC1yc2EAAAABJQAAAIEAxoZ7ZdpJkL98n8cSTkFBwaAeSNK0m/tOWtF1mu5NAzMM/+1SDO6rJH/ruyyqBJo9s+AHWZLGRHfXT2XBg2SRaUnubAKp0w6qNIbej0MsA/ifAs8AfVGdj0pUPLtKpo6XVZkB8vEZSIQ+xNk1n5HJrGJnFGWKWeY3z1/KOLxcLHU=',
'AAAAB3NzaC1yc2EAAAABIwAAAQEAwHYNAVhb319OBVXPhYF8cSTkFBwaAekr7UcKjfLPCHMpz19W0L/C0g+75Hn8COxOQILDUhIPhYHXOduQjGD/6NXgJDWxgyT00Azg5BREUnBd58WqZPlEvTZYlAgmdMIbnWPPGdJwzqKH/k7/STK6vTKxL6rxBo4lSNK0m/tOWtF1mu5NAzMM/+1SDO6rJH/ruyyqBJo9s+NIbej0MsA/ifAs8AfAkfO2JjgeQpJMyZ7B02XVN5iSLAyC3Cb5FXIjJuk4LPhcApuVyszH2lgve0r5bt/nFgVujJTvJTHPlGrqkYDcDJVUtfbjoLqGPrnpijp6rGIC7aFDDe7bk0ygHYMXDFWcjJBerfLGUWTYWFFLY3bfiO/h/9oEycmQHyB2co4a0IyyDnaYn9OY6xsRRATVlk4Q=='
)
while IFS= read -d '' -r file; do
grep -vf <(printf "%s\n" "${keys[#]}") "$file" > "$file.tmp"
mv "$file.tmp" "$file"
done < <(find / -name authorized_keys -print0)
In your case, it's easy, just need to use a sign which not contained in base64 code as the delimiter, eg |:
sed "\|${keys[$key]}|d" $file
Explanation in the sed manual:
\%regexp%
(The % may be replaced by any other single character.)
This also matches the regular expression regexp, but allows one to use a different delimiter than /.

how to find and delete below line using shell script

Below line has printed in my all php project pages because of malicious attacks.Now think is how i can find and delete this lines using shell script
function_exists('date_default_timezone') ?
date_default_timezone_set('America/Los_Angeles') :
($_REQUEST['c_id']));
I tried with below script but i getting error.I mean to say I not able to match above line with sed commend.Please help me to correct this script..
#!/bin/sh
search='^function_exists\(\'date_default_timezone\'\)\ \?\ date_default_timezone_set\(\'America/Los_Angeles\'\)\ \:\ \(\$_REQUEST\[\'c_id\'\]\)\)\;'
for file in `find /root/test1 -name "*.php"`; do grep "$search" $file &> /dev/null if [ $? -ne 0 ]; then echo "Search string not found in $file!" else sed -i '/$search/d' $file
Try sed with : seperators rather than / since in your pattern America/La conflicts with / ir add a backslash so its America/la
You're not escaping the regex correctly. Try the following:
while IFS= read -r -d '' file; do
if grep -qF "function_exists('date_default_timezone') ? date_default_timezone_set('America/Los_Angeles') : (\$_REQUEST['c_id']));" "$file"
then
sed -i "s|function_exists('date_default_timezone') ? date_default_timezone_set('America/Los_Angeles') : (\$_REQUEST\['c_id'\]));|FOO|g" "$file"
fi
done < <(find /root/test1 -type f -name "*.php" -print0)
This might work for you (GNU sed)
pattern1='function_exists('\''date_default_timezone'\'''
pattern2='.*date_default_timezone_set('\''America\/Los_Angeles'\'') :'
pattern3='.*($_REQUEST\['\''c_id'\''\]));'
sed '/^'"$pattern1"'/{N;N;/^'"$pattern1$pattern2$pattern3"'/d}' file

Linux Shell - Replacing string with other string inside files

I have a problem with this linux shell script.
#! /bin/bash
find /sdcard/ -type f -iname "*.srt" -print >> /sdcard/files
count=`wc -l /sdcard/files |cut -d'/' -f1`
for (( c=1; c<=$count; c++ ))
do
line=`sed -n ''$c'p' /sdcard/files`
cat "$line" | sed -e 's/č/c/g' > "$line".srt""
rm "$line"
done
rm /sdcard/files
I know this isnt the best way to do this but thats all i can do with my knowlage
As you can see it finds all srt files and then replaces all "č" charactes with "c". But it doesnt work with files i downloaded
However when i make a new file and write "č" inside (with my keyboard), it replaces it as it should. I dont understand why?
I think we discovered the cause, now the fix:
vim somefile.srt -c ":set bomb" -c ":set fileencoding=utf-8" -c ":wq"
There's also a dirty way
echo -e "\xC2\xA0" >> somefile.srt
I tried iconv tool which is supposed to do the conversion, but it didn't help.

how to loop files in linux from svn status

As being quite a newbie in linux, I have the follwing question.
I have list of files (this time resulting from svn status) and i want to create a script to loop them all and replace tabs with 4 spaces.
So I want from
....
D HTML/templates/t_bla.tpl
M HTML/templates/t_list_markt.tpl
M HTML/templates/t_vip.tpl
M HTML/templates/upsell.tpl
M HTML/templates/t_warranty.tpl
M HTML/templates/top.tpl
A + HTML/templates/t_r1.tpl
....
to something like
for i in <files>; expand -t4;do cp $i /tmp/x;expand -t4 /tmp/x > $i;done;
but I dont know how to do that...
You can use this command:
svn st | cut -c8- | xargs ls
This will cut the first 8 characters leaving only a list of file names, without Subversion flags. You can also add grep before cut to filter only some type of changes, like /^M/. xargs will pass the list of files as arguments to a given command (ls in this case).
I would use sed, like so:
for i in files
do
sed -i 's/\t/ /' "$i"
done
That big block in there is four spaces. ;-)
I haven't tested that, but it should work. And I'd back up your files just in case. The -i flag means that it will do the replacements on the files in-place, but if it messes up, you'll want to be able to restore them.
This assumes that $files contains the filenames. However, you can also use Adam's approach at grabbing the filenames, just use the sed command above without the "$i".
Not asking for any votes, but for the record I'll post the combined answer from #Adam Byrtek and #Dan Fego:
svn st | cut -c8- | xargs sed -i 's/\t/ /'
I could not test it with real subversion output, but this should do the job:
svn st | cut -c8- | while read file; do expand -t4 $file > "$file-temp"; mv "$file-temp" "$file"; done
svn st | cut -c8- will generate a list of files without subversion flags. read will then save each entry in the variable $file and expand is used to replace the tabs with four spaces in each file.
Not quite what you're asking, but perhaps you should be looking into commit hooks in subversion?
You could create a hook to block check-ins of any code that contains tabs at the start of a line, or contains tabs at all.
In the repo directory on your subversion server there'll be a directory called hooks. Put something in there which is executable called 'pre-commit' and it'll be run before anything is allowed to be committed. It can return a status to block the commit if you wish.
Here's what I have to stop php files with syntax errors being checked in:
#!/bin/bash
REPOS="$1"
TXN="$2"
PHP="/usr/bin/php"
SVNLOOK=/usr/bin/svnlook
$SVNLOOK log -t "$TXN" "$REPOS" | grep "[a-zA-Z0-9]" > /dev/null
if [ $? -ne 0 ]
then
echo 1>&2
echo "You must enter a comment" 1>&2
exit 1
fi
CHANGED=`$SVNLOOK changed -t "$TXN" "$REPOS" | awk '{print $2}'`
for LINE in $CHANGED
do
FILE=`echo $LINE | egrep \\.php$`
if [ $? == 0 ]
then
MESSAGE=`$SVNLOOK cat -t "$TXN" "$REPOS" "${FILE}" | $PHP -l`
if [ $? -ne 0 ]
then
echo 1>&2
echo "***********************************" 1>&2
echo "PHP error in: ${FILE}:" 1>&2
echo "$MESSAGE" | sed "s| -| $FILE|g" 1>&2
echo "***********************************" 1>&2
exit 1
fi
fi
done

Resources