Bagaimana saya bisa mengirim permintaan HTTP POST ke server dari Excel menggunakan VBA?

135

Kode VBA apa yang diperlukan untuk melakukan POST HTTP dari spreadsheet Excel?

Matthew Murdoch
sumber

Jawaban:

147
Set objHTTP = CreateObject("MSXML2.ServerXMLHTTP")
URL = "http://www.somedomain.com"
objHTTP.Open "POST", URL, False
objHTTP.setRequestHeader "User-Agent", "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.0)"
objHTTP.send("")

Atau, untuk kontrol yang lebih besar atas permintaan HTTP yang dapat Anda gunakan WinHttp.WinHttpRequest.5.1sebagai ganti MSXML2.ServerXMLHTTP.

Bill the Lizard
sumber
9
Untuk kontrol yang lebih besar atas permintaan HTTP, Anda dapat menggunakan "WinHttp.WinHttpRequest.5.1" alih-alih "MSXML2.ServerXMLHTTP"
Matthew Murdoch
5
Yang perlu diperhatikan adalah Anda juga dapat menggunakan ini untuk mengeluarkan PUT HTTP dengan mengubah "POST" menjadi "PUT". Konten ke PUT masuk dalam metode .send (). Setiap tajuk tambahan yang perlu Anda atur dapat dilakukan juga mengikuti sintaks yang digunakan dalam contoh Agen-Pengguna.
Radicand
7
Harap jangan menggunakan tanda kurung di sekitar parameter jika Anda tidak menggunakan nilai pengembalian Sub: Sintaks VBA tidak mengizinkan tanda kurung di sekitar parameter Sub (meskipun, mereka diperlukan untuk Fungsi), jadi tanda kurung ini sebenarnya tanda kurung aritmatika yang digunakan untuk memperjelas prioritas operator. Selain karena menyesatkan dan tidak jelas, ini akhirnya dapat menyebabkan kesalahan runtime jika argumennya adalah objek. Dan meskipun tidak diminta secara eksplisit, biasanya Anda ingin menggunakan respons HTTP, yang dapat Anda sebutkan dapat diambil dengan objHTTP.responseText.
Leviathan
4
@Leviathan parens benar-benar melakukan lebih dari itu: mereka membuat runtime VBA mengevaluasi ekspresi sebagai nilai , dan meneruskannya ke metode ByVal terlepas dari apakah tanda tangan metode mengatakan ByRefatau tidak. Itu sebabnya menggunakannya dengan variabel objek tipe yang tidak memiliki anggota default menyebabkan kesalahan run-time; dan menggunakannya pada objek yang memang memiliki anggota default, melewati nilai anggota default itu bukan objek yang sebenarnya.
Mathieu Guindon
1
Sejuta kali terima kasih. Saya tidak tahu mengapa, karena saya tidak melihatnya dalam contoh lain, tetapi tajuk "User-Agent" sangat penting bagi saya, karena kalau tidak, tubuh tidak dikirim dalam permintaan saya.
redOktober13
51

Jika Anda membutuhkannya untuk bekerja di Mac dan Windows, Anda dapat menggunakan QueryTables:

With ActiveSheet.QueryTables.Add(Connection:="URL;http://carbon.brighterplanet.com/flights.txt", Destination:=Range("A2"))
    .PostText = "origin_airport=MSN&destination_airport=ORD"
    .RefreshStyle = xlOverwriteCells
    .SaveData = True
    .Refresh
End With

Catatan:

  • Mengenai output ... Saya tidak tahu apakah mungkin mengembalikan hasil ke sel yang sama yang disebut fungsi VBA. Pada contoh di atas, hasilnya ditulis ke dalam A2.
  • Mengenai input ... Jika Anda ingin hasil di-refresh ketika Anda mengubah sel-sel tertentu, pastikan sel-sel itu adalah argumen untuk fungsi VBA Anda.
  • Ini tidak akan berfungsi di Excel untuk Mac 2008, yang tidak memiliki VBA. Excel untuk Mac 2011 mendapat kembali VBA.

Untuk detail lebih lanjut, Anda dapat melihat ringkasan lengkap saya tentang " menggunakan layanan web dari Excel ."

