reverse symbolic links

c’est bien plus beau quand c’est inutile :

j’installe un apache , donc dans /var/www /usr/share/apache2 /var/log/httpd /var/run/httpd.pid pour schématiser

mais j’ai un DSI maniaque obsessionnel, il veut que tout soit bien rangé dans /data /softs /logs/ ;

qu’à cela ne tienne, embobinons le avec des liens symboliques

 

/softs/apache/share -> /usr/share/apache2
/softs/apache/bin/httpd -> /usr/bin/httpd
/data/apache/data -> /var/www
/data/apache/config -> /etc/apache2.d
/data/run/httpd.pid -> /var/run/httpd.pid
/logs/apache -> /var/log/httpd

Voilà c’est joli, il n’est pas au centre et pourtant il tourne, comme dirait Galilée.

Mais le DSI est technobsessionnel, il veut que ça aille dans les bon filesystems,
le plus simple est de ne rien renommer mais d’inverser les liens symboliques

-> devient <- , ben voyons…

 

#!/bin/sh
act=$1
apps=$2
 
 
 
DRH_softs="redhat"
DRH_logs="redhat/redhat"
DRH_appli="redhat/redhat"
 
# build apps list
if [ "$apps" = "" ];then
 apps=""
 for rdd in `ls -d /softs/*/redhat /appli/*/redhat/redhat /logs/*/redhat/redhat`;do
 app=`echo $rdd|sed -e "s:/redhat.*$::" -e "s:^.*/::"`
 apps="$apps $app"
 done
 apps=`echo "$apps"|tr " " "\n"|sort -u|tr "\n" " "`
fi
 
echo "$0 [link,tar,unlink]:$act [apps]:$apps"
if [ "$act" = "" ];then exit 10;fi
 
 
for app in $apps;do
 
#count links
 cntl=5
 cntf=0
 for s in appli softs logs;do
 cnt=`find /$s/$app/redhat/ -type l |grep -v /tools/|grep -v /conf|wc -l`
 cntl=`expr $cntl + $cnt`
 cnt=`find /$s/$app/redhat/ -type f |grep -v /tools/|grep -v /conf|wc -l`
 cntf=`expr $cntf + $cnt`
 done
 if [ "$cntl" -ge "$cntf" ];then isapplnk=1;else isapplnk=2;fi
 echo "$app $cntl links, $cntf files : "
 if [ "$isapplnk" = "1" ];then echo "ok to tar or link";fi
 if [ "$isapplnk" = "2" ];then echo "ok to unlink";fi
 isok=0
 if [ $act = "link" ];then if [ "$isapplnk" = "1" ];then isok=1;fi;fi
 if [ $act = "tar" ];then if [ "$isapplnk" = "1" ];then isok=1;fi;fi
 if [ $act = "unlink" ];then if [ "$isapplnk" = "2" ];then isok=1;fi;fi
 if [ $isok = "0" ];then echo "ERR: $act not permitted";exit 5;fi
 
#do tar untar if ok
 ru=/appli/$app/redhat
 rur=/appli/$app/redhat/tar
 mkdir -p $ru;
 cd $ru
 if [ $act != "unlink" ];then #create tar
 rm -f $ru/lnks_$app.tgz
 tar cfz $ru/lnks_$app.tgz /softs/$app/redhat/ /appli/$app/redhat/redhat/ /logs/$app/redhat/redhat/
 echo "OK : $ru/lnks_$app.tgz";
 fi
 #always untar
 if [ ! -f lnks_$app.tgz ];then echo "ERR: lnks_$app.tgz not found";exit 1;fi
 rm -rf $rur;mkdir -p $rur;cd $rur;tar xfz ../lnks_$app.tgz;cd -
 
#do link unlink
 for LNKK in softs appli logs;do
 eval "LNKR=\$LNK_${LNKK}"
 eval "LNKS=/\$LNKK/\$app/\$DRH_${LNKK}"
 eval "DIR_${LNKK}=$LNKS"
 dd="$LNKS"
 rdd="$rur$LNKS"
 #for rdd in `ls -d $r/logs/$app/redhat $r/appli/$app/redhat/redhat $r/softs/$app/redhat/redhat`;do
 #dd=`echo $rdd|sed -e "s:^$r::"`
 ###app=`echo $dd|sed -e "s:/$dr/::" -e "s:/.*$::"`
 #filtre si app=papp ou papp=""
 if [ -d "$rdd" ];then
 for rl in `find $rdd -type l`;do
 l=`echo $rl|sed -e "s:^$rur::"`
 ld=`ls -ld $rl|sed -e "s/^.* -> //"`
 if [ $act = "link" ];then
 if [ -L $l ];then
 islocal=0
 if [ "`echo $ld|sed -e 's:^\.::'`" != "$ld" ];then islocal=1;fi
 if [ "`echo $ld|sed -e 's:/redhat/::'`" != "$ld" ];then islocal=1;fi
 if [ "$islocal" = "1" ];then 
 echo "INFO $l -> $ld local link unchanged"
 else
 if [ -e $ld ];then
 rm -f $l
 mv $ld $l
 ln -s $l $ld
 else
 echo "ERR $ld should exists"
 fi
 fi
 else
 echo "ERR $l should be a link"
 fi
 fi
 if [ $act = "unlink" ];then
 if [ -L $ld ];then
 if [ -e $l ];then
 rm -f $ld
 mv $l $ld
 ln -s $ld $l
 else
 echo "ERR $l should exists"
 fi
 else
 echo "ERR $ld should be a link"
 fi
 fi
 done
 fi
 done
 #clean untared
 #if [ "`basename $rur`" != "tar" ];then exit 99;fi;#just checking
 rm -rf $rur
done

en gros :
j’ai une action link, et unlink pour remettre comme avant, et tar
je fais un tar pour me rappeler comment c’était les links avant
je compte le nombre de fichiers et de liens pour savoir si j’ai déjà fait un link
(mais je pourrais plutôt comparer au tar)
je boucle pour faire un rm B, mv A B;ln -s A B.

je relance, c’est moche mais ça marche.
le rpm ne retrouve pas ses fichiers (à tester, ça se trouve c’est bon ?)
apparmor ou selinux sont un peu perdu (binaire pas en place, ou data déplacées)

un peu flippant.

 

Pocket

petits debugs du jour (RewriteRule, iptables udp dns, ulimit)

que des petites choses. allons voir :

avant, toto.fr ne pointait pas au même endroit que www.toto.fr (mais sur tartar.com), un oubli qui n’a pas été modifié de peur que google perde la bonne indexation….

berk c’est laid, je corrige.

Mais pour google je rajoute :

 

RewriteCond /home/sites/toto.fr/www/{REQUEST_URI} !-f
RewriteCond /home/sites/tartar.com/www/%{REQUEST_URI} -f
RewriteRule ^(.+)$ http://www.tartar.com/$1 [R=301,L]
 
RewriteCond /home/sites/toto.fr/www/{REQUEST_URI} !-d
RewriteCond /home/sites/tartar.com/www/%{REQUEST_URI} -d
RewriteRule ^(.+)$ http://www.tartar.com/$1 [R=301,L]

 

autre chose, une machine ne résoud pas les noms depuis que j’ai réparé la config iptables.

faut dire qu’on avait :

 

:INPUT ACCEPT
-A INPUT -p udp -m udp --dport 53 -j ACCEPT
-A INPUT -p tcp -m tcp --dport 53 -j ACCEPT
-A INPUT -p udp -m udp --dport 67 -j ACCEPT
-A INPUT -p tcp -m tcp --dport 67 -j ACCEPT
-A INPUT -p tcp -m tcp --dport 22 -j ACCEPT
-A INPUT -j REJECT --reject-with icmp-host-prohibited

pourtant ça marche sur une machine identique

ah non , ya une différence :

-A INPUT -j REJECT -p tcp –reject-with icmp-host-prohibited

eh oui, du coup les “mauvaises requetes” udp passent , et passent aussi grâce au INPUT:ACCEPT.

faut modifier

INPUT:DROP

-A INPUT -j REJECT –reject-with icmp-host-prohibited

et iptable rules to allow outgoing DNS lookups  wikipedia

les requêtes udp utilisent pour répondre la même ouverture créée par la requête entrante.
-A INPUT -p udp -m udp –sport 53 -j ACCEPT
-A INPUT -p udp -m udp –sport 67 -j ACCEPT


:INPUT DROP
-A INPUT -p udp -m udp --sport 53 -j ACCEPT
-A INPUT -p tcp -m tcp --dport 53 -j ACCEPT
-A INPUT -p udp -m udp --sport 67 -j ACCEPT
-A INPUT -p tcp -m tcp --dport 67 -j ACCEPT
-A INPUT -p tcp -m tcp --dport 22 -j ACCEPT
-A INPUT -j REJECT --reject-with icmp-host-prohibited

et une correction sur une partie de script qui lit le contenu de limit.conf pour un user et génère les commandes ulimit qui correspondent :

 

# use ulimits from original user
if [ -f "/etc/security/limits.conf" ];then
#syntaxe de ulimit differente selon version de ksh
KSH_ISPDKSH="`ksh -c 'echo \$KSH_VERSION'|sed -e 's/^.*PD *KSH.*$/pdksh/'`"
if [ "$KSH_ISPDKSH" = "pdksh" ];then
KSH_TR_ULIMIT="core-c data-d fsize-f memlock-l rss-m nofile-n stack-s cpu-t nproc-p"
else
KSH_TR_ULIMIT="core-c data-d nice-e fsize-f sigpending-i memlock-l rss-m nofile-n pipe-p msqqueue-q rtprio-r stack-s cpu-t nproc-u"
fi
ULIMIT_SYSUSER=`grep ^$GSCRIPT_SYSUSER /etc/security/limits.conf \
| sed -e 's/\t/ /g' -e 's/ */ /g' |sort -r \
| sed -e 's/^.* soft *//' -e 's/^.* hard *//' -e 's/ /_/g'`
for ULIMTR in $KSH_TR_ULIMIT;do
ULIMTRCNF=`echo $ULIMTR|sed -e 's/-.*$//'`
ULIMTRCMD=`echo $ULIMTR|sed -e 's/^.*-//'`
ULIMIT_SYSUSER=`echo "$ULIMIT_SYSUSER"|sed -e s/$ULIMTRCNF/-$ULIMTRCMD/`
done
for ULIMCMD in $ULIMIT_SYSUSER;do
if [ "`echo x$ULIMCMD|sed -e 's/^x-.*$//'`" = "" ];then
ulimit `echo $ULIMCMD|sed -e 's/_/ /g' -e 's/ -1/ unlimited/'`
fi
done
fi

en plus c’est différent suivant la version de pdksh

(fixed: -1 dans ulimit.conf doit être transcrit en unlimited)

 

Pocket

bash on Windows

ok, c’est juste trois fonctions de rien du tout, mais qui me permettent d’avoir les mêmes scripts (patchs tomcat) entre linux et windows (mingw le site mingw mingw sourceforge)

 

# input can be any C:\* C:/* /C/* /folder/* => Windows, Unix, T:W-slashed-in-file 
function path2u { echo "$*"|tr '\\' '/'|sed -e 's|^\([A-Z]\):|/\U\1|i' -e 's:[/\\]$::';} 
function path2w { echo "$*"|sed -e 's|/\([a-z]\)/|\U\1:/|i' -e 's:[/\\]$::'|tr '/' '\\';} 
function path2t { echo "$*"|sed -e 's|/\([a-z]\)/|\U\1:/|i' -e 's:[/\\]$::'|tr '\\' '/';} 
U_HERE=`path2u $*` 
W_HERE=`path2w $*` 
T_HERE=`path2t $*`

dans le script j’utilise les U_HERE pour naviguer (/C/xxx ou /toto/)

j’écris dans les fichiers de config des T_HERE (C:/xxx/) ou (là ya bien un test) W_HERE (c:\xxx) sur windows

notez le sed ([a-z]) transformé en uppercase \U\1

et le “$*” pour l’affligeant espace de “c:\program files\java\”

Pocket

MSWord Clear formatting with style, like css

Encore un truc que j’utilisais il y a longtemps, et que je retrouve.
Je fais un document word en texte pur, puis je l’organise en passant en mode plan, ctrl-alt-=> etc.. Et c’est là qu’on applique le style depuis un modèle. Simple pour un geek.

Mais apparemment c’est effrayant pour le wordien, et microsoft a peu à peu caché ces fonctions, pour dire allez y modifiez vos caractères un à un, je ne vais pas supprimer vos efforts de fourmis…

C’est surtout quand on reprend un texte, ou qu’on change de charte graphique (et de nom de société..) . Ou plus glorieux quand on a écrit sa doc en MarkDown et qu’on veut la mettre dans word (markdownpad, export html to clipboard…)

Déjà la partie gestion de style s’est cachée ici :
menu accueil / appliquer les styles / icone styles / icone gérer les styles / importer/exporter
c’est là qu’on copie les bon styles dans son document.

Maintenant la touche magique (qui n’est pas dans les menus) et que j’ai trouvé dans http://www.techhive.com/article/260668/10_microsoft_word_style_secrets.html?page=2

