2013-10-11 20 views
5

Sto lavorando con un output di comando restituito come stringa di un hash di Ruby. (Da qualcosa chiamato mcollective).Conversione di una stringa di hash di Ruby in un dizionario Python

Ecco una stringa esempio che sto ricevendo:

{:changes=>{"total"=>0},  :events=>{"failure"=>0, "success"=>0, "total"=>0},  :version=>  {"puppet"=>"2.7.21 (Puppet Enterprise 2.8.1)", "config"=>1381497648},  :time=>  {"filebucket"=>0.000287,  "cron"=>0.00212,  "package"=>0.398982,  "exec"=>0.001314,  "config_retrieval"=>5.60761618614197,  "anchor"=>0.001157,  "service"=>0.774906,  "total"=>9.85111718614197,  "host"=>0.002662,  "user"=>0.063606,  "file"=>2.998467,  "last_run"=>1381497660},  :resources=>  {"skipped"=>6,  "failed_to_restart"=>0,  "out_of_sync"=>0,  "failed"=>0,  "total"=>112,  "restarted"=>0,  "scheduled"=>0,  "changed"=>0}} 

Sono in grado di scrivere un mini parser per questo, ma sarebbe un compito laborioso. Qualcuno sa di una libreria o di uno snippet di codice che potrebbe convertire questo per me in un dizionario Python?

Se pensi che dovrei solo analizzarlo, tutti i suggerimenti sono ben accetti.

+1

Un hack rapida sarebbe quella di sostituire solo => con: e: [a-z] + con "\ 1" e quindi chiamare ast.literal_eval o json.loads. Ciò non sarebbe corretto poiché ignora i valori letterali stringa, ma potrebbe essere abbastanza buono per ora. – Antimony

+0

Secondo i loro documenti http://docs.puppetlabs.com/mcollective/reference/basic/basic_cli_usage.html possono anche esportare JSON: '-j' flag. – georg

+0

Non nella versione im in corso purtroppo. Ma sì, sarebbe meglio – joeButler

risposta

4

In realtà non era male scrivere qualcosa di abbastanza buono per le mie esigenze. Non è la cosa più carina, ma lo farà per me.

# Sometimes MCO gives us a ruby hash as a string, We can coerce this into json then into dictionary 
def convert_hash_to_dict(self,ruby_hash): 
    dict_str = ruby_hash.replace(":",'"') # Remove the ruby object key prefix 
    dict_str = dict_str.replace("=>",'" : ') # swap the k => v notation, and close any unshut quotes 
    dict_str = dict_str.replace('""','"') # strip back any double quotes we created to sinlges 
    return json.loads(dict_str) 
3

Avete considerato l'utilizzo di Ruby per serializzare questo in JSON? In questo modo è possibile serializzarlo con la libreria JSON di Python.

Se questo non è un'opzione, è possibile definire un parser linguaggio strutturato su misura con relativa facilità usando questa libreria: https://pypi.python.org/pypi/Parsley

6

Si può facilmente convertirlo in JSON utilizzando il seguente comando:

ruby -e 'require "json"; puts JSON.generate({:ruby_hash => "whatever etc..."})' 

Poi usa la libreria JSON di Python per analizzarla.

+0

Questa è una possibilità, - mi richiede di garantire un interprete rubino sul sistema, cosa che non sempre avviene. – joeButler

Problemi correlati