Seamus Abshere
sumber
3
+1: Saya hanya membutuhkannya di Windows tetapi solusi lintas platform mungkin menguntungkan orang lain.
Matthew Murdoch
Saya tidak berpikir Anda benar-benar dapat mengakses kode html, Anda hanya bisa mendapatkan informasi pada halaman web yang diberikan (bukan kode html yang sebenarnya)
user1493046
1
+1 untuk solusi lintas platform dan +1 (jika saya bisa) untuk ringkasan lengkap dengan tautan inti dan semuanya. Terima kasih!!
serangan udara
Saya harus mendukung kedua windows dan mac, dan solusi ini tepat! Perhatikan bahwa ketika Anda menentukan PostText, URL harus memproses permintaan POST, jika tidak maka akan memproses permintaan GET.
amolk
1
Apakah mungkin untuk menampilkan hasil ke variabel, bukan Rentang? Perlu melakukan parsing Json.
Stanislasdrg Reinstate Monica
42

Selain anwser dari Bill the Lizard :

Sebagian besar backends mengurai data posting mentah. Dalam PHP misalnya, Anda akan memiliki array $_POSTdi mana masing-masing variabel dalam data posting akan disimpan. Dalam hal ini Anda harus menggunakan tajuk tambahan "Content-type: application/x-www-form-urlencoded":

Set objHTTP = CreateObject("WinHttp.WinHttpRequest.5.1")
URL = "http://www.somedomain.com"
objHTTP.Open "POST", URL, False
objHTTP.setRequestHeader "User-Agent", "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.0)"
objHTTP.setRequestHeader "Content-type", "application/x-www-form-urlencoded"
objHTTP.send ("var1=value1&var2=value2&var3=value3")

Kalau tidak, Anda harus membaca data posting mentah pada variabel "$HTTP_RAW_POST_DATA".

kode ini
sumber
1
Saya mencoba mengirim permintaan ini (dengan kurung kurawal) dan mendapatkan kesalahan kompilasi ... bisakah Anda membantu: "{" request ": {" carName ":" Honda "," model ":" 1A5 "}}"
biola
6

Anda dapat menggunakan ServerXMLHTTPdalam proyek VBA dengan menambahkan referensi ke MSXML.

  1. Buka Editor VBA (biasanya dengan mengedit Makro)
  2. Buka daftar Referensi yang Tersedia
  3. Periksa Microsoft XML
  4. Klik OK.

(dari Referensi MSXML dalam Proyek VBA )

The dokumentasi ServerXMLHTTP MSDN memiliki rincian lengkap tentang semua properti dan metode dari ServerXMLHTTP.

Singkatnya, pada dasarnya kerjanya seperti ini:

  1. Panggil metode terbuka untuk terhubung ke server jarak jauh
  2. Panggilan kirim untuk mengirim permintaan.
  3. Baca responsnya melalui responseXML , responseText , responseStream , atau responseBody
Mark Biek
sumber
1
tautan itu menggunakan jscript, bukan VBA
John Henckel
1
Terima kasih @JohnHenckel. Saya telah membuat beberapa perubahan untuk memperbarui jawaban itu.
Mark Biek
3

Untuk melengkapi respons pengguna lain:

Untuk ini saya telah membuat objek "WinHttp.WinHttpRequest.5.1" .

Kirim permintaan pos dengan beberapa data dari Excel menggunakan VBA:

Dim LoginRequest As Object
Set LoginRequest = CreateObject("WinHttp.WinHttpRequest.5.1")
LoginRequest.Open "POST", "http://...", False
LoginRequest.setRequestHeader "Content-type", "application/x-www-form-urlencoded"
LoginRequest.send ("key1=value1&key2=value2")

Kirim permintaan dapatkan dengan otentikasi token dari Excel menggunakan VBA:

Dim TCRequestItem As Object
Set TCRequestItem = CreateObject("WinHttp.WinHttpRequest.5.1")
TCRequestItem.Open "GET", "http://...", False
TCRequestItem.setRequestHeader "Content-Type", "application/xml"
TCRequestItem.setRequestHeader "Accept", "application/xml"
TCRequestItem.setRequestHeader "Authorization", "Bearer " & token
TCRequestItem.send
David Q
sumber
David, begitu Anda mengirim permintaan, bagaimana Anda membaca jawabannya?
ps0604
Respons ada di dalam TCRequestItem Object, Anda dapat membacanya seperti: TCRequestItem.ResponseTextsetelah melakukanTCRequestItem.send
David Q
0

Saya melakukan ini sebelum menggunakan perpustakaan MSXML dan kemudian menggunakan objek XMLHttpRequest, lihat di sini .

Sijin
sumber
1
Berkas tidak ditemukan.
SuShuang