跨页面携带值以用作路由参数的首选方式
Posted
技术标签:
【中文标题】跨页面携带值以用作路由参数的首选方式【英文标题】:Preferred way to carry a value across pages to use as route parameter 【发布时间】:2022-01-06 11:33:05 【问题描述】:我想要一个选择列表,它将列出表查询中的项目供用户选择。 这是用
呈现的 Options = _context.BranchAssignment
.Where(a => a.ColleagueID == UserColleague)
.IgnoreQueryFilters()
.OrderBy(a => a.Branch.BranchNumber)
.Select(a =>
new SelectListItem
Value = a.BranchID.ToString(),
Text = a.Branch.BranchName
)
.ToList();
<form id="assignedBranch" method="post">
<div class="row">
<select asp-for="BranchSelect" asp-items="Model.Options" onchange="this.form.submit();"></select>
</div>
</form>
如您所见,这是一个非常简单的表格。我目前正在开发的解决方案应该是 onFormSubmit,采用选中的选项,将其设置为 cookie 值,然后如果用户导航到另一个页面,我可以为选择列表设置选中的选项。
我仍在调试这个问题,我想知道是否有更好的解决方案。理想情况下,我希望这个选择列表编写一次并显示在 _layout 导航栏中,但我相信您无法从视图组件中读取(我的最后一次尝试)来获取所选值以用作 OnGet 中的路由参数。
如果您想象用户转到页面 A 并选择列表选择的项目是选项 2,那么我想通过 onGet 加载 webaddress.com/PageA/option2,因为路由将设置为选项 2
如果他们随后转到页面 B,则选择列表将呈现并记住他们之前的 option2 选项,因此它将加载 webaddress.com/PageB/option2 以及他们是否可以更改为例如option3 和 OnFormSubmit webaddress.com/PageB/option3 之后将加载。
如果我以错误的方式处理此问题,我将感谢推动首选流程。
【问题讨论】:
不建议使用route传值,可能会造成一些路由冲突,使用cookie即可。 @XinranShen 我的问题可能不清楚,但我不打算在路由中传递任何值,cookie 是我传递值的可能选项,但路由将在 onGet 中设置基于 cookie 值的页面。 【参考方案1】:我建议你使用cookie来跨页面携带值,而不是使用路由参数。
我分两步实现:
首先,给<select>
添加一个Onchange
事件,当你选择一个选项时,Onchange
事件会设置一个cookie来保存你选择的值。
其次,当您加载其他页面时,<select>
会读取 cookie 以显示您之前的选择。
这是我的代码:
DropDown List
in _layout .cshtml
<li>
<select id="fruit" onchange="save(this.value)">
<option value=0>apple</option>
<option value=1>pear</option>
<option value=2>watermelon</option>
<option value=3>cherry</option>
</select>
</li>
javascript
in _layout .cshtml
<script>
//....................set Cookie............
var saveclass = null;
function save(cookieValue)
var sel = document.getElementById('fruit');
saveclass = saveclass ? saveclass : document.body.className;
document.body.className = saveclass + ' ' + sel.value;
setCookie('theme', cookieValue, 365);
function setCookie(cookieName, cookieValue, nDays)
var today = new Date();
var expire = new Date();
if (nDays==null || nDays==0)
nDays=1;
expire.setTime(today.getTime() + 3600000*24*nDays);
document.cookie = cookieName+"="+escape(cookieValue) + ";expires="+expire.toGMTString() +";path=/";
//......................read Cookie.............
document.addEventListener('DOMContentLoaded', function()
var themeSelect = document.getElementById('fruit');
var selectedTheme = readCookie('theme');
themeSelect.value = selectedTheme;
saveclass = saveclass ? saveclass : document.body.className;
document.body.className = saveclass + ' ' + selectedTheme;
);
function readCookie(name)
var nameEQ = name + "=";
var ca = document.cookie.split(';');
for(var i = 0; i < ca.length; i++)
var c = ca[i];
while (c.charAt(0) == ' ') c = c.substring(1, c.length);
if (c.indexOf(nameEQ) == 0) return c.substring(nameEQ.length, c.length);
return null;
</script>
然后你可以在其他页面上获取相同的选项
是的,你是对的。当我从 setCookie 函数中删除 days 组件时,cookie 只会在会话存在时存在。
【讨论】:
感谢详细的回答。但是,我确实想澄清我的问题,为了使用模型绑定,我的列表是从附加的页面模型生成的。完全消除模型绑定并在 _layout 中采用视图组件是否为 Razor 页面解决方案提供了最佳选择? 作为后续,您能否确认如果我从您的 setCookie 函数中删除 days 组件,该 cookie 将仅在会话存在时才存在。这很重要,也是 ASP.Net HTTPCookie 类的好处之一 我写这些硬代码只是为了测试方便,你也可以使用模型绑定来显示这些数据。我改变了我的答案,当我从 setCookie 函数中删除 days 组件时,你可以看到只要会话存在,cookie 就会存在 嗨@Xinran Shen,我将接受您的回答,因为它确实适用于硬编码列表。如果您说模型绑定将起作用,我将不胜感激。据我了解,在 _layout 文件中获取动态填充的选择列表的唯一方法是通过视图组件,但我看不到任何通过模型绑定的方法。 感谢您接受我的回答。在MVC中,可以在controller中使用ViewData['xx']=new SelectList(xx)
,在view中使用asp-items="xxx"
来实现模型绑定。但是,在 Razor 页面中,在_layout
中实现模型绑定非常复杂,所以,如果_layout 页面中的代码不经常更改,我建议您直接使用硬编码。以上是关于跨页面携带值以用作路由参数的首选方式的主要内容,如果未能解决你的问题,请参考以下文章
VUE学习--路由跳转方式||路由跳转携带参数方式||目标路由接受参数方式