选择性地关注Go中的重定向 [英] Selectively Follow Redirects in Go

查看:102
本文介绍了选择性地关注Go中的重定向的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试编写一个twitter解析器来解析链接缩写器等的最终URL,但是为我提供了一个手动定义的主机模式列表的URL。这样做的原因是,我不想结束与付费墙网址,但前一个。



据我可以告诉方式做到这一点是基于默认的 RoundTripper 编写我自己的客户端,因为从自定义的 CheckRedirect 函数返回一个错误会中止客户端而不让步一个响应。

有没有办法使用默认的客户端并记录URL列表/特定的URL自定义 checkRedirect 函数

解决方案

在自定义 CheckResponse 产生错误的情况下,实际上仍返回最后一个有效的 Response 评论)。



http:/ /golang.org/pkg/net/http/#Client


如果CheckRedirect返回错误,客户端的Get方法返回预先vious响应和CheckRedirect的错误(包裹在一个url.Error中),而不是发出Request req。

如果你保留一个 ($ code> CheckResponse )中的paywall-redirect中止自定义错误类型(<$在下面的例子中,c $ c> Paywalled )。
您以后的错误处理代码必须将错误类型视为特殊(非错误)的情况。



示例:

  package main 

import(
errors
fmt
net / http
net / url


var Paywalled = errors.New(下一次重定向会碰到付费墙)

var badHosts = map [string] error {
registration.ft.com:Paywalled,
}

var client =& http.Client {
CheckRedirect:func( req * http.Request,通过[] * http.Request)错误{
//注意:在生产中使用时,还要检查重定向循环
return badHosts [req.URL.Host]
},
}

func main(){
resp,err:= client.Get(http://on.ft.com/14pQBYE)
//如果它是一个包裹在url.Error中的`Paywalled`,则忽略非零错误err
if e,ok:= err。(* url.Error); (ok& e.Err!= Paywalled)|| (!ok& err!= nil){
fmt.Println(error:,err)
return
}
resp.Body.Close()
fmt.Println(resp.Request.URL)
}


I'm trying to write a twitter reader that resolves the final URLs of link shorteners etc, but gives me a URL along the way for a list of manually defined host patterns. The reason to do this is that i don't want to end up with the paywall URL but the one before.

As far as i can tell the way to do this is write my own client based on the default RoundTripper because returning an error from a custom CheckRedirect function aborts the client without yielding a response.

Is there a way to use the default client and record a list of URLs/specific URL from a custom checkRedirect function?

解决方案

The client request will actually still return the last valid Response in cases where your custom CheckResponse yields an error (As mentioned in the comments).

http://golang.org/pkg/net/http/#Client

If CheckRedirect returns an error, the Client's Get method returns both the previous Response and CheckRedirect's error (wrapped in a url.Error) instead of issuing the Request req.

If you maintain a list of "known" paywall-urls, you can abort the paywall-redirect in your CheckResponse with a custom error type (Paywalled in the example below). Your error handling code later has to consider that error type as a special (non-erroneous) case.

Example:

package main

import (
    "errors"
    "fmt"
    "net/http"
    "net/url"
)

var Paywalled = errors.New("next redirect would hit a paywall")

var badHosts = map[string]error{
    "registration.ft.com": Paywalled,
}

var client = &http.Client{
    CheckRedirect: func(req *http.Request, via []*http.Request) error {
        // N.B.: when used in production, also check for redirect loops
        return badHosts[req.URL.Host]
    },
}

func main() {
    resp, err := client.Get("http://on.ft.com/14pQBYE")
    // ignore non-nil err if it's a `Paywalled` wrapped in url.Error
    if e, ok := err.(*url.Error); (ok && e.Err != Paywalled) || (!ok && err != nil) {
        fmt.Println("error: ", err)
        return
    }   
    resp.Body.Close()
    fmt.Println(resp.Request.URL)
}                                                                                                                                     

这篇关于选择性地关注Go中的重定向的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