public async Task <IList <IssueDTO> > GetAll(ObjectId issueId, bool recursive) { var issue = await _issueRepository.GetAsync(issueId); if (issue == null) { throw new HttpStatusException(StatusCodes.Status400BadRequest, $"Issue {issueId} does not exist"); } //TODO Field can be null because DB was not cleared yet if (issue.ChildrenIssueIds == null) { return(new List <IssueDTO>()); } IList <Issue> children; if (recursive) { children = await _issueHelper.GetChildrenRecursive(issue); } else { children = await Task.WhenAll(issue.ChildrenIssueIds.Select(it => _issueRepository.GetAsync(it))); } if (await _authorizationService.HasAtLeastOneRequirement(_httpContextAccessor.HttpContext.User, await _projectRepository.GetAsync(issue.ProjectId), ProjectRolesRequirement.CustomerRequirement)) { children = children.Where(it => it.IssueDetail.Visibility).ToList(); } return(await Task.WhenAll(children.Select(it => _issueService.Get(it.Id)))); }
public void RegisterFsmEvents() { Func <Issue, StateDTO, StateDTO, Task <StateDTO> > moveToProcessingPhase = async(Issue issue, StateDTO oldState, StateDTO newState) => { if (oldState.Phase == State.NegotiationPhase && newState.Phase == State.ProcessingPhase) { if (!issue.IssueDetail.RequirementsAccepted) { throw new HttpStatusException(400, "An issue can only be moved from negotiation phase to processing phase if the requirements are accepted"); } } //Das Issue wird in Waiting gesetzt wenn das Startdatum noch nicht erreicht ist if (issue.IssueDetail.StartDate > DateTime.Now) { var waitingState = await GetStateByName(issue, State.WaitingState); return(await SetState(issue, waitingState)); } Task <Issue> parent = null; if (issue.ParentIssueId is { } parentId) { parent = _issueRepository.GetAsync(parentId); } var predecessors = Task.WhenAll(issue.PredecessorIssueIds.Select(_issueRepository.GetAsync)); Task <StateDTO> parentState = null; if (parent is { } parentNotNull) { parentState = _stateService.GetState((await parentNotNull).ProjectId, (await parentNotNull).StateId); } var predecessorStates = await Task.WhenAll((await predecessors).Select(it => _stateService.GetState(it.ProjectId, it.StateId))); /* * Issue wird blockiert wenn: * 1) Das Oberticket nicht in der Bearbeitungsphase ist * 2) Nicht alle Vorgänger abgeschlossen sind * */ if (parentState != null && ((await parentState).Phase == State.NegotiationPhase || (await parentState).Phase == State.BlockedState || (await parentState).Phase == State.WaitingState) || predecessorStates.HasWhere(it => it.Phase != State.ConclusionPhase)) { var blockedState = await GetStateByName(issue, State.BlockedState); return(await SetState(issue, blockedState)); } var res = await SetState(issue, newState); await OnIssueReachedProcessingPhase(issue); return(res); }; _updateStateHandler.AddEvent( new FsmEvent <Func <Issue, StateDTO, StateDTO, Task <StateDTO> > > //CheckingState -> NegotiationState { OldState = State.CheckingState, NewState = State.NegotiationState, Func = async(issue, oldState, newState) => await SetState(issue, newState) }); _updateStateHandler.AddEvent( new FsmEvent <Func <Issue, StateDTO, StateDTO, Task <StateDTO> > > //NegotiationState -> ProcessingState { OldState = State.NegotiationState, NewState = State.ProcessingState, Func = moveToProcessingPhase }); _updateStateHandler.AddEvent(new FsmEvent <Func <Issue, StateDTO, StateDTO, Task <StateDTO> > > //BlockedState -> ProcessingState { OldState = State.BlockedState, NewState = State.ProcessingState, Func = moveToProcessingPhase }); _updateStateHandler.AddEvent(new FsmEvent <Func <Issue, StateDTO, StateDTO, Task <StateDTO> > > //WaitingState -> ProcessingState { OldState = State.WaitingState, NewState = State.ProcessingState, Func = moveToProcessingPhase }); _updateStateHandler.AddEvent(new FsmEvent <Func <Issue, StateDTO, StateDTO, Task <StateDTO> > > //Cancel Issue { OldState = "", NewState = State.CancelledState, Func = async(issue, oldState, newState) => { //Cancels all children await SetState(issue, newState); var children = await _issueHelper.GetChildrenRecursive(issue); await Task.WhenAll(children.Select(it => UpdateState(it, newState))); await OnIssueReachedCompletionPhase(issue); return(newState); } }); _updateStateHandler.AddEvent( new FsmEvent <Func <Issue, StateDTO, StateDTO, Task <StateDTO> > > //ProcessingState -> ReviewState { OldState = State.ProcessingState, NewState = State.ReviewState, Func = async(issue, oldState, newState) => { var children = await Task.WhenAll(issue.ChildrenIssueIds.Select(_issueRepository.GetAsync)); var childrenStates = await Task.WhenAll(children.Select(it => _stateService.GetState(it.ProjectId, it.StateId))); if (childrenStates.HasWhere(it => it.Phase != State.ConclusionPhase)) { throw new HttpStatusException(400, "At least one sub issue is not in conclusion phase"); } return(await SetState(issue, newState)); } }); _updateStateHandler.AddEvent( new FsmEvent <Func <Issue, StateDTO, StateDTO, Task <StateDTO> > > //ReviewState -> CompletedState { OldState = State.ReviewState, NewState = State.CompletedState, Func = async(issue, oldState, newState) => { //TODO Projektleiter überprüft ticket await SetState(issue, newState); await OnIssueReachedCompletionPhase(issue); return(newState); } }); _updateStateHandler.AddEvent( new FsmEvent <Func <Issue, StateDTO, StateDTO, Task <StateDTO> > > //CompletedState -> ArchivedState { OldState = State.CompletedState, NewState = State.ArchivedState, Func = async(issue, oldState, newState) => { //TODO Abschlusskommentar await SetState(issue, newState); await OnIssueReachedCompletionPhase(issue); return(newState); } }); _updateStateHandler.AddEvent(new FsmEvent <Func <Issue, StateDTO, StateDTO, Task <StateDTO> > > { OldState = State.ReviewState, NewState = State.ProcessingState, Func = async(issue, oldState, newState) => await SetState(issue, newState) }); }