从Racket中的REPL发出HTTP GET

Ben*_*Ben 13 scheme http racket read-eval-print-loop

我觉得我错过了一些东西,但是在仔细阅读了net/url的文档并且一般地进行了探讨后,我无法找到从交互式提示中发出GET请求的方法.基本上,我想模仿我的python工作流来寻找一个网站:

response = urlopen("http://www.someurl.com")
Run Code Online (Sandbox Code Playgroud)

在Racket中这是可行的吗?

Gre*_*ott 13

使用call/input-url有一些优点:

  • 您不需要自己关闭端口.
  • 即使有异常,端口也会关闭.
  • 它的第三个参数是(input-port? -> any/c)- 也就是说,一个函数接受input-port并返回任何东西.除了你自己编写的函数之外,这可能是一个已定义的函数,如port->string,read-html-as-xml等等.

例如:

(call/input-url (string->url "http://www.google.com/")
                get-pure-port
                port->string)
Run Code Online (Sandbox Code Playgroud)

注意:当我输入这个答案时,我注意到Óscar编辑了他的重定向.我的类似编辑将是:

(call/input-url (string->url "http://www.google.com/")
                (curry get-pure-port #:redirections 4)
                port->string)
Run Code Online (Sandbox Code Playgroud)

当然,在REPL中频繁输入任何一种方式仍然相当冗长.因此Óscar建议定义自己的url-open功能是一个很好的建议.call/input-url我认为,实施它将是更可取的.


Ósc*_*pez 7

试试这个:

(require net/url)

(define input (get-pure-port (string->url "http://www.someurl.com")))
(define response (port->string input))
(close-input-port input)
Run Code Online (Sandbox Code Playgroud)

现在response变量将包含来自服务器的http响应.更好的是,在程序中打包上面,还注意到我添加了允许的最大重定向数:

(define (urlopen url)
  (let* ((input (get-pure-port (string->url url) #:redirections 5))
         (response (port->string input)))
    (close-input-port input)
    response))

(urlopen "http://www.someurl.com") ; this will return the response
Run Code Online (Sandbox Code Playgroud)

编辑:

关注@ GregHendershott的优秀建议(详见他的答案),这是实现所需功能的另一种更强大的方法:

(define (urlopen url)
  (call/input-url
   (string->url url)
   (curry get-pure-port #:redirections 5)
   port->string))
Run Code Online (Sandbox Code Playgroud)