zen-gitsync 2.0.3 → 2.0.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,13 +1,26 @@
1
1
  <script setup lang="ts">
2
- import { ref, onMounted, defineExpose } from 'vue'
2
+ import { ref, onMounted, computed } from 'vue'
3
3
  import { ElMessage, ElMessageBox } from 'element-plus'
4
4
  // import { io } from 'socket.io-client'
5
5
  import { Refresh, ArrowLeft, ArrowRight, Folder, Document, ArrowUp, RefreshRight } from '@element-plus/icons-vue'
6
+ import { useGitLogStore } from '../stores/gitLogStore'
7
+ import { useGitStore } from '../stores/gitStore'
8
+
9
+ // 定义props
10
+ const props = defineProps({
11
+ initialDirectory: {
12
+ type: String,
13
+ default: ''
14
+ }
15
+ })
6
16
 
7
- const status = ref('加载中...')
17
+ const gitLogStore = useGitLogStore()
18
+ const gitStore = useGitStore()
19
+ // 移除本地status定义,直接使用store中的statusText
20
+ // const status = ref('加载中...')
8
21
  // const socket = io()
9
- const isRefreshing = ref(false)
10
- const fileList = ref<{path: string, type: string}[]>([])
22
+ const isRefreshing = computed(() => gitLogStore.isLoadingStatus)
23
+ // 移除本地fileList定义,改用store中的fileList
11
24
  const selectedFile = ref('')
12
25
  const diffContent = ref('')
13
26
  const diffDialogVisible = ref(false)
@@ -25,66 +38,33 @@ const directoryItems = ref<{name: string, path: string, type: string}[]>([])
25
38
  const isBrowsing = ref(false)
26
39
  const browseErrorMessage = ref('')
27
40
 
