mirror of
https://github.com/pawelmalak/snippet-box.git
synced 2025-12-21 21:33:10 +01:00
Various changes to support authentication
This commit is contained in:
5
client/package-lock.json
generated
5
client/package-lock.json
generated
@@ -9927,6 +9927,11 @@
|
|||||||
"object.assign": "^4.1.2"
|
"object.assign": "^4.1.2"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"jwt-decode": {
|
||||||
|
"version": "3.1.2",
|
||||||
|
"resolved": "https://registry.npmjs.org/jwt-decode/-/jwt-decode-3.1.2.tgz",
|
||||||
|
"integrity": "sha512-UfpWE/VZn0iP50d8cz9NrZLM9lSWhcJ+0Gt/nm4by88UL+J1SiKN8/5dkjMmbEzwL2CAe+67GsegCbIKtbp75A=="
|
||||||
|
},
|
||||||
"killable": {
|
"killable": {
|
||||||
"version": "1.0.1",
|
"version": "1.0.1",
|
||||||
"resolved": "https://registry.npmjs.org/killable/-/killable-1.0.1.tgz",
|
"resolved": "https://registry.npmjs.org/killable/-/killable-1.0.1.tgz",
|
||||||
|
|||||||
@@ -15,6 +15,7 @@
|
|||||||
"clipboard-copy": "^4.0.1",
|
"clipboard-copy": "^4.0.1",
|
||||||
"dayjs": "^1.10.7",
|
"dayjs": "^1.10.7",
|
||||||
"highlight.js": "^11.2.0",
|
"highlight.js": "^11.2.0",
|
||||||
|
"jwt-decode": "^3.1.2",
|
||||||
"node-sass": "^6.0.1",
|
"node-sass": "^6.0.1",
|
||||||
"react": "^17.0.2",
|
"react": "^17.0.2",
|
||||||
"react-dom": "^17.0.2",
|
"react-dom": "^17.0.2",
|
||||||
|
|||||||
@@ -35,7 +35,7 @@ export const SnippetForm = (props: Props): JSX.Element => {
|
|||||||
setFormData({ ...currentSnippet });
|
setFormData({ ...currentSnippet });
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}, [currentSnippet]);
|
}, [currentSnippet, inEdit]);
|
||||||
|
|
||||||
const inputHandler = (
|
const inputHandler = (
|
||||||
e: ChangeEvent<HTMLInputElement | HTMLTextAreaElement>
|
e: ChangeEvent<HTMLInputElement | HTMLTextAreaElement>
|
||||||
|
|||||||
@@ -5,10 +5,12 @@ import { SnippetGrid } from '../components/Snippets/SnippetGrid';
|
|||||||
import { SearchBar } from '../components/SearchBar';
|
import { SearchBar } from '../components/SearchBar';
|
||||||
|
|
||||||
export const Home = (): JSX.Element => {
|
export const Home = (): JSX.Element => {
|
||||||
const { snippets, getSnippets, searchResults } = useContext(SnippetsContext);
|
const { snippets, getSnippets, searchResults, countTags } =
|
||||||
|
useContext(SnippetsContext);
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
getSnippets();
|
getSnippets();
|
||||||
|
countTags();
|
||||||
}, []);
|
}, []);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
|
|||||||
@@ -1,10 +1,11 @@
|
|||||||
import { Fragment, useContext } from 'react';
|
import { Fragment, useContext } from 'react';
|
||||||
import { AuthContext } from '../store';
|
import { AuthContext, SnippetsContext } from '../store';
|
||||||
import { Button, Card, Layout } from '../components/UI';
|
import { Button, Card, Layout } from '../components/UI';
|
||||||
import { dateParser } from '../utils';
|
import { dateParser } from '../utils';
|
||||||
|
|
||||||
export const Profile = (): JSX.Element => {
|
export const Profile = (): JSX.Element => {
|
||||||
const { user, logout } = useContext(AuthContext);
|
const { user, logout } = useContext(AuthContext);
|
||||||
|
const { clearOnLogout } = useContext(SnippetsContext);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Layout>
|
<Layout>
|
||||||
@@ -39,7 +40,10 @@ export const Profile = (): JSX.Element => {
|
|||||||
color='secondary'
|
color='secondary'
|
||||||
outline
|
outline
|
||||||
small
|
small
|
||||||
handler={logout}
|
handler={() => {
|
||||||
|
logout();
|
||||||
|
clearOnLogout();
|
||||||
|
}}
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
</Fragment>
|
</Fragment>
|
||||||
|
|||||||
@@ -20,7 +20,8 @@ export const SnippetsContext = createContext<SnippetsContextInterface>({
|
|||||||
deleteSnippet: (id: number) => {},
|
deleteSnippet: (id: number) => {},
|
||||||
toggleSnippetPin: (id: number) => {},
|
toggleSnippetPin: (id: number) => {},
|
||||||
countTags: () => {},
|
countTags: () => {},
|
||||||
searchSnippets: (query: SearchQuery) => {}
|
searchSnippets: (query: SearchQuery) => {},
|
||||||
|
clearOnLogout: () => {}
|
||||||
});
|
});
|
||||||
|
|
||||||
export const AuthContext = createContext<AuthContextInterface>({
|
export const AuthContext = createContext<AuthContextInterface>({
|
||||||
|
|||||||
@@ -40,14 +40,12 @@ export const SnippetsContextProvider = (props: Props): JSX.Element => {
|
|||||||
await getSnippetByIdAction({ id, setCurrentSnippet });
|
await getSnippetByIdAction({ id, setCurrentSnippet });
|
||||||
};
|
};
|
||||||
|
|
||||||
const setSnippet = async (id: number) => {
|
const setSnippet = (id: number) => {
|
||||||
if (id < 0) {
|
if (id < 0) {
|
||||||
setCurrentSnippet(null);
|
setCurrentSnippet(null);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
await getSnippetById(id);
|
|
||||||
|
|
||||||
const snippet = snippets.find(s => s.id === id);
|
const snippet = snippets.find(s => s.id === id);
|
||||||
|
|
||||||
if (snippet) {
|
if (snippet) {
|
||||||
@@ -117,6 +115,12 @@ export const SnippetsContextProvider = (props: Props): JSX.Element => {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const clearOnLogout = () => {
|
||||||
|
setCurrentSnippet(null);
|
||||||
|
setTagCount([]);
|
||||||
|
setSnippets([]);
|
||||||
|
};
|
||||||
|
|
||||||
const context: Context = {
|
const context: Context = {
|
||||||
snippets,
|
snippets,
|
||||||
searchResults,
|
searchResults,
|
||||||
@@ -130,7 +134,8 @@ export const SnippetsContextProvider = (props: Props): JSX.Element => {
|
|||||||
deleteSnippet,
|
deleteSnippet,
|
||||||
toggleSnippetPin,
|
toggleSnippetPin,
|
||||||
countTags,
|
countTags,
|
||||||
searchSnippets
|
searchSnippets,
|
||||||
|
clearOnLogout
|
||||||
};
|
};
|
||||||
|
|
||||||
return (
|
return (
|
||||||
|
|||||||
@@ -14,6 +14,7 @@ export interface SnippetsContext {
|
|||||||
toggleSnippetPin: (id: number) => void;
|
toggleSnippetPin: (id: number) => void;
|
||||||
countTags: () => void;
|
countTags: () => void;
|
||||||
searchSnippets: (query: SearchQuery) => void;
|
searchSnippets: (query: SearchQuery) => void;
|
||||||
|
clearOnLogout: () => void;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface AuthContext {
|
export interface AuthContext {
|
||||||
|
|||||||
5
client/src/typescript/interfaces/Token.ts
Normal file
5
client/src/typescript/interfaces/Token.ts
Normal file
@@ -0,0 +1,5 @@
|
|||||||
|
export interface Token {
|
||||||
|
email: string;
|
||||||
|
iat: number;
|
||||||
|
exp: number;
|
||||||
|
}
|
||||||
@@ -6,3 +6,4 @@ export * from './Context';
|
|||||||
export * from './Statistics';
|
export * from './Statistics';
|
||||||
export * from './SearchQuery';
|
export * from './SearchQuery';
|
||||||
export * from './User';
|
export * from './User';
|
||||||
|
export * from './Token';
|
||||||
|
|||||||
7
client/src/utils/decodeToken.ts
Normal file
7
client/src/utils/decodeToken.ts
Normal file
@@ -0,0 +1,7 @@
|
|||||||
|
import jwt_decode from 'jwt-decode';
|
||||||
|
import { Token } from '../typescript/interfaces';
|
||||||
|
|
||||||
|
export const decodeToken = (token: string): Token => {
|
||||||
|
const decoded: Token = jwt_decode(token);
|
||||||
|
return decoded;
|
||||||
|
};
|
||||||
Reference in New Issue
Block a user