2

I've been working on this for a few days and have read a lot of the details on the site here, but have yet to get this working.

I am looking to have OpenLayers running on our internal Intranet. I have OpenLayers up on IIS7, and have come to understand that I need to get a proxy file configured to serve both KML layers hosted locally, and calls to base maps that are web based.

If all these assumptions have been right thus far, I just have a question about getting the proxy to work.

1) First question, do I need to change any of the code in this file? I still don't understand how referencing this file as is connects to my local OL directory

using System;
using System.Configuration;
using System.Diagnostics;
using System.IO;
using System.Net;
using System.Text;
using System.Web;

/// <summary>
/// adapted from: http://code.google.com/p/iisproxy
/// </summary>
public class host : IHttpHandler
{
public void ProcessRequest(HttpContext context)
{
    Stopwatch watch = new Stopwatch();
    watch.Start();

    try
    {
        string uri = context.Request.QueryString["url"];
        if (String.IsNullOrEmpty(uri))
            throw new ArgumentException("url parameter null");

        StringBuilder sb = new StringBuilder();
        foreach (string s in context.Request.QueryString)
            if (!String.Equals(s, "url"))
                sb.AppendFormat("&{0}={1}", s, context.Request.QueryString[s]);
        if (sb.Length > 0)
            uri += String.Format("?{0}", sb.Remove(0, 1));

        HttpWebRequest req = (HttpWebRequest)WebRequest.Create(uri);
        req.AllowAutoRedirect = false;
        req.Method = context.Request.HttpMethod;
        req.ContentType = context.Request.ContentType;
        req.UserAgent = context.Request.UserAgent;

        string basicPwd = ConfigurationManager.AppSettings.Get("basicPwd");
        req.Credentials = basicPwd == null ? CredentialCache.DefaultCredentials : new NetworkCredential(context.User.Identity.Name, basicPwd);
        req.PreAuthenticate = true;
        req.Headers["Remote-User"] = context.User.Identity.Name;

        foreach (string s in context.Request.Headers)
            if (!WebHeaderCollection.IsRestricted(s) && !String.Equals(s, "Remote-User"))
                req.Headers.Add(s, context.Request.Headers[s]);

        if (context.Request.HttpMethod == "POST")
        {
            Stream outputStream = req.GetRequestStream();
            CopyStream(context.Request.InputStream, outputStream);
            outputStream.Close();
        }

        HttpWebResponse response;
        try
        {
            response = (HttpWebResponse)req.GetResponse();
        }
        catch (WebException we)
        {
            response = (HttpWebResponse)we.Response;
            if (response == null)
            {
                context.Response.StatusCode = 13;
                context.Response.Write("Could not contact back-end site");
                context.Response.End();
                return;
            }
        }

        context.Response.StatusCode = (int)response.StatusCode;
        context.Response.StatusDescription = response.StatusDescription;
        context.Response.ContentType = response.ContentType;
        if (response.Headers.Get("Location") != null)
        {
            string urlSuffix = response.Headers.Get("Location");
            if (urlSuffix.ToLower().StartsWith(ConfigurationManager.AppSettings["ProxyUrl"].ToLower()))
                urlSuffix = urlSuffix.Substring(ConfigurationManager.AppSettings["ProxyUrl"].Length);
            context.Response.AddHeader("Location", context.Request.Url.GetLeftPart(UriPartial.Authority) + urlSuffix);
        }

        foreach (string s in response.Headers)
            if (!WebHeaderCollection.IsRestricted(s) && !String.Equals(s, "Location"))
                context.Response.AddHeader(s, response.Headers[s]);

        CopyStream(response.GetResponseStream(), context.Response.OutputStream);
        response.Close();
        context.Response.End();
    }
    catch (Exception ex)
    {
        Trace.WriteLine("proxy error: " + ex);
        throw;
    }
    finally
    {
        watch.Stop();
        string message = String.Format("request sent in {0} milliseconds", watch.ElapsedMilliseconds);
        Debug.WriteLine(message);
    }
}

static void CopyStream(Stream input, Stream output)
{
    byte[] buffer = new byte[1024];
    int bytes;
    while ((bytes = input.Read(buffer, 0, 1024)) > 0)
        output.Write(buffer, 0, bytes);
}

public bool IsReusable
{
    get { return false; }
}

}

2) Second. When I go to the local proxy address, I am getting this error: Server Error in '/' Application.

Any help is much appreciated.

2

The reason for using a proxy, at least as far as I am aware, is to resolve Cross Domain Issues, where you are trying to load from another domain.

If your OpenLayers is hosted on the intranet at

http://myserver/index.html

and your kml file sits at

http://myserver/mykml.kml

then there is no need for a proxy.

Most likely, there is a problem serving the kml. I would guess you have not set the kml/kmz/json mime types in IIS, they are not set by default.

Go to IIS Manager, choose your web site, open MIME Types in the Features view and add the following if they are not there already:

.kml    application/vnd.google-earth.kml+xml
.kmz    application/vnd.google-earth.kmz
.json   application/json

Good chance this will resolve your problem

| improve this answer | |
  • Awesome! Thanks so much, this resolved the problem. Man, I got way too far into the weeds with proxies and other stuff...thanks a bunch. – BrianJBaldwin Oct 7 '13 at 17:09
  • Feel free to Upvote the answer. Glad it helped. – Mark Cupitt Oct 8 '13 at 1:26
  • consider it upvoted. – BrianJBaldwin Oct 8 '13 at 15:30
0

It has been a good number of years since I last used IIS (luckily) but I believe the easiest way to deploy this proxy is to create a new web application (in IIS) for it, so that it can be accessible at an address like http://myserver/proxy. And myserver must be the same domain you are using to access your OL application.

| improve this answer | |
0

I do not see why you need a proxy at all, unless I am misunderstanding what you are trying to achieve.

OpenLayers is a Client Js package served from your IIs server, or a public CDN as you prefer

So assuming you have an Intranet and your IIS server is on a machine accessible from the Intranet and you have a web site set up with the appropriate html to display the OpenLayers Map no proxy is needed.

Your kml files should reside on this machine as well. If they are on another machine, use a Virtual Directory to add them to the web site via a UNC path.

Now, eveything is on one web site so there are no cross domain issues and your kml should display just fine.

You can easily use OSM, Google or any other public Tile Service to display background maps, again without needing a proxy.

| improve this answer | |
  • This issue has come up, and the reason that it seemed I needed the proxy is that even the OL example files with KML will not load when hosted locally (on the intranet). The OSM and tile services display fine, but the KML does not load. I never thought this would be an issue, but through digging it seems that the proxy is the issue, but I could still be wrong. – BrianJBaldwin Oct 6 '13 at 14:19
  • See Answer for response to this – Mark Cupitt Oct 6 '13 at 23:58

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.