dongshan2004
dongshan2004
2019-03-04 14:40

Golang“登录到站点并下载xls文件”? [关闭]

已采纳

Tell me how to use Golang to login to the site. Download xls file is obtained, but in order to have data in the Excel table, you need to log in to the site. The site is located on the company's server. If you can tell how to do it.

For example, the VBA code that I use to do this.

Set oFields = CreateObject("Scripting.Dictionary")
With oFields
    .Add "login", "sdiscor"
    .Add "password", "sdiscor"
End With
For Each sName In oFields
    oFields(sName) = sName & "=" & EncodeUriComponent(oFields(sName))
Next
sPayLoad = Join(oFields.Items(), "&")

With CreateObject("MSXML2.XMLHTTP")
    .Open "POST", "http://effect.gvc.oao.rzd/cgi_bin/effect_access.pl?", False
    .setRequestHeader "Content-Type", "application/x-www-form-urlencoded"
    .setRequestHeader "Content-Length", LenB(sPayLoad)
    .Send (sPayLoad)

    Do While .readyState <> 4
        DoEvents
    Loop

    webLink = "http://effect.gvc.oao.rzd/effect/table/***&LOGIN=&PASSWORD="
    vLocalFile = ThisWorkbook.Path & "\SIS-Effect.xls"

    .Open "GET", webLink, True
    .Send

    Do While .readyState <> 4
        DoEvents
    Loop

    oResp = .responseBody

    vFF = FreeFile
    If Dir(vLocalFile) <> "" Then Kill vLocalFile
    Open vLocalFile For Binary As #vFF
    Put #vFF, , oResp
    Close #vFF
End With

Thank leolara!!! Final code

func main() {
urlLogin := "http://effect.gvc.oao.rzd/cgi_bin/effect_access.pl?"
urlDownload := "http://effect.gvc.oao.rzd/effect/table/OZODO10U.XLS?DAT=2019.03.04&LOGIN=&PASSWORD="

cookieJar, _ := cookiejar.New(nil)

client := &http.Client{Jar: cookieJar,}

_, err := client.PostForm(urlLogin,
    url.Values{"login": {"sdiscor"}, "password": {"sdiscor"}})
if err != nil {
    fmt.Println("Error while downloading", urlLogin, "-", err)
    return
}

fileName := "1.xls"
fmt.Println("Downloading", urlDownload, "to", fileName)
output, err := os.Create(fileName)
if err != nil {
    fmt.Println("Error while creating", fileName, "-", err)
    return
}
defer output.Close()

resp, err := client.Get(urlDownload)
if err != nil {
    fmt.Println("Error while downloading", urlDownload, "-", err)
    return
}
defer resp.Body.Close()

n, err := io.Copy(output, resp.Body)
if err != nil {
    fmt.Println("Error while downloading", urlDownload, "-", err)
    return
}

fmt.Println(n, "bytes downloaded.")

}

  • 点赞
  • 写回答
  • 关注问题
  • 收藏
  • 复制链接分享
  • 邀请回答

1条回答

  • dongmangzong8006 dongmangzong8006 2年前

    I do not know VBA, but it seems to me what you are doing a HTTP POST with the credentials, and then you are doing a HTTP GET to obtain the file you are looking for. I guess the class you are using keeps the cookies from request to request and that is how the authentication works.

    Assuming that, in Go you would use the library https://golang.org/pkg/net/http/cookiejar/ to keep the cookies and https://golang.org/pkg/net/http/ to do the actual requests.

    You pass each time the same cookie jar.

    Something along these lines (not exact or checked):

    package main
    
    import (
        "net/http"
        "net/http/cookiejar"
    )
    
    func main() {
        cookieJar, _ := cookiejar.New(nil)
    
        client := &http.Client{
            Jar: cookieJar,
        }
    
        resp, err := http.PostForm("http://example.com/loginform",
            url.Values{"login": {"sdiscor"}, "password": {"sdiscor"}})
        resp, err := client.Get("http://example.com/")
    }
    
    
    点赞 评论 复制链接分享

相关推荐