2009-09-05 8 views
8

Étant donné une URL A qui est redirigé vers un site Web tiers B, dans mon application, je dois trouver l'URL B pour l'url A donnée et l'insérer dans DB, cela peut être un application de Windows ou web ou de quelque manière que ce soit plus rapide et plus facile en utilisant C#! Merci!Un moyen de comprendre l'URL de redirection

P.S. Je n'ai pas besoin du code pour insérer dans DB.

+2

dépend de la façon la redirection fonctionne. Du côté serveur? Côté client (c'est-à-dire JS)? Essayez d'extraire l'URL avec tous les wrappers http que possède C#, et après tout 301s/302s. Si vous êtes chanceux, il pourrait même y avoir une bibliothèque pour le faire pour vous. Que faire si B redirige vers C? Voulez-vous stocker B ou C? Jusqu'où allez-vous suivre les redirections? Que faire si C redirige vers B? Assurez-vous d'éviter les boucles de redirection infinies en gardant une trace des adresses que vous avez visitées, ou en définissant une limite de redirection (ce qui est la manière dont Firefox/Chrome gère ce problème). –

+0

Exemple côté serveur serait bien ... c'est juste un outil pour extraire des données (c'est-à-dire l'URL finale) donc ne doit pas être fantaisie ... peut être fait en aucune façon! "A" redirigera toujours vers "B" et il n'y a plus de redirection à venir de là-bas qui est un fait établi. –

+0

Le code côté client ne fait pas trop mal ... Im en supposant qu'une application de formulaire de gain avec une instance de IE à l'intérieur devrait faire le travail ... juste pas sûr –

Répondre

10

WebRequest suit réoriente sans intervention de l'utilisateur, donc si les redirections utilisent 301/302 codes d'état les commandes suivantes vont travailler

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

Si les redirections sont créés en utilisant javascript ou balises meta http-equiv vous » re faire d'avoir à analyser la page et chercher ceux-ci. Le pack d'agilité HTML est probablement le meilleur moyen de le faire.

Pour prendre un peu plus loin ce qui suit est une classe qui résoudra manuellement les principaux codes d'état de redirection HTTP, la construction d'une histoire comme il va

/// <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;    
    } 
} 
+0

Merci fonctionne parfaitement! –

+0

Cela ne fonctionnera pas si l'en-tête Location contient un URI relatif. Je crois: 'Uri redirectUri; if (! Uri.TryCreate (emplacement, UriKind.Absolute, out redirectUri)) {if (! Uri.TryCreate (réponse.ReponseUri, emplacement, out redirectUri)) {throw new WebException ("Invalid redirect"); }} 'fonctionnera dans plus/plus/(tous si les étoiles s'alignent) cas, mais ne l'a pas encore testé complètement. –

+0

Quelle magnifique réponse. – Ikaso

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>"); 

Comme ce que je comprends de votre question, vous pouvez utiliser un code comme celui-ci afin que vous puissiez voir l'URL précédente et l'enregistrer dans db en utilisant Linq ou d'autres méthodes de ADO.NET. Je suppose que vous savez comment sauvegarder un enregistrement en DB avec LINQ. Si vous ne le faites pas s'il vous plaît suivez ce lien: LINQ to SQL - 5 Minute Overview

Espérons que ça aide.