Memperbarui:
Saya telah menambahkan tautan ini ke jawaban saya yang lain bagaimana menggunakan otentikasi JWT untuk ASP.NET Web API di sini untuk siapa saja yang tertarik pada JWT.
Kami telah berhasil menerapkan otentikasi HMAC untuk mengamankan Web API, dan itu berfungsi dengan baik. Otentikasi HMAC menggunakan kunci rahasia untuk setiap konsumen yang konsumen dan server sama-sama kenal untuk pesan hash hmac, HMAC256 harus digunakan. Sebagian besar kasus, kata sandi hash dari konsumen digunakan sebagai kunci rahasia.
Pesan biasanya dibangun dari data dalam permintaan HTTP, atau bahkan data khusus yang ditambahkan ke header HTTP, pesan mungkin termasuk:
- Stempel waktu: waktu permintaan dikirim (UTC atau GMT)
- Kata kerja HTTP: GET, POST, PUT, DELETE.
- memposting data dan string kueri,
- URL
Di bawah tenda, otentikasi HMAC adalah:
Konsumen mengirimkan permintaan HTTP ke server web, setelah membangun tanda tangan (output dari hmac hash), templat permintaan HTTP:
User-Agent: {agent}
Host: {host}
Timestamp: {timestamp}
Authentication: {username}:{signature}
Contoh untuk permintaan GET:
GET /webapi.hmac/api/values
User-Agent: Fiddler
Host: localhost
Timestamp: Thursday, August 02, 2012 3:30:32 PM
Authentication: cuongle:LohrhqqoDy6PhLrHAXi7dUVACyJZilQtlDzNbLqzXlw=
Pesan untuk hash untuk mendapatkan tanda tangan:
GET\n
Thursday, August 02, 2012 3:30:32 PM\n
/webapi.hmac/api/values\n
Contoh untuk permintaan POST dengan string kueri (tanda tangan di bawah ini tidak benar, hanya sebuah contoh)
POST /webapi.hmac/api/values?key2=value2
User-Agent: Fiddler
Host: localhost
Content-Type: application/x-www-form-urlencoded
Timestamp: Thursday, August 02, 2012 3:30:32 PM
Authentication: cuongle:LohrhqqoDy6PhLrHAXi7dUVACyJZilQtlDzNbLqzXlw=
key1=value1&key3=value3
Pesan untuk hash untuk mendapatkan tanda tangan
GET\n
Thursday, August 02, 2012 3:30:32 PM\n
/webapi.hmac/api/values\n
key1=value1&key2=value2&key3=value3
Harap perhatikan bahwa data formulir dan string kueri harus berurutan, sehingga kode di server mendapatkan string kueri dan data formulir untuk membuat pesan yang benar.
Ketika permintaan HTTP datang ke server, filter tindakan otentikasi diimplementasikan untuk mem-parsing permintaan untuk mendapatkan informasi: HTTP verb, timestamp, uri, form data, dan string kueri, kemudian berdasarkan ini untuk membangun tanda tangan (gunakan hash hmac) dengan rahasia kunci (kata sandi hash) di server.
Kunci rahasia didapat dari database dengan nama pengguna sesuai permintaan.
Kemudian kode server membandingkan tanda tangan pada permintaan dengan tanda tangan yang dibangun; jika sama, otentikasi dilewatkan, jika tidak, gagal.
Kode untuk membuat tanda tangan:
private static string ComputeHash(string hashedPassword, string message)
{
var key = Encoding.UTF8.GetBytes(hashedPassword.ToUpper());
string hashString;
using (var hmac = new HMACSHA256(key))
{
var hash = hmac.ComputeHash(Encoding.UTF8.GetBytes(message));
hashString = Convert.ToBase64String(hash);
}
return hashString;
}
Jadi, bagaimana cara mencegah serangan replay?
Tambahkan kendala untuk cap waktu, sesuatu seperti:
servertime - X minutes|seconds <= timestamp <= servertime + X minutes|seconds
(servertime: waktu permintaan datang ke server)
Dan, cache tanda tangan permintaan dalam memori (gunakan MemoryCache, harus tetap dalam batas waktu). Jika permintaan berikutnya datang dengan tanda tangan yang sama dengan permintaan sebelumnya, itu akan ditolak.
Kode demo diletakkan di sini:
https://github.com/cuongle/Hmac.WebApi