locked
How to get Bing Map Session Key RRS feed

  • Question

  • To reduce the billable transaction in my web form asp.net project, i decided to test it.

    I have come across following example on msdn for session key.

    Map.CredentialsProvider.GetCredentials(
        Function(c)
            Dim sessionKey As String = c.ApplicationId
            'Generate a request URL for the Bing Maps REST services.
            'Use the session key in the request as the Bing Maps key
           Return 0
        End Function)

    Code Example;

    private String GeocodeAddress(string address)
    {    string results = "";
    
    string key = "Bing Maps key";
    GeocodeRequest geocodeRequest = new GeocodeRequest();
    
    // Set the credentials using a valid Bing Maps key
    geocodeRequest.Credentials = new GeocodeService.Credentials();
    geocodeRequest.Credentials.ApplicationId = key;
    
    // Set the full address query
    geocodeRequest.Query = address;
    
    // Set the options to only return high confidence results 
    ConfidenceFilter[] filters = new ConfidenceFilter[1];
    filters[0] = new ConfidenceFilter();
    filters[0].MinimumConfidence = GeocodeService.Confidence.High;
    
    // Add the filters to the options
    GeocodeOptions geocodeOptions = new GeocodeOptions();
    geocodeOptions.Filters = filters;
    geocodeRequest.Options = geocodeOptions;
    
    // Make the geocode request
    GeocodeServiceClient geocodeService = new GeocodeServiceClient();
    GeocodeResponse geocodeResponse = geocodeService.Geocode(geocodeRequest);
    
    if (geocodeResponse.Results.Length > 0)
        results = String.Format("Latitude: {0}\nLongitude: {1}", 
          geocodeResponse.Results[0].Locations[0].Latitude, 
          geocodeResponse.Results[0].Locations[0].Longitude);
    else
        results = "No Results Found";
    
    return results;
    }
    After debugging it, i can't see any difference b/w (application id / session key) and Bing Api key. How can i get sessionkey in above example?

    Wednesday, October 15, 2014 10:33 AM

Answers

  • By postback I hope you are using an AJAX post back and not an old type of postback which reloads the page. The older type of postbacks are really inefficient and make for a poor user experience.

    I would get rid of page B and keep everything on page A and load the map dynamically. This will make for a better user experience and be more inline with how most large websites present data on a map.

    If you must have a page B then grab the data out of the session and use that to populate your map.

    To get the distances, pass the location data as an array of coordinates to the client and pass it to a JavaScript function. Have the JavaScript function fire after loading the map. hen the function fires, have it create a URL to the Bing Maps REST routing service to create a multiple point route from A to B to A To C To A .... for all your locations (assuming 12 or less locations). This will create a single route request. With the response grab the distance values from the odd route legs in the array. This will give you all the distances you want. The blog post I linked to shows how to do this.


    http://rbrundritt.wordpress.com

    • Proposed as answer by Ricky_Brundritt Friday, October 17, 2014 10:10 AM
    • Marked as answer by MUAR Thursday, October 23, 2014 8:06 AM
    Friday, October 17, 2014 10:10 AM

All replies

  • The session key can only be used on the same page as the interactive map. Passing a session key between pages is not allowed. Assuming that you have an AJAX button or something that is processing some code on the server and returning it to the same page as the map, then this would be alright.

    The first bit of code looks like you are trying to generate a session key in .NET. This would only be possible if you where using Silverlight or WPF. I'll assume you are not using the Bing Maps WPF control on the server as that's really against the terms of use. If you are using Silverlight, then there is no need to pass a key to the server side.

    So lets assuming you generate a key in JavaScript from the Bing Maps v7 control and pass it to AJAX button handler on the server. If this is the case then it's alright.

    In your code it looks like you are using the really old legacy SOAP services which is not recommended. In fact I stopped recommending them about 4 or 5 years ago. The documentation was taken offline a couple of years ago. You should be using the Bing Maps REST services which are faster, more accurate and has more features. You can find documentation on how to use them in .NET here: http://msdn.microsoft.com/en-us/library/jj819168.aspx

    Also, here are some tips on using the REST services: http://blogs.bing.com/maps/2013/02/14/bing-maps-rest-service-tips-tricks/

    ApplicationId and session key are the same thing. The SOAP services are so old it used to have a different name.

    You won't see any differences in the reports right away. It can take up to a week for the reports to sync up across all the servers/data centers as it's a low priority job with massive amounts of data.

    If your application has decent traffic you will likely end up with a lot more non-billable transactions than billable transactions which will likely cause your account to be flagged and investigated and possibly blocked.

    What you should be doing is geocoding your addresses ahead of time and storing the coordinates. This is how most applications handle this type of scenario. The only time you should need to geocode on the fly is if you have a search box for user input, all everything else should be geocoded ahead of time for performance.


    http://rbrundritt.wordpress.com


    Wednesday, October 15, 2014 2:20 PM
  • Plan is to buy the Bing Map light user license, but before its done i need to test it first.

    I am trying to implement Bing Map on my asp.net web form application. I am trying to figure out how to get the session key from code behind the page. I can do with java script but from code behind i don't know if it is possible.

    I am thinking about using session key to reduce billable transaction.

    I have a generic list of engineers which contains addresses including Lat and Lng values. Is it possible to loop through the list and calculated travel distance from given lat and lng before displaying them on the repeater control (just showing distance values) using one session key.




    • Edited by MUAR Wednesday, October 15, 2014 3:31 PM
    Wednesday, October 15, 2014 3:21 PM
  • If you have a Known User (or light Known user) then sessions won't change anything in terms of cost. With a known user license you pay for the number of users who have access to the app and not the number of transactions that are created.

    This is the limits that are documented in the current terms of use:

    You may not exceed 5 million total forward or reverse geocoding transactions, sessions or routing requests per year under the Bing Maps Enterprise Platform Service SL or Bing Maps Light Known User SL. Should you license more than 5000 Light Known User SLs these limits will be increased at the rate of 10 requests per Light Known User within any 24 hour period and 1000 requests per Light Known User per year, for each Light Known User SL above 5,000. Such increased limits will continue for the duration that you license more than 5,000 Bing Maps Light Known User SLs. 

    In this case a session refers to a map load.


    http://rbrundritt.wordpress.com

    Thursday, October 16, 2014 8:14 AM
  • Is 5 million limit per user or for all users.

    i.e. 1(user) x 5 million

    or

    300(users) x 5 million

    Also, What is meant by 'not updating the location' under Light Known User terms; If someone is showing multiple location markers on map then is it same as updating map?

    The Light Known User option is chosen when a customer has a consistent user base with users that will only be viewing the map and not updating the location (e.g. internal locators) with ability to fix costs for the service.


    • Edited by MUAR Thursday, October 16, 2014 8:44 AM
    Thursday, October 16, 2014 8:38 AM
  • For a small number of users, less than 5000, the maximum number of transactions for a known user account stays the same. After 5000 users it then increases. Note that the daily limit is the most transactions that can be done in a day, not the most transactions you can do everyday. There is a yearly limit as well which is the cap. The idea is to prevent someone from using a years worth of transactions in a single day

    http://rbrundritt.wordpress.com

    Thursday, October 16, 2014 1:15 PM
  • sorry i am confused, is your second comment still valid? Does session key matters for Light Known Users?
    • Edited by MUAR Thursday, October 16, 2014 1:40 PM
    Thursday, October 16, 2014 1:40 PM
  • A session key is different from a map session which is what the terms of use are referring to. A session key doesn't matter for light known users.

    As for the updating of locations. That refers to updating the physical location of a pushpin manually to correct data. For example, lets say you load a bunch of pins on the map, but you want to be able to correct their location using a mouse. This requires using a full known user license rather than a light one.


    http://rbrundritt.wordpress.com

    Thursday, October 16, 2014 1:43 PM
  • Thanks for your reply :)

    Just to get it right

    - If i am showing lets say 10 pins or locations on map in one go then would it count as one transaction? Here is the code

    Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
            Dim Locations As String = GetLocations()
            Dim LitStr As String = ""
    
            LitStr = "<script type='text/javascript' src='http://ecn.dev.virtualearth.net/mapcontrol/mapcontrol.ashx?v=7.0'></script>"
            LitStr = LitStr & " <script type='text/javascript'>"
    
            LitStr = LitStr & " var  map = new Microsoft.Maps.Map(document.getElementById('myMap'), {"
            LitStr = LitStr & " credentials: 'KEY'"
            LitStr = LitStr & " });"
            LitStr = LitStr & " function GetMap() {"
            LitStr = LitStr & " map.entities.clear();  " & vbCr & vbLf & "                        " + Locations + vbCr
            LitStr = LitStr & " function ZoomIn(e){"
            LitStr = LitStr & " if (e.targetType == 'pushpin'){"
            LitStr = LitStr & " var location = e.target.getLocation();"
            LitStr = LitStr & " map.setView({"
            LitStr = LitStr & " zoom:5,"
            LitStr = LitStr & " center: Location()"
            LitStr = LitStr & "  });"
            LitStr = LitStr & "  }"
            LitStr = LitStr & "  }"
            LitStr = LitStr & "  }"
            LitStr = LitStr & " </script>"
    
            Literal1.Text = LitStr
        End Sub
    
    
        Private Function GetLocations() As String
            Dim Locations As String = ""
            listI = CType(Session("SearchIns"), List(Of Inspector))
    
            For Each item As Inspector In listI
                Locations += "var pushpin = new Microsoft.Maps.Pushpin(new Microsoft.Maps.Location(" + item.Lat.ToString + ", " + item.Lng.ToString + "), null);Microsoft.Maps.Events.addHandler(pushpin, 'click', ZoomIn);map.entities.push(pushpin);"
            Next
    
            Return Locations
        End Function

    -If i am looping through the generic list of addresses to get travel distance then would it count as one transaction? Here is the code i am using for test;

     Private Function GetDistance(ByRef _list As List(Of Inspector)) As List(Of Inspector)
            Dim newList As New List(Of Inspector)
    
    
            Dim request As New BingRoutingService.RouteRequest()
            Dim creds As New BingRoutingService.Credentials()
    
            creds.ApplicationId = System.Configuration.ConfigurationManager.AppSettings("BingMapAPIKey") 
            request.Credentials = creds
    
            For Each item As Inspector In _list
                Dim address1Coordinate As Double() = New Double() {item.Lat, item.Lng}
                Dim address2Coordinate As Double() = New Double() {CDbl(hdVendorLat.Value), CDbl(hdVendorLng.Value)}
    
                Dim waypoints As BingRoutingService.Waypoint() = New BingRoutingService.Waypoint(1) {}
                waypoints(0) = New BingRoutingService.Waypoint()
                Dim start As New BingRoutingService.Location()
                start.Latitude = address1Coordinate(0)
                start.Longitude = address1Coordinate(1)
                waypoints(0).Location = start
                waypoints(1) = New BingRoutingService.Waypoint()
                Dim [end] As New BingRoutingService.Location()
                [end].Latitude = address2Coordinate(0)
                [end].Longitude = address2Coordinate(1)
                waypoints(1).Location = [end]
                request.Waypoints = waypoints
    
                Dim client As New RouteServiceClient(("BasicHttpBinding_IRouteService"))
                Dim response As RouteResponse = client.CalculateRoute(request)
                Dim result As RouteResult = response.Result
                Dim routeSummary As BingRoutingService.RouteSummary = result.Summary
    
                item.TravelDistance = Math.Round(routeSummary.Distance, 2) 
                newList.Add(item)
            Next item
    
            Return newList
    
        End Function



    • Edited by MUAR Saturday, October 18, 2014 6:32 PM
    Thursday, October 16, 2014 2:07 PM
  • Adding pushpins like you are won't generate any transactions.

    Calculating the driving distance like you are will generate a lot of billable transactions. You should be calculating these distances in client side code using a session key. You should also group multiple locations into a multi-waypoint route to reduce the number of route calls being made. Here is a blog post on how to do this: http://blogs.bing.com/maps/2011/03/18/dev-tip-of-the-week-how-to-search-by-driving-time-with-ajax-v7-rest-and-spatial-data-services/


    http://rbrundritt.wordpress.com

    Friday, October 17, 2014 8:15 AM
  • Code link is not working.

    Here is what happening on asp.net form

    - User select the search criteria and click the search button on Page A.

    - On post Back, Call is made to database and data layer returns Generic List of Inspectors. (addresses and Lat and Lng values are part list)

    - Results are shown on Page A (see attached image). I am calculating distance before results are displayed. At this point, list is saved in session.

    - On Page A, there is a Button called 'Results on Map', if user clicks on this button it will navigate him to different page (page B).

    - On Page B load event, i am getting list from session and dynamically creating java script function and push points from code behind and showing them on Map.

    To get the distance of multiple addresses from given point, how can i send the generic list or list data in any other form to client side and then calculate distance and send data back to server?


    • Edited by MUAR Friday, October 17, 2014 9:39 AM
    Friday, October 17, 2014 9:05 AM
  • By postback I hope you are using an AJAX post back and not an old type of postback which reloads the page. The older type of postbacks are really inefficient and make for a poor user experience.

    I would get rid of page B and keep everything on page A and load the map dynamically. This will make for a better user experience and be more inline with how most large websites present data on a map.

    If you must have a page B then grab the data out of the session and use that to populate your map.

    To get the distances, pass the location data as an array of coordinates to the client and pass it to a JavaScript function. Have the JavaScript function fire after loading the map. hen the function fires, have it create a URL to the Bing Maps REST routing service to create a multiple point route from A to B to A To C To A .... for all your locations (assuming 12 or less locations). This will create a single route request. With the response grab the distance values from the odd route legs in the array. This will give you all the distances you want. The blog post I linked to shows how to do this.


    http://rbrundritt.wordpress.com

    • Proposed as answer by Ricky_Brundritt Friday, October 17, 2014 10:10 AM
    • Marked as answer by MUAR Thursday, October 23, 2014 8:06 AM
    Friday, October 17, 2014 10:10 AM
  • In your blog, there is no code, When i click on the code link it shows error message.

    I am not using Ajax Post back.

    Is there any limit how many route request you cam made (for light known users) in one go? Because database can return any number of results (or addresses) may by 60 depends on user's search criteria.

    Basically user wants to see the list of inspectors from the one vendor location, within certain radius. User will given the vendor location (Lat and Lng) and radius value (i.e. 60).

    Friday, October 17, 2014 10:34 AM
  • It's not my code sample. Looks like the source code got deleted.

    There is a limit to the number of route requests you can make under a light known user license. It's part of the 5 Million total transactions allowed for light known user licenses that I mentioned earlier.

    Send me an email at ricky_brundritt at Hotmail.com and we can discuss this further and I'll loop you in with a licensing person who can answer your licensing related questions.


    http://rbrundritt.wordpress.com

    Friday, October 17, 2014 6:16 PM
  • I will email you later today.

    I have gone through the bing map code examples in detail, very useful :)

    I have one question regarding using session key.

    In my second code example where i am getting travel distance by looping through the generic list. Would that be okay if i load the map at client side the first time asp.net page is loaded and save the key in hidden field at client side and use it on every post back (of this same page) at server side.

    creds.ApplicationId = hiddenfield.Value

    If user go to page B and come back on Page A then the new map will be loaded with new key which i can use against any number of addresses after each post back of page A.

    ADDED

    I think i have finally found the server side solution on http://msdn.microsoft.com/en-GB/library/dd221354.aspx

    Here is my code for creating way point and getting route distance in one go.

    I think it would be counted as one transaction.

    private string CreateMajorRoutes(string locationString)
    {
        string results = "";
        MajorRoutesRequest majorRoutesRequest = new MajorRoutesRequest();
    
        // Set the credentials using a valid Bing Maps key
        majorRoutesRequest.Credentials = new RouteService.Credentials();
        majorRoutesRequest.Credentials.ApplicationId = key;
    
        // Set the destination of the routes from major roads
        Waypoint endPoint = new Waypoint();
        endPoint.Location = new RouteService.Location();
        string[] digits = locationString.Split(',');
        endPoint.Location.Latitude = double.Parse(digits[0].Trim());
        endPoint.Location.Longitude = double.Parse(digits[1].Trim());
        endPoint.Description = "Location";
    
        // Set the option to return full routes with directions
        MajorRoutesOptions options = new MajorRoutesOptions();
        options.ReturnRoutes = true;
    
        majorRoutesRequest.Destination = endPoint;
        majorRoutesRequest.Options = options;
    
        // Make the route-from-major-roads request
        RouteServiceClient routeService = new RouteServiceClient();
    
        // The result is an MajorRoutesResponse Object
        MajorRoutesResponse majorRoutesResponse = routeService.CalculateRoutesFromMajorRoads(majorRoutesRequest);
    
        Regex regex = new Regex("<[/a-zA-Z:]*>", 
          RegexOptions.IgnoreCase | RegexOptions.Multiline);
    
        if (majorRoutesResponse.StartingPoints.Length > 0)
        {
            StringBuilder directions = new StringBuilder();
            
            for (int i = 0; i < majorRoutesResponse.StartingPoints.Length; i++)
            {
                directions.Append(String.Format("Coming from {1}\n", i+1, 
                    majorRoutesResponse.StartingPoints[i].Description));
    
                for (int j = 0; 
                  j < majorRoutesResponse.Routes[i].Legs[0].Itinerary.Length; j++)
                {
                    //Strip tags
                    string step = regex.Replace(
                      majorRoutesResponse.Routes[i].Legs[0].Itinerary[j].Text, string.Empty);
                    directions.Append(String.Format("     {0}. {1}\n", j + 1, step));
                }
            }
    
            results = directions.ToString();
        }
        else
            results = "No Routes found";
        
        return results;
    }

    Now my question is that how many way points i can create in one go. Is it 25?

    If my generic list contains 75 addresses then do i need to send three route request with 25 way points? And it would count as 3 billable requests?


    • Edited by MUAR Saturday, October 18, 2014 9:24 PM
    Saturday, October 18, 2014 6:46 PM