Skip to content

Commit 6daffe6

Browse files
committed
feat(super-magic-module): implement hidden file functionality and update related services and DTOs
1 parent 55158a3 commit 6daffe6

File tree

6 files changed

+160
-16
lines changed

6 files changed

+160
-16
lines changed

backend/super-magic-module/src/Application/SuperAgent/Service/WorkspaceAppService.php

Lines changed: 86 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -585,6 +585,7 @@ public function getTopicAttachmentList(DataIsolation $dataIsolation, GetTopicAtt
585585
$dto->fileExtension = $entity->getFileExtension();
586586
$dto->fileKey = $entity->getFileKey();
587587
$dto->fileSize = $entity->getFileSize();
588+
$dto->isHidden = $entity->getIsHidden();
588589

589590
// Calculate relative file path by removing workDir from fileKey
590591
$fileKey = $entity->getFileKey();
@@ -639,6 +640,7 @@ private function assembleTaskFilesTree(string $sandboxId, string $workDir, array
639640
$root = [
640641
'type' => 'root',
641642
'is_directory' => true,
643+
'is_hidden' => false,
642644
'children' => [],
643645
];
644646

@@ -733,6 +735,7 @@ private function assembleTaskFilesTree(string $sandboxId, string $workDir, array
733735
// 逐级构建目录
734736
$currentPath = '';
735737
$parent = &$root;
738+
$parentIsHidden = false; // 父级是否为隐藏目录
736739

737740
foreach ($pathParts as $dirName) {
738741
if (empty($dirName)) {
@@ -744,12 +747,16 @@ private function assembleTaskFilesTree(string $sandboxId, string $workDir, array
744747

745748
// 如果当前路径的目录不存在,创建它
746749
if (! isset($directoryMap[$currentPath])) {
750+
// 判断当前目录是否为隐藏目录
751+
$isHiddenDir = $this->isHiddenDirectory($dirName) || $parentIsHidden;
752+
747753
// 创建新目录节点
748754
$newDir = [
749755
'name' => $dirName,
750756
'path' => $currentPath,
751757
'type' => 'directory',
752758
'is_directory' => true,
759+
'is_hidden' => $isHiddenDir,
753760
'children' => [],
754761
];
755762

@@ -762,6 +769,13 @@ private function assembleTaskFilesTree(string $sandboxId, string $workDir, array
762769

763770
// 更新父目录引用为当前目录
764771
$parent = &$directoryMap[$currentPath];
772+
// 更新父级隐藏状态,如果当前目录是隐藏的,那么其子级都应该是隐藏的
773+
$parentIsHidden = $parent['is_hidden'] ?? false;
774+
}
775+
776+
// 如果父目录是隐藏的,那么文件也应该被标记为隐藏
777+
if ($parentIsHidden) {
778+
$fileNode['is_hidden'] = true;
765779
}
766780

767781
// 将文件添加到最终目录的子项中
@@ -773,6 +787,78 @@ private function assembleTaskFilesTree(string $sandboxId, string $workDir, array
773787
return $root['children'];
774788
}
775789

790+
/**
791+
* 判断目录名是否为隐藏目录
792+
* 隐藏目录的判断规则:目录名以 . 开头
793+
*
794+
* @param string $dirName 目录名
795+
* @return bool true-隐藏目录,false-普通目录
796+
*/
797+
private function isHiddenDirectory(string $dirName): bool
798+
{
799+
return str_starts_with($dirName, '.');
800+
}
801+
802+
/**
803+
* 更新话题.
804+
*
805+
* @param DataIsolation $dataIsolation 数据隔离对象
806+
* @param SaveTopicRequestDTO $requestDTO 请求DTO
807+
* @return SaveTopicResultDTO 更新结果
808+
* @throws BusinessException 如果更新失败则抛出异常
809+
*/
810+
private function updateTopic(DataIsolation $dataIsolation, SaveTopicRequestDTO $requestDTO): SaveTopicResultDTO
811+
{
812+
// 更新话题名称
813+
$result = $this->workspaceDomainService->updateTopicName(
814+
$dataIsolation,
815+
(int) $requestDTO->getId(), // 传递主键ID
816+
$requestDTO->getTopicName()
817+
);
818+
819+
if (! $result) {
820+
ExceptionBuilder::throw(GenericErrorCode::SystemError, 'topic.update_failed');
821+
}
822+
823+
return SaveTopicResultDTO::fromId((int) $requestDTO->getId());
824+
}
825+
826+
/**
827+
* 创建新话题.
828+
*
829+
* @param DataIsolation $dataIsolation 数据隔离对象
830+
* @param SaveTopicRequestDTO $requestDTO 请求DTO
831+
* @return SaveTopicResultDTO 创建结果
832+
* @throws BusinessException|Throwable 如果创建失败则抛出异常
833+
*/
834+
private function createNewTopic(DataIsolation $dataIsolation, SaveTopicRequestDTO $requestDTO): SaveTopicResultDTO
835+
{
836+
// 创建新话题,使用事务确保原子性
837+
Db::beginTransaction();
838+
try {
839+
// 1. 初始化 chat 的会话和话题
840+
[$chatConversationId, $chatConversationTopicId] = $this->initMagicChatConversation($dataIsolation);
841+
842+
// 2. 创建话题
843+
$topicEntity = $this->workspaceDomainService->createTopic(
844+
$dataIsolation,
845+
(int) $requestDTO->getWorkspaceId(),
846+
$chatConversationTopicId, // 会话的话题ID
847+
$requestDTO->getTopicName()
848+
);
849+
850+
// 提交事务
851+
Db::commit();
852+
853+
// 返回结果
854+
return SaveTopicResultDTO::fromId((int) $topicEntity->getId());
855+
} catch (Throwable $e) {
856+
// 回滚事务
857+
Db::rollBack();
858+
throw $e;
859+
}
860+
}
861+
776862
/**
777863
* 初始化用户工作区.
778864
*

backend/super-magic-module/src/Domain/SuperAgent/Entity/TaskFileEntity.php

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,8 @@ class TaskFileEntity extends AbstractEntity
3535

3636
protected string $storageType = 'workspace';
3737

38+
protected bool $isHidden = false;
39+
3840
protected string $createdAt = '';
3941

4042
protected string $updatedAt = '';
@@ -161,6 +163,16 @@ public function setStorageType(string $storageType): void
161163
$this->storageType = $storageType;
162164
}
163165

166+
public function getIsHidden(): bool
167+
{
168+
return $this->isHidden;
169+
}
170+
171+
public function setIsHidden(bool $isHidden): void
172+
{
173+
$this->isHidden = $isHidden;
174+
}
175+
164176
public function getCreatedAt(): string
165177
{
166178
return $this->createdAt;
@@ -206,6 +218,7 @@ public function toArray(): array
206218
'file_size' => $this->fileSize,
207219
'external_url' => $this->externalUrl,
208220
'storage_type' => $this->storageType,
221+
'is_hidden' => $this->isHidden,
209222
'created_at' => $this->createdAt,
210223
'updated_at' => $this->updatedAt,
211224
'deleted_at' => $this->deletedAt,

backend/super-magic-module/src/Domain/SuperAgent/Repository/Model/TaskFileModel.php

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,7 @@ class TaskFileModel extends AbstractModel
3535
'external_url',
3636
'menu',
3737
'storage_type', // 存储类型,由FileProcessAppService.processAttachmentsArray方法传入
38+
'is_hidden', // 是否为隐藏文件
3839
'created_at',
3940
'updated_at',
4041
'deleted_at',
@@ -45,5 +46,13 @@ class TaskFileModel extends AbstractModel
4546
*/
4647
protected array $attributes = [
4748
'storage_type' => 'workspace', // 默认存储类型为workspace
49+
'is_hidden' => 0, // 默认不是隐藏文件:0-否,1-是
50+
];
51+
52+
/**
53+
* 类型转换
54+
*/
55+
protected array $casts = [
56+
'is_hidden' => 'boolean', // 自动将数据库中的0/1转换为false/true
4857
];
4958
}

backend/super-magic-module/src/Domain/SuperAgent/Repository/Persistence/TaskFileRepository.php

Lines changed: 12 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -76,16 +76,15 @@ public function getByTopicId(int $topicId, int $page, int $pageSize, array $file
7676
// 先获取总数
7777
$total = $query->count();
7878

79-
// 获取分页数据
80-
$query = $query->skip($offset)
79+
// 获取分页数据,使用Eloquent的get()方法让$casts生效
80+
$models = $query->skip($offset)
8181
->take($pageSize)
82-
->orderBy('file_id', 'desc');
83-
84-
$result = Db::select($query->toSql(), $query->getBindings());
82+
->orderBy('file_id', 'desc')
83+
->get();
8584

8685
$list = [];
87-
foreach ($result as $item) {
88-
$list[] = new TaskFileEntity((array) $item);
86+
foreach ($models as $model) {
87+
$list[] = new TaskFileEntity($model->toArray());
8988
}
9089

9190
return [
@@ -111,18 +110,17 @@ public function getByTaskId(int $taskId, int $page, int $pageSize): array
111110
->where('task_id', $taskId)
112111
->count();
113112

114-
// 获取分页数据
115-
$query = $this->model::query()
113+
// 获取分页数据,使用Eloquent的get()方法让$casts生效
114+
$models = $this->model::query()
116115
->where('task_id', $taskId)
117116
->skip($offset)
118117
->take($pageSize)
119-
->orderBy('file_id', 'desc');
120-
121-
$result = Db::select($query->toSql(), $query->getBindings());
118+
->orderBy('file_id', 'desc')
119+
->get();
122120

123121
$list = [];
124-
foreach ($result as $item) {
125-
$list[] = new TaskFileEntity((array) $item);
122+
foreach ($models as $model) {
123+
$list[] = new TaskFileEntity($model->toArray());
126124
}
127125

128126
return [

backend/super-magic-module/src/Domain/SuperAgent/Service/TaskDomainService.php

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -375,6 +375,8 @@ public function saveOrCreateTaskFileByFileId(
375375
$taskFileEntity->setFileName($fileData['display_filename'] ?? $fileData['filename'] ?? '');
376376
$taskFileEntity->setFileExtension($fileData['file_extension'] ?? '');
377377
$taskFileEntity->setFileSize($fileData['file_size'] ?? 0);
378+
// 判断并设置是否为隐藏文件
379+
$taskFileEntity->setIsHidden($this->isHiddenFile($fileKey));
378380
// 更新存储类型,如果提供了的话
379381
if (isset($fileData['storage_type'])) {
380382
$taskFileEntity->setStorageType($fileData['storage_type']);
@@ -406,6 +408,8 @@ public function saveOrCreateTaskFileByFileId(
406408
$taskFileEntity->setFileName($fileData['display_filename'] ?? $fileData['filename'] ?? '');
407409
$taskFileEntity->setFileExtension($fileData['file_extension'] ?? '');
408410
$taskFileEntity->setFileSize($fileData['file_size'] ?? 0);
411+
// 判断并设置是否为隐藏文件
412+
$taskFileEntity->setIsHidden($this->isHiddenFile($fileKey));
409413
// 设置存储类型,默认为workspace
410414
$taskFileEntity->setStorageType($fileData['storage_type'] ?? 'workspace');
411415

@@ -467,6 +471,8 @@ public function saveOrCreateTaskFileByFileKey(
467471
$taskFileEntity->setFileExtension($fileData['file_extension'] ?? '');
468472
$taskFileEntity->setFileSize($fileData['file_size'] ?? 0);
469473
$taskFileEntity->setExternalUrl($fileData['external_url'] ?? '');
474+
// 判断并设置是否为隐藏文件
475+
$taskFileEntity->setIsHidden($this->isHiddenFile($fileKey));
470476
// 设置存储类型,默认为workspace
471477
$taskFileEntity->setStorageType($fileData['storage_type'] ?? 'workspace');
472478

@@ -647,6 +653,30 @@ public function updateTaskStatusByTaskId(int $id, TaskStatus $status, ?string $e
647653
return $this->taskRepository->updateTaskStatusByTaskId($id, $status);
648654
}
649655

656+
/**
657+
* 判断文件是否为隐藏文件
658+
*
659+
* @param string $fileKey 文件路径
660+
* @return bool 是否为隐藏文件:true-是,false-否
661+
*/
662+
private function isHiddenFile(string $fileKey): bool
663+
{
664+
// 移除开头的斜杠,统一处理
665+
$fileKey = ltrim($fileKey, '/');
666+
667+
// 分割路径为各个部分
668+
$pathParts = explode('/', $fileKey);
669+
670+
// 检查每个路径部分是否以 . 开头
671+
foreach ($pathParts as $part) {
672+
if (!empty($part) && str_starts_with($part, '.')) {
673+
return true; // 是隐藏文件
674+
}
675+
}
676+
677+
return false; // 不是隐藏文件
678+
}
679+
650680
/**
651681
* 获取最近更新时间超过指定时间的任务列表.
652682
*

backend/super-magic-module/src/Interfaces/SuperAgent/DTO/Response/TaskFileItemDTO.php

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,11 @@ class TaskFileItemDTO extends AbstractDTO
5757
*/
5858
public string $fileUrl;
5959

60+
/**
61+
* 是否为隐藏文件:true-是,false-否.
62+
*/
63+
public bool $isHidden;
64+
6065
/**
6166
* 从实体创建DTO.
6267
*/
@@ -72,6 +77,7 @@ public static function fromEntity(TaskFileEntity $entity): self
7277
$dto->fileSize = $entity->getFileSize();
7378
$dto->relativeFilePath = '';
7479
$dto->fileUrl = $entity->getExternalUrl();
80+
$dto->isHidden = $entity->getIsHidden();
7581

7682
return $dto;
7783
}
@@ -82,15 +88,16 @@ public static function fromEntity(TaskFileEntity $entity): self
8288
public static function fromArray(array $data): self
8389
{
8490
$dto = new self();
85-
$dto->fileId = (string) ($data['file_id'] ?? '0');
86-
$dto->taskId = (string) ($data['task_id'] ?? '0');
91+
$dto->fileId = (string) ($data['file_id'] ?? '');
92+
$dto->taskId = (string) ($data['task_id'] ?? '');
8793
$dto->fileType = $data['file_type'] ?? '';
8894
$dto->fileName = $data['file_name'] ?? '';
8995
$dto->fileExtension = $data['file_extension'] ?? '';
9096
$dto->fileKey = $data['file_key'] ?? '';
9197
$dto->fileSize = $data['file_size'] ?? 0;
9298
$dto->relativeFilePath = $data['relative_file_path'] ?? '';
9399
$dto->fileUrl = $data['file_url'] ?? $data['external_url'] ?? '';
100+
$dto->isHidden = $data['is_hidden'] ?? false;
94101
return $dto;
95102
}
96103

@@ -110,6 +117,7 @@ public function toArray(): array
110117
'file_size' => $this->fileSize,
111118
'relative_file_path' => $this->relativeFilePath,
112119
'file_url' => $this->fileUrl,
120+
'is_hidden' => $this->isHidden,
113121
];
114122
}
115123
}

0 commit comments

Comments
 (0)