source: project/chicken/branches/hygienic/henrietta.scm @ 11714

Last change on this file since 11714 was 11714, checked in by felix winkelmann, 13 years ago

setup-download fixes; updated manifest

File size: 5.3 KB
Line 
1;;;; henrietta.scm - Server program (CGI) for serving eggs from a repository over HTTP
2;
3; Copyright (c) 2008, The Chicken Team
4; All rights reserved.
5;
6; Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
7; conditions are met:
8;
9;   Redistributions of source code must retain the above copyright notice, this list of conditions and the following
10;     disclaimer.
11;   Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
12;     disclaimer in the documentation and/or other materials provided with the distribution.
13;   Neither the name of the author nor the names of its contributors may be used to endorse or promote
14;     products derived from this software without specific prior written permission.
15;
16; THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS
17; OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
18; AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR
19; CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
20; CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
21; SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
22; THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
23; OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24; POSSIBILITY OF SUCH DAMAGE.
25
26
27(require-library setup-download regex extras utils ports srfi-1 posix)
28
29
30(module main ()
31
32  (import scheme chicken regex extras utils ports srfi-1 posix)
33  (import setup-utils setup-download)
34
35  (define *default-transport* 'svn)
36  (define *default-location* (current-directory))
37  (define *test* #f)
38
39  (define (headers)
40    (print "Connection: close\r\nContent-type: text/plain\r\n\r\n"))
41
42  (define (fail msg . args)
43    (pp `(error ,msg ,@args))
44    (cleanup)
45    (exit 0))
46
47  (define (cleanup)
48    (and-let* ((tmpdir (temporary-directory)))
49      (fprintf (current-error-port) "removing temporary directory `~a'~%" tmpdir)
50      (remove-directory tmpdir)))
51
52  (define (retrieve name version)
53    (let ((dir (handle-exceptions ex 
54                   (fail ((condition-property-accessor 'exn 'message) ex)
55                         ((condition-property-accessor 'exn 'arguments) ex))
56                 (retrieve-extension 
57                  name *default-transport* *default-location*
58                  version #t))))
59      (unless dir 
60        (fail "no such extension or version" name version))
61      (let walk ((dir dir) (prefix "."))
62        (let ((files (directory dir)))
63          (for-each
64           (lambda (f)
65             (let ((ff (string-append dir "/" f))
66                   (pf (string-append prefix "/" f)))
67               (cond ((directory? ff)
68                      (print "\n#|--------------------|# \"" pf "/\" 0")
69                      (walk ff pf))
70                     (else
71                      (print "\n#|--------------------|# \"" pf "\" " (file-size ff))
72                      (display (read-all ff))))))
73           files)))
74      (print "\n#!eof") ) )
75
76  (define (service)
77    (let ((qs (getenv "QUERY_STRING")))
78      (unless qs
79        (error "no QUERY_STRING set"))
80      (let ((m (string-match "[^?]+\\?(.+)" qs))
81            (egg #f)
82            (version #f))
83        (let loop ((qs (if m (cadr m) qs)))
84          (let* ((m (string-search-positions "^(\\w+)=([^&]+)" qs))
85                 (ms (and m (apply substring qs (cadr m))))
86                 (rest (and m (substring qs (cadar m)))))
87            (cond ((not m)
88                   (headers)            ; from here on use `fail'
89                   (cond (*test* 
90                          (fail "test"))
91                         (egg
92                          (retrieve egg version)
93                          (cleanup) )
94                         (else (fail "no extension name specified") ) ))
95                  ((string=? ms "version")
96                   (set! version (apply substring qs (caddr m)))
97                   (loop rest))
98                  ((string=? ms "name")
99                   (set! egg (apply substring qs (caddr m)))
100                   (loop rest))
101                  ((string=? ms "test")
102                   (set! *test* #t)
103                   (loop rest))
104                  (else
105                   (warning "unrecognized query option" ms)
106                   (loop rest))))))))
107 
108
109  (define (usage code)
110    (print #<#EOF
111usage: henrietta [OPTION ...]
112
113  -h   -help                    show this message
114  -l   -location LOCATION       install from given location (default: current directory)
115  -t   -transport TRANSPORT     use given transport instead of default (#{*default-transport*})
116EOF
117);|
118    (exit code))
119
120  (define *short-options* '(#\h #\l #\t))
121
122  (define (main args)
123    (let loop ((args args))
124      (if (null? args)
125          (service)
126          (let ((arg (car args)))
127            (cond ((or (string=? arg "-help") 
128                       (string=? arg "-h")
129                       (string=? arg "--help"))
130                   (usage 0))
131                  ((or (string=? arg "-l") (string=? arg "-location"))
132                   (unless (pair? (cdr args)) (usage 1))
133                   (set! *default-location* (cadr args))
134                   (loop (cddr args)))
135                  ((or (string=? arg "-t") (string=? arg "-transport"))
136                   (unless (pair? (cdr args)) (usage 1))
137                   (set! *default-transport* (string->symbol (cadr args)))
138                   (loop (cddr args)))
139                  ((and (positive? (string-length arg))
140                        (char=? #\- (string-ref arg 0)))
141                   (if (> (string-length arg) 2)
142                       (let ((sos (string->list (substring arg 1))))
143                         (if (null? (lset-intersection eq? *short-options* sos))
144                             (loop (append (map (cut string #\- <>) sos) (cdr args)))
145                             (usage 1)))
146                       (usage 1)))
147                  (else (loop (cdr args))))))))
148
149  (main (command-line-arguments))
150 
151)
Note: See TracBrowser for help on using the repository browser.