I have done exactly that like this.
Global.asax snippet:
routes.MapRoute(
"GotoPostOrPage",
"p/{dataItemTypeId}/{dataItemId}/{ignored}", // This allows you to append a random slug if you like
new { controller = "DataItem", action = "Details", ignored = UrlParameter.Optional }
);
And then something like this in the controller:
public PartialViewResult Details(int dataItemTypeId, int dataItemId)
{
IDataItemView dataItem = _dataItemService.SelectDataItem(dataItemTypeId, dataItemId);
DataItemViewModel vm = MappingFunctions.DataItemToViewModel(dataItem);
return PartialView("_Details", vm);
}
Note that this allows you to append a random slug which is exactly what stackoverflow does. However, stackoverflow then corrects your slug to the one stored in the database. This would be trivial to implement.
Also note that I have shown you my real code; you'd obviously need to tweak it a little bit (but not much) to fit your scenario. The important point is to append an optional url parameter in the route table. In my case I ignore it completely, which is actually what SO does too on the way in, hence you can navigate to this daft URL and still get here: https://stackoverflow.com/questions/12051094/i-like-to-eat-cake