Loading an Optional Component with ASDF - common-lisp

How do you tell ASDF to process a component file only if it exists (so it doesn't generate an error if it doesn't exist yet).
(asdf:defsystem "my-system"
:components ((:file "utilities")
(:file "temp-file" :depends-on ("utilities"))))
My workaround is using a reader macro #. on (probe-file "temp-file") but can't get that to work.

I think what you really are trying to do is have ASDF merely warn you instead of bringing up the debugger during compilation errors. Change *compile-file-warnings-behaviour* and *compile-file-failure-behaviour*, and read the section on error handling in the manual.
The rest of this answer is how to check for a whole system. You could package the maybe-to-load files into their own systems and do it this way below.
From the ASDF Manual section 6.3.8.
6.3.8 Weakly depends on
We do NOT recommend you use this feature.
So you could just use it anyway. Like this:
(defpackage :foo-system
(:use :cl :asdf))
(in-package :foo-system)
(defsystem foo
:description "The main package that maybe loads bar if it exists."
:weakly-depends-on (:bar)
:components ((:file "foo")))
Simple right?
Here is what they recommend:
If you are tempted to write a system foo that weakly-depends-on a
system bar, we recommend that you should instead write system foo in a
parametric way, and offer some special variable and/or some hook to
specialize its behaviour; then you should write a system foo+bar that
does the hooking of things together.
I've never seen one of these in the wild, probably because it is a horrible confusing mess to do it that way.
(defpackage :bar-system
(:use :cl :asdf))
(in-package :bar-system)
(defsystem bar
:description "The package that maybe exists and is needed by foo."
:components ((:file "bar")))
(defpackage :foo+bar-system
(:use :cl :asdf))
(in-package :foo+bar-system)
(defsystem foo+bar
:version "0.1.0"
:description "Hook together foo and bar."
:author "Spenser Truex <web#spensertruex.com>"
:serial t
:components ((:file "foo+bar")))
(defpackage :foo-system
(:use :cl :asdf))
(in-package :foo-system)
(defsystem foo
:description "The main package that maybe loads bar if it exists."
:depends-on (:foo+bar)
:components ((:file "foo")))

Related

asdf can't find package

