Post-ServiceStack 中的注册操作
Post-registration action in ServiceStack
我已经将 ServiceStack 用于几个项目并且非常喜欢它。也就是说,这是我第一次尝试以任何方式处理用户身份验证,所以如果我在这里的理解或实施中犯了任何基本错误,请原谅我。
我需要能够跟踪用户的自定义属性,例如他们的用户类型和关联的公司。为此,我创建了一个单独的 "User" class,其中仅包含有关我要跟踪的用户的详细信息以及自定义位。我喜欢这样,因为例如,我可以将 UserTypeId 存储为 User 的 属性,并将 [Reference] 存储为实际的 UserType 对象。这让我使用服务代码中其他地方的 LoadReferences 将嵌套数据发送回客户端。
为了执行其中任何一项,我需要获取自定义用户对象以发送回浏览器(它是一个网络应用程序)。到目前为止,我已经实现了一个 CustomCredentialsAuthProvider,它将用户对象添加到 AuthResponse,如下所示:
public override object Authenticate(IServiceBase authService, IAuthSession session, Authenticate request)
{
//let normal authentication happen
var authResponse = (AuthenticateResponse)base.Authenticate(authService, session, request);
using (var db = authService.TryResolve<IDbConnectionFactory>().OpenDbConnection())
{
User user = db.LoadSingleById<User>(int.Parse(authResponse.UserId));
//return your own class, but take neccessary data from AuthResponse
return new
{
SessionId = authResponse.SessionId,
ReferrerUrl = authResponse.ReferrerUrl,
ResponseStatus = authResponse.ResponseStatus,
UserSession = user
};
}
}
这很好用。为了在应用程序中处理用户配置文件管理,我 post 任何需要的更新都会写入用户 table 以及 IUserAuthRepository(均使用当前会话 UserAuthId 作为密钥)。
好的,这就是所有的基础工作。如果可能的话,我现在需要做的是允许用户 A 注册另一个用户 B 而无需将他们的会话切换到用户 B。据我所知,Register 方法 returns 只是用户 ID创建...
{"userId":"1019","responseStatus":{}}
...并将会话 cookie 设置为新创建的用户会话。我想我需要一种方法来防止这种自动会话分配,并且能够独立于其他任何事情注册新用户并获取他们的 ID。这可能吗?
在相关说明中,我希望能够在注册后立即取回整个用户配置文件,而不仅仅是 "userId"。就目前而言,我需要立即进行另一个服务器调用以获取用户详细信息(根据 session.UserAuthId 从用户中提取)。
提前致谢!
自定义身份验证服务响应
我建议您始终 return ServiceStack 服务中的具体 class(即,而不是匿名对象)这有助于为 DTO 类型生成元数据服务,并让您反序列化类型化 API 中的响应。
您还应该考虑遵守 Authenticate
服务合同(所有客户都期望)并继续 return AuthenticateResponse
类型。您可以使用 Dictionary<string,string> Meta
属性 将附加元数据附加到 return 类型,例如:
var r = (AuthenticateResponse)base.Authenticate(authService, session, request);
using (var db = authService.TryResolve<IDbConnectionFactory>().Open())
{
User user = db.LoadSingleById<User>(int.Parse(r.UserId));
r.Meta = new Dictionary<String,String> {
{"customId", user.CustomId},
//etc
};
return r;
}
如果您选择 return 不同的类型,您的服务仍然可以工作,但这样它就不会破坏期望接收类型 AuthenticateResponse
.[=25 的 .NET 服务客户端=]
自定义注册实现
对于自定义注册而不是使用现有的 RegisterService 实现,请复制并创建您自己的版本来执行您想要的操作。
注册服务使用 IAuthRepository
依赖来创建新用户:
public IAuthRepository AuthRepo { get; set; }
它转换为 IUserAuthRepository 以便它可以访问更丰富的 API,例如:
var userAuthRepo = AuthRepo.AsUserAuthRepository(GetResolver());
在这里您可以通过填充 UserAuth class 的实例来注册新用户,例如:
var newUserAuth = request.ConvertTo<UserAuth>();
newUserAuth.PrimaryEmail = request.Email;
您可以使用它来创建新用户:
userAuthRepo.CreateUserAuth(newUserAuth, request.Password)
这只是将新的 UserAuth
信息保存到已注册的 IUserAuthRepository
。
由于您现在正在使用自己的 Register class 实现,它不会影响您现有的会话,您可以 return 任何您喜欢的响应。
我已经将 ServiceStack 用于几个项目并且非常喜欢它。也就是说,这是我第一次尝试以任何方式处理用户身份验证,所以如果我在这里的理解或实施中犯了任何基本错误,请原谅我。
我需要能够跟踪用户的自定义属性,例如他们的用户类型和关联的公司。为此,我创建了一个单独的 "User" class,其中仅包含有关我要跟踪的用户的详细信息以及自定义位。我喜欢这样,因为例如,我可以将 UserTypeId 存储为 User 的 属性,并将 [Reference] 存储为实际的 UserType 对象。这让我使用服务代码中其他地方的 LoadReferences 将嵌套数据发送回客户端。
为了执行其中任何一项,我需要获取自定义用户对象以发送回浏览器(它是一个网络应用程序)。到目前为止,我已经实现了一个 CustomCredentialsAuthProvider,它将用户对象添加到 AuthResponse,如下所示:
public override object Authenticate(IServiceBase authService, IAuthSession session, Authenticate request)
{
//let normal authentication happen
var authResponse = (AuthenticateResponse)base.Authenticate(authService, session, request);
using (var db = authService.TryResolve<IDbConnectionFactory>().OpenDbConnection())
{
User user = db.LoadSingleById<User>(int.Parse(authResponse.UserId));
//return your own class, but take neccessary data from AuthResponse
return new
{
SessionId = authResponse.SessionId,
ReferrerUrl = authResponse.ReferrerUrl,
ResponseStatus = authResponse.ResponseStatus,
UserSession = user
};
}
}
这很好用。为了在应用程序中处理用户配置文件管理,我 post 任何需要的更新都会写入用户 table 以及 IUserAuthRepository(均使用当前会话 UserAuthId 作为密钥)。
好的,这就是所有的基础工作。如果可能的话,我现在需要做的是允许用户 A 注册另一个用户 B 而无需将他们的会话切换到用户 B。据我所知,Register 方法 returns 只是用户 ID创建...
{"userId":"1019","responseStatus":{}}
...并将会话 cookie 设置为新创建的用户会话。我想我需要一种方法来防止这种自动会话分配,并且能够独立于其他任何事情注册新用户并获取他们的 ID。这可能吗?
在相关说明中,我希望能够在注册后立即取回整个用户配置文件,而不仅仅是 "userId"。就目前而言,我需要立即进行另一个服务器调用以获取用户详细信息(根据 session.UserAuthId 从用户中提取)。
提前致谢!
自定义身份验证服务响应
我建议您始终 return ServiceStack 服务中的具体 class(即,而不是匿名对象)这有助于为 DTO 类型生成元数据服务,并让您反序列化类型化 API 中的响应。
您还应该考虑遵守 Authenticate
服务合同(所有客户都期望)并继续 return AuthenticateResponse
类型。您可以使用 Dictionary<string,string> Meta
属性 将附加元数据附加到 return 类型,例如:
var r = (AuthenticateResponse)base.Authenticate(authService, session, request);
using (var db = authService.TryResolve<IDbConnectionFactory>().Open())
{
User user = db.LoadSingleById<User>(int.Parse(r.UserId));
r.Meta = new Dictionary<String,String> {
{"customId", user.CustomId},
//etc
};
return r;
}
如果您选择 return 不同的类型,您的服务仍然可以工作,但这样它就不会破坏期望接收类型 AuthenticateResponse
.[=25 的 .NET 服务客户端=]
自定义注册实现
对于自定义注册而不是使用现有的 RegisterService 实现,请复制并创建您自己的版本来执行您想要的操作。
注册服务使用 IAuthRepository
依赖来创建新用户:
public IAuthRepository AuthRepo { get; set; }
它转换为 IUserAuthRepository 以便它可以访问更丰富的 API,例如:
var userAuthRepo = AuthRepo.AsUserAuthRepository(GetResolver());
在这里您可以通过填充 UserAuth class 的实例来注册新用户,例如:
var newUserAuth = request.ConvertTo<UserAuth>();
newUserAuth.PrimaryEmail = request.Email;
您可以使用它来创建新用户:
userAuthRepo.CreateUserAuth(newUserAuth, request.Password)
这只是将新的 UserAuth
信息保存到已注册的 IUserAuthRepository
。
由于您现在正在使用自己的 Register class 实现,它不会影响您现有的会话,您可以 return 任何您喜欢的响应。