Olen tekemässä ohjelmaa joka lataa netistä eräältä sivulta tietoa ja käsittelee niitä haluamallani tavalla. Tietojen lataus onnistuisi mainioisti tällä, mutta kun sivulle pitäisi kirjautua ennen kuin tiedot saa näkyviin.
Eli ohjelman pitäisi kirjoittaa pääsivulle käyttäjätunnus ja salasana ja sitten vielä painaa "kirjaudu" nappia.
Mites tällainen toteutetaan.... vinkkejä tms kaipailen.
Voit käytää luokkaa HttpWebRequest. Tekstikentän täyttäminen ja lähettäminen tarkoittaa käytännössä tietynlaisen datan lähettämistä palvelimelle, ja tämän voit selvittää vaikkala Firefoxin Live HTTP Headers -lisäosan avulla.
Moikka taas novice!
lainataan tätä täältä ja muutetaan hieman...
Imports System
Imports System.Net
Imports System.Text
'...
Dim wc As New WebClient()
Dim cc As New CredentialCache()
Dim Url As String = "http://www.esimerkki.com/"
cc.Add(New Uri(Url),"Basic", _
New NetworkCredential("tunnuksesi","salasanasi"))
wc.Credentials = cc
Dim tieto As String = Encoding.ASCII.GetString( _
wc.DownloadData(Url & "tietoa.txt"))
TextBox1.Text = tieto
wc.DisposeMihin textboxiin tuo networkcredential laittaa tunnuksen ja salasanan ja minkä formin se lähettää eteenpäin?
Moikka Short Php!
Jos luit mitä Metabolix kirjoitti, niin lienee selvinnyt, että mitään textboxeja ei tässä täytellä fyysisesti...
Eipä onnistunut... Metabolix:n vinkki pölisi yli hilseen (ehkäpä se aukeaisi jos löytyisi kunnollinen esimerkki) ja Neaun vinkillä sain sivulta ulos seuraavan; "You cannot use this function".
En tiedä sitten mitä tein väärin... voiko tuon CredentialCache kirjautumisen estää?
Moikka taas novice!
Kyllä on mahdollista estää palvelinpäässä CredentialCache'n käyttö
elikä: ...security.util.CredentialCacheEnabled = false
Opera selaimeni osaa kuitenkin kirjautua sivulle, joten jollain tavallahan sen on onnistuttava.
Onko seuraa etappi HttpWebRequest luokan opiskelu? Olisin kiitollinen esimerkistä...
Jos oikein ymmärsin, niin se ei kysy http-protokollan tasolla käyttäjätunnusta ja salasanaa, vaan siinä on kirjautumislomake. Eli mikäli nyt en ihan väärin arvaa, niin tuosta networkcredentialista ei ole hyötyä.
Se mahdollisesti antaa evästeen, joka pitäisi välittää myöhemmissä sivuissa. Jos näin, niin kannattaa tutustua miten evästeitä käytetään HttpWebRequestin kanssa.
WOW Grez!
You really are an incredible man!
Moi Nea, on se hyvä jos pienellä luetunymmärtämisellä pääsee uskomattomaksi...
Vai mitä mahdoit tarkoittaa?
Okei.. sivulle kirjauduttaessa evästeet on oltava päällä.
Aloin tutkailemaan HttpWebRequest-luokkaa ja Firefoxin Live HTTP Headers -lisäosaa. HTTP Headers:n avulla (jos nyt oikein sitä käytin/tajusin) selvitin, että ladattaessa sivu lähettää selaimelle evästeen ja sisään kirjauduttaessa selain lähettää sivulle saman evästeen. Sen jälkeen aina uutta sivua (samasta osoiteesta) ladattaessa lähettää sivu selaimelle saman evästeen. Eikä selain kirjautumisen jälkeen enää postaa evästettä mihinkään.
Nyt pitäisi VB ohjelmalla saada se eväste ja postata se kirjautumisen yhteydessä sivulle. Yritin seuraavaa, mutta sain textboxiin vain sivun lähdekoodin jossa ei ole tätä tarvitsemaani evästettä.
Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
Dim URL As String = "http://www.esimerkki.com/index.php"
Dim Request As HttpWebRequest = WebRequest.Create(URL)
Request.UserAgent = _
"Mozilla/5.0 (Windows; U; Windows NT 5.1; fi; rv:1.9.0.5) _
Gecko/2008120122 Firefox/3.0.5 (.NET CLR 3.5.30729)"
Request.Method = WebRequestMethods.Http.Get
Dim Response As HttpWebResponse = Request.GetResponse()
Dim reader As New StreamReader(Response.GetResponseStream())
Dim tmp As String = reader.ReadToEnd()
Response.Close()
TextBox1.Text = tmp
End SubMiten saan evästeen textboxiin?
Tiedän että olen aika kartanolla ja oikeat termit ovat hakusessa... koettakaa siitä huolimatta ymmärtää ja auttaa miestä mäessä.
No kun näitä on niin hirveen tylsää demota ilman että on se sivu josta ne tiedot pitäisi hakea.. (etkä nähtävästi halua kertoa mikä se on) joten tein tollaisen demosivun joka vaatii keksit ja jolle pitää ensin kirjautua
http://grez.info/putka/novice/
Käyttäjätunnus on novice ja salasana ecivon
Nyt kun meillä on sivu, jolla testata, niin voidaan tehdä ohjelma, joka ohjelmallisesti kirjautuu ja hakee tiedot... Esimerkiksi näin:
Imports System.Net
Imports System.IO
Module Salanoutaja
Sub Main()
'Tarvitsemme keksipurkin. Se on vähän kuin Nalle Puhin hinajapurkki,
'mutta siinä ei ole hinajaa vaan keksejä eli evästeitä.
Dim Cookies As New CookieContainer
'Kirjaudutaan
Dim request As HttpWebRequest = WebRequest.Create("http://grez.info/putka/novice/")
'Annetaan keksipurkki, johon webrequest voi laittaa saamansa keksit
request.CookieContainer = Cookies
request.Method = "POST"
request.ContentType = "application/x-www-form-urlencoded"
'Kirjauduttaessa lähetetään käyttäjätunnus ja salasana palvelimelle
Dim bytes() As Byte = System.Text.Encoding.Default.GetBytes("user=novice&pass=ecivon")
request.ContentLength = bytes.Length
Dim outputStream As System.IO.Stream = request.GetRequestStream()
outputStream.Write(bytes, 0, bytes.Length)
outputStream.Close()
Dim Response As WebResponse = request.GetResponse()
'Kirjautuminen on lähetetty, voidaan sulkea
Response.Close()
'Ladataan salainen sivu
request = WebRequest.Create("http://grez.info/putka/novice/sisalto.php")
'Käytetään samaa keksipurkkia, niin selain saa takaisin lähettämänsä keksit
request.CookieContainer = Cookies
Response = request.GetResponse()
Dim reader As StreamReader = New StreamReader(Response.GetResponseStream, System.Text.Encoding.Default)
'Luetaan vastaus
Dim Vastaus As String = reader.ReadToEnd
reader.Close()
Response.Close()
'Näytetään salaiset tiedot käyttäjälle
Console.Out.Write(Vastaus)
End Sub
End ModuleWOW Grez!
You really are an incredible man!
Sehän toimi hienosti... välistä puuttui vain yksi lause:
request.ProtocolVersion = HttpVersion.Version10
Eikä mennyt kuin 8h että tuon keksin väliin tyrkätä.
Mutta no... tuon 8h aikana tuli HttpWebRequest-luokka hieman tutummaksi ;)
Suuret kiitokset sinulle Grez!!!
Tuolla esimerkkisivullani kyllä toimi (ainakin itselläni) ilman tuota ja tuon kanssa taas luulen että tuo esimerkkisivuni ei toimi (HTTP 1.0:ssa kun ei ole host headeria jota useita www-sivuja yhdessä IP:ssä hostattaessa tarvii)
Mutta ilmeisesti tarkoititkin sen sivun kanssa, johon tuota itse tarvitsit. (Tosin siinäkin olisi mielenkiintoista tietää mikä oli oikea syy toimimattomuuteen, tuskin kuitenkaan se, ettei se tukisi HTTP 1.1:stä)
Juu, kyllä esimerkkisivullasi toimii molemilla versioilla.
Käyttämälläni sivulla ilman "versiointia" tai versiolla 1.1 tulee virheilmoitus:
The remote server returned an error: (417) Expectation Failed.
riville:
Dim Response As WebResponse = request.GetResponse().
Vaikkakin sivut antavat HTTP headeriin ensimmäiseksi seuraavan rivin:
esimerkkisivusi: GET /putka/novice/ HTTP/1.1
käyttämäni sivu: GET /fi/index.php HTTP/1.1
Eikös tuo nimenomaan kerro tuon versionumeron? Vai olenko taas kartanolla?
Veikkaisin, ettei nyt ole kyse tuosta versiosta vaan jostain datasta, jota palvelin 1.1-versiota käytettäessä odottaa ja jota ei jostain syystä tule. Pystytkö tarkistamaan, mitä muuta ohjelma lähettää ja mitä esimerkiksi normaali selain vastaavassa tilanteessa lähettää?
Heippa taas!
Rupesi jurppimaan tuo Grez'n hieno demo joten päätin yhdistää jutskan WebClient-luokkaan...
Imports System
Imports System.IO
Imports System.Net
Imports System.Text
Public Partial Class MainForm
Public Sub New()
Me.InitializeComponent()
Me.Visible = False
End Sub
Sub MainFormLoad(sender As Object, e As EventArgs)
Using client As New MyClient()
client.HeadOnly = True
Dim uri As String = "http://grez.info/putka/novice/"
Dim body As Byte() = client.DownloadData(uri)
Dim type As String = client.ResponseHeaders("content-type")
client.HeadOnly = False
If type.StartsWith("text/") Then
Dim text As String = _
client.DownloadString(uri + "sisalto.php")
msgbox(text)
Me.Close
End If
End Using
End Sub
Class MyClient: Inherits WebClient
Public Property HeadOnly() As Boolean
Get
End Get
Set
End Set
End Property
Private Cookies As New CookieContainer()
Protected Overloads Overrides Function _
GetWebRequest(address As Uri) As WebRequest
Dim request As WebRequest = _
MyBase.GetWebRequest(address)
If HeadOnly AndAlso request.Method = "GET" Then
request.Method = "HEAD"
End If
If TypeOf(request) Is HttpWebRequest Then
TryCast(request, HttpWebRequest). _
CookieContainer = Cookies
request.Method = "POST"
request.ContentType = _
"application/x-www-form-urlencoded"
Dim bytes() As Byte = _
Encoding.Default.GetBytes("user=novice&pass=ecivon")
request.ContentLength = bytes.Length
Dim oStream As Stream = _
request.GetRequestStream()
oStream.Write(bytes, 0, bytes.Length)
oStream.Close()
End If
Return request
End Function
End Class
End Classneau33 kirjoitti:
Rupesi jurppimaan tuo Grez'n hieno demo joten päätin yhdistää jutskan WebClient-luokkaan...
Mikäs siinä rupesi jurppimaan? Tuo lihavoimasi osako, vai oliko siinä muutakin vikaa?
No heippa taas!
@Grez: ei vaan se HIENO
Aihe on jo aika vanha, joten et voi enää vastata siihen.