Browse Source

add "create sub project"

tags/Baseline_30082024_BACKEND_UAT
cyril.tsui 1 year ago
parent
commit
ad929b0323
5 changed files with 150 additions and 68 deletions
  1. +2
    -2
      src/main/java/com/ffii/tsms/modules/project/entity/ProjectRepository.kt
  2. +109
    -65
      src/main/java/com/ffii/tsms/modules/project/service/ProjectsService.kt
  3. +8
    -1
      src/main/java/com/ffii/tsms/modules/project/web/ProjectsController.kt
  4. +30
    -0
      src/main/java/com/ffii/tsms/modules/project/web/models/MainProjectDetails.kt
  5. +1
    -0
      src/main/java/com/ffii/tsms/modules/project/web/models/NewProjectRequest.kt

+ 2
- 2
src/main/java/com/ffii/tsms/modules/project/entity/ProjectRepository.kt View File

@@ -21,12 +21,12 @@ interface ProjectRepository : AbstractRepository<Project, Long> {


fun findAllByPlanStartLessThanEqualAndPlanEndGreaterThanEqual(remainedDateFrom: LocalDate?, remainedDateTo: LocalDate?):List<Project> fun findAllByPlanStartLessThanEqualAndPlanEndGreaterThanEqual(remainedDateFrom: LocalDate?, remainedDateTo: LocalDate?):List<Project>


//fun findAllByDateRange(start: LocalDate, end: LocalDate): List<Project>

@Query("SELECT max(cast(substring_index(substring_index(p.code, '-', 2), '-', -1) as long)) FROM Project p WHERE p.isClpProject = ?1 and p.id != ?2" + @Query("SELECT max(cast(substring_index(substring_index(p.code, '-', 2), '-', -1) as long)) FROM Project p WHERE p.isClpProject = ?1 and p.id != ?2" +
"") "")
fun getLatestCodeNumberByMainProject(isClpProject: Boolean, id: Serializable?): Long? fun getLatestCodeNumberByMainProject(isClpProject: Boolean, id: Serializable?): Long?


@Query("SELECT max(cast(substring_index(p.code, '-', -1) as long)) FROM Project p WHERE p.code like ?1 and p.id != ?2") @Query("SELECT max(cast(substring_index(p.code, '-', -1) as long)) FROM Project p WHERE p.code like ?1 and p.id != ?2")
fun getLatestCodeNumberBySubProject(code: String, id: Serializable?): Long? fun getLatestCodeNumberBySubProject(code: String, id: Serializable?): Long?

fun findAllByStatusIsNotAndMainProjectIsNull(status: String): List<Project>
} }

+ 109
- 65
src/main/java/com/ffii/tsms/modules/project/service/ProjectsService.kt View File

@@ -6,6 +6,7 @@ import com.ffii.tsms.modules.data.service.CustomerContactService
import com.ffii.tsms.modules.project.entity.projections.ProjectSearchInfo import com.ffii.tsms.modules.project.entity.projections.ProjectSearchInfo
import com.ffii.tsms.modules.data.service.CustomerService import com.ffii.tsms.modules.data.service.CustomerService
import com.ffii.tsms.modules.data.service.GradeService import com.ffii.tsms.modules.data.service.GradeService
import com.ffii.tsms.modules.data.service.SubsidiaryContactService
import com.ffii.tsms.modules.project.entity.* import com.ffii.tsms.modules.project.entity.*
import com.ffii.tsms.modules.project.entity.Milestone import com.ffii.tsms.modules.project.entity.Milestone
import com.ffii.tsms.modules.project.entity.projections.InvoiceInfoSearchInfo import com.ffii.tsms.modules.project.entity.projections.InvoiceInfoSearchInfo
@@ -44,10 +45,12 @@ open class ProjectsService(
private val taskGroupRepository: TaskGroupRepository, private val taskGroupRepository: TaskGroupRepository,
private val timesheetRepository: TimesheetRepository, private val timesheetRepository: TimesheetRepository,
private val taskTemplateRepository: TaskTemplateRepository, private val taskTemplateRepository: TaskTemplateRepository,
private val subsidiaryRepository: SubsidiaryRepository, private val subsidiaryContactRepository: SubsidiaryContactRepository
private val subsidiaryContactService: SubsidiaryContactService,
private val subsidiaryContactRepository: SubsidiaryContactRepository
) { ) {
open fun allProjects(): List<ProjectSearchInfo> { open fun allProjects(): List<ProjectSearchInfo> {
return projectRepository.findProjectSearchInfoByOrderByCreatedDesc().sortedByDescending { it.status?.lowercase() != "deleted" }
return projectRepository.findProjectSearchInfoByOrderByCreatedDesc()
.sortedByDescending { it.status?.lowercase() != "deleted" }
} }


open fun allInvoices(): List<InvoiceSearchInfo> { open fun allInvoices(): List<InvoiceSearchInfo> {
@@ -63,63 +66,57 @@ open class ProjectsService(
} }


open fun markDeleted(id: Long) { open fun markDeleted(id: Long) {
projectRepository.save(projectRepository.findById(id).orElseThrow()
.apply {
deleted = true
status = "Deleted"
})
projectRepository.save(projectRepository.findById(id).orElseThrow().apply {
deleted = true
status = "Deleted"
})
} }


open fun allAssignedProjects(): List<AssignedProject> { open fun allAssignedProjects(): List<AssignedProject> {
return SecurityUtils.getUser().getOrNull()?.let { user -> return SecurityUtils.getUser().getOrNull()?.let { user ->
staffRepository.findByUserId(user.id).getOrNull()?.let { staff -> staffRepository.findByUserId(user.id).getOrNull()?.let { staff ->
staffAllocationRepository.findAssignedProjectsByStaff(staff)
.mapNotNull {
it.project?.let { project ->
val timesheetHours = timesheetRepository.totalHoursConsumedByProject(project)

AssignedProject(
id = project.id!!,
code = project.code!!,
name = project.name!!,
tasks = projectTaskRepository.findAllByProject(project).mapNotNull { pt -> pt.task },
milestones = milestoneRepository.findAllByProject(project)
.filter { milestone -> milestone.taskGroup?.id != null }
.associateBy { milestone -> milestone.taskGroup!!.id!! }
.mapValues { (_, milestone) ->
MilestoneInfo(
startDate = milestone.startDate?.format(DateTimeFormatter.ISO_LOCAL_DATE),
endDate = milestone.endDate?.format(DateTimeFormatter.ISO_LOCAL_DATE)
)
},
hoursAllocated = project.totalManhour ?: 0.0,
hoursAllocatedOther = 0.0,
hoursSpent = timesheetHours.normalConsumed,
hoursSpentOther = timesheetHours.otConsumed
)
}
staffAllocationRepository.findAssignedProjectsByStaff(staff).mapNotNull {
it.project?.let { project ->
val timesheetHours = timesheetRepository.totalHoursConsumedByProject(project)

AssignedProject(id = project.id!!,
code = project.code!!,
name = project.name!!,
tasks = projectTaskRepository.findAllByProject(project).mapNotNull { pt -> pt.task },
milestones = milestoneRepository.findAllByProject(project)
.filter { milestone -> milestone.taskGroup?.id != null }
.associateBy { milestone -> milestone.taskGroup!!.id!! }
.mapValues { (_, milestone) ->
MilestoneInfo(
startDate = milestone.startDate?.format(DateTimeFormatter.ISO_LOCAL_DATE),
endDate = milestone.endDate?.format(DateTimeFormatter.ISO_LOCAL_DATE)
)
},
hoursAllocated = project.totalManhour ?: 0.0,
hoursAllocatedOther = 0.0,
hoursSpent = timesheetHours.normalConsumed,
hoursSpentOther = timesheetHours.otConsumed
)
} }
}
} }
} ?: emptyList() } ?: emptyList()
} }


open fun allProjectWithTasks(): List<ProjectWithTasks> { open fun allProjectWithTasks(): List<ProjectWithTasks> {
return projectRepository.findAll().map { project -> return projectRepository.findAll().map { project ->
ProjectWithTasks(
id = project.id!!,
ProjectWithTasks(id = project.id!!,
code = project.code!!, code = project.code!!,
name = project.name!!, name = project.name!!,
tasks = projectTaskRepository.findAllByProject(project).mapNotNull { pt -> pt.task }, tasks = projectTaskRepository.findAllByProject(project).mapNotNull { pt -> pt.task },
milestones = milestoneRepository.findAllByProject(project) milestones = milestoneRepository.findAllByProject(project)
.filter { milestone -> milestone.taskGroup?.id != null } .filter { milestone -> milestone.taskGroup?.id != null }
.associateBy { milestone -> milestone.taskGroup!!.id!! }
.mapValues { (_, milestone) ->
.associateBy { milestone -> milestone.taskGroup!!.id!! }.mapValues { (_, milestone) ->
MilestoneInfo( MilestoneInfo(
startDate = milestone.startDate?.format(DateTimeFormatter.ISO_LOCAL_DATE), startDate = milestone.startDate?.format(DateTimeFormatter.ISO_LOCAL_DATE),
endDate = milestone.endDate?.format(DateTimeFormatter.ISO_LOCAL_DATE) endDate = milestone.endDate?.format(DateTimeFormatter.ISO_LOCAL_DATE)
) )
}
)
})
} }
} }


@@ -135,15 +132,28 @@ open class ProjectsService(


if (latestProjectCode != null) { if (latestProjectCode != null) {
val lastFix = latestProjectCode val lastFix = latestProjectCode
return "$prefix-" + String.format("%04d", lastFix + 1L)
return "$prefix-" + String.format("%04d", lastFix + 1L)
} else { } else {
return "$prefix-0001" return "$prefix-0001"
} }
} }

open fun createSubProjectCode(mainProject: Project, project: Project): String {
val prefix = mainProject.code

val latestProjectCode = projectRepository.getLatestCodeNumberBySubProject(prefix!!, project.id ?: -1)

if (latestProjectCode != null) {
val lastFix = latestProjectCode
return "$prefix-" + String.format("%03d", lastFix + 1L)
} else {
return "$prefix-001"
}
}

@Transactional @Transactional
open fun saveProject(request: NewProjectRequest): NewProjectResponse { open fun saveProject(request: NewProjectRequest): NewProjectResponse {
val projectCategory =
projectCategoryRepository.findById(request.projectCategoryId).orElseThrow()
val projectCategory = projectCategoryRepository.findById(request.projectCategoryId).orElseThrow()
val fundingType = fundingTypeRepository.findById(request.fundingTypeId).orElseThrow() val fundingType = fundingTypeRepository.findById(request.fundingTypeId).orElseThrow()
val serviceType = serviceTypeRepository.findById(request.serviceTypeId).orElseThrow() val serviceType = serviceTypeRepository.findById(request.serviceTypeId).orElseThrow()
val contractType = contractTypeRepository.findById(request.contractTypeId).orElseThrow() val contractType = contractTypeRepository.findById(request.contractTypeId).orElseThrow()
@@ -158,6 +168,7 @@ open class ProjectsService(
val subsidiaryContact = subsidiaryContactRepository.findById(request.clientContactId).orElse(null) val subsidiaryContact = subsidiaryContactRepository.findById(request.clientContactId).orElse(null)
val clientContact = customerContactService.findByContactId(request.clientContactId) val clientContact = customerContactService.findByContactId(request.clientContactId)
val customerSubsidiary = request.clientSubsidiaryId?.let { subsidiaryService.findSubsidiary(it) } val customerSubsidiary = request.clientSubsidiaryId?.let { subsidiaryService.findSubsidiary(it) }
val mainProject = if (request.mainProjectId != null && request.mainProjectId > 0) projectRepository.findById(request.mainProjectId).orElse(null) else null


val allTasksMap = tasksService.allTasks().associateBy { it.id } val allTasksMap = tasksService.allTasks().associateBy { it.id }
val taskGroupMap = tasksService.allTaskGroups().associateBy { it.id } val taskGroupMap = tasksService.allTaskGroups().associateBy { it.id }
@@ -169,7 +180,7 @@ open class ProjectsService(
project.apply { project.apply {
name = request.projectName name = request.projectName
description = request.projectDescription description = request.projectDescription
code = if (this.code.isNullOrEmpty()) createProjectCode(request.isClpProject, project) else this.code
code = if (this.code.isNullOrEmpty() && request.mainProjectId == null) createProjectCode(request.isClpProject, project) else if (this.code.isNullOrEmpty() && request.mainProjectId != null && mainProject != null) createSubProjectCode(mainProject, project) else this.code
expectedTotalFee = request.expectedProjectFee expectedTotalFee = request.expectedProjectFee
totalManhour = request.totalManhour totalManhour = request.totalManhour
actualStart = request.projectActualStart actualStart = request.projectActualStart
@@ -179,6 +190,7 @@ open class ProjectsService(
else if (this.actualStart != null) "On-going" else if (this.actualStart != null) "On-going"
else "Pending To Start" else "Pending To Start"
isClpProject = request.isClpProject isClpProject = request.isClpProject
this.mainProject = mainProject


this.projectCategory = projectCategory this.projectCategory = projectCategory
this.fundingType = fundingType this.fundingType = fundingType
@@ -191,9 +203,12 @@ open class ProjectsService(


this.teamLead = teamLead this.teamLead = teamLead
this.customer = customer this.customer = customer
custLeadName = if (request.isSubsidiaryContact == null || !request.isSubsidiaryContact) clientContact.name else subsidiaryContact.name
custLeadEmail = if (request.isSubsidiaryContact == null || !request.isSubsidiaryContact) clientContact.email else subsidiaryContact.email
custLeadPhone = if (request.isSubsidiaryContact == null || !request.isSubsidiaryContact) clientContact.phone else subsidiaryContact.phone
custLeadName =
if (request.isSubsidiaryContact == null || !request.isSubsidiaryContact) clientContact.name else subsidiaryContact.name
custLeadEmail =
if (request.isSubsidiaryContact == null || !request.isSubsidiaryContact) clientContact.email else subsidiaryContact.email
custLeadPhone =
if (request.isSubsidiaryContact == null || !request.isSubsidiaryContact) clientContact.phone else subsidiaryContact.phone
this.customerSubsidiary = customerSubsidiary this.customerSubsidiary = customerSubsidiary
} }


@@ -203,8 +218,7 @@ open class ProjectsService(
val milestones = request.taskGroups.entries.map { (taskStageId, taskGroupAllocation) -> val milestones = request.taskGroups.entries.map { (taskStageId, taskGroupAllocation) ->
val taskGroup = taskGroupRepository.findById(taskStageId).orElse(TaskGroup()) ?: TaskGroup() val taskGroup = taskGroupRepository.findById(taskStageId).orElse(TaskGroup()) ?: TaskGroup()
val milestone = if (project.id != null && project.id!! > 0L) milestoneRepository.findByProjectAndTaskGroup( val milestone = if (project.id != null && project.id!! > 0L) milestoneRepository.findByProjectAndTaskGroup(
project,
taskGroup
project, taskGroup
) ?: Milestone() else Milestone() ) ?: Milestone() else Milestone()
milestone.apply { milestone.apply {
val newMilestone = this val newMilestone = this
@@ -233,8 +247,7 @@ open class ProjectsService(
taskGroupAllocation.taskIds.map { taskId -> taskGroupAllocation.taskIds.map { taskId ->
val projectTask = val projectTask =
if (project.id != null && project.id!! > 0L) projectTaskRepository.findByProjectAndTask( if (project.id != null && project.id!! > 0L) projectTaskRepository.findByProjectAndTask(
project,
allTasksMap[taskId]!!
project, allTasksMap[taskId]!!
) ?: ProjectTask() else ProjectTask() ) ?: ProjectTask() else ProjectTask()


projectTask.apply { projectTask.apply {
@@ -252,8 +265,7 @@ open class ProjectsService(
val gradeAllocations = request.manhourPercentageByGrade.entries.map { val gradeAllocations = request.manhourPercentageByGrade.entries.map {
val gradeAllocation = val gradeAllocation =
if (project.id != null && project.id!! > 0L) gradeAllocationRepository.findByProjectAndGrade( if (project.id != null && project.id!! > 0L) gradeAllocationRepository.findByProjectAndGrade(
project,
gradeMap[it.key]!!
project, gradeMap[it.key]!!
) ?: GradeAllocation() else GradeAllocation() ) ?: GradeAllocation() else GradeAllocation()


gradeAllocation.apply { gradeAllocation.apply {
@@ -313,16 +325,16 @@ open class ProjectsService(
val project = projectRepository.findById(projectId) val project = projectRepository.findById(projectId)


return project.getOrNull()?.let { return project.getOrNull()?.let {
val customerContact =
it.customer?.id?.let { customerId -> customerContactService.findAllByCustomerId(customerId) }
?: emptyList()
val subsidiaryContact = it.customerSubsidiary?.id?.let { subsidiaryId ->
subsidiaryContactService.findAllBySubsidiaryId(subsidiaryId)
} ?: emptyList()
val customerContact = it.customer?.id?.let { customerId -> customerContactService.findAllByCustomerId(customerId) }
?: emptyList()


val milestoneMap = it.milestones
.filter { milestone -> milestone.taskGroup?.id != null }
val milestoneMap = it.milestones.filter { milestone -> milestone.taskGroup?.id != null }
.associateBy { milestone -> milestone.taskGroup!!.id!! } .associateBy { milestone -> milestone.taskGroup!!.id!! }


EditProjectDetails(
projectId = it.id,
EditProjectDetails(projectId = it.id,
projectDeleted = it.deleted, projectDeleted = it.deleted,
projectCode = it.code, projectCode = it.code,
projectName = it.name, projectName = it.name,
@@ -341,7 +353,7 @@ open class ProjectsService(
buildingTypeIds = it.buildingTypes.mapNotNull { buildingType -> buildingType.id }, buildingTypeIds = it.buildingTypes.mapNotNull { buildingType -> buildingType.id },
workNatureIds = it.workNatures.mapNotNull { workNature -> workNature.id }, workNatureIds = it.workNatures.mapNotNull { workNature -> workNature.id },
clientId = it.customer?.id, clientId = it.customer?.id,
clientContactId = customerContact.find { contact -> contact.name == it.custLeadName }?.id,
clientContactId = subsidiaryContact.find { contact -> contact.name == it.custLeadName }?.id ?: customerContact.find { contact -> contact.name == it.custLeadName }?.id,
clientSubsidiaryId = it.customerSubsidiary?.id, clientSubsidiaryId = it.customerSubsidiary?.id,
totalManhour = it.totalManhour, totalManhour = it.totalManhour,
manhourPercentageByGrade = gradeAllocationRepository.findByProject(it) manhourPercentageByGrade = gradeAllocationRepository.findByProject(it)
@@ -349,8 +361,7 @@ open class ProjectsService(
.associate { allocation -> Pair(allocation.grade!!.id!!, allocation.manhour ?: 0.0) }, .associate { allocation -> Pair(allocation.grade!!.id!!, allocation.manhour ?: 0.0) },
taskGroups = projectTaskRepository.findAllByProject(it) taskGroups = projectTaskRepository.findAllByProject(it)
.mapNotNull { projectTask -> if (projectTask.task?.taskGroup?.id != null) projectTask.task else null } .mapNotNull { projectTask -> if (projectTask.task?.taskGroup?.id != null) projectTask.task else null }
.groupBy { task -> task.taskGroup!!.id!! }
.mapValues { (taskGroupId, tasks) ->
.groupBy { task -> task.taskGroup!!.id!! }.mapValues { (taskGroupId, tasks) ->
TaskGroupAllocation( TaskGroupAllocation(
taskIds = tasks.mapNotNull { task -> task.id }, taskIds = tasks.mapNotNull { task -> task.id },
percentAllocation = milestoneMap[taskGroupId]?.stagePercentAllocation ?: 0.0 percentAllocation = milestoneMap[taskGroupId]?.stagePercentAllocation ?: 0.0
@@ -359,8 +370,9 @@ open class ProjectsService(
allocatedStaffIds = staffAllocationRepository.findByProject(it) allocatedStaffIds = staffAllocationRepository.findByProject(it)
.mapNotNull { allocation -> allocation.staff?.id }, .mapNotNull { allocation -> allocation.staff?.id },
milestones = milestoneMap.mapValues { (_, milestone) -> milestones = milestoneMap.mapValues { (_, milestone) ->
com.ffii.tsms.modules.project.web.models.Milestone(
startDate = milestone.startDate?.format(DateTimeFormatter.ISO_LOCAL_DATE),
com.ffii.tsms.modules.project.web.models.Milestone(startDate = milestone.startDate?.format(
DateTimeFormatter.ISO_LOCAL_DATE
),
endDate = milestone.endDate?.format(DateTimeFormatter.ISO_LOCAL_DATE), endDate = milestone.endDate?.format(DateTimeFormatter.ISO_LOCAL_DATE),
payments = milestone.milestonePayments.map { payment -> payments = milestone.milestonePayments.map { payment ->
PaymentInputs( PaymentInputs(
@@ -369,8 +381,7 @@ open class ProjectsService(
description = payment.description!!, description = payment.description!!,
date = payment.date!!.format(DateTimeFormatter.ISO_LOCAL_DATE) date = payment.date!!.format(DateTimeFormatter.ISO_LOCAL_DATE)
) )
}
)
})
}, },
expectedProjectFee = it.expectedTotalFee expectedProjectFee = it.expectedTotalFee
) )
@@ -400,4 +411,37 @@ open class ProjectsService(
open fun allWorkNatures(): List<WorkNature> { open fun allWorkNatures(): List<WorkNature> {
return workNatureRepository.findAll() return workNatureRepository.findAll()
} }

open fun allMainProjects(): List<MainProjectDetails> {
val mainProjects: List<Project> = projectRepository.findAllByStatusIsNotAndMainProjectIsNull("Deleted")

return mainProjects.map { project: Project ->
val subsidiaryContact = project.customerSubsidiary?.id?.let { subsidiaryId ->
subsidiaryContactService.findAllBySubsidiaryId(subsidiaryId)
} ?: emptyList()
val customerContact = project.customer?.id?.let { customerId -> customerContactService.findAllByCustomerId(customerId) }
?: emptyList()

MainProjectDetails(
projectId = project.id,
projectCode = project.code,
projectName = project.name,
projectCategoryId = project.projectCategory?.id,
projectDescription = project.description,
projectLeadId = project.teamLead?.id,
projectStatus = project.status,
isClpProject = project.isClpProject,
serviceTypeId = project.serviceType?.id,
fundingTypeId = project.fundingType?.id,
contractTypeId = project.contractType?.id,
locationId = project.location?.id,
buildingTypeIds = project.buildingTypes.mapNotNull { buildingType -> buildingType.id },
workNatureIds = project.workNatures.mapNotNull { workNature -> workNature.id },
clientId = project.customer?.id,
clientContactId = subsidiaryContact.find { contact -> contact.name == project.custLeadName }?.id ?: customerContact.find { contact -> contact.name == project.custLeadName }?.id,
clientSubsidiaryId = project.customerSubsidiary?.id,
expectedProjectFee = project.expectedTotalFee
)
}
}
} }

+ 8
- 1
src/main/java/com/ffii/tsms/modules/project/web/ProjectsController.kt View File

@@ -2,8 +2,10 @@ package com.ffii.tsms.modules.project.web


import com.ffii.core.exception.NotFoundException import com.ffii.core.exception.NotFoundException
import com.ffii.tsms.modules.data.entity.* import com.ffii.tsms.modules.data.entity.*
import com.ffii.tsms.modules.project.entity.Project
import com.ffii.tsms.modules.project.entity.projections.ProjectSearchInfo import com.ffii.tsms.modules.project.entity.projections.ProjectSearchInfo
import com.ffii.tsms.modules.project.entity.ProjectCategory import com.ffii.tsms.modules.project.entity.ProjectCategory
import com.ffii.tsms.modules.project.entity.ProjectRepository
import com.ffii.tsms.modules.project.service.ProjectsService import com.ffii.tsms.modules.project.service.ProjectsService
import com.ffii.tsms.modules.project.web.models.* import com.ffii.tsms.modules.project.web.models.*
import jakarta.validation.Valid import jakarta.validation.Valid
@@ -12,12 +14,17 @@ import org.springframework.web.bind.annotation.*


@RestController @RestController
@RequestMapping("/projects") @RequestMapping("/projects")
class ProjectsController(private val projectsService: ProjectsService) {
class ProjectsController(private val projectsService: ProjectsService, private val projectRepository: ProjectRepository) {
@GetMapping @GetMapping
fun allProjects(): List<ProjectSearchInfo> { fun allProjects(): List<ProjectSearchInfo> {
return projectsService.allProjects() return projectsService.allProjects()
} }


@GetMapping("/main")
fun allMainProjects(): List<MainProjectDetails> {
return projectsService.allMainProjects()
}

@DeleteMapping("/{id}") @DeleteMapping("/{id}")
@ResponseStatus(HttpStatus.NO_CONTENT) @ResponseStatus(HttpStatus.NO_CONTENT)
fun deleteProject(@PathVariable id: Long) { fun deleteProject(@PathVariable id: Long) {


+ 30
- 0
src/main/java/com/ffii/tsms/modules/project/web/models/MainProjectDetails.kt View File

@@ -0,0 +1,30 @@
package com.ffii.tsms.modules.project.web.models

data class MainProjectDetails (

// Project details
val projectId: Long?,
val projectCode: String?,
val projectName: String?,

val projectCategoryId: Long?,
val projectDescription: String?,

val projectLeadId: Long?,
val projectStatus: String?,
val isClpProject: Boolean?,

val serviceTypeId: Long?,
val fundingTypeId: Long?,
val contractTypeId: Long?,
val locationId: Long?,
val buildingTypeIds: List<Long>,
val workNatureIds: List<Long>,

// Client details
val clientId: Long?,
val clientContactId: Long?,
val clientSubsidiaryId: Long?,

val expectedProjectFee: Double?,
)

+ 1
- 0
src/main/java/com/ffii/tsms/modules/project/web/models/NewProjectRequest.kt View File

@@ -17,6 +17,7 @@ data class NewProjectRequest(
val projectActualStart: LocalDate?, val projectActualStart: LocalDate?,
val projectActualEnd: LocalDate?, val projectActualEnd: LocalDate?,
val isClpProject: Boolean?, val isClpProject: Boolean?,
val mainProjectId: Long?,


val serviceTypeId: Long, val serviceTypeId: Long,
val fundingTypeId: Long, val fundingTypeId: Long,


Loading…
Cancel
Save