我不想刮一个网站,这需要我登录。我决定用Jsoup来做这件事。我遇到了麻烦"翻译"这段代码正确地适用于Clojure:
Connection.Response loginForm = Jsoup.connect("**url**")
.method(Connection.Method.GET)
.execute();
如果没有在我的Clojure代码中指定类Connection.Response
,则连接具有类jsoup.helper.HttpConnect
,它缺少会话中的cookie所需的方法。
到目前为止,我已经提出了以下Clojure代码:
(import (org.jsoup Jsoup Connection
Connection$Response Connection$Method))
(do
(def url "*URL*")
(def res (doto (org.jsoup.Jsoup/connect url)
(.data "username" "*USERNAME*")
(.data "password" "*PASSWORD")
(.method Connection$Method/POST)
(.execute)))
(type res))
答案 0 :(得分:5)
问题是你在doto
使用->
线程宏:
(let [url "*URL*"]
(-> url
(org.jsoup.Jsoup/connect)
(.data "username" "*USERNAME*")
(.data "password" "*PASSWORD*")
(.method "Connection$Method/POST)
(.execute)))
当您需要设置一个Java对象时,通常会使用 doto
表单,该对象提供类似于setter的方法,返回void
并阻止您使用线程。
(doto (SomeClass.)
(.setA 1)
(.setB 2)
(.execute))
转换为:
(let [obj (SomeClass.)]
(.setA obj 1)
(.setB obj 2)
(.execute obj)
obj)
正如您所看到的,doto
没有返回最后一个方法调用的结果,但是作为第一个参数提供的对象(在这种情况下为SomeClass
对象)。因此,您当前的代码将返回由Jsoup/connect
方法(jsoup.helper.HttpConnect
发出通知时)创建的对象,而不是Connection.Response
方法调用的execute()
结果。
您需要的是:
(-> (SomeClass.)
(.withA 1)
(.withB 2)
(.execute))
其中with*
是返回this
而不是void
的构建器方法。
上述线程表相当于:
(.execute
(.withB
(.withA
(SomeClass.)
1)
2))