MVC: Динамические маршруты в Home-Controller без влияния на другие контроллеры - PullRequest
0 голосов
/ 11 мая 2019

Это не общий вопрос о том, как работают контроллеры и действия, а вопрос о представлении известных структур URL пользователю в ядре dotnet MVC Client.

Я хочу создать "домашнюю страницу" с блогом и, возможно, позже с магазином. Общая структура URL должна быть

https://xxx.xx/... => Homepage content
https://xxx.xx/Blog/... => Blog content
https://xxx.xx/Shop/... => Shop content

«Блог» и «Магазин» являются определенными областями на веб-сайте, поэтому дополнительный путь знаком для пользователя, а контроллеры и действия работают так, как задумано.

Обычно для домашней страницы есть такая структура:

https://xxx.xx/ => Index
https://xxx.xx/privacy
https://xxx.xx/about
https://xxx.xx/company/team

То, что вы не хотите (для глаз), это что-то вроде

https://xxx.xx/Home/privacy

Кроме того, мне нравится получать эти "страницы" из базы данных, так что сам контроллер Home имеет два условия:

  1. Если после домена ничего не происходит, вызовите контроллер Home, действие Index и Index.cshtml
  2. Если за доменом есть что-то, у которого нет пути «Блог /» или «Магазин /», это имя или фрагмент страницы и, следовательно, вызовите контроллер Home с «действием страницы» и отобразите страницу. cshtml с контентом из базы данных.

Если я сделаю что-то подобное в домашнем контроллере

[HttpGet("{slug?}")]
public async Task<IActionResult> Index(string slug)

Работает домашняя страница, которая мне нравится, но я больше не могу вызывать другие контроллеры.

Я играл с пользовательскими маршрутами, но моя проблема в том, что, очевидно, маршрутизация не может различить «путь» и «действие».

Есть ли решение моей проблемы или мне нужно иметь дело с этим?

1 Ответ

1 голос
/ 11 мая 2019

Попробуйте этот маршрут и перенаправьте его на цель

public static void RegisterRoutes(RouteCollection routes)
        {
            routes.IgnoreRoute("{resource}.axd/{*pathInfo}");


            routes.MapRoute(
                name: "Link",
                url: "{slug}",
                defaults: new { controller = "Slug", action = "GoTo" }
            );

            routes.MapRoute(
                name: "Default",
                url: "{controller}/{action}/{id}",
                defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional }
            );
        }

и в контроллере слагов:

public async Task<ActionResult> GoTo(string ShortLink)
        {
            if (String.IsNullOrWhiteSpace(ShortLink))
                return RedirectToAction("Index", "Home");


            LinkModels linkModels = db.Links.Where(sl => sl.ShortLinkURL == ShortLink).FirstOrDefault();

            if (linkModels == null)
            {
                return RedirectToAction("Index", "Home");
            }
            else
            {
                ClickModels cm = new ClickModels();
                if (System.Web.HttpContext.Current.Request.UrlReferrer != null)
                {
                    linkModels.ReferralCount++;
                    cm.LinkType = 1;
                    cm.RequestURL = System.Web.HttpContext.Current.Request.UrlReferrer.AbsoluteUri;
                    cm.RequestIP = BitOneWeb.Helper.GetClientIP.GetIP();
                    cm.ClickDateTime = DateTime.Now;


                }
                else
                {
                    linkModels.DirectCount++;
                    cm.LinkType = 0;
                    //cm.RequestURL = "Direct";
                    cm.RequestIP = BitOneWeb.Helper.GetClientIP.GetIP();
                    cm.ClickDateTime = DateTime.Now;

                }
                linkModels.LinkCount = linkModels.DirectCount + linkModels.ReferralCount;
                db.Clicks.Add(cm);
                linkModels.Clicks.Add(cm);

                db.Entry(linkModels).State = EntityState.Modified;


                await db.SaveChangesAsync();
                return Redirect(linkModels.LongLinkURL);
            }
        }

Это нормально для меня, но если у вас есть контроллер исправлений типа http://yoursite/blog или http://yoursite/contact, вы можете статически справиться с этим в контроллере слагов

...