Geneva Forum
我正在研究一个场景,在这个场景中,我们有一个具有广泛安装基础的win forms应用程序,它将在整个操作过程中频繁地向我们集中托管的各种服务发出呼叫。
这些服务都使用日内瓦框架,所有客户都希望首先呼叫我们的STS,并获得令牌以允许访问这些服务。
我更喜欢ws2007FederationHttpBinding方法,在这种方法中,客户端只需像任何其他WCF服务一样调用该服务,而对Geneva一无所知,绑定负责令牌交换。
后来有人(乔恩·辛普森)给了我一个(我认为是)好主意——添加一个服务,托管在应用程序本身中,以缓存本地检索到的令牌。
本地缓存服务将实现与STS相同的契约;当接收到请求时,它将检查是否存在cahced令牌,如果存在,它将返回它,否则它将调用“真实”STS,检索新令牌,缓存它并返回它。
通过这种方式,我认为我们可以实现两全其美——缓存令牌,而无需服务sepcific定制代码;我们的缓存应该能够处理所有RPs的令牌。
我已经创建了一个非常简单的原型,看看它是否能工作。不幸的是,这并不奇怪,我有点卡住了-
我的本地服务(目前是一个控制台应用程序)收到请求,第一次调用STS来检索令牌,缓存令牌并成功地将其返回给客户端,客户端随后使用它来调用RP。一切都很好。
然而,第二次,我的本地cahce服务再次尝试使用相同的令牌,但客户端失败,出现MessageSecurityException-
static LocalTokenCache.STS.Trust13IssueResponse cachedResponse = null;
public LocalTokenCache.STS.Trust13IssueResponse Trust13Issue(LocalTokenCache.STS.Trust13IssueRequest request)
{
if (TokenCache.cachedResponse == null)
{
Console.WriteLine("cached token not found, calling STS");
//create proxy for real STS
STS.WSTrust13SyncClient sts = new LocalTokenCache.STS.WSTrust13SyncClient();
//set credentials for sts
sts.ClientCredentials.UserName.UserName = "Yossi";
sts.ClientCredentials.UserName.Password = "p@ssw0rd";
//call issue on real sts
STS.RequestSecurityTokenResponseCollectionType stsResponse = sts.Trust13Issue(request.RequestSecurityToken);
//create result object - this is a container type for the response returned and is what we need to return;
TokenCache.cachedResponse = new LocalTokenCache.STS.Trust13IssueResponse();
//assign sts response to return value...
TokenCache.cachedResponse.RequestSecurityTokenResponseCollection = stsResponse;
}
else
{
}
//...and reutn
return TokenCache.cachedResponse;