]> git.llucax.com Git - software/sercom.git/blob - sercom/validators.py
ABM curso
[software/sercom.git] / sercom / validators.py
1 # vim: set et sw=4 sts=4 encoding=utf-8 :
2
3 from turbogears.validators import *
4
5 class ParseError(ValueError): pass
6
7 def params_to_list(params):
8     r"""Parsea un string de forma similar al bash, separando por espacios y
9     teniendo en cuenta comillas simples y dobles para agrupar. Para poner
10     comillas se puede usar el \ como caracter de escape (\' y \") y también
11     interpreta \n y \t. Devuelve una lista con los parámetros encontrados.
12     >>> param2seq('--prueba')
13     ['--prueba']
14     >>> params_to_list('--prueba larga "con espacios"')
15     ['--prueba', 'larga', 'con espacios']
16     >>> params_to_list(u'''"con enter\\nentre 'comillas \\"dobles\\"'" --unicode''')
17     [u'con enter\nentre \'comillas "dobles"\'', u'--unicode']
18     >>> params_to_list('"archivo\\tseparado\\tpor\\ttabs" -h')
19     ['archivo\tseparado\tpor\ttabs', '-h']
20     """
21     # Constantes
22     SEP, TOKEN, DQUOTE, SQUOTE = ' ', None, '"', "'"
23     seq = []
24     buff = ''
25     escape = False
26     state = SEP
27     if not params: return seq
28     for c in params:
29         # Es un caracter escapado
30         if escape:
31             if c == 'n':
32                 buff += '\n'
33             elif c == 't':
34                 buff += '\t'
35             else:
36                 buff += c
37             escape = False
38             continue
39         # Es una secuencia de escape
40         if c == '\\':
41             escape = True
42             continue
43         # Si está buscando espacios
44         if state == SEP:
45             if c == SEP:
46                 continue
47             else:
48                 state = TOKEN # Encontró
49         if state == TOKEN:
50             if c == DQUOTE:
51                 state = DQUOTE
52                 continue
53             if c == SQUOTE:
54                 state = SQUOTE
55                 continue
56             if c == SEP:
57                 state = SEP
58                 seq.append(buff)
59                 buff = ''
60                 continue
61             buff += c
62             continue
63         if state == DQUOTE:
64             if c == DQUOTE:
65                 state = TOKEN
66                 continue
67             buff += c
68             continue
69         if state == SQUOTE:
70             if c == SQUOTE:
71                 state = TOKEN
72                 continue
73             buff += c
74             continue
75         raise ParseError, 'Invalid syntax'
76     if state == DQUOTE or state == SQUOTE:
77         raise ParseError, 'Missing closing quote %s' % state
78     if buff:
79         seq.append(buff)
80     return seq
81
82 class ParamsValidator(UnicodeString):
83     def validate_python(self, value, state):
84         try:
85             params_to_list(value)
86         except ParseError, e:
87             raise Invalid(str(e), value, state)
88