Formatter du code
=================
Il est important de pouvoir suivre des règles dans l'écriture de code.
Cela permet notamment une lecture (ou relecture) de code plus simple et de
pouvoir partager avec d'autres développeur le travail réalisé.
Il me parait indispensable lors d'une revue de code d'avoir un code formatté.
Heureusement il existe de nombreux outils qui facilite ce travail.
.. note::
Il est possible de réaliser le "format" de notre code via notre éditeur
préféré **vim**, puisque ce dernier permet de lancer des commandes depuis
son interface
Nous allons traiter les principaux languages que j'utilise
XML
---
Il existe un utilitaire pour traiter du code xml **xmllint**.
Il existe une version windows (non testé) sur le site
http://code.google.com/p/xmllint/
Pour debian son installation est simple
.. code-block:: bash
apt-get install libxml2-utils
Concernant son utilisation, nous avons un fichier nommé **toto.xml** contenant
.. code-block:: xml
ab
on traite le fichier par **xmllin**
.. code-block:: bash
xmllint --format toto.xml --output toto.xml
et on obtient un fichier xml contenant
.. code-block:: xml
a
b
.. note::
xmllint fait beaucoup plus, il peut utiliser un xpath pour faire de la
recherche dans les fichiers xml
.. code-block:: bash
xmllint --xpath "/bookstore/book/price" books.xml
Java
----
Il existe une librairie java externe qui réalise cette tâche: jalopy.
Il est hebergé sur sourceforge et il existe sous forme de plugin pour eclipse
par exemple.
son installation
.. code-block:: bash
wget http://sourceforge.net/projects/jalopy/files/plugin%20console/0.1-1.5rc3/jalopy-console-0.1-1.5rc3.zip/download
mv download jalopy-1.5.zip
unzip jalopy-1.5.zip
cd jalopy-console-0.1-1.5rc3
On peut obtenir le manuel de jalopy sur http://jalopy.sourceforge.net/existing/manual.html
On trouve deux fichier pour lancer jalopy :
- un fichier sh pour linux
- un fichier bat pour windows
mais cela revien à faire
.. code-block:: bash
java -cp lib/jalopy.jar:lib/jalopy-console.jar:lib/log4j.jar:lib/getopt.jar de.hunsicker.jalopy.plugin.console.ConsolePlugin -v
.. note::
on peut faire plus simple concernant cette ligne de commande
.. code-block:: bash
java -classpath lib/* de.hunsicker.jalopy.plugin.console.ConsolePlugin -v
Prenons l'exemple du fichier **test/Test.java** contenant le code
.. code-block:: java
public class Test {
private String x = "hello ";
public String getText(String name) {
string s = x + name;return s;}}
.. note::
ce code est valide, java ne gère pas d'indentation
Nous allons traiter ce fichier par jalopy
.. code-block:: bash
java -cp lib/jalopy.jar:lib/jalopy-console.jar:lib/log4j.jar:lib/getopt.jar de.hunsicker.jalopy.plugin.console.ConsolePlugin test/Test.java
et nous obtenons
.. code-block:: java
public class Test {
private String x = "hello ";
public String getText(String name) {
string s = x + name;
return s;
}
}
On peut traiter un répertoire entier via l'argument
.. code-block:: bash
jalopy -r myDir
On peut aussi faire que le traitement n'écrase pas les originaux
.. code-block:: bash
jalopy -d /otherDir
Afin de rendre l'utilisation plus simple de jalopy on peut:
- placer le soft dans /opt
- ajouter un alias dans son .bashrc
.. code-block:: bash
alias jalopy="java -cp /opt/jalopy/lib/jalopy.jar:/opt/jalopy/lib/jalopy-console.jar:/opt/jalopy/lib/log4j.jar:/opt/jalopy/lib/getopt.jar de.hunsicker.jalopy.plugin.console.ConsolePlugin"
SQL
---
Pour sql on va utiliser un module python nommer sqlparse. Il fonctionne avec
toutes versions de Python supérieur à 2.5
.. code-block:: bash
apt-get install python-pip
pip install sqlparse
Son utilisation est assez simple
.. code-block:: python
import sqlparse
code="SELECT tutu,titi from toto"
r = sqlparse.format(code, reindent=True, keyword_case='upper')
print(r)
Python
------
Python possède son propre outil de contrôle qui valide le code python par
rapport à la norme identifié dans le pep8 de python.
.. code-block:: bash
pip install pep8
pip install autopep8
Son utilisation est assez simple
.. code-block:: python
import pep8
import autopep8
r = autopep8.fix_code(code)
print(r)
Pour la gestion de fichier en Python, XML et SQL sans passer par une console python,
on peut utiliser le code suivant, placé dans le fichier **prettycode.py**
.. code-block:: python
import sys
import locale
from optparse import OptionParser
VERSION="0.2"
PROG="prettycode"
DESCRIPTION="""format code"""
AUTHOR="Frederic Aoustin"
PARAMS_PARSER = {
'sql' : "'reindent' : True, 'keyword_case' : 'upper'",
'python' : "",
'xml' : ""
}
is_Windows = sys.platform.startswith('win')
if is_Windows:
import ctypes
strcpy = ctypes.cdll.msvcrt.strcpy
ocb = ctypes.windll.user32.OpenClipboard #Basic Clipboard functions
ecb = ctypes.windll.user32.EmptyClipboard
gcd = ctypes.windll.user32.GetClipboardData
scd = ctypes.windll.user32.SetClipboardData
ccb = ctypes.windll.user32.CloseClipboard
ga = ctypes.windll.kernel32.GlobalAlloc # Global Memory allocation
gl = ctypes.windll.kernel32.GlobalLock # Global Memory Locking
gul = ctypes.windll.kernel32.GlobalUnlock
GMEM_DDESHARE = 0x2000
if sys.version_info < (3, 0):
str = unicode
import sqlparse
else:
import sqlparse3 as sqlparse
import pep8
import autopep8
import xml.dom.minidom
if __name__ == '__main__':
parser = OptionParser(version="%s %s" % (PROG,VERSION))
parser.description= DESCRIPTION
parser.epilog = AUTHOR
parser.add_option("-i", "--file-in",
dest = "ifile",
help = "file format",
default = None,
type = "string")
parser.add_option("-o", "--file-out",
dest = "ofile",
help = "file formatting",
default = None ,
type = "string")
parser.add_option("-s", "--syntax",
dest = "syntax",
choices = ['sql','python','xml'],
help ="syntax format",
default = "sql",
type = "choice")
parser.add_option("-e", "--encoding",
dest = "encoding",
help = "encoding data (default: %s)" % locale.getdefaultlocale()[1],
default = locale.getdefaultlocale()[1],
type = "string")
parser.add_option("-p", "--other-parameter",
dest = "args",
help = "add parameter for parser (%s)" % ('; '.join([i+' => '+ PARAMS_PARSER[i] for i in PARAMS_PARSER.keys()])) ,
default = None,
type = "string")
try:
(options, args) = parser.parse_args()
if options.args == None:
options.args = PARAMS_PARSER[options.syntax]
exec("args = {%s}" % options.args)
if options.ifile == None:
if is_Windows:
ocb(None)
p_contents = gcd(1)
code = str(ctypes.c_char_p(p_contents).value, options.encoding)
ccb()
else:
raise AttributeError("file in is unknown")
else:
f = open(options.ifile,'r')
code = ''.join(f.readlines())
f.close()
if options.syntax == 'sql':
result_parser = sqlparse.format(code, **args)
if options.syntax == 'python':
result_parser = autopep8.fix_code(code, **args)
if options.syntax == 'xml':
xml = xml.dom.minidom.parseString(code)
result_parser = xml.toprettyxml()
if options.ofile != None:
f = open(options.ofile,'w')#, encoding='utf-8')
f.write(result_parser)
f.close()
else:
print(result_parser)
except Exception as e:
print(parser.error(e))
parser.print_help()
sys.exit(1)
L'utilisation de ce programme est assez simple
.. code-block:: bash
python prettycode -i tutu.py -o tutu.py -s python