[英]How do I encrypt URLs in ASP.NET MVC?
我需要在ASP.NET MVC應用程序中加密URL。
我是否需要在Route Collection中的Global頁面中編寫代碼以加密所有URL?
加密URL是個壞主意。 期。
你可能想知道我為什么這么說。
我為一家加密其URL的公司申請了一份申請。 這是一個webforms應用程序。 僅從URL中,幾乎不可能分辨出我要引起該問題的代碼部分。 由於調用webform控件的動態特性,您只需知道軟件將要發生的路徑。 這讓人非常不安。
除此之外,應用程序中沒有基於角色的授權。 這一切都基於加密的URL。 如果你可以解密URL(如果它可以被加密,它可以被解密),那么你可以想象輸入另一個加密的URL並冒充另一個用戶。 我不是說這很簡單,但可能會發生。
最后,您多久使用一次互聯網並查看加密的URL? 當你這樣做的時候,你內心有點死嗎? 我做。 URL旨在傳達公共信息。 如果您不希望它這樣做,請不要將其放在您的URL中(或者需要對您站點的敏感區域進行授權)。
您在數據庫中使用的ID應該是可供用戶查看的ID。 如果您使用SSN作為主鍵,則應更改Web應用程序的架構。
任何可以加密的東西都可以被解密,因此容易受到攻擊。
如果您希望用戶只有在獲得授權的情況下才能訪問某些URL,那么您應該使用ASP.NET MVC中提供的[Authorize]
屬性。
加密整個網址,我同意,非常糟糕的主意。 加密網址參數? 不是那么多,實際上是一種有效且廣泛使用的技術。
如果你真的想要加密/解密url參數(這根本不是一個壞主意),那么請查看Mads Kristensen的文章“ 用於查詢字符串加密的HttpModule ”。
您需要修改context_BeginRequest以使其適用於MVC。 只需刪除if語句的第一部分,檢查原始URL是否包含“aspx”。
話雖如此,我已經在幾個項目中使用過這個模塊(如果需要的話,還有一個轉換后的VB版本),並且在大多數情況下,它就像一個魅力。
但是,在某些情況下,我遇到了一些jQuery / Ajax調用無法正常工作的問題。 我確信可以修改模塊以補償這些情況。
基於這里的答案,這對我來說不起作用BTW,我找到了另一種基於我特定的MVC實現的解決方案 ,以及它的工作原理取決於你是使用II7還是II6。 兩種情況都需要稍作修改。
II6
首先,您需要將以下內容添加到web.config (root,而不是View文件夾中的那個)。
<system.web>
<httpModules>
<add name="URIHandler" type="URIHandler" />
</httpModules>
II7
將此添加到web.config中 (root,而不是View文件夾中的那個)。
<system.webServer>
<validation validateIntegratedModeConfiguration="false" />
<modules runAllManagedModulesForAllRequests="true">
<remove name="URIHandler" />
<add name="URIHandler" type="URIHandler" />
</modules>
或者你可以添加兩者。 真的沒關系。
接下來使用這個類。 我打電話給你,你可能已經注意到了 - URIHandler 。
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc;
using System.IO;
using System.Text;
using System.Security.Cryptography;
using System.Diagnostics.CodeAnalysis;
public class URIHandler : IHttpModule
{
#region IHttpModule members
public void Dispose()
{
}
public void Init(HttpApplication context)
{
context.BeginRequest += new EventHandler(context_BeginRequest);
}
#endregion
private const string PARAMETER_NAME = "enc=";
private const string ENCRYPTION_KEY = "key";
private void context_BeginRequest(object sender, EventArgs e)
{
HttpContext context = HttpContext.Current;
//if (context.Request.Url.OriginalString.Contains("aspx") && context.Request.RawUrl.Contains("?"))
if (context.Request.RawUrl.Contains("?"))
{
string query = ExtractQuery(context.Request.RawUrl);
string path = GetVirtualPath();
if (query.StartsWith(PARAMETER_NAME, StringComparison.OrdinalIgnoreCase))
{
// Decrypts the query string and rewrites the path.
string rawQuery = query.Replace(PARAMETER_NAME, string.Empty);
string decryptedQuery = Decrypt(rawQuery);
context.RewritePath(path, string.Empty, decryptedQuery);
}
else if (context.Request.HttpMethod == "GET")
{
// Encrypt the query string and redirects to the encrypted URL.
// Remove if you don't want all query strings to be encrypted automatically.
string encryptedQuery = Encrypt(query);
context.Response.Redirect(path + encryptedQuery);
}
}
}
/// <summary>
/// Parses the current URL and extracts the virtual path without query string.
/// </summary>
/// <returns>The virtual path of the current URL.</returns>
private static string GetVirtualPath()
{
string path = HttpContext.Current.Request.RawUrl;
path = path.Substring(0, path.IndexOf("?"));
path = path.Substring(path.LastIndexOf("/") + 1);
return path;
}
/// <summary>
/// Parses a URL and returns the query string.
/// </summary>
/// <param name="url">The URL to parse.</param>
/// <returns>The query string without the question mark.</returns>
private static string ExtractQuery(string url)
{
int index = url.IndexOf("?") + 1;
return url.Substring(index);
}
#region Encryption/decryption
/// <summary>
/// The salt value used to strengthen the encryption.
/// </summary>
private readonly static byte[] SALT = Encoding.ASCII.GetBytes(ENCRYPTION_KEY.Length.ToString());
/// <summary>
/// Encrypts any string using the Rijndael algorithm.
/// </summary>
/// <param name="inputText">The string to encrypt.</param>
/// <returns>A Base64 encrypted string.</returns>
[SuppressMessage("Microsoft.Usage", "CA2202:Do not dispose objects multiple times")]
public static string Encrypt(string inputText)
{
RijndaelManaged rijndaelCipher = new RijndaelManaged();
byte[] plainText = Encoding.Unicode.GetBytes(inputText);
PasswordDeriveBytes SecretKey = new PasswordDeriveBytes(ENCRYPTION_KEY, SALT);
using (ICryptoTransform encryptor = rijndaelCipher.CreateEncryptor(SecretKey.GetBytes(32), SecretKey.GetBytes(16)))
{
using (MemoryStream memoryStream = new MemoryStream())
{
using (CryptoStream cryptoStream = new CryptoStream(memoryStream, encryptor, CryptoStreamMode.Write))
{
cryptoStream.Write(plainText, 0, plainText.Length);
cryptoStream.FlushFinalBlock();
return "?" + PARAMETER_NAME + Convert.ToBase64String(memoryStream.ToArray());
}
}
}
}
/// <summary>
/// Decrypts a previously encrypted string.
/// </summary>
/// <param name="inputText">The encrypted string to decrypt.</param>
/// <returns>A decrypted string.</returns>
[SuppressMessage("Microsoft.Usage", "CA2202:Do not dispose objects multiple times")]
public static string Decrypt(string inputText)
{
RijndaelManaged rijndaelCipher = new RijndaelManaged();
byte[] encryptedData = Convert.FromBase64String(inputText);
PasswordDeriveBytes secretKey = new PasswordDeriveBytes(ENCRYPTION_KEY, SALT);
using (ICryptoTransform decryptor = rijndaelCipher.CreateDecryptor(secretKey.GetBytes(32), secretKey.GetBytes(16)))
{
using (MemoryStream memoryStream = new MemoryStream(encryptedData))
{
using (CryptoStream cryptoStream = new CryptoStream(memoryStream, decryptor, CryptoStreamMode.Read))
{
byte[] plainText = new byte[encryptedData.Length];
int decryptedCount = cryptoStream.Read(plainText, 0, plainText.Length);
return Encoding.Unicode.GetString(plainText, 0, decryptedCount);
}
}
}
}
#endregion
}
您不需要NameSpace
。
上面的類可以執行加密和解密以'?'
開頭的任何URL參數所需的一切 字符。 它甚至可以很好地將您的參數變量重命名為'enc',這是一個獎勵。
最后,將類放在App_Start
文件夾中,而不是 App_Code
文件夾,因為這會與“明確錯誤”沖突。
完成。
積分:
https://www.codeproject.com/questions/1036066/how-to-hide-url-parameter-asp-net-mvc
https://msdn.microsoft.com/en-us/library/aa719858(v=vs.71).aspx
https://stackoverflow.com/questions/1391060/httpmodule-with-asp-net-mvc-not-被叫
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.