I'm trying to scaffold a Common Lisp project using the instructions I found here: http://turtleware.eu/posts/Tutorial-Working-with-FiveAM.html. I cloned the repo and followed the instructions in the document so that my .asd file, my package.lisp file, and my tests/package.lisp and tests/main.lisp files matched the instructions. I ran (asdf:test-system 'quasirpg) and everything worked fine.
I copied this example project to my real working folder and did a search and replace to change all instances of quasirpg to foo. I ran (asdf:test-system 'foo) and the REPL gave me an error that the package "FOO-TESTS" couldn't be found.
Now, I re-ran (asdf:test-system 'quasirpg), which worked before, and the REPL is giving me the same error, that the package "QUASIRPG-TESTS" can't be found.
Can anybody please explain what's going on here and how I get my asdf package manager to find the test packages?
Thank you.
;;;; foo.asd
(asdf:defsystem #:foo
:description "Part of the FiveAM tutorial"
:author "Tomek 'uint' Kurcz"
:license "GPLv3"
:serial t
:components ((:file "package")
(:file "foo"))
:in-order-to ((test-op (test-op "foo/tests"))))
(asdf:defsystem #:foo/tests
:depends-on (:foo :fiveam)
:components ((:module "tests"
:serial t
:components ((:file "package")
(:file "main"))))
:perform (test-op (o s)
(uiop:symbol-call :fiveam :run! 'foo-tests:all-tests)))
;;;; tests/package.lisp
(defpackage #:foo-tests
(:use :cl :fiveam)
(:export #:run! #:all-tests))
;;;; tests/main.lisp
(in-package #:foo-tests)
(def-suite all-tests
:description "The master suite of all foo tests.")
;; tests continue below
I'm not a fan of automated testing like fiveam, but your problem is the reference in the :perform to the symbol foo-tests:all-tests which is in a package that won't exist until after the system is loaded. Use find-symbol instead of quote
The following script runs to completion on my machine (I started with the snippets in your post):
DIR=~/quicklisp/local-projects/foo
mkdir $DIR
cd $DIR
cat >foo.asd <<EOF
(asdf:defsystem #:foo
:description "Part of the FiveAM tutorial"
:author "Tomek 'uint' Kurcz"
:license "GPLv3"
:serial t
:components ((:file "package")
(:file "foo"))
:in-order-to ((test-op (test-op "foo/tests"))))
(asdf:defsystem #:foo/tests
:depends-on (:foo :fiveam)
:components ((:module "tests"
:serial t
:components ((:file "package")
(:file "main"))))
:perform (test-op (o s)
(uiop:symbol-call :fiveam
:run!
(find-symbol "ALL-TESTS"
"FOO"))))
EOF
touch package.lisp
touch foo.lisp
mkdir tests
cat >tests/package.lisp <<EOF
(defpackage #:foo-tests
(:use :cl :fiveam)
(:export #:run! #:all-tests))
EOF
cat >tests.main.lisp <<EOF
(in-package #:foo-tests)
(def-suite all-tests
:description "The master suite of all foo tests.")
EOF
sbcl --eval '(asdf:load-system "foo")'
Avoiding this kind of symbol shenaniganery is a pain and why I wouldn't generally touch the asdf testing machinery, I just make functions that can be run from the repl.

ASDF Does Not Load Common Lisp Files

I am currently building a project in Common Lisp and am using the ASDF. However, I am experiencing some difficulties. Namely, when I run asdf:compile-system, it seems to compile. I can then do asdf:load-system successfully. However, some functions located in some of the files remain undefined. To make them known, I have to manually navigate to that file and compile it.
Here is the declaration for the system. Could someone tell me what I am doing incorrectly?
(defsystem "xxx-xxxx"
:version "0.1.0"
:author ""
:license ""
:depends-on ("cl-mongo" "hunchentoot" "clack" "ningle" "cl-json" "hermetic" "lack-middleware-session" "cl-markup")
:components ((:module "src"
:components
((:file "packages")
(:file "lisp-utils")
(:file "xxx-xxxx" :depends-on ("packages"))
(:file "database" :depends-on ("packages"))
(:file "database-config" :depends-on ("packages"))
(:file "server" :depends-on ("packages"))
(:file "clack" :depends-on ("packages"))
(:file "routes/activities" :depends-on ("packages"))
(:file "route-processors" :depends-on ("packages")))))
:description ""
:long-description
#.(read-file-string
(subpathname *load-pathname* "README.markdown"))
:in-order-to ((test-op (test-op "xxx-xxxx-test"))))
In particular, I am having an issue with the file routes/activities and possibly route-processors.
Given my experience with asdf the only off thing of your system definition is the "routes/activities" file as subfolders are defined as modules. This file should fix your problem:
(defsystem "xxx-xxxx"
:version "0.1.0"
:author ""
:license ""
:depends-on ("cl-mongo"
"hunchentoot"
"clack"
"ningle"
"cl-json"
"hermetic"
"lack-middleware-session"
"cl-markup")
:components ((:module "src"
:components
((:file "packages")
(:file "lisp-utils")
(:file "xxx-xxxx"
:depends-on ("packages"))
(:file "database"
:depends-on ("packages"))
(:file "database-config"
:depends-on ("packages"))
(:file "server"
:depends-on ("packages"))
(:file "clack"
:depends-on ("packages"))
(:module "routes"
:components ((:file "activities"))
:depends-on ("packages"))
(:file "route-processors"
:depends-on ("packages")))))
:description ""
:long-description
#.(read-file-string
(subpathname *load-pathname* "README.markdown"))
:in-order-to ((test-op (test-op "xxx-xxxx-test"))))
Addressing your last comment. The reason for the exception is that dependencies are resolved within the list the parent of the dependency resides in. So if you say that "activities" depends on "packages" but have "activities" in a module asdf will search for packages in that module/subfolder and due to its non-existance not find it. Whether it is presumptuous or not is irrelevant, this is how it works. It also makes sense as a module usually describes a logical coherent unit and thus dependencies are expected to be similar for that unit, else you might want to rethink your project structure.

Start ESS process in R script

I've got the following problem in my Emacs (i am a complete newby and way far from LISP programming): When i open a .R file, no ESS process is starting. This is a problem because i want to configure TAB-completion and see R Documentation in scripts.
This is the Error message:"No ESS process associated with current buffer
"
This is only the case in .R files. When starting inferior ESS i dont have this problem. (hope i got this right: M-x R starts a process und Emacs and is therefore called inferior?)
My .emacs is cofigured like this:
(require 'auto-complete)
(require 'auto-complete-config)
(require 'ess-stata-mode)
(require 'ess-eldoc)
(add-hook 'inferior-ess-mode-hook 'ess-use-eldoc)
(autoload 'R-mode "ess-site.el" "" t)
(add-to-list 'auto-mode-alist '("\\.R\\'" . R-mode))
Those two lines above should start ESS in script, shouldn't they?
(global-auto-complete-mode t)
(setq ess-tab-complete-in-script t)
(setq ess-use-auto-complete 't)
(setq ess-use-eldoc 't)
(setq ess-use-company 't)
And I included ElDoc and AC to get Autocompletion.
I want to get to see the Documentation of R in Emacs.
I'd really appreciate your help. What did I miss?
Greetings and Thanks in advance

spacemacs ess knitr doesn't work with Rmd files

I really want to switch from RStudio to Spacemacs with ess layer. However I can't get it to work. I have the following in my dotfile:
dotspacemacs-configuration-layers
'(
html
;; ----------------------------------------------------------------
;; Example of useful layers you may want to use right away.
;; Uncomment some layer names and press <SPC f e R> (Vim style) or
;; <M-m f e R> (Emacs style) to install them.
;; ----------------------------------------------------------------
markdown
helm
ess
auto-completion
better-defaults
emacs-lisp
git
polymode
mu4e
;; markdown
;; (shell :variables
org
;; shell-default-height 30
;; shell-default-position 'bottom)
spell-checking
syntax-checking
;; version-control
)
I have the following packages.el in my .emacs.d private folder copied with thanks from github.
;;; packages.el --- polymode layer packages file for Spacemacs.
;;
;; Copyright (c) 2012-2016 Sylvain Benner & Contributors
;;
;; Author: Walmes Zeviani & Fernando Mayer
;; URL: https://github.com/syl20bnr/spacemacs
;;; Code:
(defconst polymode-packages
'(polymode))
(defun polymode/init-polymode ()
(use-package polymode
:mode (("\\.Rmd" . Rmd-mode))
:init
(progn
(defun Rmd-mode ()
"ESS Markdown mode for Rmd files"
(interactive)
(require 'poly-R)
(require 'poly-markdown)
(R-mode)
(poly-markdown+r-mode))
))
)
;;; packages.el ends here
Syntax highlighting and code completeion etc are working fine but if I try and send code chunks to REPL i get 'wrong type argument stringp nil' error with both Rmd and Rmv files.
emacs 25.2.1 with spacemacs
fresh install on both mac and linux with no other config loaded. Own .emacs has been deleted
some functions seem to work but not like they should e.g. eval-buffer will just send the current code chunk to REPL
Very grateful for any help.
It was a bit tricky to me to make it works with Rmd. Have you try with a simple .R file to see if it works?
This is what I currently have in mi .emacs file for the Rmd files
;; MARKDOWN
(add-to-list 'auto-mode-alist '("\\.md" . poly-markdown-mode))
;; R modes
(add-to-list 'auto-mode-alist '("\\.Snw" . poly-noweb+r-mode))
(add-to-list 'auto-mode-alist '("\\.Rnw" . poly-noweb+r-mode))
(add-to-list 'auto-mode-alist '("\\.Rmd" . poly-markdown+r-mode))
;; polymode
(setq load-path (append '("/home/fer/.emacs.d/elpa/polymode-20170307.322"
"/home/farce/.emacs.d/polymode/modes") load-path))
(require 'poly-R)
(require 'poly-markdown)
(add-to-list 'auto-mode-alist '("\\.Rmd" . poly-markdown+r-mode))

ESS and R from spacemacs

I hope this isn't a really dumb question, but I've used emacs in the past with ESS to edit R files and run them in an R process. I'd like to do the same with spacemacs. As far as I can read and grasp, it just means I have to enable the ess layer in the .spacemacs file, and that's it.
So in my .spacemacs I have the following:
'(
;; ----------------------------------------------------------------
;; Example of useful layers you may want to use right away.
;; Uncomment some layer names and press <SPC f e R> (Vim style) or
;; <M-m f e R> (Emacs style) to install them.
;; ----------------------------------------------------------------
;; auto-completion
;; better-defaults
emacs-lisp
;; git
markdown
javascript
colors
haskell
c-c++
ess
html
;; org
;; (shell :variables
;; shell-default-height 30
;; shell-default-position 'bottom)
;; spell-checking
;; syntax-checking
;; version-control
)
But if I close spacemacs then, and reboot, and try to create say an R file, there's no ess or formatting/colours or anything like that. The same for something like markdown too. All files are just opened in Fundamental mode. I thought spacemacs had layers so you can just add them and it work out of the box. So what am I missing or what should I check? I'm on OSX.
Thanks,
Ben.

Resources