protected function _getIssueRelatedUsers(TBGIssue $issue)
 {
     $uids = array();
     $cu = TBGContext::getUser()->getID();
     $ns = $this->getSetting(self::NOTIFY_ISSUE_UPDATED_SELF, $cu);
     // Add all users who's marked this issue as interesting
     $uids = TBGUserIssuesTable::getTable()->getUserIDsByIssueID($issue->getID());
     // Add all users from the team owning the issue if valid
     // or add the owning user if a user owns the issue
     if ($issue->getOwnerType() == TBGIdentifiableClass::TYPE_TEAM) {
         foreach ($issue->getOwner()->getMembers() as $member) {
             if ($member->getID() == $cu && !$ns) {
                 continue;
             }
             $uids[$member->getID()] = $member->getID();
         }
     } elseif ($issue->getOwnerType() == TBGIdentifiableClass::TYPE_USER) {
         if (!($issue->getOwnerID() == $cu && !$ns)) {
             $uids[$issue->getOwnerID()] = $issue->getOwnerID();
         }
     }
     // Add the poster
     if ($this->getSetting(self::NOTIFY_ISSUE_POSTED_UPDATED, $issue->getPostedByID())) {
         if (!($issue->getPostedByID() == $cu && !$ns)) {
             $uids[$issue->getPostedByID()] = $issue->getPostedByID();
         }
     }
     // Add all users from the team assigned to the issue if valid
     // or add the assigned user if a user is assigned to the issue
     if ($issue->getAssigneeType() == TBGIdentifiableClass::TYPE_TEAM) {
         // Get team member IDs
         foreach ($issue->getAssignee()->getMembers() as $member) {
             if ($member->getID() == $cu && !$ns) {
                 continue;
             }
             if (!$this->getSetting(self::NOTIFY_ISSUE_TEAMASSIGNED_UPDATED, $member->getID())) {
                 continue;
             }
             $uids[$member->getID()] = $member->getID();
         }
     } elseif ($issue->getAssigneeType() == TBGIdentifiableClass::TYPE_USER) {
         if (!($issue->getAssigneeID() == $cu && !$ns) && !!$this->getSetting(self::NOTIFY_ISSUE_ASSIGNED_UPDATED, $issue->getAssigneeID())) {
             $uids[$issue->getAssigneeID()] = $issue->getAssigneeID();
         }
     }
     // Add all users in the team who leads the project, if valid
     // or add the user who leads the project, if valid
     if ($issue->getProject()->getLeaderType() == TBGIdentifiableClass::TYPE_TEAM) {
         foreach ($issue->getProject()->getLeader()->getMembers() as $member) {
             if ($member->getID() == $cu && !$ns) {
                 continue;
             }
             if (!$this->getSetting(self::NOTIFY_ISSUE_RELATED_PROJECT_TEAMASSIGNED, $member->getID())) {
                 continue;
             }
             $uids[$member->getID()] = $member->getID();
         }
     } elseif ($issue->getProject()->getLeaderType() == TBGIdentifiableClass::TYPE_USER) {
         if (!($issue->getProject()->getLeaderID() == $cu && !$ns) && !!$this->getSetting(self::NOTIFY_ISSUE_PROJECT_ASSIGNED, $issue->getProject()->getLeaderID())) {
             $uids[$issue->getProject()->getLeaderID()] = $issue->getProject()->getLeaderID();
         }
     }
     // Same for QA
     if ($issue->getProject()->getQaResponsibleType() == TBGIdentifiableClass::TYPE_TEAM) {
         foreach ($issue->getProject()->getQaResponsible()->getMembers() as $member) {
             if ($member->getID() == $cu && !$ns) {
                 continue;
             }
             if (!$this->getSetting(self::NOTIFY_ISSUE_RELATED_PROJECT_TEAMASSIGNED, $member->getID())) {
                 continue;
             }
             $uids[$member->getID()] = $member->getID();
         }
     } elseif ($issue->getProject()->getQaResponsibleType() == TBGIdentifiableClass::TYPE_USER) {
         if (!($issue->getProject()->getQaResponsibleID() == $cu && !$ns) && !!$this->getSetting(self::NOTIFY_ISSUE_PROJECT_ASSIGNED, $issue->getProject()->getQaResponsibleID())) {
             $uids[$issue->getProject()->getQaResponsibleID()] = $issue->getProject()->getQaResponsibleID();
         }
     }
     foreach ($issue->getProject()->getAssignedTeams() as $team_id => $assignments) {
         foreach (TBGContext::factory()->TBGTeam($team_id)->getMembers() as $member) {
             if ($member->getID() == $cu && !$ns) {
                 continue;
             }
             if (!$this->getSetting(self::NOTIFY_ISSUE_RELATED_PROJECT_TEAMASSIGNED, $member->getID())) {
                 continue;
             }
             $uids[$member->getID()] = $member->getID();
         }
     }
     foreach ($issue->getProject()->getAssignedUsers() as $user_id => $assignments) {
         $member = TBGContext::factory()->TBGUser($user_id);
         if (!($member->getID() == $cu && !$ns) && !!$this->getSetting(self::NOTIFY_ISSUE_PROJECT_ASSIGNED, $member->getID())) {
             $uids[$member->getID()] = $member->getID();
         }
     }
     // Add all users relevant for all affected editions
     foreach ($issue->getEditions() as $edition_list) {
         if ($edition_list['edition']->getLeaderType() == TBGIdentifiableClass::TYPE_TEAM) {
             foreach ($edition_list['edition']->getLeader()->getMembers() as $member) {
                 if ($member->getID() == $cu && !$ns) {
                     continue;
                 }
                 if (!$this->getSetting(self::NOTIFY_ISSUE_RELATED_PROJECT_TEAMASSIGNED, $member->getID())) {
                     continue;
                 }
                 $uids[$member->getID()] = $member->getID();
             }
         } elseif ($edition_list['edition']->getLeaderType() == TBGIdentifiableClass::TYPE_USER) {
             if (!($edition_list['edition']->getLeaderID() == $cu && !$ns) && !!$this->getSetting(self::NOTIFY_ISSUE_PROJECT_ASSIGNED, $edition_list['edition']->getLeaderID())) {
                 $uids[$edition_list['edition']->getLeaderID()] = $edition_list['edition']->getLeaderID();
             }
         }
         if ($edition_list['edition']->getQaResponsibleType() == TBGIdentifiableClass::TYPE_TEAM) {
             foreach ($edition_list['edition']->getQaResponsible()->getMembers() as $member) {
                 if ($member->getID() == $cu && !$ns) {
                     continue;
                 }
                 if (!$this->getSetting(self::NOTIFY_ISSUE_RELATED_PROJECT_TEAMASSIGNED, $member->getID())) {
                     continue;
                 }
                 $uids[$member->getID()] = $member->getID();
             }
         } elseif ($edition_list['edition']->getQaResponsibleType() == TBGIdentifiableClass::TYPE_USER) {
             if (!($edition_list['edition']->getQaResponsibleID() == $cu && !$ns) && !!$this->getSetting(self::NOTIFY_ISSUE_PROJECT_ASSIGNED, $edition_list['edition']->getQaResponsibleID())) {
                 $uids[$edition_list['edition']->getQaResponsibleID()] = $edition_list['edition']->getQaResponsibleID();
             }
         }
         foreach ($edition_list['edition']->getAssignedTeams() as $team_id => $assignments) {
             foreach (TBGContext::factory()->TBGTeam($team_id)->getMembers() as $member) {
                 if ($member->getID() == $cu && !$ns) {
                     continue;
                 }
                 if (!$this->getSetting(self::NOTIFY_ISSUE_RELATED_PROJECT_TEAMASSIGNED, $member->getID())) {
                     continue;
                 }
                 $uids[$member->getID()] = $member->getID();
             }
         }
         foreach ($edition_list['edition']->getAssignedUsers() as $user_id => $assignments) {
             $member = TBGContext::factory()->TBGUser($user_id);
             if ($member->getID() == $cu && !$ns) {
                 continue;
             }
             if (!$this->getSetting(self::NOTIFY_ISSUE_PROJECT_ASSIGNED, $member->getID())) {
                 continue;
             }
             $uids[$member->getID()] = $member->getID();
         }
     }
     // Add all users relevant for all affected components
     foreach ($issue->getComponents() as $component_list) {
         foreach ($component_list['component']->getAssignedTeams() as $team_id => $assignments) {
             foreach (TBGContext::factory()->TBGTeam($team_id)->getMembers() as $member) {
                 if ($member->getID() == $cu && !$ns) {
                     continue;
                 }
                 if (!$this->getSetting(self::NOTIFY_ISSUE_RELATED_PROJECT_TEAMASSIGNED, $member->getID())) {
                     continue;
                 }
                 $uids[$member->getID()] = $member->getID();
             }
         }
         foreach ($component_list['component']->getAssignedUsers() as $user_id => $assignments) {
             $member = TBGContext::factory()->TBGUser($user_id);
             if ($member->getID() == $cu && !$ns) {
                 continue;
             }
             if (!$this->getSetting(self::NOTIFY_ISSUE_PROJECT_ASSIGNED, $member->getID())) {
                 continue;
             }
             $uids[$member->getID()] = $member->getID();
         }
     }
     foreach ($uids as $uid => $val) {
         if ($this->getSetting(self::NOTIFY_ISSUE_ONCE, $uid)) {
             if ($this->getSetting(self::NOTIFY_ISSUE_ONCE . '_' . $issue->getID(), $uid)) {
                 unset($uids[$uid]);
                 continue;
             } else {
                 $this->saveSetting(self::NOTIFY_ISSUE_ONCE . '_' . $issue->getID(), 1, $uid);
             }
         }
         $uids[$uid] = TBGContext::factory()->TBGUser($uid);
     }
     return $uids;
 }
 public function componentBulkWorkflow()
 {
     $workflow_items = array();
     $project = null;
     $issues = array();
     $first = true;
     foreach ($this->issue_ids as $issue_id) {
         $issue = new TBGIssue($issue_id);
         $issues[$issue_id] = $issue;
         if ($first) {
             $workflow_items = $issue->getAvailableWorkflowTransitions();
             $project = $issue->getProject();
             $first = false;
         } else {
             $transitions = $issue->getAvailableWorkflowTransitions();
             foreach ($workflow_items as $transition_id => $transition) {
                 if (!array_key_exists($transition_id, $transitions)) {
                     unset($workflow_items[$transition_id]);
                 }
             }
             if ($issue->getProject()->getID() != $project->getID()) {
                 $project = null;
                 break;
             }
         }
         if (!count($workflow_items)) {
             break;
         }
     }
     $this->issues = $issues;
     $this->project = $project;
     $this->available_transitions = $workflow_items;
 }
 /**
  * View an issue
  * 
  * @param TBGRequest $request
  */
 public function runViewIssue(TBGRequest $request)
 {
     //TBGEvent::listen('core', 'viewissue', array($this, 'listenViewIssuePostError'));
     TBGLogging::log('Loading issue');
     if ($issue_no = TBGContext::getRequest()->getParameter('issue_no')) {
         $issue = TBGIssue::getIssueFromLink($issue_no);
         if ($issue instanceof TBGIssue) {
             if (!$this->selected_project instanceof TBGProject || $issue->getProjectID() != $this->selected_project->getID()) {
                 $issue = null;
             }
         } else {
             TBGLogging::log("Issue no [{$issue_no}] not a valid issue no", 'main', TBGLogging::LEVEL_WARNING_RISK);
         }
     }
     TBGLogging::log('done (Loading issue)');
     //$this->getResponse()->setPage('viewissue');
     if ($issue instanceof TBGIssue && (!$issue->hasAccess() || $issue->isDeleted())) {
         $issue = null;
     }
     if ($issue instanceof TBGIssue) {
         if (!array_key_exists('viewissue_list', $_SESSION)) {
             $_SESSION['viewissue_list'] = array();
         }
         $k = array_search($issue->getID(), $_SESSION['viewissue_list']);
         if ($k !== false) {
             unset($_SESSION['viewissue_list'][$k]);
         }
         array_push($_SESSION['viewissue_list'], $issue->getID());
         if (count($_SESSION['viewissue_list']) > 10) {
             array_shift($_SESSION['viewissue_list']);
         }
         TBGEvent::createNew('core', 'viewissue', $issue)->trigger();
     }
     $message = TBGContext::getMessageAndClear('issue_saved');
     $uploaded = TBGContext::getMessageAndClear('issue_file_uploaded');
     if ($request->isMethod(TBGRequest::POST) && $issue instanceof TBGIssue && $request->hasParameter('issue_action')) {
         switch ($request->getParameter('issue_action')) {
             case 'save':
                 if ($issue->hasUnsavedChanges()) {
                     if (!$issue->hasMergeErrors()) {
                         try {
                             $issue->getWorkflowStep()->getWorkflow()->moveIssueToMatchingWorkflowStep($issue);
                             $issue->save();
                             TBGContext::setMessage('issue_saved', true);
                             $this->forward(TBGContext::getRouting()->generate('viewissue', array('project_key' => $issue->getProject()->getKey(), 'issue_no' => $issue->getFormattedIssueNo())));
                         } catch (TBGWorkflowException $e) {
                             $this->error = $e->getMessage();
                             $this->workflow_error = true;
                         } catch (Exception $e) {
                             $this->error = $e->getMessage();
                         }
                     } else {
                         $this->issue_unsaved = true;
                     }
                 } else {
                     $this->forward(TBGContext::getRouting()->generate('viewissue', array('project_key' => $issue->getProject()->getKey(), 'issue_no' => $issue->getFormattedIssueNo())));
                 }
                 break;
         }
     } elseif ($message == true) {
         $this->issue_saved = true;
     } elseif ($uploaded == true) {
         $this->issue_file_uploaded = true;
     } elseif (TBGContext::hasMessage('issue_error')) {
         $this->error = TBGContext::getMessageAndClear('issue_error');
     } elseif (TBGContext::hasMessage('issue_message')) {
         $this->issue_message = TBGContext::getMessageAndClear('issue_message');
     }
     $issuelist = array();
     $issues = TBGContext::getUser()->getStarredIssues();
     if (count($issues)) {
         foreach ($issues as $starred_issue) {
             if (!$starred_issue instanceof TBGIssue || !$starred_issue->getProject() instanceof TBGProject || !$this->selected_project instanceof TBGProject) {
                 continue;
             }
             if ($starred_issue->isOpen() && $starred_issue->getProject()->getID() == $this->selected_project->getID()) {
                 $issuelist[$starred_issue->getID()] = array('url' => TBGContext::getRouting()->generate('viewissue', array('project_key' => $this->selected_project->getKey(), 'issue_no' => $starred_issue->getFormattedIssueNo())), 'title' => $starred_issue->getFormattedTitle(true, true));
             }
         }
     }
     if (array_key_exists('viewissue_list', $_SESSION) && is_array($_SESSION['viewissue_list'])) {
         foreach ($_SESSION['viewissue_list'] as $k => $i_id) {
             try {
                 $an_issue = new TBGIssue($i_id);
                 array_unshift($issuelist, array('url' => TBGContext::getRouting()->generate('viewissue', array('project_key' => $an_issue->getProject()->getKey(), 'issue_no' => $an_issue->getFormattedIssueNo())), 'title' => $an_issue->getFormattedTitle(true, true)));
             } catch (Exception $e) {
                 unset($_SESSION['viewissue_list'][$k]);
             }
         }
     }
     if (count($issuelist) == 1) {
         $issuelist = null;
     }
     $this->issuelist = $issuelist;
     $this->issue = $issue;
     $event = TBGEvent::createNew('core', 'viewissue', $issue)->trigger();
     $this->listenViewIssuePostError($event);
 }