Skip to content

Commit 12ca3a9

Browse files
committed
Merge branch 'develop'
2 parents bca557b + 9b3eb1d commit 12ca3a9

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

43 files changed

+750
-266
lines changed

README.md

+10-10
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
<h1>웹 메모</h1>
44
<p>웹 페이지를 읽으며 간편하게 기록하세요</p>
55
<div>
6-
<img src="https://github.com/user-attachments/assets/f6c29e51-30be-462e-9dcb-108af9dd69dd" alt="화면" />
6+
<img src="https://github.com/user-attachments/assets/7cc006e4-846f-4b65-ac27-2dd1b23d449a" alt="화면" />
77
</div>
88
<br />
99
</div>
@@ -33,22 +33,22 @@
3333

3434
## 📝 주요 기능
3535

36-
1. 📝 **메모**: 웹 페이지에서 기록으로 남기고 싶은 내용을 손쉽게 작성할 수 있어요.
37-
2. 📊 **사이드 패널**: 웹 페이지의 화면을 방해하지 않고 분리된 사이드 패널에서 편리하게 기록할 수 있어요
38-
3. 📚 **페이지 요약**: ChatGPT가 웹사이트 내용을 요약해주어 효율적으로 글을 읽을 수 있도록 도와드려요.
39-
4. 🔍 **메모 확인**: 저장한 메모를 웹사이트에서 한눈에 볼 수 있어요.
40-
5. 🔄 **자동 저장**: 작성 중인 메모가 실시간으로 자동저장되요.
41-
6. 단축키 지원 : 사이드 패널을 열고 닫을 때 단축키로 가능해요.
42-
- Windows : alt + s
43-
- MacOS : option + s
36+
1. **메모** : 유튜브 영상을 보다가, 혹은 글을 읽다가 번뜩이는 아이디어가 떠오르면 언제든지 사이드 패널을 열어 기록하세요!
37+
2. **페이지 요약** : ChatGPT가 웹사이트 내용을 요약해주어 효율적으로 글을 읽을 수 있도록 도와드립니다.
38+
3. **메모 확인** : 한 눈에 들어
39+
4. **데이터 영구 저장 및 추출** : 데이터는 손실될 걱정 없이 영구 저장됩니다. 필요에 따라 엑셀 파일로 다운로드하실 수 있습니다.
40+
5. **단축키**
41+
- 사이드 패널을 쉽게 열고 닫을 수 있습니다 : Alt + S / Options + S
42+
- 메모를 손쉽게 저장할 수 있습니다 : Windows + S / Command + S
4443

4544
## 🚨 주의 사항
4645

4746
- 요약 기능의 경우 특정 사이트에서 동작하지 않아요
4847
- e.g. 크롬 웹스토어, 크롬 설정 페이지, 새 탭, PDF파일
4948
- 메모는 모든 사이트에서 가능하답니다.
5049

51-
## 📞 문의
50+
51+
## 📬 소통 창구:
5252

5353
여러분의 의견이 웹 메모를 더 좋게 만들어요. 새로운 기능 제안이나 개선점이 있다면 언제든 알려주세요!
5454

