Bonjour, je cherche actuellement à automatiser ma comptabilité informatique à l'aide de Python, pour cela je voulais utiliser le package ezodf qui de ce que j'ai lu permet de modifier des tableurs au format ods facilement.
J'ai développé ( un bien grand mot ) le code qui me permet de lire mes tableurs d'entrées, celui qui me permet de lire le tableur de sortie, malheureusement le code pour écrire dans le tableur de sortie ne fonctionne pas, et ce exclusivement sur le tableur de sortie que je demande

Je viens donc demander si ici quelqu'un a déjà utilisé cette librairie ou au moins pense pouvoir m'aider à résoudre ce problème d'écriture.

Maintenant pour la partie technique:

La version python que j'utilise : Python 3.4.2 (default, Oct 8 2014, 10:45:20) on linux (64 bits).
J'utilise Pyzo 2.3.0 comme IDE de développement, avec ezodf à la version 0.3.2

Les différentes parties de mon programme :

Les fonctions utilitaires et import de librairies
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
 
 
import os
import sys
import shutil
import ezodf
from datetime import datetime
 
rep_fact="./"  #Répertoire des factures (entrée)
rep_stat="./"  #Répertoire des statistiques (sortie)
 
def is_int(p):
    try:
        int(p)
    except ValueError:
        return False
    return True
 
def get_lex(string, dep=0):
    cur = ''
    for i in range(dep,len(string)):
        if string[i] in [' ', '-', '/', '\\']:
            return cur,i
        else:
            cur += string[i]
    return cur, len(string)
 
def get_date(string):
    if is_int(string):
        return -1
    list = []
    curw, i = get_lex(string)
    while i != len(string) or curw != '':
        try:
            list.append(int(curw))
        except ValueError:
            curw = curw.capitalize()
            list.append(curw)
        curw, i = get_lex(string,i+1)
    if len(list) != 3:
        return -1
    else:
        if is_int(list[1]):
            months = ['Janvier', 'Fevrier', 'Mars', 'Avril', 
            'Mai', 'Juin', 'Juillet', 'Aout', 
            'Septembre','Octobre','Novembre','Decembre']
            list[1] = months[list[1]-1]
        list[0],list[2]=list[2],list[0] #On remet la date dans le format "Date Mois Année"
        return list
 
def sec_ecrire(odsFile, sheet, cell, data):
    c = odsFile.sheets[sheet].get_cell(cell)
    c.set_value(data)
    if (lire_donnee(odsFile, sheet, cell) != data):
        print("Write error occur in : "+odsFile.docname+" at "+sheet+" "+cell)
        return -1
    return c.value
 
def ecrire_donnee_stat(fichier, position, donnee): #Ecrire donnee dans le fichier sortie (stat)
    sec_ecrire(fichier, 1, position, donnee)
 
def lire_donnee(fichier,sheet, position):
    sheet = fichier.sheets[sheet]
    value = sheet[position].value
    if value is None:
        return 0
    return sheet[position].value
 
def is_fact_name(string):
    list=[]
    curw,i = get_lex(string)
    while i != len(string) or curw != '':
        try:
            list.append(int(curw))
        except ValueError:
            curw = curw[0].capitalize() + curw[1:]
            list.append(curw)
        curw, i = get_lex(string, i+1)
    if list[1] != "Facture":
        return False
    elif not is_int(list[0]):
        return False
    else:
        return True
Les fonctions de lectures dans les fichiers d'entrée (factures) (données du tableur)

Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
 
def est_facture_normale(fact): #Fonction type : True -> Normale ; False -> Loc
    type = str(lire_donnee(fact, 0, 'I8'))
    if (type.upper().find("LOC") != -1): #Type de la facture
        return False
    else:
        return True
 
def date_arrivee(fact):
    return get_date(lire_donnee(fact,0, 'C13'))
 
def jour_arrivee(fact): #Fonction pour récupérer le jour d'arrivée d'une facture => Fichier ODS
    date = get_date(lire_donnee(fact, 0, 'C13'))
    if date != -1:
        return date[0]
    else:
        return -1
 
def mois_arrivee(fact): #Fonction pour récupérer le mois d'une facture => Fichier ODS
    date = get_date(lire_donnee(fact, 0, 'C13'))
    if date != -1:
        return date[1]
    else:
        return -1
 
def date_depart(fact):
    return get_date(lire_donnee(fact,0, 'C14'))
 
def jour_depart(fact):
    date = get_date(lire_donnee(fact, 0, 'C14'))
    if date != -1:
        return date[0]
    else:
        return -1
 
def mois_depart(fact):
    date = get_date(lire_donnee(fact, 0, 'C14'))
    if date != -1:
        return date[1]
    else:
        return -1
 
def nb_nuitee(fact): #Fonction pour récupérer le nombre de nuitées dans fact => Fichier ODS
    return lire_donnee(fact,0, 'G24')
 
def nb_emplacements(fact): #Fonction pour récupérer le nombre d'emplacement dans fact => Fichier ODS
    return lire_donnee(fact,0, 'D17')
 
def nb_personnes(fact): #Fonction pour récupérer le nombre de personnes dans fact => Fichier ODS
    return lire_donnee(fact,0, 'D20')+lire_donnee(fact,0, 'D21')+lire_donnee(fact,0, 'D22')
 
def pays_fact(fact):
    s= lire_donnee(fact,0, 'H7')
    if is_int(s):
        return ""
    return s
Les fonctions de récupération et sauvegarde des fichiers entrées et sortie

Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
 
