1 17 package org.alfresco.repo.webservice.administration; 18 19 import java.io.Serializable ; 20 import java.rmi.RemoteException ; 21 import java.text.MessageFormat ; 22 import java.util.ArrayList ; 23 import java.util.HashMap ; 24 import java.util.HashSet ; 25 import java.util.List ; 26 import java.util.Map ; 27 import java.util.Set ; 28 29 import org.alfresco.model.ContentModel; 30 import org.alfresco.repo.cache.SimpleCache; 31 import org.alfresco.repo.transaction.TransactionComponent; 32 import org.alfresco.repo.transaction.TransactionUtil; 33 import org.alfresco.repo.transaction.TransactionUtil.TransactionWork; 34 import org.alfresco.repo.webservice.AbstractWebService; 35 import org.alfresco.repo.webservice.Utils; 36 import org.alfresco.repo.webservice.action.ActionFault; 37 import org.alfresco.repo.webservice.repository.QuerySession; 38 import org.alfresco.repo.webservice.types.NamedValue; 39 import org.alfresco.service.cmr.repository.NodeRef; 40 import org.alfresco.service.cmr.repository.datatype.DefaultTypeConverter; 41 import org.alfresco.service.cmr.security.AuthenticationService; 42 import org.alfresco.service.cmr.security.PersonService; 43 import org.alfresco.service.namespace.QName; 44 import org.alfresco.util.GUID; 45 import org.apache.axis.MessageContext; 46 import org.apache.commons.logging.Log; 47 import org.apache.commons.logging.LogFactory; 48 49 52 public class AdministrationWebService extends AbstractWebService implements 53 AdministrationServiceSoapPort 54 { 55 56 private static Log logger = LogFactory.getLog(AdministrationWebService.class); 57 58 59 private PersonService personService = null; 60 61 62 private AuthenticationService authenticationService = null; 63 64 65 private TransactionComponent transactionService = null; 66 67 68 private static Set <QName> ignoredProperties = new HashSet <QName>(3); 69 70 71 private SimpleCache<String , UserQuerySession> querySessionCache; 72 73 76 public AdministrationWebService() 77 { 78 AdministrationWebService.ignoredProperties.add(ContentModel.PROP_STORE_PROTOCOL); 80 AdministrationWebService.ignoredProperties.add(ContentModel.PROP_STORE_IDENTIFIER); 81 AdministrationWebService.ignoredProperties.add(ContentModel.PROP_NODE_UUID); 82 } 83 84 89 public void setTransactionService(TransactionComponent transactionService) 90 { 91 this.transactionService = transactionService; 92 } 93 94 99 public void setPersonService(PersonService personService) 100 { 101 this.personService = personService; 102 } 103 104 109 public void setAuthenticationService(AuthenticationService authenticationService) 110 { 111 this.authenticationService = authenticationService; 112 } 113 114 120 public void setQuerySessionCache( 121 SimpleCache<String , UserQuerySession> querySessionCache) 122 { 123 this.querySessionCache = querySessionCache; 124 } 125 126 129 public UserQueryResults queryUsers(final UserFilter filter) 130 throws RemoteException , AdministrationFault 131 { 132 try 133 { 134 return TransactionUtil.executeInUserTransaction(this.transactionService, new TransactionWork<UserQueryResults>() 135 { 136 public UserQueryResults doWork() throws Exception 137 { 138 return queryUsersImpl(filter); 139 } 140 }); 141 } 142 catch (Throwable exception) 143 { 144 if (logger.isDebugEnabled()) 145 { 146 logger.error("Unexpected error occurred", exception); 147 } 148 149 throw new ActionFault(0, exception.getMessage()); 150 } 151 } 152 153 159 private UserQueryResults queryUsersImpl(UserFilter filter) 160 { 161 MessageContext msgContext = MessageContext.getCurrentContext(); 162 163 UserQuerySession userQuerySession = new UserQuerySession(Utils.getBatchSize(msgContext), filter); 165 UserQueryResults userQueryResults = userQuerySession.getNextBatch(); 166 167 if (userQueryResults.getQuerySession() != null) 169 { 170 this.querySessionCache.put(userQueryResults.getQuerySession(), userQuerySession); 172 } 173 174 return userQueryResults; 175 } 176 177 180 public UserQueryResults fetchMoreUsers(final String querySession) 181 throws RemoteException , AdministrationFault 182 { 183 try 184 { 185 return TransactionUtil.executeInUserTransaction(this.transactionService, new TransactionWork<UserQueryResults>() 186 { 187 public UserQueryResults doWork() throws Exception 188 { 189 return fetchMoreUsersImpl(querySession); 190 } 191 }); 192 } 193 catch (Throwable exception) 194 { 195 if (logger.isDebugEnabled()) 196 { 197 logger.error("Unexpected error occurred", exception); 198 } 199 200 throw new ActionFault(0, exception.getMessage()); 201 } 202 } 203 204 209 private UserQueryResults fetchMoreUsersImpl(String querySession) 210 { 211 UserQueryResults queryResult = null; 212 UserQuerySession session = this.querySessionCache.get(querySession); 213 214 if (session != null) 215 { 216 queryResult = session.getNextBatch(); 217 if (queryResult.getQuerySession() == null) 218 { 219 this.querySessionCache.remove(querySession); 220 } 221 } 222 223 return queryResult; 224 } 225 226 229 public UserDetails getUser(final String userName) throws RemoteException , AdministrationFault 230 { 231 try 232 { 233 return TransactionUtil.executeInUserTransaction(this.transactionService, new TransactionWork<UserDetails>() 234 { 235 public UserDetails doWork() throws Exception 236 { 237 return getUserImpl(userName); 238 } 239 }); 240 } 241 catch (Throwable exception) 242 { 243 if (logger.isDebugEnabled()) 244 { 245 logger.error("Unexpected error occurred", exception); 246 } 247 248 throw new ActionFault(0, exception.getMessage()); 249 } 250 } 251 252 260 private UserDetails getUserImpl(String userName) 261 { 262 UserDetails userDetails = null; 263 264 if (this.personService.personExists(userName) == true) 265 { 266 NodeRef nodeRef = this.personService.getPerson(userName); 267 userDetails = createUserDetails(userName, nodeRef); 268 } 269 else 270 { 271 throw new RuntimeException (MessageFormat.format("The user with name {0} does not exist.", new Object []{userName})); 273 } 274 275 return userDetails; 276 } 277 278 284 private UserDetails createUserDetails(String userName, NodeRef nodeRef) 285 { 286 UserDetails userDetails = new UserDetails(); 288 289 userDetails.setUserName(userName); 291 292 Map <QName, Serializable > properties = this.nodeService.getProperties(nodeRef); 294 List <NamedValue> namedValues = new ArrayList <NamedValue>(properties.size()); 295 for (Map.Entry <QName, Serializable > entry : properties.entrySet()) 296 { 297 if (AdministrationWebService.ignoredProperties.contains(entry.getKey()) == false) 298 { 299 String value = null; 300 try 301 { 302 value = DefaultTypeConverter.INSTANCE.convert(String .class, entry.getValue()); 303 } 304 catch (Throwable exception) 305 { 306 value = entry.getValue().toString(); 307 } 308 namedValues.add(new NamedValue(entry.getKey().toString(), value)); 309 } 310 } 311 userDetails.setProperties((NamedValue[])namedValues.toArray(new NamedValue[namedValues.size()])); 312 313 return userDetails; 314 } 315 316 319 public UserDetails[] createUsers(final NewUserDetails[] newUsers) throws RemoteException , AdministrationFault 320 { 321 try 322 { 323 return TransactionUtil.executeInUserTransaction(this.transactionService, new TransactionWork<UserDetails[]>() 324 { 325 public UserDetails[] doWork() throws Exception 326 { 327 return createUsersImpl(newUsers); 328 } 329 }); 330 } 331 catch (Throwable exception) 332 { 333 if (logger.isDebugEnabled()) 334 { 335 logger.error("Unexpected error occurred", exception); 336 } 337 338 throw new ActionFault(0, exception.getMessage()); 339 } 340 } 341 342 350 private UserDetails[] createUsersImpl(NewUserDetails[] newUsers) 351 { 352 UserDetails[] userDetails = new UserDetails[newUsers.length]; 353 354 int index = 0; 355 for (NewUserDetails newUser : newUsers) 356 { 357 this.authenticationService.createAuthentication(newUser.getUserName(), newUser.getPassword().toCharArray()); 359 360 Map <QName, Serializable > properties = new HashMap <QName, Serializable >(7); 362 properties.put(ContentModel.PROP_USERNAME, newUser.getUserName()); 363 for (NamedValue namedValue : newUser.getProperties()) 364 { 365 properties.put(QName.createQName(namedValue.getName()), namedValue.getValue()); 366 } 367 NodeRef personNodeRef = this.personService.createPerson(properties); 368 369 userDetails[index] = createUserDetails(newUser.getUserName(), personNodeRef); 371 index++; 372 } 373 374 return userDetails; 375 } 376 377 380 public UserDetails[] updateUsers(final UserDetails[] users) throws RemoteException , AdministrationFault 381 { 382 try 383 { 384 return TransactionUtil.executeInUserTransaction(this.transactionService, new TransactionWork<UserDetails[]>() 385 { 386 public UserDetails[] doWork() throws Exception 387 { 388 return updateUsersImpl(users); 389 } 390 }); 391 } 392 catch (Throwable exception) 393 { 394 if (logger.isDebugEnabled()) 395 { 396 logger.error("Unexpected error occurred", exception); 397 } 398 399 throw new ActionFault(0, exception.getMessage()); 400 } 401 } 402 403 409 private UserDetails[] updateUsersImpl(UserDetails[] users) 410 { 411 UserDetails[] userDetails = new UserDetails[users.length]; 412 413 int index = 0; 414 for (UserDetails user : users) 415 { 416 Map <QName, Serializable > properties = new HashMap <QName, Serializable >(7); 418 properties.put(ContentModel.PROP_USERNAME, user.getUserName()); 419 for (NamedValue namedValue : user.getProperties()) 420 { 421 properties.put(QName.createQName(namedValue.getName()), namedValue.getValue()); 422 } 423 424 this.personService.setPersonProperties(user.getUserName(), properties); 426 427 NodeRef nodeRef = this.personService.getPerson(user.getUserName()); 429 userDetails[index] = createUserDetails(user.getUserName(), nodeRef); 430 index++; 431 } 432 433 return userDetails; 434 } 435 436 439 public void changePassword(final String userName, final String oldPassword, final String newPassword) throws RemoteException , AdministrationFault 440 { 441 try 442 { 443 TransactionUtil.executeInUserTransaction(this.transactionService, new TransactionWork<Object >() 444 { 445 public Object doWork() throws Exception 446 { 447 changePasswordImpl(userName, oldPassword, newPassword); 448 return null; 449 } 450 }); 451 } 452 catch (Throwable exception) 453 { 454 if (logger.isDebugEnabled()) 455 { 456 logger.error("Unexpected error occurred", exception); 457 } 458 459 throw new ActionFault(0, exception.getMessage()); 460 } 461 } 462 463 470 private void changePasswordImpl(String userName, String oldPassword, String newPassword) 471 { 472 this.authenticationService.updateAuthentication(userName, oldPassword.toCharArray(), newPassword.toCharArray()); 474 } 475 476 479 public void deleteUsers(final String [] userNames) throws RemoteException , 480 AdministrationFault 481 { 482 try 483 { 484 TransactionUtil.executeInUserTransaction(this.transactionService, new TransactionWork<Object >() 485 { 486 public Object doWork() throws Exception 487 { 488 deleteUsersImpl(userNames); 489 return null; 490 } 491 }); 492 } 493 catch (Throwable exception) 494 { 495 if (logger.isDebugEnabled()) 496 { 497 logger.error("Unexpected error occurred", exception); 498 } 499 500 throw new ActionFault(0, exception.getMessage()); 501 } 502 } 503 504 509 private void deleteUsersImpl(String [] userNames) 510 { 511 for (String userName : userNames) 512 { 513 this.personService.deletePerson(userName); 514 } 515 } 516 517 522 private class UserQuerySession implements Serializable 523 { 524 private static final long serialVersionUID = -2960711874297744356L; 525 526 private int batchSize = -1; 527 private UserFilter filter; 528 protected int position = 0; 529 private String id; 530 531 537 public UserQuerySession(int batchSize, UserFilter filter) 538 { 539 this.batchSize = batchSize; 540 this.filter = filter; 541 this.id = GUID.generate(); 542 } 543 544 547 public String getId() 548 { 549 return this.id; 550 } 551 552 558 protected int calculateLastRowIndex(int totalRowCount) 559 { 560 int lastRowIndex = totalRowCount; 561 562 if ((this.batchSize != -1) && ((this.position + this.batchSize) < totalRowCount)) 565 { 566 lastRowIndex = this.position + this.batchSize; 567 } 568 569 return lastRowIndex; 570 } 571 572 580 protected void updatePosition(int totalRowCount, UserQueryResults queryResult) 581 { 582 if (this.batchSize == -1) 583 { 584 this.position = -1; 585 queryResult.setQuerySession(null); 586 } 587 else 588 { 589 this.position += this.batchSize; 590 if (this.position >= totalRowCount) 591 { 592 this.position = -1; 594 queryResult.setQuerySession(null); 595 } 596 } 597 } 598 599 604 public UserQueryResults getNextBatch() 605 { 606 UserQueryResults queryResult = null; 607 608 if (this.position != -1) 609 { 610 if (logger.isDebugEnabled()) 611 logger.debug("Before getNextBatch: " + toString()); 612 613 Set <NodeRef> nodeRefs = AdministrationWebService.this.personService.getAllPeople(); 614 615 List <NodeRef> filteredNodeRefs = new ArrayList <NodeRef>(nodeRefs); 617 618 int totalRows = filteredNodeRefs.size(); 619 int lastRow = calculateLastRowIndex(totalRows); 620 int currentBatchSize = lastRow - this.position; 621 622 if (logger.isDebugEnabled()) 623 logger.debug("Total rows = " + totalRows + ", current batch size = " + currentBatchSize); 624 625 List <UserDetails> userDetailsList = new ArrayList <UserDetails>(currentBatchSize); 626 627 for (int x = this.position; x < lastRow; x++) 628 { 629 NodeRef nodeRef = (NodeRef)filteredNodeRefs.get(x); 630 String userName = (String )AdministrationWebService.this.nodeService.getProperty(nodeRef, ContentModel.PROP_USERNAME); 631 UserDetails userDetails = AdministrationWebService.this.createUserDetails(userName, nodeRef); 632 userDetailsList.add(userDetails); 633 } 634 635 queryResult = new UserQueryResults(getId(), (UserDetails[])userDetailsList.toArray(new UserDetails[userDetailsList.size()])); 636 637 updatePosition(totalRows, queryResult); 639 640 if (logger.isDebugEnabled()) 641 logger.debug("After getNextBatch: " + toString()); 642 } 643 644 return queryResult; 645 } 646 } 647 } 648 | Popular Tags |