Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Kareha & India - Water #29

Open
wants to merge 43 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
43 commits
Select commit Hold shift + click to select a range
47d31a9
working ex of video list
agesak Jan 20, 2021
8e92ddf
Merge pull request #1 from indiakato/kma-videos-router
indiakato Jan 20, 2021
adcc1cc
video title as buttons
agesak Jan 20, 2021
a3d71cc
shows title when selected
agesak Jan 20, 2021
792bb62
added customer page
indiakato Jan 20, 2021
4845ec5
Merge pull request #2 from indiakato/kma-select-video
indiakato Jan 20, 2021
7535d4b
added errorhandling to customers
indiakato Jan 20, 2021
c8e76d6
Merge branch 'master' into customerList
agesak Jan 20, 2021
6aba0a4
Merge pull request #3 from indiakato/customerList
agesak Jan 20, 2021
2dcf1aa
customer link always shows
agesak Jan 20, 2021
370f672
Merge pull request #5 from indiakato/kma-customer-link
indiakato Jan 20, 2021
fa79272
changed order of links/routes with Noam
agesak Jan 21, 2021
c94b2ef
change videos to library
agesak Jan 21, 2021
b178ba5
moved axios calls to App
agesak Jan 21, 2021
545e129
show selected customer
agesak Jan 21, 2021
fe2c3a8
maybe how to checkout?
agesak Jan 21, 2021
e554295
checking out works
agesak Jan 21, 2021
8e69b83
pass customer name and id
agesak Jan 21, 2021
5faed01
Merge pull request #6 from indiakato/kma-select-customer
indiakato Jan 21, 2021
a364550
a nav bar
agesak Jan 21, 2021
2dda531
search functionality working
indiakato Jan 21, 2021
318c693
videos sort of formatted and a customer table
agesak Jan 22, 2021
cf7fed9
formatted customer table
agesak Jan 22, 2021
921e199
unneeded separation
agesak Jan 22, 2021
490217b
alert box when selecting customer/video
agesak Jan 22, 2021
7a48155
remove commenting
agesak Jan 22, 2021
a1528e5
just send id
agesak Jan 22, 2021
daeffdc
Merge pull request #7 from indiakato/kma-styling
indiakato Jan 22, 2021
cbb34a1
Merge branch 'master' into searchFunction
agesak Jan 22, 2021
b56eb16
Merge pull request #8 from indiakato/searchFunction
agesak Jan 22, 2021
c0648cd
button not working
indiakato Jan 22, 2021
f9b4493
format search in nav
agesak Jan 22, 2021
47584d8
only show search bar when click link
agesak Jan 22, 2021
7d6987b
better looking video page
agesak Jan 22, 2021
5124671
remove comments
agesak Jan 22, 2021
0438846
add to library button
indiakato Jan 22, 2021
0c282ce
library
indiakato Jan 22, 2021
f7266ee
Merge branch 'master' into addLibrary
indiakato Jan 22, 2021
13ed6f2
Merge pull request #9 from indiakato/addLibrary
indiakato Jan 22, 2021
bb9fd7a
finished styling
indiakato Jan 22, 2021
0c9b32c
final touches
indiakato Jan 22, 2021
85975d8
added homepage image
indiakato Jan 22, 2021
bf875a6
search link
indiakato Jan 22, 2021
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11,697 changes: 7,519 additions & 4,178 deletions package-lock.json

Large diffs are not rendered by default.

9 changes: 7 additions & 2 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -3,15 +3,20 @@
"version": "0.1.1",
"private": true,
"dependencies": {
"axios": "^0.21.1",
"bootstrap": "^4.6.0",
"moment": "^2.29.1",
"react": "^17.0.1",
"react-bootstrap": "^1.4.3",
"react-dom": "^17.0.1",
"react-router-dom": "^5.2.0",
"react-scripts": "4.0.1"
},
"devDependencies": {
"gh-pages": "^3.1.0",
"@testing-library/jest-dom": "^5.11.9",
"@testing-library/react": "^11.2.3",
"@testing-library/user-event": "^12.6.0"
"@testing-library/user-event": "^12.6.0",
"gh-pages": "^3.1.0"
},
"scripts": {
"start": "PORT=3001 react-scripts start",
Expand Down
22 changes: 21 additions & 1 deletion src/App.css
Original file line number Diff line number Diff line change
Expand Up @@ -7,11 +7,18 @@
height: 80px;
}