def get_stat_file(mois): #Fonction pour ouvrir le fichier Statistiques du mois s'il existe, sinon le créer
    curdir = os.getcwd()
    os.chdir(rep_stat)
    name= "Stat "+mois+" 2017.ods"
    if(os.path.isfile(name)):
        stat_file = ezodf.opendoc(name)
    else:
        stat_file = ezodf.opendoc("Sortie.ods")
        stat_file.saveas(name)
    os.chdir(curdir)
    return stat_file
 
def get_factures(rep, log_file): #Fonction pour récuperer les factures, non traitées, dans le repertoire rep
    files = os.listdir(rep)
    facts = []
    for file in files:
        print("Process file ",file, file=log_file)
        if (not file.endswith('.ods')) or file.endswith('FF.ods'):
            print("\t Not a facture", file=log_file)
            continue
        elif not is_fact_name(os.path.splitext(file)[0]):
            print("\t Not a facture", file=log_file)
            continue
        else:
            print("\t facture", file=log_file)
            fact = ezodf.opendoc(rep+file)
            cond_date = date_arrivee(fact) != -1 and  date_depart(fact) != -1
            cond_mois = mois_arrivee(fact) == mois_depart(fact)
            cond_autre=lire_donnee(fact, 0, 'G27')==lire_donnee(fact,0,'G28')=="Autre"
            cond_pays= pays_fact(fact).upper() in ["PAYS1","PAYS2","PAYS3"]
            if cond_date and cond_mois and cond_autre and cond_pays:
                print("\t\t facture normale !!!!", file=log_file)
                facts.append(fact.docname)
            else:
                print("\t\t facture anormale :", file=log_file)
                if not cond_date:
                    print("\t\t\t Date incorrecte", file=log_file)
                if not cond_mois:
                    print("\t\t\t Mois chevauchant", file=log_file)
                if not cond_autre:
                    print("\t\t\t Données dans Autres", file=log_file)
                if not cond_pays:
                    print("\t\t\t Pays non supporté", file=log_file)
                continue
    return facts
 
def fin_traitement(rep,file, rename): #Sauvegarde, ferme et renomme file si rename == TRUE)
    cur = os.getcwd()
    os.chdir(rep)
    if rename:
        name = file.docname
        file.saveas(os.path.splitext(file.docname)[0]+"FF.ods")
        os.remove(name)
    else:
        file.save()
    os.chdir(cur)
Les fonction d'écriture dans le fichier sortie
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
 
def ecrire_arrivee(fact,stat, log_file): #Fonction pour écrire les données du jour d'arrivée (Colonne selon pays, date)
    date = jour_arrivee(fact)
    p = pays_fact(fact)
    ligne=0
    colonne=0 # Pays1
 
    #Determiner ligne arrivée selon première quinzaine 
    # ou deuxieme quinzaine, et alignement sur notation info
    if date <= 15:
        ligne= (date*2+1) - 1
    else:
        ligne= (date*2+6) - 1
 
    if not est_facture_normale(fact): #Facture LOC
        ligne += 1
 
    emp = nb_emplacements(fact) + lire_donnee(stat,1, (ligne, 2))
    ecrire_donnee_stat(stat, (ligne,2), emp)
    if p == "Pays1":
        colonne = 3
    elif p == "Pays2":
        colonne = 5
    elif p == "Pays3":
        colonne = 7
    else:
        print("Pays inconnu dans la feuille de stat : ", p, file=log_file)
        return -1
 
    pers = nb_personnes(fact) + lire_donnee(stat,1, (ligne, colonne))
    ecrire_donnee_stat(stat, (ligne,colonne), pers)
    return (ligne,colonne)
 
def ecrire_sejour_entier(fact,stat, log_file): # Fonction pour écrire arrivée et nuitée
    date = jour_arrivee(fact)
    pers = nb_personnes(fact)
 
    ligne,colonne = ecrire_arrivee(fact,stat,log_file)
    colonne += 1 # On decale sur la rangée des nuitées
 
    for i in range(0, int(nb_nuitee(fact))):
        total_pers = pers + lire_donnee(stat,1, (ligne, colonne))
        ecrire_donnee_stat(stat, (ligne,colonne), total_pers)
        if (date +i == 16 ): # On passe dans la deuxieme quinzaine
            ligne =37
        else:
            ligne += 2 # On passe au jour d'après dans une quinzaine
    return 0
La fonction principale

Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
 
def main():
    log_file=open("log.txt", "a")
    log_file.write(str(datetime.now())+"\n")
    list=get_factures(rep_fact, log_file)
    mois_precedent=""
    for name in list:
        fact =ezodf.opendoc(name)
        #On récupère en interne : La facture, le fichier stat correspondant.        
        mois_cur = mois_arrivee(fact)
        if mois_precedent == "":
            stat = get_stat_file(mois_cur)
            mois_precedent = mois_cur
        elif mois_cur != mois_precedent:
            fin_traitement(rep_stat, stat, False)
            stat = get_stat_file(mois_cur)
            mois_precedent = mois_cur
        ecrire_sejour_entier(fact,stat, log_file)
        #fin_traitement(rep_fact, fact, True)
        if name == list[len(list)-1]:
            fin_traitement(rep_stat, stat, False)
    log_file.close()
Je fournirais les fichiers ods d'entrée et sortie si besoin, sachant que les cellules que l'on manipule ne contienne que des dates, chiffres, ou chaines de caractères simples.

Merci à vous.