001// -------------------------------------------------------------------------------- 002// Copyright 2002-2024 Echo Three, LLC 003// 004// Licensed under the Apache License, Version 2.0 (the "License"); 005// you may not use this file except in compliance with the License. 006// You may obtain a copy of the License at 007// 008// http://www.apache.org/licenses/LICENSE-2.0 009// 010// Unless required by applicable law or agreed to in writing, software 011// distributed under the License is distributed on an "AS IS" BASIS, 012// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013// See the License for the specific language governing permissions and 014// limitations under the License. 015// -------------------------------------------------------------------------------- 016 017package com.echothree.model.control.workflow.server.logic; 018 019import com.echothree.control.user.workflow.common.spec.WorkflowEntranceUniversalSpec; 020import com.echothree.model.control.core.common.ComponentVendors; 021import com.echothree.model.control.core.common.EntityTypes; 022import com.echothree.model.control.core.common.exception.InvalidParameterCountException; 023import com.echothree.model.control.core.server.logic.EntityInstanceLogic; 024import com.echothree.model.control.party.server.logic.PartyLogic; 025import com.echothree.model.control.security.server.logic.SecurityRoleLogic; 026import com.echothree.model.control.selector.server.logic.SelectorLogic; 027import com.echothree.model.control.workflow.common.exception.MissingRequiredWorkflowNameException; 028import com.echothree.model.control.workflow.common.exception.UnknownDefaultWorkflowEntranceException; 029import com.echothree.model.control.workflow.common.exception.UnknownEntranceWorkflowNameException; 030import com.echothree.model.control.workflow.common.exception.UnknownEntranceWorkflowStepNameException; 031import com.echothree.model.control.workflow.common.exception.UnknownWorkflowEntranceNameException; 032import com.echothree.model.control.workflow.common.exception.UnknownWorkflowEntrancePartyTypeException; 033import com.echothree.model.control.workflow.common.exception.UnknownWorkflowEntranceSecurityRoleException; 034import com.echothree.model.control.workflow.common.exception.UnknownWorkflowEntranceSelectorException; 035import com.echothree.model.control.workflow.common.exception.UnknownWorkflowEntranceStepException; 036import com.echothree.model.control.workflow.common.exception.WorkflowMissingSecurityRoleGroupException; 037import com.echothree.model.control.workflow.common.exception.WorkflowMissingSelectorTypeException; 038import com.echothree.model.control.workflow.server.control.WorkflowControl; 039import com.echothree.model.data.party.server.entity.PartyType; 040import com.echothree.model.data.workflow.server.entity.Workflow; 041import com.echothree.model.data.workflow.server.entity.WorkflowEntrance; 042import com.echothree.model.data.workflow.server.entity.WorkflowEntrancePartyType; 043import com.echothree.model.data.workflow.server.entity.WorkflowEntranceSecurityRole; 044import com.echothree.model.data.workflow.server.entity.WorkflowEntranceSelector; 045import com.echothree.model.data.workflow.server.entity.WorkflowEntranceStep; 046import com.echothree.model.data.workflow.server.entity.WorkflowStep; 047import com.echothree.util.common.exception.BaseException; 048import com.echothree.util.common.message.ExecutionErrors; 049import com.echothree.util.server.control.BaseLogic; 050import com.echothree.util.server.message.ExecutionErrorAccumulator; 051import com.echothree.util.server.persistence.EntityPermission; 052import com.echothree.util.server.persistence.Session; 053import com.echothree.util.server.validation.ParameterUtils; 054 055public class WorkflowEntranceLogic 056 extends BaseLogic { 057 058 private WorkflowEntranceLogic() { 059 super(); 060 } 061 062 private static class WorkflowEntranceLogicHolder { 063 static WorkflowEntranceLogic instance = new WorkflowEntranceLogic(); 064 } 065 066 public static WorkflowEntranceLogic getInstance() { 067 return WorkflowEntranceLogicHolder.instance; 068 } 069 070 public WorkflowEntrance getWorkflowEntranceByName(final Class<? extends BaseException> unknownWorkflowException, final ExecutionErrors unknownWorkflowExecutionError, 071 final Class<? extends BaseException> unknownWorkflowEntranceException, final ExecutionErrors unknownWorkflowEntranceExecutionError, 072 final ExecutionErrorAccumulator eea, final String workflowName, final String workflowEntranceName) { 073 var workflow = WorkflowLogic.getInstance().getWorkflowByName(unknownWorkflowException, unknownWorkflowExecutionError, 074 eea, workflowName, EntityPermission.READ_ONLY); 075 WorkflowEntrance workflowEntrance = null; 076 077 if(eea == null || !eea.hasExecutionErrors()) { 078 workflowEntrance = getWorkflowEntranceByName(unknownWorkflowEntranceException, unknownWorkflowEntranceExecutionError, eea, 079 workflow, workflowEntranceName); 080 } 081 082 return workflowEntrance; 083 } 084 085 public WorkflowEntrance getWorkflowEntranceByName(final Class<? extends BaseException> unknownException, final ExecutionErrors unknownExecutionError, 086 final ExecutionErrorAccumulator eea, final Workflow workflow, final String workflowEntranceName, EntityPermission entityPermission) { 087 var workflowControl = Session.getModelController(WorkflowControl.class); 088 var workflowEntrance = workflowControl.getWorkflowEntranceByName(workflow, workflowEntranceName, entityPermission); 089 090 if(workflowEntrance == null) { 091 handleExecutionError(unknownException, eea, unknownExecutionError.name(), workflow.getLastDetail().getWorkflowName(), 092 workflowEntranceName); 093 } 094 095 return workflowEntrance; 096 } 097 098 public WorkflowEntrance getWorkflowEntranceByName(final Class<? extends BaseException> unknownException, final ExecutionErrors unknownExecutionError, 099 final ExecutionErrorAccumulator eea, final Workflow workflow, final String workflowEntranceName) { 100 return getWorkflowEntranceByName(unknownException, unknownExecutionError, eea, workflow, workflowEntranceName, EntityPermission.READ_ONLY); 101 } 102 103 public WorkflowEntrance getWorkflowEntranceByNameForUpdate(final Class<? extends BaseException> unknownException, final ExecutionErrors unknownExecutionError, 104 final ExecutionErrorAccumulator eea, final Workflow workflow, final String workflowEntranceName) { 105 return getWorkflowEntranceByName(unknownException, unknownExecutionError, eea, workflow, workflowEntranceName, EntityPermission.READ_WRITE); 106 } 107 108 public WorkflowEntrance getWorkflowEntranceByName(final ExecutionErrorAccumulator eea, final Workflow workflow, final String workflowEntranceName, 109 final EntityPermission entityPermission) { 110 return getWorkflowEntranceByName(UnknownWorkflowEntranceNameException.class, ExecutionErrors.UnknownWorkflowEntranceName, 111 eea, workflow, workflowEntranceName, entityPermission); 112 } 113 114 public WorkflowEntrance getWorkflowEntranceByName(final ExecutionErrorAccumulator eea, final Workflow workflow, final String workflowEntranceName) { 115 return getWorkflowEntranceByName(UnknownWorkflowEntranceNameException.class, ExecutionErrors.UnknownWorkflowEntranceName, 116 eea, workflow, workflowEntranceName); 117 } 118 119 public WorkflowEntrance getWorkflowEntranceByNameForUpdate(final ExecutionErrorAccumulator eea, final Workflow workflow, final String workflowEntranceName) { 120 return getWorkflowEntranceByNameForUpdate(UnknownWorkflowEntranceNameException.class, ExecutionErrors.UnknownWorkflowEntranceName, 121 eea, workflow, workflowEntranceName); 122 } 123 124 public WorkflowEntrance getWorkflowEntranceByName(final ExecutionErrorAccumulator eea, final String workflowName, final String workflowEntranceName, 125 final EntityPermission entityPermission) { 126 var workflow = WorkflowLogic.getInstance().getWorkflowByName(eea, workflowName); 127 WorkflowEntrance workflowEntrance = null; 128 129 if(!eea.hasExecutionErrors()) { 130 workflowEntrance = getWorkflowEntranceByName(UnknownWorkflowEntranceNameException.class, ExecutionErrors.UnknownWorkflowEntranceName, 131 eea, workflow, workflowEntranceName, entityPermission); 132 } 133 134 return workflowEntrance; 135 } 136 137 public WorkflowEntrance getWorkflowEntranceByName(final ExecutionErrorAccumulator eea, final String workflowName, final String workflowEntranceName) { 138 return getWorkflowEntranceByName(eea, workflowName, workflowEntranceName, EntityPermission.READ_ONLY); 139 } 140 141 public WorkflowEntrance getWorkflowEntranceByNameForUpdate(final ExecutionErrorAccumulator eea, final String workflowName, final String workflowEntranceName) { 142 return getWorkflowEntranceByName(eea, workflowName, workflowEntranceName, EntityPermission.READ_WRITE); 143 } 144 145 public WorkflowEntrance getWorkflowEntranceByUniversalSpec(final ExecutionErrorAccumulator eea, final WorkflowEntranceUniversalSpec universalSpec, 146 final boolean allowDefault, final EntityPermission entityPermission) { 147 var workflowControl = Session.getModelController(WorkflowControl.class); 148 var workflowName = universalSpec.getWorkflowName(); 149 var workflowEntranceName = universalSpec.getWorkflowEntranceName(); 150 var nameParameterCount= ParameterUtils.getInstance().countNonNullParameters(workflowName, workflowEntranceName); 151 var possibleEntitySpecs= EntityInstanceLogic.getInstance().countPossibleEntitySpecs(universalSpec); 152 WorkflowEntrance workflowEntrance = null; 153 154 if(nameParameterCount < 3 && possibleEntitySpecs == 0) { 155 Workflow workflow = null; 156 157 if(workflowName != null) { 158 workflow = WorkflowLogic.getInstance().getWorkflowByName(eea, workflowName); 159 } else { 160 handleExecutionError(MissingRequiredWorkflowNameException.class, eea, ExecutionErrors.MissingRequiredWorkflowName.name()); 161 } 162 163 if(!eea.hasExecutionErrors()) { 164 if(workflowEntranceName == null) { 165 if(allowDefault) { 166 workflowEntrance = workflowControl.getDefaultWorkflowEntrance(workflow, entityPermission); 167 168 if(workflowEntrance == null) { 169 handleExecutionError(UnknownDefaultWorkflowEntranceException.class, eea, ExecutionErrors.UnknownDefaultWorkflowEntrance.name()); 170 } 171 } else { 172 handleExecutionError(InvalidParameterCountException.class, eea, ExecutionErrors.InvalidParameterCount.name()); 173 } 174 } else { 175 workflowEntrance = getWorkflowEntranceByName(eea, workflow, workflowEntranceName, entityPermission); 176 } 177 } 178 } else if(nameParameterCount == 0 && possibleEntitySpecs == 1) { 179 var entityInstance = EntityInstanceLogic.getInstance().getEntityInstance(eea, universalSpec, 180 ComponentVendors.ECHO_THREE.name(), EntityTypes.WorkflowEntrance.name()); 181 182 if(!eea.hasExecutionErrors()) { 183 workflowEntrance = workflowControl.getWorkflowEntranceByEntityInstance(entityInstance, entityPermission); 184 } 185 } else { 186 handleExecutionError(InvalidParameterCountException.class, eea, ExecutionErrors.InvalidParameterCount.name()); 187 } 188 189 return workflowEntrance; 190 } 191 192 public WorkflowEntrance getWorkflowEntranceByUniversalSpec(final ExecutionErrorAccumulator eea, final WorkflowEntranceUniversalSpec universalSpec, 193 boolean allowDefault) { 194 return getWorkflowEntranceByUniversalSpec(eea, universalSpec, allowDefault, EntityPermission.READ_ONLY); 195 } 196 197 public WorkflowEntrance getWorkflowEntranceByUniversalSpecForUpdate(final ExecutionErrorAccumulator eea, final WorkflowEntranceUniversalSpec universalSpec, 198 boolean allowDefault) { 199 return getWorkflowEntranceByUniversalSpec(eea, universalSpec, allowDefault, EntityPermission.READ_WRITE); 200 } 201 202 public WorkflowEntrancePartyType getWorkflowEntrancePartyType(final ExecutionErrorAccumulator eea, final WorkflowEntrance workflowEntrance, 203 final PartyType partyType, final EntityPermission entityPermission) { 204 WorkflowEntrancePartyType workflowEntrancePartyType = null; 205 206 if(eea == null || !eea.hasExecutionErrors()) { 207 var workflowControl = Session.getModelController(WorkflowControl.class); 208 209 workflowEntrancePartyType = workflowControl.getWorkflowEntrancePartyType(workflowEntrance, partyType, entityPermission); 210 211 if(workflowEntrancePartyType == null) { 212 var workflowEntranceDetail = workflowEntrance.getLastDetail(); 213 214 handleExecutionError(UnknownWorkflowEntrancePartyTypeException.class, eea, ExecutionErrors.UnknownWorkflowEntrancePartyType.name(), 215 workflowEntranceDetail.getWorkflow().getLastDetail().getWorkflowName(), 216 workflowEntranceDetail.getWorkflowEntranceName(), partyType.getPartyTypeName()); 217 } 218 } 219 220 return workflowEntrancePartyType; 221 } 222 223 public WorkflowEntrancePartyType getWorkflowEntrancePartyType(final ExecutionErrorAccumulator eea, final WorkflowEntrance workflowEntrance, 224 final PartyType partyType) { 225 return getWorkflowEntrancePartyType(eea, workflowEntrance, partyType, EntityPermission.READ_ONLY); 226 } 227 228 public WorkflowEntrancePartyType getWorkflowEntrancePartyTypeForUpdate(final ExecutionErrorAccumulator eea, final WorkflowEntrance workflowEntrance, 229 final PartyType partyType) { 230 return getWorkflowEntrancePartyType(eea, workflowEntrance, partyType, EntityPermission.READ_WRITE); 231 } 232 233 public WorkflowEntrancePartyType getWorkflowEntrancePartyTypeByName(final ExecutionErrorAccumulator eea, final String workflowName, 234 final String workflowEntranceName, final String partyTypeName, final EntityPermission entityPermission) { 235 var workflowEntrance = getWorkflowEntranceByName(eea, workflowName, workflowEntranceName); 236 var partyType = PartyLogic.getInstance().getPartyTypeByName(eea, partyTypeName); 237 238 return getWorkflowEntrancePartyType(eea, workflowEntrance, partyType, entityPermission); 239 } 240 241 public WorkflowEntrancePartyType getWorkflowEntrancePartyTypeByName(final ExecutionErrorAccumulator eea, final String workflowName, 242 final String workflowEntranceName, final String partyTypeName) { 243 return getWorkflowEntrancePartyTypeByName(eea, workflowName, workflowEntranceName, partyTypeName, 244 EntityPermission.READ_ONLY); 245 } 246 247 248 public WorkflowEntrancePartyType getWorkflowEntrancePartyTypeByNameForUpdate(final ExecutionErrorAccumulator eea, final String workflowName, 249 final String workflowEntranceName, final String partyTypeName) { 250 return getWorkflowEntrancePartyTypeByName(eea, workflowName, workflowEntranceName, partyTypeName, 251 EntityPermission.READ_WRITE); 252 } 253 254 public WorkflowEntranceSecurityRole getWorkflowEntranceSecurityRoleByName(final ExecutionErrorAccumulator eea, final String workflowName, 255 final String workflowEntranceName, final String partyTypeName, final String securityRoleName, 256 final EntityPermission entityPermission) { 257 var workflowEntrance = getWorkflowEntranceByName(eea, workflowName, workflowEntranceName); 258 var partyType = PartyLogic.getInstance().getPartyTypeByName(eea, partyTypeName); 259 WorkflowEntranceSecurityRole workflowEntranceSecurityRole = null; 260 261 if(eea == null || !eea.hasExecutionErrors()) { 262 var securityRoleGroup = workflowEntrance.getLastDetail().getWorkflow().getLastDetail().getSecurityRoleGroup(); 263 264 if(securityRoleGroup != null) { 265 var securityRole = SecurityRoleLogic.getInstance().getSecurityRoleByName(eea, securityRoleGroup, securityRoleName); 266 267 if(eea == null || !eea.hasExecutionErrors()) { 268 var workflowEntrancePartyType = getWorkflowEntrancePartyType(eea, workflowEntrance, partyType); 269 270 if(eea == null || !eea.hasExecutionErrors()) { 271 var workflowControl = Session.getModelController(WorkflowControl.class); 272 273 workflowEntranceSecurityRole = workflowControl.getWorkflowEntranceSecurityRole(workflowEntrancePartyType, 274 securityRole, entityPermission); 275 276 if(workflowEntranceSecurityRole == null) { 277 var workflowEntranceDetail = workflowEntrance.getLastDetail(); 278 var securityRoleDetail = securityRole.getLastDetail(); 279 280 handleExecutionError(UnknownWorkflowEntranceSecurityRoleException.class, eea, ExecutionErrors.UnknownWorkflowEntranceSecurityRole.name(), 281 workflowEntranceDetail.getWorkflow().getLastDetail().getWorkflowName(), 282 workflowEntranceDetail.getWorkflowEntranceName(), partyType.getPartyTypeName(), 283 securityRoleDetail.getSecurityRole().getLastDetail().getSecurityRoleName()); 284 } 285 } 286 } 287 } else { 288 var workflowEntranceDetail = workflowEntrance.getLastDetail(); 289 290 handleExecutionError(WorkflowMissingSecurityRoleGroupException.class, eea, ExecutionErrors.WorkflowMissingSecurityRoleGroup.name(), 291 workflowEntranceDetail.getWorkflow().getLastDetail().getWorkflowName()); 292 } 293 } 294 295 return workflowEntranceSecurityRole; 296 } 297 298 public WorkflowEntranceSecurityRole getWorkflowEntranceSecurityRoleByName(final ExecutionErrorAccumulator eea, final String workflowName, 299 final String workflowEntranceName, final String partyTypeName, final String securityRoleName) { 300 return getWorkflowEntranceSecurityRoleByName(eea, workflowName, workflowEntranceName, partyTypeName, securityRoleName, 301 EntityPermission.READ_ONLY); 302 } 303 304 305 public WorkflowEntranceSecurityRole getWorkflowEntranceSecurityRoleByNameForUpdate(final ExecutionErrorAccumulator eea, final String workflowName, 306 final String workflowEntranceName, final String partyTypeName, final String securityRoleName) { 307 return getWorkflowEntranceSecurityRoleByName(eea, workflowName, workflowEntranceName, partyTypeName, securityRoleName, 308 EntityPermission.READ_WRITE); 309 } 310 311 public WorkflowEntranceSelector getWorkflowEntranceSelectorByName(final ExecutionErrorAccumulator eea, final String workflowName, 312 final String workflowEntranceName, final String selectorName, final EntityPermission entityPermission) { 313 var workflowEntrance = getWorkflowEntranceByName(eea, workflowName, workflowEntranceName); 314 WorkflowEntranceSelector workflowEntranceSelector = null; 315 316 if(eea == null || !eea.hasExecutionErrors()) { 317 var selectorType = workflowEntrance.getLastDetail().getWorkflow().getLastDetail().getSelectorType(); 318 319 if(selectorType != null) { 320 var selector = SelectorLogic.getInstance().getSelectorByName(eea, selectorType, selectorName); 321 322 if(eea == null || !eea.hasExecutionErrors()) { 323 var workflowControl = Session.getModelController(WorkflowControl.class); 324 325 workflowEntranceSelector = workflowControl.getWorkflowEntranceSelector(workflowEntrance, 326 selector, entityPermission); 327 328 if(workflowEntranceSelector == null) { 329 var workflowEntranceDetail = workflowEntrance.getLastDetail(); 330 var selectorDetail = selector.getLastDetail(); 331 332 handleExecutionError(UnknownWorkflowEntranceSelectorException.class, eea, ExecutionErrors.UnknownWorkflowEntranceSelector.name(), 333 workflowEntranceDetail.getWorkflow().getLastDetail().getWorkflowName(), 334 workflowEntranceDetail.getWorkflowEntranceName(), 335 selectorDetail.getSelector().getLastDetail().getSelectorName()); 336 } 337 } 338 } else { 339 var workflowEntranceDetail = workflowEntrance.getLastDetail(); 340 341 handleExecutionError(WorkflowMissingSelectorTypeException.class, eea, ExecutionErrors.WorkflowMissingSelectorType.name(), 342 workflowEntranceDetail.getWorkflow().getLastDetail().getWorkflowName()); 343 } 344 } 345 346 return workflowEntranceSelector; 347 } 348 349 public WorkflowEntranceSelector getWorkflowEntranceSelectorByName(final ExecutionErrorAccumulator eea, final String workflowName, 350 final String workflowEntranceName, final String selectorName) { 351 return getWorkflowEntranceSelectorByName(eea, workflowName, workflowEntranceName, selectorName, 352 EntityPermission.READ_ONLY); 353 } 354 355 356 public WorkflowEntranceSelector getWorkflowEntranceSelectorByNameForUpdate(final ExecutionErrorAccumulator eea, final String workflowName, 357 final String workflowEntranceName, final String selectorName) { 358 return getWorkflowEntranceSelectorByName(eea, workflowName, workflowEntranceName, selectorName, 359 EntityPermission.READ_WRITE); 360 } 361 362 public WorkflowStep getEntranceWorkflowStep(final ExecutionErrorAccumulator eea, final String entranceWorkflowName, 363 final String entranceWorkflowStepName) { 364 return WorkflowStepLogic.getInstance().getWorkflowStepByName( 365 UnknownEntranceWorkflowNameException.class, ExecutionErrors.UnknownEntranceWorkflowName, 366 UnknownEntranceWorkflowStepNameException.class, ExecutionErrors.UnknownEntranceWorkflowStepName, 367 eea, entranceWorkflowName, entranceWorkflowStepName); 368 } 369 370 public WorkflowEntranceStep getWorkflowEntranceStep(final ExecutionErrorAccumulator eea, 371 WorkflowEntrance workflowEntrance, WorkflowStep entranceWorkflowStep) { 372 var workflowControl = Session.getModelController(WorkflowControl.class); 373 var workflowEntranceStep = workflowControl.getWorkflowEntranceStep(workflowEntrance, entranceWorkflowStep); 374 375 if(workflowEntranceStep == null) { 376 var workflowEntranceDetail = workflowEntrance.getLastDetail(); 377 var entranceWorkflowStepDetail = entranceWorkflowStep.getLastDetail(); 378 379 handleExecutionError(UnknownWorkflowEntranceStepException.class, eea, ExecutionErrors.UnknownWorkflowEntranceStep.name(), 380 workflowEntranceDetail.getWorkflow().getLastDetail().getWorkflowName(), 381 workflowEntranceDetail.getWorkflowEntranceName(), 382 entranceWorkflowStepDetail.getWorkflow().getLastDetail().getWorkflowName(), 383 entranceWorkflowStepDetail.getWorkflowStepName()); 384 } 385 386 return workflowEntranceStep; 387 } 388 389 public WorkflowEntranceStep getWorkflowEntranceStepByName(final ExecutionErrorAccumulator eea, 390 final String workflowName, final String workflowEntranceName, final String entranceWorkflowName, 391 final String entranceWorkflowStepName) { 392 var workflowEntrance = getWorkflowEntranceByName(eea, workflowName, workflowEntranceName); 393 var entranceWorkflowStep = getEntranceWorkflowStep(eea, entranceWorkflowName, entranceWorkflowStepName); 394 WorkflowEntranceStep workflowEntranceStep = null; 395 396 if(eea == null || !eea.hasExecutionErrors()) { 397 workflowEntranceStep = getWorkflowEntranceStep(eea, workflowEntrance, entranceWorkflowStep); 398 } 399 400 return workflowEntranceStep; 401 } 402 403}