@moontra/moonui-pro 2.18.3 → 2.18.4
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.
package/dist/index.mjs
CHANGED
|
@@ -61374,6 +61374,12 @@ var AdvancedForms = ({ className, ...props }) => {
|
|
|
61374
61374
|
|
|
61375
61375
|
// src/components/github-stars/github-api.ts
|
|
61376
61376
|
var cache = /* @__PURE__ */ new Map();
|
|
61377
|
+
var isDocsMode = () => {
|
|
61378
|
+
return typeof window !== "undefined" && (window.location.pathname.includes("/docs/") || window.location.pathname.includes("/components/"));
|
|
61379
|
+
};
|
|
61380
|
+
var getCacheDuration = (defaultDuration) => {
|
|
61381
|
+
return isDocsMode() ? 18e5 : defaultDuration;
|
|
61382
|
+
};
|
|
61377
61383
|
var LANGUAGE_COLORS = {
|
|
61378
61384
|
JavaScript: "#f7df1e",
|
|
61379
61385
|
TypeScript: "#3178c6",
|
|
@@ -61441,8 +61447,8 @@ async function getRateLimitInfo(token) {
|
|
|
61441
61447
|
cache.set(cacheKey, {
|
|
61442
61448
|
data: rateLimitInfo,
|
|
61443
61449
|
timestamp: Date.now(),
|
|
61444
|
-
expiresAt: Date.now() + 6e4
|
|
61445
|
-
//
|
|
61450
|
+
expiresAt: Date.now() + getCacheDuration(6e4)
|
|
61451
|
+
// Docs modunda daha uzun cache
|
|
61446
61452
|
});
|
|
61447
61453
|
return rateLimitInfo;
|
|
61448
61454
|
}
|
|
@@ -61462,8 +61468,8 @@ async function fetchUserRepositories(username, token, options) {
|
|
|
61462
61468
|
cache.set(cacheKey, {
|
|
61463
61469
|
data: repos,
|
|
61464
61470
|
timestamp: Date.now(),
|
|
61465
|
-
expiresAt: Date.now() + 3e5
|
|
61466
|
-
//
|
|
61471
|
+
expiresAt: Date.now() + getCacheDuration(3e5)
|
|
61472
|
+
// Docs modunda 30 dakika
|
|
61467
61473
|
});
|
|
61468
61474
|
return repos;
|
|
61469
61475
|
}
|
|
@@ -61478,8 +61484,8 @@ async function fetchRepository(owner, repo, token) {
|
|
|
61478
61484
|
cache.set(cacheKey, {
|
|
61479
61485
|
data: repository,
|
|
61480
61486
|
timestamp: Date.now(),
|
|
61481
|
-
expiresAt: Date.now() + 3e5
|
|
61482
|
-
//
|
|
61487
|
+
expiresAt: Date.now() + getCacheDuration(3e5)
|
|
61488
|
+
// Docs modunda 30 dakika
|
|
61483
61489
|
});
|
|
61484
61490
|
return repository;
|
|
61485
61491
|
}
|
|
@@ -61502,8 +61508,8 @@ async function fetchContributorsCount(owner, repo, token) {
|
|
|
61502
61508
|
cache.set(cacheKey, {
|
|
61503
61509
|
data: count4,
|
|
61504
61510
|
timestamp: Date.now(),
|
|
61505
|
-
expiresAt: Date.now() + 36e5
|
|
61506
|
-
//
|
|
61511
|
+
expiresAt: Date.now() + getCacheDuration(36e5)
|
|
61512
|
+
// Docs modunda 30 dakika
|
|
61507
61513
|
});
|
|
61508
61514
|
return count4;
|
|
61509
61515
|
}
|
|
@@ -61513,8 +61519,8 @@ async function fetchContributorsCount(owner, repo, token) {
|
|
|
61513
61519
|
cache.set(cacheKey, {
|
|
61514
61520
|
data: count3,
|
|
61515
61521
|
timestamp: Date.now(),
|
|
61516
|
-
expiresAt: Date.now() + 36e5
|
|
61517
|
-
//
|
|
61522
|
+
expiresAt: Date.now() + getCacheDuration(36e5)
|
|
61523
|
+
// Docs modunda 30 dakika
|
|
61518
61524
|
});
|
|
61519
61525
|
return count3;
|
|
61520
61526
|
} catch (error) {
|
|
@@ -61676,8 +61682,12 @@ function useGitHubData({
|
|
|
61676
61682
|
onError,
|
|
61677
61683
|
onDataUpdate,
|
|
61678
61684
|
onMilestoneReached,
|
|
61679
|
-
milestones = [10, 50, 100, 500, 1e3, 5e3, 1e4]
|
|
61685
|
+
milestones = [10, 50, 100, 500, 1e3, 5e3, 1e4],
|
|
61686
|
+
docsMode = false,
|
|
61687
|
+
mockDataFallback = true
|
|
61680
61688
|
}) {
|
|
61689
|
+
const isDocsMode2 = docsMode || typeof window !== "undefined" && (window.location.pathname.includes("/docs/") || window.location.pathname.includes("/components/"));
|
|
61690
|
+
const effectiveAutoRefresh = isDocsMode2 ? false : autoRefresh;
|
|
61681
61691
|
const [repos, setRepos] = useState([]);
|
|
61682
61692
|
const [stats, setStats] = useState(null);
|
|
61683
61693
|
const [loading, setLoading] = useState(true);
|
|
@@ -61687,7 +61697,9 @@ function useGitHubData({
|
|
|
61687
61697
|
const refreshTimeoutRef = useRef();
|
|
61688
61698
|
const previousStarsRef = useRef(/* @__PURE__ */ new Map());
|
|
61689
61699
|
const errorCountRef = useRef(0);
|
|
61690
|
-
const maxErrorCount = 2;
|
|
61700
|
+
const maxErrorCount = isDocsMode2 ? 1 : 2;
|
|
61701
|
+
const hasInitialFetchedRef = useRef(false);
|
|
61702
|
+
const docsDataCacheRef = useRef(null);
|
|
61691
61703
|
const milestonesRef = useRef(milestones);
|
|
61692
61704
|
const onMilestoneReachedRef = useRef(onMilestoneReached);
|
|
61693
61705
|
useEffect(() => {
|
|
@@ -61716,10 +61728,26 @@ function useGitHubData({
|
|
|
61716
61728
|
});
|
|
61717
61729
|
}, []);
|
|
61718
61730
|
const fetchData = useCallback(async () => {
|
|
61731
|
+
if (isDocsMode2 && hasInitialFetchedRef.current && docsDataCacheRef.current) {
|
|
61732
|
+
console.log("[Docs Mode] Returning cached data, skipping API request");
|
|
61733
|
+
setRepos(docsDataCacheRef.current);
|
|
61734
|
+
const calculatedStats = calculateStats(docsDataCacheRef.current);
|
|
61735
|
+
setStats(calculatedStats);
|
|
61736
|
+
setLoading(false);
|
|
61737
|
+
return;
|
|
61738
|
+
}
|
|
61719
61739
|
if (errorCountRef.current >= maxErrorCount) {
|
|
61720
61740
|
console.warn("Maximum error count reached. Stopping requests.");
|
|
61741
|
+
if (isDocsMode2 && mockDataFallback) {
|
|
61742
|
+
const mockData = getMockGitHubData(username, repository, repositories);
|
|
61743
|
+
setRepos(mockData);
|
|
61744
|
+
const calculatedStats = calculateStats(mockData);
|
|
61745
|
+
setStats(calculatedStats);
|
|
61746
|
+
setError(null);
|
|
61747
|
+
} else {
|
|
61748
|
+
setError("Maximum retry limit exceeded. Please check your configuration.");
|
|
61749
|
+
}
|
|
61721
61750
|
setLoading(false);
|
|
61722
|
-
setError("Maximum retry limit exceeded. Please check your configuration.");
|
|
61723
61751
|
return;
|
|
61724
61752
|
}
|
|
61725
61753
|
const hasValidInput = username && repository || // Tek repository modu
|
|
@@ -61812,12 +61840,25 @@ function useGitHubData({
|
|
|
61812
61840
|
}
|
|
61813
61841
|
setLastUpdated(/* @__PURE__ */ new Date());
|
|
61814
61842
|
errorCountRef.current = 0;
|
|
61843
|
+
if (isDocsMode2) {
|
|
61844
|
+
hasInitialFetchedRef.current = true;
|
|
61845
|
+
docsDataCacheRef.current = enhancedRepos;
|
|
61846
|
+
}
|
|
61815
61847
|
} catch (err) {
|
|
61816
61848
|
const errorMessage = err instanceof Error ? err.message : "Failed to fetch data";
|
|
61817
61849
|
setError(errorMessage);
|
|
61818
61850
|
errorCountRef.current += 1;
|
|
61819
61851
|
console.error(`GitHub API error (${errorCountRef.current}/${maxErrorCount}):`, errorMessage);
|
|
61820
|
-
if (
|
|
61852
|
+
if (isDocsMode2 && mockDataFallback && !hasInitialFetchedRef.current) {
|
|
61853
|
+
console.warn("[Docs Mode] API failed, using mock data");
|
|
61854
|
+
const mockData = getMockGitHubData(username, repository, repositories);
|
|
61855
|
+
setRepos(mockData);
|
|
61856
|
+
const calculatedStats = calculateStats(mockData);
|
|
61857
|
+
setStats(calculatedStats);
|
|
61858
|
+
setError(null);
|
|
61859
|
+
hasInitialFetchedRef.current = true;
|
|
61860
|
+
docsDataCacheRef.current = mockData;
|
|
61861
|
+
} else if (onError) {
|
|
61821
61862
|
onError(err instanceof Error ? err : new Error(errorMessage));
|
|
61822
61863
|
}
|
|
61823
61864
|
} finally {
|
|
@@ -61834,7 +61875,9 @@ function useGitHubData({
|
|
|
61834
61875
|
checkMilestones,
|
|
61835
61876
|
// Artık stable
|
|
61836
61877
|
onDataUpdate,
|
|
61837
|
-
onError
|
|
61878
|
+
onError,
|
|
61879
|
+
isDocsMode2,
|
|
61880
|
+
mockDataFallback
|
|
61838
61881
|
]);
|
|
61839
61882
|
useEffect(() => {
|
|
61840
61883
|
const hasValidInput = username && repository || username && repositories && repositories.length > 0 || repositories && repositories.length > 0 && repositories.every((r2) => r2.includes("/")) || username;
|
|
@@ -61845,7 +61888,7 @@ function useGitHubData({
|
|
|
61845
61888
|
}
|
|
61846
61889
|
}, [fetchData]);
|
|
61847
61890
|
useEffect(() => {
|
|
61848
|
-
if (!
|
|
61891
|
+
if (!effectiveAutoRefresh)
|
|
61849
61892
|
return;
|
|
61850
61893
|
const scheduleRefresh = () => {
|
|
61851
61894
|
refreshTimeoutRef.current = setTimeout(() => {
|
|
@@ -61859,15 +61902,19 @@ function useGitHubData({
|
|
|
61859
61902
|
clearTimeout(refreshTimeoutRef.current);
|
|
61860
61903
|
}
|
|
61861
61904
|
};
|
|
61862
|
-
}, [
|
|
61905
|
+
}, [effectiveAutoRefresh, refreshInterval, fetchData]);
|
|
61863
61906
|
const refresh = useCallback(() => {
|
|
61907
|
+
if (isDocsMode2 && hasInitialFetchedRef.current) {
|
|
61908
|
+
console.warn("[Docs Mode] Refresh disabled after initial fetch");
|
|
61909
|
+
return Promise.resolve();
|
|
61910
|
+
}
|
|
61864
61911
|
if (errorCountRef.current >= maxErrorCount) {
|
|
61865
61912
|
console.warn("Cannot refresh: maximum error count reached");
|
|
61866
61913
|
return Promise.resolve();
|
|
61867
61914
|
}
|
|
61868
61915
|
clearCache();
|
|
61869
61916
|
return fetchData();
|
|
61870
|
-
}, [fetchData]);
|
|
61917
|
+
}, [fetchData, isDocsMode2]);
|
|
61871
61918
|
return {
|
|
61872
61919
|
repos,
|
|
61873
61920
|
stats,
|
|
@@ -61907,6 +61954,64 @@ function useGitHubNotifications(enabled = true) {
|
|
|
61907
61954
|
);
|
|
61908
61955
|
return { permission, notify };
|
|
61909
61956
|
}
|
|
61957
|
+
function getMockGitHubData(username, repository, repositories) {
|
|
61958
|
+
const defaultRepos = [
|
|
61959
|
+
{
|
|
61960
|
+
id: 1,
|
|
61961
|
+
name: repository || "awesome-project",
|
|
61962
|
+
full_name: `${username || "moonui"}/${repository || "awesome-project"}`,
|
|
61963
|
+
description: "An amazing open source project with great features",
|
|
61964
|
+
html_url: `https://github.com/${username || "moonui"}/${repository || "awesome-project"}`,
|
|
61965
|
+
homepage: "https://awesome-project.dev",
|
|
61966
|
+
stargazers_count: 12453,
|
|
61967
|
+
watchers_count: 543,
|
|
61968
|
+
forks_count: 2341,
|
|
61969
|
+
language: "TypeScript",
|
|
61970
|
+
topics: ["react", "ui", "components", "typescript"],
|
|
61971
|
+
created_at: "2022-01-15T10:30:00Z",
|
|
61972
|
+
updated_at: (/* @__PURE__ */ new Date()).toISOString(),
|
|
61973
|
+
pushed_at: (/* @__PURE__ */ new Date()).toISOString(),
|
|
61974
|
+
size: 4567,
|
|
61975
|
+
open_issues_count: 23,
|
|
61976
|
+
license: {
|
|
61977
|
+
key: "mit",
|
|
61978
|
+
name: "MIT License",
|
|
61979
|
+
spdx_id: "MIT",
|
|
61980
|
+
url: "https://api.github.com/licenses/mit"
|
|
61981
|
+
},
|
|
61982
|
+
owner: {
|
|
61983
|
+
login: username || "moonui",
|
|
61984
|
+
avatar_url: `https://github.com/${username || "moonui"}.png`,
|
|
61985
|
+
html_url: `https://github.com/${username || "moonui"}`,
|
|
61986
|
+
type: "Organization"
|
|
61987
|
+
},
|
|
61988
|
+
contributors_count: 89
|
|
61989
|
+
}
|
|
61990
|
+
];
|
|
61991
|
+
if (repositories && repositories.length > 0) {
|
|
61992
|
+
return repositories.map((repo, index2) => {
|
|
61993
|
+
const [owner, name] = repo.includes("/") ? repo.split("/") : [username || "moonui", repo];
|
|
61994
|
+
return {
|
|
61995
|
+
...defaultRepos[0],
|
|
61996
|
+
id: index2 + 1,
|
|
61997
|
+
name,
|
|
61998
|
+
full_name: `${owner}/${name}`,
|
|
61999
|
+
html_url: `https://github.com/${owner}/${name}`,
|
|
62000
|
+
stargazers_count: Math.floor(Math.random() * 2e4) + 1e3,
|
|
62001
|
+
forks_count: Math.floor(Math.random() * 3e3) + 100,
|
|
62002
|
+
watchers_count: Math.floor(Math.random() * 1e3) + 50,
|
|
62003
|
+
language: ["TypeScript", "JavaScript", "Python", "Go", "Rust"][index2 % 5],
|
|
62004
|
+
owner: {
|
|
62005
|
+
login: owner,
|
|
62006
|
+
avatar_url: `https://github.com/${owner}.png`,
|
|
62007
|
+
html_url: `https://github.com/${owner}`,
|
|
62008
|
+
type: "Organization"
|
|
62009
|
+
}
|
|
62010
|
+
};
|
|
62011
|
+
});
|
|
62012
|
+
}
|
|
62013
|
+
return defaultRepos;
|
|
62014
|
+
}
|
|
61910
62015
|
var MinimalVariant = ({ repos, stats, className }) => {
|
|
61911
62016
|
if (!stats)
|
|
61912
62017
|
return null;
|
|
@@ -62429,7 +62534,11 @@ var GitHubStarsInternal = ({
|
|
|
62429
62534
|
size: size4 = "md",
|
|
62430
62535
|
customColors
|
|
62431
62536
|
}) => {
|
|
62432
|
-
const
|
|
62537
|
+
const isDocsMode2 = typeof window !== "undefined" && (window.location.pathname.includes("/docs/") || window.location.pathname.includes("/components/"));
|
|
62538
|
+
const effectiveAutoRefresh = isDocsMode2 ? false : autoRefresh;
|
|
62539
|
+
const effectiveNotifications = isDocsMode2 ? false : enableNotifications;
|
|
62540
|
+
const effectiveRefreshInterval = isDocsMode2 ? 36e5 : refreshInterval;
|
|
62541
|
+
const { notify } = useGitHubNotifications(effectiveNotifications);
|
|
62433
62542
|
const handleMilestoneReached = t__default.useCallback((milestone) => {
|
|
62434
62543
|
if (celebrateAt?.includes(milestone.count)) {
|
|
62435
62544
|
confetti({
|
|
@@ -62457,14 +62566,18 @@ var GitHubStarsInternal = ({
|
|
|
62457
62566
|
repository,
|
|
62458
62567
|
repositories,
|
|
62459
62568
|
token,
|
|
62460
|
-
autoRefresh,
|
|
62461
|
-
refreshInterval,
|
|
62569
|
+
autoRefresh: effectiveAutoRefresh,
|
|
62570
|
+
refreshInterval: effectiveRefreshInterval,
|
|
62462
62571
|
sortBy,
|
|
62463
62572
|
maxItems,
|
|
62464
62573
|
onError,
|
|
62465
62574
|
onDataUpdate,
|
|
62466
62575
|
onMilestoneReached: handleMilestoneReached,
|
|
62467
|
-
milestones
|
|
62576
|
+
milestones,
|
|
62577
|
+
docsMode: isDocsMode2,
|
|
62578
|
+
// Docs mode flag'ini gönder
|
|
62579
|
+
mockDataFallback: true
|
|
62580
|
+
// Docs modunda mock data kullan
|
|
62468
62581
|
});
|
|
62469
62582
|
const handleExport = t__default.useCallback((format7) => {
|
|
62470
62583
|
if (!enableExport)
|
|
@@ -62613,12 +62726,13 @@ var GitHubStarsInternal = ({
|
|
|
62613
62726
|
className: cn("w-full", className),
|
|
62614
62727
|
children: [
|
|
62615
62728
|
renderVariant(),
|
|
62616
|
-
rateLimitInfo && rateLimitInfo.remaining < 10 && /* @__PURE__ */ jsx("div", { className: "mt-4 p-3 bg-yellow-50 dark:bg-yellow-900/20 rounded-md text-sm", children: /* @__PURE__ */ jsxs("p", { className: "text-yellow-800 dark:text-yellow-200", children: [
|
|
62729
|
+
!isDocsMode2 && rateLimitInfo && rateLimitInfo.remaining < 10 && /* @__PURE__ */ jsx("div", { className: "mt-4 p-3 bg-yellow-50 dark:bg-yellow-900/20 rounded-md text-sm", children: /* @__PURE__ */ jsxs("p", { className: "text-yellow-800 dark:text-yellow-200", children: [
|
|
62617
62730
|
"\u26A0\uFE0F Low API rate limit: ",
|
|
62618
62731
|
rateLimitInfo.remaining,
|
|
62619
62732
|
" requests remaining.",
|
|
62620
62733
|
token ? "" : " Consider adding a GitHub token for higher limits."
|
|
62621
|
-
] }) })
|
|
62734
|
+
] }) }),
|
|
62735
|
+
isDocsMode2 && true && /* @__PURE__ */ jsx("div", { className: "mt-2 text-xs text-muted-foreground text-center", children: "\u{1F4DA} Docs Mode: API istekleri optimize edildi" })
|
|
62622
62736
|
]
|
|
62623
62737
|
}
|
|
62624
62738
|
);
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@moontra/moonui-pro",
|
|
3
|
-
"version": "2.18.
|
|
3
|
+
"version": "2.18.4",
|
|
4
4
|
"description": "Premium React components for MoonUI - Advanced UI library with 50+ pro components including performance, interactive, and gesture components",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "dist/index.mjs",
|
|
@@ -3,6 +3,19 @@ import { GitHubRepository, GitHubStats, GitHubActivity, LanguageStats, RateLimit
|
|
|
3
3
|
// Cache management
|
|
4
4
|
const cache = new Map<string, { data: any; timestamp: number; expiresAt: number }>()
|
|
5
5
|
|
|
6
|
+
// Docs mode detection
|
|
7
|
+
const isDocsMode = () => {
|
|
8
|
+
return typeof window !== "undefined" &&
|
|
9
|
+
(window.location.pathname.includes("/docs/") ||
|
|
10
|
+
window.location.pathname.includes("/components/"))
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
// Get cache duration based on mode
|
|
14
|
+
const getCacheDuration = (defaultDuration: number) => {
|
|
15
|
+
// Docs modunda cache süresini 30 dakikaya çıkar
|
|
16
|
+
return isDocsMode() ? 1800000 : defaultDuration // 30 dakika : default
|
|
17
|
+
}
|
|
18
|
+
|
|
6
19
|
// Language colors
|
|
7
20
|
export const LANGUAGE_COLORS: Record<string, string> = {
|
|
8
21
|
JavaScript: "#f7df1e",
|
|
@@ -86,7 +99,7 @@ export async function getRateLimitInfo(token?: string): Promise<RateLimitInfo> {
|
|
|
86
99
|
cache.set(cacheKey, {
|
|
87
100
|
data: rateLimitInfo,
|
|
88
101
|
timestamp: Date.now(),
|
|
89
|
-
expiresAt: Date.now() + 60000, //
|
|
102
|
+
expiresAt: Date.now() + getCacheDuration(60000), // Docs modunda daha uzun cache
|
|
90
103
|
})
|
|
91
104
|
|
|
92
105
|
return rateLimitInfo
|
|
@@ -121,7 +134,7 @@ export async function fetchUserRepositories(
|
|
|
121
134
|
cache.set(cacheKey, {
|
|
122
135
|
data: repos,
|
|
123
136
|
timestamp: Date.now(),
|
|
124
|
-
expiresAt: Date.now() + 300000, //
|
|
137
|
+
expiresAt: Date.now() + getCacheDuration(300000), // Docs modunda 30 dakika
|
|
125
138
|
})
|
|
126
139
|
|
|
127
140
|
return repos
|
|
@@ -146,7 +159,7 @@ export async function fetchRepository(
|
|
|
146
159
|
cache.set(cacheKey, {
|
|
147
160
|
data: repository,
|
|
148
161
|
timestamp: Date.now(),
|
|
149
|
-
expiresAt: Date.now() + 300000, //
|
|
162
|
+
expiresAt: Date.now() + getCacheDuration(300000), // Docs modunda 30 dakika
|
|
150
163
|
})
|
|
151
164
|
|
|
152
165
|
return repository
|
|
@@ -180,7 +193,7 @@ export async function fetchContributorsCount(
|
|
|
180
193
|
cache.set(cacheKey, {
|
|
181
194
|
data: count,
|
|
182
195
|
timestamp: Date.now(),
|
|
183
|
-
expiresAt: Date.now() + 3600000, //
|
|
196
|
+
expiresAt: Date.now() + getCacheDuration(3600000), // Docs modunda 30 dakika
|
|
184
197
|
})
|
|
185
198
|
return count
|
|
186
199
|
}
|
|
@@ -193,7 +206,7 @@ export async function fetchContributorsCount(
|
|
|
193
206
|
cache.set(cacheKey, {
|
|
194
207
|
data: count,
|
|
195
208
|
timestamp: Date.now(),
|
|
196
|
-
expiresAt: Date.now() + 3600000, //
|
|
209
|
+
expiresAt: Date.now() + getCacheDuration(3600000), // Docs modunda 30 dakika
|
|
197
210
|
})
|
|
198
211
|
|
|
199
212
|
return count
|
|
@@ -233,7 +246,7 @@ export async function fetchStarHistory(
|
|
|
233
246
|
cache.set(cacheKey, {
|
|
234
247
|
data: history,
|
|
235
248
|
timestamp: Date.now(),
|
|
236
|
-
expiresAt: Date.now() + 3600000, //
|
|
249
|
+
expiresAt: Date.now() + getCacheDuration(3600000), // Docs modunda 30 dakika
|
|
237
250
|
})
|
|
238
251
|
|
|
239
252
|
return history
|
|
@@ -29,6 +29,9 @@ interface UseGitHubDataOptions {
|
|
|
29
29
|
onDataUpdate?: (stats: GitHubStats) => void
|
|
30
30
|
onMilestoneReached?: (milestone: Milestone) => void
|
|
31
31
|
milestones?: number[]
|
|
32
|
+
// Docs mode optimizasyonları için
|
|
33
|
+
docsMode?: boolean
|
|
34
|
+
mockDataFallback?: boolean
|
|
32
35
|
}
|
|
33
36
|
|
|
34
37
|
export function useGitHubData({
|
|
@@ -44,7 +47,16 @@ export function useGitHubData({
|
|
|
44
47
|
onDataUpdate,
|
|
45
48
|
onMilestoneReached,
|
|
46
49
|
milestones = [10, 50, 100, 500, 1000, 5000, 10000],
|
|
50
|
+
docsMode = false,
|
|
51
|
+
mockDataFallback = true,
|
|
47
52
|
}: UseGitHubDataOptions) {
|
|
53
|
+
// Docs mode tespiti
|
|
54
|
+
const isDocsMode = docsMode || (typeof window !== "undefined" &&
|
|
55
|
+
(window.location.pathname.includes("/docs/") ||
|
|
56
|
+
window.location.pathname.includes("/components/")))
|
|
57
|
+
|
|
58
|
+
// Docs modunda autoRefresh'i devre dışı bırak
|
|
59
|
+
const effectiveAutoRefresh = isDocsMode ? false : autoRefresh
|
|
48
60
|
const [repos, setRepos] = useState<GitHubRepository[]>([])
|
|
49
61
|
const [stats, setStats] = useState<GitHubStats | null>(null)
|
|
50
62
|
const [loading, setLoading] = useState(true)
|
|
@@ -55,7 +67,9 @@ export function useGitHubData({
|
|
|
55
67
|
const refreshTimeoutRef = useRef<NodeJS.Timeout>()
|
|
56
68
|
const previousStarsRef = useRef<Map<string, number>>(new Map())
|
|
57
69
|
const errorCountRef = useRef<number>(0) // Hata sayısını takip et
|
|
58
|
-
const maxErrorCount = 2 //
|
|
70
|
+
const maxErrorCount = isDocsMode ? 1 : 2 // Docs modunda daha az deneme
|
|
71
|
+
const hasInitialFetchedRef = useRef(false) // İlk fetch yapıldı mı?
|
|
72
|
+
const docsDataCacheRef = useRef<GitHubRepository[] | null>(null) // Docs mode cache
|
|
59
73
|
|
|
60
74
|
// checkMilestones fonksiyonunu ref olarak sakla - bu şekilde her render'da yeniden oluşturulmaz
|
|
61
75
|
const milestonesRef = useRef(milestones)
|
|
@@ -93,11 +107,32 @@ export function useGitHubData({
|
|
|
93
107
|
}, []) // Boş dependency array - fonksiyon asla yeniden oluşturulmaz
|
|
94
108
|
|
|
95
109
|
const fetchData = useCallback(async () => {
|
|
110
|
+
// Docs modunda ve daha önce fetch yapıldıysa, cache'den döndür
|
|
111
|
+
if (isDocsMode && hasInitialFetchedRef.current && docsDataCacheRef.current) {
|
|
112
|
+
console.log("[Docs Mode] Returning cached data, skipping API request")
|
|
113
|
+
setRepos(docsDataCacheRef.current)
|
|
114
|
+
const calculatedStats = calculateStats(docsDataCacheRef.current)
|
|
115
|
+
setStats(calculatedStats)
|
|
116
|
+
setLoading(false)
|
|
117
|
+
return
|
|
118
|
+
}
|
|
119
|
+
|
|
96
120
|
// Hata limiti aşıldıysa istek yapma
|
|
97
121
|
if (errorCountRef.current >= maxErrorCount) {
|
|
98
122
|
console.warn("Maximum error count reached. Stopping requests.")
|
|
123
|
+
|
|
124
|
+
// Docs modunda ve mockDataFallback aktifse mock data göster
|
|
125
|
+
if (isDocsMode && mockDataFallback) {
|
|
126
|
+
const mockData = getMockGitHubData(username, repository, repositories)
|
|
127
|
+
setRepos(mockData)
|
|
128
|
+
const calculatedStats = calculateStats(mockData)
|
|
129
|
+
setStats(calculatedStats)
|
|
130
|
+
setError(null)
|
|
131
|
+
} else {
|
|
132
|
+
setError("Maximum retry limit exceeded. Please check your configuration.")
|
|
133
|
+
}
|
|
134
|
+
|
|
99
135
|
setLoading(false)
|
|
100
|
-
setError("Maximum retry limit exceeded. Please check your configuration.")
|
|
101
136
|
return
|
|
102
137
|
}
|
|
103
138
|
|
|
@@ -222,6 +257,12 @@ export function useGitHubData({
|
|
|
222
257
|
setLastUpdated(new Date())
|
|
223
258
|
// Başarılı olduğunda hata sayacını sıfırla
|
|
224
259
|
errorCountRef.current = 0
|
|
260
|
+
|
|
261
|
+
// Docs modunda başarılı veriyi cache'le
|
|
262
|
+
if (isDocsMode) {
|
|
263
|
+
hasInitialFetchedRef.current = true
|
|
264
|
+
docsDataCacheRef.current = enhancedRepos
|
|
265
|
+
}
|
|
225
266
|
} catch (err) {
|
|
226
267
|
const errorMessage = err instanceof Error ? err.message : "Failed to fetch data"
|
|
227
268
|
setError(errorMessage)
|
|
@@ -230,7 +271,17 @@ export function useGitHubData({
|
|
|
230
271
|
errorCountRef.current += 1
|
|
231
272
|
console.error(`GitHub API error (${errorCountRef.current}/${maxErrorCount}):`, errorMessage)
|
|
232
273
|
|
|
233
|
-
|
|
274
|
+
// Docs modunda ve mockDataFallback aktifse mock data göster
|
|
275
|
+
if (isDocsMode && mockDataFallback && !hasInitialFetchedRef.current) {
|
|
276
|
+
console.warn("[Docs Mode] API failed, using mock data")
|
|
277
|
+
const mockData = getMockGitHubData(username, repository, repositories)
|
|
278
|
+
setRepos(mockData)
|
|
279
|
+
const calculatedStats = calculateStats(mockData)
|
|
280
|
+
setStats(calculatedStats)
|
|
281
|
+
setError(null)
|
|
282
|
+
hasInitialFetchedRef.current = true
|
|
283
|
+
docsDataCacheRef.current = mockData
|
|
284
|
+
} else if (onError) {
|
|
234
285
|
onError(err instanceof Error ? err : new Error(errorMessage))
|
|
235
286
|
}
|
|
236
287
|
} finally {
|
|
@@ -246,6 +297,8 @@ export function useGitHubData({
|
|
|
246
297
|
checkMilestones, // Artık stable
|
|
247
298
|
onDataUpdate,
|
|
248
299
|
onError,
|
|
300
|
+
isDocsMode,
|
|
301
|
+
mockDataFallback,
|
|
249
302
|
])
|
|
250
303
|
|
|
251
304
|
// Initial fetch
|
|
@@ -266,7 +319,8 @@ export function useGitHubData({
|
|
|
266
319
|
|
|
267
320
|
// Auto-refresh
|
|
268
321
|
useEffect(() => {
|
|
269
|
-
|
|
322
|
+
// Docs modunda auto-refresh'i tamamen devre dışı bırak
|
|
323
|
+
if (!effectiveAutoRefresh) return
|
|
270
324
|
|
|
271
325
|
const scheduleRefresh = () => {
|
|
272
326
|
refreshTimeoutRef.current = setTimeout(() => {
|
|
@@ -282,9 +336,15 @@ export function useGitHubData({
|
|
|
282
336
|
clearTimeout(refreshTimeoutRef.current)
|
|
283
337
|
}
|
|
284
338
|
}
|
|
285
|
-
}, [
|
|
339
|
+
}, [effectiveAutoRefresh, refreshInterval, fetchData])
|
|
286
340
|
|
|
287
341
|
const refresh = useCallback(() => {
|
|
342
|
+
// Docs modunda refresh'i sınırla
|
|
343
|
+
if (isDocsMode && hasInitialFetchedRef.current) {
|
|
344
|
+
console.warn("[Docs Mode] Refresh disabled after initial fetch")
|
|
345
|
+
return Promise.resolve()
|
|
346
|
+
}
|
|
347
|
+
|
|
288
348
|
// Hata limiti aşıldıysa refresh yapma
|
|
289
349
|
if (errorCountRef.current >= maxErrorCount) {
|
|
290
350
|
console.warn("Cannot refresh: maximum error count reached")
|
|
@@ -293,7 +353,7 @@ export function useGitHubData({
|
|
|
293
353
|
|
|
294
354
|
clearCache()
|
|
295
355
|
return fetchData()
|
|
296
|
-
}, [fetchData])
|
|
356
|
+
}, [fetchData, isDocsMode])
|
|
297
357
|
|
|
298
358
|
return {
|
|
299
359
|
repos,
|
|
@@ -372,4 +432,70 @@ export function useGitHubNotifications(enabled: boolean = true) {
|
|
|
372
432
|
)
|
|
373
433
|
|
|
374
434
|
return { permission, notify }
|
|
435
|
+
}
|
|
436
|
+
|
|
437
|
+
// Mock data generator for docs mode
|
|
438
|
+
function getMockGitHubData(
|
|
439
|
+
username?: string,
|
|
440
|
+
repository?: string,
|
|
441
|
+
repositories?: string[]
|
|
442
|
+
): GitHubRepository[] {
|
|
443
|
+
const defaultRepos: GitHubRepository[] = [
|
|
444
|
+
{
|
|
445
|
+
id: 1,
|
|
446
|
+
name: repository || "awesome-project",
|
|
447
|
+
full_name: `${username || "moonui"}/${repository || "awesome-project"}`,
|
|
448
|
+
description: "An amazing open source project with great features",
|
|
449
|
+
html_url: `https://github.com/${username || "moonui"}/${repository || "awesome-project"}`,
|
|
450
|
+
homepage: "https://awesome-project.dev",
|
|
451
|
+
stargazers_count: 12453,
|
|
452
|
+
watchers_count: 543,
|
|
453
|
+
forks_count: 2341,
|
|
454
|
+
language: "TypeScript",
|
|
455
|
+
topics: ["react", "ui", "components", "typescript"],
|
|
456
|
+
created_at: "2022-01-15T10:30:00Z",
|
|
457
|
+
updated_at: new Date().toISOString(),
|
|
458
|
+
pushed_at: new Date().toISOString(),
|
|
459
|
+
size: 4567,
|
|
460
|
+
open_issues_count: 23,
|
|
461
|
+
license: {
|
|
462
|
+
key: "mit",
|
|
463
|
+
name: "MIT License",
|
|
464
|
+
spdx_id: "MIT",
|
|
465
|
+
url: "https://api.github.com/licenses/mit",
|
|
466
|
+
},
|
|
467
|
+
owner: {
|
|
468
|
+
login: username || "moonui",
|
|
469
|
+
avatar_url: `https://github.com/${username || "moonui"}.png`,
|
|
470
|
+
html_url: `https://github.com/${username || "moonui"}`,
|
|
471
|
+
type: "Organization",
|
|
472
|
+
},
|
|
473
|
+
contributors_count: 89,
|
|
474
|
+
},
|
|
475
|
+
]
|
|
476
|
+
|
|
477
|
+
if (repositories && repositories.length > 0) {
|
|
478
|
+
return repositories.map((repo, index) => {
|
|
479
|
+
const [owner, name] = repo.includes('/') ? repo.split('/') : [username || "moonui", repo]
|
|
480
|
+
return {
|
|
481
|
+
...defaultRepos[0],
|
|
482
|
+
id: index + 1,
|
|
483
|
+
name: name,
|
|
484
|
+
full_name: `${owner}/${name}`,
|
|
485
|
+
html_url: `https://github.com/${owner}/${name}`,
|
|
486
|
+
stargazers_count: Math.floor(Math.random() * 20000) + 1000,
|
|
487
|
+
forks_count: Math.floor(Math.random() * 3000) + 100,
|
|
488
|
+
watchers_count: Math.floor(Math.random() * 1000) + 50,
|
|
489
|
+
language: ["TypeScript", "JavaScript", "Python", "Go", "Rust"][index % 5],
|
|
490
|
+
owner: {
|
|
491
|
+
login: owner,
|
|
492
|
+
avatar_url: `https://github.com/${owner}.png`,
|
|
493
|
+
html_url: `https://github.com/${owner}`,
|
|
494
|
+
type: "Organization",
|
|
495
|
+
},
|
|
496
|
+
}
|
|
497
|
+
})
|
|
498
|
+
}
|
|
499
|
+
|
|
500
|
+
return defaultRepos
|
|
375
501
|
}
|
|
@@ -60,7 +60,16 @@ const GitHubStarsInternal: React.FC<GitHubStarsProps> = ({
|
|
|
60
60
|
size = "md",
|
|
61
61
|
customColors,
|
|
62
62
|
}) => {
|
|
63
|
-
|
|
63
|
+
// Docs mode tespiti
|
|
64
|
+
const isDocsMode = typeof window !== "undefined" &&
|
|
65
|
+
(window.location.pathname.includes("/docs/") ||
|
|
66
|
+
window.location.pathname.includes("/components/"))
|
|
67
|
+
|
|
68
|
+
// Docs modunda bazı özellikleri override et
|
|
69
|
+
const effectiveAutoRefresh = isDocsMode ? false : autoRefresh
|
|
70
|
+
const effectiveNotifications = isDocsMode ? false : enableNotifications
|
|
71
|
+
const effectiveRefreshInterval = isDocsMode ? 3600000 : refreshInterval // Docs modunda 1 saat
|
|
72
|
+
const { notify } = useGitHubNotifications(effectiveNotifications)
|
|
64
73
|
|
|
65
74
|
// onMilestoneReached callback'ini memoize et
|
|
66
75
|
const handleMilestoneReached = React.useCallback((milestone: any) => {
|
|
@@ -96,14 +105,16 @@ const GitHubStarsInternal: React.FC<GitHubStarsProps> = ({
|
|
|
96
105
|
repository,
|
|
97
106
|
repositories,
|
|
98
107
|
token,
|
|
99
|
-
autoRefresh,
|
|
100
|
-
refreshInterval,
|
|
108
|
+
autoRefresh: effectiveAutoRefresh,
|
|
109
|
+
refreshInterval: effectiveRefreshInterval,
|
|
101
110
|
sortBy,
|
|
102
111
|
maxItems,
|
|
103
112
|
onError,
|
|
104
113
|
onDataUpdate,
|
|
105
114
|
onMilestoneReached: handleMilestoneReached,
|
|
106
115
|
milestones,
|
|
116
|
+
docsMode: isDocsMode, // Docs mode flag'ini gönder
|
|
117
|
+
mockDataFallback: true, // Docs modunda mock data kullan
|
|
107
118
|
})
|
|
108
119
|
|
|
109
120
|
const handleExport = React.useCallback((format: "json" | "csv") => {
|
|
@@ -296,8 +307,8 @@ const GitHubStarsInternal: React.FC<GitHubStarsProps> = ({
|
|
|
296
307
|
>
|
|
297
308
|
{renderVariant()}
|
|
298
309
|
|
|
299
|
-
{/* Rate limit warning */}
|
|
300
|
-
{rateLimitInfo && rateLimitInfo.remaining < 10 && (
|
|
310
|
+
{/* Rate limit warning - Docs modunda gösterme */}
|
|
311
|
+
{!isDocsMode && rateLimitInfo && rateLimitInfo.remaining < 10 && (
|
|
301
312
|
<div className="mt-4 p-3 bg-yellow-50 dark:bg-yellow-900/20 rounded-md text-sm">
|
|
302
313
|
<p className="text-yellow-800 dark:text-yellow-200">
|
|
303
314
|
⚠️ Low API rate limit: {rateLimitInfo.remaining} requests remaining.
|
|
@@ -305,6 +316,13 @@ const GitHubStarsInternal: React.FC<GitHubStarsProps> = ({
|
|
|
305
316
|
</p>
|
|
306
317
|
</div>
|
|
307
318
|
)}
|
|
319
|
+
|
|
320
|
+
{/* Docs mode indicator - sadece development modunda göster */}
|
|
321
|
+
{isDocsMode && process.env.NODE_ENV === "development" && (
|
|
322
|
+
<div className="mt-2 text-xs text-muted-foreground text-center">
|
|
323
|
+
📚 Docs Mode: API istekleri optimize edildi
|
|
324
|
+
</div>
|
|
325
|
+
)}
|
|
308
326
|
</motion.div>
|
|
309
327
|
)
|
|
310
328
|
}
|