input('orgHash'); if (!$orgHash) { return ResponseHelper::returnIncorrectDetails(); } $org = Organization::where('hashkey', $orgHash)->first(); if (!$org) { return ResponseHelper::returnError('Organization not found', 404); } // Get latest versions (where parent_hashkey IS NULL or it is the latest in its group) // For simplicity, we'll fetch all active docs and group them by parent_hashkey or hashkey $allDocs = CooperativeDocument::where('organization_id', $org->id) ->where('is_active', true) ->orderBy('version_number', 'desc') ->get(); $fileHashes = $allDocs->pluck('file_hashkey')->filter()->unique()->toArray(); $fileLists = FileList::whereIn('hashkey', $fileHashes)->with('fileContent')->get()->keyBy('hashkey'); $grouped = []; foreach ($allDocs as $doc) { $rootKey = $doc->parent_hashkey ?? $doc->hashkey; if (!isset($grouped[$rootKey])) { $grouped[$rootKey] = []; } $grouped[$rootKey][] = $doc; } $data = []; foreach ($grouped as $rootKey => $versions) { $latest = $versions[0]; // ordered desc by version_number $fileList = $fileLists[$latest->file_hashkey] ?? null; if ($fileList) { $history = []; foreach ($versions as $v) { $vFileList = $fileLists[$v->file_hashkey] ?? null; if ($vFileList) { $history[] = [ 'hashkey' => $v->hashkey, 'version' => $v->version_number, 'name' => $vFileList->filename, 'date' => $v->created_at ? $v->created_at->format('Y-m-d H:i') : null, 'note' => $v->revision_note, 'url' => $vFileList->resolvedUrl() ]; } } $data[] = [ 'hashkey' => $latest->hashkey, 'parent_hashkey' => $latest->parent_hashkey, 'name' => $fileList->filename, 'type' => $latest->document_type ?? 'Document', 'date' => $latest->created_at ? $latest->created_at->toDateString() : null, 'size' => $this->formatBytes($fileList->fileContent->size_in_bytes ?? 0), 'url' => $fileList->resolvedUrl(), 'version' => $latest->version_number, 'note' => $latest->revision_note, 'history' => $history ]; } } return response()->json([ 'success' => true, 'data' => $data ]); } public function uploadDocument(Request $request) { if (!UserPermissions::isActionPermitted(Auth::user()->acct_type, UserActions::ManageOrganizations)) { return ResponseHelper::returnUnauthorized(); } $orgHash = $request->input('orgHash'); $docType = $request->input('type', 'OTHERS'); if (!$orgHash || !$request->hasFile('file')) { return ResponseHelper::returnIncorrectDetails(); } $org = Organization::where('hashkey', $orgHash)->first(); if (!$org) { return ResponseHelper::returnError('Organization not found', 404); } $file = $request->file('file'); $filename = $file->getClientFilename(); $fileList = FilesMainController::uploadFileList( $file, $filename, $filename, 'Cooperative Document for ' . $org->name, ['type' => 'coop_document', 'org_id' => $org->id], 'CooperativeDocuments', [], 0, 'cooperative_document', ); if (!$fileList || !isset($fileList->hashkey)) { return ResponseHelper::returnError('File upload failed'); } $doc = new CooperativeDocument([ 'hashkey' => (string) Str::uuid(), 'organization_id' => $org->id, 'file_hashkey' => $fileList->hashkey, 'document_type' => $docType, 'created_by' => Auth::id(), 'is_active' => true, ]); if ($doc->save()) { return response()->json([ 'success' => true, 'message' => 'Document uploaded successfully', 'data' => [ 'hashkey' => $doc->hashkey, 'name' => $filename, 'url' => $fileList->resolvedUrl() ] ]); } return ResponseHelper::returnError('Failed to save document record'); } public function reviseDocument(Request $request) { if (!UserPermissions::isActionPermitted(Auth::user()->acct_type, UserActions::ManageOrganizations)) { return ResponseHelper::returnUnauthorized(); } $parentHash = $request->input('parentHash'); $note = $request->input('note'); if (!$parentHash || !$request->hasFile('file')) { return ResponseHelper::returnIncorrectDetails(); } $parentDoc = CooperativeDocument::where('hashkey', $parentHash)->first(); if (!$parentDoc) { return ResponseHelper::returnError('Original document not found', 404); } // The real parent is either its own parent or it is the parent $rootHash = $parentDoc->parent_hashkey ?? $parentDoc->hashkey; // Find highest version number $lastVersion = CooperativeDocument::where('hashkey', $rootHash) ->orWhere('parent_hashkey', $rootHash) ->max('version_number'); $file = $request->file('file'); $filename = $file->getClientFilename(); $fileList = FilesMainController::uploadFileList( $file, $filename, $filename, 'Revision of ' . $parentDoc->hashkey, ['type' => 'coop_document_revision', 'parent_id' => $parentDoc->id], 'CooperativeDocuments', [], 0, 'cooperative_document_revision', ); if (!$fileList) { return ResponseHelper::returnError('File upload failed'); } $doc = new CooperativeDocument([ 'hashkey' => (string) Str::uuid(), 'parent_hashkey' => $rootHash, 'version_number' => $lastVersion + 1, 'organization_id' => $parentDoc->organization_id, 'file_hashkey' => $fileList->hashkey, 'document_type' => $parentDoc->document_type, 'revision_note' => $note, 'created_by' => Auth::id(), 'is_active' => true, ]); if ($doc->save()) { return response()->json([ 'success' => true, 'message' => 'Revision uploaded successfully', 'data' => $doc ]); } return ResponseHelper::returnError('Failed to save revision record'); } public function deleteDocument(Request $request) { if (!UserPermissions::isActionPermitted(Auth::user()->acct_type, UserActions::ManageOrganizations)) { return ResponseHelper::returnUnauthorized(); } $hashkey = $request->input('hashkey'); if (!$hashkey) { return ResponseHelper::returnIncorrectDetails(); } $doc = CooperativeDocument::where('hashkey', $hashkey)->first(); if (!$doc) { return ResponseHelper::returnError('Document not found', 404); } // If it's a version, we might want to just deactivate that version. // If it's the root, we might want to deactivate all versions. // For now, let's just deactivate the specific one. $doc->is_active = false; if ($doc->save()) { return response()->json(['success' => true, 'message' => 'Document/Revision deleted']); } return ResponseHelper::returnError('Failed to delete document'); } private function formatBytes($bytes, $precision = 1) { $units = ['B', 'KB', 'MB', 'GB', 'TB']; $bytes = max($bytes, 0); $pow = floor(($bytes ? log($bytes) : 0) / log(1024)); $pow = min($pow, count($units) - 1); $bytes /= (1 << (10 * $pow)); return round($bytes, $precision) . ' ' . $units[$pow]; } }