2015-08-14 17 views
6

Ho il seguente come parte di una vista del modello che popola una vista parziale:Link rottura quando View Serialized

public string DownloadLink 
{ 
    get 
    { 
     UrlHelper url = new UrlHelper(HttpContext.Current.Request.RequestContext); 
     switch (this.Type) 
     { 
      case (int)DocumentTypes.WasteNote: { 

       return url.Action("PaperWork", "Jobs", new { JobId = this.DOCJobId }, HttpContext.Current.Request.IsSecureConnection ? "https" : "http"); 
      } 
      case (int)DocumentTypes.Contract: 
      case (int)DocumentTypes.DestructionCert: 
      case (int)DocumentTypes.Quote: 
      default: { return url.Action("Download", "Documents", new { DocId = this.DocumentLinkId }, HttpContext.Current.Request.IsSecureConnection ? "https" : "http"); } 
     } 
    } 
} 

Chiamato nella visualizzazione così:

@model IEnumerable<Document> 
@using CustomerDashboard.ViewModels; 
@using CustomerDashboard.Utilities; 
@{ Layout = null; } 
    @foreach (Document doc in Model) 
    { 
     <li> 
      <a href="@doc.DownloadLink" class="documentDownload"> 
       <div class="col-sm-12 col-md-5 li-row li-row-icon"> 
        <div class="pull-left"> 
         <img height="40" src="/Content/img/file-icons/@doc.Icon" /> 
        </div> 
        ... 
      </a> 
     </li> 
    } 

Mentre questo viene reso direttamente un altro Visualizza il collegamento generato va bene, tuttavia sto serializzando il partial e restituendo come JSON:

public string RenderRazorViewToString(string viewName, object model) 
    { 
     //https://gist.github.com/timiles/2828976 
     ViewData.Model = model; 
     using (var sw = new StringWriter()) 
     { 
      var viewResult = ViewEngines.Engines.FindPartialView(ControllerContext, 
                    viewName); 
      var viewContext = new ViewContext(ControllerContext, viewResult.View, 
             ViewData, TempData, sw); 
      viewResult.View.Render(viewContext, sw); 
      viewResult.ViewEngine.ReleaseView(ControllerContext, viewResult.View); 
      return sw.GetStringBuilder().ToString(); 
     } 
    } 

E 'poi tornato come JSON dal controller:

 return Json(new { 
      totalCount = (int)Session["DocumentTotalCount"], 
      markup = RenderRazorViewToString("_DocumentListAjax", docs) 
     },JsonRequestBehavior.AllowGet); 

essere chiaro, però, il problema sta accadendo prima della serializzazione JSON - questo è brutto, ma elimina il prefisso www:

 return Json(new { 
      totalCount = (int)Session["DocumentTotalCount"], 
      markup = RenderRazorViewToString("_DocumentListAjax", docs).Replace("www.","") 
     },JsonRequestBehavior.AllowGet); 

Nel fare questo , da quello che sembra essere al di fuori della LAN (che suona strano), tutti gli URL hanno anteposto www - ovvero https://example.com diventa https://www.example.com. Sto facendo fatica a rintracciare perché questo sta accadendo e come risolverlo.

+1

Come si ottiene questo risultato in JSON? –

+0

@ MichałKędrzyński Ho modificato la domanda – SWa

+0

quale URL stai usando per la chiamata ajax o come viene generato l'url per la chiamata ajax? È un URL completo o solo un url relativo? – Kevin

risposta

1

Con il proprio codice, il comportamento descritto può verificarsi solo durante l'assistenza di richieste diverse. Il rendering della vista parziale all'interno di un'altra vista deve essere il risultato della gestione di una richiesta HTTP il cui host del contesto è impostato su example.com (ad esempio una richiesta a https://example.com/viewWithAPartialView).

Il servizio JSON che contiene una vista parziale, d'altra parte, viene eseguito come conseguenza della gestione di una richiesta a www.example.com (ad esempio una richiesta a https://www.example.com/getPartialViewJson/partialViewName).

Poiché il rendering della vista parziale all'interno della sua vista principale è probabilmente fatto durante la navigazione del sito web tramite il suo URL "normale" - tutto va come previsto.

L'endpoint JSON può essere interrogato tramite AJAX, controllare il codice che costituisce la richiesta - è il colpevole. Un'altra possibilità è che la riscrittura dell'URL sia impostata per eliminare il prefisso www e, per qualche motivo, la regola di riscrittura non corrisponde all'endpoint di pubblicazione JSON.

Aggiornamento:

Dato il ulteriori informazioni sembra che il problema può essere correlato ad ospitare la configurazione (impostazioni di IIS e di bilanciamento del carico). Quello che posso suggerire è quello di cercare di aggiungere la seguente riga al file web.config:

<appSettings> 
    ... 
    <add key="aspnet:UseHostHeaderForRequestUrl" value="true" /> 
    ... 
</appSettings> 

questo costringerà ASP.NET di utilizzare l'intestazione host da richieste in arrivo invece di chiedere una variabile nome del server. Se la causa del problema è davvero un problema di configurazione, questo dovrebbe aiutare.

+0

Sei proprio corretto che la vista parziale è effettivamente chiamata tramite 'AJAX', tuttavia il link è relativo ed è corretto - l'url chiamato doesn avere www prefisso.Non ci sono regole di riscrittura né sul server di staging interno dove funzionano le cose, né sull'ambiente live – SWa

+0

Quindi, fondamentalmente su una delle pagine di 'test.com', si effettua una richiesta' $ .ajax' a '/ getPartialViewJson/partialViewName'. Al momento di questa richiesta, l'url inserito nel browser è 'test.com/something' senza il prefisso' www'. È giusto? In altre parole, in un esploratore di rete si vede che una richiesta 'ajax' è appena capita di' test.com' senza 'www'. –

+0

Sì, giusto – SWa

Problemi correlati