8

Given a URL A which gets redirected to a 3rd party website B, in my application I need to to find out URL B for the given url A and insert it in DB , this can be a windows application or web or whichever way is faster and easier using C#! Thanks !

P.S. I do not require the code to insert in DB.

Murtaza Mandvi
  • 10,708
  • 23
  • 74
  • 109
  • 2
    Depends how the redirect works. Server-side? Client-side (i.e. JS)? Try fetching the URL with whatever http wrappers C# has, and following any 301s/302s. If you're lucky there might even be a library to do that for you. What if B redirects to C? Do you want to store B or C? How far will you follow redirects? What if C redirects to B? Make sure you avoid infinite redirection loops by keeping track of what addresses you've visited, or setting a redirection limit (which I think is how Firefox/Chrome handle this issue). – Dominic Rodger Sep 05 '09 at 06:49
  • Server side example would be fine...this is just a tool to extract data (i.e. final URL) so does not have to be fancy ...can be done in any way ! "A" will always redirect to "B" and there is no more redirection to happen further on from there that is an established fact. – Murtaza Mandvi Sep 05 '09 at 06:52
  • Client side code does not hurt too ...Im assuming a win form application with an instance of IE inside should do the job...just not sure – Murtaza Mandvi Sep 05 '09 at 06:53
  • In simple words, you want to know where the user came from to fall in your site? Thats it? Request.ServerVariables("HTTP_REFERER")? – Havenard Sep 05 '09 at 06:58
  • just to clarif this is jsuta tool lets say I have a URL www.abc.com which when typed internal (from their own server) redirects to a 3rd party site i.e. www.def.com and both the URL's are not in any way associated with my own site ...in the tool I should give it the 1st URL i.e. www.abc.coma nd it should give me the result as www.def.com and thats it ! Referer wlogic would only work in the case that the final URL would be my own site which is not the case. – Murtaza Mandvi Sep 05 '09 at 07:02

2 Answers2

11

WebRequest follows redirects without user intervention, so if the redirects are using 301/302 status codes then the following will work

WebRequest request = WebRequest.Create(destination);
WebResponse response = request.GetResponse();
Console.WriteLine(response.ResponseUri);

If the redirects are created using javascript or HTTP-Equiv meta tags then you're doing to have to parse the page and look for those. The HTML agility pack is probably the best way to do this.

To take this a little further the following is a class which will manually resolve the main HTTP redirect status codes, building up a history as it goes

/// <summary>
/// Digs through HTTP redirects until a non-redirected URL is found.
/// </summary>
public class Digger
{
    /// <summary>
    /// Initializes a new instance of the <see cref="Digger"/> class.
    /// </summary>
    public Digger() : this(20)
    {            
    }

    /// <summary>
    /// Initializes a new instance of the <see cref="Digger"/> class.
    /// </summary>
    /// <param name="maximumDepth">The maximum depth of redirects to parse.</param>
    public Digger(int maximumDepth)
    {
        this.MaximumDepth = maximumDepth;
    }

    /// <summary>
    /// Gets the maximum depth of redirects to parse.
    /// </summary>
    /// <value>The maximum depth of redirects to parse.</value>
    public int MaximumDepth
    {
        get; 
        private set;
    }

    /// <summary>
    /// Resolves any redirects at the specified URI.
    /// </summary>
    /// <param name="destination">The initial URI.</param>
    /// <returns>The URI after resolving any HTTP redirects.</returns>
    public Uri Resolve(Uri destination)
    {
        List<Uri> redirectHistory = new List<Uri>();
        return this.Resolve(destination, redirectHistory);
    }

    /// <summary>
    /// Resolves any redirects at the specified URI.
    /// </summary>
    /// <param name="destination">The initial URI.</param>
    /// <param name="redirectHistory">A collection of <see cref="Uri"/> objects representing the redirect history.</param>
    /// <returns>The URI after resolving any HTTP redirects.</returns>
    public Uri Resolve(Uri destination, ICollection<Uri> redirectHistory)
    {
        redirectHistory.Add(destination);
        return this.Resolve(destination, this.MaximumDepth, redirectHistory);
    }

    /// <summary>
    /// Resolves any redirects at the specified URI.
    /// </summary>
    /// <param name="destination">The initial URI.</param>
    /// <param name="hopsLeft">The maximum number of redirects left to follow.</param>
    /// <param name="redirectHistory">A collection of <see cref="Uri"/> objects representing the redirect history.</param>
    /// <returns>The URI after resolving any HTTP redirects.</returns>
    private Uri Resolve(Uri destination, int hopsLeft, ICollection<Uri> redirectHistory)
    {
        HttpWebRequest request = (HttpWebRequest)WebRequest.Create(destination);
        request.AllowAutoRedirect = false;
        request.Method = "HEAD";

        HttpWebResponse response = (HttpWebResponse)request.GetResponse();

        Uri resolvedUri;

        if (response.StatusCode == HttpStatusCode.Redirect || 
            response.StatusCode == HttpStatusCode.Moved || 
            response.StatusCode == HttpStatusCode.MovedPermanently)
        {
            if (hopsLeft > 0)
            {
                Uri redirectUri = new Uri(response.GetResponseHeader("Location"));
                if (redirectHistory.Contains(redirectUri))
                {
                    throw new Exception("Recursive redirection found");
                }

                redirectHistory.Add(redirectUri);
                resolvedUri = this.Resolve(redirectUri, hopsLeft - 1, redirectHistory);
            }
            else
            {
                throw new Exception("Maximum redirect depth reached");
            }
        }
        else
        {
            resolvedUri = response.ResponseUri;
        }

        return resolvedUri;            
    }
}
blowdart
  • 55,577
  • 12
  • 114
  • 149
  • This will not work if the Location header contains a relative URI. I believe: `Uri redirectUri; if (!Uri.TryCreate(location, UriKind.Absolute, out redirectUri)) { if (!Uri.TryCreate(response.ResponseUri, location, out redirectUri)) { throw new WebException("Invalid redirect"); } }` will work in more/most/(all if the stars align) cases, but haven't tested it thoroughly yet. –  Aug 18 '11 at 21:48
  • This solution is easy. Thanks – ROOT Sep 19 '18 at 14:04
0
Uri MyUrl = Request.UrlReferrer;
Response.Write("Referrer URL Port: " + Server.HtmlEncode(MyUrl.Port.ToString()) + "<br>");
Response.Write("Referrer URL Protocol: " + Server.HtmlEncode(MyUrl.Scheme) + "<br>");

As what I understand from your question you can use a code like this so you can see the previous url and save it into db by using Linq or other ADO.NET methods.

I assume that you know how to save record in db with LINQ. If you don't please follow this link : LINQ to SQL - 5 Minute Overview

Hope it helps.

Tarik
  • 79,711
  • 83
  • 236
  • 349