summaryrefslogtreecommitdiffstats
path: root/stepped-solutions/42/frontend/components
diff options
context:
space:
mode:
Diffstat (limited to 'stepped-solutions/42/frontend/components')
-rwxr-xr-xstepped-solutions/42/frontend/components/AddToCart.js35
-rwxr-xr-xstepped-solutions/42/frontend/components/Cart.js63
-rwxr-xr-xstepped-solutions/42/frontend/components/CartItem.js41
-rwxr-xr-xstepped-solutions/42/frontend/components/User.js38
4 files changed, 177 insertions, 0 deletions
diff --git a/stepped-solutions/42/frontend/components/AddToCart.js b/stepped-solutions/42/frontend/components/AddToCart.js
new file mode 100755
index 0000000..3e2842b
--- /dev/null
+++ b/stepped-solutions/42/frontend/components/AddToCart.js
@@ -0,0 +1,35 @@
+import React from 'react';
+import { Mutation } from 'react-apollo';
+import gql from 'graphql-tag';
+import { CURRENT_USER_QUERY } from './User';
+
+const ADD_TO_CART_MUTATION = gql`
+ mutation addToCart($id: ID!) {
+ addToCart(id: $id) {
+ id
+ quantity
+ }
+ }
+`;
+
+class AddToCart extends React.Component {
+ render() {
+ const { id } = this.props;
+ return (
+ <Mutation
+ mutation={ADD_TO_CART_MUTATION}
+ variables={{
+ id,
+ }}
+ refetchQueries={[{ query: CURRENT_USER_QUERY }]}
+ >
+ {(addToCart, { loading }) => (
+ <button disabled={loading} onClick={addToCart}>
+ Add{loading && 'ing'} To Cart 🛒
+ </button>
+ )}
+ </Mutation>
+ );
+ }
+}
+export default AddToCart;
diff --git a/stepped-solutions/42/frontend/components/Cart.js b/stepped-solutions/42/frontend/components/Cart.js
new file mode 100755
index 0000000..1895235
--- /dev/null
+++ b/stepped-solutions/42/frontend/components/Cart.js
@@ -0,0 +1,63 @@
+import React from 'react';
+import { Query, Mutation } from 'react-apollo';
+import gql from 'graphql-tag';
+import User from './User';
+import CartStyles from './styles/CartStyles';
+import Supreme from './styles/Supreme';
+import CloseButton from './styles/CloseButton';
+import SickButton from './styles/SickButton';
+import CartItem from './CartItem';
+import calcTotalPrice from '../lib/calcTotalPrice';
+import formatMoney from '../lib/formatMoney';
+
+const LOCAL_STATE_QUERY = gql`
+ query {
+ cartOpen @client
+ }
+`;
+
+const TOGGLE_CART_MUTATION = gql`
+ mutation {
+ toggleCart @client
+ }
+`;
+
+const Cart = () => (
+ <User>
+ {({ data: { me } }) => {
+ if (!me) return null;
+ console.log(me);
+ return (
+ <Mutation mutation={TOGGLE_CART_MUTATION}>
+ {toggleCart => (
+ <Query query={LOCAL_STATE_QUERY}>
+ {({ data }) => (
+ <CartStyles open={data.cartOpen}>
+ <header>
+ <CloseButton onClick={toggleCart} title="close">
+ &times;
+ </CloseButton>
+ <Supreme>{me.name}'s Cart</Supreme>
+ <p>
+ You Have {me.cart.length} Item{me.cart.length === 1 ? '' : 's'} in your cart.
+ </p>
+ </header>
+ <ul>
+ {me.cart.map(cartItem => <CartItem key={cartItem.id} cartItem={cartItem} />)}
+ </ul>
+ <footer>
+ <p>{formatMoney(calcTotalPrice(me.cart))}</p>
+ <SickButton>Checkout</SickButton>
+ </footer>
+ </CartStyles>
+ )}
+ </Query>
+ )}
+ </Mutation>
+ );
+ }}
+ </User>
+);
+
+export default Cart;
+export { LOCAL_STATE_QUERY, TOGGLE_CART_MUTATION };
diff --git a/stepped-solutions/42/frontend/components/CartItem.js b/stepped-solutions/42/frontend/components/CartItem.js
new file mode 100755
index 0000000..8f6a099
--- /dev/null
+++ b/stepped-solutions/42/frontend/components/CartItem.js
@@ -0,0 +1,41 @@
+import React from 'react';
+import styled from 'styled-components';
+import PropTypes from 'prop-types';
+import formatMoney from '../lib/formatMoney';
+
+const CartItemStyles = styled.li`
+ padding: 1rem 0;
+ border-bottom: 1px solid ${props => props.theme.lightgrey};
+ display: grid;
+ align-items: center;
+ grid-template-columns: auto 1fr auto;
+ img {
+ margin-right: 10px;
+ }
+ h3,
+ p {
+ margin: 0;
+ }
+`;
+
+const CartItem = ({ cartItem }) => (
+ <CartItemStyles>
+ <img width="100" src={cartItem.item.image} alt={cartItem.item.title} />
+ <div className="cart-item-details">
+ <h3>{cartItem.item.title}</h3>
+ <p>
+ {formatMoney(cartItem.item.price * cartItem.quantity)}
+ {' - '}
+ <em>
+ {cartItem.quantity} &times; {formatMoney(cartItem.item.price)} each
+ </em>
+ </p>
+ </div>
+ </CartItemStyles>
+);
+
+CartItem.propTypes = {
+ cartItem: PropTypes.object.isRequired,
+};
+
+export default CartItem;
diff --git a/stepped-solutions/42/frontend/components/User.js b/stepped-solutions/42/frontend/components/User.js
new file mode 100755
index 0000000..429bb25
--- /dev/null
+++ b/stepped-solutions/42/frontend/components/User.js
@@ -0,0 +1,38 @@
+import { Query } from 'react-apollo';
+import gql from 'graphql-tag';
+import PropTypes from 'prop-types';
+
+const CURRENT_USER_QUERY = gql`
+ query {
+ me {
+ id
+ email
+ name
+ permissions
+ cart {
+ id
+ quantity
+ item {
+ id
+ price
+ image
+ title
+ description
+ }
+ }
+ }
+ }
+`;
+
+const User = props => (
+ <Query {...props} query={CURRENT_USER_QUERY}>
+ {payload => props.children(payload)}
+ </Query>
+);
+
+User.propTypes = {
+ children: PropTypes.func.isRequired,
+};
+
+export default User;
+export { CURRENT_USER_QUERY };