Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commitb8daf6f

Browse files
committed
Refactor storage and options page with improved type safety and GitHub-like styling
- Introduced STORAGE_KEYS constant for consistent key management- Enhanced options page with GitHub-inspired design and color scheme- Improved storage utilities with better error handling and cache management- Added dark mode support for options page- Simplified token validation and storage processes- Implemented more robust cache clearing mechanism
1 parent83d86c7 commitb8daf6f

File tree

6 files changed

+623
-277
lines changed

6 files changed

+623
-277
lines changed

‎src/action.js‎

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,10 @@
11
/* global chrome */
22

3+
/**
4+
* Contributors on GitHub - Browser Extension
5+
* Opens the options page when the extension icon is clicked
6+
*/
7+
38
// Open options page when extension icon is clicked
49
chrome.action.onClicked.addListener(()=>{
510
chrome.runtime.openOptionsPage();

‎src/content.js‎

Lines changed: 66 additions & 45 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
/* global getSyncStorage, setStorage, getStorage,gitHubInjection */
1+
/* global getSyncStorage, setStorage, getStorage,STORAGE_KEYS */
22

33
// Define key selectors as constants for easier maintenance
44
constSELECTORS={
@@ -26,7 +26,7 @@ const ELEMENT_IDS = {
2626

2727
// Configuration constants
2828
constCONFIG={
29-
CACHE_EXPIRATION:7*24*60*60*1000,// 7 days in milliseconds (was 24 hours)
29+
CACHE_EXPIRATION:7*24*60*60*1000,// 7 days in milliseconds
3030
HOVER_DELAY:100,// milliseconds to wait before hiding panel
3131
STAT_PADDING:3,// number of digits to pad stats to
3232
};
@@ -66,7 +66,7 @@ function getPathInfo() {
6666

6767
functionbuildUrl({
6868
base,
69-
q:{ type, filterUser, author, repo, user},
69+
q:{ type, filterUser, author, repo, user, created},
7070
sort,
7171
order,
7272
per_page,
@@ -77,21 +77,22 @@ function buildUrl({
7777
query+=`${user ?`+user:${user}` :""}`;
7878
query+=`${type ?`+type:${type}` :""}`;
7979
query+=`${filterUser ?`+-user:${filterUser}` :""}`;
80+
query+=`${created ?`+created:${created}` :""}`;
8081
query+=`${order ?`&order=${order}` :""}`;
8182
query+=`${per_page ?`&per_page=${per_page}` :""}`;
8283
query+=`${sort ?`&sort=${sort}` :""}`;
8384

8485
returnquery;
8586
}
8687

87-
functioncontributorCount({
88+
asyncfunctioncontributorCount({
8889
access_token,
8990
contributor,
9091
user,
9192
repoPath,
9293
old={},
9394
type,
94-
scope,
95+
scope
9596
}){
9697
letrepo=repoPath;
9798

@@ -108,43 +109,46 @@ function contributorCount({
108109
type,
109110
repo,
110111
author:contributor,
111-
user:user,
112+
user:user
112113
},
113114
sort:"created",
114115
});
115116

116-
returnfetch(searchURL,{
117-
headers:{
118-
Authorization:`token${access_token}`,
119-
},
120-
})
121-
.then((res)=>res.json())
122-
.then((json)=>{
123-
if(json.errors||json.message){
124-
returnjson;
125-
}
117+
try{
118+
constresponse=awaitfetch(searchURL,{
119+
headers:{
120+
Authorization:`token${access_token}`,
121+
},
122+
});
123+
constjson=awaitresponse.json();
126124

127-
letobj={
128-
lastUpdate:Date.now(),
129-
};
125+
if(json.errors||json.message){
126+
returnjson;
127+
}
130128

131-
if(type==="pr"){
132-
obj.prs=json.total_count;
133-
}elseif(type==="issue"){
134-
obj.issues=json.total_count;
135-
}
129+
letobj={
130+
lastUpdate:Date.now()
131+
};
136132

137-
if(json.items?.length){
138-
obj[`first${type[0].toUpperCase()+type.slice(1)}Number`]=
139-
json.items[0].number;
140-
}
133+
if(type==="pr"){
134+
obj.prs=json.total_count;
135+
}elseif(type==="issue"){
136+
obj.issues=json.total_count;
137+
}
141138

142-
obj=Object.assign(old,obj);
139+
if(json.items?.length){
140+
obj[`first${type[0].toUpperCase()+type.slice(1)}Number`]=
141+
json.items[0].number;
142+
}
143143

144-
setStorage(contributor,repoPath,obj);
144+
obj=Object.assign(old,obj);
145145

146-
returnobj;
147-
});
146+
setStorage(contributor,repoPath,obj);
147+
148+
returnobj;
149+
}catch(error){
150+
console.error(error);
151+
}
148152
}
149153

150154
functionformatText(count,firstNumber,currentNum,scope){
@@ -346,16 +350,27 @@ function setupHoverBehavior() {
346350
functionsetupSyncButton({ contributor, repoPath, currentNum, org}){
347351
const$syncButton=document.getElementById(ELEMENT_IDS.SYNC_BUTTON);
348352
$syncButton.addEventListener("click",()=>{
349-
// Clear all stats and fetch fresh data
350-
setStorage(contributor,repoPath,{});
351-
setStorage(contributor,org,{});
352-
setStorage(contributor,"__self",{});
353+
// Clear local cache for this contributor
354+
clearContributorCache(contributor);
353355

354356
// Fetch all scopes
355357
fetchAllStats({ contributor, repoPath, currentNum, org});
356358
});
357359
}
358360

361+
// Clear cache for a specific contributor
362+
functionclearContributorCache(contributor){
363+
try{
364+
for(constkeyofObject.keys(localStorage)){
365+
if(key.startsWith('gce-cache-')&&key.includes(contributor)){
366+
localStorage.removeItem(key);
367+
}
368+
}
369+
}catch(e){
370+
console.error("Error clearing contributor cache:",e);
371+
}
372+
}
373+
359374
// Check if cache is expired
360375
functionisCacheExpired(lastUpdate){
361376
if(!lastUpdate)returntrue;
@@ -457,25 +472,25 @@ function fetchStats({ contributor, repoPath, currentNum, scope, user }) {
457472
updateStatsDisplay({ prText, issueText, scope,lastUpdate:storageRes.lastUpdate});
458473
}else{
459474
// If cache is expired or no data, fetch fresh data
460-
getSyncStorage({access_token:null}).then((res)=>{
475+
getSyncStorage({[STORAGE_KEYS.ACCESS_TOKEN]:null}).then((res)=>{
461476
Promise.all([
462477
contributorCount({
463478
old:storageRes,
464479
user,
465-
access_token:res.access_token,
480+
access_token:res[STORAGE_KEYS.ACCESS_TOKEN],
466481
type:"pr",
467482
contributor,
468483
repoPath,
469-
scope,
484+
scope
470485
}),
471486
contributorCount({
472487
old:storageRes,
473488
user,
474-
access_token:res.access_token,
489+
access_token:res[STORAGE_KEYS.ACCESS_TOKEN],
475490
type:"issue",
476491
contributor,
477492
repoPath,
478-
scope,
493+
scope
479494
}),
480495
])
481496
.then(([prInfo,issueInfo])=>{
@@ -629,9 +644,9 @@ function showToast(message, type = "error") {
629644
// Main initialization function
630645
functioninitializeContributorStats(){
631646
if(isPR(location.pathname)||isIssue(location.pathname)){
632-
getSyncStorage({_showPrivateRepos:null}).then(
633-
({ _showPrivateRepos})=>{
634-
if(!_showPrivateRepos&&isPrivate())return;
647+
getSyncStorage({[STORAGE_KEYS.SHOW_PRIVATE_REPOS]:null}).then(
648+
(result)=>{
649+
if(!result[STORAGE_KEYS.SHOW_PRIVATE_REPOS]&&isPrivate())return;
635650

636651
if(getFirstContributor()){
637652
injectInitialUI(getPathInfo());
@@ -643,5 +658,11 @@ function initializeContributorStats() {
643658

644659
// Initialize when DOM is ready
645660
document.addEventListener("DOMContentLoaded",()=>{
646-
gitHubInjection(initializeContributorStats);
661+
// Check if gitHubInjection is available
662+
if(typeofgitHubInjection==='function'){
663+
gitHubInjection(initializeContributorStats);
664+
}else{
665+
// Fallback to direct initialization
666+
initializeContributorStats();
667+
}
647668
});

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp