Skip to content

Commit 1963fa2

Browse files
authored
feat/error-handling-browser (#22)
* feat: Add error handling for expected browser errors * chore: update gitignore with .claude/ directory * docs: add pull request and commit convention documentation * chore: bump version to 0.1.12
1 parent 6e95894 commit 1963fa2

File tree

5 files changed

+131
-1
lines changed

5 files changed

+131
-1
lines changed

.gitignore

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,6 @@
1+
# Agent
2+
.claude/
3+
14
# docs, notes
25
.hidden/
36
repomix.config.json
Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,41 @@
1+
# Commit Convention
2+
3+
## Format
4+
5+
```
6+
<type>(<scope>): <description>
7+
```
8+
9+
## Types
10+
11+
| Type | Description |
12+
|------|-------------|
13+
| `feat` | New feature |
14+
| `fix` | Bug fix |
15+
| `docs` | Documentation only |
16+
| `refactor` | Code refactoring (no feature/fix) |
17+
| `perf` | Performance improvement |
18+
| `test` | Add or update tests |
19+
| `chore` | Build, dependencies, configs |
20+
21+
## Scope (optional)
22+
23+
Component or area affected: `popup`, `background`, `content`, `options`, `ui`, `db`, etc.
24+
25+
## Examples
26+
27+
```bash
28+
feat(popup): add time tracking chart
29+
fix(background): resolve memory leak in timer
30+
refactor: migrate to composition API
31+
docs: update README installation steps
32+
perf(db): optimize query performance
33+
chore: update dependencies
34+
```
35+
36+
## Rules
37+
38+
1. Use lowercase
39+
2. No period at the end
40+
3. Use imperative mood ("add" not "added")
41+
4. Keep under 72 characters
Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
# Pull Request Convention
2+
3+
## Branch Naming
4+
5+
```
6+
<type>/<short-description>
7+
```
8+
9+
Examples:
10+
- `feat/dark-mode`
11+
- `fix/timer-accuracy`
12+
- `refactor/state-management`
13+
14+
## PR Title
15+
16+
Same format as commit messages:
17+
18+
```
19+
<type>(<scope>): <description>
20+
```
21+
22+
## PR Labels
23+
24+
Add one of these labels for auto-generated release notes:
25+
26+
| Label | Use for |
27+
|-------|---------|
28+
| `enhancement` or `feature` | New features |
29+
| `bug` or `fix` | Bug fixes |
30+
| `performance` | Performance improvements |
31+
| `documentation` | Documentation updates |
32+
33+
## PR Body Template
34+
35+
```markdown
36+
## Summary
37+
- Brief description of changes
38+
39+
## Type
40+
<!-- Add label: enhancement, bug, documentation, performance -->
41+
42+
## Changes
43+
- Change 1
44+
- Change 2
45+
46+
## Test
47+
- [ ] Tested locally
48+
```
49+
50+
## Workflow
51+
52+
1. Create feature branch: `git checkout -b feat/xxx`
53+
2. Make commits following commit convention
54+
3. Push: `git push -u origin HEAD`
55+
4. Create PR on GitHub
56+
5. Add appropriate label
57+
6. Request review if needed
58+
7. Merge to main

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
"name": "lumin-time",
33
"description": "LuminTime is a privacy-first browser extension that automatically tracks your online activity and labels it intelligently.",
44
"private": true,
5-
"version": "0.1.1",
5+
"version": "0.1.12",
66
"type": "module",
77
"scripts": {
88
"dev": "wxt",

src/entrypoints/background.ts

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ import { SessionManager, type ActiveSessionData } from "@/utils/SessionManager";
55
import { debugTools } from "@/utils/debugTools";
66

77
const IDLE_DETECTION_INTERVAL = 30;
8+
89
const SESSION_TICK_ALARM_NAME = "session-update";
910
const SESSION_PER_MINUTE = 1;
1011

@@ -18,6 +19,17 @@ const sessionStorage = storage.defineItem<ActiveSessionData>("session:activeSess
1819
},
1920
});
2021

22+
const isExpectedBrowserError = (error: unknown): boolean => {
23+
if (!(error instanceof Error)) return false;
24+
const msg = error.message;
25+
return (
26+
msg.includes("No tab with id") ||
27+
msg.includes("No window with id") ||
28+
msg.includes("No last-focused window") ||
29+
msg.includes("Tabs cannot be edited")
30+
);
31+
};
32+
2133
const getActiveTabUrl = async () => {
2234
const tabs = await browser.tabs.query({ active: true, currentWindow: true });
2335
if (tabs.length === 0) {
@@ -70,6 +82,10 @@ export default defineBackground(() => {
7082
eventSource: "tab_activated",
7183
});
7284
} catch (error) {
85+
if (isExpectedBrowserError(error)) {
86+
console.debug("[TabActivated] Tab unavailable:", error);
87+
return;
88+
}
7389
console.error("Failed to handle tab activation:", error);
7490
}
7591
})();
@@ -95,6 +111,10 @@ export default defineBackground(() => {
95111
eventSource: "navigation",
96112
});
97113
} catch (error) {
114+
if (isExpectedBrowserError(error)) {
115+
console.debug("[Navigation] Tab/window unavailable:", error);
116+
return;
117+
}
98118
console.error(`Failed to process navigation to ${details.url}:`, error);
99119
}
100120
})();
@@ -116,6 +136,10 @@ export default defineBackground(() => {
116136
});
117137
}
118138
} catch (error) {
139+
if (isExpectedBrowserError(error)) {
140+
console.debug("[WindowFocus] Window unavailable:", error);
141+
return;
142+
}
119143
console.error("Failed to process window focus change:", error);
120144
}
121145
})();
@@ -148,6 +172,10 @@ export default defineBackground(() => {
148172
sessionManager.handleEvent("idle", { url: null });
149173
}
150174
} catch (error) {
175+
if (isExpectedBrowserError(error)) {
176+
console.debug("[IdleState] Browser state unavailable:", error);
177+
return;
178+
}
151179
console.error("Failed to handle idle state change:", error);
152180
}
153181
})();

0 commit comments

Comments
 (0)