ASDF的compile-bundle-op为何未生成package-inferred-system项目的FASL?
ASDF中package-inferred-system项目无法生成compile-bundle-op的FASL文件问题
现象描述
在传统ASDF项目中,compile-bundle-op和monolithic-compile-bundle-op均可正常生成对应FASL文件:
# compile-bundle-op 生成的FASL <asdf-fasl-project-folder>/<project-name>--system.fasl # monolithic-compile-bundle-op 生成的FASL <asdf-fasl-project-folder>/<project-name>--all-systems.fasl
但采用:package-inferred-system类的项目,仅能通过monolithic-compile-bundle-op生成FASL,compile-bundle-op无对应输出。
复现步骤
需确保两个项目均能被ASDF识别,执行以下shell命令创建测试项目:
mkdir sample-app mkdir sample-app-classic-asdf # 创建package-inferred-system项目 cat << 'EOF' > sample-app/sample-app.asd ;; 使用ASDF的package-inferred-system (defsystem "sample-app" :class :package-inferred-system :depends-on ("sample-app/sample-app")) EOF cat << 'EOF' > sample-app/sample-app.lisp (defpackage :sample-app/sample-app (:nicknames :sample-app) (:use :cl) (:import-from :sample-app/sample-lib :ayy) (:import-from :alexandria :flatten) (:export :ayy-lmao)) (in-package :sample-app/sample-app) (defun lmao () (format t "SAMPLE-APP: Generating 'lmao'~%") "lmao") (defun ayy-lmao () (flatten (list (list (ayy)) (list (lmao))))) EOF cat << 'EOF' > sample-app/sample-lib.lisp (defpackage :sample-app/sample-lib (:use :cl) (:export :ayy :lmao)) (in-package :sample-app/sample-lib) (defun ayy () (format t "SAMPLE-LIB: Generating 'ayy'~%") "ayy") (defun lmao () (format t "SAMPLE-LIB: Generating 'lmao'~%") "lmao") EOF # 创建传统ASDF项目 cat << 'EOF' > sample-app-classic-asdf/sample-app-classic-asdf.asd (defsystem "sample-app-classic-asdf" :depends-on ("alexandria") :components ((:file "sample-lib") (:file "sample-app" :depends-on ("sample-lib")))) EOF cat << 'EOF' > sample-app-classic-asdf/sample-app.lisp (defpackage :sample-app-classic-asdf (:use :cl) (:import-from :sample-lib :ayy) (:import-from :alexandria :flatten) (:export :ayy-lmao)) (in-package :sample-app-classic-asdf) (defun lmao () (format t "SAMPLE-APP: Generating 'lmao'~%") "lmao") (defun ayy-lmao () (flatten (list (list (ayy)) (list (lmao))))) EOF cat << 'EOF' > sample-app-classic-asdf/sample-lib.lisp (defpackage :sample-lib (:use :cl) (:export :ayy :lmao)) (in-package :sample-lib) (defun ayy () (format t "SAMPLE-LIB: Generating 'ayy'~%") "ayy") (defun lmao () (format t "SAMPLE-LIB: Generating 'lmao'~%") "lmao") EOF
验证操作
在Lisp REPL中执行以下命令:
(asdf:load-system "sample-app") (asdf:load-system "sample-app-classic-asdf") (asdf:oos 'asdf:compile-bundle-op "sample-app") (asdf:oos 'asdf:compile-bundle-op "sample-app-classic-asdf")
观察FASL输出目录,sample-app(package-inferred-system项目)无compile-bundle-op生成的FASL文件,而传统项目正常生成。
原因分析
这不是ASDF的bug,而是package-inferred-system的设计特性与compile-bundle-op的行为逻辑共同导致的:
compile-bundle-op的作用是仅编译并打包当前系统的直接组件,不包含依赖的其他系统。package-inferred-system本身没有显式定义的代码组件(比如:file),它的所有功能都依赖于自动生成的子系统(如sample-app/sample-app),这些子系统被视为独立的依赖系统,而非当前系统的直接组件。- 因此,当对顶层的
sample-app系统执行compile-bundle-op时,ASDF找不到需要打包的直接组件,自然不会生成FASL文件。 - 而
monolithic-compile-bundle-op会递归包含当前系统的所有依赖(包括自动生成的子系统),所以能正常生成包含全部代码的FASL。
解决方案
如果需要为package-inferred-system项目生成对应compile-bundle-op的FASL,直接针对具体的子系统执行操作即可:
(asdf:oos 'asdf:compile-bundle-op "sample-app/sample-app")
这样会生成对应子系统代码的FASL文件。
内容的提问来源于stack exchange,提问作者Sebastian Carlos
相关产品推荐
相关产品推荐

