Components Imported to have a nice Navbar

This commit is contained in:
Luis Fernando Molina committed 2018-09-04 09:23:55 +02:00
1 parent 2f9a881275
commit 61896e7162
15 files changed
+415 -3

No files matched your search

+103
View File
@@ -635,6 +635,15 @@
"resolved": "https://registry.npmjs.org/aws4/-/aws4-1.8.0.tgz",
"integrity": "sha512-ReZxvNHIOv88FlT7rxcXIIC0fPt4KZqZbOlivyWtXLt8ESx84zd3kMC6iK5jVeS2qt+g7ftS7ye4fi06X5rtRQ=="
},
"axios": {
"version": "0.18.0",
"resolved": "http://registry.npmjs.org/axios/-/axios-0.18.0.tgz",
"integrity": "sha1-MtU+SFHv3AoRmTts0AB4nXDAUQI=",
"requires": {
"follow-redirects": "1.5.7",
"is-buffer": "1.1.6"
}
},
"axobject-query": {
"version": "0.1.0",
"resolved": "https://registry.npmjs.org/axobject-query/-/axobject-query-0.1.0.tgz",
@@ -5051,6 +5060,28 @@
"resolved": "https://registry.npmjs.org/he/-/he-1.1.1.tgz",
"integrity": "sha1-k0EP0hsAlzUVH4howvJx80J+I/0="
},
"history": {
"version": "4.7.2",
"resolved": "https://registry.npmjs.org/history/-/history-4.7.2.tgz",
"integrity": "sha512-1zkBRWW6XweO0NBcjiphtVJVsIQ+SXF29z9DVkceeaSLVMFXHool+fdCZD4spDCfZJCILPILc3bm7Bc+HRi0nA==",
"requires": {
"invariant": "2.2.4",
"loose-envify": "1.4.0",
"resolve-pathname": "2.2.0",
"value-equal": "0.4.0",
"warning": "3.0.0"
},
"dependencies": {
"warning": {
"version": "3.0.0",
"resolved": "https://registry.npmjs.org/warning/-/warning-3.0.0.tgz",
"integrity": "sha1-MuU3fLVy3kqwR1O9+IIcAe1gW3w=",
"requires": {
"loose-envify": "1.4.0"
}
}
}
},
"hmac-drbg": {
"version": "1.0.1",
"resolved": "https://registry.npmjs.org/hmac-drbg/-/hmac-drbg-1.0.1.tgz",
@@ -6430,6 +6461,11 @@
"resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.10.tgz",
"integrity": "sha512-UejweD1pDoXu+AD825lWwp4ZGtSwgnpZxb3JDViD7StjQz+Nb/6l093lx4OQ0foGWNRoc19mWy7BzL+UAK2iVg=="
},
"lodash-es": {
"version": "4.17.10",
"resolved": "https://registry.npmjs.org/lodash-es/-/lodash-es-4.17.10.tgz",
"integrity": "sha512-iesFYPmxYYGTcmQK0sL8bX3TGHyM6b2qREaB4kamHfQyfPJP0xgoGxp19nsH16nsfquLdiyKyX3mQkfiSGV8Rg=="
},
"lodash._reinterpolate": {
"version": "3.0.0",
"resolved": "https://registry.npmjs.org/lodash._reinterpolate/-/lodash._reinterpolate-3.0.0.tgz",
@@ -8932,6 +8968,46 @@
"resolved": "https://registry.npmjs.org/react-error-overlay/-/react-error-overlay-4.0.1.tgz",
"integrity": "sha512-xXUbDAZkU08aAkjtUvldqbvI04ogv+a1XdHxvYuHPYKIVk/42BIOD0zSKTHAWV4+gDy3yGm283z2072rA2gdtw=="
},
"react-redux": {
"version": "5.0.7",
"resolved": "https://registry.npmjs.org/react-redux/-/react-redux-5.0.7.tgz",
"integrity": "sha512-5VI8EV5hdgNgyjfmWzBbdrqUkrVRKlyTKk1sGH3jzM2M2Mhj/seQgPXaz6gVAj2lz/nz688AdTqMO18Lr24Zhg==",
"requires": {
"hoist-non-react-statics": "2.5.5",
"invariant": "2.2.4",
"lodash": "4.17.10",
"lodash-es": "4.17.10",
"loose-envify": "1.4.0",
"prop-types": "15.6.2"
}
},
"react-router": {
"version": "4.3.1",
"resolved": "https://registry.npmjs.org/react-router/-/react-router-4.3.1.tgz",
"integrity": "sha512-yrvL8AogDh2X42Dt9iknk4wF4V8bWREPirFfS9gLU1huk6qK41sg7Z/1S81jjTrGHxa3B8R3J6xIkDAA6CVarg==",
"requires": {
"history": "4.7.2",
"hoist-non-react-statics": "2.5.5",
"invariant": "2.2.4",
"loose-envify": "1.4.0",
"path-to-regexp": "1.7.0",
"prop-types": "15.6.2",
"warning": "4.0.2"
}
},
"react-router-dom": {
"version": "4.3.1",
"resolved": "https://registry.npmjs.org/react-router-dom/-/react-router-dom-4.3.1.tgz",
"integrity": "sha512-c/MlywfxDdCp7EnB7YfPMOfMD3tOtIjrQlj/CKfNMBxdmpJP8xcz5P/UAFn3JbnQCNUxsHyVVqllF9LhgVyFCA==",
"requires": {
"history": "4.7.2",
"invariant": "2.2.4",
"loose-envify": "1.4.0",
"prop-types": "15.6.2",
"react-router": "4.3.1",
"warning": "4.0.2"
}
},
"react-scripts": {
"version": "1.1.5",
"resolved": "https://registry.npmjs.org/react-scripts/-/react-scripts-1.1.5.tgz",
@@ -9096,6 +9172,15 @@
}
}
},
"redux": {
"version": "4.0.0",
"resolved": "https://registry.npmjs.org/redux/-/redux-4.0.0.tgz",
"integrity": "sha512-NnnHF0h0WVE/hXyrB6OlX67LYRuaf/rJcbWvnHHEPCF/Xa/AZpwhs/20WyqzQae5x4SD2F9nPObgBh2rxAgLiA==",
"requires": {
"loose-envify": "1.4.0",
"symbol-observable": "1.2.0"
}
},
"regenerate": {
"version": "1.4.0",
"resolved": "https://registry.npmjs.org/regenerate/-/regenerate-1.4.0.tgz",
@@ -9320,6 +9405,11 @@
"resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-1.0.1.tgz",
"integrity": "sha1-Jsv+k10a7uq7Kbw/5a6wHpPUQiY="
},
"resolve-pathname": {
"version": "2.2.0",
"resolved": "https://registry.npmjs.org/resolve-pathname/-/resolve-pathname-2.2.0.tgz",
"integrity": "sha512-bAFz9ld18RzJfddgrO2e/0S2O81710++chRMUxHjXOYKF6jTAMrUNZrEZ1PvV0zlhfjidm08iRPdTLPno1FuRg=="
},
"resolve-url": {
"version": "0.2.1",
"resolved": "https://registry.npmjs.org/resolve-url/-/resolve-url-0.2.1.tgz",
@@ -10651,6 +10741,11 @@
"spdx-expression-parse": "3.0.0"
}
},
"value-equal": {
"version": "0.4.0",
"resolved": "https://registry.npmjs.org/value-equal/-/value-equal-0.4.0.tgz",
"integrity": "sha512-x+cYdNnaA3CxvMaTX0INdTCN8m8aF2uY9BvEqmxuYp8bL09cs/kWVQPVGcA35fMktdOsP69IgU7wFj/61dJHEw=="
},
"vary": {
"version": "1.1.2",
"resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz",
@@ -10687,6 +10782,14 @@
"makeerror": "1.0.11"
}
},
"warning": {
"version": "4.0.2",
"resolved": "https://registry.npmjs.org/warning/-/warning-4.0.2.tgz",
"integrity": "sha512-wbTp09q/9C+jJn4KKJfJfoS6VleK/Dti0yqWSm6KMvJ4MRCXFQNapHuJXutJIrWV0Cf4AhTdeIe4qdKHR1+Hug==",
"requires": {
"loose-envify": "1.4.0"
}
},
"watch": {
"version": "0.10.0",
"resolved": "https://registry.npmjs.org/watch/-/watch-0.10.0.tgz",
+5 -1
View File
@@ -4,11 +4,15 @@
"private": true,
"dependencies": {
"apollo-boost": "^0.1.15",
"axios": "^0.18.0",
"graphql": "^14.0.0",
"react": "^16.4.2",
"react-apollo": "^2.1.11",
"react-dom": "^16.4.2",
"react-scripts": "1.1.5"
"react-redux": "^5.0.7",
"react-router-dom": "^4.3.1",
"react-scripts": "1.1.5",
"redux": "^4.0.0"
},
"scripts": {
"start": "react-scripts start",
+6
View File
@@ -19,6 +19,12 @@
work correctly both with client-side routing and a non-root public URL.
Learn how to configure a non-root public URL by running `npm run build`.
-->
<!-- font awesome -->
<link rel="stylesheet" href="https://use.fontawesome.com/releases/v5.0.13/css/all.css" integrity="sha384-DNOHZ68U8hZfKXOrtjWvjxusGo9WQnrNx2sqG0tfsghAvtVlRW3tvkXWZh58N9jp" crossorigin="anonymous">
<!--Import Google Icon Font-->
<link href="https://fonts.googleapis.com/icon?family=Material+Icons" rel="stylesheet">
<!-- Compiled and minified CSS -->
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/materialize/1.0.0-beta/css/materialize.min.css">
<title>React App</title>
</head>
<body>
+7
View File
@@ -2,6 +2,13 @@ import React, { Component } from 'react';
import ApolloClient from 'apollo-boost';
import {ApolloProvider} from 'react-apollo';
import Navbar from './components/Navbar'
import { Route, BrowserRouter, Switch } from 'react-router-dom'
import Home from './components/Home'
import About from './components/About'
import Contact from './components/Contact'
import Post from './components/Post'
// Components
import UserList from './components/UserList';
+6
View File
@@ -0,0 +1,6 @@
export const deletePost = (id) => {
return {
type: 'DELETE_POST',
id
}
}
+14
View File
@@ -0,0 +1,14 @@
import React from 'react'
const About = () => {
return (
<div>
<div className="container">
<h4 className="center">About</h4>
<p>Lorem ipsum dolor sit amet consectetur adipisicing elit. Recusandae repudiandae repellat illo magni eligendi cupiditate voluptates eius nam voluptate. Incidunt nihil ullam quae quia officia quaerat, deserunt eligendi explicabo totam?</p>
</div>
</div>
)
}
export default About
+14
View File
@@ -0,0 +1,14 @@
import React from 'react'
const Contact = () => {
return (
<div>
<div className="container">
<h4 className="center">Contact</h4>
<p>Lorem ipsum dolor sit amet consectetur adipisicing elit. Recusandae repudiandae repellat illo magni eligendi cupiditate voluptates eius nam voluptate. Incidunt nihil ullam quae quia officia quaerat, deserunt eligendi explicabo totam?</p>
</div>
</div>
)
}
export default Contact
+44
View File
@@ -0,0 +1,44 @@
import React, { Component } from 'react'
import { Link } from 'react-router-dom'
import Pokeball from '../pokeball.png'
import { connect } from 'react-redux'
class Home extends Component {
render(){
const { posts } = this.props
const postList = posts.length ? (
posts.map(post => {
return (
<div className="post card" key={post.id}>
<img src={Pokeball} alt="A Pokeball" />
<div className="card-content">
<Link to={'/' + post.id}>
<span className="card-title red-text">{post.title}</span>
</Link>
<p>{post.body}</p>
</div>
</div>
)
})
) : (
<div className="center">No posts to show</div>
);
return (
<div>
<div className="container home">
<h4 className="center">Home</h4>
{postList}
</div>
</div>
)
}
}
const mapStateToProps = (state) => {
return {
posts: state.posts
}
}
export default connect(mapStateToProps)(Home)
+19
View File
@@ -0,0 +1,19 @@
import React from 'react';
import { Link, NavLink, withRouter } from 'react-router-dom'
const Navbar = (props) => {
return (
<nav className="nav-wrapper red darken-3">
<div className="container">
<Link className="brand-logo" to="/">Poke' Times</Link>
<ul className="right">
<li><NavLink exact to="/">Home</NavLink></li>
<li><NavLink to='/about'>About</NavLink></li>
<li><NavLink to='/contact'>Contact</NavLink></li>
</ul>
</div>
</nav>
)
}
export default withRouter(Navbar)
+47
View File
@@ -0,0 +1,47 @@
import React, { Component } from 'react'
import { connect } from 'react-redux'
import { deletePost } from '../actions/postActions'
class Post extends Component {
handleClick = () => {
this.props.deletePost(this.props.post.id);
this.props.history.push('/');
}
render() {
const post = this.props.post ? (
<div className="post">
<h4 className="center">{this.props.post.title}</h4>
<p>{this.props.post.body}</p>
<div className="center">
<button className="btn grey" onClick={this.handleClick}>
Delete Post
</button>
</div>
</div>
) : (
<div className="center">Loading post...</div>
);
return (
<div className="container">
{post}
</div>
)
}
}
const mapStateToProps = (state, ownProps) => {
let id = ownProps.match.params.post_id;
return {
post: state.posts.find(post => post.id === id)
}
}
const mapDispatchToProps = (dispatch) => {
return {
deletePost: (id) => dispatch(deletePost(id))
}
}
export default connect(mapStateToProps, mapDispatchToProps)(Post)
+11 -1
View File
@@ -2,7 +2,16 @@ import React, { Component } from 'react';
import {graphql} from 'react-apollo';
import {getUsersQuery} from '../queries/queries';
// components
import UserProfile from './UserProfile';
class UserList extends Component {
constructor(props){
super(props);
this.state = {
selected: null
}
}
displayUsers(){
let data = this.props.data;
@@ -11,7 +20,7 @@ class UserList extends Component {
} else {
return data.users.map(user => {
return (
<li key={user.id}>{user.alias}</li>
<li id="user-list-li" key={user.id} onClick={ (e) => {this.setState({ selected: user.id})}} >{user.alias}</li>
)
});
}
@@ -22,6 +31,7 @@ class UserList extends Component {
<ul id='user-list'>
{this.displayUsers()}
</ul>
<UserProfile userId={this.state.selected}/>
</div>
);
}
+41
View File
@@ -0,0 +1,41 @@
import React, { Component } from 'react';
import {graphql} from 'react-apollo';
import {getUserProfileQuery} from '../queries/queries';
class UserProfile extends Component {
displayUserProfile(){
const {user} = this.props.data;
console.log(user);
if(user){
return(
<div id="user-profile">
<h2>{ user.alias }</h2>
<p>{ user.firstName }</p>
<p>{ user.lastName }</p>
<p>{ user.role.name }</p>
</div>
);
} else {
return( <div>No User selected...</div> );
}
}
render() {
return (
<div>
{this.displayUserProfile()}
</div>
);
}
}
export default graphql(getUserProfileQuery, { // What follows is the way to pass a parameter to a query.
options: (props) => {
return {
variables: {
id: props.userId
}
}
}
})(UserProfile); // This binds the querty to the component
+82
View File
@@ -2,3 +2,85 @@ body {
background: #eee;
font-family: "Arial";
}
#main h1{
color:#444;
text-align: center;
}
#main{
padding: 0px;
box-sizing: border-box;
width: 60%;
height: 100%;
}
#user-list{
color: black;
padding: 0;
}
#user-list-li{
color: pink;
display: inline-block;
margin: 12px;
padding: 10px;
border-radius: 4px;
border: 1px solid #889E4F;
box-shadow: 1px 2px 3px rgba(0,0,0,3);
cursor: pointer;
color: #880E4F;
}
form{
background: #fff;
padding: 20px;
position: fixed;
left: 0;
bottom: 0;
width: 50%;
}
form .field{
display: grid;
grid-template-columns: 1fr 1fr;
grid-gap: 10px;
}
form label{
text-align: right;
padding: 6px;
}
form input, form select{
margin: 4px 0;
padding: 6px;
box-sizing: border-box;
}
form button{
color: #fff;
font-size: 2em;
background: #AD1457;
border: 0;
padding: 0 10px;
border-radius: 50%;
cursor: pointer;
position: absolute;
bottom: 10px;
left: 10px;
}
#user-profile{
position: fixed;
top: 0;
right: 0;
width: 40%;
height: 100%;
background: #AD1457;
padding: 30px;
overflow: auto;
box-shadow: -2px -3px 5px rgba(0,0,0,0.3);
box-sizing: border-box;
color: #fff;
}
Binary file not shown.

After

Width:  |  Height:  |  Size: 16 KiB

+16 -1
View File
@@ -11,6 +11,21 @@ const getUsersQuery = gql`
}
}
`
const getUserProfileQuery = gql`
query($id: ID){
user (id: $id){
id
alias
firstName
lastName
role {
name
}
}
}
`
const getRolesQuery = gql`
{
roles {
@@ -28,4 +43,4 @@ mutation($alias: String!, $firstName:String, $lastName:String, $roleId:String!)
}
}
`
export {getUsersQuery, getRolesQuery, addUserMutation}
export {getUsersQuery, getRolesQuery, addUserMutation, getUserProfileQuery}