Skip to content

Commit 6fbc3d2

Browse files
authored
refactor(handlers): icon color and formatted names (#2160)
* refactor: use handler for icon color Signed-off-by: Adam Setch <[email protected]> * refactor: handler enhancements Signed-off-by: Adam Setch <[email protected]> * refactor: handler enhancements Signed-off-by: Adam Setch <[email protected]> * refactor: handler enhancements Signed-off-by: Adam Setch <[email protected]> --------- Signed-off-by: Adam Setch <[email protected]>
1 parent a6fbbca commit 6fbc3d2

32 files changed

+282
-338
lines changed

src/renderer/components/notifications/NotificationRow.tsx

Lines changed: 5 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -8,8 +8,6 @@ import { GroupBy, Opacity, Size } from '../../types';
88
import type { Notification } from '../../typesGitHub';
99
import { cn } from '../../utils/cn';
1010
import { isMarkAsDoneFeatureSupported } from '../../utils/features';
11-
import { formatForDisplay } from '../../utils/helpers';
12-
import { getNotificationTypeIconColor } from '../../utils/icons';
1311
import { openNotification } from '../../utils/links';
1412
import { createNotificationHandler } from '../../utils/notifications/handlers';
1513
import { HoverButton } from '../primitives/HoverButton';
@@ -72,22 +70,11 @@ export const NotificationRow: FC<INotificationRow> = ({
7270
};
7371

7472
const handler = createNotificationHandler(notification);
75-
76-
const NotificationIcon = handler.getIcon(notification.subject);
77-
const iconColor = getNotificationTypeIconColor(notification.subject);
78-
79-
const notificationType = formatForDisplay([
80-
notification.subject.state,
81-
notification.subject.type,
82-
]);
83-
84-
const notificationNumber = notification.subject?.number
85-
? `#${notification.subject.number}`
86-
: '';
87-
88-
const notificationTitle = notificationNumber
89-
? `${notification.subject.title} [${notificationNumber}]`
90-
: notification.subject.title;
73+
const NotificationIcon = handler.iconType(notification.subject);
74+
const iconColor = handler.iconColor(notification.subject);
75+
const notificationType = handler.formattedNotificationType(notification);
76+
const notificationNumber = handler.formattedNotificationNumber(notification);
77+
const notificationTitle = handler.formattedNotificationTitle(notification);
9178

9279
const groupByDate = settings.groupBy === GroupBy.DATE;
9380

src/renderer/components/notifications/__snapshots__/AccountNotifications.test.tsx.snap

Lines changed: 2 additions & 2 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

src/renderer/utils/__snapshots__/icons.test.ts.snap

Lines changed: 0 additions & 30 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

src/renderer/utils/helpers.test.ts

Lines changed: 0 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,6 @@ import {
1616
} from './api/__mocks__/response-mocks';
1717
import * as apiRequests from './api/request';
1818
import {
19-
formatForDisplay,
2019
generateGitHubWebUrl,
2120
generateNotificationReferrerId,
2221
getChevronDetails,
@@ -517,22 +516,6 @@ describe('renderer/utils/helpers.ts', () => {
517516
});
518517
});
519518

520-
describe('formatting', () => {
521-
it('formatForDisplay', () => {
522-
expect(formatForDisplay(null)).toBe('');
523-
expect(formatForDisplay([])).toBe('');
524-
expect(formatForDisplay(['open', 'PullRequest'])).toBe(
525-
'Open Pull Request',
526-
);
527-
expect(formatForDisplay(['OUTDATED', 'Discussion'])).toBe(
528-
'Outdated Discussion',
529-
);
530-
expect(formatForDisplay(['not_planned', 'Issue'])).toBe(
531-
'Not Planned Issue',
532-
);
533-
});
534-
});
535-
536519
describe('getChevronDetails', () => {
537520
it('should return correct chevron details', () => {
538521
expect(getChevronDetails(true, true, 'account')).toEqual({

src/renderer/utils/helpers.ts

Lines changed: 0 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -171,21 +171,6 @@ export async function generateGitHubWebUrl(
171171
return url.toString() as Link;
172172
}
173173

174-
export function formatForDisplay(text: string[]): string {
175-
if (!text) {
176-
return '';
177-
}
178-
179-
return text
180-
.join(' ')
181-
.replace(/([a-z])([A-Z])/g, '$1 $2') // Add space between lowercase character followed by an uppercase character
182-
.replace(/_/g, ' ') // Replace underscores with spaces
183-
.replace(/\w+/g, (word) => {
184-
// Convert to proper case (capitalize first letter of each word)
185-
return word.charAt(0).toUpperCase() + word.slice(1).toLowerCase();
186-
});
187-
}
188-
189174
export function getChevronDetails(
190175
hasNotifications: boolean,
191176
isVisible: boolean,

src/renderer/utils/icons.test.ts

Lines changed: 1 addition & 118 deletions
Original file line numberDiff line numberDiff line change
@@ -8,118 +8,15 @@ import {
88
} from '@primer/octicons-react';
99

1010
import { IconColor } from '../types';
11-
import type {
12-
GitifyPullRequestReview,
13-
StateType,
14-
Subject,
15-
SubjectType,
16-
} from '../typesGitHub';
11+
import type { GitifyPullRequestReview } from '../typesGitHub';
1712
import {
1813
getAuthMethodIcon,
1914
getDefaultUserIcon,
20-
getNotificationTypeIconColor,
2115
getPlatformIcon,
2216
getPullRequestReviewIcon,
2317
} from './icons';
2418

2519
describe('renderer/utils/icons.ts', () => {
26-
describe('getNotificationTypeIconColor', () => {
27-
it('should format the notification color for check suite', () => {
28-
expect(
29-
getNotificationTypeIconColor(
30-
createSubjectMock({
31-
type: 'CheckSuite',
32-
state: 'cancelled',
33-
}),
34-
),
35-
).toMatchSnapshot();
36-
37-
expect(
38-
getNotificationTypeIconColor(
39-
createSubjectMock({
40-
type: 'CheckSuite',
41-
state: 'failure',
42-
}),
43-
),
44-
).toMatchSnapshot();
45-
46-
expect(
47-
getNotificationTypeIconColor(
48-
createSubjectMock({
49-
type: 'CheckSuite',
50-
state: 'skipped',
51-
}),
52-
),
53-
).toMatchSnapshot();
54-
55-
expect(
56-
getNotificationTypeIconColor(
57-
createSubjectMock({
58-
type: 'CheckSuite',
59-
state: 'success',
60-
}),
61-
),
62-
).toMatchSnapshot();
63-
64-
expect(
65-
getNotificationTypeIconColor(
66-
createSubjectMock({
67-
type: 'CheckSuite',
68-
state: null,
69-
}),
70-
),
71-
).toMatchSnapshot();
72-
});
73-
74-
it('should format the notification color for state', () => {
75-
expect(
76-
getNotificationTypeIconColor(createSubjectMock({ state: 'ANSWERED' })),
77-
).toMatchSnapshot();
78-
79-
expect(
80-
getNotificationTypeIconColor(createSubjectMock({ state: 'closed' })),
81-
).toMatchSnapshot();
82-
83-
expect(
84-
getNotificationTypeIconColor(createSubjectMock({ state: 'completed' })),
85-
).toMatchSnapshot();
86-
87-
expect(
88-
getNotificationTypeIconColor(createSubjectMock({ state: 'draft' })),
89-
).toMatchSnapshot();
90-
91-
expect(
92-
getNotificationTypeIconColor(createSubjectMock({ state: 'merged' })),
93-
).toMatchSnapshot();
94-
95-
expect(
96-
getNotificationTypeIconColor(
97-
createSubjectMock({ state: 'not_planned' }),
98-
),
99-
).toMatchSnapshot();
100-
101-
expect(
102-
getNotificationTypeIconColor(createSubjectMock({ state: 'open' })),
103-
).toMatchSnapshot();
104-
105-
expect(
106-
getNotificationTypeIconColor(createSubjectMock({ state: 'reopened' })),
107-
).toMatchSnapshot();
108-
109-
expect(
110-
getNotificationTypeIconColor(createSubjectMock({ state: 'RESOLVED' })),
111-
).toMatchSnapshot();
112-
113-
expect(
114-
getNotificationTypeIconColor(
115-
createSubjectMock({
116-
state: 'something_else_unknown' as StateType,
117-
}),
118-
),
119-
).toMatchSnapshot();
120-
});
121-
});
122-
12320
describe('getPullRequestReviewIcon', () => {
12421
let mockReviewSingleReviewer: GitifyPullRequestReview;
12522
let mockReviewMultipleReviewer: GitifyPullRequestReview;
@@ -235,17 +132,3 @@ describe('renderer/utils/icons.ts', () => {
235132
expect(getDefaultUserIcon('User')).toBe(FeedPersonIcon);
236133
});
237134
});
238-
239-
function createSubjectMock(mocks: {
240-
title?: string;
241-
type?: SubjectType;
242-
state?: StateType;
243-
}): Subject {
244-
return {
245-
title: mocks.title ?? 'Mock Subject',
246-
type: mocks.type ?? ('Unknown' as SubjectType),
247-
state: mocks.state ?? ('Unknown' as StateType),
248-
url: null,
249-
latest_comment_url: null,
250-
};
251-
}

src/renderer/utils/icons.ts

Lines changed: 1 addition & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -15,32 +15,9 @@ import {
1515
} from '@primer/octicons-react';
1616

1717
import { IconColor, type PullRequestApprovalIcon } from '../types';
18-
import type {
19-
GitifyPullRequestReview,
20-
Subject,
21-
UserType,
22-
} from '../typesGitHub';
18+
import type { GitifyPullRequestReview, UserType } from '../typesGitHub';
2319
import type { AuthMethod, PlatformType } from './auth/types';
2420

25-
export function getNotificationTypeIconColor(subject: Subject): IconColor {
26-
switch (subject.state) {
27-
case 'open':
28-
case 'reopened':
29-
case 'ANSWERED':
30-
case 'success':
31-
return IconColor.GREEN;
32-
case 'closed':
33-
case 'failure':
34-
return IconColor.RED;
35-
case 'completed':
36-
case 'RESOLVED':
37-
case 'merged':
38-
return IconColor.PURPLE;
39-
default:
40-
return IconColor.GRAY;
41-
}
42-
}
43-
4421
export function getPullRequestReviewIcon(
4522
review: GitifyPullRequestReview,
4623
): PullRequestApprovalIcon | null {

src/renderer/utils/notifications/handlers/checkSuite.test.ts

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -136,15 +136,15 @@ describe('renderer/utils/notifications/handlers/checkSuite.ts', () => {
136136
});
137137
});
138138

139-
it('getIcon', () => {
139+
it('iconType', () => {
140140
expect(
141-
checkSuiteHandler.getIcon(
141+
checkSuiteHandler.iconType(
142142
createSubjectMock({ type: 'CheckSuite', state: null }),
143143
).displayName,
144144
).toBe('RocketIcon');
145145

146146
expect(
147-
checkSuiteHandler.getIcon(
147+
checkSuiteHandler.iconType(
148148
createSubjectMock({
149149
type: 'CheckSuite',
150150
state: 'cancelled',
@@ -153,7 +153,7 @@ describe('renderer/utils/notifications/handlers/checkSuite.ts', () => {
153153
).toBe('StopIcon');
154154

155155
expect(
156-
checkSuiteHandler.getIcon(
156+
checkSuiteHandler.iconType(
157157
createSubjectMock({
158158
type: 'CheckSuite',
159159
state: 'failure',
@@ -162,7 +162,7 @@ describe('renderer/utils/notifications/handlers/checkSuite.ts', () => {
162162
).toBe('XIcon');
163163

164164
expect(
165-
checkSuiteHandler.getIcon(
165+
checkSuiteHandler.iconType(
166166
createSubjectMock({
167167
type: 'CheckSuite',
168168
state: 'skipped',
@@ -171,7 +171,7 @@ describe('renderer/utils/notifications/handlers/checkSuite.ts', () => {
171171
).toBe('SkipIcon');
172172

173173
expect(
174-
checkSuiteHandler.getIcon(
174+
checkSuiteHandler.iconType(
175175
createSubjectMock({
176176
type: 'CheckSuite',
177177
state: 'success',

src/renderer/utils/notifications/handlers/checkSuite.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -17,9 +17,9 @@ import type {
1717
Notification,
1818
Subject,
1919
} from '../../../typesGitHub';
20-
import type { NotificationTypeHandler } from './types';
20+
import { DefaultHandler } from './default';
2121

22-
class CheckSuiteHandler implements NotificationTypeHandler {
22+
class CheckSuiteHandler extends DefaultHandler {
2323
readonly type = 'CheckSuite';
2424

2525
async enrich(
@@ -38,7 +38,7 @@ class CheckSuiteHandler implements NotificationTypeHandler {
3838
return null;
3939
}
4040

41-
getIcon(subject: Subject): FC<OcticonProps> | null {
41+
iconType(subject: Subject): FC<OcticonProps> | null {
4242
switch (subject.state) {
4343
case 'cancelled':
4444
return StopIcon;

src/renderer/utils/notifications/handlers/commit.test.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -97,9 +97,9 @@ describe('renderer/utils/notifications/handlers/commit.ts', () => {
9797
});
9898
});
9999

100-
it('getIcon', () => {
100+
it('iconType', () => {
101101
expect(
102-
commitHandler.getIcon(createSubjectMock({ type: 'Commit' })).displayName,
102+
commitHandler.iconType(createSubjectMock({ type: 'Commit' })).displayName,
103103
).toBe('GitCommitIcon');
104104
});
105105
});

0 commit comments

Comments
 (0)