Using VB2008 to acccess the Betfair API: A tutorial

Collapse
This topic is closed.
X
X
 
  • Time
  • Show
Clear All
new posts

  • whymetry
    replied
    Originally posted by Mumbles0 View Post
    whymetry, gunhero,

    I think you are using the wrong event handler sub. Your code should be in
    Private Sub BetFairUK_getCompleteMarketPricesCompressedComplet ed

    But it look like you are using:
    Private Sub BetFairUK_getMarketPricesCompressedCompleted.
    Thank you. Now working

    Leave a comment:


  • gvigliani
    replied
    Search Engine for Soccer (for the moment)

    Hello everyone,
    I read somewhere on the forum, who felt the need 'of a search engine events. I have tried to solve the problem this way:
    1) I created a combo box and I added an event Collections:

    Football | Soccer | Final Result | Match Odds
    Football | Soccer | End 1st Time | Time Half
    Football | Soccer | End 1-Time / End Game | Half Time / Full Time
    Football | Soccer | Goal 1 Time | Half Time Scores
    Football | Soccer | Total Goals | Total Goals
    Football | Soccer | Minute Goal 1 | First Goal Odds
    Football | Soccer | Draw - No bets | Draw No Bet
    Football | Soccer | More / less than 1.5 goals | Over / Under 1.5 Goals
    Football | Soccer | Over / under 2.5 goals | Over / Under 2.5 Goals
    Football | Soccer | More / less than 3.5 goals | Over / Under 3.5 Goals
    Football | Soccer | More / under 4.5 goals | Over / Under 4.5 Goals
    Football | Soccer | More / under 5.5 goals | Over / Under 5.5 Goals
    Football | Soccer | More / less than 6.5 goals | Over / Under 6.5 Goals
    Football | Soccer | Score | Correct Score
    Football | Soccer | End Result of 1 Time | Half Time
    Football | Soccer | Mark both? | Both Teams to Score?
    Football | Soccer | Hat-tricks Score | Triplet
    Football | Soccer | Odd or Even | Odd or Even

    each string is divided by "|" and I entered:
    Calcio (IT) |
    Soccer (En)
    MarketName (IT)
    MarketName (EN)

    obviously if you do not need the Italian version you can avoid modifying the code to put it.

    code for search:

    Code:
    ' Sub for call  (Combo Box) 
    Private Sub freeSearch_SelectedValueChanged(ByVal sender As Object, ByVal e As System.EventArgs) Handles freeSearch.SelectedValueChanged
            tvMarkets.Nodes.Clear()
            Call carica_mercati_free()
        End Sub
    
    
    ' Sub for Api Called
      Private Sub carica_mercati_free()
            PrintRes("*** Markets ***")
            Dim oMarketsReq As New BFUK.GetAllMarketsReq
            oMarketsReq.header = oHeaderUK()
            oMarketsReq.fromDate = Today
            oMarketsReq.toDate = Today.AddDays(CDbl(DayinGame.Text)) ' 0=oggi 1 = domani n=numero di giorni
            With BetFairUK.getAllMarkets(oMarketsReq)  'Call the API
                CheckHeader(.header)
                PrintRes("ErrorCode = " & .errorCode.ToString)
                If .errorCode = BFUK.GetAllMarketsErrorEnum.OK Then
                    PopulateTreeViewfree(New UnpackAllMarkets(.marketData), tvMarkets)
                End If
            End With
        End Sub
    
    
    ' Search Engine
    Friend Sub PopulateTreeViewfree(ByVal AllMarkets As UnpackAllMarkets, ByVal TreeView As TreeView)
            Dim Ids, Names As String(), Nodes As TreeNodeCollection, M_name() As String, M_disp As String
            Dim prova As String
            Dim NumMerc As Integer = 0
    
            With AllMarkets
                Array.Sort(AllMarkets.marketData, Function(x, y) Date.Compare(x.eventDate, y.eventDate))  ' sort for event date
                For i = 0 To .marketData.Length - 1          'For each market
                    With .marketData(i)
                        M_name = Split(freeSearch.Text, "|")
                        Ids = .eventHeirachy.Split("/")        'Array of Ids
                        prova = Replace(.menuPath, " ", " ")
                        prova = Replace(prova, "/", "\")
                        Names = prova.Split("\")       'Array of names
                        M_disp = .marketName
                        If InStr(UCase(prova), UCase(M_name(0))) = 0 And InStr(UCase(prova), UCase(M_name(1))) = 0 Then GoTo incrementa
                        If UCase(M_disp) <> UCase(M_name(2)) And UCase(M_disp) <> UCase(M_name(3)) Then GoTo incrementa
                        Nodes = TreeView.Nodes          'Initial collection of child nodes
                        NumMerc += 1 : N_Mark.Text = NumMerc.ToString
                        Dim Node As New TreeNode       'Add a new node if it doesn't exist
                        Node.Text = Names(UBound(Names)) & "/" & M_name(3)
                        Node.Name = Ids(UBound(Ids))  'This is the key
                        Node.Tag = Format(.eventDate.AddHours(2), "HH:mm")
                        Node.Text = Node.Tag & "-" & Names(UBound(Names)) & "/" & M_name(3)
                        Nodes.Add(Node)
                    End With
    incrementa:
                Next i
            End With
        End Sub
    Thank you Mumble0 for your teaching

    gvigliani
    Last edited by gvigliani; 25-08-2010, 02:56 PM.

    Leave a comment:


  • gvigliani
    replied
    Originally posted by Mumbles0 View Post
    gvigliani,

    You can sort the AllMarkets.marketData array in order of .eventDate (which is start time) with this statement:

    Array.Sort(AllMarkets.marketData, Function(x, y) Date.Compare(x.eventDate, y.eventDate))
    Thank you ,
    Thank you
    Thank you
    Thank you
    Thank you
    Thank you

    Leave a comment:


  • Mumbles0
    replied
    whymetry, gunhero,

    I think you are using the wrong event handler sub. Your code should be in
    Private Sub BetFairUK_getCompleteMarketPricesCompressedComplet ed

    But it look like you are using:
    Private Sub BetFairUK_getMarketPricesCompressedCompleted.

    Leave a comment:


  • gunhero
    replied
    hi

    I have the same problem
    if I use the hints of VB2010 the variable completeMarketPrices doesn't exist :/

    thanks for your help

    gunhero

    Leave a comment:


  • whymetry
    replied
    Mumbles thank you ever so much for this tutorial. I am amazed how much I have managed to understand and get through so quickly. I am having a problem however with step 10 getting unpack2 to work correctly. I follow the instructions but for line

    Dim oMarketPrices As New UnpackCompleteMarketPricesCompressed(.completeMark etPrices)

    get
    Error 1 'completeMarketPrices' is not a member of 'BetfairX.BFUK.GetMarketPricesCompressedResp'.

    Any ideas to what silly mistake I have made?
    Last edited by whymetry; 24-08-2010, 11:34 AM.

    Leave a comment:


  • gunhero
    replied
    oh thank you
    now it works

    thanks @ mumbles0
    gunny

    Leave a comment:


  • Mumbles0
    replied
    gunhero,

    Your problem is because Function MpricesReq does not return a value. You must return the object it creates with a Return statement.

    Code:
    [COLOR="Gray"]Function MpricesReq() As BFUK.GetMarketPricesReq
      Dim oMPReq As New BFUK.GetMarketPricesReq
      With oMPReq
        .header = oHeaderUK()
        .marketId = 101657573
      End With
      [COLOR="Black"]Return oMPReq    '<<< Must have return statement![/COLOR]
    End Function[/COLOR]

    Leave a comment:


  • gunhero
    replied
    I have the value changed, but the mistake don't go away.
    the marketId is the number before the marketName if i press the button markets right?

    thanks

    Leave a comment:


  • gvigliani
    replied
    Market id

    Are you sure for the value in .marketid??

    Bye

    Leave a comment:


  • gunhero
    replied
    Step 7: Problem with SoapHeaderException

    Hi community,
    today I have started to programm the bot by this thread. First ... thank you for this thread
    Step by step I programmed the bot, and it runs. But in step 7 I 've a problem and no idea to get it.

    I have included following code:

    Code:
     
        Function MpricesReq() As BFUK.GetMarketPricesReq
            Dim oMPReq As New BFUK.GetMarketPricesReq
            With oMPReq
                .header = oHeaderUK()
                .marketId = 101657573
            End With
        End Function
    
        Sub ShowMprices(ByVal MpriceResp As BFUK.GetMarketPricesResp)
            Dim Lay, Back As String
            With MpriceResp
                CheckHeader(.header)
                Print("ErrorCode = " & .errorCode.ToString)
                If .errorCode = BFUK.GetMarketPricesErrorEnum.OK Then
                    With .marketPrices
                        Print("MarketID = " & .marketId)
                        For i = 0 To .runnerPrices.Length - 1
                            With .runnerPrices(i)
                                Print("Runner " & i + 1 & "  LPM = " & .lastPriceMatched)
                                Back = ""
                                For j = 0 To .bestPricesToBack.Length - 1
                                    With .bestPricesToBack(j)
                                        Back = Back & "  " & .price & "/" & Int(.amountAvailable)
                                    End With
                                Next
                                Lay = ""
                                For j = 0 To .bestPricesToLay.Length - 1
                                    With .bestPricesToLay(j)
                                        Lay = Lay & "  " & .price & "/" & Int(.amountAvailable)
                                    End With
                                Next
                                Print("Back = " & Back & "   Lay = " & Lay)
                            End With
                        Next
                    End With
                End If
            End With
        End Sub
    
    Private Sub bPrices_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles bPrices.Click
            Print("*** Prices ***")
            ShowMprices(BetFairUK.getMarketPrices(MpricesReq))   'Get market prices
        End Sub
    When I start the Debugger, login and click the "Price"-Button the Debugger says: "Eine Ausnahme (erste Chance) des Typs "System.Web.Services.Protocols.SoapHeaderException " ist in System.Web.Services.dll aufgetreten." ("An exception of the type "System.Web.Services.Protocols.SoapHeaderException " occured in System.Web.Services.dll")
    The pointer shows to "ShowMprices(BetFairUK.getMarketPrices(MpricesReq) ) 'Get market prices".

    Can you help me to find the mistake?

    Thank you at all

    gunhero

    and sorry for my bad english
    Last edited by gunhero; 23-08-2010, 04:44 PM.

    Leave a comment:


  • Mumbles0
    replied
    gvigliani,

    You can sort the AllMarkets.marketData array in order of .eventDate (which is start time) with this statement:

    Array.Sort(AllMarkets.marketData, Function(x, y) Date.Compare(x.eventDate, y.eventDate))

    Leave a comment:


  • gvigliani
    replied
    Horse Racing in Quick List

    Hello Mumbles0,
    as time passes the more I am fascinated by bees of Bf. For several days trying desperately to create a 'Quick List' to Win Horse Racing UK. The code I wrote is this:
    Code:
    Friend Sub PopulateTreeViewIppicaGB(ByVal AllMarkets As UnpackAllMarkets, ByVal TreeView As TreeView)
            Dim Ids, Names As String(), Nodes As TreeNodeCollection
            Dim NumMerc As Integer = 0
            Dim ok As Boolean
            With AllMarkets
                For i = 0 To .marketData.Length - 1          'For each market
                    With .marketData(i)
                        NumMerc += 1 : N_Mark.Text = NumMerc.ToString
                        Ids = .eventHeirachy.Split("/")        'Array of Ids
                        Names = .menuPath.Split("\")       'Array of names
                        Nodes = TreeView.Nodes          'Initial collection of child nodes
                        For j = 1 To UBound(Ids)               'For each event list item
                            If Not Nodes.ContainsKey(Ids(j)) Then
                                Dim Node As New TreeNode       'Add a new node if it doesn't exist
                                Node.Text = If(j <= UBound(Names), Names(j), .marketName)
                                Node.Name = Ids(j)  'This is the key
                                Node.Tag = Format(.eventDate, "HH:mm")
                                If (Names(1) = "Ippica" Or Names(1) = "Horse Racing") And Names(2) = "GB" Then
                                    If Val(Mid$(Node.Text, 1, 1)) > 0 Then
                                        Nodes.Add(Node)
                                        ok = True
                                    End If
                                End If
                            End If
                        Next
                    End With
                Next
            End With
        End Sub
    Unfortunately, the quick list is not sorted by time and then I could have a first race at 18:15 and the second string at 15.22. Is there a way to sort the events by time start?
    Thanks

    gvigliani

    Leave a comment:


  • Mumbles0
    replied
    Step 29. Adding controls to a form at run time.

    It is easy to add a control when you are designing a form - you simply drag the control from the Toolbox onto the form. But what if, for example, you want to add a button for each runner in a horse race? You can’t do this at design time because you don’t know how many runners there will be. Because the controls in the Toolbox are objects derived from classes, they can be added by the program while it is running.

    To display the list of runners returned by a getMarket call, a logical choice would be to use either a ListBox or a DataGridView control. As an alternative, this step will show how to add a set of buttons for the runners in a market. This is an interesting exercise.

    First add a new form to your project. From the Project menu select Add New Item . Select Windows Form and name it MarketForm.vb, then click the Add button. The new form should now appear in the solution explorer.

    The code for the form is this:

    Code:
    Public Class MarketForm
    
      Const PosLeft = 25   'Position of buttons from left edge of form
      Const PosTop = 25    'Position of buttons from top of form
      Const PosBut = 30    'Button spacing
      Const Bwidth = 150   'Button width
    
      Private Buttons As Button()  'The array of buttons
    
      Sub AddRunnerButtons(ByVal oMarketResp As BFUK.GetMarketResp)
        Dim Tpos As Integer = PosTop   'Top position of first button
        Dim m As Integer = oMarketResp.market.runners.Length - 1  'Number of runners - 1
    
        ReDim Buttons(m)
        For i = 0 To m   'For each runner
          Buttons(i) = New Button  'Create a new button object in the array element
          With Buttons(i)  'Set button properties as required
            .Left = PosLeft   'Set left position
            .Text = oMarketResp.market.runners(i).name   'Set the text
            .Tag = oMarketResp.market.runners(i).selectionId 'Save the selectionId in the button's Tag property
            .TextAlign = ContentAlignment.MiddleLeft  'Set the text alignment
            .Top = Tpos  'Set top position
            .Width = Bwidth 'Set button width
          End With
          Controls.Add(Buttons(i))   'Display this button on the form
          AddHandler Buttons(i).Click, AddressOf RunnerButton_Click  'Assign the event handler for this button's click event
          Tpos += PosBut   'Top position of the next button
        Next
    
      End Sub
    
      'The 'Click' event handler
    
      Private Sub RunnerButton_Click(ByVal sender As Object, ByVal e As System.EventArgs)
        Dim RunnerButton As Button = sender  'A reference to the button that was clicked
        With RunnerButton
          MsgBox(.Tag & "   " & .Text)  'Show the data for the clicked button
        End With
      End Sub
    
    End Class
    The constants (PosLeft, PosTop, PosBut, Bwidth) define the physical position of the buttons on the form. You can change these as required. These values are in pixels.

    The Buttons array will hold references to the buttons that we add.

    Sub AddRunnerButtons is called with the response object from a getMarket call as a parameter. This contains the runner info.

    For each runner we create a new Button object from the Button class (in the System.Windows.Forms namespace) and assign it to the next array element. We now set the properties of this button to what we want. We set the button’s .Text property to the runner’s name, and the selectionId is stored in the .Tag property. (The .Tag is a handy property that you can use for any purpose.)

    A windows form is said the be a “container” object, meaning that it can contain controls. Container objects have a Controls property which is a Collection object. (A Collection is a kind of array). The statement: Controls.Add(Buttons(i)) causes this button to appear on the form.

    The AddHandler statement links this button’s Click event to the event handler sub.

    That takes care of this button. the variable Tpos is incremented so that the top of the next button is positioned below this button. The process repeats until buttons for all runners have been created.

    The click event handler Sub RunnerButton_Click is executed whenever one of the buttons is clicked. The sender parameter contains a reference to the button that was clicked. Using this we can access the button’s properties, in particular .Tag which holds the selectionId. You can now take action such as setting up a bet or displaying the prices for this runner.

    Elsewhere in your program it is easy to access to properties of the runner buttons using the Buttons array. The buttons are numbered 0, 1, 2 ... n-1 corresponding to the array elements. For example:

    Buttons(2).BackColor = Color.LightBlue
    changes the colour of the button for the 3rd runner.

    --------------------------------------------------------

    We can test this using the code of Step 12 which calls getMarket to get a list of runners. Add 2 more lines to Sub bRunners_Click :

    Code:
    [COLOR="Gray"].....
    With oMarketResp        'Process the response
      CheckHeader(.header)
      Print("ErrorCode = " & .errorCode.ToString)
      If .errorCode = BFUK.GetMarketErrorEnum.OK Then
        With .market
          Print("MarketId = " & .marketId)    'Print id, name and status
          Print("Name = " & .name)
          Print("Status = " & .marketStatus.ToString)
          For i = 0 To .runners.Length - 1
            With .runners(i)
              Print(.selectionId & "  " & .name)   'Print list of runners
            End With
          Next
    [COLOR="Black"]      MarketForm.Show()    'Show the market form
          MarketForm.AddRunnerButtons(oMarketResp)  'Add the runner buttons[/COLOR]
        End With
      End If
    End With
    .....[/COLOR]
    Run the project. When you click the "Runners" button an array of runner buttons should appear on MarketForm.

    Leave a comment:


  • G-Factor
    replied
    I put a timer on it today.

    The first Login took 14397ms, then I logged out and in again several times and they ranged from 90-110ms!

    I vaguely remember reading somewhere when I first noticed this that it was something to do with 64-bit or Windows7, I can't remember now.

    It doesn't really matter, as it's only once and well before racing starts, I was just curious if anyone else had come across it.

    I do have gzip enabled, and a couple of other things (which I've tried removing with no effect) which did make my prog faster when I was on XP.

    I have this in my app.config file

    Code:
    <system.net>
    		<connectionManagement>
    			<add address="*" maxconnection="20" />
    		</connectionManagement>
    		<settings>
    			<servicePointManager
        expect100Continue="false"
        useNagleAlgorithm="false"/>
    		</settings>
    	</system.net>
    I don't have enough knowledge to know what I was doing by monitoring what's being sent and received over my network. As I said, it doesn't really matter.
    15 seconds seems like ages in this day and age though doesn't it!

    As for changing the text style in the datagridview, that doesn't really matter either. I wouldn't be using the extra information for anything, just curious if anyone had a way to do it.

    Once again, great work.

    Leave a comment:

Working...
X