Changeset 15813
- Timestamp:
- 02/26/18 13:38:05 (7 years ago)
- Location:
- branches/2839_HiveProjectManagement
- Files:
-
- 8 edited
Legend:
- Unmodified
- Added
- Removed
-
branches/2839_HiveProjectManagement/HeuristicLab.Clients.Hive.Administrator/3.3/Views/ProjectPermissionsView.cs
r15760 r15813 216 216 217 217 private static IEnumerable<UserGroupBase> GetGrantedPermissionsForProject(Guid projectId) { 218 if (projectId == Guid.Empty) return Enumerable.Empty<UserGroupBase>(); 218 219 var projectPermissions = HiveServiceLocator.Instance.CallHiveService(s => s.GetProjectPermissions(projectId)); 219 220 var userIds = new HashSet<Guid>(projectPermissions.Select(x => x.GrantedUserId)); -
branches/2839_HiveProjectManagement/HeuristicLab.Clients.Hive.Administrator/3.3/Views/ProjectResourcesView.cs
r15760 r15813 170 170 171 171 private static IEnumerable<Resource> GetAssignedResourcesForProject(Guid projectId) { 172 if (projectId == Guid.Empty) return Enumerable.Empty<Resource>(); 172 173 var assignedProjectResources = HiveServiceLocator.Instance.CallHiveService(s => s.GetAssignedResourcesForProjectAdministration(projectId)); 173 174 return HiveAdminClient.Instance.Resources.Where(x => assignedProjectResources.Select(y => y.ResourceId).Contains(x.Id)); -
branches/2839_HiveProjectManagement/HeuristicLab.Clients.Hive.Administrator/3.3/Views/ProjectsView.cs
r15792 r15813 40 40 private const int greenFlagImageIndex = 0; 41 41 private const int redFlagImageIndex = 1; 42 43 private readonly Color changedColor = Color.FromArgb(255, 87, 191, 193); // #57bfc1 44 private readonly Color selectedColor = Color.FromArgb(255, 240, 194, 59); // #f0c23b 42 private const string SELECTED_TAG = ""; // " [selected]"; 43 private const string NOT_STORED_TAG = "**"; // " [not stored]"; 44 private const string CHANGES_NOT_STORED_TAG = "*"; // " [changes not stored]"; 45 46 private readonly Color selectedBackColor = Color.DodgerBlue; 47 private readonly Color selectedForeColor = Color.White; 45 48 46 49 private Project selectedProject = null; … … 222 225 } 223 226 224 if(!IsAdmin() 225 && HiveAdminClient.Instance.CheckOwnershipOfParentProject(selectedProject, 226 UserInformation.Instance.User.Id)) { 227 MessageBox.Show( 228 "Only subprojects of owned projects can be deleted.", 229 "HeuristicLab Hive Administrator", 230 MessageBoxButtons.OK, 231 MessageBoxIcon.Error); 232 return; 233 } 234 235 if (!IsAdmin() && Content.Any(x => x.ParentProjectId == selectedProject.Id)) { 227 if (Content.Any(x => x.ParentProjectId == selectedProject.Id)) { 236 228 MessageBox.Show( 237 229 "Only empty projects can be deleted.", … … 387 379 } 388 380 if (newProject.Id == selectedProject.Id && !nodeSelected) { 389 newNode.BackColor = selectedColor; 390 newNode.Text += " [selected]"; 381 newNode.BackColor = selectedBackColor; 382 newNode.ForeColor = selectedForeColor; 383 newNode.Text += SELECTED_TAG; 391 384 nodeSelected = true; 392 385 } … … 430 423 431 424 if (p.Id == Guid.Empty) { 432 n.Text += " [not stored]";425 n.Text += NOT_STORED_TAG; 433 426 } else if (p.Modified) { 434 n.Text += " [changes not stored]";427 n.Text += CHANGES_NOT_STORED_TAG; 435 428 } 436 429 } … … 450 443 projectResourcesView.Content = project; 451 444 452 bool locked = project == null || (project != null && project.Id == Guid.Empty); 445 bool projectIsNew = project != null && project.Id == Guid.Empty; 446 bool locked = project == null || projectIsNew; 447 bool deleteEnabled = project != null && ( 448 projectIsNew 449 || HiveAdminClient.Instance.CheckOwnershipOfParentProject(project, UserInformation.Instance.User.Id) 450 || !HiveAdminClient.Instance.ProjectDescendants[project.Id].Any()); 451 453 452 addButton.Enabled = !locked; 453 removeButton.Enabled = deleteEnabled; 454 454 projectPermissionsView.Locked = locked; 455 455 projectResourcesView.Locked = locked; … … 461 461 SelectedProject = (Project)projectNode.Tag; 462 462 ResetTreeNodes(projectsTreeView.Nodes); 463 projectNode.BackColor = selectedColor; 464 projectNode.Text += " [selected]"; 463 projectNode.BackColor = selectedBackColor; 464 projectNode.ForeColor = selectedForeColor; 465 projectNode.Text += SELECTED_TAG; 465 466 } 466 467 -
branches/2839_HiveProjectManagement/HeuristicLab.Clients.Hive.Administrator/3.3/Views/ResourcesView.Designer.cs
r15777 r15813 149 149 | System.Windows.Forms.AnchorStyles.Left) 150 150 | System.Windows.Forms.AnchorStyles.Right))); 151 this.treeView.CheckBoxes = true; 151 152 this.treeView.ImageIndex = 0; 152 153 this.treeView.ImageList = this.imageListSlaveGroups; … … 162 163 this.treeView.DragEnter += new System.Windows.Forms.DragEventHandler(this.treeSlaveGroup_DragEnterOver); 163 164 this.treeView.DragOver += new System.Windows.Forms.DragEventHandler(this.treeSlaveGroup_DragEnterOver); 164 this.treeView. QueryContinueDrag += new System.Windows.Forms.QueryContinueDragEventHandler(this.treeSlaveGroup_QueryContinueDrag);165 this.treeView.BeforeCheck += new System.Windows.Forms.TreeViewCancelEventHandler(this.treeSlaveGroup_BeforeCheck); 165 166 // 166 167 // tabSlaveGroup … … 176 177 this.tabSlaveGroup.Size = new System.Drawing.Size(585, 541); 177 178 this.tabSlaveGroup.TabIndex = 1; 179 //this.tabSlaveGroup.TabIndexChanged += TabSlaveGroup_TabIndexChanged; 180 this.tabSlaveGroup.Selected += TabSlaveGroup_Selected; 178 181 // 179 182 // tabDetails … … 245 248 246 249 } 247 248 250 #endregion 249 251 -
branches/2839_HiveProjectManagement/HeuristicLab.Clients.Hive.Administrator/3.3/Views/ResourcesView.cs
r15792 r15813 40 40 private const int slaveImageIndex = 0; 41 41 private const int slaveGroupImageIndex = 1; 42 public const string ungroupedGroupName = "UNGROUPED"; 43 public const string ungroupedGroupDescription = "Contains slaves that are not assigned to any group."; 42 public const string UNGROUPED_GROUP_NAME = "UNGROUPED"; 43 public const string UNGROUPED_GROUP_DESCRIPTION = "Contains slaves that are not assigned to any group."; 44 private const string SELECTED_TAG = ""; // " [selected]"; 45 private const string NOT_STORED_TAG = "**"; // " [not stored]"; 46 private const string CHANGES_NOT_STORED_TAG = "*"; // " [changes not stored]"; 44 47 45 48 private readonly Color changedColor = Color.FromArgb(255, 87, 191, 193); // #57bfc1 46 private readonly Color selectedColor = Color.FromArgb(255, 240, 194, 59); // #f0c23b 49 private readonly Color selectedBackColor = Color.DodgerBlue; 50 private readonly Color selectedForeColor = Color.White; 47 51 private readonly Color calculatingColor = Color.FromArgb(255, 58, 114, 35); // #3a7223 48 52 private readonly Color offlineColor = Color.FromArgb(255, 187, 36, 36); // #bb2424 53 54 55 56 private TreeNode ungroupedGroupNode; 49 57 50 58 private Resource selectedResource = null; … … 107 115 protected override void SetEnabledStateOfControls() { 108 116 base.SetEnabledStateOfControls(); 109 bool enabled = Content != null && !Locked && !ReadOnly && IsAdmin(); 110 btnAddGroup.Enabled = enabled; 111 btnRemoveGroup.Enabled = enabled; 112 btnSave.Enabled = enabled; 113 scheduleView.SetEnabledStateOfSchedule(enabled && IsAdmin()); 117 118 bool locked = Content == null || Locked || ReadOnly || !IsAdmin(); 119 bool scheduleLocked = locked || (selectedResource != null && selectedResource.Id == Guid.Empty); 120 bool addLocked = locked || (selectedResource != null && selectedResource.Id == Guid.Empty) || selectedResource is Slave; 121 122 btnAddGroup.Enabled = !addLocked; 123 btnRemoveGroup.Enabled = !locked; 124 btnSave.Enabled = !locked; 125 viewHost.Locked = locked; 126 scheduleView.Locked = locked; 127 scheduleView.SetEnabledStateOfSchedule(!scheduleLocked); 114 128 } 115 129 #endregion … … 284 298 private void treeSlaveGroup_MouseDown(object sender, MouseEventArgs e) { 285 299 var node = treeView.GetNodeAt(e.Location); 286 if(node != null && !node.Text.StartsWith(ungroupedGroupName)) ChangeSelectedResourceNode(node);300 if(node != null && node != ungroupedGroupNode /*!node.Text.StartsWith(UNGROUPED_GROUP_NAME)*/) ChangeSelectedResourceNode(node); 287 301 } 288 302 … … 291 305 } 292 306 307 private void treeSlaveGroup_BeforeCheck(object sender, TreeViewCancelEventArgs e) { 308 if(e.Node == ungroupedGroupNode) { 309 e.Cancel = true; 310 } 311 } 312 293 313 private void treeSlaveGroup_DragDrop(object sender, DragEventArgs e) { 294 314 if (e.Effect == DragDropEffects.None) return; 295 315 296 var sourceNode = (TreeNode)e.Data.GetData(typeof(TreeNode)); 297 if (sourceNode == null) return; 298 var sourceResource = ((Resource)sourceNode.Tag); 299 if (sourceResource == null) return; 300 301 var treeView = (TreeView)sender; 302 if (sourceNode.TreeView != treeView) return; 303 304 var targetPoint = treeView.PointToClient(new Point(e.X, e.Y)); 305 var targetNode = treeView.GetNodeAt(targetPoint); 306 316 var targetNode = treeView.GetNodeAt(treeView.PointToClient(new Point(e.X, e.Y))); 307 317 var targetResource = (targetNode != null) ? (Resource)targetNode.Tag : null; 308 309 if(!HiveAdminClient.Instance.CheckParentChange(sourceResource, targetResource)) { 310 MessageBox.Show( 311 "You cannot drag resources to this group.", 312 "HeuristicLab Hive Administrator", 313 MessageBoxButtons.OK, 314 MessageBoxIcon.Information); 315 return; 316 } 317 318 if (sourceNode.Parent == null) 319 treeView.Nodes.Remove(sourceNode); 320 else { 321 sourceNode.Parent.Nodes.Remove(sourceNode); 322 sourceResource.ParentResourceId = null; 323 } 324 325 if (targetNode == null) { 326 treeView.Nodes.Add(sourceNode); 327 } else if(targetResource.Id != Guid.Empty) { 328 targetNode.Nodes.Add(sourceNode); 329 sourceResource.ParentResourceId = targetResource.Id; 318 var resources = e.Data.GetData(HeuristicLab.Common.Constants.DragDropDataFormat) as IEnumerable<Resource>; 319 320 foreach(var r in resources) { 321 r.ParentResourceId = targetResource?.Id; 330 322 } 331 323 332 324 HiveAdminClient.Instance.UpdateResourceGenealogy(Content); 333 SelectedResource = sourceResource;334 325 OnContentChanged(); 335 326 } 336 327 337 328 private void treeSlaveGroup_ItemDrag(object sender, ItemDragEventArgs e) { 329 if (!IsAdmin()) return; 330 331 var nodes = GetCheckedNodes(treeView.Nodes).ToList(); 338 332 TreeNode sourceNode = (TreeNode)e.Item; 339 if (IsAdmin()) 340 DoDragDrop(sourceNode, DragDropEffects.All); 333 if(!sourceNode.Checked) nodes.Add(sourceNode); 334 nodes.Remove(ungroupedGroupNode); 335 ungroupedGroupNode.Checked = false; 336 var resources = nodes.Select(x => x.Tag).OfType<Resource>().ToList(); 337 338 if(resources.Count > 0) { 339 DataObject data = new DataObject(); 340 data.SetData(HeuristicLab.Common.Constants.DragDropDataFormat, resources); 341 var action = DoDragDrop(data, DragDropEffects.Copy | DragDropEffects.Link | DragDropEffects.Move); 342 if(action.HasFlag(DragDropEffects.Move)) { 343 foreach (var node in nodes) node.Remove(); 344 StyleTreeNode(ungroupedGroupNode, (Resource)ungroupedGroupNode.Tag, resources); 345 } 346 } 347 } 348 349 private IEnumerable<TreeNode> GetCheckedNodes(TreeNodeCollection nodes) { 350 if (nodes != null) { 351 foreach (var node in nodes.OfType<TreeNode>()) { 352 if (node.Checked && node != ungroupedGroupNode) yield return node; 353 foreach (var child in GetCheckedNodes(node.Nodes)) 354 yield return child; 355 } 356 } 341 357 } 342 358 343 359 private void treeSlaveGroup_DragEnterOver(object sender, DragEventArgs e) { 344 360 e.Effect = DragDropEffects.Move; 345 346 var sourceNode = (TreeNode)e.Data.GetData(typeof(TreeNode)); 347 var sourceResource = ((Resource)sourceNode.Tag); 348 349 var targetPoint = treeView.PointToClient(new Point(e.X, e.Y)); 350 var targetNode = treeView.GetNodeAt(targetPoint); 351 var targetResource = (targetNode != null) ? (Resource)targetNode.Tag : null; 361 var resources = e.Data.GetData(HeuristicLab.Common.Constants.DragDropDataFormat) as IEnumerable<Resource>; 362 var targetNode = treeView.GetNodeAt(treeView.PointToClient(new Point(e.X, e.Y))); 363 var targetResource = targetNode?.Tag as Resource; 352 364 353 365 if(!IsAdmin() 354 || sourceNode == null 355 || sourceResource == null 356 || sourceNode == targetNode 357 || !HiveAdminClient.Instance.CheckParentChange(sourceResource, targetResource) 358 || (targetNode != null && (targetNode.Text.StartsWith(ungroupedGroupName) || targetNode.Parent != null && targetNode.Parent.Text.StartsWith(ungroupedGroupName)))) { 366 || resources == null 367 || !resources.Any() 368 || resources.Any(x => !HiveAdminClient.Instance.CheckParentChange(x, targetResource)) 369 || (targetNode != null && (targetNode == ungroupedGroupNode || targetNode.Parent == ungroupedGroupNode))) { 359 370 e.Effect = DragDropEffects.None; 360 371 } 361 372 } 362 373 363 private void treeSlaveGroup_QueryContinueDrag(object sender, QueryContinueDragEventArgs e) { 364 e.Action = DragAction.Continue; 374 private void TabSlaveGroup_TabIndexChanged(object sender, EventArgs e) { 375 throw new NotImplementedException(); 376 } 377 378 private async void TabSlaveGroup_Selected(object sender, System.Windows.Forms.TabControlEventArgs e) { 379 if(e.TabPage == tabSchedule) { 380 await SecurityExceptionUtil.TryAsyncAndReportSecurityExceptions( 381 action: () => UpdateSchedule(), 382 finallyCallback: () => scheduleView.Content = HiveAdminClient.Instance.Downtimes); 383 } 384 SetEnabledStateOfControls(); 365 385 } 366 386 #endregion … … 394 414 } 395 415 if (newResource.Id == selectedResource.Id && !nodeSelected) { 396 newNode.BackColor = selectedColor; 397 newNode.Text += " [selected]"; 416 newNode.BackColor = selectedBackColor; 417 newNode.ForeColor = selectedForeColor; 418 newNode.Text += SELECTED_TAG; 398 419 nodeSelected = true; 399 420 } … … 427 448 } 428 449 429 var ungroupedNode = new TreeNode(ungroupedGroupName) { 450 // collapse slave-only nodes 451 foreach(TreeNode n in treeView.Nodes) { 452 CollapseSlaveOnlyNodes(n); 453 } 454 455 ungroupedGroupNode = new TreeNode(UNGROUPED_GROUP_NAME) { 430 456 ForeColor = SystemColors.GrayText, 431 457 Tag = new SlaveGroup() { 432 Name = ungroupedGroupName,433 Description = ungroupedGroupDescription458 Name = UNGROUPED_GROUP_NAME, 459 Description = UNGROUPED_GROUP_DESCRIPTION 434 460 } 435 461 }; 436 462 437 int ungroupedSlavesCount = 0;438 463 foreach (var slave in subResources.OfType<Slave>().OrderBy(x => x.Name)) { 439 464 var slaveNode = new TreeNode(slave.Name) { Tag = slave }; 440 465 StyleTreeNode(slaveNode, slave, resources); 441 ungroupedNode.Nodes.Add(slaveNode); 442 ungroupedSlavesCount++; 466 ungroupedGroupNode.Nodes.Add(slaveNode); 443 467 if (selectedResource == null) { 444 468 SelectedResource = slave; … … 446 470 447 471 if (slave.Id == selectedResource.Id && !nodeSelected) { 448 slaveNode.BackColor = selectedColor; 449 slaveNode.Text += " [selected]"; 472 slaveNode.BackColor = selectedBackColor; 473 slaveNode.ForeColor = selectedForeColor; 474 slaveNode.Text += SELECTED_TAG; 450 475 nodeSelected = true; 451 476 } 452 477 } 453 478 454 if (ungroupedSlavesCount > 0) 455 ungroupedNode.Text += " [" + ungroupedSlavesCount.ToString() + "]"; 456 treeView.Nodes.Add(ungroupedNode); 457 treeView.ExpandAll(); 458 479 if (ungroupedGroupNode.Nodes.Count > 0) { 480 ungroupedGroupNode.Text += " [" + ungroupedGroupNode.Nodes.Count.ToString() + "]"; 481 ungroupedGroupNode.Expand(); 482 } 483 treeView.Nodes.Add(ungroupedGroupNode); 484 } 485 486 private void CollapseSlaveOnlyNodes(TreeNode tn) { 487 Resource r = (Resource)tn.Tag; 488 var descendants = HiveAdminClient.Instance.ResourceDescendants; 489 if(descendants.ContainsKey(r.Id)) { 490 if(descendants[r.Id].OfType<SlaveGroup>().Any()) { 491 tn.Expand(); 492 foreach (TreeNode n in tn.Nodes) CollapseSlaveOnlyNodes(n); 493 } else { 494 tn.Collapse(); 495 } 496 } 459 497 } 460 498 … … 511 549 n.BackColor = Color.Transparent; 512 550 n.ForeColor = Color.Black; 551 552 // not stored (i.e. new), changed 553 if (r.Id == Guid.Empty && n != ungroupedGroupNode /*!r.Name.StartsWith(UNGROUPED_GROUP_NAME)*/) { 554 n.Text += NOT_STORED_TAG; 555 } else if (r.Modified && n != ungroupedGroupNode /*!r.Name.StartsWith(UNGROUPED_GROUP_NAME)*/) { 556 n.Text += CHANGES_NOT_STORED_TAG; 557 } 513 558 514 559 // slave count … … 523 568 .Count(); 524 569 } 525 } else if( r.Name.StartsWith(ungroupedGroupName)) {570 } else if(n == ungroupedGroupNode /*|| r.Name.StartsWith(UNGROUPED_GROUP_NAME)*/) { 526 571 childSlavesCount = resources 527 572 .OfType<Slave>() … … 549 594 } 550 595 551 // not stored (i.e. new), changed552 if (r.Id == Guid.Empty && !r.Name.StartsWith(ungroupedGroupName)) {553 n.Text += " [not stored]";554 } else if (r.Modified && !r.Name.StartsWith(ungroupedGroupName)) {555 n.Text += " [changes not stored]";556 }557 558 596 // ungrouped 559 if( r.Name.StartsWith(ungroupedGroupName)) {597 if(n == ungroupedGroupNode /*r.Name.StartsWith(UNGROUPED_GROUP_NAME)*/) { 560 598 n.ForeColor = ForeColor = SystemColors.GrayText; 561 599 } … … 574 612 selectedResource = resource; 575 613 viewHost.Content = selectedResource; 614 576 615 HiveAdminClient.Instance.DowntimeForResourceId = selectedResource != null ? selectedResource.Id : Guid.Empty; 577 await SecurityExceptionUtil.TryAsyncAndReportSecurityExceptions( 578 action: () => UpdateSchedule(), 579 finallyCallback: () => scheduleView.Content = HiveAdminClient.Instance.Downtimes); 580 581 bool locked = !IsAdmin() || resource == null; 582 bool scheduleLocked = locked || (resource != null && resource.Id == Guid.Empty); 583 bool addLocked = locked || (resource != null && resource.Id == Guid.Empty) || resource is Slave; 584 585 btnAddGroup.Enabled = !addLocked; 586 btnRemoveGroup.Enabled = !locked; 587 btnSave.Enabled = !locked; 588 viewHost.Locked = locked; 589 scheduleView.Locked = locked; 590 scheduleView.SetEnabledStateOfSchedule(!scheduleLocked); 616 if (tabSlaveGroup.SelectedTab == tabSchedule) { 617 await SecurityExceptionUtil.TryAsyncAndReportSecurityExceptions( 618 action: () => UpdateSchedule(), 619 finallyCallback: () => scheduleView.Content = HiveAdminClient.Instance.Downtimes); 620 } 621 622 SetEnabledStateOfControls(); 591 623 } 592 624 … … 595 627 SelectedResource = (Resource)resourceNode.Tag; 596 628 ResetTreeNodes(treeView.Nodes, Content); 597 resourceNode.BackColor = selectedColor; 598 resourceNode.Text += " [selected]"; 629 resourceNode.BackColor = selectedBackColor; 630 resourceNode.ForeColor = selectedForeColor; 631 resourceNode.Text += SELECTED_TAG; 599 632 } 600 633 -
branches/2839_HiveProjectManagement/HeuristicLab.Clients.Hive.Administrator/3.3/Views/ScheduleView.cs
r15760 r15813 235 235 } else { 236 236 if (Content == null || Locked || ReadOnly) state = false; 237 groupBox1.Enabled = state;237 //groupBox1.Enabled = state; 238 238 btnClearCal.Enabled = state; 239 239 btnSaveCal.Enabled = state; -
branches/2839_HiveProjectManagement/HeuristicLab.Clients.Hive/3.3/HiveAdminClient.cs
r15792 r15813 327 327 328 328 // change is not possisble... 329 // ... if the moved resource is null 329 // ... if the child resource is null 330 // ... or the child resource equals the parent 330 331 // ... or the new parent is not stored yet 331 332 // ... or the new parent is a slave 332 333 // ... or there is not parental change 333 334 if (child == null 335 || child == parent 334 336 || (parent != null && parent.Id == Guid.Empty) 335 337 || (parent != null && parent is Slave) -
branches/2839_HiveProjectManagement/HeuristicLab.Services.Hive/3.3/Manager/AuthorizationManager.cs
r15737 r15813 93 93 // authorize if user is admin, project owner or owner of a parent project 94 94 public void AuthorizeForProjectAdministration(Guid projectId, bool parentalOwnership) { 95 if (projectId == null ) return;95 if (projectId == null || projectId == Guid.Empty) return; 96 96 var currentUserId = UserManager.CurrentUserId; 97 97 var pm = PersistenceManager; … … 99 99 pm.UseTransaction(() => { 100 100 List<Project> projectBranch = null; 101 if(parentalOwnership) project Dao.GetParentProjectsById(projectId).ToList();101 if(parentalOwnership) projectBranch = projectDao.GetParentProjectsById(projectId).ToList(); 102 102 else projectBranch = projectDao.GetCurrentAndParentProjectsById(projectId).ToList(); 103 103 … … 111 111 // authorize if user is admin, or owner of a parent project, for which the resources are assigned to 112 112 public void AuthorizeForProjectResourceAdministration(Guid projectId, IEnumerable<Guid> resourceIds) { 113 if (projectId == null ) return;113 if (projectId == null || projectId == Guid.Empty) return; 114 114 var currentUserId = UserManager.CurrentUserId; 115 115 var pm = PersistenceManager; … … 146 146 // Check if a project is authorized to use a list of resources 147 147 public void AuthorizeProjectForResourcesUse(Guid projectId, IEnumerable<Guid> resourceIds) { 148 if (projectId == null || resourceIds == null || !resourceIds.Any()) return;148 if (projectId == null || projectId == Guid.Empty || resourceIds == null || !resourceIds.Any()) return; 149 149 var pm = PersistenceManager; 150 150 var assignedProjectResourceDao = pm.AssignedProjectResourceDao;
Note: See TracChangeset
for help on using the changeset viewer.