}
private XmlObject actionGeneratePlan(PortletRequest request, RealmData data) {
normalize(data);
ModuleDocument doc = ModuleDocument.Factory.newInstance();
ModuleType root = doc.addNewModule();
EnvironmentType environment = root.addNewEnvironment();
ArtifactType configId = environment.addNewModuleId();
configId.setGroupId("console.realm");
String artifactId = data.getName();
if(artifactId.indexOf('/') != -1) {
// slash in artifact-id results in invalid configuration-id and leads to deployment errors.
// Note: 0x002F = '/'
artifactId = artifactId.replaceAll("/", "%2F");
}
configId.setArtifactId(artifactId);
configId.setVersion("1.0");
configId.setType("car");
// Parent
DependenciesType dependenciesType = environment.addNewDependencies();
ArtifactType parent = dependenciesType.addNewDependency();
parent.setGroupId("org.apache.geronimo.configs");
parent.setArtifactId("j2ee-security");
parent.setType("car");
// Dependencies
if (data.getJar() != null) {
ArtifactType artifactType = dependenciesType.addNewDependency();
Artifact artifact = Artifact.create(data.getJar());
artifactType.setGroupId(artifact.getGroupId());
artifactType.setArtifactId(artifact.getArtifactId());
artifactType.setVersion(artifact.getVersion().toString());
artifactType.setType(artifact.getType());
}
// Build the realm GBean
GbeanType realm = GbeanType.Factory.newInstance();
realm.setName(data.getName());
realm.setClass1("org.apache.geronimo.security.realm.GenericSecurityRealm");
AttributeType realmName = realm.addNewAttribute();
realmName.setName("realmName");
realmName.setStringValue(data.getName());
ReferenceType serverInfo = realm.addNewReference();
serverInfo.setName2("ServerInfo");
serverInfo.setName((String) PortletManager.getNameFor(request, PortletManager.getCurrentServer(request).getServerInfo()).getName().get("name"));
ReferenceType loginService = realm.addNewReference();
loginService.setName2("LoginService");
loginService.setName((String) PortletManager.getNameFor(request, PortletManager.getCurrentServer(request).getLoginService()).getName().get("name"));
XmlAttributeType config = realm.addNewXmlReference();
// Construct the content to put in the XmlAttributeType
GerLoginConfigDocument lcDoc = GerLoginConfigDocument.Factory.newInstance();
GerLoginConfigType login = lcDoc.addNewLoginConfig();
for (int i = 0; i < data.getModules().length; i++) {
LoginModuleDetails details = data.getModules()[i];
if (details.getLoginDomainName() == null || details.getLoginDomainName().equals("")) {
continue;
}
GerLoginModuleType module = login.addNewLoginModule();
module.setControlFlag(details.getControlFlag().equals("OPTIONAL") ? GerControlFlagType.OPTIONAL :
details.getControlFlag().equals("REQUIRED") ? GerControlFlagType.REQUIRED :
details.getControlFlag().equals("REQUISITE") ? GerControlFlagType.REQUISITE :
details.getControlFlag().equals("SUFFICIENT") ? GerControlFlagType.SUFFICIENT :
GerControlFlagType.OPTIONAL);
module.setServerSide(details.isServerSide());
module.setLoginDomainName(details.getLoginDomainName());
module.setLoginModuleClass(details.getClassName());
module.setWrapPrincipals(details.isWrapPrincipals());
for (Iterator it = details.getOptions().entrySet().iterator(); it.hasNext();) {
Map.Entry entry = (Map.Entry) it.next();
GerOptionType option = module.addNewOption();
option.setName((String) entry.getKey());
option.setStringValue((String) entry.getValue());
}
// bit of a hack -- to put the DataSource module in as a parent for SQL modules
if (details.getClassName().indexOf("SQL") > -1) {
String poolName = (String) details.getOptions().get("dataSourceName");
String appName = (String) details.getOptions().get("dataSourceApplication");
if (poolName != null) {
if (appName == null) appName = "null";
JCAManagedConnectionFactory[] factories = PortletManager.getOutboundFactoriesOfType(request, "javax.sql.DataSource");
for (int j = 0; j < factories.length; j++) {
JCAManagedConnectionFactory factory = factories[j];
try {
ObjectName objectName = ObjectName.getInstance(factory.getObjectName());
final String testName = objectName.getKeyProperty(NameFactory.J2EE_NAME);
final String testApp = objectName.getKeyProperty(NameFactory.J2EE_APPLICATION);
if (testName.equals(poolName) && testApp.equals(appName)) {
String moduleName = objectName.getKeyProperty(NameFactory.JCA_RESOURCE);
ArtifactType artifactType = dependenciesType.addNewDependency();
Artifact artifact = Artifact.create(moduleName);
artifactType.setGroupId(artifact.getGroupId());
artifactType.setArtifactId(artifact.getArtifactId());
artifactType.setVersion(artifact.getVersion().toString());
artifactType.setType(artifact.getType());
break;
}
} catch (MalformedObjectNameException e) {
log.error("Unable to parse ObjectName", e);
}
}
}
}
}
// Copy the content into the XmlAttributeType
XmlCursor loginCursor = lcDoc.newCursor();
loginCursor.toFirstContentToken();
XmlCursor destination = config.newCursor();
destination.toNextToken();
loginCursor.moveXml(destination);
loginCursor.dispose();
destination.dispose();
config.setName("LoginModuleConfiguration");
root.setServiceArray(new AbstractServiceType[]{realm});
//Above code inserts gbean using xsi:type=dep:GBeanType. We also need to account for the substitution group
//by changing the qname:
XmlCursor gbeanCursor = root.newCursor();
try {
if (!gbeanCursor.toChild(ServiceDocument.type.getDocumentElementName())) {
throw new RuntimeException("Could not find service element");
}
gbeanCursor.setName(GBEAN_QNAME);