关于简单的HTTP的一个简单问题

发布于 2025-02-13 19:20:19 字数 960 浏览 0 评论 0原文

我正在尝试学习Haskell,还有什么比通过转换我已经为Haskell制作的已经存在的程序来学习的方法更好,因为我知道程序的工作原理。

第一步是使简单的HTTP获取请求到为我提供JSON字符串的链接。我一直在挖掘,并且垃圾箱尽可能多地研究Haskell文档,但是我发现Haskell文档显然是……非Haskell程序员无法访问的想法。

我需要取一个链接 - 可以说 https://aur.archlinux.org/rpc/?v=5&Type=search&by = name-desc&; arg; arg; arg; arg = brave

并在该链接上提出get request。在其他语言中,似乎有一种简单的方法可以使该响应的主体作为字符串。在Haskell中,我用字节折断了我的大脑? 因为主要是io”等等。

和“你不能这样做, 呢

{-# LANGUAGE OverloadedStrings #-}
import Network.HTTP.Simple

import qualified Data.ByteString.Char8 as B8

main :: IO ()
main = do
  httpBS "https://aur.archlinux.org/rpc/?v=5&type=search&by=name-desc&arg=brave" >>= B8.putStrLn . getResponseBody

这样做会得到响应并将其作为标准输出,但是我需要将其保存为字符串,还是从bytestring转换它?到一根字符串,以便我可以解析。

如果我听起来很失败,那是因为我很大。

I'm trying to learn haskell, and what better a way than to learn by converting an already existing program I have made over to haskell, since I know how my program works otherwise.

the first step is to make a simple http get request to a link that provides me a JSON string. I have been digging, and dumpster diving through as much haskell documentation as I can, but I am getting the idea that haskell documentation is obviously... not accessible to non-haskell programmers.

I need to take a link- lets say https://aur.archlinux.org/rpc/?v=5&type=search&by=name-desc&arg=brave

and make a get request on that link. In other languages, there seemed to be an easy way to get the body of that response as a STRING. In haskell im wracking my brain with bytestrings? and "you cant do this because main is IO" and etc etc.

I just can't make any sense of it and I want to breach through this accessibility barrier that haskell has because I otherwise love functional programming, I dont wanna program another way!

{-# LANGUAGE OverloadedStrings #-}
import Network.HTTP.Simple

import qualified Data.ByteString.Char8 as B8

main :: IO ()
main = do
  httpBS "https://aur.archlinux.org/rpc/?v=5&type=search&by=name-desc&arg=brave" >>= B8.putStrLn . getResponseBody

Doing this gets the response and outputs it as standard out, but I need to save this as a string, or convert it from a bytestring? to a string so that I can parse it.

If I sound defeated it's because I very much am.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

等你爱我 2025-02-20 19:20:19

有什么比通过转换我已经存在的程序为Haskell学习的方法更好的方法了,因为我知道我的程序是如何工作的。

该策略将鼓励您从原始语言中掌握成语。我猜想您先前的语言不鼓励使用单子,也不懒惰。也许它甚至没有功能,但要点是这实际上可能是一个有害的开始。

我只是无法理解它,我想在此可访问性障碍中突破

学习阅读文档的文档(至少对我来说)很难。了解每个角色实际上很重要。例如,一个bytestring-一个字节数组,或者只是bytes,如果它更好地命名 - 不是一个困难的概念,而是该名称暗示着对人的事物。

如果我听起来很失败,那是因为我很大。

你真接近!想想高级别:

  1. 使用HTTP获取数据
  2. 将数据(或字节)的数据放在结构中。例如,Python使用词典。

您已经做了1,做得很好。与其在一行无点样式的一行中进行所有操作(与一堆操作员一起组成一堆函数),让我们命名我们的中间值,并且每行有一个概念:

#!/usr/bin/env cabal
{- cabal:
    build-depends: base, http-conduit, aeson
-}
{-# LANGUAGE OverloadedStrings #-}

我正在使用Shebang,这样我就可以我开发时Chmod +x file.hs./ file.hs

import Network.HTTP.Simple
import qualified Data.Aeson as Aeson

Haskell中最常见的JSON库是Aeson,我们将使用它来将字节解析到JSON中,就像Python的json.loads一样。

main :: IO ()
main = do
  httpRequest <- parseRequest "https://aur.archlinux.org/rpc/?v=5&type=search&by=name-desc&arg=brave"
  response <- httpLBS httpRequest

你开始很好。请注意,HTTPBS是一类函数,通常http&lt; lyy oppeofresult&gt;,而不是httpget,就像您在Java或Python中看到的那样。该函数在使用request数据类型中的字段中学习是否是get(vs post等)和标题。要获取请求我们解析URL字符串,只需使用parserequest s默认值(这是HTTP GET)即可。

我确实更改为获取懒惰字符串(LBS),因为我知道Aeson库以后使用这些库。这就像迭代器产生字节(直觉,而不是完全准确)。

而不是&gt;&gt; = morefunctions我正在命名中间值响应,因此我们可以使用它并分别查看每个步骤。

  let body = getResponseBody response

从响应中提取身体就像您所拥有的一样,除了单独的表达外。

  let obj = Aeson.decode body :: Maybe Aeson.Object

最大的部分是将字节解码为JSON。希望这是熟悉的,因为太阳下的每种语言都对某种词典/地图/对象进行了解码。在Haskell中,您会发现将其解码到地图上不太常见,而更常见的是定义在JSON中期望具有的结构,然后使用FromJSON类制作该类型的自定义解码例程 - 您不喜欢t 来做到这一点,它带来的概念比刚开始成为初学者时所需的概念要多。

  print obj

我知道这不需要解释。

替代

如果看到文档您可能已经看到(或考虑过搜索页面的JSON)。这可以节省大量时间!

#!/usr/bin/env cabal
{- cabal:
    build-depends: base, http-conduit, aeson
-}
{-# LANGUAGE OverloadedStrings #-}
import Network.HTTP.Simple
import qualified Data.Aeson as Aeson

main :: IO ()
main = do
  response <- httpJSON =<< parseRequest "https://aur.archlinux.org/rpc/?v=5&type=search&by=name-desc&arg=brave"
  let obj = getResponseBody response :: Maybe Aeson.Object
  print obj

what better a way than to learn by converting an already existing program I have made over to haskell, since I know how my program works otherwise.

This strategy will encourage you to carry over idioms from the original language. I'm guessing your prior language didn't encourage use of monads and wasn't lazy. Perhaps it wasn't even functional, but the point is this can actually be a detrimental start.

I just can't make any sense of it and I want to breach through this accessibility barrier

Learning to read documentation is hard in any unknown language (for me at least). Understanding each character is actually rather important. For example, a ByteString - an array of bytes, or just Bytes if it were better named - isn't a hard concept but the name implies things to people.

If I sound defeated it's because I very much am.

You're so close! Think of the high level:

  1. Get the data with an HTTP GET
  2. Parse the data from the string (or bytes) into a structure. Python uses a dictionary, for example.

You did 1 already, nice work. Rather than do everything in a single line in point free style (composing a bunch of functions with a bunch of operators), let's name our intermediate values and have one concept per line:

#!/usr/bin/env cabal
{- cabal:
    build-depends: base, http-conduit, aeson
-}
{-# LANGUAGE OverloadedStrings #-}

I'm using a shebang so I can just chmod +x file.hs and ./file.hs as I develop.

import Network.HTTP.Simple
import qualified Data.Aeson as Aeson

The most common JSON library in Haskell is Aeson, we'll use that to parse the bytes into json much like python's json.loads.

main :: IO ()
main = do
  httpRequest <- parseRequest "https://aur.archlinux.org/rpc/?v=5&type=search&by=name-desc&arg=brave"
  response <- httpLBS httpRequest

You're start is good. Notice httpBS is a class of functions generically http<SomeTypeOfResult> and not httpGet like you might have seen in Java or Python. The function learns if this is a GET (vs POST etc) and the headers using fields in the Request data type. To get a Request we parse the URL string and just use all of parseRequests defaults (which is HTTP GET).

I did change to getting lazy byte strings (LBS) because I know the Aeson library uses those later on. This is something like an iterator that produces bytestrings (for intuition, not entirely accurate).

Rather than >>= moreFunctions I'm naming the intermediate value response so we can use it and look at each step separately.

  let body = getResponseBody response

Extracting the body from the response is just like what you had, except as a separate expression.

  let obj = Aeson.decode body :: Maybe Aeson.Object

The big part is to decode the bytes to JSON. This is hopefully familiar since every language under the sun does json decoding to some sort of dictionary/map/object. In Haskell you'll find it less common to decode to a map and more common to define a structure that is explicit in what you expect to have in the JSON then make a custom decoding routine for that type using the FromJSON class - you don't have to do that, it brings in way more concepts than you'll want when just getting started as a beginner.

  print obj

I know this doesn't need explained.

Alternative

If you saw the documentation you might have seen (or considered searching the page for) JSON. This can save you lots of time!

#!/usr/bin/env cabal
{- cabal:
    build-depends: base, http-conduit, aeson
-}
{-# LANGUAGE OverloadedStrings #-}
import Network.HTTP.Simple
import qualified Data.Aeson as Aeson

main :: IO ()
main = do
  response <- httpJSON =<< parseRequest "https://aur.archlinux.org/rpc/?v=5&type=search&by=name-desc&arg=brave"
  let obj = getResponseBody response :: Maybe Aeson.Object
  print obj
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文