App.js 18.41 KiB
import React from 'react';
import FourButtons from './Components/FourButtons';
import { Dialog } from 'react-overlay-pack';
import CorrectSign from './material/sign_correct.png';
import ErrorSign from './material/sign_error.png';
import ElementDisplay from './Components/ElementDisplay';
function App() {
/* Activate Hooks */
const { useState } = React;
/* Initializing Hooks for component values showed in main page */
const [queryStr, setQueryStr] = useState('')
const [sign, setSign] = useState(CorrectSign)
const [text, setText] = useState('This area shows the result of requests..')
const [formState, setFormState] = useState('hide')
const [dialogState, setDialogState] = useState(false)
const [renderState, setRenderState] = useState(false)
/* initializing form-like input of bookData for PUT and POST */
const [bookURLState, setBookURLState] = useState('')
const [bookTitleState, setBookTitleState] = useState('')
const [bookIDState, setBookIDState] = useState('')
const [bookISBNState, setBookISBNState] = useState('')
const [bookAuthorState, setBookAuthorState] = useState('')
const [bookAuthorURLState, setBookAuthorURLState] = useState('')
const [bookRatingState, setBookRatingState] = useState('')
const [bookRatingCountState, setBookRatingCountState] = useState('')
const [bookReviewCountState, setBookReviewCountState] = useState('')
const [bookImageURLState, setBookImageURLState] = useState('')
const [bookSimilarBooksState, setBookSimilarBooksState] = useState('')
/* Initializing form-like input of authorData for PUT AND POST */
const [authorNameState, setAuthorNameState] = useState('')
const [authorURLState, setAuthorURLState] = useState('')
const [authorIDState, setAuthorIDState] = useState('')
const [authorRatingState, setAuthorRatingState] = useState('')
const [authorRatingCountState, setAuthorRatingCountState] = useState('')
const [authorReviewCountState, setAuthorReviewCountState] = useState('')
const [authorImageURLState, setAuthorImageURLState] = useState('')
const [authorRelatedAuthorsState, setAuthorRelatedAuthorsState] = useState('')
const [authorAuthorBooksState, setAuthorAuthorBooksState] = useState('')
/* Hooks used to show whether the data passed in is bookData or authorData */
const [dataState, setDataState] = useState({})
/* Activating axios */
const axios = require('axios').default;
var center = {display: 'flex', justifyContent: 'center', alignItems: 'center'}
/** Function used to hide the input form */
function hideForm() {
setFormState('hide')
}
/** Function used to show bookData input form */
function changeFormStateBook() {
setRenderState(false)
if (formState === 'hide') {
setFormState('showBook')
} else {
setFormState('hide')
}
}
/** Function used to show authorData input form */
function changeFormStateAuthor() {
setRenderState(false)
if (formState === 'hide') {
setFormState('showAuthor')
} else {
setFormState('hide')
}
}
/** Function used to set Dialog visible, which is called when a response is received */
function showDialog() {
setDialogState(true)
}
/** Function used in GET Requests */
function get() {
axios.get('http://127.0.0.1:5000/api/' + queryStr)
.then(function (response) {
// handle success
setSign(CorrectSign)
showDialog()
document.getElementById('dialog').value = response.status + ":\n" + response.statusText
if (queryStr.includes('book')) {
setDataState(response.data['books'])
} else {
setDataState(response.data['authors'])
}
setRenderState(true)
})
.catch(function (error) {
// handle error
setSign(ErrorSign)
showDialog()
document.getElementById('dialog').value = error //.response.status + ":\n" + error.response.statusText
})
}
/** Function used in PUT and POST: extract user input of bookData from the form and parse into JSON */
function createJson() {
var bookData = {}
bookData.type = 'book'
/* Set corresponding value if the input is not empty */
if(bookURLState !== '') {bookData.book_url = bookURLState}
if(bookTitleState !== '') {bookData.title = bookTitleState}
if(bookIDState !== '') {bookData.id = bookIDState}
if(bookISBNState !== '') {bookData.ISBN = bookISBNState}
if(bookAuthorURLState !== '') {bookData.author_url = bookAuthorURLState}
if(bookAuthorState !== '') {bookData.author = bookAuthorState}
if(bookRatingState !== '') {bookData.rating = parseFloat(bookRatingState)}
if(bookRatingCountState !== '') {bookData.rating_count = parseInt(bookRatingCountState)}
if(bookReviewCountState !== '') {bookData.review_count = parseInt(bookReviewCountState)}
if(bookSimilarBooksState !== '') {bookData.similar_books = bookSimilarBooksState.split(', ')}
setDataState(bookData)
return bookData
}
/** Function used in PUT and POST: extract user input of authorData from the form and parse into JSON */
function createJsonAuthor() {
var authorData = {}
authorData.type = 'author'
/* Set corresponding value if the input is not empty */
if(authorNameState !== '') {authorData.name = authorNameState}
if(authorURLState !== '') {authorData.author_url = authorURLState}
if(authorIDState !== '') {authorData.id = authorIDState}
if(authorRatingState !== '') {authorData.rating = parseFloat(authorRatingState)}
if(authorRatingCountState !== '') {authorData.rating_count = parseInt(authorRatingCountState)}
if(authorReviewCountState !== '') {authorData.review_count = parseInt(authorReviewCountState)}
if(authorImageURLState !== '') {authorData.image_url = authorImageURLState}
if(authorRelatedAuthorsState !== '') {authorData.related_authors = authorRelatedAuthorsState.split(', ')}
if(authorAuthorBooksState !== '') {authorData.author_books = authorAuthorBooksState.split(',')}
setDataState(authorData)
return authorData
}
/** Function used in PUT requests */
function put() {
setRenderState(false)
hideForm()
var data;
if (queryStr.includes('book')) {
data = createJson()
} else {
data = createJsonAuthor()
}
let config = {
headers: {
'Content-Type': 'application/json',
}
}
axios.put('http://127.0.0.1:5000/api/' + queryStr, data, config)
.then(function (response) {
// handle success
setSign(CorrectSign)
showDialog()
document.getElementById('dialog').value = response.status + ":\n" + response.statusText
})
.catch(function (error) {
// handle error
setSign(ErrorSign)
showDialog()
document.getElementById('dialog').value = error //.response.status + ":\n" + error.response.statusText
})
}
/** Function used in POST requests */
function post() {
setRenderState(false)
let config = {
headers: {
'Content-Type': 'application/json',
}
}
hideForm()
var data;
if (queryStr.includes('book')) {
data = createJson()
} else {
data = createJsonAuthor()
}
axios.post('http://127.0.0.1:5000/api/' + queryStr, JSON.stringify(data), config)
.then(function (response) {
// handle success
setSign(CorrectSign)
showDialog()
document.getElementById('dialog').value = response.status + ":\n" + response.statusText
})
.catch(function (error) {
// handle error
setSign(ErrorSign);
showDialog();
document.getElementById('dialog').value = error //.response.status + ":\n" + error.response.statusText
})
}
/** Function used in DELETE requests */
function delete_data() {
setRenderState(false)
axios.delete('http://127.0.0.1:5000/api/' + queryStr)
.then(function (response) {
// handle success
setSign(CorrectSign)
showDialog()
document.getElementById('dialog').value = response.status + ":\n" + response.statusText
})
.catch(function (error) {
// handle error
setSign(ErrorSign)
showDialog()
document.getElementById('dialog').value = error //.response.status + ":\n" + error.response.statusText
})
}
/** HTML code */
return (
<div>
{/* Dialog used when received response from server */}
{dialogState === true &&
<Dialog //Warning, not responsive!
show={dialogState}
onOutsideClick={() => setDialogState(false)}>
<div style={{marginTop:'20%'}}>
<div style={{
marginLeft: '35%'
}}>
<img alt='responseStatus' src={sign}/>
</div>
<div>
<textarea id='dialog'
readOnly={true}
rows="3"
cols="38"
style={{
border:'2px solid silver',
backgroundColor: 'white',
fontSize: '200%',
margin: '50px'
}}>
{text}
</textarea>
</div>
</div>
</Dialog>}
<h1 style={center}>
Welcome to the home page of GoodReads Crawler! </h1>
<h3 style={center}> Please input your query string:</h3>
<div style={center}>
<input
id='queryString'
type='text'
placeholder='example: book/?id=12345678'
size='40'
value={queryStr}
onChange={(e) => setQueryStr(e.target.value)}
/>
</div>
<h3 style={center}> Please input your data for uploading (only effective for POST and PUT):</h3>
{/* Buttons used to select book or author data to be passed to PUT/POST */}
{formState === 'hide' &&
<div style={center}>
<button style={{width:60}} onClick={changeFormStateBook}>
book
</button>
<button style={{marginLeft:10, width:60}} onClick={changeFormStateAuthor}>
author
</button>
</div>}
{/* Form-like input for bookData */}
{formState === 'showBook' &&
<form style={{border:'2px solid silver', marginLeft:'180px', marginRight: '180px'}}>
<div style={center}>
<input id='bookURL' style={center} type='text' size='40' value={bookURLState} placeholder='bookURL' onChange={(e) => setBookURLState(e.target.value)}/>
</div>
<div style={center}>
<input id='bookTtile' style={center} type='text' size='40' value={bookTitleState} placeholder='bookTtile' onChange={(e) => setBookTitleState(e.target.value)}/>
</div>
<div style={center}>
<input id='bookID' type='text' size='40' value={bookIDState} placeholder='bookID' onChange={(e) => setBookIDState(e.target.value)}/>
</div>
<div style={center}>
<input id='bookISBN' type='text' size='40' value={bookISBNState} placeholder='bookISBN' onChange={(e) => setBookISBNState(e.target.value)}/>
</div>
<div style={center}>
<input id='bookAuthorURL' type='text' size='40' value={bookAuthorURLState} placeholder='bookAuthorURL' onChange={(e) => setBookAuthorURLState(e.target.value)}/>
</div>
<div style={center}>
<input id='bookAuthor' type='text' size='40' value={bookAuthorState} placeholder='bookAuthor' onChange={(e) => setBookAuthorState(e.target.value)}/>
</div>
<div style={center}>
<input id='bookRating' type='text' size='40' value={bookRatingState} placeholder='bookRating' onChange={(e) => setBookRatingState(e.target.value)}/>
</div>
<div style={center}>
<input id='bookRatingCount' type='text' size='40' value={bookRatingCountState} placeholder='bookRatingCount' onChange={(e) => setBookRatingCountState(e.target.value)}/>
</div>
<div style={center}>
<input id='bookReviewCount' type='text' size='40' value={bookReviewCountState} placeholder='bookReviewCount' onChange={(e) => setBookReviewCountState(e.target.value)}/>
</div>
<div style={center}>
<input id='bookImageURL' type='text' size='40' value={bookImageURLState} placeholder='bookImageURL' onChange={(e) => setBookImageURLState(e.target.value)}/>
</div>
<div style={center}>
<input id='bookSimilarBooks' type='text' size='40' value={bookSimilarBooksState} placeholder='bookSimilarBooks' onChange={(e) => setBookSimilarBooksState(e.target.value)}/>
</div>
</form>
}
{/* Form-like input for authorData */}
{formState === 'showAuthor' &&
<form style={{border:'2px solid silver', marginLeft:'180px', marginRight: '180px'}}>
<div style={center}>
<input id='authorName' style={center} type='text' size='40' value={authorNameState} placeholder='authorName' onChange={(e) => setAuthorNameState(e.target.value)}/>
</div>
<div style={center}>
<input id='authorURL' style={center} type='text' size='40' value={authorURLState} placeholder='authorURL' onChange={(e) => setAuthorURLState(e.target.value)}/>
</div>
<div style={center}>
<input id='authorID' type='text' size='40' value={authorIDState} placeholder='authorID' onChange={(e) => setAuthorIDState(e.target.value)}/>
</div>
<div style={center}>
<input id='authorRating' type='text' size='40' value={authorRatingState} placeholder='authorRating' onChange={(e) => setAuthorRatingState(e.target.value)}/>
</div>
<div style={center}>
<input id='authorRatingCount' type='text' size='40' value={authorRatingCountState} placeholder='authorRatingCount' onChange={(e) => setAuthorRatingCountState(e.target.value)}/>
</div>
<div style={center}>
<input id='authorReviewCount' type='text' size='40' value={authorReviewCountState} placeholder='authorReviewCount' onChange={(e) => setAuthorReviewCountState(e.target.value)}/>
</div>
<div style={center}>
<input id='authorImageURL' type='text' size='40' value={authorImageURLState} placeholder='authorImageURL' onChange={(e) => setAuthorImageURLState(e.target.value)}/>
</div>
<div style={center}>
<input id='authorRelatedAuthors' type='text' size='40' value={authorRelatedAuthorsState} placeholder='authorRelatedAuthors' onChange={(e) => setAuthorRelatedAuthorsState(e.target.value)}/>
</div>
<div style={center}>
<input id='authorBooks' type='text' size='40' value={authorAuthorBooksState} placeholder='authorBooks' onChange={(e) => setAuthorAuthorBooksState(e.target.value)}/>
</div>
</form>
}
{formState !== 'hide' &&
<button style={{marginLeft:600, width:60}} onClick={hideForm}> back </button>
}
<div style={{marginTop:20, display: 'flex', justifyContent: 'center', alignItems: 'center'}}>
{/* Fout buttons for GET PUT POST and DELETE */}
<FourButtons
backColor='blue'
borderColor='RoyalBlue'
leftMargin={0}
text='GET'
func={get} />
<FourButtons
backColor='black'
borderColor='gray'
leftMargin={20}
text='PUT'
func={put} />
<FourButtons
backColor='green'
borderColor='seagreen'
leftMargin={20}
text='POST'
func={post} />
<FourButtons
backColor='red'
borderColor='indianred'
leftMargin={20}
text='DELETE'
func={delete_data} />
</div>
{renderState === true &&
<div>
{/* Data Table used to render response json data */}
<ElementDisplay data={dataState}/>
</div>}
</div>
);
}
export default App;