使用FoxPro下载文件(HTTP)

时间:2011-12-15 18:51:54

标签: foxpro visual-foxpro

今天我被要求帮助解决FoxPro问题,关于如何通过HTTP下载文件。

我发现了两件事:一件是付费的ActiveX,other one需要libcurl。

有没有其他方法可以做到这一点(VFP 8),如Java中的HttpURLConnection?例如,使用Microsoft.XMLHTTP

6 个答案:

答案 0 :(得分:8)

两个有效的片段,不需要额外的文件/ dll / flls /等。

Local loRequest, lcUrl, lcFilename

lcUrl = "http://example.com/foo.zip"
lcFilename = "C:\Temp\PSV.zip"

loRequest = Createobject('MsXml2.XmlHttp')
loRequest.Open("GET",lcUrl,.F.)
loRequest.Send()
StrToFile(loRequest.ResponseBody,lcFilename)

lox = CREATEOBJECT("inetctls.inet")
lcSuff = lox.OpenURL("http://whatever.co.uk/suff.htm")
STRTOFILE(lcStuff, "c:\data\myfile.htm")

(摘自here

答案 1 :(得分:1)

是我的 HttpClient.prg 文件(仅支持GET个响应):

#define INTERNET_OPEN_TYPE_PRECONFIG_WITH_NO_AUTOPROXY 4

#define REQ_STATE_UNINITIALIZED 0 && open()has not been called yet.
#define REQ_STATE_LOADING       1 && send()has not been called yet.
#define REQ_STATE_LOADED        2 && send() has been called, and headers and status are available.
#define REQ_STATE_INTERACTIVE   3 && Downloading; responseText holds partial data.
#define REQ_STATE_COMPLETED     4 && The operation is complete.

DEFINE CLASS HttpClientRequest As Custom
  readystate=REQ_STATE_UNINITIALIZED
  Protocol=NULL
  Url=NULL
  requestBody=NULL
  responseBody=NULL

  PROCEDURE Open(tcProtocol, tcUrl)
    IF this.readystate != REQ_STATE_UNINITIALIZED
      ERROR "HttpClientRequest is already opened."
    ENDIF
    IF VARTYPE(m.tcProtocol)!="C" OR VARTYPE(m.tcUrl)!="C" 
      ERROR "Invalid type or count of parameters."
    ENDIF
    IF NOT INLIST(m.tcProtocol,"GET")
      ERROR "Unsupported or currently not implemented protocol type."
    ENDIF
    this.Protocol = m.tcProtocol
    this.Url = m.tcUrl
    this.readystate = REQ_STATE_LOADING
  ENDPROC

  PROCEDURE Send(tcBody)
    IF this.readystate != REQ_STATE_LOADING
      ERROR "HttpClientRequest is not in initialized state."
    ENDIF
    IF PCOUNT()=0
      m.tcBody=NULL
    ENDIF
    IF this.Protocol=="GET" AND (NOT ISNULL(m.tcBody))
      ERROR "Invalid type or count of parameters."
    ENDIF
    this.requestBody = m.tcBody
    this.readystate = REQ_STATE_LOADED


    DECLARE integer InternetOpen IN "wininet.dll" ;
      string @ lpszAgent, ;
      integer dwAccessType, ;
      string @ lpszProxyName, ;
      string @ lpszProxyBypass, ;
      integer dwFlags
    DECLARE integer InternetCloseHandle IN "wininet.dll" ;
      integer hInternet
    DECLARE integer InternetCanonicalizeUrl IN "wininet.dll" ;
      string @ lpszUrl, ;
      string @ lpszBuffer, ;
      integer @ lpdwBufferLength, ;
      integer dwFlags
    DECLARE integer InternetOpenUrl IN "wininet.dll" ;
      integer hInternet, ;
      string @ lpszUrl, ;
      string @ lpszHeaders, ;
      integer dwHeadersLength, ;
      integer dwFlags, ;
      integer dwContext
    DECLARE integer InternetReadFile IN "wininet.dll" ;
      integer hFile, ;
      string @ lpBuffer, ;
      integer dwNumberOfBytesToRead, ;
      integer @ lpdwNumberOfBytesRead

    LOCAL m.hInternet,lcUrl,lnUrlLen,m.hInternetFile,lcBuffer,lnBufferLen,lnReaded
    m.hInternet = InternetOpen("a.k.d. HttpClientRequest for Visual FoxPro", ;
                               INTERNET_OPEN_TYPE_PRECONFIG_WITH_NO_AUTOPROXY, ;
                               NULL, NULL, 0)
    this.responseBody = ""
    IF m.hInternet != 0
      m.lnUrlLen = LEN(this.Url)*8
      m.lcUrl = REPLICATE(CHR(0),m.lnUrlLen)
      InternetCanonicalizeUrl(this.Url, @lcUrl, @lnUrlLen, 0)
      m.hInternetFile = InternetOpenUrl(m.hInternet, @lcUrl, NULL, -1, 0, 0)
      IF m.hInternetFile != 0
        m.lnBufferLen = 10240
        DO WHILE .T.
           m.lcBuffer = REPLICATE(CHR(0),m.lnBufferLen)
           m.lnReaded = 0
           IF NOT (0!=InternetReadFile(m.hInternetFile, @lcBuffer, m.lnBufferLen, @lnReaded) AND m.lnReaded>0)
             EXIT
           ENDIF
          this.responseBody = this.responseBody + LEFT(m.lcBuffer,m.lnReaded)
          this.readystate = REQ_STATE_INTERACTIVE
        ENDDO
        InternetCloseHandle(m.hInternetFile)
      ENDIF
      InternetCloseHandle(m.hInternet)
    ENDIF
    this.readystate = REQ_STATE_COMPLETED
  ENDPROC
ENDDEFINE

GET次请求的使用情况:

Local HttpClient
m.HttpClient = NEWOBJECT("HttpClientRequest","httpclient.prg")
m.HttpClient.Open("GET","http://servername/path/resourcename")
m.HttpClient.Send()

执行上述代码后,m.HttpClient.responseBody属性中包含服务器响应,您可以将值存储到文件中,或者将图片存储到Image对象的PictureVal属性中:

STRTOFILE(m.HttpClient.responseBody,"c:\filename");

m.myform.AddObject("myimg",""image")
m.myform.myimg.PictureVal=m.HttpClient.responseBody

答案 2 :(得分:0)

了解使用West Wind Web Connect。这是一个框架,允许您编写可从Web访问的VFP应用程序。

答案 3 :(得分:0)

您可以在VFP中执行此操作,但它需要注册Windows DLL才能打开连接句柄,并调用以获取数据。

另一种选择是使用自动化,例如使用Internet Explorer。您可以在VFP中创建一个ie对象,并调用其方法打开一个给定的URL,等待它的“Ready State”完成,然后查看内容。至于尝试获取需要URL参数字符串的东西,你可以添加那些没有问题,但如果它需要POST变量,那就多一点努力。

正如Jerry所提到的,West-Wind工具非常强大,Rick Strahl自从......大约1993年以来一直在这样做。他的另一个工具是wwIPTools.DLL,它提供了更多的功能。

答案 4 :(得分:0)

您还可以查看Craig Boyd的免费VFPConnection库,他还有一个优秀的免费JSON库。

答案 5 :(得分:0)

选项1:

Declare Integer URLDownloadToFile In urlmon.dll As _apiURLDownloadToFile;
Integer pCaller, ;
String  szURL, ;
String  szFileName, ;
Integer dwReserved, ;
Integer lpfnCB

首先让shure从缓存中清除文件:

Declare Integer DeleteUrlCacheEntry In wininet.dll As _apiDeleteUrlCacheEntry ;
    String  lpszUrlName

或者在网址的末尾添加一个随机参数,例如“?somerandomvalue”。

选项2:

Declare Integer InternetOpen In wininet.dll As _apiInternetOpen ;
    String  lpszAgent, ;
    Integer dwAccessType, ;
    String  lpszProxy, ;
    String  lpszProxyBypass, ;
    Integer dwFlags

Declare Integer InternetOpenUrl In wininet.dll As _apiInternetOpenUrl ;
    Integer hInternet,;
    String  lpszUrl,;
    String  lpszHeaders,;
    Integer dwHeadersLength,;
    Integer dwFlags,;
    Integer dwContext

Declare Integer InternetReadFile In wininet.dll As _apiInternetReadFile ;
    Integer hFile, ;
    String  @lpBuffer, ;
    Integer dwNumberOfBytesToRead, ;
    Integer @lpdwNumberOfBytesRead

Declare Integer InternetCloseHandle In wininet.dll As _apiInternetCloseHandle ;
    Integer hInternet

可以在MSDN上找到这些功能的正确使用。

PS:你错过了这个:http://curl.haxx.se/libcurl/foxpro/