URL nelle pagine master (C#)

di Scott Mitchell

Scarica il PDF

Risolve il modo in cui gli URL nella pagina master possono interrompersi a causa del file di pagina master in una directory relativa diversa rispetto alla pagina del contenuto. Esamina i rebasing degli URL tramite ~ nella sintassi dichiarativa e usa ResolveUrl e ResolveClientUrl a livello di codice. (Vedere anche

Introduzione

In tutti gli esempi finora illustrati, le pagine master e di contenuto si trovano nella stessa cartella (cartella radice del sito Web). Ma non c'è motivo per cui le pagine master e contenuto devono trovarsi nella stessa cartella. È certamente possibile creare pagine di contenuto in sottocartelle. Analogamente, è possibile creare una ~/MasterPages/ cartella in cui inserire le pagine master del sito.

Un potenziale problema relativo all'inserimento di pagine master e contenuto in cartelle diverse comporta l'interruzione degli URL. Se la pagina master contiene URL relativi in collegamenti ipertestuali, immagini o altri elementi, il collegamento non sarà valido per le pagine di contenuto che risiedono in una cartella diversa. In questa esercitazione viene esaminata l'origine di questo problema e le soluzioni alternative.

Problema con gli URL relativi

Un URL in una pagina Web viene detto url relativo se la posizione della risorsa a cui punta è relativa alla posizione della pagina Web nella struttura di cartelle del sito Web. Qualsiasi URL che non inizia con una barra iniziale (/) o un protocollo (ad esempio http://) è relativo perché viene risolto dal browser in base alla posizione della pagina Web che contiene l'URL.

Ad esempio, il sito Web ha una ~/Images/ cartella con un singolo file di immagine, PoweredByASPNET.gif. Il file Site.master di pagina master ha un <img> elemento nell'area footerContent con il markup seguente:

<div id="footerContent">
 <img src="Images/PoweredByASPNET.gif" alt="Powered by ASP.NET!" />
</div>

Il src valore dell'attributo nell'elemento <img> è un URL relativo perché non inizia con / o http://. In breve, il valore dell'attributo src indica al browser di cercare nella Images sottocartella un file denominato PoweredByASPNET.gif.

Quando si visita una pagina di contenuto, il markup precedente viene inviato direttamente al browser. Visitare e visualizzare About.aspx l'origine HTML inviata al browser. Si scoprirà che lo stesso markup nella pagina master è stato inviato al browser.

<div id="footerContent">
 <img src="Images/PoweredByASPNET.gif" alt="Powered by ASP.NET!" />
</div>

Se la pagina del contenuto si trova nella cartella radice (così come è About.aspx) tutto funziona come previsto perché è presente una Images sottocartella relativa alla cartella radice. Tuttavia, se la pagina del contenuto si trova in una cartella diversa dalla pagina master, si interrompe. Per illustrare questa operazione, creare una sottocartella denominata Admin. Aggiungere quindi una pagina di contenuto denominata Default.aspx alla Admin cartella, assicurandosi di associare la nuova pagina alla Site.master pagina master.

Nota

Nell'esercitazione Specifica del titolo, dei meta tag e di altre intestazioni HTML nell'esercitazione pagina master è stata creata una classe di pagina di base personalizzata denominata BasePage che imposta automaticamente il titolo della pagina del contenuto (se non è stato assegnato in modo esplicito). Non dimenticare di avere la classe code-behind della pagina appena creata derivare da BasePage in modo che possa usare questa funzionalità.

Dopo aver creato questa pagina di contenuto, il Esplora soluzioni dovrebbe essere simile alla figura 1.

È stata aggiunta una nuova cartella e una pagina ASP.NET al progetto

Figura 01: Una nuova cartella e ASP.NET pagina sono state aggiunte al progetto

Aggiornare quindi il Web.sitemap file in modo da includere una nuova <siteMapNode> voce per questa lezione. Il codice XML seguente illustra il markup completo Web.sitemap , che include ora l'aggiunta di un terzo <siteMapNode> elemento.

<?xml version="1.0" encoding="utf-8" ?>
<siteMap xmlns="http://schemas.microsoft.com/AspNet/SiteMap-File-1.0" >
 <siteMapNode url="~/Default.aspx" title="Home">
 <siteMapNode url="~/About.aspx" title="About the Author" />
 <siteMapNode url="~/MultipleContentPlaceHolders.aspx" title="Using Multiple ContentPlaceHolder Controls" />
 <siteMapNode url="~/Admin/Default.aspx" title="Rebasing URLs" />
 </siteMapNode>
</siteMap>

La pagina appena creata Default.aspx deve avere quattro controlli Contenuto corrispondenti ai quattro ContentPlaceHolders in Site.master. Aggiungere testo al controllo Contenuto che fa riferimento a MainContent ContentPlaceHolder e quindi visitare la pagina tramite un browser. Come illustrato nella figura 2, il browser non riesce a trovare il PoweredByASPNET.gif file di immagine. Cosa avviene qui?

La ~/Admin/Default.aspx pagina di contenuto viene inviata allo stesso codice HTML per l'area footerContent geografica in cui si trovava la About.aspx pagina:

<div id="footerContent">
 <img src="Images/PoweredByASPNET.gif" alt="Powered by ASP.NET!" />
</div>

Poiché l'attributo <img> dell'elemento src è un URL relativo, il browser tenta di cercare una Images cartella rispetto al percorso della cartella della pagina Web. In altre parole, il browser sta cercando il file Admin/Images/PoweredByASPNET.gifdi immagine .

Impossibile trovare il file di immagine PoweredByASPNET.gif

Figura 02: Impossibile trovare il PoweredByASPNET.gif file di immagine (fare clic per visualizzare l'immagine a dimensione intera)

Sostituzione degli URL relativi con URL assoluti

L'opposto di un URL relativo è un URL assoluto, ovvero uno che inizia con una barra (/) o un protocollo, ad http://esempio . Poiché un URL assoluto specifica la posizione di una risorsa da un punto fisso noto, lo stesso URL assoluto è valido in qualsiasi pagina Web, indipendentemente dalla posizione della pagina Web nella struttura di cartelle del sito Web.

Per risolvere l'immagine interrotta illustrata nella figura 2, è necessario aggiornare l'attributo <img> dell'elemento src in modo che usi un URL assoluto invece di uno relativo. Per determinare l'URL assoluto corretto, visitare una delle pagine Web nel sito Web ed esaminare la barra degli indirizzi. Come illustrato nella barra degli indirizzi nella figura 2, il percorso completo dell'applicazione Web è http://localhost:3908/ASPNET_MasterPages_Tutorial_04_CS/. Pertanto, è possibile aggiornare l'attributo <img> dell'elemento src a uno dei due URL assoluti seguenti:

  • /ASPNET_MasterPages_Tutorial_04_CS/Images/PoweredByASPNET.gif
  • http://localhost:3908/ASPNET_MasterPages_Tutorial_04_CS/Images/PoweredByASPNET.gif

È necessario aggiornare l'attributo <img> dell'elemento src a un URL assoluto usando uno dei moduli indicati in precedenza e quindi visitare la ~/Admin/Default.aspx pagina tramite un browser. Questa volta il browser troverà e visualizzerà correttamente il PoweredByASPNET.gif file di immagine (vedere la figura 3).

L'immagine PoweredByASPNET.gif è ora visualizzata

Figura 03: L'immagine PoweredByASPNET.gif è ora visualizzata (fare clic per visualizzare l'immagine a dimensione intera)

Anche se il hardcoded nell'URL assoluto funziona, associa strettamente il codice HTML al percorso del server e della cartella del sito Web, che può cambiare. L'uso di un URL assoluto del modulo http://localhost:3908/... è fragile perché il numero di porta precedente localhost viene selezionato automaticamente ogni volta che viene avviato il server Web di sviluppo ASP.NET di Visual Studio predefinito. Analogamente, la http://localhost parte è valida solo quando si esegue il test in locale. Dopo aver distribuito il codice in un server di produzione, la base URL cambierà in un altro elemento, ad esempio http://www.yourserver.com. L'URL assoluto nel formato /ASPNET_MasterPages_Tutorial_04_CS/... presenta anche la stessa fragilità perché spesso questo percorso dell'applicazione differisce tra i server di sviluppo e di produzione.

La buona notizia è che ASP.NET offre un metodo per generare un URL relativo valido in fase di esecuzione.

Uso di~eResolveClientUrl

Anziché impostare come hardcoded un URL assoluto, ASP.NET consente agli sviluppatori di pagine di usare la tilde (~) per indicare la radice dell'applicazione Web. Ad esempio, in precedenza in questa esercitazione ho usato la notazione ~/Admin/Default.aspx nel testo per fare riferimento alla Default.aspx pagina nella Admin cartella. Indica ~ che la Admin cartella è una sottocartella della radice dell'applicazione Web.

Il Control metodo della ResolveClientUrl classe accetta un URL e lo modifica in un URL relativo appropriato per la pagina Web in cui risiede il controllo. Ad esempio, la chiamata ResolveClientUrl("~/Images/PoweredByASPNET.gif") da About.aspx restituisce Images/PoweredByASPNET.gif. Chiamandola da ~/Admin/Default.aspx, tuttavia, restituisce ../Images/PoweredByASPNET.gif.

Nota

Poiché tutti i controlli server ASP.NET derivano dalla Control classe , tutti i controlli server hanno accesso al ResolveClientUrl metodo . Anche la Page classe deriva dalla Control classe , vale a dire che è possibile usare questo metodo direttamente dalle classi code-behind delle pagine di ASP.NET.

Uso~nel markup dichiarativo

Diversi controlli Web ASP.NET includono proprietà correlate all'URL: il controllo HyperLink ha una NavigateUrl proprietà, il controllo Image ha una ImageUrl proprietà e così via. Quando ne viene eseguito il rendering, questi controlli passano i relativi valori di proprietà correlati all'URL a ResolveClientUrl. Di conseguenza, se queste proprietà contengono un ~ oggetto per indicare la radice dell'applicazione Web, l'URL verrà modificato in un URL relativo valido.

Tenere presente che solo ASP.NET controlli server trasformano nella proprietà correlata all'URL ~ . Se un ~ oggetto viene visualizzato nel markup HTML statico, ad esempio <img src="~/Images/PoweredByASPNET.gif" />, il motore di ASP.NET invia al ~ browser insieme al resto del contenuto HTML. Il browser presuppone che faccia ~ parte dell'URL. Ad esempio, se il browser riceve il markup <img src="~/Images/PoweredByASPNET.gif" /> presuppone che sia presente una sottocartella denominata ~ con una sottocartella Images che contiene il file PoweredByASPNET.gifdi immagine .

Per correggere il markup dell'immagine in Site.master, sostituire l'elemento esistente <img> con un controllo Web image ASP.NET. Impostare il controllo Web image su IDPoweredByImage, la relativa ImageUrl proprietà su ~/Images/PoweredByASPNET.gife la relativa AlternateText proprietà su "Powered by ASP.NET!"

<div id="footerContent">
 <asp:Image ID="PoweredByImage" runat="server" ImageUrl="~/Images/PoweredByASPNET.gif" 
    AlternateText="Powered by ASP.NET!" />
</div>

Dopo aver apportato questa modifica alla pagina master, rivedere nuovamente la ~/Admin/Default.aspx pagina. Questa volta il PoweredByASPNET.gif file di immagine viene visualizzato nella pagina (vedere la figura 3). Quando viene eseguito il rendering del controllo Web Image, viene utilizzato il metodo per risolvere il ResolveClientUrl valore della ImageUrl proprietà. ImageUrl In ~/Admin/Default.aspx viene convertito in un URL relativo appropriato, come illustrato nel frammento di codice sorgente HTML seguente:

<div id="footerContent">
 <img id="ctl00_PoweredByImage" src="../Images/PoweredByASPNET.gif" alt="Powered by ASP.NET!" />
</div>

Nota

Oltre a essere usato nelle proprietà del controllo Web basato su URL, è ~ anche possibile usare quando si chiamano i Response.Redirect metodi e Server.MapPath , tra gli altri. Inoltre, il ResolveClientUrl metodo può essere richiamato direttamente da un ASP.NET o dal markup dichiarativo di una pagina master.

Correzione degli URL relativi rimanenti della pagina master

Oltre all'elemento nell'oggetto <img>footerContent appena corretto, la pagina master contiene un altro URL relativo che richiede l'attenzione. L'area topContent include il collegamento "Esercitazioni sulle pagine master", che punta a Default.aspx.

<div id="topContent">
 <a href="Default.aspx">Master Pages Tutorials</a>
</div>

Poiché questo URL è relativo, invierà l'utente alla Default.aspx pagina nella cartella della pagina del contenuto che sta visitando. Per fare in modo che questo collegamento punti Default.aspx sempre alla cartella radice, è necessario sostituire l'elemento <a> con un controllo Web HyperLink in modo da poter usare la ~ notazione.

Rimuovere il markup dell'elemento <a> e aggiungere un controllo HyperLink al suo posto. Impostare HyperLink su IDlnkHome, la relativa NavigateUrl proprietà su ~/Default.aspxe la relativa Text proprietà su "Master Pages Tutorials".

<div id="topContent">
 <asp:HyperLink ID="lnkHome" runat="server" NavigateUrl="~/Default.aspx"
    Text="Master Pages Tutorials" />
</div>

Questo è tutto. A questo punto tutti gli URL della pagina master vengono basati correttamente quando viene eseguito il rendering da una pagina di contenuto indipendentemente dalle cartelle in cui si trova la pagina master e la pagina del contenuto.

Risoluzione automatica degli URL nella<head>sezione

Nell'esercitazione Creazione di un layout Site-Wide usando pagine master è stato aggiunto un <link> oggetto al file nell'area Styles.css<head>:

<head runat="server">
 <title>Untitled Page</title>
 <asp:ContentPlaceHolder id="head" runat="server">
 </asp:ContentPlaceHolder>
 <link href="Styles.css" rel="stylesheet" type="text/css" />
</head>

Anche se l'attributo <link> dell'elemento href è relativo, viene convertito automaticamente in un percorso appropriato in fase di esecuzione. Come illustrato nell'esercitazione Specificare titolo, meta tag e altre intestazioni HTML nell'esercitazione Pagina master , l'area <head> è in realtà un controllo lato server, che consente di modificare il contenuto dei relativi controlli interni quando viene eseguito il rendering.

Per verificare questa operazione, rivedere la ~/Admin/Default.aspx pagina e visualizzare l'origine HTML inviata al browser. Come illustrato nel frammento di codice seguente, l'attributo <link> dell'elemento href è stato modificato automaticamente in un URL relativo appropriato, ../Styles.css.

<head>
 <title>
 Default
 </title>
 <link href="../Styles.css" rel="stylesheet" type="text/css" />
</head>

Riepilogo

Le pagine master includono spesso collegamenti, immagini e altre risorse esterne che devono essere specificate tramite un URL. Poiché la pagina master e le pagine del contenuto potrebbero non esistere nella stessa cartella, è importante evitare di usare URL relativi. Anche se è possibile usare URL assoluti con codice rigido, in modo strettamente associa l'URL assoluto all'applicazione Web. Se l'URL assoluto cambia, come spesso accade quando si sposta o si distribuisce un'applicazione Web, è necessario ricordare di tornare indietro e aggiornare gli URL assoluti.

L'approccio ideale consiste nell'usare la tilde (~) per indicare la radice dell'applicazione. ASP.NET controlli Web che contengono proprietà correlate all'URL mappano l'oggetto ~ alla radice dell'applicazione in fase di esecuzione. Internamente, i controlli Web usano il Control metodo della ResolveClientUrl classe per generare un URL relativo valido. Questo metodo è pubblico e disponibile da ogni controllo server (inclusa la Page classe), in modo da poterlo usare a livello di codice dalle classi code-behind, se necessario.

Programmazione felice!

Altre informazioni

Per altre informazioni sugli argomenti illustrati in questa esercitazione, vedere le risorse seguenti:

Informazioni sull'autore

Scott Mitchell, autore di più libri ASP/ASP.NET e fondatore di 4GuysFromRolla.com, ha lavorato con le tecnologie Web Microsoft dal 1998. Scott lavora come consulente indipendente, allenatore e scrittore. Il suo ultimo libro è Sams Teach Yourself ASP.NET 3,5 in 24 ore. Scott può essere raggiunto all'indirizzo mitchell@4GuysFromRolla.com o tramite il suo blog all'indirizzo http://ScottOnWriting.NET.

Grazie speciali

Interessati a esaminare i prossimi articoli MSDN? In tal caso, lasciami una riga in mitchell@4GuysFromRolla.com.