我正在设置 Django 以发送 JWT 响应而不是视图。我尝试使用 django-rest-framework-simplejwt。
在这个框架中提供了一个TokenObtainPairView.as_view()
返回一对jwt的函数。我需要使用另一个 Json 响应返回访问令牌,而不是提供的两个令牌。
理想情况下,我想要一个包含与此相同的访问令牌的 JsonResponse:TokenObtainPairView.as_view()
.
我尝试创建自己的视图,如下所示。
更新:在 Settings.py 中提供
SIMPLE_JWT = {
'ACCESS_TOKEN_LIFETIME': timedelta(days=1),
'REFRESH_TOKEN_LIFETIME': timedelta(days=1),
'ROTATE_REFRESH_TOKENS': False,
'BLACKLIST_AFTER_ROTATION': True,
'ALGORITHM': 'HS256',
'SIGNING_KEY': SECRET_KEY,
'VERIFYING_KEY': None,
'AUTH_HEADER_TYPES': ('Bearer',),
'USER_ID_FIELD': 'id',
'USER_ID_CLAIM': 'user_id',
'AUTH_TOKEN_CLASSES': ('rest_framework_simplejwt.tokens.AccessToken',),
'TOKEN_TYPE_CLAIM': 'token_type',
'SLIDING_TOKEN_REFRESH_EXP_CLAIM': 'refresh_exp',
'SLIDING_TOKEN_LIFETIME': timedelta(days=1),
'SLIDING_TOKEN_REFRESH_LIFETIME': timedelta(days=1),
}
Run Code Online (Sandbox Code Playgroud)
登录网址路径
urlpatterns = [
path('auth/', views.LoginView.as_view()),
]
Run Code Online (Sandbox Code Playgroud)
我创建的登录视图
class LoginView(APIView):
permission_classes = (AllowAny,)
def post(self, request, *args, **kwargs):
username = request.data['username']
password = request.data['password']
user = …
Run Code Online (Sandbox Code Playgroud) 我有以下 JWT 令牌,
eyJhbGciOiJIUzUxMiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJjbGllbnRpZCIsImF1ZCI6ImNsaWVudGlkIiwic3ViIjoiMTIzIiwiYSI6IjQ1NiIsImlhdCI6MTYyMTc5OTU5OCwiZXhwIjoxNjIxNzk5NjU4fQ.hglbX63zhPwTOsB-zSiOMfxEKl5OaIk6zX1o9-LEhP3nro8fa5_3QyIH7I5971j-xuO1bccX1TOh0kNcQ-ACAg
Run Code Online (Sandbox Code Playgroud)
这是使用生成的,
public static string GenerateToken(string key, string a1, string a2)
{
var securityKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(key));
var token = new JwtSecurityToken(
claims: new Claim[]
{
new Claim(JwtRegisteredClaimNames.Iss, "clientid"),
new Claim(JwtRegisteredClaimNames.Aud, "clientid"),
new Claim(JwtRegisteredClaimNames.Sub, a1),
new Claim("a", a2),
new Claim(JwtRegisteredClaimNames.Iat, DateTimeOffset.UtcNow.ToUnixTimeSeconds().ToString(), ClaimValueTypes.Integer64),
},
//notBefore: new DateTimeOffset(DateTime.Now).DateTime,
expires: new DateTimeOffset(DateTime.Now.AddMinutes(1)).DateTime,
signingCredentials: new SigningCredentials(securityKey, SecurityAlgorithms.HmacSha512)
);
return new JwtSecurityTokenHandler().WriteToken(token);
}
var key = "Ym7AD3OT2kpuIRcVAXCweYhV64B0Oi9ETAO6XRbqB8LDL3tF4bMk9x/59PljcGbP5v38BSzCjD1VTwuO6iWA8uzDVAjw2fMNfcT2/LyRlMOsynblo3envlivtgHnKkZj6HqRrG5ltgwy5NsCQ7WwwYPkldhLTF+wUYAnq28+QnU=";
// Key is test
var token = GenerateToken(key, "123", "456");
Run Code Online (Sandbox Code Playgroud)
获得令牌后,我使用下面的代码进行验证,
var key = "Ym7AD3OT2kpuIRcVAXCweYhV64B0Oi9ETAO6XRbqB8LDL3tF4bMk9x/59PljcGbP5v38BSzCjD1VTwuO6iWA8uzDVAjw2fMNfcT2/LyRlMOsynblo3envlivtgHnKkZj6HqRrG5ltgwy5NsCQ7WwwYPkldhLTF+wUYAnq28+QnU="; …
Run Code Online (Sandbox Code Playgroud) 我成功地完成了JwtSecurityTokenHandler
工作X509Certificate2
.我能够用一个X509Certificate2
对象签署令牌.我还能够通过使用证书的原始数据通过X509Certificate2.RawData
属性来验证令牌.
这是代码:
class Program
{
static void Main(string[] args)
{
X509Store store = new X509Store("My");
store.Open(OpenFlags.ReadOnly);
X509Certificate2 signingCert = store.Certificates[0];
string token = CreateTokenWithX509SigningCredentials(signingCert);
ClaimsPrincipal principal = ValidateTokenWithX509SecurityToken(
new X509RawDataKeyIdentifierClause(signingCert.RawData), token);
}
static string CreateTokenWithX509SigningCredentials(X509Certificate2 signingCert)
{
var now = DateTime.UtcNow;
var tokenHandler = new JwtSecurityTokenHandler();
var tokenDescriptor = new SecurityTokenDescriptor
{
Subject = new ClaimsIdentity(new Claim[]
{
new Claim(ClaimTypes.Name, "Tugberk"),
new Claim(ClaimTypes.Role, "Sales"),
}),
TokenIssuerName = "self",
AppliesToAddress = "http://www.example.com",
Lifetime …
Run Code Online (Sandbox Code Playgroud) 使用thinktecture JWT身份验证资源所有者流,我使用JWT的声明部分来进行客户端使用.我的问题是,如果它可以在身份服务器中添加声明并将其解码为客户端中的数组.
数组类型没有ClaimTypeValues.
作为一种解决方法,
var user = IdentityServerPrincipal.Create(response.UserName, response.UserName);
user.Identities.First().AddClaims(
new List<Claim>()
{
new Claim(ClaimTypes.Name, response.UserName),
new Claim(ClaimTypes.Email, response.Email),
new Claim(FullName, response.FullName),
new Claim(AuthorizedCompanies,JsonConvert.SerializeObject(response.AuthorizedCompanies))
});
return new AuthenticateResult(user);
Run Code Online (Sandbox Code Playgroud)
我将声明添加为json数组来声明AuthorizedCompanies并在客户端解析它.如果有的话,这里的设计模式是什么?
我有一个laravel 5后端,使用jwt-auth在登录时发送jwt-token作为json响应.
现在我想将用户角色添加到laravel发送的jwt令牌中,我尝试了以下方式:
这是我现在的控制器
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Http\Controllers\Controller;
use JWTAuth;
use Tymon\JWTAuth\Exceptions\JWTException;
use Illuminate\Database\Eloquent\Model;
use App\User;
class AuthenticateController extends Controller
{
public function authenticate(Request $request)
{
// grab credentials from the request
$credentials = $request->only('email', 'password');
$user = User::where('email', '=', $credentials['email'])->first();
$customClaims = ['role' => $user->role];
try {
// attempt to verify the credentials and create a token for the user
if (! $token = JWTAuth::attempt($credentials, $customClaims)) {
return response()->json(['error' => 'invalid_credentials'], 401);
}
} …
Run Code Online (Sandbox Code Playgroud) 我在WebApi2项目中收到以下错误:
无法加载文件或程序集'System.IdentityModel.Tokens.Jwt,Version = 4.0.0.0,Culture = neutral,PublicKeyToken = 31bf3856ad364e35'或其依赖项之一.定位的程序集的清单定义与程序集引用不匹配.(HRESULT异常:0x80131040)
我安装了这些相关的NuGet包以及其他一些包:
"Microsoft.IdentityModel.Protocol.Extensions"version ="1.0.2.206221351"targetFramework ="net45"
"Microsoft.Owin"version ="3.0.1"targetFramework ="net45"
"Microsoft.Owin.Host.SystemWeb"version ="3.0.1"targetFramework ="net45"
"Microsoft.Owin.Security"version ="3.0.1"targetFramework ="net45"
"Microsoft.Owin.Security.ActiveDirectory"version ="3.0.1"targetFramework ="net45"
"Microsoft.Owin.Security.Jwt"version ="3.0.1"targetFramework ="net45"
"Microsoft.Owin.Security.OAuth"version ="3.0.1"targetFramework ="net45"
"System.IdentityModel.Tokens.Jwt"version ="4.0.2.206221351"targetFramework ="net45"
顺便说一下,我的web.config中也有以下绑定重定向,但它仍然试图加载4.0版本.
<dependentAssembly>
<assemblyIdentity name="System.IdentityModel.Tokens.Jwt" publicKeyToken="31bf3856ad364e35" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-4.0.20622.1351" newVersion="4.0.20622.1351" />
</dependentAssembly>
Run Code Online (Sandbox Code Playgroud)
任何有关故障排除的帮助将非常感谢.
我有一个令牌,一个包含公钥的文件,我想验证签名.我试图基于此验证签名.
但是,decodingCrypto和decodingSignature不匹配.
这是我的代码:
public static string Decode(string token, string key, bool verify)
{
var parts = token.Split('.');
var header = parts[0];
var payload = parts[1];
byte[] crypto = Base64UrlDecode(parts[2]);
var headerJson = Encoding.UTF8.GetString(Base64UrlDecode(header));
var headerData = JObject.Parse(headerJson);
var payloadJson = Encoding.UTF8.GetString(Base64UrlDecode(payload));
var payloadData = JObject.Parse(payloadJson);
if (verify)
{
var bytesToSign = Encoding.UTF8.GetBytes(string.Concat(header, ".", payload));
var keyBytes = Encoding.UTF8.GetBytes(key);
var algorithm = (string)headerData["alg"];
var signature = HashAlgorithms[GetHashAlgorithm(algorithm)](keyBytes, bytesToSign);
var decodedCrypto = Convert.ToBase64String(crypto);
var decodedSignature = Convert.ToBase64String(signature);
if (decodedCrypto != …
Run Code Online (Sandbox Code Playgroud) 我不希望我的令牌过期而且永远有效.
var token = jwt.sign({email_id:'123@gmail.com'}, "Stack", {
expiresIn: '24h' // expires in 24 hours
});
Run Code Online (Sandbox Code Playgroud)
在上面的代码我已经给了24小时..我不希望我的令牌过期.该怎么办?
我认为jwt.io不能很好地解释为什么或何时使用jwt.它解释了可以考虑的其他事情,但决定是否使用它或者为什么它会派上用场并不重要.
我想为什么要使用JSON Web令牌?
身份验证: 将会话存储在服务之外并从无状态专业人员中获益(例如:升级)非常有用.
因此,JWT将不会实现远程会话解决方案,这将需要例如memcached基础架构,令牌管理器软件模块来创建,更新,使令牌无效.但它的缺点是会话信息将在客户端中暴露出来.
信息交换:共享您的秘密(或公钥),以便允许发件人签署令牌.为什么不使用https这个或证书?
什么时候应该使用JSON Web令牌?
身份验证:这是使用JWT的最常见方案.一旦用户登录,每个后续请求将包括JWT,允许用户访问该令牌允许的路由,服务和资源.Single Sign On是一种现在广泛使用JWT的功能,因为它的开销很小,并且能够在不同的域中轻松使用.
信息交换:JSON Web令牌是在各方之间安全传输信息的好方法.因为JWT可以签名 - 例如,使用公钥/私钥对 - 您可以确定发件人是他们所说的人.此外,由于使用标头和有效负载计算签名,您还可以验证内容是否未被篡改.
JSON Web令牌如何工作?
Jtw-Diagram(某种序列图)
我们为什么要使用JSON Web令牌?
让我们来谈谈JSON Web Tokens(JWT)与Simple Web Tokens(SWT)和Security Assertion Markup Language Tokens(SAML)相比的好处.
由于JSON比XML更简洁,因此在编码时它的大小也更小,使得JWT比SAML更紧凑.这使得JWT成为在HTML和HTTP环境中传递的不错选择.**不是jwt本身属性,它是json属性**
在安全方面,SWT只能使用HMAC算法通过共享密钥对称签名.但是,JWT和SAML令牌可以使用X.509证书形式的公钥/私钥对进行签名.与签名JSON的简单性相比,使用XML数字签名对XML进行签名而不会引入模糊的安全漏洞非常困难.**公钥/私钥对签名不新**
JSON解析器在大多数编程语言中很常见,因为它们直接映射到对象.相反,XML没有自然的文档到对象映射.这使得使用JWT比使用SAML断言更容易.
关于使用,JWT用于互联网规模.这突出了在多个平台(尤其是移动平台)上轻松进行JSON Web令牌的客户端处理.**不解释为何在互联网上使用它(在我看来是因为无状态服务器**
我的中间件代码是:
exports.isAuthenticated = (req, res, context) => {
return new Promise((resolve, reject) => {
return passport.authenticate('jwt',{session: false}, (err, user, info) => {
if(err) {
res.status(500).send({message: 'Internal Server Error'})
return resolve(context.stop);
}
if(user) {
return resolve(context.continue);
} else {
res.status(401).send({message: 'Unauthorized'})
return resolve(context.stop)
}
})(req, res);
});
}
Run Code Online (Sandbox Code Playgroud)
我的结语代码是:
// Data plan REST API
const dataplan = epilogue.resource({
model: global.db.DataPlan,
endpoints: ['/api/dataplan', '/api/dataplan/:id']
});
dataplan.all.auth(middleware.isAuthenticated)
dataplan.use(require('./epilogue/dataplan.js'))
Run Code Online (Sandbox Code Playgroud)
而我的dataplan.js
是:
module.exports = {
list: {
auth: async function (req, res, context) { …
Run Code Online (Sandbox Code Playgroud)