Skip to content

Commit 718bbb3

Browse files
committed
分页优化
1 parent c96ff64 commit 718bbb3

File tree

5 files changed

+36
-13
lines changed

5 files changed

+36
-13
lines changed

src/main/java/com/layor/tinyflow/repository/DailyClickRepository.java

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
package com.layor.tinyflow.repository;
22

33
import com.layor.tinyflow.entity.DailyClick;
4-
import io.lettuce.core.dynamic.annotation.Param;
4+
import org.springframework.data.repository.query.Param;
55
import org.springframework.data.jpa.repository.JpaRepository;
66
import org.springframework.data.jpa.repository.Modifying;
77
import org.springframework.data.jpa.repository.Query;
@@ -24,6 +24,9 @@ List<DailyClick> findRecentTrend(@Param("shortCode") String shortCode,
2424
@Query("SELECT d.clicks FROM DailyClick d WHERE d.shortCode = :shortCode AND d.date = CURRENT_DATE")
2525
Integer getTodayClicksByShortCode(String shortCode);
2626

27+
@Query("SELECT d.shortCode, d.clicks FROM DailyClick d WHERE d.date = CURRENT_DATE AND d.shortCode IN (:codes)")
28+
List<Object[]> findTodayClicksByShortCodes(@Param("codes") List<String> codes);
29+
2730
DailyClick findByShortCode(String shortCode);
2831

2932
void deleteByShortCode(String shortCode);

src/main/java/com/layor/tinyflow/service/ClickRecorderService.java

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -118,6 +118,7 @@ public void recordClickEvent(String shortCode, String referer, String ua, String
118118
clickEventRepository.save(ev);
119119
}
120120

121+
121122
@Scheduled(fixedDelay = 2000)
122123
@Transactional
123124
public void flushCounters() {

src/main/java/com/layor/tinyflow/service/ShortUrlService.java

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -248,14 +248,18 @@ public Page<UrlListResponseDTO> getAllUrls(int page, int size) {
248248
return new PageImpl<>(Collections.emptyList(), pageable, 0);
249249
}
250250

251-
List<UrlListResponseDTO> urlListResponseDTO= shortUrls.stream()
251+
List<String> codes = shortUrls.stream().map(ShortUrl::getShortCode).toList();
252+
Map<String, Integer> todayMap = dailyClickRepo.findTodayClicksByShortCodes(codes).stream()
253+
.collect(Collectors.toMap(r -> (String) r[0], r -> ((Number) r[1]).intValue()));
254+
List<UrlListResponseDTO> urlListResponseDTO = shortUrls.stream()
252255
.map(shortUrl -> UrlListResponseDTO.builder()
253256
.shortCode(shortUrl.getShortCode())
254257
.longUrl(shortUrl.getLongUrl())
255258
.totalVisits(Long.valueOf(shortUrl.getClickCount()))
256-
.todayVisits(dailyClickRepo.getTodayClicksByShortCode(shortUrl.getShortCode()))
259+
.todayVisits(todayMap.getOrDefault(shortUrl.getShortCode(), 0))
257260
.createdAt(shortUrl.getCreatedAt())
258-
.build()).toList();
261+
.build())
262+
.toList();
259263

260264
return new PageImpl<>(urlListResponseDTO, pageable, shortUrlPage.getTotalElements());
261265

web/src/composables/useStats.js

Lines changed: 17 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,13 +7,16 @@ function createApiState() {
77
return { data: ref(null), loading: ref(false), error: ref(null) }
88
}
99

10-
export function useFetchList() {
10+
export function useFetchList(pageRef, sizeRef) {
1111
const state = createApiState()
12+
state.meta = ref({ totalElements: 0, totalPages: 1, size: 10, number: 0 })
1213
const refresh = async () => {
1314
state.loading.value = true
1415
state.error.value = null
1516
try {
16-
const res = await axios.get('/api/urls')
17+
const p = (pageRef && typeof pageRef === 'object' && 'value' in pageRef) ? Number(pageRef.value) : Number(pageRef || 1)
18+
const s = (sizeRef && typeof sizeRef === 'object' && 'value' in sizeRef) ? Number(sizeRef.value) : Number(sizeRef || 10)
19+
const res = await axios.get('/api/urls', { params: { page: Math.max(0, p - 1), size: Math.max(1, s) } })
1720
const payload = res?.data ?? null
1821
// 兼容后端分页返回结构:PageResponseDTO { content, totalElements, ... }
1922
const list = Array.isArray(payload)
@@ -34,8 +37,20 @@ export function useFetchList() {
3437
const fixed = code ? `${SHORT_BASE}/${encodeURIComponent(code)}` : raw
3538
return { ...it, shortUrl: fixed }
3639
})
40+
state.meta.value = {
41+
totalElements: Number(payload?.data?.totalElements ?? payload?.totalElements ?? (Array.isArray(list) ? list.length : 0)),
42+
totalPages: Number(payload?.data?.totalPages ?? payload?.totalPages ?? 1),
43+
size: Number(payload?.data?.size ?? payload?.size ?? s),
44+
number: Number(payload?.data?.number ?? payload?.number ?? Math.max(0, p - 1))
45+
}
3746
} catch {
3847
state.data.value = list
48+
state.meta.value = {
49+
totalElements: Number(payload?.data?.totalElements ?? payload?.totalElements ?? (Array.isArray(list) ? list.length : 0)),
50+
totalPages: Number(payload?.data?.totalPages ?? payload?.totalPages ?? 1),
51+
size: Number(payload?.data?.size ?? payload?.size ?? s),
52+
number: Number(payload?.data?.number ?? payload?.number ?? Math.max(0, p - 1))
53+
}
3954
}
4055
} catch (e) {
4156
state.error.value = e

web/src/pages/DashboardPage.vue

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -103,7 +103,7 @@
103103
</div>
104104
<!-- Pagination -->
105105
<div class="flex items-center justify-between mt-4">
106-
<div class="md-muted">{{ $t('dashboard.pagination.total', { count: filteredList.length, page: page, pages: totalPages }) }}</div>
106+
<div class="md-muted">{{ $t('dashboard.pagination.total', { count: (meta?.value && meta.value.totalElements) || 0, page: page, pages: totalPages }) }}</div>
107107
<div class="flex items-center gap-3">
108108
<button @click="prev" class="md-btn-text">{{ $t('dashboard.pagination.prev') }}</button>
109109
<button @click="next" class="md-btn-text">{{ $t('dashboard.pagination.next') }}</button>
@@ -134,9 +134,9 @@ const { t } = useI18n()
134134
135135
const query = ref('')
136136
const page = ref(1)
137-
const pageSize = 10
137+
const pageSize = ref(10)
138138
139-
const { data: listRef, loading, error, refresh } = useFetchList()
139+
const { data: listRef, loading, error, refresh, meta } = useFetchList(page, pageSize)
140140
// 新增:点击统计(用于饼图)来源于 /api/urls/click-stats
141141
const { data: clickStatsRef, loading: clickLoading, error: clickError, refresh: refreshClickStats } = useFetchClickStats()
142142
const list = listRef
@@ -292,10 +292,10 @@ const filteredList = computed(() => {
292292
return base.sort((a,b) => Number(b.totalVisits||0) - Number(a.totalVisits||0))
293293
})
294294
295-
const totalPages = computed(() => Math.max(1, Math.ceil(filteredList.value.length / pageSize)))
296-
const pagedList = computed(() => filteredList.value.slice((page.value-1)*pageSize, page.value*pageSize))
297-
function prev(){ page.value = Math.max(1, page.value-1) }
298-
function next(){ page.value = Math.min(totalPages.value, page.value+1) }
295+
const totalPages = computed(() => Math.max(1, Number((meta?.value && meta.value.totalPages) || 1)))
296+
const pagedList = computed(() => filteredList.value)
297+
async function prev(){ page.value = Math.max(1, page.value-1); await refresh() }
298+
async function next(){ page.value = Math.min(totalPages.value, page.value+1); await refresh() }
299299
300300
// 已移除趋势与Top5对比相关逻辑
301301

0 commit comments

Comments
 (0)