chrome-extension/lib/background/index.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -53,7 +53,7 @@ if (chrome.contextMenus)
5353
chrome.contextMenus.onClicked.addListener(async item => {
5454
switch (item.menuItemId) {
5555
case CONTEXT_MENU_ID_CHECK_MEMO:
56-
await Tab.create({ url: `${WEB_URL}/memo` });
56+
await Tab.create({ url: `${WEB_URL}/memos` });
5757
break;
5858
case CONTEXT_MENU_ID_SHOW_GUIDE:
5959
if (I18n.getUILanguage() === 'ko') Tab.create({ url: URL_GUIDE_KO });

chrome-extension/manifest.js

+1-1
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,7 @@ const manifest = deepmerge(
2222
name: '__MSG_extensionName__',
2323
version: packageJson.version,
2424
description: '__MSG_extensionDescription__',
25-
default_locale: 'en',
25+
default_locale: 'ko',
2626
permissions: ['sidePanel', 'storage', 'tabs', 'contextMenus', 'cookies'],
2727
host_permissions: ['<all_urls>'],
2828
options_page: 'options/index.html',

chrome-extension/public/_locales/ko/messages.json

+2-2
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,9 @@
11
{
22
"extensionDescription": {
3-
"message": "서핑 중 편하게 기록할 수 있도록 돕는 확장 프로그램입니다."
3+
"message": "어시스턴트 & 웹 페이지 요약를 위해 ChatGPT 사용"
44
},
55
"extensionName": {
6-
"message": "웹 메모"
6+
"message": "웹 메모: 웹 어시스턴트 & 웹 페이지 요약"
77
},
88
"no_memo": {
99
"message": "메모가 없습니다."

package.json

+6-2
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
{
2-
"name": "chrome-extension-boilerplate-react-vite",
2+
"name": "web-memo",
33
"version": "1.4.2",
44
"description": "Web Memo - Chrome Extension",
55
"bugs": "https://github.com/guesung/Web-Memo/issues",
@@ -43,10 +43,14 @@
4343
"@tanstack/react-query": "^5.59.0",
4444
"@tanstack/react-query-devtools": "^5.59.0",
4545
"dotenv": "^16.4.5",
46+
"driver.js": "^1.3.1",
47+
"framer-motion": "^11.11.8",
4648
"next": "14.2.10",
4749
"openai": "^4.57.0",
50+
"postcss-import": "^16.1.0",
4851
"react": "18.3.1",
49-
"react-dom": "18.3.1"
52+
"react-dom": "18.3.1",
53+
"react-toastify": "^10.0.6"
5054
},
5155
"devDependencies": {
5256
"@playwright/test": "^1.47.0",

packages/shared/src/hooks/index.ts

+1
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ export { default as useThrottle } from './useThrottle';
55
export { default as useUserPreferDarkMode } from './useUserPreferDarkMode';
66
export { default as useTabQuery } from './useTabQuery';
77
export { default as useMemoPostMutation } from './useMemoPostMutation';
8+
export { default as useMemoPatchMutation } from './useMemoPatchMutation';
89
export { default as useMemoListQuery } from './useMemoListQuery';
910
export { default as useSupabaseClient } from './useSupabaseClient';
1011
export { default as useSupabaseUser } from './useSupabaseUser';
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
import { queryKeys } from '@src/constants';
2+
import { MemoSupabaseClient, MemoSupabaseResponse } from '@src/types';
3+
import { NoMemoError, NoMemoListError, updateMemo, UpdateMemoProps } from '@src/utils';
4+
import { useMutation, UseMutationOptions, useQueryClient } from '@tanstack/react-query';
5+
6+
interface UseMemoPostMutationProps extends UseMutationOptions<MemoSupabaseResponse, Error, UpdateMemoProps> {
7+
supabaseClient: MemoSupabaseClient;
8+
handleSuccess: () => void;
9+
}
10+
11+
export default function useMemoPatchMutation({
12+
supabaseClient,
13+
handleSuccess,
14+
...useMutationProps
15+
}: UseMemoPostMutationProps) {
16+
const queryClient = useQueryClient();
17+
return useMutation<MemoSupabaseResponse, Error, UpdateMemoProps>({
18+
...useMutationProps,
19+
mutationFn: async (updateMemoProps: UpdateMemoProps) => await updateMemo(supabaseClient, updateMemoProps),
20+
onMutate: async currentMemo => {
21+
await queryClient.cancelQueries({ queryKey: queryKeys.memoList() });
22+
const previousMemoList = queryClient.getQueryData<MemoSupabaseResponse>(queryKeys.memoList());
23+
24+
if (!previousMemoList) throw new NoMemoListError();
25+
26+
const { data: previousMemoListData } = previousMemoList;
27+
28+
if (!previousMemoListData) throw new NoMemoListError();
29+
30+
const currentMemoIndex = previousMemoListData.findIndex(memo => memo.id === currentMemo.id);
31+
const currentMemoBase = previousMemoListData.find(memo => memo.id === currentMemo.id);
32+
33+
if (currentMemoIndex === -1 || !currentMemoBase) throw new NoMemoError();
34+
35+
previousMemoListData.splice(currentMemoIndex, 1, { ...currentMemoBase, ...currentMemo });
36+
37+
await queryClient.setQueryData(queryKeys.memoList(), { ...previousMemoList, data: previousMemoListData });
38+
39+
return { previousMemoList };
40+
},
41+
onSuccess: async () => {
42+
handleSuccess();
43+
},
44+
});
45+
}
Original file line numberDiff line numberDiff line change
@@ -1,46 +1,27 @@
11
import { queryKeys } from '@src/constants';
2-
import { MemoSupabaseClient, MemoSupabaseResponse } from '@src/types';
3-
import { formatUrl, insertMemo, updateMemo } from '@src/utils';
4-
import { getSupabaseClient } from '@src/utils/extension';
2+
import { MemoSupabaseClient, MemoSupabaseResponse, MemoTableInsert } from '@src/types';
3+
import { insertMemo } from '@src/utils';
54
import { useMutation, UseMutationOptions, useQueryClient } from '@tanstack/react-query';
6-
import useMemoListQuery from './useMemoListQuery';
75

8-
interface SaveMemoProps {
9-
memo: string;
10-
url: string;
11-
title: string;
12-
category: string;
13-
}
6+
interface PostMemoProps extends MemoTableInsert {}
147

15-
interface UseMemoPostMutationProps extends UseMutationOptions<MemoSupabaseResponse, Error, SaveMemoProps> {
8+
interface UseMemoPostMutationProps extends UseMutationOptions<MemoSupabaseResponse, Error, PostMemoProps> {
169
supabaseClient: MemoSupabaseClient;
17-
handleSettled: () => void;
10+
handleSuccess: () => void;
1811
}
1912

2013
export default function useMemoPostMutation({
2114
supabaseClient,
22-
handleSettled,
15+
handleSuccess,
2316
...useMutationProps
2417
}: UseMemoPostMutationProps) {
2518
const queryClient = useQueryClient();
26-
const { data: memoList } = useMemoListQuery({ supabaseClient });
27-
28-
const saveMemo = async ({ memo, title, url, category }: SaveMemoProps) => {
29-
const currentMemo = memoList?.data?.find(memo => memo.url === formatUrl(url));
30-
const supabaseClient = await getSupabaseClient();
31-
32-
console.log(memo, title, url, category);
33-
34-
if (currentMemo) return await updateMemo(supabaseClient, { ...currentMemo, memo, category });
35-
else return await insertMemo(supabaseClient, { memo, title, url, category });
36-
};
37-
38-
return useMutation<MemoSupabaseResponse, Error, SaveMemoProps>({
19+
return useMutation<MemoSupabaseResponse, Error, PostMemoProps>({
3920
...useMutationProps,
40-
mutationFn: saveMemo,
41-
onSettled: async () => {
21+
mutationFn: async (postMemoProps: PostMemoProps) => await insertMemo(supabaseClient, postMemoProps),
22+
onSuccess: async () => {
4223
queryClient.invalidateQueries({ queryKey: queryKeys.memoList() });
43-
handleSettled();
24+
handleSuccess();
4425
},
4526
});
4627
}

0 commit comments

Comments
 (0)