monotone

monotone Mtn Source Tree

Root/cmd_db.cc

1// Copyright (C) 2002 Graydon Hoare <graydon@pobox.com>
2//
3// This program is made available under the GNU GPL version 2.0 or
4// greater. See the accompanying file COPYING for details.
5//
6// This program is distributed WITHOUT ANY WARRANTY; without even the
7// implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
8// PURPOSE.
9
10#include "base.hh"
11#include <iostream>
12#include <utility>
13
14#include "charset.hh"
15#include "cmd.hh"
16#include "database_check.hh"
17#include "revision.hh"
18#include "constants.hh"
19#include "app_state.hh"
20
21using std::cin;
22using std::cout;
23using std::make_pair;
24using std::pair;
25using std::set;
26using std::string;
27
28CMD_GROUP(db, "db", "", CMD_REF(database),
29 N_("Deals with the database"),
30 "");
31
32// Deletes a revision from the local database. This can be used to
33// 'undo' a changed revision from a local database without leaving
34// (much of) a trace.
35
36static void
37kill_rev_locally(app_state& app, string const& id)
38{
39 revision_id ident;
40 complete(app, id, ident);
41 N(app.db.revision_exists(ident),
42 F("no such revision '%s'") % ident);
43
44 //check that the revision does not have any children
45 set<revision_id> children;
46 app.db.get_revision_children(ident, children);
47 N(!children.size(),
48 F("revision %s already has children. We cannot kill it.") % ident);
49
50 app.db.delete_existing_rev_and_certs(ident);
51}
52
53CMD(db_init, "init", "", CMD_REF(db), "",
54 N_("Initializes a database"),
55 N_("Creates a new database file and initializes it."),
56 options::opts::none)
57{
58 N(args.size() == 0,
59 F("no arguments needed"));
60
61 app.db.initialize();
62}
63
64CMD(db_info, "info", "", CMD_REF(db), "",
65 N_("Shows information about the database"),
66 "",
67 options::opts::none)
68{
69 N(args.size() == 0,
70 F("no arguments needed"));
71
72 app.db.info(cout);
73}
74
75CMD(db_version, "version", "", CMD_REF(db), "",
76 N_("Shows the database's version"),
77 "",
78 options::opts::none)
79{
80 N(args.size() == 0,
81 F("no arguments needed"));
82
83 app.db.version(cout);
84}
85
86CMD(db_dump, "dump", "", CMD_REF(db), "",
87 N_("Dumps the contents of the database"),
88 N_("Generates a list of SQL instructions that represent the whole "
89 "contents of the database. The resulting output is useful to later "
90 "restore the database from a text file that serves as a backup."),
91 options::opts::none)
92{
93 N(args.size() == 0,
94 F("no arguments needed"));
95
96 app.db.dump(cout);
97}
98
99CMD(db_load, "load", "", CMD_REF(db), "",
100 N_("Loads the contents of the database"),
101 N_("Reads a list of SQL instructions that regenerate the contents of "
102 "the database. This is supposed to be used in conjunction with the "
103 "output generated by the 'dump' command."),
104 options::opts::none)
105{
106 N(args.size() == 0,
107 F("no arguments needed"));
108
109 app.db.load(cin);
110}
111
112CMD(db_migrate, "migrate", "", CMD_REF(db), "",
113 N_("Migrates the database to a newer schema"),
114 N_("Updates the database's internal schema to the most recent one. "
115 "Needed to automatically resolve incompatibilities that may be "
116 "introduced in newer versions of monotone."),
117 options::opts::none)
118{
119 N(args.size() == 0,
120 F("no arguments needed"));
121
122 app.db.migrate();
123}
124
125CMD(db_execute, "execute", "", CMD_REF(db), "",
126 N_("Executes an SQL command on the database"),
127 N_("Directly executes the given SQL command on the database"),
128 options::opts::none)
129{
130 if (args.size() != 1)
131 throw usage(execid);
132
133 app.db.debug(idx(args, 0)(), cout);
134}
135
136CMD(db_kill_rev_locally, "kill_rev_locally", "", CMD_REF(db), "ID",
137 N_("Kills a revision from the local database"),
138 "",
139 options::opts::none)
140{
141 if (args.size() != 1)
142 throw usage(execid);
143
144 kill_rev_locally(app,idx(args, 0)());
145}
146
147CMD(db_kill_branch_certs_locally, "kill_branch_certs_locally", "", CMD_REF(db),
148 "BRANCH",
149 N_("Kills branch certificates from the local database"),
150 "",
151 options::opts::none)
152{
153 if (args.size() != 1)
154 throw usage(execid);
155
156 app.db.delete_branch_named(cert_value(idx(args, 0)()));
157}
158
159CMD(db_kill_tag_locally, "kill_tag_locally", "", CMD_REF(db), "TAG",
160 N_("Kills a tag from the local database"),
161 "",
162 options::opts::none)
163{
164 if (args.size() != 1)
165 throw usage(execid);
166
167 app.db.delete_tag_named(cert_value(idx(args, 0)()));
168}
169
170CMD(db_check, "check", "", CMD_REF(db), "",
171 N_("Does some sanity checks on the database"),
172 N_("Ensures that the database is consistent by issuing multiple "
173 "checks."),
174 options::opts::none)
175{
176 N(args.size() == 0,
177 F("no arguments needed"));
178
179 check_db(app);
180}
181
182CMD(db_changesetify, "changesetify", "", CMD_REF(db), "",
183 N_("Converts the database to the changeset format"),
184 "",
185 options::opts::none)
186{
187 N(args.size() == 0,
188 F("no arguments needed"));
189
190 build_changesets_from_manifest_ancestry(app);
191}
192
193CMD(db_rosterify, "rosterify", "", CMD_REF(db), "",
194 N_("Converts the database to the rosters format"),
195 "",
196 options::opts::drop_attr)
197{
198 N(args.size() == 0,
199 F("no arguments needed"));
200
201 build_roster_style_revs_from_manifest_style_revs(app);
202}
203
204CMD(db_regenerate_caches, "regenerate_caches", "", CMD_REF(db), "",
205 N_("Regenerates the caches stored in the database"),
206 "",
207 options::opts::none)
208{
209 N(args.size() == 0,
210 F("no arguments needed"));
211
212 regenerate_caches(app);
213}
214
215CMD_HIDDEN(clear_epoch, "clear_epoch", "", CMD_REF(db), "BRANCH",
216 N_("Clears the branch's epoch"),
217 "",
218 options::opts::none)
219{
220 if (args.size() != 1)
221 throw usage(execid);
222
223 app.db.clear_epoch(branch_name(idx(args, 0)()));
224}
225
226CMD(db_set_epoch, "set_epoch", "", CMD_REF(db), "BRANCH EPOCH",
227 N_("Sets the branch's epoch"),
228 "",
229 options::opts::none)
230{
231 if (args.size() != 2)
232 throw usage(execid);
233
234 epoch_data ed(idx(args, 1)());
235 N(ed.inner()().size() == constants::epochlen,
236 F("The epoch must be %s characters") % constants::epochlen);
237 app.db.set_epoch(branch_name(idx(args, 0)()), ed);
238}
239
240CMD(set, "set", "", CMD_REF(variables), N_("DOMAIN NAME VALUE"),
241 N_("Sets a database variable"),
242 N_("This command modifies (or adds if it did not exist before) the "
243 "variable named NAME, stored in the database, and sets it to the "
244 "given value in VALUE. The variable is placed in the domain DOMAIN."),
245 options::opts::none)
246{
247 if (args.size() != 3)
248 throw usage(execid);
249
250 var_domain d;
251 var_name n;
252 var_value v;
253 internalize_var_domain(idx(args, 0), d);
254 n = var_name(idx(args, 1)());
255 v = var_value(idx(args, 2)());
256 app.db.set_var(make_pair(d, n), v);
257}
258
259CMD(unset, "unset", "", CMD_REF(variables), N_("DOMAIN NAME"),
260 N_("Unsets a database variable"),
261 N_("This command removes the variable NAME from domain DOMAIN, which "
262 "was previously stored in the database."),
263 options::opts::none)
264{
265 if (args.size() != 2)
266 throw usage(execid);
267
268 var_domain d;
269 var_name n;
270 internalize_var_domain(idx(args, 0), d);
271 n = var_name(idx(args, 1)());
272 var_key k(d, n);
273 N(app.db.var_exists(k),
274 F("no var with name %s in domain %s") % n % d);
275 app.db.clear_var(k);
276}
277
278CMD(complete, "complete", "", CMD_REF(informative),
279 N_("(revision|file|key) PARTIAL-ID"),
280 N_("Completes a partial identifier"),
281 "",
282 options::opts::verbose)
283{
284 if (args.size() != 2)
285 throw usage(execid);
286
287 bool verbose = app.opts.verbose;
288
289 N(idx(args, 1)().find_first_not_of("abcdef0123456789") == string::npos,
290 F("non-hex digits in partial id"));
291
292 if (idx(args, 0)() == "revision")
293 {
294 set<revision_id> completions;
295 app.db.complete(idx(args, 1)(), completions);
296 for (set<revision_id>::const_iterator i = completions.begin();
297 i != completions.end(); ++i)
298 {
299 if (!verbose) cout << i->inner()() << '\n';
300 else cout << describe_revision(app, *i) << '\n';
301 }
302 }
303 else if (idx(args, 0)() == "file")
304 {
305 set<file_id> completions;
306 app.db.complete(idx(args, 1)(), completions);
307 for (set<file_id>::const_iterator i = completions.begin();
308 i != completions.end(); ++i)
309 cout << i->inner()() << '\n';
310 }
311 else if (idx(args, 0)() == "key")
312 {
313 typedef set< pair<key_id, utf8 > > completions_t;
314 completions_t completions;
315 app.db.complete(idx(args, 1)(), completions);
316 for (completions_t::const_iterator i = completions.begin();
317 i != completions.end(); ++i)
318 {
319 cout << i->first.inner()();
320 if (verbose) cout << ' ' << i->second();
321 cout << '\n';
322 }
323 }
324 else
325 throw usage(execid);
326}
327
328CMD_HIDDEN(test_migration_step, "test_migration_step", "", CMD_REF(db),
329 "SCHEMA",
330 N_("Runs one step of migration on the specified database"),
331 N_("This command migrates the given database from the specified "
332 "schema in SCHEMA to its successor."),
333 options::opts::none)
334{
335 if (args.size() != 1)
336 throw usage(execid);
337 app.db.test_migration_step(idx(args,0)());
338}
339
340// Local Variables:
341// mode: C++
342// fill-column: 76
343// c-file-style: "gnu"
344// indent-tabs-mode: nil
345// End:
346// vim: et:sw=2:sts=2:ts=2:cino=>2s,{s,\:s,+s,t0,g0,^-2,e-2,n-2,p2s,(0,=s:

Archive Download this file

Branches

Tags

Quick Links:     www.monotone.ca    -     Downloads    -     Documentation    -     Wiki    -     Code Forge    -     Build Status