zHaytam / SmartBreadcrumbs

A utility library for ASP.NET Core (both MVC and Razor Pages) websites to easily add and customize breadcrumbs.
https://blog.zhaytam.com/2018/06/24/asp-net-core-using-smartbreadcrumbs/
MIT License
161 stars 77 forks source link

FromController with parameters #76

Open alexstephens opened 4 years ago

alexstephens commented 4 years ago

Hi,

Started using smartbreadcrumbs in core 3.1 and all good until i needed to setup a parent crumb. The parent needs a routeValue of the Id passed into the child action.

example: Home / Product / Upgrade

Product url should be /member/product/12345

Can this be achieved with SMartbreadCrumbs? I have this working but not passing the routeValue.

[Breadcrumb("Upgrade", FromAction = "Product", FromController = typeof(MemberController))]

Regards

Alex

zHaytam commented 4 years ago

Hello,

Since c# attributes can't contain dynamic values (e.g. product id), SmartBreadcrumbs gives you the possible to set manual nodes.
Please look at this wiki: https://github.com/zHaytam/SmartBreadcrumbs/wiki/4.-Manual-nodes

You'll want to set RouteValues (which will contain the id) in your Product breadcrumb node.

gandhiarpit commented 3 years ago

The example is bit of confusing to me. Do you have a working sample to try out ? What should be the attribute on the action method be like [Breadcrumb("ViewData.BreadcrumbNode")]

How should be the MvcBreadcrumbNode, MvcControllerBreadcrumbNode, RazorPageBreadcrumbNode setup if my route is something like below. Do I have to specify these 3 classes in the order mentioned?

Batch Management --> Batches --> Batch Details

var childNode1 = new MvcBreadcrumbNode("Index", "Batch", "Batch Management"); var childNode2 = new MvcControllerBreadcrumbNode("Batch", "Batches") { OverwriteTitleOnExactMatch = false, Parent = childNode1, RouteValues = new { tenantId, iterationId } }; var childNode3 = new RazorPageBreadcrumbNode($"/Batch/Batches/BatchDetails", "Batch Details") { OverwriteTitleOnExactMatch = true, Parent = childNode2, }; ViewData["BreadcrumbNode"] = childNode3;

Only thing stopping me from using this is dynamic routing. Everything else was pretty easy to work with.

Thanks

gandhiarpit commented 3 years ago

Also, will it be possible to retrieve the Breadcrumb structure in an action method? Like what is the existing structure so that I can build on that? Reason being that it is possible to call that action from 2 different controllers with totally different breadcrumb structure.

I know I am asking for something which should not be done maybe. Just throwing this out.

Regards,

zHaytam commented 3 years ago

Hello @gandhiarpit,

Doesn't the code you showed in your previous reply work? Looks like your manually created nodes are valid. For your last question, should I make Dictionary<string, BreadcrumbNode> _nodes (e.g. Nodes) public so that you guys can inject BreadcrumbManager?

gandhiarpit commented 3 years ago

Hello @gandhiarpit,

Doesn't the code you showed in your previous reply work? Looks like your manually created nodes are valid. For your last question, should I make Dictionary<string, BreadcrumbNode> _nodes (e.g. Nodes) public so that you guys can inject BreadcrumbManager?

Hi @zHaytam,

No the link for Batches Breadcrumb is missing the action part.

This is generated http://localhost:65527/Batch?tenantId=5&iterationId=9

But it should be http://localhost:65527/Batch/Batches?tenantId=5&iterationId=9

image

I got it working using below code, which does not match with your example. Also, not sure if that the correct way even.

`
var childNode1 = new MvcBreadcrumbNode("Index", "Batch", "Batch Management");

        var childNode2 = new MvcBreadcrumbNode("Batches", "Batch", "Batches")
        {
            Parent = childNode1,
            RouteValues = new { tenantId, iterationId }
        };

        var childNode3 = new RazorPageBreadcrumbNode($"/Batch/Batches/BatchDetails", "Batch Details")
        {
            OverwriteTitleOnExactMatch = true,
            Parent = childNode2
        };`

So I asked about what's the difference between MvcBreadcrumbNode, MvcControllerBreadcrumbNode, RazorPageBreadcrumbNode as their is no documentation on what to use when.

Regarding 'BreadcrumbManager' --> Yes that might help, but you are talking about injecting. Will it be possible to retrieve current nodes from the manager?

zHaytam commented 3 years ago

The difference between those node types are in their names. Each type represents a type of "route". MvcBreadcrumbNode points to an action in a controller, RazorPageBreadcrumbNode points to a razor page, etc... So you need to choose the correct types for your website.

What do you mean by current nodes?

gandhiarpit commented 3 years ago

The difference between those node types are in their names. Each type represents a type of "route". MvcBreadcrumbNode points to an action in a controller, RazorPageBreadcrumbNode points to a razor page, etc... So you need to choose the correct types for your website.

What do you mean by current nodes?

Aah, now it makes sense.

By current nodes I mean, Is there a way to find out what breadcrumbs are set already while navigating to that page/view?

zHaytam commented 3 years ago

You could try:

var nodeKey = new NodeKey(ViewContext.ActionDescriptor.RouteValues, ViewContext.HttpContext.Request.Method);
var node = _breadcrumbManager.GetNode(nodeKey.Value);