¿Cuándo usarías el atributo ChildActionOnly? ¿Qué es ay ChildActionen qué circunstancias desearía restringir una acción utilizando este atributo?
¿Cuándo usarías el atributo ChildActionOnly? ¿Qué es ay ChildActionen qué circunstancias desearía restringir una acción utilizando este atributo?
Respuestas:
El ChildActionOnlyatributo garantiza que un método de acción se pueda invocar solo como un método secundario desde una vista. Un método de acción no necesita tener este atributo para usarse como una acción secundaria, pero tendemos a usar este atributo para evitar que los métodos de acción se invoquen como resultado de una solicitud del usuario. Habiendo definido un método de acción, necesitamos crear lo que se representará cuando se invoque la acción. Las acciones secundarias suelen asociarse con vistas parciales, aunque esto no es obligatorio.
[ChildActionOnly] permitiendo acceso restringido a través del código en Ver
Implementación de información de estado para URL de página específica. Ejemplo: la sintaxis de razor de URL de página de pago (pagando solo una vez) permite llamar a acciones específicas condicional
// 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." Para evitar un GET a un determinado controlador directamente, pero solo desde otro controlador / acción. Probable: _Vistas parciales.
InvalidOperationExceptioncuando <ChildActionOnly>se llama a un Método marcado a través del navegador?
Con el atributo [ChildActionOnly] anotado, un método de acción solo se puede invocar como un método secundario desde una vista. Aquí hay un ejemplo para [ChildActionOnly]. .
Hay dos métodos de acción: Index () y MyDateTime () y Vistas correspondientes: Index.cshtml y MyDateTime.cshtml. esto es 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);
}
}
Aquí está la vista de 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>
Aquí está la vista parcial MyDateTime.cshtml .
@model DateTime
<p>
This is the child action result: @Model.ToLongTimeString()
<br />
@ViewBag.Message
</p>
si ejecuta la aplicación y realiza esta solicitud http: // localhost: 57803 / home / mydatetime El resultado será un error del servidor así:

Esto significa que no puede llamar directamente a la vista parcial. pero se puede llamar a través de la vista Index () como en el Index.cshtml
@ Html.Action ("MyDateTime") // Llamando a la vista parcial: MyDateTime ().
Si elimina [ChildActionOnly] y realiza la misma solicitud http: // localhost: 57803 / home / mydatetime, le permite obtener el resultado de la vista parcial de mydatetime:
This is the child action result. 12:53:31 PM
This is from MyDateTime()
NonActiontambién, ¿qué diferencia hace?
Lo usaría si está utilizando RenderActioncualquiera de sus vistas, generalmente para representar una vista parcial.
La razón para marcarlo [ChildActionOnly]es que necesita que el método del controlador sea público para poder llamarlo, RenderActionpero no desea que alguien pueda navegar a una URL (por ejemplo, / Controller / SomeChildAction) y ver los resultados. acción directa
RenderActionya sea
NonActionAttributeen proyectos reales?
privateo protected. Realmente no puedo pensar en ninguna buena razón por la que se quiere hacer un método de control public, excepto si desea ser capaz de llamar directamente o por medio deRenderAction
Un poco tarde para la fiesta, pero ...
Las otras respuestas hacen un buen trabajo al explicar qué efecto tiene el [ChildActionOnly]atributo. Sin embargo, en la mayoría de los ejemplos, seguí preguntándome por qué crearía un nuevo método de acción solo para representar una vista parcial, dentro de otra vista, cuando simplemente podría renderizar @Html.Partial("_MyParialView")directamente en la vista. Parecía una capa innecesaria. Sin embargo, mientras investigaba, descubrí que un beneficio es que la acción del niño puede crear un modelo diferente y pasarlo a la vista parcial. El modelo necesario para el parcial podría no estar disponible en el modelo de la vista en la que se representa la vista parcial. En lugar de modificar la estructura del modelo para obtener los objetos / propiedades necesarios allí solo para representar la vista parcial, puede llamar a la acción secundaria y hacer que el método de acción se encargue de crear el modelo necesario para la vista parcial.
Esto puede ser útil, por ejemplo, en _Layout.cshtml. Si tiene algunas propiedades comunes a todas las páginas, una forma de lograr esto es usar un modelo de vista base y hacer que todos los demás modelos de vista hereden de él. Luego, _Layoutpuede usar el modelo de vista base y las propiedades comunes. La desventaja (que es subjetiva) es que todos los modelos de vista deben heredar del modelo de vista base para garantizar que esas propiedades comunes estén siempre disponibles. La alternativa es renderizar @Html.Actionen esos lugares comunes. El método de acción crearía un modelo separado necesario para la vista parcial común a todas las páginas, lo que no afectaría el modelo para la vista "principal". En esta alternativa, la _Layoutpágina no necesita tener un modelo. Se deduce que todos los demás modelos de vista no necesitan heredar de ningún modelo de vista base.
Estoy seguro de que hay otras razones para usar el [ChildActionOnly]atributo, pero esto me parece bueno, así que pensé en compartirlo.
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