c# - الحصول على وحدة تحكم واسم العمل من داخل وحدة تحكم؟




asp.net-mvc controller action (12)

يبدو أن هذا يعمل بشكل جيد بالنسبة لي (حتى الآن) ، ويعمل أيضًا إذا كنت تستخدم توجيه السمات.

public class BaseController : Controller
{
    protected string CurrentAction { get; private set; }
    protected string CurrentController { get; private set; }

    protected override void Initialize(RequestContext requestContext)
    {
        this.PopulateControllerActionInfo(requestContext);
    }

    private void PopulateControllerActionInfo(RequestContext requestContext)
    {
        RouteData routedata = requestContext.RouteData;

        object routes;

        if (routedata.Values.TryGetValue("MS_DirectRouteMatches", out routes))
        {
            routedata = (routes as List<RouteData>)?.FirstOrDefault();
        }

        if (routedata == null)
            return;

        Func<string, string> getValue = (s) =>
        {
            object o;
            return routedata.Values.TryGetValue(s, out o) ? o.ToString() : String.Empty;
        };

        this.CurrentAction = getValue("action");
        this.CurrentController = getValue("controller");
    }
}

بالنسبة إلى تطبيق الويب الخاص بنا ، أحتاج إلى حفظ ترتيب العناصر التي تم جلبها والعرض بناءً على طريقة العرض - أو على وجه الدقة - وحدة التحكم والإجراء الذي ولّد طريقة العرض (ومعرف المستخدم بالطبع ، ولكن ليس هذا هو الهدف هنا).

بدلاً من مجرد إعطاء معرّف نفسي في كل إجراء متحكم (لكي نستخدمه في بعض الفرز الذي يعتمد على عرض مخرجات DB) ، اعتقدت أنه سيكون من الأسهل والأيسر إنشاء هذا المعرف تلقائيًا من وحدة التحكم وطريقة العمل التي تحصل عليها دعا من.

كيف يمكنني الحصول على اسم وحدة التحكم والإجراء من خلال طريقة الإجراء في وحدة التحكم؟ أو هل أنا بحاجة إلى التفكير في ذلك؟ اعتقد انها سهلة جدا ، وذلك بفضل مقدما!


var routeValues = HttpContext.Current.Request.RequestContext.RouteData.Values;
if (routeValues != null) 
{
    if (routeValues.ContainsKey("action"))
    {
        var actionName = routeValues["action"].ToString();
                }
    if (routeValues.ContainsKey("controller"))
    {
        var controllerName = routeValues["controller"].ToString();
    }
}

لإزالة الحاجة إلى استخدام استدعاء ToString()

string actionName = ControllerContext.RouteData.GetRequiredString("action");
string controllerName = ControllerContext.RouteData.GetRequiredString("controller");

في ما يلي بعض طرق الإضافات للحصول على هذه المعلومات (وهي تتضمن أيضًا المعرف):

public static class HtmlRequestHelper
{
    public static string Id(this HtmlHelper htmlHelper)
    {
        var routeValues = HttpContext.Current.Request.RequestContext.RouteData.Values;

        if (routeValues.ContainsKey("id"))
            return (string)routeValues["id"];
        else if (HttpContext.Current.Request.QueryString.AllKeys.Contains("id"))
            return HttpContext.Current.Request.QueryString["id"];

        return string.Empty;
    }

    public static string Controller(this HtmlHelper htmlHelper)
    {
        var routeValues = HttpContext.Current.Request.RequestContext.RouteData.Values;

        if (routeValues.ContainsKey("controller"))
            return (string)routeValues["controller"];

        return string.Empty;
    }

    public static string Action(this HtmlHelper htmlHelper)
    {
        var routeValues = HttpContext.Current.Request.RequestContext.RouteData.Values;

        if (routeValues.ContainsKey("action"))
            return (string)routeValues["action"];

        return string.Empty;
    }
}

الاستعمال:

@Html.Controller();
@Html.Action();
@Html.Id();

هذا ما لدي حتى الآن:

var actionName = filterContext.ActionDescriptor.ActionName;
var controllerName = filterContext.ActionDescriptor.ControllerDescriptor.ControllerName;

إليك الإجابة الأبسط والأكثر عملية للحصول على اسم:

var actionName = RouteData.Values["controller"];
var controllerName = RouteData.Values["action"];

أو

string actionName = RouteData.Values["controller"].ToString();
string controllerName = RouteData.Values["action"].ToString();

