source: tags/arb-6.0/SL/PTCLEAN/ptclean.cxx

Last change on this file was 11060, checked in by westram, 11 years ago
File size: 6.0 KB
Line 
1// ================================================================= //
2//                                                                   //
3//   File      : ptclean.cxx                                         //
4//   Purpose   : prepare db for ptserver/ptpan                       //
5//                                                                   //
6//   Coded by Ralf Westram (coder@reallysoft.de) in September 2011   //
7//   Institute of Microbiology (Technical University Munich)         //
8//   http://www.arb-home.de/                                         //
9//                                                                   //
10// ================================================================= //
11
12#include "ptclean.h"
13#include <arbdbt.h>
14#include <arb_progress.h>
15#include <arb_diff.h>
16
17#define pt_assert(cond) arb_assert(cond)
18
19class EntryRemover : virtual Noncopyable {
20    // deletes all entries from DB, which are of no use for PTSERVER
21
22    GBDATA         *gb_main;
23    GB_transaction  ta;
24    Servertype      type;
25    char           *ali_name;
26
27    mutable arb_progress progress;
28
29    enum Need {
30        NONE,
31        ALL,
32        SOME_OF_ROOT,
33        SOME_OF_SPECIES_DATA,
34        SOME_OF_EXTENDED_DATA,
35        SOME_OF_SPECIES,
36        SOME_OF_EXTENDED,
37        SOME_OF_ALI_CONTAINER, // below species or SAI
38    };
39
40    Need data_needed(GBDATA *gbd, const char *keyname, Need from) const {
41        switch (from) {
42            case SOME_OF_ROOT:
43                if (strcmp(keyname, GB_SYSTEM_FOLDER)== 0) return ALL;
44                if (strcmp(keyname, "genom_db")      == 0) return ALL;
45                if (strcmp(keyname, "gene_map")      == 0) return ALL;
46                if (strcmp(keyname, "species_data")  == 0) return SOME_OF_SPECIES_DATA;
47                if (strcmp(keyname, "extended_data") == 0) return SOME_OF_EXTENDED_DATA;
48                if (strcmp(keyname, "presets")       == 0) return ALL;
49                break;
50
51            case SOME_OF_SPECIES_DATA:
52                if (strcmp(keyname, "species") == 0) {
53                    progress.inc();
54                    return SOME_OF_SPECIES;
55                }
56                break;
57
58            case SOME_OF_EXTENDED_DATA:
59                if (strcmp(keyname, "extended") == 0) {
60                    const char *sainame = GBT_read_name(gbd);
61                    if (strcmp(sainame, "ECOLI") == 0) return SOME_OF_EXTENDED; 
62                    if (strcmp(sainame, "HELIX") == 0) return SOME_OF_EXTENDED;
63                    if (strcmp(sainame, "HELIX_NR") == 0) return SOME_OF_EXTENDED;
64                }
65                break;
66
67            case SOME_OF_SPECIES:
68            case SOME_OF_EXTENDED:
69                if (from == SOME_OF_SPECIES) {
70                    if (strcmp(keyname, "abspos") == 0) return ALL;
71                }
72                if (strcmp(keyname, "name")      == 0) return ALL;
73                if (strcmp(keyname, "acc")       == 0) return ALL;
74                if (strcmp(keyname, "full_name") == 0) return ALL;
75                if (strcmp(keyname, ali_name)    == 0) return SOME_OF_ALI_CONTAINER;
76                break;
77
78            case SOME_OF_ALI_CONTAINER:
79                if (strcmp(keyname, "data") == 0) return ALL;
80                break;
81
82            case NONE: pt_assert(0); break;
83            case ALL:  pt_assert(0); break;
84        }
85
86        return NONE;
87    }
88
89    GB_ERROR del_child(GBDATA *gb_entry, const char *keyname, Need from) {
90        GB_ERROR error = 0;
91        Need     need  = data_needed(gb_entry, keyname, from);
92        switch (need) {
93            case NONE: error = GB_delete(gb_entry); break;
94            case ALL:  break;
95            default:   error = del_subentries(gb_entry, need); break;
96        }
97        return error;
98    }
99    GB_ERROR del_subentries(GBDATA *gb_father, Need from) {
100        GB_ERROR error = 0;
101        if (!GB_is_temporary(gb_father)) {
102            GBDATA *gb_next_child = NULL;
103            for (GBDATA *gb_child = GB_child(gb_father); gb_child && !error; gb_child = gb_next_child) {
104                gb_next_child = GB_nextChild(gb_child);
105                const char *key = GB_read_key_pntr(gb_child);
106                error           = del_child(gb_child, key, from);
107            }
108        }
109        return error;
110    }
111
112public:
113    EntryRemover(Servertype type_, GBDATA *gb_main_)
114        : gb_main(gb_main_),
115          ta(gb_main),
116          type(type_),
117          ali_name(GBT_get_default_alignment(gb_main)),
118          progress("Remove unused database entries", GBT_get_species_count(gb_main))
119    {}
120    ~EntryRemover() {
121        free(ali_name);
122        progress.done();
123    }
124
125    GB_ERROR del_unwanted_entries() { return del_subentries(gb_main, SOME_OF_ROOT); }
126};
127
128inline GB_ERROR clean_ptserver_database(GBDATA *gb_main, Servertype type) {
129    return EntryRemover(type, gb_main).del_unwanted_entries();
130}
131
132GB_ERROR cleanup_ptserver_database(GBDATA *gb_main, Servertype type) {
133    GB_ERROR error    = GB_request_undo_type(gb_main, GB_UNDO_NONE);
134    if (!error) {
135        GB_push_my_security(gb_main);
136        error = clean_ptserver_database(gb_main, type);
137        GB_pop_my_security(gb_main);
138    }
139    return error;
140}
141// --------------------------------------------------------------------------------
142
143#ifdef UNIT_TESTS
144#ifndef TEST_UNIT_H
145#include <test_unit.h>
146#endif
147#include <arb_file.h>
148
149void TEST_SLOW_ptclean() {
150    GB_shell    shell;
151    GBDATA     *gb_main = GB_open("TEST_pt_src.arb", "rw");
152    const char *saveas  = "TEST_pt_cleaned.arb";
153
154    TEST_REJECT_NULL(gb_main);
155    TEST_EXPECT_NO_ERROR(cleanup_ptserver_database(gb_main, PTSERVER));
156    TEST_EXPECT_NO_ERROR(GB_save_as(gb_main, saveas, "a"));
157    GB_close(gb_main);
158
159// #define TEST_AUTO_UPDATE
160#if defined(TEST_AUTO_UPDATE)
161    TEST_COPY_FILE("TEST_pt_cleaned.arb", "TEST_pt_cleaned_expected.arb");
162#else
163    TEST_EXPECT_TEXTFILES_EQUAL("TEST_pt_cleaned.arb", "TEST_pt_cleaned_expected.arb");
164#endif
165    TEST_EXPECT_ZERO_OR_SHOW_ERRNO(GB_unlink(saveas));
166}
167
168#endif // UNIT_TESTS
169
170// --------------------------------------------------------------------------------
171
Note: See TracBrowser for help on using the repository browser.