Clear formatting and reapply original style : CTRL-SPACE CTRL-Q

sélectionner tout le texte et faire ctrl-espace (clear formatting), ctrl-q (original style) miracle on se croit dans une CSS.

Pocket

ce site ne possède pas de certificat de clé publique

sur Google Chrome on peut voir que le site “ne possède pas de certificat de clé publique”,
le cadenas est gris, avec un petit triangle jaune.
J’ai encore plus fouillé, et encore appris un peu du monde SSL  :
1/ c’est une erreur de traductions coté googlechrome,
(un glissement sémantique ?)
https://productforums.google.com/forum/#!topic/chrome-fr/7ohvzv2WSTg
ce site n’a pas de “public audit record”
2/”public audit record” WTF?
il s’agit du niveau d’authentification du SSL
http://security.stackexchange.com/questions/52834/what-exactly-does-it-mean-when-chrome-reports-a-certificate-does-not-have-publi
ma copine d’il y a dix ans de TBS l’expliquait bien :
http://www.tbs-certificats.com/authentification.html
ici le certificat est validé par Gandi, qui lui-même est validé par un validateur public (comodo)
son authentification (nom de personne, de société) n’est pas validé directement par une autorité publique.
firefox l’indique par “Ce site web ne fournit pas d’informations sur son propriétaire.”
et google par “identité non validée”
les cadenas de ssl (ou cadenas sur fond vert) sont obtenus avec
des certificats extended validation (EV), (gandi-business)
plus long avec envoi de copie de papiers officiels etc (et donc plus cher…)
(j’ai aussi un site avec le même niveau de certificat mais il s’affiche avec un https barré rouge, pas compris)

 

Pocket

demi-cadratin et tiret Word : why copy paste command line from MS-WORD with dashes fail

Word devient de plus en plus évolué, il remplace les tirets par les signes typographiques évolués qu’il faut. Dont les tirets.

http://fr.wikipedia.org/wiki/Tiret

copier coller depuis word génère

# keytool -list –v -keystore tomcat.jks
Unrecognized command: –v

c’est invisible pour qui ne voit pas l’hexadécimal

[root@h0l1ice11t conf]# echo "keytool -list –v ..."|od -cx
0000000 k e y t o o l   - l i s t   342 200 
      656b 7479 6f6f 206c 6c2d 7369 2074 80e2
0000020 223 v  
      7693 

pour cooorriger …..
* dans word, désactiver tout automatisme
menu file / option / verification / option auto-correction ….
uncheck outrageously
* replace – by – [sic]
il y une option pour saisir ‘tiret-demi-cadratin’
the option : “Plus>>” “special” “tiret demi cadratin” (what’s the name in english?)

use MD (markdown)

Pocket

prefix variable

petite bug

 

def gdflib_stinsta(param,action)
execute "actioninstanceparamappli" do
action :run
command "ls"
end

la fonction était un peu plus longue, en réduisant on voit assez vite que la confusion vient de la variable d’entrée action identique à l’élément de langage action.

Le problème qui me chagrine dans ruby, autant que dans java, python C et d’autres c’est que le langage n’a pas imposé un préfique aux variables. Perl et php imposent un $ (un @, un _, un % en perl et un peu en ruby mais pas assez). C’est assez mauvais, je ne comprends pas comment on a pu autoriser à revenir en arrière sur la séparation entre les variables(données) et le langage(programme). Alors qu’on sépare view, model, controller, data, events. Même si tout ça c’est des variables (functions as variables).

Bon ok dans ce cas c’est un mélange de scopes de variables locales et globales (action) qui aurait du générer un warning.

N’empêche.

 

Pocket

Chef.io, j’ai glissé …

Wha le flou artistique de chef.

Apparemment au vu des fichiers, c’est un tas de json, lus par du ruby, et exécuté pour installer des trucs. Il y a des librairies chef pour ça.

Sauf que,
ça n’installe pas. ça crée un script d’installation. nuance.
on s’en aperçoit assez vite quand les prints et les if ne se font pas au même moment que ls actions.

Ces librairies chef ce sont les actions d’installations.
toute la partie qui est faite avant concerne la lecture des jsons (et tous les map select merge qu’on imagine), et les blocks chef (file, command, rubyblock..) sont les morceaux exécutés plus tard, au moment de la phase ‘action’.

Il faut donc repenser le script en deux temps. Anyway.

 

Pocket

