1 13 14 package org.ejbca.core.ejb.upgrade; 15 16 import java.io.ByteArrayOutputStream ; 17 import java.io.IOException ; 18 import java.io.InputStream ; 19 import java.io.InputStreamReader ; 20 import java.io.UnsupportedEncodingException ; 21 import java.sql.Connection ; 22 import java.sql.PreparedStatement ; 23 import java.sql.ResultSet ; 24 import java.sql.SQLException ; 25 import java.util.ArrayList ; 26 import java.util.Collection ; 27 import java.util.Iterator ; 28 29 import javax.ejb.CreateException ; 30 import javax.ejb.EJBException ; 31 32 import org.apache.commons.lang.StringUtils; 33 import org.ejbca.core.ejb.BaseSessionBean; 34 import org.ejbca.core.ejb.JNDINames; 35 import org.ejbca.core.ejb.ServiceLocator; 36 import org.ejbca.core.ejb.ca.caadmin.ICAAdminSessionLocal; 37 import org.ejbca.core.ejb.ca.caadmin.ICAAdminSessionLocalHome; 38 import org.ejbca.core.ejb.log.LogConfigurationDataLocal; 39 import org.ejbca.core.ejb.log.LogConfigurationDataLocalHome; 40 import org.ejbca.core.model.log.Admin; 41 import org.ejbca.util.JDBCUtil; 42 import org.ejbca.util.SqlExecutor; 43 44 import se.anatom.ejbca.log.OldLogConfigurationDataLocal; 45 import se.anatom.ejbca.log.OldLogConfigurationDataLocalHome; 46 47 107 public class UpgradeSessionBean extends BaseSessionBean { 108 109 110 private String dataSource = ""; 111 112 private OldLogConfigurationDataLocalHome oldLogHome = null; 113 private LogConfigurationDataLocalHome logHome = null; 114 115 private ICAAdminSessionLocal caadminsession = null; 116 private Admin administrator = null; 117 118 123 public void ejbCreate() throws CreateException { 124 dataSource = getLocator().getString(JNDINames.DATASOURCE); 125 logHome = (LogConfigurationDataLocalHome)ServiceLocator.getInstance().getLocalHome(LogConfigurationDataLocalHome.COMP_NAME); 126 oldLogHome = (OldLogConfigurationDataLocalHome)ServiceLocator.getInstance().getLocalHome(OldLogConfigurationDataLocalHome.COMP_NAME); 127 128 } 129 130 133 private ICAAdminSessionLocal getCaAdminSession() { 134 if(caadminsession == null){ 135 try{ 136 ICAAdminSessionLocalHome caadminsessionhome = (ICAAdminSessionLocalHome)getLocator().getLocalHome(ICAAdminSessionLocalHome.COMP_NAME); 137 caadminsession = caadminsessionhome.create(); 138 }catch(Exception e){ 139 throw new EJBException (e); 140 } 141 } 142 return caadminsession; 143 } 145 149 private boolean preCheck() { 150 debug(">preCheck"); 151 boolean ret = false; 152 Connection con = null; 153 PreparedStatement ps = null; 154 try { 155 error("Getting connection for: "+dataSource); 156 con = JDBCUtil.getDBConnection(JNDINames.DATASOURCE); 157 ps = con.prepareStatement("select userDataVO from CertReqHistoryData"); 158 ResultSet rs = ps.executeQuery(); 159 if (rs.next()) { 160 try { 161 String ud = rs.getString(1); 162 java.beans.XMLDecoder decoder = null; 163 try { 164 decoder = new java.beans.XMLDecoder ( 165 new java.io.ByteArrayInputStream (ud.getBytes("UTF8"))); 166 } catch (UnsupportedEncodingException e) { 167 error("Can not decode old UserDataVO: ", e); 168 } 169 se.anatom.ejbca.common.UserDataVO oldud = (se.anatom.ejbca.common.UserDataVO)decoder.readObject(); 170 decoder.close(); 171 ret = true; 173 error("(this is not an error) during pre-check successfully decoded old UserDataVO with username="+oldud.getUsername()); 174 } catch (Exception e) { 175 error("Can not decode old UserDataVO: ", e); 176 } 177 } 178 } catch (Exception e) { 179 error("Database error during preCheck: ", e); 180 } finally { 181 JDBCUtil.close(ps); 182 JDBCUtil.close(con); 183 } 184 debug("<preCheck("+ret+")"); 185 return ret; 186 } 187 188 195 public boolean upgrade(Admin admin, String [] args) { 196 debug(">upgrade("+admin.toString()+")"); 197 this.administrator = admin; 198 199 String dbtype = null; 200 if (args.length > 0) { 201 dbtype = args[0]; 202 debug("Database type="+dbtype); 203 } 204 205 boolean upgradefrom31 = false; 206 if (args.length > 1) { 207 String u = args[1]; 208 if (StringUtils.equalsIgnoreCase(u, "yes")) { 209 upgradefrom31 = true; 210 } 211 } 212 213 if (!migradeDatabase33(dbtype)) { 215 } 218 219 if (!upgradefrom31) { 221 return true; 222 } 223 224 if (!preCheck()) { 225 info("preCheck failed, no upgrade performed."); 226 return false; 227 } 228 229 if (!migradeDatabase31(dbtype)) { 230 return false; 231 } 232 233 if (!upgradeHardTokenClassPath()) { 234 return false; 235 } 236 if (!upgradeUserDataVO()) { 237 return false; 238 } 239 ArrayList datas = logConfStep1(); 240 if (datas != null) { 242 if (!logConfStep2(datas)) { 243 return false; 244 } 245 if (!logConfStep3(datas)) { 246 return false; 247 } 248 } 249 debug("<upgrade()"); 250 return true; 251 } 252 253 254 256 public boolean migradeDatabase(String resource) { 257 InputStream in = this.getClass().getResourceAsStream(resource); 259 if (in == null) { 260 error("Can not read resource for database '"+resource+"', this database probably does not need table definition changes."); 261 return true; 263 } 264 265 Connection con = null; 267 info("Start migration of database."); 268 try { 269 InputStreamReader inreader = new InputStreamReader (in); 270 con = JDBCUtil.getDBConnection(JNDINames.DATASOURCE); 271 SqlExecutor sqlex = new SqlExecutor(con, false); 272 sqlex.runCommands(inreader); 273 } catch (SQLException e) { 274 error("SQL error during database migration: ", e); 275 return false; 276 } catch (IOException e) { 277 error("IO error during database migration: ", e); 278 return false; 279 } finally { 280 JDBCUtil.close(con); 281 } 282 error("(this is not an error) Finished migrating database."); 283 return true; 284 } 285 286 291 public boolean migradeDatabase31(String dbtype) { 292 error("(this is not an error) Starting upgrade from ejbca 3.1.x to ejbca 3.2.x"); 293 boolean ret = migradeDatabase("/31_32/31_32-upgrade-"+dbtype+".sql"); 294 error("(this is not an error) Finished migrating database."); 295 return ret; 296 } 297 302 public boolean migradeDatabase33(String dbtype) { 303 error("(this is not an error) Starting upgrade from ejbca 3.3.x to ejbca 3.4.x"); 304 boolean ret = migradeDatabase("/33_34/33_34-upgrade-"+dbtype+".sql"); 305 error("(this is not an error) Finished migrating database."); 306 return ret; 307 } 308 309 314 public boolean upgradeHardTokenClassPath() { 315 try { 316 ICAAdminSessionLocal casession = getCaAdminSession(); 317 Collection caids = casession.getAvailableCAs(administrator); 318 Iterator iter = caids.iterator(); 319 while (iter.hasNext()) { 320 int caid = ((Integer ) iter.next()).intValue(); 321 casession.upgradeFromOldCAHSMKeyStore(administrator, caid); 322 } 323 } catch (Exception e) { 324 error("Error upgrading hard token class path: ", e); 325 return false; 326 } 327 return true; 328 } 329 330 335 public ArrayList logConfStep1() { 336 ArrayList datas = new ArrayList (); 337 try { 338 Collection oldColl = oldLogHome.findAll(); 339 Iterator it = oldColl.iterator(); 340 while (it.hasNext()) { 341 OldLogConfigurationDataLocal odata = (OldLogConfigurationDataLocal)it.next(); 342 LogConfData d = new LogConfData(); 343 d.id = odata.getId(); 344 d.data = odata.getLogConfiguration(); 345 d.row = odata.getLogEntryRowNumber(); 346 datas.add(d); 347 } 348 error("(this is not an error) read "+datas.size()+" old LogConfigurationData."); 349 } catch (Exception e) { 350 error("Error reading old LogConfigurationData: ", e); 351 return null; 352 } 353 return datas; 354 } 355 356 361 public boolean logConfStep2(ArrayList datas) { 362 try { 363 Iterator it2 = datas.iterator(); 364 while (it2.hasNext()) { 365 LogConfData d = (LogConfData) it2.next(); 366 OldLogConfigurationDataLocal l = oldLogHome.findByPrimaryKey(d.id); 367 oldLogHome.remove(l.getPrimaryKey()); 368 } 369 error("(this is not an error) deleted old LogConfigurationData."); 370 } catch (Exception e) { 371 error("Failed to delete old LogConfigurationData"); 372 return false; 373 } 374 return true; 375 } 376 381 public boolean logConfStep3(ArrayList datas) { 382 try { 383 Iterator it2 = datas.iterator(); 385 error("(this is not an error) Upgrading "+datas.size()+" LogConfigurationData."); 386 while (it2.hasNext()) { 387 LogConfData d = (LogConfData)it2.next(); 388 se.anatom.ejbca.log.LogConfiguration logConf = d.data; 389 org.ejbca.core.model.log.LogConfiguration newLog = new org.ejbca.core.model.log.LogConfiguration( 390 logConf.useLogDB(), logConf.useExternalLogDevices(), logConf.getConfigurationData()); 391 logHome.create(d.id, newLog); 392 LogConfigurationDataLocal dl = logHome.findByPrimaryKey(d.id); 393 dl.setLogEntryRowNumber(d.row); 394 } 395 error("(this is not an error) Upgraded LogConfigurationData successfully."); 396 } catch (Exception e) { 397 error("Error upgrading LogConfigurationData: ", e); 398 return false; 399 } 400 return true; 401 } 402 403 private boolean upgradeUserDataVO() { 404 PreparedStatement ps1 = null; 405 PreparedStatement ps2 = null; 406 Connection con = null; 407 int count = 0; 408 try { 409 con = JDBCUtil.getDBConnection(JNDINames.DATASOURCE); 410 ps1 = con.prepareStatement("select fingerprint,userDataVO from CertReqHistoryData"); 411 ps2 = con.prepareStatement("update CertReqHistoryData set userDataVO=? where fingerprint=?"); 412 ResultSet rs = ps1.executeQuery(); 413 se.anatom.ejbca.common.UserDataVO oldud = null; 414 while (rs.next()) { 415 boolean goon = true; 416 String fp = rs.getString(1); 417 String ud = rs.getString(2); 418 try { 419 java.beans.XMLDecoder decoder = null; 420 try { 421 decoder = new java.beans.XMLDecoder ( 422 new java.io.ByteArrayInputStream (ud.getBytes("UTF8"))); 423 } catch (UnsupportedEncodingException e) { 424 goon = false; 425 } 426 if (goon) { 427 oldud = (se.anatom.ejbca.common.UserDataVO)decoder.readObject(); 428 } 429 decoder.close(); 430 } catch (Exception e) { 431 error("Can not decode old UserDataVO for fingerprint "+fp+": ", e); 432 goon = false; 433 } 434 if (goon) { 435 org.ejbca.core.model.ra.UserDataVO newud = createNewUserDataVO(oldud); 436 ByteArrayOutputStream baos = null; 437 try { 438 baos = new java.io.ByteArrayOutputStream (); 439 java.beans.XMLEncoder encoder = new java.beans.XMLEncoder (baos); 440 encoder.writeObject(newud); 441 encoder.close(); 442 String newudstr = baos.toString("UTF8"); 443 ps2.setString(1, newudstr); 444 ps2.setString(2, fp); 445 ps2.executeUpdate(); 446 count ++; 447 } catch (Exception e) { 448 error("Can not create new UserDataVO for fingerprint "+fp+": ", e); 449 } finally { 450 try { 451 if (baos != null) baos.close(); 452 } catch (Exception e) {} 453 } 454 } 455 if ( (count % 1000) == 0) { 456 error("(this is not an error) migrated "+count+" UserDataVO"); 457 } 458 } 459 } catch (SQLException sqle) { 461 error("Error updating CertReqHistoryData: ", sqle); 462 return false; 463 } finally { 464 JDBCUtil.close(ps1); 465 JDBCUtil.close(ps2); 466 JDBCUtil.close(con); 467 } 468 error("(this is not an error) migrated "+count+" UserDataVO"); 469 return true; 470 } 471 472 private org.ejbca.core.model.ra.UserDataVO createNewUserDataVO(se.anatom.ejbca.common.UserDataVO old) { 473 org.ejbca.core.model.ra.UserDataVO ret = new org.ejbca.core.model.ra.UserDataVO( 474 old.getUsername(), old.getDN(), old.getCAId(), 475 old.getSubjectAltName(),old.getEmail(),old.getStatus(), 476 old.getType(),old.getEndEntityProfileId(),old.getCertificateProfileId(), 477 old.getTimeCreated(),old.getTimeModified(),old.getTokenType(), 478 old.getHardTokenIssuerId(),old.getExtendedinformation() 479 ); 480 return ret; 481 } 482 486 private class LogConfData { 487 public Integer id; 488 public se.anatom.ejbca.log.LogConfiguration data; 489 public int row; 490 } 491 } | Popular Tags |