(define datadir "../common/")

(load (string-append datadir "str.scm"))
(load (string-append datadir "woobus.scm"))
(load (string-append datadir "dynload.scm"))
(load (string-append datadir "command.scm"))
(load (string-append datadir "command-compat.scm"))

;read message from the bus
(define (read-message)
  (read-bus-address ('>> (read-bus-message))))

;extract commands from the message
(define (message->commands msg)
  (with-input-from-string msg
    (lambda()
      (let loop ((result '())
		 (cmd (read-command)))
	(if (null? cmd)
	  result
	  (loop (append result (list cmd))
		(read-command)))))))

;filter: split command name, convert args to associative list
(define (prepare-cmds cmds)
  (let loop ((result '())
	     (cmds cmds))
    (cond
      ((null? cmds) result)
      ((not (pair? (car cmds))) (error "invalid command in list"))
      (else
	(let ((current (car cmds)))
	  (loop (append result 
			(list (cons (string-split (sure-string (car current)) #\/)
				    (command-fold acons '() current))))
		(cdr cmds)))))))

;input to easy to use lists
(define (in) (prepare-cmds (message->commands (read-message))))

;default backend for all commands: always answers - "backend not found"
(define (ghost-mariner object action)
  (lambda args  '(error "backend not found")))

;try to load an appropriate backend
;temporary DEMO: always return ghost mariner
(define (load-mariner sym continue)
  (format #t "loading new marnier on board: ~A~%" sym)
  (continue 'ghost-mariner))

(define (resolv-name sym)
  (dynload sym (lambda (sym) (eval sym (current-module))) load-mariner))

;load low-level backend
(define (call-mariner cmd)
    (let ((name (car cmd))
	(args (cdr cmd)))
    (if (not (null? name))
      (let ((mariner (resolv-name (string->symbol (car name))))
	    (action  (assoc 'action args)))
	(if action
	  ((mariner (cdr name) (cdr action)) args)
	  '(error "action field not found" cmd))))))

;process commands from list and autoconvert results
;todo: use fold here for applying multiple answers
;(define (process-command cmd))

