我试图使用F#
下面的代码片断发送异步POST请求火力地堡:特别是下列的操作,这允许匿名登录:F#异步HTTP请求 - 解析JSON响应
https://firebase.google.com/docs/reference/rest/auth/#section-sign-in-anonymously
let makePostRequest (url : string) (requestBody : string) =
let req = WebRequest.CreateHttp url
req.CookieContainer <- new CookieContainer()
req.Method <- "POST"
req.ProtocolVersion <- HttpVersion.Version10
let postBytes = requestBody |> System.Text.Encoding.ASCII.GetBytes
req.ContentLength <- postBytes.LongLength
req.ContentType <- "application/xml; charset=utf-8"
async{
use! reqStream = req.GetRequestStreamAsync() |> Async.AwaitTask
do! reqStream.WriteAsync(postBytes, 0, postBytes.Length) |> Async.AwaitIAsyncResult |> Async.Ignore
reqStream.Close()
use! res = req.AsyncGetResponse()
use stream = res.GetResponseStream()
use reader = new StreamReader(stream)
let! rdata = reader.ReadToEndAsync() |> Async.AwaitTask
return rdata
}
我打电话,如下所示:
let url = "https://www.googleapis.com/identitytoolkit/v3/relyingparty/signupNewUser?key=XXXXXXXXXXXXXXXXX"
let data = "returnSecureToken=true"
makePostRequest url data
我很新的F#
,有点搞不清关于这是如何工作的。我如何从这个请求中获得JSON响应?我如何知道何时完成?这会阻止主线程上的UI吗?我做的是翻译的斯威夫特以下代码块:
Auth.auth().signInAnonymously(completion: { (user, error) in
if let err = error {
print(err.localizedDescription)
return
}
})
这里的一切对我来说很有意义,因为我们有一个完成块的方法执行完毕后调用的,而且我们知道,user
变量包含从服务器获得的响应,这在F#中对我来说意义不大。
UPDATE:
继在意见的建议,我已引用F#数据:HTTP实用程序,并创建了下面的代码片段:
let url = "https://www.googleapis.com/identitytoolkit/v3/relyingparty/signupNewUser?key=XXXXXXXXXXXX"
Http.RequestString
(url,
headers = [ ContentType HttpContentTypes.Json ],
body = TextRequest """ {"returnSecureToken": true} """)
然而,这会产生错误The value, namespace, type or module Http is not defined
UPDATE 2: 我已经解决了以下代码:
let fetchUrl callback url (requestBody : string) =
let req = WebRequest.Create(Uri(url))
req.Method <- "POST"
let postBytes = requestBody |> System.Text.Encoding.ASCII.GetBytes
req.ContentLength <- postBytes.LongLength
req.ContentType <- "application/json; charset=utf-8"
let reqStream = req.GetRequestStream()
reqStream.Write(postBytes, 0, postBytes.Length);
reqStream.Close()
use resp = req.GetResponse()
use stream = resp.GetResponseStream()
use reader = new IO.StreamReader(stream)
callback reader url
let myCallback (reader:IO.StreamReader) url =
let html = reader.ReadToEnd()
let html1000 = html.Substring(0,1000)
printfn "Downloaded %s. First 1000 is %s" url html1000
html // return all the html
let openLandlord() =
let url = "https://www.googleapis.com/identitytoolkit/v3/relyingparty/signupNewUser?key=XXXXXXXXXXXXXXXXXXX"
let requestBody = """ {"returnSecureToken": true} """
fetchUrl myCallback url requestBody
以下这里的例子:
https://fsharpforfunandprofit.com/posts/fvsc-download/
但是当我打电话openLandlord
功能在这里:
override x.ViewDidLoad() =
base.ViewDidLoad()
openLandlord()
我收到以下错误:
这种表达预计有型但是这里有字符串。
错误:
- 在或结合在此点之前的不完全的结构化构建体。
- 未定义构造函数请求的值。
- 成员定义中的意外关键字匹配。
- 未定义值,名称空间,类型或模块响应。
- 成员定义中意外标识。
你的问题太广泛了。并且您将一个高级API与另一个低级API进行比较。如果需要,可以将请求处理委托给库。例如,FSharp.Data具有很好的HTTP实用程序:http://fsharp.github.io/FSharp.Data/library/Http.html –
我不认为它太宽泛...我想要做的就是发送一个HTTP POST请求异步而不会阻塞UI,然后在闭包块(或与其等效的东西)中获得此请求的JSON响应。我试过使用Http.fs,但是这不会为xamarinios安装显然 – Alk
对不起,我刚刚阅读“有点困惑,这是如何工作的”作为鼓励我详细解释代码的细节,这需要太广泛的答案。如果您只想从响应数据获取JSON,则可以使用FSharp.Data或.NET Newtonsoft.JSON中的特定于F#的JSON类型提供程序。两者都有很多例子。如果您使用异步操作,UI线程将会很好。 –