Skip to content

Commit b2b1cde

Browse files
committed
added download file
1 parent 3a6c483 commit b2b1cde

File tree

15 files changed

+690
-258
lines changed

15 files changed

+690
-258
lines changed

.gitignore

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,3 +35,6 @@ yarn-error.log*
3535

3636
# typescript
3737
*.tsbuildinfo
38+
39+
# vscode configs
40+
.vscode

README.md

Lines changed: 0 additions & 34 deletions
This file was deleted.

package.json

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,13 +8,22 @@
88
"lint": "next lint"
99
},
1010
"dependencies": {
11+
"axios": "^0.24.0",
12+
"mime-types": "^2.1.34",
1113
"next": "12.0.4",
1214
"react": "17.0.2",
13-
"react-dom": "17.0.2"
15+
"react-dom": "17.0.2",
16+
"react-dropzone": "^11.4.2",
17+
"react-feather": "^2.0.9",
18+
"react-spinners": "^0.11.0",
19+
"react-toastify": "^8.1.0",
20+
"styled-components": "^5.3.3"
1421
},
1522
"devDependencies": {
23+
"@types/mime-types": "^2.1.1",
1624
"@types/node": "16.11.9",
1725
"@types/react": "17.0.35",
26+
"@types/styled-components": "^5.1.15",
1827
"eslint": "7",
1928
"eslint-config-next": "12.0.4",
2029
"typescript": "4.5.2"

pages/_app.tsx

Lines changed: 10 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,13 @@
1-
import '../styles/globals.css'
1+
import '../styles/defaultStyles.css';
22
import type { AppProps } from 'next/app'
3+
import { ToastContainer } from 'react-toastify';
4+
import 'react-toastify/dist/ReactToastify.css';
35

4-
function MyApp({ Component, pageProps }: AppProps) {
5-
return <Component {...pageProps} />
6+
export default function MyApp({ Component, pageProps }: AppProps) {
7+
return (
8+
<>
9+
<ToastContainer />
10+
<Component {...pageProps} />
11+
</>
12+
);
613
}
7-
8-
export default MyApp

pages/_document.tsx

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
import Document from 'next/document'
2+
import { ServerStyleSheet } from 'styled-components'
3+
4+
export default class MyDocument extends Document {
5+
static async getInitialProps(ctx:any) {
6+
const sheet = new ServerStyleSheet()
7+
const originalRenderPage = ctx.renderPage
8+
9+
try {
10+
ctx.renderPage = () =>
11+
originalRenderPage({
12+
enhanceApp: (App:any) => (props:any) =>
13+
sheet.collectStyles(<App {...props} />),
14+
})
15+
16+
const initialProps = await Document.getInitialProps(ctx);
17+
return {
18+
...initialProps,
19+
styles: (
20+
<>
21+
{initialProps.styles}
22+
{sheet.getStyleElement()}
23+
</>
24+
),
25+
}
26+
} finally {
27+
sheet.seal()
28+
}
29+
}
30+
}

pages/api/hello.ts

Lines changed: 0 additions & 13 deletions
This file was deleted.

pages/index.tsx

Lines changed: 126 additions & 63 deletions
Original file line numberDiff line numberDiff line change
@@ -1,72 +1,135 @@
1-
import type { NextPage } from 'next'
2-
import Head from 'next/head'
3-
import Image from 'next/image'
4-
import styles from '../styles/Home.module.css'
1+
import {
2+
Container,
3+
Title,
4+
DropzoneSection,
5+
DropzoneInputContainer,
6+
DropzoneFileInput,
7+
DropzoneText,
8+
Footer,
9+
FooterText,
10+
FooterLink,
11+
FooterImageAvatar,
12+
LoaderContainer,
13+
LoadingText,
14+
Table
15+
} from "../styles/homePage";
16+
import { Download, Tool } from "react-feather";
17+
import Dropzone from 'react-dropzone';
18+
import { useEffect, useState } from "react";
19+
import sendFiles from "../utils/sendFiles";
20+
import { RingLoader } from "react-spinners";
21+
import MimeTypes from 'mime-types';
22+
import { useRouter } from "next/dist/client/router";
523

6-
const Home: NextPage = () => {
7-
return (
8-
<div className={styles.container}>
9-
<Head>
10-
<title>Create Next App</title>
11-
<meta name="description" content="Generated by create next app" />
12-
<link rel="icon" href="/favicon.ico" />
13-
</Head>
24+
export default function Home(){
25+
const [files, setFiles] = useState<any>([]);
26+
const [results, setResults] = useState<any>([]);
1427

15-
<main className={styles.main}>
16-
<h1 className={styles.title}>
17-
Welcome to <a href="https://nextjs.org">Next.js!</a>
18-
</h1>
28+
const [loading, setLoading] = useState<boolean>(false);
1929

20-
<p className={styles.description}>
21-
Get started by editing{' '}
22-
<code className={styles.code}>pages/index.tsx</code>
23-
</p>
30+
useEffect(() => {
31+
async function getResultFiles(){
32+
const response = await sendFiles(files);
33+
setResults(response);
34+
setFiles([]);
35+
setLoading(false);
36+
}
2437

25-
<div className={styles.grid}>
26-
<a href="https://nextjs.org/docs" className={styles.card}>
27-
<h2>Documentation &rarr;</h2>
28-
<p>Find in-depth information about Next.js features and API.</p>
29-
</a>
38+
if(files.length >= 1){
39+
setLoading(true);
40+
getResultFiles();
41+
}
42+
}, [files]);
3043

31-
<a href="https://nextjs.org/learn" className={styles.card}>
32-
<h2>Learn &rarr;</h2>
33-
<p>Learn about Next.js in an interactive course with quizzes!</p>
34-
</a>
44+
async function getFile(index:number){
45+
const fileDataUrl = 'data:'+MimeTypes.lookup(results[index].filename)+';base64,'+results[index].file;
3546

36-
<a
37-
href="https://github.com/vercel/next.js/tree/master/examples"
38-
className={styles.card}
39-
>
40-
<h2>Examples &rarr;</h2>
41-
<p>Discover and deploy boilerplate example Next.js projects.</p>
42-
</a>
47+
let downloadElement = document.getElementById('downloadFile');
4348

44-
<a
45-
href="https://vercel.com/new?utm_source=create-next-app&utm_medium=default-template&utm_campaign=create-next-app"
46-
className={styles.card}
47-
>
48-
<h2>Deploy &rarr;</h2>
49-
<p>
50-
Instantly deploy your Next.js site to a public URL with Vercel.
51-
</p>
52-
</a>
53-
</div>
54-
</main>
49+
if(!downloadElement){
50+
const aElement = document.createElement('a')
51+
aElement.setAttribute('href', fileDataUrl);
52+
aElement.setAttribute('download', results[index].filename);
53+
aElement.setAttribute('id', 'downloadFile');
54+
document.body.appendChild(aElement);
55+
downloadElement = document.getElementById('downloadFile');
56+
}
57+
else{
58+
downloadElement.setAttribute('href', fileDataUrl);
59+
downloadElement.setAttribute('download', results[index].filename);
60+
}
61+
62+
downloadElement?.click();
63+
}
5564

56-
<footer className={styles.footer}>
57-
<a
58-
href="https://vercel.com?utm_source=create-next-app&utm_medium=default-template&utm_campaign=create-next-app"
59-
target="_blank"
60-
rel="noopener noreferrer"
61-
>
62-
Powered by{' '}
63-
<span className={styles.logo}>
64-
<Image src="/vercel.svg" alt="Vercel Logo" width={72} height={16} />
65-
</span>
66-
</a>
67-
</footer>
68-
</div>
69-
)
70-
}
65+
function backToStart(){
66+
setResults([]);
67+
setFiles([]);
68+
setLoading(false);
69+
}
7170

72-
export default Home
71+
return(
72+
<Container>
73+
74+
<Title onClick={backToStart}>
75+
<Tool />Metadata Cleaner<Tool />
76+
</Title>
77+
78+
{
79+
loading ? (
80+
<LoaderContainer>
81+
<RingLoader size={150} loading={loading} color="#6B4F4F" />
82+
<LoadingText>Loading...</LoadingText>
83+
</LoaderContainer>
84+
)
85+
: null
86+
}
87+
{
88+
results.length <= 0 && !loading ? (
89+
<Dropzone multiple={true} onDrop={(acceptedFiles:any) => setFiles(acceptedFiles)}>
90+
{({getRootProps, getInputProps}) => (
91+
<DropzoneSection>
92+
<DropzoneInputContainer {...getRootProps()}>
93+
<DropzoneFileInput {...getInputProps()} />
94+
<DropzoneText>Drop or click to insert your files!</DropzoneText>
95+
</DropzoneInputContainer>
96+
</DropzoneSection>
97+
)}
98+
</Dropzone>
99+
): null
100+
}
101+
102+
{
103+
results.length > 0 && !loading ? (
104+
<Table>
105+
<tr>
106+
<th>Filename</th>
107+
<th>Status</th>
108+
<th>Download</th>
109+
</tr>
110+
{ results.map((result:any, index:number) => (
111+
<tr key={index}>
112+
<td>{result.filename}</td>
113+
<td>{result.status}</td>
114+
<td><Download onClick={() => getFile(index)}/></td>
115+
116+
</tr>
117+
)) }
118+
</Table>
119+
) : null
120+
}
121+
122+
123+
<Footer>
124+
<FooterText>
125+
Made by{' '}
126+
<FooterLink href={process.env.NEXT_PUBLIC_GITHUB}>
127+
DPBM
128+
<FooterImageAvatar src={process.env.NEXT_PUBLIC_GITHUB_AVATAR} alt="Dpbm Avatar"/>
129+
</FooterLink>
130+
</FooterText>
131+
</Footer>
132+
133+
</Container>
134+
);
135+
}

public/favicon.ico

-25.3 KB
Binary file not shown.

public/vercel.svg

Lines changed: 0 additions & 4 deletions
This file was deleted.

0 commit comments

Comments
 (0)