Quando useresti l'attributo ChildActionOnly
? Che cos'è un ChildAction
e in quale circostanza vorresti limitare un'azione usando questo attributo?
Quando useresti l'attributo ChildActionOnly
? Che cos'è un ChildAction
e in quale circostanza vorresti limitare un'azione usando questo attributo?
Risposte:
L' ChildActionOnly
attributo garantisce che un metodo di azione possa essere chiamato solo come metodo figlio all'interno di una vista. Un metodo di azione non ha bisogno di avere questo attributo per essere usato come azione figlio, ma tendiamo a usare questo attributo per evitare che i metodi di azione vengano invocati a seguito di una richiesta dell'utente. Dopo aver definito un metodo di azione, dobbiamo creare ciò che verrà reso quando l'azione viene invocata. Le azioni dei bambini sono in genere associate a viste parziali, sebbene ciò non sia obbligatorio.
[ChildActionOnly] che consente l'accesso limitato tramite codice in Visualizza
Implementazione delle informazioni sullo stato per l'URL specifico della pagina. Esempio: l'URL della pagina di pagamento (pagando una sola volta) la sintassi del rasoio consente di chiamare determinate azioni condizionali
// example from Music Store // GET: /ShoppingCart/CartSummary [ChildActionOnly] public ActionResult CartSummary() { // your stuff } /ShoppingCart/CartSummary will return "The action 'CartSummary' is accessible only by a child request."
Quindi si impedisce direttamente a un determinato controller di entrare, ma solo all'interno di un altro controller / azione. Probabile: _ Viste parziale.
InvalidOperationException
quando <ChildActionOnly>
viene chiamato un metodo contrassegnato tramite il browser?
Con l' attributo [ChildActionOnly] annotato, un metodo di azione può essere chiamato solo come metodo figlio all'interno di una vista. Ecco un esempio di [ChildActionOnly]. .
ci sono due metodi di azione: Index () e MyDateTime () e viste corrispondenti: Index.cshtml e MyDateTime.cshtml. questo è HomeController.cs
public class HomeController : Controller
{
public ActionResult Index()
{
ViewBag.Message = "This is from Index()";
var model = DateTime.Now;
return View(model);
}
[ChildActionOnly]
public PartialViewResult MyDateTime()
{
ViewBag.Message = "This is from MyDateTime()";
var model = DateTime.Now;
return PartialView(model);
}
}
Ecco la vista per Index.cshtml .
@model DateTime
@{
ViewBag.Title = "Index";
}
<h2>
Index</h2>
<div>
This is the index view for Home : @Model.ToLongTimeString()
</div>
<div>
@Html.Action("MyDateTime") // Calling the partial view: MyDateTime().
</div>
<div>
@ViewBag.Message
</div>
Ecco la vista parziale MyDateTime.cshtml .
@model DateTime
<p>
This is the child action result: @Model.ToLongTimeString()
<br />
@ViewBag.Message
</p>
se esegui l'applicazione e fai questa richiesta http: // localhost: 57803 / home / mydatetime Il risultato sarà un errore del server in questo modo:
Ciò significa che non è possibile chiamare direttamente la vista parziale. ma può essere chiamato tramite la vista Index () come in Index.cshtml
@ Html.Action ("MyDateTime") // Chiamata della vista parziale: MyDateTime ().
Se rimuovi [ChildActionOnly] e fai la stessa richiesta http: // localhost: 57803 / home / mydatetime ti consente di ottenere il risultato della vista parziale mydatetime:
This is the child action result. 12:53:31 PM
This is from MyDateTime()
NonAction
anche usando , che differenza fa?
Lo useresti se lo stai usando RenderAction
in una qualsiasi delle tue viste, solitamente per renderizzare una vista parziale.
Il motivo per cui è stato contrassegnato [ChildActionOnly]
è che è necessario che il metodo del controller sia pubblico, in modo da poterlo chiamare RenderAction
ma non si desidera che qualcuno sia in grado di navigare verso un URL (ad es. / Controller / SomeChildAction) e vedere i risultati di quello azione direttamente.
RenderAction
nessuno dei due
NonActionAttribute
nei progetti reali?
private
o protected
. Non riesco davvero a pensare a nessuna buona ragione per cui vorresti creare un metodo controller public
tranne se volessi essere in grado di chiamarlo direttamente o viaRenderAction
Un po 'tardi alla festa, ma ...
Le altre risposte fanno un buon lavoro nel spiegare l'effetto [ChildActionOnly]
dell'attributo. Tuttavia, nella maggior parte degli esempi, continuavo a chiedermi perché avrei creato un nuovo metodo di azione solo per rendere una vista parziale, all'interno di un'altra vista, quando si poteva semplicemente eseguire il rendering @Html.Partial("_MyParialView")
direttamente nella vista. Sembrava uno strato inutile. Tuttavia, come ho studiato, ho scoperto che un vantaggio è che l'azione figlio può creare un modello diverso e passarlo alla vista parziale. Il modello necessario per il parziale potrebbe non essere disponibile nel modello della vista in cui viene visualizzata la vista parziale. Invece di modificare la struttura del modello per ottenere lì gli oggetti / le proprietà necessari solo per eseguire il rendering della vista parziale, è possibile chiamare l'azione figlio e fare in modo che il metodo di azione si occupi della creazione del modello necessario per la vista parziale.
Questo può tornare utile, ad esempio, in _Layout.cshtml
. Se hai alcune proprietà comuni a tutte le pagine, un modo per farlo è usare un modello di vista di base e avere tutti gli altri modelli di vista ereditati da esso. Quindi, è _Layout
possibile utilizzare il modello della vista di base e le proprietà comuni. Il rovescio della medaglia (che è soggettivo) è che tutti i modelli di vista devono ereditare dal modello di vista di base per garantire che tali proprietà comuni siano sempre disponibili. L'alternativa è rendere @Html.Action
in quei luoghi comuni. Il metodo di azione creerebbe un modello separato necessario per la vista parziale comune a tutte le pagine, che non influirebbe sul modello per la vista "principale". In questa alternativa, la _Layout
pagina non deve avere un modello. Ne consegue che tutti gli altri modelli di vista non devono ereditare da alcun modello di vista di base.
Sono sicuro che ci sono altri motivi per usare l' [ChildActionOnly]
attributo, ma questo mi sembra buono, quindi ho pensato di condividere.
public class HomeController : Controller
{
public ActionResult Index()
{
ViewBag.TempValue = "Index Action called at HomeController";
return View();
}
[ChildActionOnly]
public ActionResult ChildAction(string param)
{
ViewBag.Message = "Child Action called. " + param;
return View();
}
}
The code is initially invoking an Index action that in turn returns two Index views and at the View level it calls the ChildAction named “ChildAction”.
@{
ViewBag.Title = "Index";
}
<h2>
Index
</h2>
<!DOCTYPE html>
<html>
<head>
<title>Error</title>
</head>
<body>
<ul>
<li>
@ViewBag.TempValue
</li>
<li>@ViewBag.OnExceptionError</li>
@*<li>@{Html.RenderAction("ChildAction", new { param = "first" });}</li>@**@
@Html.Action("ChildAction", "Home", new { param = "first" })
</ul>
</body>
</html>
Copy and paste the code to see the result .thanks