]> git.donarmstrong.com Git - cran2deb.git/blob - branch/multisys/R/db.R
82fa1d45a1dcb227d121dc8419ed0480d2128f9c
[cran2deb.git] / branch / multisys / R / db.R
1
2 db_start <- function() {
3     drv <- dbDriver('SQLite')
4     con <- dbConnect(drv, dbname=file.path(cache_root,'cran2deb.db'))
5     if (!dbExistsTable(con,'sysreq_override')) {
6         dbGetQuery(con,paste('CREATE TABLE sysreq_override ('
7                   ,' depend_alias TEXT NOT NULL'
8                   ,',r_pattern TEXT PRIMARY KEY NOT NULL'
9                   ,')'))
10     }
11     if (!dbExistsTable(con,'debian_dependency')) {
12         dbGetQuery(con,paste('CREATE TABLE debian_dependency ('
13                   ,' id INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL'
14                   ,',alias TEXT NOT NULL'
15                   ,',build INTEGER NOT NULL'
16                   ,',debian_pkg TEXT NOT NULL'
17                   ,',UNIQUE (alias,build,debian_pkg)'
18                   ,')'))
19     }
20     if (!dbExistsTable(con,'forced_depends')) {
21         dbGetQuery(con,paste('CREATE TABLE forced_depends ('
22                   ,' r_name TEXT NOT NULL'
23                   ,',depend_alias TEXT NOT NULL'
24                   ,',PRIMARY KEY (r_name,depend_alias)'
25                   ,')'))
26     }
27     if (!dbExistsTable(con,'license_override')) {
28         dbGetQuery(con,paste('CREATE TABLE license_override ('
29                   ,' name TEXT PRIMARY KEY NOT NULL'
30                   ,',accept INT NOT NULL'
31                   ,')'))
32     }
33     if (!dbExistsTable(con,'license_hashes')) {
34         dbGetQuery(con,paste('CREATE TABLE license_hashes ('
35                   ,' name TEXT NOT NULL'
36                   ,',sha1 TEXT PRIMARY KEY NOT NULL'
37                   ,')'))
38     }
39     if (!dbExistsTable(con,'database_versions')) {
40         dbGetQuery(con,paste('CREATE TABLE database_versions ('
41                   ,' version INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL'
42                   ,',version_date INTEGER NOT NULL'
43                   ,',base_epoch INTEGER NOT NULL'
44                   ,')'))
45         db_add_version(con,1,0)
46     }
47     if (!dbExistsTable(con,'packages')) {
48         dbGetQuery(con,paste('CREATE TABLE packages ('
49                   ,' package TEXT PRIMARY KEY NOT NULL'
50                   ,',latest_r_version TEXT'
51                   ,')'))
52     }
53     if (!dbExistsTable(con,'builds')) {
54         dbGetQuery(con,paste('CREATE TABLE builds ('
55                   ,' id INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL'
56                   ,',system TEXT NOT NULL'
57                   ,',package TEXT NOT NULL'
58                   ,',r_version TEXT NOT NULL'
59                   ,',deb_epoch INTEGER NOT NULL'
60                   ,',deb_revision INTEGER NOT NULL'
61                   ,',db_version INTEGER NOT NULL'
62                   ,',date_stamp TEXT NOT NULL'
63                   ,',scm_revision TEXT NOT NULL'
64                   ,',success INTEGER NOT NULL'
65                   ,',log TEXT'
66                   ,',UNIQUE(package,system,r_version,deb_epoch,deb_revision,db_version)'
67                   ,')'))
68     }
69     return(con)
70 }
71
72 db_stop <- function(con,bump=F) {
73     if (bump) {
74         db_bump(con)
75     }
76     dbDisconnect(con)
77 }
78
79 db_quote <- function(text) {
80     return(paste('\'', gsub('([\'"])','\\1\\1',text),'\'',sep=''))
81 }
82
83 db_now <- function() {
84     return(as.integer(gsub('-','',Sys.Date())))
85 }
86
87 db_cur_version <- function(con) {
88     return(as.integer(dbGetQuery(con, 'SELECT max(version) FROM database_versions')[[1]]))
89 }
90
91 db_base_epoch <- function(con) {
92     return(as.integer(dbGetQuery(con,
93         paste('SELECT max(base_epoch) FROM database_versions'
94              ,'WHERE version IN (SELECT max(version) FROM database_versions)'))[[1]]))
95 }
96
97 db_get_base_epoch <- function() {
98     con <- db_start()
99     v <- db_base_epoch(con)
100     db_stop(con)
101     return(v)
102 }
103
104 db_get_version <- function() {
105     con <- db_start()
106     v <- db_cur_version(con)
107     db_stop(con)
108     return(v)
109 }
110
111 db_add_version <- function(con, version, epoch) {
112     dbGetQuery(con,paste('INSERT INTO database_versions (version,version_date,base_epoch)'
113               ,'VALUES (',as.integer(version),',',db_now(),',',as.integer(epoch),')'))
114 }
115
116 db_bump <- function(con) {
117     db_add_version(con,db_cur_version(con)+1, db_base_epoch(con))
118 }
119
120 db_bump_epoch <- function(con) {
121     db_add_version(con,db_cur_version(con)+1, db_base_epoch(con)+1)
122 }
123
124 db_sysreq_override <- function(sysreq_text) {
125     con <- db_start()
126     results <- dbGetQuery(con,paste(
127                     'SELECT DISTINCT depend_alias FROM sysreq_override WHERE'
128                             ,db_quote(tolower(sysreq_text)),'LIKE r_pattern'))
129     db_stop(con)
130     if (length(results) == 0) {
131         return(NULL)
132     }
133     return(results$depend_alias)
134 }
135
136 db_add_sysreq_override <- function(pattern,depend_alias) {
137     con <- db_start()
138     results <- dbGetQuery(con,paste(
139                      'INSERT OR REPLACE INTO sysreq_override'
140                     ,'(depend_alias, r_pattern) VALUES ('
141                     ,' ',db_quote(tolower(depend_alias))
142                     ,',',db_quote(tolower(pattern))
143                     ,')'))
144     db_stop(con,TRUE)
145 }
146
147 db_sysreq_overrides <- function() {
148     con <- db_start()
149     overrides <- dbGetQuery(con,paste('SELECT * FROM sysreq_override'))
150     db_stop(con)
151     return(overrides)
152 }
153
154 db_get_depends <- function(depend_alias,build=F) {
155     con <- db_start()
156     results <- dbGetQuery(con,paste(
157                     'SELECT DISTINCT debian_pkg FROM debian_dependency WHERE'
158                     ,db_quote(tolower(depend_alias)),'= alias'
159                     ,'AND',as.integer(build),'= build'))
160     db_stop(con)
161     return(results$debian_pkg)
162 }
163
164 db_add_depends <- function(depend_alias,debian_pkg,build=F) {
165     con <- db_start()
166     results <- dbGetQuery(con,paste(
167                      'INSERT OR REPLACE INTO debian_dependency'
168                     ,'(alias, build, debian_pkg) VALUES ('
169                     ,' ',db_quote(tolower(depend_alias))
170                     ,',',as.integer(build)
171                     ,',',db_quote(tolower(debian_pkg))
172                     ,')'))
173     db_stop(con,TRUE)
174 }
175
176 db_depends <- function() {
177     con <- db_start()
178     depends <- dbGetQuery(con,paste('SELECT * FROM debian_dependency'))
179     db_stop(con)
180     return(depends)
181 }
182
183 db_get_forced_depends <- function(r_name) {
184     con <- db_start()
185     forced_depends <- dbGetQuery(con,
186                 paste('SELECT depend_alias FROM forced_depends WHERE'
187                      ,db_quote(r_name),'= r_name'))
188     db_stop(con)
189     return(forced_depends$depend_alias)
190 }
191
192 db_add_forced_depends <- function(r_name, depend_alias) {
193     if (!length(db_get_depends(depend_alias,build=F)) &&
194         !length(db_get_depends(depend_alias,build=T))) {
195         fail('Debian dependency alias',depend_alias,'is not know,'
196                   ,'yet trying to force a dependency on it?')
197     }
198     con <- db_start()
199     dbGetQuery(con,
200             paste('INSERT OR REPLACE INTO forced_depends (r_name, depend_alias)'
201                  ,'VALUES (',db_quote(r_name),',',db_quote(depend_alias),')'))
202     db_stop(con,TRUE)
203 }
204
205 db_forced_depends <- function() {
206     con <- db_start()
207     depends <- dbGetQuery(con,paste('SELECT * FROM forced_depends'))
208     db_stop(con)
209     return(depends)
210 }
211
212 db_license_override_name <- function(name) {
213     con <- db_start()
214     results <- dbGetQuery(con,paste(
215                     'SELECT DISTINCT accept FROM license_override WHERE'
216                             ,db_quote(tolower(name)),'= name'))
217     db_stop(con)
218     if (length(results) == 0) {
219         return(NULL)
220     }
221     return(as.logical(results$accept))
222 }
223
224 db_add_license_override <- function(name,accept) {
225     notice('adding',name,'accept?',accept)
226     if (accept != TRUE && accept != FALSE) {
227         fail('accept must be TRUE or FALSE')
228     }
229     con <- db_start()
230     results <- dbGetQuery(con,paste(
231                      'INSERT OR REPLACE INTO license_override'
232                     ,'(name, accept) VALUES ('
233                     ,' ',db_quote(tolower(name))
234                     ,',',as.integer(accept)
235                     ,')'))
236     db_stop(con,TRUE)
237 }
238
239 db_license_override_hash <- function(license_sha1) {
240     con <- db_start()
241     results <- dbGetQuery(con,paste(
242                      'SELECT DISTINCT accept FROM license_override'
243                     ,'INNER JOIN license_hashes'
244                     ,'ON license_hashes.name = license_override.name WHERE'
245                     ,db_quote(tolower(license_sha1)),'= license_hashes.sha1'))
246     db_stop(con)
247     if (length(results) == 0) {
248         return(NULL)
249     }
250     return(as.logical(results$accept))
251 }
252
253 db_license_overrides <- function() {
254     con <- db_start()
255     overrides <- dbGetQuery(con,paste('SELECT * FROM license_override'))
256     hashes    <- dbGetQuery(con,paste('SELECT * FROM license_hashes'))
257     db_stop(con)
258     return(list(overrides=overrides,hashes=hashes))
259 }
260
261 db_add_license_hash <- function(name,license_sha1) {
262     if (is.null(db_license_override_name(name))) {
263         fail('license',name,'is not know, yet trying to add a hash for it?')
264     }
265     notice('adding hash',license_sha1,'for',name)
266     con <- db_start()
267     dbGetQuery(con,paste(
268          'INSERT OR REPLACE INTO license_hashes'
269         ,'(name, sha1) VALUES ('
270         ,' ',db_quote(tolower(name))
271         ,',',db_quote(tolower(license_sha1))
272         ,')'))
273     db_stop(con,TRUE)
274 }
275
276
277 db_update_package_versions <- function() {
278     con <- db_start()
279     for (package in available[,'Package']) {
280         dbGetQuery(con, paste('INSERT OR REPLACE INTO packages (package,latest_r_version)'
281                              ,'VALUES (',db_quote(package)
282                              ,',',db_quote(available[package,'Version']),')'))
283     }
284     db_stop(con)
285 }
286
287 db_record_build <- function(package, deb_version, log, success=F) {
288     con <- db_start()
289     dbGetQuery(con,paste('INSERT OR REPLACE INTO builds'
290                         ,'(package,system,r_version,deb_epoch,deb_revision,db_version,success,date_stamp,scm_revision,log)'
291                         ,'VALUES'
292                         ,'(',db_quote(package)
293                         ,',',db_quote(which_system)
294                         ,',',db_quote(version_upstream(deb_version))
295                         ,',',db_quote(version_epoch(deb_version))
296                         ,',',db_quote(version_revision(deb_version))
297                         ,',',db_cur_version(con)
298                         ,',',as.integer(success)
299                         ,',',db_quote(format(Sys.time(),'%a, %d %b %Y %H:%M:%S %z'))
300                         ,',',db_quote(scm_revision)
301                         ,',',db_quote(paste(log, collapse='\n'))
302                         ,')'))
303     db_stop(con)
304 }
305
306 db_builds <- function(pkgname) {
307     # returns all successful builds
308     con <- db_start()
309     build <- dbGetQuery(con, paste('SELECT * FROM builds'
310                        ,'WHERE success = 1'
311                        ,'AND system =',db_quote(which_system)
312                        ,'AND package =',db_quote(pkgname)))
313     db_stop(con)
314     if (length(build) == 0) {
315         return(NULL)
316     }
317     build$success <- as.logical(build$success)
318     return(build)
319 }
320
321 db_latest_build <- function(pkgname) {
322     con <- db_start()
323     build <- dbGetQuery(con, paste('SELECT * FROM builds'
324                        ,'NATURAL JOIN (SELECT package,max(id) AS max_id FROM builds'
325                        ,              'WHERE system =',db_quote(which_system)
326                        ,              'GROUP BY package) AS last'
327                        ,'WHERE id = max_id'
328                        ,'AND builds.package =',db_quote(pkgname)))
329     db_stop(con)
330     if (length(build) == 0) {
331         return(NULL)
332     }
333     build$success <- as.logical(build$success)
334     return(build)
335 }
336
337 db_latest_build_version <- function(pkgname) {
338     build <- db_latest_build(pkgname)
339     if (is.null(build)) {
340         return(NULL)
341     }
342     return(version_new(build$r_version, build$deb_revision, build$deb_epoch))
343 }
344
345 db_latest_build_status <- function(pkgname) {
346     build <- db_latest_build(pkgname)
347     if (is.null(build)) {
348         return(NULL)
349     }
350     return(list(build$success,build$log))
351 }
352
353 db_outdated_packages <- function() {
354     con <- db_start()
355     packages <- dbGetQuery(con,paste('SELECT packages.package FROM packages'
356                ,'LEFT OUTER JOIN ('
357                # extract the latest attempt at building each package
358                ,      'SELECT * FROM builds'
359                ,      'NATURAL JOIN (SELECT package,max(id) AS max_id FROM builds'
360                ,                    'WHERE system =',db_quote(which_system)
361                ,                    'GROUP BY package) AS last'
362                ,      'WHERE id = max_id) AS build'
363                ,'ON build.package = packages.package'
364                # outdated iff:
365                # - there is no latest build
366                ,'WHERE build.package IS NULL'
367                # - the database has changed since last build
368                ,'OR build.db_version < (SELECT max(version) FROM database_versions)'
369                # - the debian epoch has been bumped up
370                ,'OR build.deb_epoch < (SELECT max(base_epoch) FROM database_versions'
371                ,                        'WHERE version IN ('
372                ,                            'SELECT max(version) FROM database_versions))'
373                # - the latest build is not of the latest R version
374                ,'OR build.r_version != packages.latest_r_version'
375                ))$package
376     db_stop(con)
377     return(packages)
378 }
379