LD_LIBRARY_PATH annoyances

Hey, mais on n’a pas besoin de ld_library_path ?

pourtant j’avais codé un élégant script :

#reorder front path items matching ie(PATH,/opt:/usr:/sbin:/bin) R_PATH

reorderpath()
{
A_PATH=$1
P_BEFORES=$2
A_PATH=`echo "$A_PATH"|sed -e 's/::/:/g' -e 's/^://' -e 's/:$//'`
if [ "$A_PATH" = "" ];then return;fi
if [ "$P_BEFORES" = "" ];then return;fi
for P_BEFORE in `echo $P_BEFORES|sed -e 's/:/ /g'`;do
R_PATH=""
for I_PATH in `echo $A_PATH|sed -e 's/:/ /g'`;do
J_PATH=`echo $I_PATH|sed -e "s:^$P_BEFORE::"`
if [ "$I_PATH" = "$J_PATH" ];then
R_PATH="$R_PATH:$I_PATH"
else
R_PATH="$I_PATH:$R_PATH"
fi
done
R_PATH=`echo "$R_PATH"|sed -e 's/::/:/g' -e 's/^://' -e 's/:$//'`
A_PATH=$R_PATH
done
}

mais sur AIX, impossible de concilier chef-solo et rpm

reorderpath $LD_LIBRARY_PATH /usr:/lib:/opt/freeware

ça met rpm en premier, rpm marche, mais pas chef-solo qui prend les libs (zlib) de /lib au lieu de /opt/chef/embedded ;

vice versa, rpm a besoin des libs zlib de /lib ;

et comme rpm est lancé par chef, ils devraient partager le même LD_LIBRARY_PATH.

je croyais ça insolube, eh ben non :

dans les fichiers compilés, il y a en dur la localisation de la lib.

Why LD_LIBRARY_PATH is bad says :

  1. Never ever set LD_LIBRARY_PATH globally.
  2. If you must ship binaries that use shared libraries and want to allow your clients to install the program outside a ‘standard’ location, do one of the following:
    • Ship your binaries as .o files, and as part of the install process relink them with the correct installation library path. (like oracle..)
    • Ship executables with a very long “dummy” run-time library path, and as part of the install process use a binary editor to substitute the correct install library path in the executable. (whaou, hacky!+1!)
  3. If you are forced to set LD_LIBRARY_PATH, do so only as part of a wrapper.

 

so (redhat/solaris/aix):

unset LD_LIBRARY_PATH LD_RUN_PATH LIBPATH

 

Pocket

mysql replication repairing script

mysql replication repairing script

Ah je ne vous ai pas montré le script pour réparer ma réplication mysql  :
à lancer sur le backup qui a foiré.
* copie fichier de la base à froid
* on trouve à quel redo/pos on peut reprendre (c’est là l’astuce)
* après y a plus qu’à refaire la conf de réplication

#####my_repl_bk2rp.sh
 
#!/bin/sh
echo "quand la repl. foire, faire repartir de zero"
echo "copie le bk vers la replication, ok?"
read "ok"
 
/etc/init.d/mysqld stop
 
#merci à www.rsnapshot.org génial
rsync -e ssh -va --delete serveurdesauvegarde:/backup/hourly.0/mysql /home/
#replay, just to be sure...
rsync -e ssh -va --delete serveurdesauvegarde:/backup/hourly.0/mysql /home/
 
/etc/init.d/mysqld start
 
cd /repertoire/mysql
 
lastredo=$(tail -n 1 redo*.index|sed -e 's:^.*/::')
 
lastredopos=$(mysqlbinlog $lastredo|grep end_log_pos|tail -n 1|sed -e 's/^.*end_log_pos *//' -e 's/ .*$//')
 
mysql -pmotdepasseenclair <
CHANGE MASTER TO \
MASTER_HOST='masterserver', \
MASTER_USER='slave', \
MASTER_PASSWORD='passduuserslave', \
MASTER_LOG_FILE='$lastredo', \
MASTER_LOG_POS=$lastredopos;
START SLAVE;
EOT
 
tail /var/log/mysqld.log
sleep 1
echo "my_repl_check.sh"
mysql -u root -pmotdepasse <
 
show slave hosts \G;
show slave status \G;
show master status \G;
EOT

et ça marche !!
quand on perd la réplication, on galère pour retrouver comment on fait pour la rebrancher,
surtout avec le stress, t le risque de perdre encore plus. pff. chouette script, merci moi-même.

Pocket