RequirementController.php 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306
  1. <?php
  2. namespace App\Http\Controllers\API;
  3. use App\Exports\DownloadHelper;
  4. use App\Exports\RequirementExport;
  5. use App\Http\Controllers\Controller;
  6. use App\Http\Requests\API\Requirement\ClosedRequest;
  7. use App\Http\Requests\API\Requirement\CreateOrUpdateRequest;
  8. use App\Http\Requests\API\Requirement\LinkPlanRequest;
  9. use App\Http\Requests\API\Requirement\BatchCreateRequest;
  10. use App\Http\Resources\API\AssetRequirementResource;
  11. use App\Http\Resources\API\RequirementResource;
  12. use App\Http\Resources\API\RequirementSimpleResource;
  13. use App\Imports\RequirementImport;
  14. use App\Models\Approval;
  15. use App\Models\Asset;
  16. use App\Models\Enums\ActionObjectType;
  17. use App\Models\Enums\FileObjectType;
  18. use App\Models\Enums\RequirementStatus;
  19. use App\Models\Enums\ObjectAction;
  20. use App\Models\Plan;
  21. use App\Models\ProjectRequirement;
  22. use App\Models\Requirement;
  23. use App\Repositories\ActionRepository;
  24. use App\Services\File\FileAssociationService;
  25. use App\Services\History\ModelChangeDetector;
  26. use Illuminate\Http\Request;
  27. use Illuminate\Support\Facades\Auth;
  28. use Illuminate\Support\Facades\DB;
  29. use Maatwebsite\Excel\Facades\Excel;
  30. class RequirementController extends Controller
  31. {
  32. use DownloadHelper;
  33. /**
  34. * Display a listing of the resource.
  35. */
  36. public function index(Request $request)
  37. {
  38. $pageSize=$request->get('page_size') ?? 10;
  39. $requirements = Requirement::filter($request->all())
  40. ->allowed()
  41. ->where('company_id',Auth::user()->company_id)
  42. ->orderBy('created_at', $request->input('sort','desc'))
  43. ->with(['createdBy', 'plan','group','asset.parent','projects'])
  44. ->paginate($pageSize);
  45. return AssetRequirementResource::collection($requirements);
  46. }
  47. //公共Requirement查询
  48. public function publicSearch(Request $request)
  49. {
  50. $pageSize=$request->get('page_size') ?? 10;
  51. $requirements = Requirement::filter($request->all())
  52. ->allowed()
  53. ->where('company_id',Auth::user()->company_id)
  54. ->orderByDesc('created_at')
  55. ->paginate($pageSize);
  56. return RequirementSimpleResource::collection($requirements);
  57. }
  58. // public function byAsset(Request $request,string $assetId)
  59. // {
  60. // $requirements=Requirement::filter($request->all())->with(['createdBy', 'plan','group']) ->where('asset_id', $assetId)->simplePaginate();
  61. //
  62. // return AssetRequirementResource::collection($requirements);
  63. // }
  64. public function export(Request $request)
  65. {
  66. return $this->downloadExcelHelper(
  67. new RequirementExport(),
  68. "requirement",
  69. $request->get("extension"),
  70. );
  71. }
  72. /**
  73. * Store a newly created resource in storage.
  74. */
  75. public function store(FileAssociationService $service, CreateOrUpdateRequest $request)
  76. {
  77. $requirement = new Requirement();
  78. $requirement->mergeFillable([
  79. 'company_id', 'created_by',
  80. ]);
  81. $service->check(
  82. $request->get("file_ids", []),
  83. FileObjectType::REQUIREMENT,
  84. $request->get("file_uuid"),
  85. );
  86. $requirement->fill([
  87. ...$request->all(),
  88. 'company_id' => Auth::user()->company_id,
  89. 'description' => $request->description? (new \App\Services\File\ImageUrlService)->interceptImageUrl($request->description) : null,
  90. 'created_by' => Auth::id(),
  91. ]);
  92. $requirement->save();
  93. //如果选择了需求关联的项目,则同时进行关联
  94. $projectsId = $request->get('project_id', []);
  95. if(!empty($projectsId) && $projectsId !== []){
  96. foreach ($projectsId as $projectId){
  97. ProjectRequirement::query()->firstOrCreate([
  98. 'project_id' => $projectId,
  99. 'requirement_id' => $requirement->id,
  100. 'asset_id' => $request->asset_id,
  101. 'requirement_group_id'=> $request->requirement_group_id,
  102. ]);
  103. }
  104. }
  105. ActionRepository::createRequirement(
  106. $requirement, ObjectAction::CREATED
  107. );
  108. $service->association($requirement->id);
  109. return $this->created();
  110. }
  111. /**
  112. * Display the specified resource.
  113. */
  114. public function show(string $id)
  115. {
  116. $requirement = Requirement::query()->allowed()->with('projects')->findOrFail($id);
  117. return new RequirementResource($requirement);
  118. }
  119. /**
  120. * Update the specified resource in storage.
  121. */
  122. public function update(CreateOrUpdateRequest $request, string $id)
  123. {
  124. $requirement = Requirement::allowed()->findOrFail($id);
  125. $requirement->fill([
  126. ...$request->all(),
  127. 'description' => $request->description? (new \App\Services\File\ImageUrlService)->interceptImageUrl($request->description) : null,
  128. ]);
  129. $changes = ModelChangeDetector::detector(ActionObjectType::REQUIREMENT, $requirement);
  130. DB::transaction(function () use ($requirement,$request) {
  131. ProjectRequirement::where('requirement_id', $requirement->id)->delete();
  132. $requirement->save();
  133. //如果选择了需求关联的项目,则同时进行关联
  134. $projectsId=$request->project_id;
  135. if (!empty($request->project_id)){
  136. foreach ($projectsId as $projectId){
  137. ProjectRequirement::query()->firstOrCreate([
  138. 'project_id' => $projectId,
  139. 'requirement_id' => $requirement->id,
  140. 'asset_id' => $request->asset_id,
  141. 'requirement_group_id'=> $request->requirement_group_id,
  142. ]);
  143. }
  144. }
  145. });
  146. ActionRepository::createRequirement(
  147. $requirement, ObjectAction::EDITED,objectChanges: $changes
  148. );
  149. return $this->noContent();
  150. }
  151. /**
  152. * Remove the specified resource from storage.
  153. */
  154. public function destroy(string $id)
  155. {
  156. $requirement = Requirement::query()->allowed()->with(['projects','tasks'])->findOrFail($id);
  157. $requirement->delete();
  158. Approval::query()->where('object_type','requirement')->where('object_id',$id)->delete();
  159. ActionRepository::createRequirement(
  160. $requirement, ObjectAction::DELETED
  161. );
  162. return $this->noContent();
  163. }
  164. public function close(Request $request,string $id){
  165. $requirement = Requirement::allowed()->findOrFail($id);
  166. $requirement->status = RequirementStatus::CLOSED->value;
  167. $changes = ModelChangeDetector::detector(ActionObjectType::REQUIREMENT, $requirement);
  168. $requirement->save();
  169. ActionRepository::createRequirement(
  170. $requirement,
  171. ObjectAction::CLOSED,
  172. $request->comment?(new \App\Services\File\ImageUrlService)->interceptImageUrl($request->comment) : null,
  173. objectChanges: $changes
  174. );
  175. return $this->noContent();
  176. }
  177. public function start(Request $request, string $id)
  178. {
  179. $requirement = Requirement::allowed()->findOrFail($id);
  180. $requirement->status = RequirementStatus::ACTIVE->value;
  181. $changes = ModelChangeDetector::detector(ActionObjectType::REQUIREMENT, $requirement);
  182. $requirement->save();
  183. ActionRepository::createRequirement(
  184. $requirement,
  185. ObjectAction::STARTED,
  186. $request->comment?(new \App\Services\File\ImageUrlService)->interceptImageUrl($request->comment) : null,
  187. objectChanges: $changes
  188. );
  189. return $this->noContent();
  190. }
  191. public function linkPlan(LinkPlanRequest $request, string $planId)
  192. {
  193. $plan = Plan::query()->findOrFail($planId);
  194. Requirement::query()->allowed()->where("asset_id", $plan->asset_id)
  195. ->whereIn('id', $request->get("requirement_ids"))
  196. ->update([
  197. 'plan_id' => $plan->id,
  198. ]);
  199. return $this->noContent();
  200. }
  201. public function unlinkPlan(LinkPlanRequest $request)
  202. {
  203. Requirement::query()->allowed()->whereIn('id', $request->get("requirement_ids"))
  204. ->update([
  205. 'plan_id' => null,
  206. ]);
  207. return $this->noContent();
  208. }
  209. public function batchStore(BatchCreateRequest $request)
  210. {
  211. $requirementsData = $request->all();
  212. $companyId = Auth::user()->company_id;
  213. $created_by = Auth::id();
  214. DB::transaction(function () use ($requirementsData,$companyId,$created_by) {
  215. foreach ($requirementsData as $k => $data) {
  216. $requirement = new Requirement();
  217. $requirement->mergeFillable([
  218. 'company_id', 'created_by',
  219. ]);
  220. if($k != 0){
  221. $requirementsData[$k]["requirement_group_id"] = $requirementsData[$k]["requirement_group_id"] == 'ditto'?$requirementsData[$k-1]["requirement_group_id"]:$requirementsData[$k]["requirement_group_id"];
  222. $requirementsData[$k]["priority"] = $requirementsData[$k]["priority"] == 'ditto'? $requirementsData[$k-1]["priority"]: $requirementsData[$k]["priority"];
  223. $requirementsData[$k]["plan_id"] = $requirementsData[$k]["plan_id"] == 'ditto'? $requirementsData[$k-1]["plan_id"]: $requirementsData[$k]["plan_id"];
  224. $requirementsData[$k]["project_id"]=$requirementsData[$k]["project_id"] == 'ditto'? $requirementsData[$k-1]["project_id"]: $requirementsData[$k]["project_id"];
  225. }
  226. $requirement->fill([
  227. ...$requirementsData[$k],
  228. 'company_id' => $companyId,
  229. 'created_by' => $created_by,
  230. 'status' => RequirementStatus::ACTIVE,
  231. 'mailto' => [],
  232. ]);
  233. DB::transaction(function () use ($requirement,$requirementsData,$k) {
  234. $requirement->save();
  235. //如果选择了需求关联的项目,则同时进行关联
  236. $projectsId=$requirementsData[$k]['project_id'];
  237. if (!empty($projectsId)){
  238. foreach ($projectsId as $projectId){
  239. ProjectRequirement::query()->firstOrCreate([
  240. 'project_id' => $projectId,
  241. 'requirement_id' => $requirement->id,
  242. 'asset_id' => $requirementsData[$k]['asset_id'],
  243. 'requirement_group_id'=> $requirementsData[$k]['requirement_group_id'],
  244. ]);
  245. }
  246. }
  247. });
  248. ActionRepository::createRequirement(
  249. $requirement, ObjectAction::CREATED
  250. );
  251. }
  252. });
  253. return $this->created();
  254. }
  255. public function import(Request $request)
  256. {
  257. Excel::import(new RequirementImport(), $request->file("file"));
  258. return $this->created();
  259. }
  260. }