28
- // 解析 git status 输出,提取文件及类型
29
- function parseStatus(statusText: string) {
30
- if (statusText === undefined) return
31
- const lines = statusText.split('\n')
32
- const files: {path: string, type: string}[] = []
33
- for (const line of lines) {
34
- // 匹配常见的 git status --porcelain 格式
35
- // M: 修改, A: 新增, D: 删除, ??: 未跟踪
36
- const match = line.match(/^([ MADRCU\?]{2})\s+(.+)$/)
37
- if (match) {
38
- let type = ''
39
- const code = match[1].trim()
40
- if (code === 'M' || code === 'MM' || code === 'AM' || code === 'RM') type = 'modified'
41
- else if (code === 'A' || code === 'AA') type = 'added'
42
- else if (code === 'D' || code === 'AD' || code === 'DA') type = 'deleted'
43
- else if (code === '??') type = 'untracked'
44
- else type = 'other'
45
- files.push({ path: match[2], type })
46
- }
47
- }
48
- fileList.value = files
49
- }
50
-
51
- const currentDirectory = ref('')
41
+ const currentDirectory = ref(props.initialDirectory || '');
52
42
  async function loadStatus() {
53
43
  try {
54
- isRefreshing.value = true
55
- // 获取当前工作目录
56
- const responseDir = await fetch('/api/current_directory')
57
- const dirData = await responseDir.json()
58
- currentDirectory.value = dirData.directory || '未知目录'
44
+ // 如果没有初始目录,才需要请求当前目录
45
+ if (!currentDirectory.value) {
46
+ const responseDir = await fetch('/api/current_directory')
47
+ const dirData = await responseDir.json()
48
+ currentDirectory.value = dirData.directory || '未知目录'
49
+ }
59
50
 
60
- // 如果不是Git仓库,显示提示并返回
61
- if (dirData.isGitRepo === false) {
62
- status.value = '当前目录不是一个Git仓库'
63
- fileList.value = []
64
- ElMessage.warning('当前目录不是一个Git仓库')
51
+ // 如果不是Git仓库,直接显示提示并返回
52
+ if (!gitStore.isGitRepo) {
65
53
  return
66
54
  }
67
55
 
68
- const response = await fetch('/api/status')
69
- const data = await response.json()
70
- status.value = data.status
71
-
72
- const response_porcelain = await fetch('/api/status_porcelain')
73
- const data_porcelain = await response_porcelain.json()
74
- parseStatus(data_porcelain.status)
56
+ // 使用gitLogStore获取Git状态
57
+ await gitLogStore.fetchStatus()
58
+
75
59
  ElMessage({
76
60
  message: 'Git 状态已刷新',
77
61
  type: 'success',
78
62
  })
79
63
  } catch (error) {
80
- status.value = '加载状态失败: ' + (error as Error).message
81
- fileList.value = []
82
64
  ElMessage({
83
65
  message: '刷新失败: ' + (error as Error).message,
84
66
  type: 'error',
85
67
  })
86
- } finally {
87
- isRefreshing.value = false
88
68
  }
89
69
  }
90
70
 
@@ -134,7 +114,7 @@ async function getFileDiff(filePath: string) {
134
114
  isLoadingDiff.value = true
135
115
  selectedFile.value = filePath
136
116
  // 设置当前文件索引
137
- currentFileIndex.value = fileList.value.findIndex(file => file.path === filePath)
117
+ currentFileIndex.value = gitLogStore.fileList.findIndex(file => file.path === filePath)
138
118
  const response = await fetch(`/api/diff?file=${encodeURIComponent(filePath)}`)
139
119
  const data = await response.json()
140
120
  diffContent.value = data.diff || '没有变更'
@@ -152,19 +132,19 @@ async function getFileDiff(filePath: string) {
152
132
 
153
133
  // 添加切换到上一个文件的方法
154
134
  async function goToPreviousFile() {
155
- if (fileList.value.length === 0 || currentFileIndex.value <= 0) return
135
+ if (gitLogStore.fileList.length === 0 || currentFileIndex.value <= 0) return
156
136
 
157
137
  const newIndex = currentFileIndex.value - 1
158
- const prevFile = fileList.value[newIndex]
138
+ const prevFile = gitLogStore.fileList[newIndex]
159
139
  await getFileDiff(prevFile.path)
160
140
  }
161
141
 
162
142
  // 添加切换到下一个文件的方法
163
143
  async function goToNextFile() {
164
- if (fileList.value.length === 0 || currentFileIndex.value >= fileList.value.length - 1) return
144
+ if (gitLogStore.fileList.length === 0 || currentFileIndex.value >= gitLogStore.fileList.length - 1) return
165
145
 
166
146
  const newIndex = currentFileIndex.value + 1
167
- const nextFile = fileList.value[newIndex]
147
+ const nextFile = gitLogStore.fileList[newIndex]
168
148
  await getFileDiff(nextFile.path)
169
149
  }
170
150
 
@@ -289,13 +269,25 @@ async function changeDirectory() {
289
269
  currentDirectory.value = result.directory
290
270
  isDirectoryDialogVisible.value = false
291
271
 
292
- // 如果新目录不是Git仓库,显示警告
293
- if (!result.isGitRepo) {
272
+ // 直接使用API返回的Git仓库状态
273
+ gitStore.isGitRepo = result.isGitRepo
274
+
275
+ // 如果是Git仓库,加载Git相关数据
276
+ if (result.isGitRepo) {
277
+ // 加载Git分支和用户信息
278
+ await Promise.all([
279
+ gitStore.getCurrentBranch(),
280
+ gitStore.getAllBranches(),
281
+ gitStore.getUserInfo()
282
+ ])
283
+
284
+ // 刷新Git状态
285
+ await loadStatus()
286
+ } else {
294
287
  ElMessage.warning('当前目录不是一个Git仓库')
288
+ // 清空Git相关状态
289
+ gitStore.$reset() // 使用pinia的reset方法重置状态
295
290
  }
296
-
297
- // 刷新状态
298
- loadStatus()
299
291
  } else {
300
292
  ElMessage.error(result.error || '切换目录失败')
301
293
  }
@@ -368,13 +360,9 @@ async function revertFileChanges(filePath: string) {
368
360
  }
369
361
 
370
362
  onMounted(() => {
363
+ // App.vue已经加载了Git相关数据,此时只需加载状态
364
+ // 如果已有初始目录,则只需加载状态
371
365
  loadStatus()
372
-
373
- // Socket.io 事件
374
- // socket.on('status_update', (data: { status: string }) => {
375
- // status.value = data.status
376
- // parseStatus(data.status)
377
- // })
378
366
  })
379
367
 
380
368
  // onUnmounted(() => {
@@ -397,7 +385,7 @@ defineExpose({
397
385
  </el-button>
398
386
  </div>
399
387
  <div class="status-header">
400
- <h2>Git 状态</h2>
388
+ <h2>Git 状态(git status)</h2>
401
389
  <el-button
402
390
  type="primary"
403
391
  :icon="Refresh"
@@ -407,11 +395,13 @@ defineExpose({
407
395
  :loading="isRefreshing"
408
396
  />
409
397
  </div>
410
- <div class="status-box">{{ status }}</div>
398
+ <div class="status-box">
399
+ {{ !gitStore.isGitRepo ? '当前目录不是一个Git仓库' : gitLogStore.statusText || '加载中...' }}
400
+ </div>
411
401
  <!-- 颜色区分不同类型文件 -->
412
- <div v-if="fileList.length" class="file-list">
402
+ <div v-if="gitLogStore.fileList.length" class="file-list">
413
403
  <div
414
- v-for="file in fileList"
404
+ v-for="file in gitLogStore.fileList"
415
405
  :key="file.path"
416
406
  :class="['file-item', file.type]"
417
407
  >
@@ -492,18 +482,20 @@ defineExpose({
492
482
  </div>
493
483
 
494
484
  <!-- 目录内容列表 -->
495
- <ul class="directory-items">
496
- <li
497
- v-for="item in directoryItems"
498
- :key="item.path"
499
- :class="['directory-item', item.type]"
500
- @click="selectDirectoryItem(item)"
501
- >
502
- <el-icon v-if="item.type === 'directory'"><Folder /></el-icon>
503
- <el-icon v-else><Document /></el-icon>
504
- <span>{{ item.name }}</span>
505
- </li>
506
- </ul>
485
+ <div class="directory-items-container">
486
+ <ul class="directory-items">
487
+ <li
488
+ v-for="item in directoryItems"
489
+ :key="item.path"
490
+ :class="['directory-item', item.type]"
491
+ @click="selectDirectoryItem(item)"
492
+ >
493
+ <el-icon v-if="item.type === 'directory'"><Folder /></el-icon>
494
+ <el-icon v-else><Document /></el-icon>
495
+ <span>{{ item.name }}</span>
496
+ </li>
497
+ </ul>
498
+ </div>
507
499
  </div>
508
500
  </el-dialog>
509
501
 
@@ -524,14 +516,14 @@ defineExpose({
524
516
  <el-button
525
517
  :icon="ArrowLeft"
526
518
  @click="goToPreviousFile"
527
- :disabled="currentFileIndex <= 0 || fileList.length === 0"
519
+ :disabled="currentFileIndex <= 0 || gitLogStore.fileList.length === 0"
528
520
  circle
529
521
  />
530
- <span class="file-counter">{{ currentFileIndex + 1 }} / {{ fileList.length }}</span>
522
+ <span class="file-counter">{{ currentFileIndex + 1 }} / {{ gitLogStore.fileList.length }}</span>
531
523
  <el-button
532
524
  :icon="ArrowRight"
533
525
  @click="goToNextFile"
534
- :disabled="currentFileIndex >= fileList.length - 1 || fileList.length === 0"
526
+ :disabled="currentFileIndex >= gitLogStore.fileList.length - 1 || gitLogStore.fileList.length === 0"
535
527
  circle
536
528
  />
537
529
  </div>
@@ -708,14 +700,25 @@ defineExpose({
708
700
 
709
701
  .directory-browser {
710
702
  padding: 10px;
711
- max-height: 400px;
712
- overflow-y: auto;
703
+ height: 400px;
704
+ display: flex;
705
+ flex-direction: column;
713
706
  }
714
707
 
715
708
  .browser-nav {
716
709
  margin-bottom: 10px;
717
710
  display: flex;
718
711
  justify-content: space-between;
712
+ position: sticky;
713
+ top: 0;
714
+ background-color: #fff;
715
+ z-index: 1;
716
+ padding: 10px 0;
717
+ }
718
+
719
+ .directory-items-container {
720
+ flex: 1;
721
+ overflow-y: auto;
719
722
  }
720
723
 
721
724
  .directory-items {