GenericSecurityTokenFactory SPI를 사용하여 WS-Security 런타임 환경에 사용할 X.509 토큰을 작성할 수 있습니다. 이러한
보안 토큰은 WSSAPI 및 JAAS 로그인 모듈 등에 사용할 수 있습니다.
이 태스크 정보
XML을 포함하지 않는 X.509 토큰을 작성하는 데 GenericSecurityTokenFactory SPI를 사용하는 경우 이 토큰은
X.509 생성기에 의해서만 생성되고 X.509 이용자만 이용할 수 있습니다. 따라서 X.509 토큰은
각 토큰 특정 생성기 또는 이용자만 사용할 수 있도록 의도된 단순 토큰으로 간주됩니다. X.509 토큰은 GenericSecurityTokenLoginModule이 생성할 수 없습니다.
GenericSecurityTokenFactory는 X509GenerateLoginModule을 사용하여 생성하거나 X509ConsumeLoginModule이 이용할 수 있는 X.509 토큰을 작성하는 데 사용할 수 있는 여러 SPI를 제공합니다. GenericSecurityTokenFactory SPI를 사용하여 작성되는 X.509 토큰은
아웃바운드 메시지에 서명 또는 암호화하거나 인바운드 메시지의 서명을 복호화하거나 검증하는 데 사용할 수 있는
공개 및/또는 개인 키를 포함합니다.
다음과 같은 경우에 이 유형의 토큰을 사용할 수 있습니다.
- 메시지의 서명 키를 동적으로 변경해야 하는 경우.
예를 들어, X509GenerateCallbackHandler에서는 구성 시에 서명 키가 하드 코딩되어야 합니다. 이 하드코딩된 값을 대체해야 하는 경우
로그인 모듈이 단순 X.509 토큰을 공유 상태로 넣을 수 있도록 X509GenerateLoginModule 위로 스택되는
JAAS 로그인 모듈을 코드화할 수 있습니다. 그러면 X509GenerateLoginModule이
단순 X.509 토큰에서 지정되는 개인 키를 사용하여 콜백 핸들러에서 구성된 개인 키를 대체합니다.
- SOAP 메시지에 표시되지 않은 복수의 서명 검증 인증서를 허용해야 하는 경우. 이러한 메시지는
KEYID 및 X509IssuerSerial과 같은 속성에서 참조되는 인증서를 포함합니다.
WS-Security 엔진은 SOAP 메시지에 표시되지 않는 인증서를 동적으로 분석하지 않습니다. 이 인증서는
X509ConsumeCallbackHandler에서 하드코딩되어야 하고 콜백 핸들러에서 한 개의 인증서만 구성할 수 있습니다. 인증서를
스스로 분석하는 코드를 구현하기로 선택하면 이 코드를 X509ConsumeLoginModule 위로 스택되는 JAAS 로그인 모듈에 넣은 다음
단순 X.509 토큰을 원하는 공용 인증서가 들어 있는 공유 상태로 넣을 수 있습니다. 그러면 X509ConsumeLoginModule이
단순 X.509 토큰에서 지정되는 공용 인증서를 사용하여 콜백 핸들러에서 구성되는
인증서를 대체합니다.
X.509 토큰이 작성된 후에는 토큰의 공개 키 및 개인 키를 수정할 수 없습니다. 따라서
작성할 토큰 유형을 판별한 후 다음 단계에 지정된 것과 유사한 명령을 발행하여 토큰 및 JAAS 로그인 모듈을 작성해야 합니다.
- 단순 X.509 토큰 작성
작성할 단순 X.509 토큰의 유형을 결정하고 다음과 같은 일련의 명령 중 하나와 비슷한 명령을 발행하십시오.
- 공용 인증서를 포함하는 단순 X.509 토큰을 작성하십시오.
import com.ibm.websphere.wssecurity.wssapi.token.GenericSecurityTokenFactory;
import com.ibm.websphere.wssecurity.wssapi.token.X509Token;
import java.security.cert.X509Certificate;
...
X509Certificate publicCert = null;
GenericSecurityTokenFactory factory = GenericSecurityTokenFactory.getInstance();
//implement code to obtain the public certificate
X509Token x509 = factory.getSimpleX509PublicToken(publicCert);
- 개인 키 및 선택적 공개 키를 포함하는 단순 X.509 토큰을 작성하십시오.
import com.ibm.websphere.wssecurity.wssapi.token.GenericSecurityTokenFactory;
import com.ibm.websphere.wssecurity.wssapi.token.X509Token;
import java.security.Key;
import java.security.cert.X509Certificate;
...
Key privateKey = null;
X509Certificate publicCert = null;
GenericSecurityTokenFactory factory = GenericSecurityTokenFactory.getInstance();
//implement code to obtain the private key
//optionally implement code to obtain the public certificate
X509Token x509 = null;
try {
x509 = factory.getSimpleX509PrivateToken(publicCert , privateKey);
} catch (WSSException ex) {
//throws an exception if privateKey is null
}
- X509GenerateLoginModule 또는 X509ConsumeLoginModule 위에 스택될 수 있는 JAAS 로그인 모듈을 작성하십시오.
package test.tokens;
import com.ibm.websphere.wssecurity.wssapi.token.GenericSecurityTokenFactory;
import com.ibm.websphere.wssecurity.wssapi.WSSUtilFactory;
import java.util.Map;
import javax.security.auth.Subject;
import javax.security.auth.callback.CallbackHandler;
import javax.security.auth.login.LoginException;
import javax.security.auth.spi.LoginModule;
import com.ibm.websphere.wssecurity.wssapi.token.X509Token;
import java.security.KeyStore;
import java.security.cert.X509Certificate;
public class MyX509LoginModule implements LoginModule {
//For the sake of readability, this login module does not
//protect against all NPE's
private Map _sharedState;
private Map _options;
private CallbackHandler _handler;
public void initialize(Subject subject, CallbackHandler callbackHandler,
Map<String, ?> sharedState, Map<String, ?> options) {
this._handler = callbackHandler;
this._sharedState = sharedState;
this._options = options;
}
public boolean login() throws LoginException {
GenericSecurityTokenFactory factory = null;
WSSUtilFactory utilFactory = null;
try {
factory = GenericSecurityTokenFactory.getInstance();
utilFactory = WSSUtilFactory.getInstance();
} catch (Exception e) {
throw new LoginException(e.toString());
}
X509Token x509 = null;
try {
x509 = getX509Token(factory, utilFactory);
} catch (Exception e) {
throw new LoginException("Exception: "+e.toString());
}
//if generating (signing/encrypting):
factory.putGeneratorTokenToSharedState(this._sharedState, x509);
//if consuming (decrypting/signature verification):
factory.putConsumerTokenToSharedState(this._sharedState, x509);
return true;
}
public X509Token getX509Token (GenericSecurityTokenFactory factory,
WSSUtilFactory utilFactory) throws Exception{
//This sample uses a sample keystore
final String KEYSTORE = "c:/WebSphere/AppServer/profiles/AppSrv01/etc/ws-security/samples/dsig-sender.ks";
final String KEYSTORE_PASS = "client";
final String ALIAS = "soaprequester";
final String ALIAS_PASS = "client";
final String KEYSTORE_TYPE = "jks";
X509Certificate publicKey = null;
java.security.Key privateKey = null;
java.security.cert.Certificate cert = null;
X509Token x509 = null;
//if you need to get the inbound token so that you can do some processing
//to determine which certificate to obtain, get then OMElement for the inbound token
Map wssContext = utilFactory.GetWSSContext(this._handler);
org.apache.axiom.om.OMElement element = utilFactory.getProcessingElement(wssContext);
//Open the keystore
java.security.KeyStore keystore = utilFactory.getKeyStore(KEYSTORE_TYPE, KEYSTORE, KEYSTORE_PASS.toCharArray());
//Get the entry from the keystore
KeyStore.PasswordProtection pwdProtection = null;
if (ALIAS_PASS != null) {
pwdProtection = new KeyStore.PasswordProtection(ALIAS_PASS.toCharArray());
}
KeyStore.Entry entry = keystore.getEntry(ALIAS, pwdProtection);
//Get the public and/or private key from the entry
if (entry instanceof KeyStore.PrivateKeyEntry) {
//entry is a private key
KeyStore.PrivateKeyEntry pkentry = (KeyStore.PrivateKeyEntry)entry;
cert = pkentry.getCertificate();
privateKey = pkentry.getPrivateKey();
} else if (entry instanceof KeyStore.TrustedCertificateEntry) {
//entry is a public key
KeyStore.TrustedCertificateEntry tcentry = (KeyStore.TrustedCertificateEntry)entry;
cert = tcentry.getTrustedCertificate();
}
if ((cert != null) && (cert instanceof X509Certificate)) {
publicKey = (X509Certificate)cert;
} else {
throw new LoginException("Certificate is not X509Certificate");
}
x509 = factory.getSimpleX509Token(publicKey, privateKey);
if (x509 == null) {
throw new LoginException("X509Token is null");
}
return x509;
}
}
- JAAS 로그인 구성을 작성하십시오.
참고: 이 단계에서는 토큰을 생성하기 위해 X509GenerateLoginModule 위로
스택하고 있는 것으로 가정합니다. X509ConsumeLoginModule 위로 스택하여 토큰을 이용하려는 경우
단계를 수정하여 변화를 수용해야 합니다.
- 관리 콘솔에서 으로 이동하십시오.
- 인증 아래에서 으로 이동하십시오.
- 새로 작성을 클릭하고 별명에 test.generate.x509를 입력하십시오.
- JAAS 로그인 모듈에서 새로 작성을 클릭하고 모듈 클래스 이름에 test.tokens.MyX509LoginModule을 입력하십시오.
로그인 모듈 프록시 사용을 선택하고 확인을 클릭하십시오.
- 새로 작성을 클릭하고 모듈 클래스 이름에 com.ibm.ws.wssecurity.wssapi.token.impl.X509GenerateLoginModule을 입력하십시오.
확인을 클릭하십시오.
- JAAS 시스템 로그인 페이지로 돌아가려면 이동 경로에서 JAAS - 시스템 로그인을 클릭하십시오.
- 새 JAAS 구성을 사용하도록 X.509 토큰 생성기를 구성하십시오.
참고: 이 단계에서는 토큰을 생성하기 위해 X509GenerateLoginModule 위로
스택하고 있는 것으로 가정합니다. X509ConsumeLoginModule 위로 스택하여 토큰을 이용하려는 경우
단계를 수정하여 변화를 수용해야 합니다.
- 관리 콘솔에서 변경하려는 바인딩 구성을 여십시오.
- 를 선택하십시오.
- 인증 토큰에서 변경할 아웃바운드 X.509 토큰을 선택하십시오.
- JAAS 로그인에서 test.generate.x509를 선택하십시오.
- 확인과
저장을 차례로 클릭하십시오.
- 애플리케이션 서버를 다시 시작하여 JAAS 구성 변경사항을 적용하십시오.
- 서비스를 테스트하십시오.