.App-header {
.App-header-text {
background-color: #222;
height: 150px;
padding: 20px;
color: white;
text-align: center;
vertical-align: middle;
line-height: 100px;
}

.App-header {
vertical-align: middle;
}

.App-title {
Expand All @@ -26,3 +33,16 @@
from { transform: rotate(0deg); }
to { transform: rotate(360deg); }
}

.Search-bar {
vertical-align: middle;
height: 15px
}

.Video-image {
display: block;
margin-left: auto;
margin-right: auto;
height: 500px;
width: 50%;
}
155 changes: 141 additions & 14 deletions src/App.js
Original file line number Diff line number Diff line change
@@ -1,21 +1,148 @@
import React, { Component } from 'react';
import logo from './logo.svg';
import React, { useEffect, useState } from 'react';
import { BrowserRouter as Router, Link, Route} from 'react-router-dom';
import './App.css';
import Videos from './components/Videos';
import Customers from './components/Customers'
import Videosearch from './components/Videosearch'
import axios from 'axios'
import moment from 'moment'
import videoImage from './IMG_1508.jpeg'

class App extends Component {
render() {
const BASE_URL = 'http://localhost:3000';

const App = () => {

const [selectedVideo, setSelectedVideo] = useState('');
const [selectedCustomer, setSelectedCustomer] = useState('');
const [videos, setVideos] = useState([]);
const [customers, setCustomers] = useState([]);
const [errorMessage, setErrorMessage] = useState([]);


const getDueDate = () => {
const date = new Date()
date.setDate(date.getDate() + 7)
return (moment(date).format('MMM, D YYYY'))
}

const showVideo = (videoTitle) => {
setSelectedVideo(videoTitle)
}

const showCustomer = (customerID) => {
setSelectedCustomer(customerID)
}

const checkOutVideoBtn = () => {
return (
<div className="App">
<header className="App-header">
<img src={logo} className="App-logo" alt="logo" />
<h1 className="App-title">Welcome to React</h1>
</header>
<p className="App-intro">
To get started, edit <code>src/App.js</code> and save to reload.
</p>
</div>
);
<button onClick={checkout} className="btn btn-info">Check Out</button>
)
}



useEffect(() => {
axios.get(BASE_URL + '/videos')
.then((response) => {
const apiVideos = response.data.map((apiVideo) => {
return ({
id: apiVideo.id,
title: apiVideo.title,
overview: apiVideo.overview,
releaseDate: apiVideo.release_date,
imageUrl: apiVideo.image_url,
externalID: apiVideo.externalID
})
})
setVideos(apiVideos)
})
.catch((error) => {
setErrorMessage(error.message)
})
}, [])


useEffect(() => {
axios.get(BASE_URL + '/customers')
.then((response) => {
const apiCustomers = response.data.map((apiCustomer) => {
return ({
id: apiCustomer.id,
name: apiCustomer.name,
registeredAt: apiCustomer.registered_at,
address: apiCustomer.address,
city: apiCustomer.city,
state: apiCustomer.state,
postalCode: apiCustomer.postal_code,
phone: apiCustomer.phone,
accountCredit: apiCustomer.account_credit,
videosCheckedOutCount: apiCustomer.videos_checked_out_count
})
})
setCustomers(apiCustomers)
})
.catch((error) => {
setErrorMessage(error.message)
})
}, [])

const checkout = () => {
axios.post(`${BASE_URL}/rentals/${selectedVideo}/check-out?customer_id=${selectedCustomer}&due_date=${getDueDate()}`)
.then((response) => {
console.log(response)
setErrorMessage(`Movie titled ${selectedVideo} checked out to Customer ID: ${selectedCustomer}`)
})
.catch((error) =>{
setErrorMessage(`Unable to checkout movie titled ${selectedVideo} to Customer ID: ${selectedCustomer}`);
})

}

const videoCustomerShow = () => {

return(<div class="alert alert-primary" role="alert">
<p>{selectedCustomer ? `Selected Customer ID: ${selectedCustomer}` : ''}</p>
<p>{selectedVideo ? `Selected Video Title: ${selectedVideo}` : ''}</p>
{selectedCustomer && selectedVideo ? checkOutVideoBtn() : ''}
</div>)
}




return (
<div>

<Router>
<nav className="navbar navbar-expand-lg navbar-light bg-light">
<span className="navbar-brand">Full Stack Video Store</span>
<button className="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarNavAltMarkup" aria-controls="navbarNavAltMarkup" aria-expanded="false" aria-label="Toggle navigation">
<span className="navbar-toggler-icon"></span>
</button>
<div className="collapse navbar-collapse" id="navbarNavAltMarkup">
<div className="navbar-nav">
<Link to='/' className="nav-item nav-link">Home</Link>
<Link to='/customers' className="nav-item nav-link">Customers</Link>
<Link to='/library' className="nav-item nav-link">Videos</Link>
<Link to='/search' className='nav-item nav-link'>Search</Link>
</div>
</div>
</nav>

{errorMessage ? <div><h2>{errorMessage}</h2></div> : ''}
<Route path='/' render={selectedCustomer || selectedVideo ? videoCustomerShow : ''} />
<Route path='/customers' component={() => <Customers customers={customers} onClickCallback={showCustomer} />}/>
<Route path='/library' component={() => <Videos videos={videos} onClickCallback={showVideo}/>}/>
<Route path='/search' component={() => <Videosearch videos={videos }/>}/>
<Route exact path='/'/>
</Router>
<div className='App-header'>
<h1 className='App-header-text'>Welcome to your Video Store</h1>
</div>
<img className='Video-image' src={videoImage} alt='video store' />
</div>

);
}

export default App;
Binary file added src/IMG_1508.jpeg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
35 changes: 35 additions & 0 deletions src/components/Customer.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
import React from 'react';
import PropTypes from 'prop-types';

const Customer = ({id, name, registeredAt, address, city, state, postalCode, phone, accountCredit, videosCheckedOutCount, onClickCallback}) => {

const onButtonClick = () => {
onClickCallback(id);
}

return(
<tr>
<td>{<button onClick={onButtonClick} className="btn btn-info">Select</button>}</td>
<td>{name}</td>
<td>{registeredAt}</td>
<td>{address} {city}, {state} {postalCode}</td>
<td>{phone}</td>
<td>{accountCredit}</td>
<td>{videosCheckedOutCount}</td>
</tr>
)
}


Customer.propTypes = {
id: PropTypes.number.isRequired,
name: PropTypes.string.isRequired,
registeredAt: PropTypes.string.isRequired,
address: PropTypes.string.isRequired,
city: PropTypes.string.isRequired,
state: PropTypes.string.isRequired,
postalCode: PropTypes.string.isRequired,
videosCheckedOutCount: PropTypes.number.isRequired,
};

export default Customer;
3 changes: 3 additions & 0 deletions src/components/Customers.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
h2 {
margin-left: 20px;
}
46 changes: 46 additions & 0 deletions src/components/Customers.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
import React from 'react'
import PropTypes from 'prop-types'
import Customer from './Customer'
import './Customers.css'

const Customers = ({customers, onClickCallback}) => {

const loadCustomers = () => {
return customers.map((customer) => {
return <Customer id={customer.id} name={customer.name} registeredAt={customer.registeredAt} address={customer.address} city={customer.city} state={customer.state} postalCode={customer.postalCode} phone={customer.phone} accountCredit={customer.accountCredit} videosCheckedOutCount={customer.videosCheckedOutCount} onClickCallback={onClickCallback} key={customer.id}/>
})
}
return(
<div>
<h2>Customers</h2>

<div className="container">
<table className="table">
<thead>
<tr>
<th scope="col"></th>
<th scope="col">Name</th>
<th scope="col">Registered At</th>
<th scope="col">Address</th>
<th scope="col">Phone</th>
<th scope="col">Account Credit</th>
<th scope="col">Videos Checked Out Count</th>
</tr>
</thead>
<tbody>
{loadCustomers()}
</tbody>
</table>
</div>
</div>

)

}

Customers.propTypes = {
customers: PropTypes.array.isRequired,
onClickCallback: PropTypes.func.isRequired
};

export default Customers;
21 changes: 21 additions & 0 deletions src/components/Result.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
import React from 'react'
import PropTypes from 'prop-types'

const Result = (props) => {

return (
<div>
<p >{props.title}</p>
{<button onClick={props.addToLibrary} className="btn btn-info">Add to Library</button>}
</div>
)
}

Result.propTypes = {
title: PropTypes.string,
overview: PropTypes.string,
releaseDate: PropTypes.string,
addToLibrary: PropTypes.func
}

export default Result
5 changes: 5 additions & 0 deletions src/components/Video.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
.card {
margin: 0 auto;
float: none;
margin-bottom: 10px;
}
38 changes: 38 additions & 0 deletions src/components/Video.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
import React from 'react';
import PropTypes from 'prop-types';
import './Video.css'

const Video = ({id, title, overview, releaseDate, imageUrl, externalId, onClickCallback}) => {

const onButtonClick = () => {
onClickCallback(title);
}
return(
<div className="card">
<img className="card-img-top" src={imageUrl} alt={`${title} book cover`}></img>
<div className="card-body">
<div className="d-flex justify-content-between align-items-center mb-3">
<h5 className="card-title">{title}</h5>
<button onClick={onButtonClick} className="btn btn-info">Select Title</button>
</div>
<p className="card-text">Published: {releaseDate}</p>
<p className="card-text">{overview}</p>
</div>
</div>

)

}


Video.propTypes = {
id: PropTypes.number.isRequired,
title: PropTypes.string.isRequired,
overview: PropTypes.string.isRequired,
releaseDate: PropTypes.string.isRequired,
imageUrl: PropTypes.string,
externalID: PropTypes.number,
onClickCallback: PropTypes.func.isRequired
};

export default Video;
Loading