رمز الاختبارات أعلاه مع asp.net mvc 5.


من الممكن ان يكون مفيدا. كنت بحاجة إلى الإجراء في منشئ وحدة التحكم ، ويظهر في هذه المرحلة من دورة حياة MVC ، لم تتم تهيئة هذا ، و ControllerContext = null . بدلاً من الخوض في دورة حياة MVC والعثور على اسم الدالة المناسب RequestContext.RouteData ، اكتشفت الإجراء في RequestContext.RouteData .

ولكن من أجل القيام بذلك ، كما هو الحال مع أي من استخدامات HttpContext ذات الصلة في المُنشئ ، يجب عليك تحديد مساحة الاسم بالكامل ، لأن this.HttpContext أيضًا لم تتم تهيئته. لحسن الحظ ، يبدو System.Web.HttpContext.Current ثابت.

// controller constructor
public MyController() {
    // grab action from RequestContext
    string action = System.Web.HttpContext.Current.Request.RequestContext.RouteData.GetRequiredString("action");

    // grab session (another example of using System.Web.HttpContext static reference)
    string sessionTest = System.Web.HttpContext.Current.Session["test"] as string
}

ملاحظة: من المحتمل ألا تكون الطريقة الأكثر دعمًا للوصول إلى جميع الخصائص في HttpContext ، ولكن بالنسبة لـ RequestContext و Session ، يبدو أنها تعمل بشكل جيد في التطبيق الخاص بي.


لماذا لا يكون لديك شيء أكثر بساطة؟

ما عليك سوى الاتصال بـ Request.Path ، فسوف يعرض سلسلة مفصولة بواسطة "/"

ومن ثم يمكنك استخدام .Split('/')[1] للحصول على اسم وحدة التحكم.


إضافة هذا إلى وحدة تحكم الأساسي الخاص بك داخل أسلوب GetDefaults ()

    protected override void OnActionExecuting(ActionExecutingContext filterContext)
    {
         GetDefaults();
         base.OnActionExecuting(filterContext);
    }

    private void GetDefaults()
    {
    var actionName = filterContext.ActionDescriptor.ActionName;
    var controllerName = filterContext.ActionDescriptor.ControllerDescriptor.ControllerName;
    }

تنفيذ وحدات التحكم الخاصة بك إلى Basecontroller

إضافة عرض جزئي _Breadcrumb.cshtml وإضافته في كل الصفحات المطلوبة مع @ Html.Partial ("_ Breadcrumb")

_Breadcrumb.cshtml

<span>
    <a href="../@ViewData["controllerName"]">
        @ViewData["controllerName"]
    </a> > @ViewData["actionName"]
</span>

string actionName = this.ControllerContext.RouteData.Values["action"].ToString();
string controllerName = this.ControllerContext.RouteData.Values["controller"].ToString();

يمكنك الحصول على اسم وحدة التحكم أو اسم الإجراء من الإجراء مثل أي متغير. فهي خاصة فقط (وحدة تحكم وإجراء) وتم تعريفها بالفعل بحيث لا تحتاج إلى القيام بأي شيء خاص للحصول عليها ما عدا إخبارك أنك بحاجة إليها.

public string Index(string controller,string action)
   {
     var names=string.Format("Controller : {0}, Action: {1}",controller,action);
     return names;
   }

أو يمكنك تضمين وحدة التحكم ، والعمل في النماذج الخاصة بك للحصول على اثنين منهم والبيانات المخصصة الخاصة بك.

public class DtoModel
    {
        public string Action { get; set; }
        public string Controller { get; set; }
        public string Name { get; set; }
    }

public string Index(DtoModel baseModel)
    {
        var names=string.Format("Controller : {0}, Action: {1}",baseModel.Controller,baseModel.Action);
        return names;
    }

في حال كان هذا من أي استخدام للقراء في المستقبل ، في حالتي كان هذا الخطأ بسبب مفتاح أجنبي تم تكوينه بشكل غير صحيح في قاعدة البيانات الخاصة بي (وطراز تم إنشاؤه من DB).

كان لدي جداول:

Parent (1-1) Child (1-many) Grandchild

و قد استقبلت جدول Grandchild عن غير قصد مفتاحًا أجنبيًا حتى أصله (الطفل) و هو جده (الأب). عند حفظ عدة كيانات رئيسية من جديدة ، تلقيت هذا الخطأ. كان الإصلاح لتصحيح المفتاح الخارجي.





c# asp.net-mvc controller action