我正在尝试从库中加载两个名称空间“spurious-aws-sdk-helper”(顺便说一下,我在本地安装 - 这是我在部署到Clojars之前测试它)。我正在从if
语句中加载名称空间。
加载名称空间后,我调用一个由加载的名称空间之一提供的函数。
问题是当通过lein ring server
执行代码时,我收到一个Java异常,通知我我正在尝试访问的命名空间不可用。
但是如果我运行lein repl
然后(use 'spurious-clojure-example.routes.home)
相关的顶级命名空间;然后(require '[spurious-aws-sdk-helper.core :as core])
命名空间 - 就像我稍后将链接的代码演示一样 - 然后命名空间将可用,随后对函数的调用不会出错?
我不确定这是否是误导性的错误之一,实际上它不是我试图要求的命名空间问题,但是内部的问题是什么?但如果这是真的,那么为什么在lein repl
内自己手动调用呢?
(ns spurious-clojure-example.routes.home
(:use [amazonica.aws.s3])
(:require [compojure.core :refer :all]
[environ.core :refer [env]]
[spurious-clojure-example.views.layout :as layout]))
(if (env :debug)
(do
(require '[spurious-aws-sdk-helper.core :as core])
(require '[spurious-aws-sdk-helper.utils :refer [endpoint cred]])
(core/configure {:s3 "test-bucket4"
:sqs "test-queue4"
:ddb (slurp "./resources/config/schema.yaml")})))
(def bucket-path "news-archive/dev/election2014-council_title")
(def content
(apply str (line-seq
(clojure.java.io/reader
(:object-content
(get-object (cred (endpoint :spurious-s3)) :bucket-name "shared" :key bucket-path))))))
(defn home []
(layout/common [:h1 content]))
(defroutes home-routes
(GET "/" [] (home)))
(core/configure ...)
调用触发Java异常,说“核心”命名空间不可用。但是从lein repl
运行以下代码可以正常工作......
(use 'spurious-clojure-example.routes.home)
(require '[spurious-aws-sdk-helper.core :as core])
(core/configure ...rest of code...)
更新1 :
只是为了澄清我已经更新了代码如下......
(when (env :debug)
(require '[spurious-aws-sdk-helper.core :as core])
(require '[spurious-aws-sdk-helper.utils :refer [endpoint cred]])
(core/configure
{:s3 "test-bucket7"
:sqs "test-queue9"
:ddb (slurp "./resources/config/schema.yaml")}))
...当在REPL中运行它时,它可以正常工作。
问题在于通过lein ring server
运行时。
我开始在这里阅读(ns-resolve)
:http://technomancy.us/143
但它建议的解决方案:(ns-resolve 'core 'configure)
不起作用;它只是引发了Unable to resolve symbol: core in this context
错误。
答案 0 :(得分:2)
尝试:
(when true ; also tried with false
(require '[clojure.string :as str])
(str/split "Clojure is awesome!" #" "))
=> No such namespace: str
我也有点惊讶,因为if
和when
应该只评估适当分支的表达式主体,而不是触及其他表达式。我没想到假的命名空间错误。
更令人惊讶的是,我没想到命名空间错误也是如此。我猜这是一些java编译事情,甚至在代码评估之前就试图解析命名空间。我不知道原因的具体细节。
至于你应该做什么,这段代码很时髦,我从来没有想过或看到有人在做类似的事情。除非有一些特定的理由这样做,解决方案很简单:将您的需求推到ns
的最顶层。没有必要改变其他任何东西。
答案 1 :(得分:2)
我使用lein new compojure-app
创建了一个应用,当:debug
值为真时,需要clojure.string :as str
,然后再将某些内容打印到shell。
以下代码通过lein ring server
运行。我使用:debug
值true
和false
对其进行了测试。我在您的示例中看到,您使用environ
因此,我将{:debug true}
或{:debug false}
放入.lein-env
。
(ns integralist.handler (:require [compojure.core :refer [defroutes routes]] [ring.middleware.resource :refer [wrap-resource]] [ring.middleware.file-info :refer [wrap-file-info]] [hiccup.middleware :refer [wrap-base-url]] [compojure.handler :as handler] [compojure.route :as route] [integralist.routes.home :refer [home-routes]] [environ.core :refer [env]])) (when (env :debug) (require '[clojure.string :as str])) (when (env :debug) (defn it-works! [] (println "It works!:" (str/split "Clojure is Awesome" #" ")))) (defn init [] (println "integralist is starting") (when (env :debug) (it-works!))) (defn destroy [] (println "integralist is shutting down")) (defroutes app-routes (route/resources "/") (route/not-found "Not Found")) (def app (-> (routes home-routes app-routes) (handler/site) (wrap-base-url)))