Python Flask
https://flask.palletsprojects.com/en/2.2.x/installation/
Create an environment
C:\flask_dev>py -3 -m venv venv
Activate the environment
C:\flask_dev>venv\Scripts\activate
Install Flask
venv C:\flask_dev>pip install Flask
C:\flask_dev\flaskreact\app.py
Install requirements
Flask-Cors
A Flask extension for handling Cross Origin Resource Sharing (CORS), making cross-origin AJAX possible.
https://pypi.org/project/Flask-Cors/
(venv) PS C:\flask_dev\flaskreact>pip install -U flask-cors
(venv) PS C:\flask_dev\flaskreact>pip install Werkzeug
C:\flask_dev\flaskreact\app.py
#C:\flask_dev\flaskreact\app.py
from flask import Flask, json, request, jsonify
import os
import urllib.request
from werkzeug.utils import secure_filename #pip install Werkzeug
from flask_cors import CORS #ModuleNotFoundError: No module named 'flask_cors' = pip install Flask-Cors
app = Flask(__name__)
CORS(app, supports_credentials=True)
app.secret_key = "caircocoders-ednalan"
UPLOAD_FOLDER = 'static/uploads'
app.config['UPLOAD_FOLDER'] = UPLOAD_FOLDER
app.config['MAX_CONTENT_LENGTH'] = 16 * 1024 * 1024
ALLOWED_EXTENSIONS = set(['txt', 'pdf', 'png', 'jpg', 'jpeg', 'gif'])
def allowed_file(filename):
return '.' in filename and filename.rsplit('.', 1)[1].lower() in ALLOWED_EXTENSIONS
@app.route('/')
def main():
return 'Homepage'
@app.route('/upload', methods=['POST'])
def upload_file():
# check if the post request has the file part
if 'files[]' not in request.files:
resp = jsonify({
"message": 'No file part in the request',
"status": 'failed'
})
resp.status_code = 400
return resp
files = request.files.getlist('files[]')
errors = {}
success = False
for file in files:
if file and allowed_file(file.filename):
filename = secure_filename(file.filename)
file.save(os.path.join(app.config['UPLOAD_FOLDER'], filename))
success = True
else:
resp = jsonify({
"message": 'File type is not allowed',
"status": 'failed'
})
return resp
if success and errors:
errors['message'] = 'File(s) successfully uploaded'
errors['status'] = 'failed'
resp = jsonify(errors)
resp.status_code = 500
return resp
if success:
resp = jsonify({
"message": 'Files successfully uploaded',
"status": 'successs'
})
resp.status_code = 201
return resp
else:
resp = jsonify(errors)
resp.status_code = 500
return resp
if __name__ == '__main__':
app.run(debug=True)
Postman Postman is an API platform for building and using APIs. Postman simplifies each step of the API lifecycle and streamlines collaboration so you can create better APIs—faster.
https://www.postman.com/
upload
Post : http://127.0.0.1:5000/upload
Body - Form-data
Key : files[] - files
Value : select images
Create folder static\uploads
run (venv) C:\flask_dev\flaskreact>flask run
React JS
https://create-react-app.dev/
Create Project
C:\react-js>npx create-react-app myreactdev
Run
C:\react-js\myreactdev> npm start
C:\react-js\myreactdev\src\App.js
//C:\react-js\myreactdev\src\App.js
import React, { Component } from 'react';
import { BrowserRouter as Router, Route, Routes } from 'react-router-dom';
import ImageUpload from './components/ImageUpload';
import './App.css';
class App extends Component {
render() {
return (
<Router>
<Routes>
<Route exact path="/upload-image" element={<ImageUpload/>}/>
</Routes>
</Router>
);
}
}
export default App;
Install React Router Dom https://www.npmjs.com/package/react-router-dom
C:\react-js\myreactdev>npm i react-router-dom --save
Install Axios
https://www.npmjs.com/package/axios
C:\react-js\myreactdev>npm install axios --save
C:\react-js\myreactdev\src\components\ImageUpload.js
//C:\react-js\myreactdev\src\components\ImageUpload.js
import React, { Component } from "react";
import axios from "axios";
export default class ImageUpload extends Component {
constructor(props) {
super(props);
this.state = {
image: "",
responseMsg: {
status: "",
message: "",
error: "",
},
};
}
// image onchange hander
handleChange = (e) => {
const imagesArray = [];
for (let i = 0; i < e.target.files.length; i++) {
this.fileValidate(e.target.files[i]);
imagesArray.push(e.target.files[i]);
}
this.setState({
image: imagesArray,
});
};
// submit handler
submitHandler = (e) => {
e.preventDefault();
const data = new FormData();
for (let i = 0; i < this.state.image.length; i++) {
data.append("files[]", this.state.image[i]);
}
axios.post("http://127.0.0.1:5000/upload", data)
.then((response) => {
console.log(response)
if (response.status === 201) {
this.setState({
responseMsg: {
status: response.data.status,
message: response.data.message,
},
});
setTimeout(() => {
this.setState({
image: "",
responseMsg: "",
});
}, 100000);
document.querySelector("#imageForm").reset();
}
alert("Successfully Uploaded");
})
.catch((error) => {
console.error(error);
if (error.response) {
console.log(error.response)
if (error.response.status === 401) {
alert("Invalid credentials");
}
}
});
};
// file validation
fileValidate = (file) => {
if (
file.type === "image/png" ||
file.type === "image/jpg" ||
file.type === "image/jpeg"
) {
this.setState({
responseMsg: {
error: "",
},
});
return true;
} else {
this.setState({
responseMsg: {
error: "File type allowed only jpg, png, jpeg",
},
});
return false;
}
};
render() {
return (
<div className="container py-5">
<div className="row">
<div className="col-lg-12">
<form onSubmit={this.submitHandler} encType="multipart/form-data" id="imageForm">
<div className="card shadow">
{this.state.responseMsg.status === "successs" ? (
<div className="alert alert-success">
{this.state.responseMsg.message}
</div>
) : this.state.responseMsg.status === "failed" ? (
<div className="alert alert-danger">
{this.state.responseMsg.message}
</div>
) : (
""
)}
<div className="card-header">
<h4 className="card-title fw-bold">
React-JS and Python Flask Multiple Image Upload with validation
</h4>
</div>
<div className="card-body">
<div className="form-group py-2">
<label htmlFor="images">Images</label>
<input
type="file"
name="image"
multiple
onChange={this.handleChange}
className="form-control"
/>
<span className="text-danger">
{this.state.responseMsg.error}
</span>
</div>
</div>
<div className="card-footer">
<button type="submit" className="btn btn-success">
Upload
</button>
</div>
</div>
</form>
</div>
</div>
</div>
);
}
}
react-js\myreactdev\public\index.html
//react-js\myreactdev\public\index.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" />
<link rel="icon" href="%PUBLIC_URL%/favicon.ico" />
<meta name="viewport" content="width=device-width, initial-scale=1" />
<meta name="theme-color" content="#000000" />
<meta
name="description"
content="Web site created using create-react-app"
/>
<link rel="apple-touch-icon" href="%PUBLIC_URL%/logo192.png" />
<link rel="manifest" href="%PUBLIC_URL%/manifest.json" />
<title>React App</title>
<link rel="stylesheet" type="text/css" href="https://cdn.jsdelivr.net/npm/bootstrap@5.0.2/dist/css/bootstrap.min.css"/>
</head>
<body>
<noscript>You need to enable JavaScript to run this app.</noscript>
<div id="root"></div>
</body>
</html>
Run C:\react-j\myreactdev>npm start http://localhost:3000/
