-
Notifications
You must be signed in to change notification settings - Fork 1
/
system.rkt
85 lines (69 loc) · 2.42 KB
/
system.rkt
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
85
#lang racket/base
;; API for making system calls
(require racket/contract)
(provide
(contract-out
[shell
(-> path-string? (or/c path-string? (listof path-string?)) string?)]
;; `(shell cmd arg*)` finds the executable that `cmd` denotes,
;; then invokes the executable with arguments `arg*`.
;; Raises an exception if the executable exists uncleanly,
;; otherwise returns a string containing all output produced by the exe.
[md5sum
(-> path-string? string?)]
;; Compute MD5 hash of the contents of the given file
))
(require
gtp-util
(only-in openssl/md5
md5)
(only-in racket/port
with-output-to-string)
(only-in racket/string
string-trim)
(only-in racket/system
system*))
;; =============================================================================
(define (shell pre-exe pre-cmd)
(define exe (find-exe pre-exe))
(define success? (box #f))
(define cmd* (map path-string->string (if (path-string? pre-cmd) (list pre-cmd) pre-cmd)))
(define str
(with-output-to-string
(lambda ()
(set-box! success? (apply system* exe cmd*)))))
(if (unbox success?)
(string-trim str)
(raise-user-error 'shell "failed to apply '~a' to arguments '~a'" exe cmd*)))
;; find-exe : path-string? -> path-string?
(define (find-exe pre-exe)
(define fep (find-executable-path pre-exe))
(if (path? fep)
fep
(raise-user-error 'shell "cannot find executable '~a', please install and try again" pre-exe)))
(define (md5sum ps)
(call-with-input-file ps md5))
;; =============================================================================
(module+ test
(require rackunit racket/runtime-path (only-in racket/string string-split))
(define-runtime-path a-text-file "README.md")
(unless (or (eq? (system-type 'os) 'windows)
(equal? "true" (getenv "CI")))
(test-case "shell"
(check-regexp-match #rx"^Welcome to Racket"
(shell "racket" '("--version"))))
(test-case "find-exe"
(check-equal?
(find-exe "racket")
(find-executable-path "racket"))
(check-exn exn:fail:user?
(lambda () (find-exe "this-is-not-racket-this-is-sparta"))))
(test-case "md5sum"
(define (check-md5 ps)
(define openssl-md5 (md5sum a-text-file))
(define system-md5 (car (string-split (shell "md5sum" (path->string a-text-file)))))
(check-equal? openssl-md5 system-md5))
(check-md5 a-text-file)
)
)
)