Sau khi chi tiêu một số lượng đáng kể thời gian với cuộc điều tra, sử dụng một sự kết hợp của Sentry và Azure bản ghi máy chủ web, tôi đã tìm thấy 2 nguyên nhân chính của các lỗi được đề cập:
1) Trên điện thoại di động, khi trình duyệt đang chạy ẩn, hệ điều hành có thể đột ngột dừng lại để giải phóng tài nguyên. Khi điều này xảy ra, thông thường, trang được lưu trữ trên ổ đĩa của điện thoại và được tải lại từ đó khi trình duyệt được mở lại.
Vấn đề, tuy nhiên, vào thời điểm này, Mã thông báo chống giả mạo, là cookie phiên, đã hết hạn vì đây thực chất là phiên mới. Vì vậy, trang tải mà không có Cookie chống Giả mạo, sử dụng HTML từ phiên trước đó. Điều này gây ra ngoại lệ The required anti-forgery cookie is not present
.
2) Trong khi dường như có liên quan, ngoại lệ tokens do not match
thường chỉ liên quan đến tiếp tuyến. Nguyên nhân có vẻ là hành vi của người dùng khi mở nhiều tab cùng một lúc.
Cookie chống giả mạo chỉ được chỉ định khi người dùng đến trang có biểu mẫu trên đó. Điều này có nghĩa là họ có thể truy cập trang chủ của bạn và không có cookie chống giả mạo. Sau đó, họ có thể mở nhiều tab bằng cách nhấp chuột giữa. Nhiều tab là nhiều yêu cầu song song, mỗi yêu cầu không có cookie chống giả mạo.
Vì những yêu cầu này không có cookie chống giả mạo, cho mỗi người trong số họ, ASP.NET tạo ra một mã thông báo giả ngẫu nhiên riêng biệt cho cookie của họ và sử dụng nó trong biểu mẫu; tuy nhiên, chỉ kết quả của tiêu đề cuối cùng nhận được sẽ được giữ lại. Điều này có nghĩa là tất cả các trang khác sẽ có mã thông báo không hợp lệ trên trang, vì cookie chống giả mạo của họ bị ghi đè.
Đối với một giải pháp, tôi đã tạo ra một bộ lọc toàn cầu phải đảm bảo rằng
- Cookie Chống giả mạo được gán vào bất kỳ trang nào, ngay cả khi trang không có hình thức, và
- Các Chống Cookie -Forgery không phải là phiên ràng buộc. Tuổi thọ của nó phải được điều chỉnh để khớp với mã thông báo đăng nhập của người dùng, nhưng nó phải tồn tại giữa các phiên trong trường hợp thiết bị di động tải lại trang mà không có phiên.
Mã bên dưới là FilterAttribute
phải được thêm vào bên trong FilterConfig.cs
làm bộ lọc chung. Xin lưu ý rằng, trong khi tôi không tin rằng điều này sẽ tạo ra một lỗ hổng bảo mật, tôi không có nghĩa là một chuyên gia bảo mật, vì vậy bất kỳ đầu vào được chào đón.
[AttributeUsage(AttributeTargets.Class | AttributeTargets.Method)]
public class AntiForgeryFilter : FilterAttribute, IActionFilter
{
public void OnActionExecuting(ActionExecutingContext filterContext)
{
var cookie = filterContext.HttpContext.Request.Cookies.Get(AntiForgeryConfig.CookieName);
var addCookie = true;
if (string.IsNullOrEmpty(cookie?.Value))
{
cookie = filterContext.HttpContext.Response.Cookies.Get(AntiForgeryConfig.CookieName);
addCookie = false;
}
if (string.IsNullOrEmpty(cookie?.Value))
{
AntiForgery.GetTokens(null, out string cookieToken, out string _);
cookie = new HttpCookie(AntiForgeryConfig.CookieName, cookieToken)
{
HttpOnly = true,
Secure = AntiForgeryConfig.RequireSsl
};
}
cookie.Expires = DateTime.UtcNow.AddYears(1);
if(addCookie) filterContext.HttpContext.Response.Cookies.Add(cookie);
}
public void OnActionExecuted(ActionExecutedContext filterContext)
{
}
}
Bạn đã bao giờ tìm thấy câu trả lời cho điều này chưa? –
Không, chúng tôi đã phải loại bỏ kiểm tra chống ung thư (nó đã được sử dụng cho các hình thức tích hợp đơn giản. Không có gì quan trọng về nó). Thiết lập Azure của chúng tôi có hai đĩa CD logic, do đó, tôi đoán nó có liên quan đến các đĩa CD khác nhau xử lý yêu cầu và phản hồi. Đó chỉ là phỏng đoán của tôi. – TamerM
Tôi rất buồn khi nghe điều đó, mặc dù tôi không nghĩ rằng đây là vấn đề, trừ khi bạn có miền được xác định trong hành động biểu mẫu (sau đó chuyển hướng người dùng sang một đĩa CD khác cho POST, nhưng tôi nghi ngờ rằng sẽ là trường hợp vì nếu bạn đã sử dụng UrlHelper, điều đó không chuyển hướng người dùng giữa các tên miền). –