<div dir="ltr"><div class="gmail_extra"><div class="gmail_quote">2014-03-17 22:57 GMT+01:00 Balan Victor <span dir="ltr"><<a href="mailto:balan.victor0@gmail.com" target="_blank">balan.victor0@gmail.com</a>></span>:<br>

<blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex"><div dir="ltr">Ho un array di tuple cosi formate da 3 elementi: (int|float|boolean|string|datetime|..., string, boolean). Es:<div>

<br></div><div>[</div><div> (10, "value >= 1", True),</div><div> ("Ciao", "o in value", True),</div>
<div> (True, "value == False", False),</div><div> (92.5f, "value >= 92.0f", True),</div><div>] <div>Il primo elemento della tupla può essere qualunque tipo o classe di python.</div></div><div>Il secondo elemento è una espressione da applicare sulla tupla e che deve restituire True or False(value si riferisce al primo elemento della tupa)</div>


<div>Il terzo elemento è il risultato dell'operazione appena sopra.</div><div><br></div><div>A intervalli regolari ho bisogno di scorrere l'array sopra e aggiornare il valore del terzo elemento.</div><div>Ho pensato di usare eval in questo modo:</div>


<div><br></div><div>def check_status(value, eval_string):</div><div>  rc =  eval(eval_string)</div><div>  if rc is not bool: raise WrongEvalString()</div><div>  return rc</div><div><br></div><div>Conosco i rischi di eval e vorrei evitare di usarlo però non riesco a trovare nulla di altrettanto semplice e con le stesse potenzialità.</div>


<div><br></div></div></blockquote><div><br></div><div>eval è relativamente sicuro, dato che può eseguire solo espressioni, e non statement completi come exec.</div><div>Lo puoi rendere ancora più sicuro limitando il namespace, ad esempio:</div>
<div><br></div><div><div>def expand_template(template, **kwargs):</div><div>    from string import Template</div><div><br></div><div>    return Template(template).substitute(**kwargs)</div><div><br></div><div>def eval_expression(expr_literal, value):</div>
<div>    expr = expand_template(expr_literal, value=value)</div><div><br></div><div>    return eval(expr, {}, {})</div><div><br></div><div><br></div><div>def check_status(value, eval_string):</div><div>  rc =  eval_expression(eval_string, value)</div>
<div>  if rc is not True:</div><div>      raise WrongEvalString()</div></div><div><br></div><div><div>check_status(10, "$value == 10")</div></div><div><br></div><div>Questo però non basta, devi avere il controllo anche su value, ad esempio accettando solo stringhe secondo un dato protocollo, di cui farai il parsing e validazione.</div>
<div>Il mio protocollo preferito è "Typed NetStrings":</div><div>  "<typeid><len>:<literal></div><div>Ad esempio per un intero:</div><div>  "i3:777"</div><div><br></div><div>tale protocollo è facile da leggere, parsare e validare (perchè verboso)</div>
<div><br></div>
<blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex"><div dir="ltr"><div></div><div>NB: In realtà la stringa che fa la validazione può essere impostata solo da qualcuno di autorizzato quindi il rischio che mi cancelli tutto il fs non ci dovrebbe essere, e non dovrebbero nemmeno fare operazioni del tipo "value ** value" però in ogni caso vorrei trovare qualcosa che mi metta al sicuro da questo tipo di operazioni.</div>
</div></blockquote><div><br></div><div>Riguardo operazioni non autorizzate sei abbastanza al sicuro, grazie al fatto che eval esegue solo espressioni, ed al fatto che valuti solo oggetti a te noti.</div><div>In caso di dubbi, leggi la grammatica di Python per sapere cosa può contenere una espressione.</div>
<div><br></div><div>Riguardo "value ** value" temi un attacco di tipo DoS?</div><div><br></div><div>In questo caso se vuoi limitare anche le possibili espressioni, l'unica alternativa e scriverti un tuo parser, come ti hanno già suggerito.  Dai una occhiata al modulo ast di Python.</div>
<div><br></div><div></div></div><br></div><div class="gmail_extra">Ciao  Manlio</div></div>