Commit 6a82d6a4 authored by hasan khaddour's avatar hasan khaddour

Refactor and Comment

parent 37f508dc
...@@ -84,6 +84,14 @@ namespace PSManagement.Api.DI ...@@ -84,6 +84,14 @@ namespace PSManagement.Api.DI
.AllowAnyMethod() .AllowAnyMethod()
.AllowCredentials()); .AllowCredentials());
options.AddPolicy("AllowHiast",
builder => builder
.WithOrigins("**.hiast.edu.sy/") // Add your frontend URL here
.AllowAnyHeader()
.AllowAnyMethod()
.AllowCredentials());
}); });
......
...@@ -46,6 +46,8 @@ namespace PSManagement.Application.Mappers ...@@ -46,6 +46,8 @@ namespace PSManagement.Application.Mappers
CreateMap<StepTrack, StepTrackDTO>() CreateMap<StepTrack, StepTrackDTO>()
.ForMember(d => d.StepInfo, opt => opt.MapFrom(s => s.Step.StepInfo)) .ForMember(d => d.StepInfo, opt => opt.MapFrom(s => s.Step.StepInfo))
.ForMember(d => d.TrackInfo, op => op.MapFrom(e => e.Track.TrackInfo)) .ForMember(d => d.TrackInfo, op => op.MapFrom(e => e.Track.TrackInfo))
.ForMember(d => d.StepWeight, op => op.MapFrom(e => e.Step.Weight))
; ;
CreateMap<EmployeeTrack, EmployeeTrackDTO>() CreateMap<EmployeeTrack, EmployeeTrackDTO>()
.ForMember(d => d.TrackInfo, op => op.MapFrom(e => e.Track.TrackInfo)) .ForMember(d => d.TrackInfo, op => op.MapFrom(e => e.Track.TrackInfo))
......
...@@ -52,6 +52,7 @@ namespace PSManagement.Application.Projects.UseCases.Commands.CreateProject ...@@ -52,6 +52,7 @@ namespace PSManagement.Application.Projects.UseCases.Commands.CreateProject
.WithClassification(request.ProjectClassification) .WithClassification(request.ProjectClassification)
.Build(); .Build();
project.ProjectTypeId = request.ProjectTypeId; project.ProjectTypeId = request.ProjectTypeId;
project.Propose(); project.Propose();
...@@ -60,7 +61,9 @@ namespace PSManagement.Application.Projects.UseCases.Commands.CreateProject ...@@ -60,7 +61,9 @@ namespace PSManagement.Application.Projects.UseCases.Commands.CreateProject
project.AddDomainEvent(new ProjectCreatedEvent(project.Id,project.TeamLeaderId,project.ProjectManagerId)); project.AddDomainEvent(new ProjectCreatedEvent(project.Id,project.TeamLeaderId,project.ProjectManagerId));
await _unitOfWork.SaveChangesAsync(); await _unitOfWork.SaveChangesAsync();
return Result.Success(project.Id); return Result.Success(project.Id);
} }
......
...@@ -42,11 +42,10 @@ namespace PSManagement.Application.Projects.UseCases.Queries.GetCompletionContri ...@@ -42,11 +42,10 @@ namespace PSManagement.Application.Projects.UseCases.Queries.GetCompletionContri
public async Task<Result<IEnumerable<EmployeeContributionDTO>>> Handle(GetCompletionContributionQuery request, CancellationToken cancellationToken) public async Task<Result<IEnumerable<EmployeeContributionDTO>>> Handle(GetCompletionContributionQuery request, CancellationToken cancellationToken)
{ {
_trackSpecification.AddInclude(e => e.EmployeeTracks); _projectSpecification.AddInclude(e=> e.Tracks);
_trackSpecification.AddInclude("EmployeeTracks.Employee"); _projectSpecification.AddInclude("Tracks.EmployeeTracks.Employee");
_trackSpecification.Criteria = e => e.ProjectId == request.ProjectId;
_projectSpecification.AddInclude(e=>e.ProjectCompletion); _projectSpecification.AddInclude(e=>e.ProjectCompletion);
Project project = await _projectsRepository.GetByIdAsync(request.ProjectId, _projectSpecification); Project project = await _projectsRepository.GetByIdAsync(request.ProjectId, _projectSpecification);
if (project is null) if (project is null)
...@@ -61,49 +60,9 @@ namespace PSManagement.Application.Projects.UseCases.Queries.GetCompletionContri ...@@ -61,49 +60,9 @@ namespace PSManagement.Application.Projects.UseCases.Queries.GetCompletionContri
return Result.Invalid(ProjectsErrors.UnCompletedError); return Result.Invalid(ProjectsErrors.UnCompletedError);
} }
IEnumerable<ParticipantContribution> contributions = project.CalculateContributions();
var tracks = await _tracksRepository.ListAsync(_trackSpecification);
return Result.Success(_mapper.Map<IEnumerable<EmployeeContributionDTO>>(contributions));
// Dictionary to accumulate contributions by employee
var contributionsByEmployee = new Dictionary<int, EmployeeContributionDTO>();
foreach (Track track in tracks)
{
foreach (EmployeeTrack employeeTrack in track.EmployeeTracks)
{
var employeeId = employeeTrack.Employee.Id; // Assuming Employee has an Id property
var contributionRatio = employeeTrack.EmployeeWork.ContributingRatio;
// If employee already has contributions, sum them up
if (contributionsByEmployee.ContainsKey(employeeId))
{
contributionsByEmployee[employeeId].ContributionRatio += contributionRatio;
}
else
{
// Otherwise, add a new entry for the employee
contributionsByEmployee[employeeId] = new EmployeeContributionDTO(contributionRatio, _mapper.Map<EmployeeDTO>(employeeTrack.Employee));
}
}
}
// Convert the dictionary values to a list for the final result
var contributions = contributionsByEmployee.Values.ToList();
//var tracks = await _tracksRepository.ListAsync(_trackSpecification);
//var contributions = new List<EmployeeContributionDTO>();
//foreach (Track track in tracks) {
// foreach (EmployeeTrack employeeTrack in track.EmployeeTracks) {
// // need to fix
// contributions.Add(
// new (employeeTrack.EmployeeWork.ContributingRatio,employeeTrack.Employee));
// }
//}
return Result.Success(contributions.AsEnumerable());
} }
......
...@@ -31,7 +31,7 @@ namespace PSManagement.Application.Steps.UseCases.Commands.ChangeStepWeight ...@@ -31,7 +31,7 @@ namespace PSManagement.Application.Steps.UseCases.Commands.ChangeStepWeight
return Result.Invalid(StepsErrors.InvalidWeightError); return Result.Invalid(StepsErrors.InvalidWeightError);
} }
step.Weight = request.Weight; step.UpdateWeight(request.Weight);
await _stepsRepository.UpdateAsync(step); await _stepsRepository.UpdateAsync(step);
......
...@@ -32,7 +32,7 @@ namespace PSManagement.Application.Steps.UseCases.Commands.UpdateCompletionRatio ...@@ -32,7 +32,7 @@ namespace PSManagement.Application.Steps.UseCases.Commands.UpdateCompletionRatio
return Result.Invalid(StepsErrors.InvalidCompletionRatioError); return Result.Invalid(StepsErrors.InvalidCompletionRatioError);
} }
step.CurrentCompletionRatio = request.CompletionRatio; step.ChangeCompletionRatio(request.CompletionRatio);
await _stepsRepository.UpdateAsync(step); await _stepsRepository.UpdateAsync(step);
......
...@@ -10,6 +10,7 @@ namespace PSManagement.Application.Tracks.Common ...@@ -10,6 +10,7 @@ namespace PSManagement.Application.Tracks.Common
public int Id { get; set; } public int Id { get; set; }
public int StepId { get; set; } public int StepId { get; set; }
public int TrackId { get; set; } public int TrackId { get; set; }
public int StepWeight { get; set; }
public StepInfo StepInfo { get; set; } public StepInfo StepInfo { get; set; }
public TrackInfo TrackInfo { get; set; } public TrackInfo TrackInfo { get; set; }
......
...@@ -48,21 +48,22 @@ namespace PSManagement.Application.Tracks.UseCaes.Commands.AddEmployeeTrack ...@@ -48,21 +48,22 @@ namespace PSManagement.Application.Tracks.UseCaes.Commands.AddEmployeeTrack
} }
if (track.TrackInfo.IsCompleted) if (track.IsCompleted())
{ {
return Result.Invalid(TracksErrors.TrackCompletedUpdateError); return Result.Invalid(TracksErrors.TrackCompletedUpdateError);
} }
if (track.EmployeeTracks.Any(e => e.EmployeeId == request.EmployeeId)) { if (track.HasEmployee(request.EmployeeId)) {
return Result.Invalid(TracksErrors.ParticipantTrackExistError); return Result.Invalid(TracksErrors.ParticipantTrackExistError);
} }
var r =_mapper.Map<EmployeeTrack>(request);
//Console.WriteLine(r.EmloyeeId);
EmployeeTrack employeeTrack = await _employeeTracksRepository.AddAsync(_mapper.Map<EmployeeTrack>(request));
var employeeTrack =_mapper.Map<EmployeeTrack>(request);
track.AddEmployeeTrack(request.EmployeeId,request.EmployeeWork,request.EmployeeWorkInfo,request.Notes);
await _unitOfWork.SaveChangesAsync(); await _unitOfWork.SaveChangesAsync();
return Result.Success(employeeTrack.Id); return Result.Success(employeeTrack.Id);
......
...@@ -34,7 +34,7 @@ namespace PSManagement.Application.Tracks.UseCaes.Queries.GetTracksByFilter ...@@ -34,7 +34,7 @@ namespace PSManagement.Application.Tracks.UseCaes.Queries.GetTracksByFilter
public async Task<Result<IEnumerable<TrackDTO>>> Handle(GetTracksByFilterQuery request, CancellationToken cancellationToken) public async Task<Result<IEnumerable<TrackDTO>>> Handle(GetTracksByFilterQuery request, CancellationToken cancellationToken)
{ {
_specification.ApplyOptionalPagination(request.PageSize, request.PageNumber); _specification.ApplyOptionalPagination(request.PageSize, request.PageNumber);
_specification.AddInclude(e => e.Project);
var tracks = await _tracksRepository.ListAsync(_specification); var tracks = await _tracksRepository.ListAsync(_specification);
return Result.Success(_mapper.Map<IEnumerable<TrackDTO>>(tracks)); return Result.Success(_mapper.Map<IEnumerable<TrackDTO>>(tracks));
......
...@@ -31,7 +31,7 @@ namespace PSManagement.Application.Tracks.UseCaes.Queries.GetUncompletedTracks ...@@ -31,7 +31,7 @@ namespace PSManagement.Application.Tracks.UseCaes.Queries.GetUncompletedTracks
{ {
_specification.Criteria = c => c.TrackInfo.IsCompleted == false; _specification.Criteria = c => c.TrackInfo.IsCompleted == false;
_specification.AddInclude(e => e.Project);
var tracks = await _tracksRepository.ListAsync(_specification); var tracks = await _tracksRepository.ListAsync(_specification);
......
...@@ -12,7 +12,7 @@ namespace PSManagement.Contracts.Tracks.Response ...@@ -12,7 +12,7 @@ namespace PSManagement.Contracts.Tracks.Response
TrackInfo TrackInfo, TrackInfo TrackInfo,
String ExecutionState, String ExecutionState,
int TrackExecutionRatio, int TrackExecutionRatio,
int OldExecutionRatio int OldExecutionRatio,
int StepWeight
); );
} }
...@@ -10,11 +10,18 @@ using System.Threading.Tasks; ...@@ -10,11 +10,18 @@ using System.Threading.Tasks;
namespace PSManagement.Domain.Customers.Entities namespace PSManagement.Domain.Customers.Entities
{ {
/// <summary>
/// the class represent the contact info item for the customer
/// </summary>
public sealed class ContactInfo : BaseEntity public sealed class ContactInfo : BaseEntity
{ {
// the key for contact
public String ContactType { get; private set; } public String ContactType { get; private set; }
//the value for contact
public String ContactValue { get; private set; } public String ContactValue { get; private set; }
#region Constructors
public ContactInfo(string contactValue, string contactType) public ContactInfo(string contactValue, string contactType)
{ {
ContactValue = contactValue; ContactValue = contactValue;
...@@ -25,6 +32,6 @@ namespace PSManagement.Domain.Customers.Entities ...@@ -25,6 +32,6 @@ namespace PSManagement.Domain.Customers.Entities
{ {
} }
#endregion Constructors
} }
} }
...@@ -7,6 +7,11 @@ using System.Threading.Tasks; ...@@ -7,6 +7,11 @@ using System.Threading.Tasks;
namespace PSManagement.Domain.Customers.ValueObjects namespace PSManagement.Domain.Customers.ValueObjects
{ {
/// <summary>
/// this is a value object to hide the contact number
/// its old and deprected
/// i use the record instead
/// </summary>
public sealed class ContactNumber : ValueObject public sealed class ContactNumber : ValueObject
{ {
public int Number { get; private set; } public int Number { get; private set; }
......
...@@ -10,6 +10,8 @@ namespace PSManagement.Domain.Employees.Entities ...@@ -10,6 +10,8 @@ namespace PSManagement.Domain.Employees.Entities
public class Department : BaseEntity public class Department : BaseEntity
{ {
public string Name { get; set; } public string Name { get; set; }
#region Constructors
public Department(string name) public Department(string name)
{ {
Name = name; Name = name;
...@@ -18,5 +20,6 @@ namespace PSManagement.Domain.Employees.Entities ...@@ -18,5 +20,6 @@ namespace PSManagement.Domain.Employees.Entities
{ {
} }
#endregion Constructors
} }
} }
...@@ -13,6 +13,13 @@ using System.Threading.Tasks; ...@@ -13,6 +13,13 @@ using System.Threading.Tasks;
namespace PSManagement.Domain.Employees.Entities namespace PSManagement.Domain.Employees.Entities
{ {
/// <summary>
/// Employee Class
///
/// </summary>
/// this class represent an employee that work and manage and lead a project
/// in this class we abstract the employee data and take
/// the only needed data in our problem
public class Employee : BaseEntity public class Employee : BaseEntity
{ {
public int HIASTId { get; set; } public int HIASTId { get; set; }
...@@ -22,6 +29,10 @@ namespace PSManagement.Domain.Employees.Entities ...@@ -22,6 +29,10 @@ namespace PSManagement.Domain.Employees.Entities
public Department Department { get; set; } public Department Department { get; set; }
public PersonalInfo PersonalInfo { get; set; } public PersonalInfo PersonalInfo { get; set; }
public WorkInfo WorkInfo { get; set; } public WorkInfo WorkInfo { get; set; }
// the availablity value object
// we only care about the working hours
// any other inof can be hide in it
public Availability Availability { get; set; } public Availability Availability { get; set; }
......
namespace PSManagement.Domain.Employees.Entities namespace PSManagement.Domain.Employees.Entities
{ {
/// <summary>
/// Availability Details
/// </summary>
/// Current Working Hours on our system
/// this info should be integrated with ldap
public record Availability( public record Availability(
int CurrentWorkingHours, int CurrentWorkingHours,
bool IsAvailable bool IsAvailable
......
namespace PSManagement.Domain.Employees.Entities namespace PSManagement.Domain.Employees.Entities
{ {
/// <summary>
/// Personal Information
/// </summary>
/// this cvalue object record represent the
/// personal information that we care about it in our case
/// we only need the first and last name
public record PersonalInfo( public record PersonalInfo(
string FirstName, string FirstName,
string LastName string LastName
......
...@@ -2,6 +2,12 @@ ...@@ -2,6 +2,12 @@
namespace PSManagement.Domain.Employees.Entities namespace PSManagement.Domain.Employees.Entities
{ {
/// <summary>
/// Work Informations
/// </summary>
/// this record (VO) contain two proerties :
/// Work Type : for the type of work that the employee do like programmer , designer researcher ...
/// Work Job : for the career of the employee like doctor , engineer ,...
public record WorkInfo ( public record WorkInfo (
String WorkType , String WorkType ,
String WorkJob String WorkJob
......
...@@ -5,7 +5,11 @@ ...@@ -5,7 +5,11 @@
</PropertyGroup> </PropertyGroup>
<ItemGroup> <ItemGroup>
<Folder Include="FinancialSpends\DomainErrors\" />
<Folder Include="FinancialSpends\DomainEvents\" />
<Folder Include="FinancialSpends\ValueObjects\" />
<Folder Include="Identity\ValueObjects\" /> <Folder Include="Identity\ValueObjects\" />
<Folder Include="ProjectsTypes\ValueObjects\" />
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>
......
using PSManagement.Domain.Employees.Entities;
namespace PSManagement.Domain.Projects.Entities
{
public class ParticipantContribution {
public int ContributionRatio { get; set; }
public Employee Employee { get; set; }
public ParticipantContribution(int contributionRatio, Employee employee)
{
ContributionRatio = contributionRatio;
Employee = employee;
}
}
}
...@@ -65,7 +65,7 @@ namespace PSManagement.Domain.Projects.Entities ...@@ -65,7 +65,7 @@ namespace PSManagement.Domain.Projects.Entities
public string CurrentState { get; private set; } // Persisted in the database public string CurrentState { get; private set; } // Persisted in the database
[NotMapped] [NotMapped]
private IProjectState _state ; private IProjectState _state;
[NotMapped] [NotMapped]
public IProjectState State { public IProjectState State {
...@@ -77,7 +77,7 @@ namespace PSManagement.Domain.Projects.Entities ...@@ -77,7 +77,7 @@ namespace PSManagement.Domain.Projects.Entities
return _state; return _state;
} }
set => _state = value; set => _state = value;
} }
...@@ -144,20 +144,20 @@ namespace PSManagement.Domain.Projects.Entities ...@@ -144,20 +144,20 @@ namespace PSManagement.Domain.Projects.Entities
public bool HasAttachment(int attachmentId) public bool HasAttachment(int attachmentId)
{ {
return Attachments.Where(e => e.Id == attachmentId).FirstOrDefault() is null; return Attachments.Where(e => e.Id == attachmentId).FirstOrDefault() is not null;
} }
public void AddParticipation(int participantId, int projectId, string role, int partialTimeRatio) public void AddParticipation(int participantId, int projectId, string role, int partialTimeRatio)
{ {
this.EmployeeParticipates.Add(new (participantId,projectId,role, partialTimeRatio)); this.EmployeeParticipates.Add(new(participantId, projectId, role, partialTimeRatio));
AddDomainEvent(new ParticipantAddedEvent(participantId, projectId,partialTimeRatio, role)); AddDomainEvent(new ParticipantAddedEvent(participantId, projectId, partialTimeRatio, role));
} }
public void AddAttachment(string attachmentUrl,string attachmentName,string attachmentDescription,int projectId) public void AddAttachment(string attachmentUrl, string attachmentName, string attachmentDescription, int projectId)
{ {
Attachment attachment = new(attachmentUrl, attachmentName,attachmentDescription, projectId); Attachment attachment = new(attachmentUrl, attachmentName, attachmentDescription, projectId);
Attachments.Add(attachment); Attachments.Add(attachment);
...@@ -175,6 +175,46 @@ namespace PSManagement.Domain.Projects.Entities ...@@ -175,6 +175,46 @@ namespace PSManagement.Domain.Projects.Entities
#endregion Encapsulating the collection operations #endregion Encapsulating the collection operations
// this methods encaplsulate the way to calcs the
// total contributions of the employees overall the tracks
//
#region Encapsulate Complteion Rules
public IEnumerable<ParticipantContribution> CalculateContributions() {
// Dictionary to accumulate contributions by employee
var contributionsByEmployee = new Dictionary<int, ParticipantContribution>();
foreach (Track track in Tracks)
{
foreach (EmployeeTrack employeeTrack in track.EmployeeTracks)
{
// to aggreagte the employees based on there ids
var employeeId = employeeTrack.Employee.Id;
var contributionRatio = employeeTrack.EmployeeWork.ContributingRatio;
// If employee already has contributions, sum them up
if (contributionsByEmployee.ContainsKey(employeeId))
{
contributionsByEmployee[employeeId].ContributionRatio += contributionRatio;
}
else
{
// Otherwise, add a new entry for the employee
contributionsByEmployee[employeeId] = new ParticipantContribution(contributionRatio,employeeTrack.Employee);
}
}
}
// Convert the dictionary values to a list for the final result
var contributions = contributionsByEmployee.Values.ToList();
return contributions.AsEnumerable();
}
#endregion Encapsulate Completion Rules
// the transition of the project state // the transition of the project state
// each handler (stated transition) move the project state form one ot other // each handler (stated transition) move the project state form one ot other
...@@ -182,10 +222,10 @@ namespace PSManagement.Domain.Projects.Entities ...@@ -182,10 +222,10 @@ namespace PSManagement.Domain.Projects.Entities
#region State Transitions #region State Transitions
public Result Complete(ProjectCompletion projectCompletion) public Result Complete(ProjectCompletion projectCompletion)
{ {
return State.Complete(this, projectCompletion ); return State.Complete(this, projectCompletion);
} }
public Result Plan() public Result Plan()
{ {
...@@ -199,7 +239,7 @@ namespace PSManagement.Domain.Projects.Entities ...@@ -199,7 +239,7 @@ namespace PSManagement.Domain.Projects.Entities
} }
public Result Cancel(DateTime canellationTime) public Result Cancel(DateTime canellationTime)
{ {
return State.Cancel(this,canellationTime); return State.Cancel(this, canellationTime);
} }
public Result Propose() public Result Propose()
...@@ -235,16 +275,16 @@ namespace PSManagement.Domain.Projects.Entities ...@@ -235,16 +275,16 @@ namespace PSManagement.Domain.Projects.Entities
var participate = EmployeeParticipates.Where(e => e.EmployeeId == participantId).FirstOrDefault(); var participate = EmployeeParticipates.Where(e => e.EmployeeId == participantId).FirstOrDefault();
AddDomainEvent(new ParticipationChangedEvent( AddDomainEvent(new ParticipationChangedEvent(
participantId, participantId,
participate.PartialTimeRatio,partialTimeRation, participate.PartialTimeRatio, partialTimeRation,
role,participate.Role, Id, DateTime.Now)); role, participate.Role, Id, DateTime.Now));
participate.Role = role; participate.Role = role;
participate.PartialTimeRatio = partialTimeRation; participate.PartialTimeRatio = partialTimeRation;
} }
public bool HasParticipant(int participantId) public bool HasParticipant(int participantId)
{ {
return EmployeeParticipates.Where(e => e.EmployeeId ==participantId).FirstOrDefault() is not null; return EmployeeParticipates.Where(e => e.EmployeeId == participantId).FirstOrDefault() is not null;
} }
#endregion Busines rules validators #endregion Busines rules validators
...@@ -318,5 +358,4 @@ namespace PSManagement.Domain.Projects.Entities ...@@ -318,5 +358,4 @@ namespace PSManagement.Domain.Projects.Entities
#endregion state extracting from state name #endregion state extracting from state name
} }
} }
...@@ -14,16 +14,24 @@ namespace PSManagement.Domain.Projects.Entities ...@@ -14,16 +14,24 @@ namespace PSManagement.Domain.Projects.Entities
{ {
public class Step : BaseEntity public class Step : BaseEntity
{ {
// value object represent the subjective information of the step
public StepInfo StepInfo { get; set; } public StepInfo StepInfo { get; set; }
// this field can be calculated from the track // this field can be calculated from the track
// but we use it for performance matter // but we use it for performance matter
public int CurrentCompletionRatio { get; set; } public int CurrentCompletionRatio { get; set; }
//
public int Weight { get; set; } public int Weight { get; set; }
#region Association
public int ProjectId { get; set; } public int ProjectId { get; set; }
public Project Project { get; set; } public Project Project { get; set; }
public ICollection<StepTrack> StepTracks { get; set; } public ICollection<StepTrack> StepTracks { get; set; }
#endregion Association
#region Constructors #region Constructors
public Step() public Step()
{ {
...@@ -38,8 +46,20 @@ namespace PSManagement.Domain.Projects.Entities ...@@ -38,8 +46,20 @@ namespace PSManagement.Domain.Projects.Entities
Weight = weight; Weight = weight;
} }
#endregion Constructors #endregion Constructors
#region Encpasulate Business Rules
public void UpdateWeight(int weight)
{
Weight = weight;
}
public void ChangeCompletionRatio(int completionRatio)
{
CurrentCompletionRatio = completionRatio;
}
public void ChangeInfo(StepInfo stepInfo) public void ChangeInfo(StepInfo stepInfo)
...@@ -47,6 +67,7 @@ namespace PSManagement.Domain.Projects.Entities ...@@ -47,6 +67,7 @@ namespace PSManagement.Domain.Projects.Entities
this.StepInfo = new (stepInfo.StepName,stepInfo.Description,stepInfo.StartDate,stepInfo.Duration,stepInfo.NumberOfWorker); this.StepInfo = new (stepInfo.StepName,stepInfo.Description,stepInfo.StartDate,stepInfo.Duration,stepInfo.NumberOfWorker);
} }
#endregion Encpasulate Business Rules
} }
......
using PSManagement.SharedKernel.Events;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace PSManagement.Domain.ProjectsTypes.DomainEvents
{
public record NewTypeAddedEvent(
string TypeName ,
int Id
):IDomainEvent;
}
...@@ -13,6 +13,12 @@ using System.Threading.Tasks; ...@@ -13,6 +13,12 @@ using System.Threading.Tasks;
namespace PSManagement.Domain.Tracking namespace PSManagement.Domain.Tracking
{ {
/// <summary>
/// Track Class
/// </summary>
/// this class represent the track action
/// on a specific project
///
public class Track : BaseEntity public class Track : BaseEntity
{ {
public TrackInfo TrackInfo { get; set; } public TrackInfo TrackInfo { get; set; }
...@@ -36,6 +42,7 @@ namespace PSManagement.Domain.Tracking ...@@ -36,6 +42,7 @@ namespace PSManagement.Domain.Tracking
#endregion Constructors #endregion Constructors
#region Encapsulation
// this method hide the publishing of the domain events // this method hide the publishing of the domain events
public void Complete(DateTime completionDate) public void Complete(DateTime completionDate)
...@@ -45,5 +52,31 @@ namespace PSManagement.Domain.Tracking ...@@ -45,5 +52,31 @@ namespace PSManagement.Domain.Tracking
AddDomainEvent(new TrackCompletedEvent(ProjectId, Id, completionDate)); AddDomainEvent(new TrackCompletedEvent(ProjectId, Id, completionDate));
} }
public bool IsCompleted()
{
return TrackInfo.IsCompleted;
}
public bool HasEmployee(int employeeId)
{
return EmployeeTracks.Any(e => e.EmployeeId == employeeId);
}
public void AddEmployeeTrack(int employeeId, EmployeeWork employeeWork, EmployeeWorkInfo employeeWorkInfo, string notes)
{
EmployeeTracks.Add(new EmployeeTrack {
EmployeeWork=employeeWork,
EmployeeWorkInfo=employeeWorkInfo,
EmployeeId=employeeId,
TrackId=Id,
Notes=notes
});
}
#endregion Encapsulation
} }
} }
...@@ -79,7 +79,7 @@ namespace PSManagement.Presentation.Controllers.Projects ...@@ -79,7 +79,7 @@ namespace PSManagement.Presentation.Controllers.Projects
} }
[HttpGet("Completion{id}")] [HttpGet("Completion/{id}")]
public async Task<IActionResult> GetProjectCompletion(int id) public async Task<IActionResult> GetProjectCompletion(int id)
{ {
var query = new GetProjectCompletionQuery(id); var query = new GetProjectCompletionQuery(id);
......
...@@ -19,7 +19,7 @@ using PSManagement.Contracts.Tracks.Response; ...@@ -19,7 +19,7 @@ using PSManagement.Contracts.Tracks.Response;
using PSManagement.Presentation.Controllers.ApiBase; using PSManagement.Presentation.Controllers.ApiBase;
using System.Collections.Generic; using System.Collections.Generic;
using System.Threading.Tasks; using System.Threading.Tasks;
using PSManagement.Application.Tracks.UseCaes.Queries.GetTracksByFilter;
namespace PSManagement.Presentation.Controllers.Tracks namespace PSManagement.Presentation.Controllers.Tracks
{ {
[Route("api/[controller]")] [Route("api/[controller]")]
...@@ -54,6 +54,19 @@ namespace PSManagement.Presentation.Controllers.Tracks ...@@ -54,6 +54,19 @@ namespace PSManagement.Presentation.Controllers.Tracks
return HandleResult(result); return HandleResult(result);
} }
[HttpGet("ByFilter")]
public async Task<IActionResult> GeTracksByFilter([FromQuery] GetTracksByFilterRequest request)
{
var query = _mapper.Map<GetTracksByFilterQuery>(request);
var result = _mapper.Map<Result<IEnumerable<TrackResponse>>>(await _sender.Send(query));
return HandleResult(result);
}
[HttpGet("UnCompleted")] [HttpGet("UnCompleted")]
public async Task<IActionResult> GetUnCompleted() public async Task<IActionResult> GetUnCompleted()
{ {
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment