;; guile-lib ;; Copyright (C) 2007 Andy Wingo ;; This program is free software; you can redistribute it and/or ;; modify it under the terms of the GNU General Public License as ;; published by the Free Software Foundation; either version 2 of ;; the License, or (at your option) any later version. ;; ;; This program is distributed in the hope that it will be useful, ;; but WITHOUT ANY WARRANTY; without even the implied warranty of ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ;; GNU General Public License for more details. ;; ;; You should have received a copy of the GNU General Public License ;; along with this program; if not, contact: ;; ;; Free Software Foundation Voice: +1-617-542-5942 ;; 59 Temple Place - Suite 330 Fax: +1-617-542-2652 ;; Boston, MA 02111-1307, USA gnu@gnu.org ;;; Commentary: ;; ;; @code{(apicheck)} exports two routines. @code{apicheck-generate} ;; produces a description of the Scheme API exported by a set of modules ;; as an S-expression. @code{apicheck-validate} verifies that the API ;; exported by a set of modules is compatible with an API description ;; generated by @code{apicheck-generate}. ;; ;; It would be nice to have Makefile.am fragments here, but for now, see ;; the Guile-Library source distribution for information on how to ;; integrate apicheck with your module's unit test suite. ;; ;;; Code: (define-module (apicheck) #:use-module (unit-test) #:use-module (oop goops) #:use-module (ice-9 pretty-print) #:use-module ((ice-9 common-list) #:select (uniq)) #:use-module ((srfi srfi-1) #:select (append-map lset-difference)) #:export (apicheck-generate apicheck-validate)) (define (interface module) (case (module-kind module) ((interface) module) (else (error "Invalid API: imported module ~a not an interface" module)))) (define (module-all-uses module) (let ((direct (module-uses module))) (map interface (append direct (apply append (map module-all-uses direct)))))) (define (module-exports module) (module-map (lambda (k v) k) module)) (define (symbolcomp pred) (lambda (a b) (pred (symbol->string a) (symbol->string b)))) (define symbol? (symbolcomp string>?)) (define (symlist? (car a) (car b)) #f) (else (symlist) (list 'class)) ((is-a? val ) (cons 'generic (sort (map method-specializer-names (generic-function-methods val)) symlist