reza added products and product api

master
RezaAshrafi77 3 years ago
parent 975d787694
commit 1bfe0c3272
  1. 165
      src/AppRouter.js
  2. 31
      src/Redux/actions/book.js
  3. 1
      src/Redux/actions/index.js
  4. 28
      src/Redux/reducers/book.js
  5. 1
      src/Redux/reducers/index.js
  6. 2
      src/Redux/reducers/user.js
  7. 2
      src/views/Auth/Profile/index.js
  8. 253
      src/views/Product/index.js
  9. 1
      src/views/Product/index.scss
  10. 25
      src/views/Products/Product/index.js
  11. 3
      src/views/Products/Product/index.scss
  12. 111
      src/views/Products/index.js
  13. 35
      src/views/QR/Image/index.js
  14. 13
      src/views/QR/Image/index.scss
  15. 7
      src/views/QR/index.js

@ -46,7 +46,7 @@ class AppRouter extends Component {
let home = (
<Route exact path={"/"}>
{proxy.status() ? (
this.props.profile.status ? (
this.props.profile ? (
<Home />
) : (
<Auth page={"profile"} />
@ -62,24 +62,71 @@ class AppRouter extends Component {
<Switch>
{home}
<Route exact path={"/faq"}>
<Faq />
{proxy.status() ? (
<Faq />
) : (
<Redirect
to={{
pathname: "/auth",
}}
/>
)}
</Route>
<Route exact path={"/contact"}>
<Contact />
{proxy.status() ? (
<Contact />
) : (
<Redirect
to={{
pathname: "/auth",
}}
/>
)}
</Route>
<Route exact path={"/about"}>
<About />
{proxy.status() ? (
<About />
) : (
<Redirect
to={{
pathname: "/auth",
}}
/>
)}
</Route>
<Route exact path={"/products"}>
<Products />
{proxy.status() ? (
<Products />
) : (
<Redirect
to={{
pathname: "/auth",
}}
/>
)}
</Route>
<Route exact path={"/products/:id"}>
<Product />
{proxy.status() ? (
<Product />
) : (
<Redirect
to={{
pathname: "/auth",
}}
/>
)}
</Route>
<Route exact path={"/qr"}>
<QR />
{proxy.status() ? (
<QR />
) : (
<Redirect
to={{
pathname: "/auth",
}}
/>
)}
</Route>
<Route exact path={"/auth"}>
<Auth />
</Route>
@ -87,41 +134,105 @@ class AppRouter extends Component {
<Auth page={"profile"} />
</Route>
<Route exact path={"/qr-scan"}>
<QRScan />
{proxy.status() ? (
<QRScan />
) : (
<Redirect
to={{
pathname: "/auth",
}}
/>
)}
</Route>
<Route exact path={"/activation"}>
<Activation />
{proxy.status() ? (
<Activation />
) : (
<Redirect
to={{
pathname: "/auth",
}}
/>
)}
</Route>
<Route exact path={"/chatroom"}>
<ChatList />
{proxy.status() ? (
<Chatroom />
) : (
<Redirect
to={{
pathname: "/auth",
}}
/>
)}
</Route>
<Route exact path={"/cart"}>
<Cart />
{proxy.status() ? (
<Cart />
) : (
<Redirect
to={{
pathname: "/auth",
}}
/>
)}
</Route>
<Route exact path={"/mybooks"}>
<MyBooks />
{proxy.status() ? (
<MyBooks />
) : (
<Redirect
to={{
pathname: "/auth",
}}
/>
)}
</Route>
<Route exact path={"/ar"}>
<AR />
{proxy.status() ? (
<AR />
) : (
<Redirect
to={{
pathname: "/auth",
}}
/>
)}
</Route>
{window.innerWidth < 1000 ? (
<Route exact path={"/chatroom/:id"}>
<Chatroom />
{proxy.status() ? (
<Chatroom />
) : (
<Redirect
to={{
pathname: "/auth",
}}
/>
)}
</Route>
) : null}
<Route path={""}>
<Redirect
to={{
pathname: "/qr",
search:
"?id=" +
window.location.pathname.slice(
window.location.pathname.lastIndexOf("/") + 1,
window.location.pathname.length
),
}}
/>
{proxy.status() ? (
<Redirect
to={{
pathname: "/qr",
search:
"?id=" +
window.location.pathname.slice(
window.location.pathname.lastIndexOf("/") + 1,
window.location.pathname.length
),
}}
/>
) : (
<Redirect
to={{
pathname: "/auth",
}}
/>
)}
</Route>
</Switch>
</Router>
@ -131,7 +242,7 @@ class AppRouter extends Component {
export default connect(
(state) => ({
profile: state.user.status || {},
profile: state.user.status,
// status: state.user.status,
}),
{ getProfile: user.getProfile }

@ -0,0 +1,31 @@
import proxy from "../proxy";
const book = {
list:
(data = {}) =>
async (dispatch) =>
await proxy.get("book/list", data, { dispatch }),
info:
(data = {}) =>
async (dispatch) =>
await proxy.get("book/info", data, { dispatch }),
update:
(data = {}, data2 = {}) =>
async (dispatch) => {
await proxy.put("book/update", data);
await proxy.get("book/list", data2, { dispatch });
},
add:
(data = {}, data2 = {}) =>
async (dispatch) => {
await proxy.post("book/add", data);
await proxy.get("book/list", data2, { dispatch });
},
del:
(data = {}, data2 = {}) =>
async (dispatch) => {
await proxy.delete("book/delete", data);
await proxy.get("book/list", data2, { dispatch });
},
};
export default book;

@ -5,3 +5,4 @@ export { default as chat } from "./chat.js";
// export { default as public } from './public.js';
export { default as user } from "./user.js";
export { default as qr } from "./qr.js";
export { default as book } from "./book.js";

@ -0,0 +1,28 @@
const initialState = {
loading: false,
error: null,
list: null,
info: null,
};
export default function book(state = initialState, action) {
let { type, data } = action;
switch (type) {
case "book/list":
return { ...state, loading: false, list: data, error: null };
case "book/info":
return { ...state, loading: false, list: null, info: data, error: null };
case "book/update":
return { ...state, loading: false, error: null };
case "book/add":
return { ...state, loading: false, error: null };
case "book/delete":
return { ...state, loading: false, error: null };
/////////////
case "loading":
return { ...state, loading: true };
case "error":
return { ...state, loading: false, error: data.message };
default:
return state;
}
}

@ -5,3 +5,4 @@ export { default as message } from "./message.js";
export { default as public } from "./public.js";
export { default as user } from "./user.js";
export { default as qr } from "./qr.js";
export { default as book } from "./book.js";

@ -1,7 +1,7 @@
import proxy from "../proxy";
import { ToastContainer, toast } from "react-toastify";
const initialState = {
status: proxy.status(),
status: null,
loading: false,
error: null,
list: null,

@ -57,7 +57,7 @@ class Profile extends Component {
};
componentDidMount() {
this.props.getProfile();
// this.props.getProfile();
}
onChange = (name, value) => {

@ -1,5 +1,7 @@
import React, { Component } from "react";
import { Link } from "react-router-dom";
import { connect } from "react-redux";
import { book } from "~/Redux/actions";
import Footer from "../Home/Footer/index";
import Navbar from "../Home/Navbar/index";
@ -10,6 +12,7 @@ import Info from "./Info/index";
import AddToCart from "./AddToCart/index";
import HomeScroll from "../Home/HomeScroll/index";
import HomeSlider from "../Home/HomeSlider/index";
import Loader from "~/components/Loader/index";
import sciense_7 from "~/assets/images/sciense-7.png";
import sciense_6 from "~/assets/images/sciense-6.png";
@ -40,138 +43,176 @@ const fontSize = {
li: window.innerWidth > maxMobileSize ? 14 : window.innerWidth / 29,
},
};
export default class Product extends Component {
class Product extends Component {
componentDidMount() {
this.props.getInfo({
id: window.location.pathname.slice(
window.location.pathname.lastIndexOf("/") + 1,
window.location.pathname.length
),
});
}
render() {
const { product, sameProducts, supportItems } = this.props;
const { product, sameProducts, supportItems, info } = this.props;
return (
<>
{window.innerWidth > 1000 ? (
<>
<div className="product d-flex flex-column">
<Navbar />
<Breadcrumbs />
<header className="product__header d-flex mt-4">
<Gallery gallery={product.gallery} />
<Info
subTitle={product.subTitle}
title={product.title}
description={product.description}
/>
<AddToCart
supportItems={supportItems}
price={product.price}
off={product.off}
/>
</header>
<div className="product__comments d-flex flex-column">
<div className="d-flex justify-content-between">
<h3 style={{ fontSize: fontSize.desktop.h1 }}>
نظرات خریداران
</h3>
<button>
ارسال نظر
<img src={send_comment} alt="ارسال نظر" />
</button>
</div>
this.props.info ? (
<>
<div className="product d-flex flex-column">
<Navbar />
<Breadcrumbs />
<header className="product__header d-flex mt-4">
<Gallery gallery={product.gallery} />
<Info
subTitle={product.subTitle}
title={product.title}
description={product.description}
/>
<AddToCart
supportItems={supportItems}
price={product.price}
off={product.off}
/>
</header>
<div className="product__comments d-flex flex-column">
<div className="d-flex justify-content-between">
<h3 style={{ fontSize: fontSize.desktop.h1 }}>
نظرات خریداران
</h3>
<button>
ارسال نظر
<img src={send_comment} alt="ارسال نظر" />
</button>
</div>
<div className="product__comments--list d-flex flex-column">
<Comment comment={product.comments[0]} />
<div className="product__comments--list d-flex flex-column">
<Comment comment={product.comments[0]} />
</div>
</div>
<Identifier item={sameProducts} />
</div>
<Identifier item={sameProducts} />
<Footer />
</>
) : (
<div
className="d-flex justify-content-center align-items-center"
style={{ height: "100vh", width: "100vw" }}
>
<Loader />
</div>
<Footer />
</>
)
) : null}
{window.innerWidth < 1000 ? (
<>
<div className="mobile-product d-flex flex-column">
<Navbar />
<header className="mobile-product__header d-flex flex-column align-items-center">
<img src={product.image} alt={product.title} />
<h1 style={{ fontSize: fontSize.mobile.h1 }}>
{product.title}
</h1>
<h2 style={{ fontSize: fontSize.mobile.h2 }}>
{product.subTitle}
</h2>
<div className="d-flex flex-column mt-3">
<div className="d-flex">
this.props.info ? (
<>
<div className="mobile-product d-flex flex-column">
<Navbar />
<header className="mobile-product__header d-flex flex-column align-items-center">
<img
src={`https://dnvn.ir/api/v1/file/${info.fileIds}`}
alt={info.name}
/>
<h1 style={{ fontSize: fontSize.mobile.h1 }}>{info.name}</h1>
<h2 style={{ fontSize: fontSize.mobile.h2 }}>
{product.subTitle}
</h2>
<div className="d-flex flex-column mt-3">
<div className="d-flex">
<Link
to={`/products/${product.id}/sample`}
className="mobile-product__header--digitalButton"
style={{ fontSize: fontSize.mobile.a }}
>
خرید نسخه دیجیتال
</Link>
<Link
to={`/products/${product.id}/sample`}
className="mobile-product__header--purchase"
style={{ fontSize: fontSize.mobile.a }}
>
خرید نسخه چاپی
</Link>
</div>
<Link
to={`/products/${product.id}/sample`}
className="mobile-product__header--digitalButton"
className="mobile-product__header--sampleButton"
style={{ fontSize: fontSize.mobile.a }}
>
خرید نسخه دیجیتال
</Link>
<Link
to={`/products/${product.id}/sample`}
className="mobile-product__header--purchase"
style={{ fontSize: fontSize.mobile.a }}
>
خرید نسخه چاپی
مطالعه نمونه کتاب
</Link>
</div>
<Link
to={`/products/${product.id}/sample`}
className="mobile-product__header--sampleButton"
style={{ fontSize: fontSize.mobile.a }}
>
مطالعه نمونه کتاب
</Link>
</header>
<div className="mobile-product__abstraction d-flex flex-column">
<h3 style={{ fontSize: fontSize.mobile.h3 }}>خلاصه کتاب</h3>
<p style={{ fontSize: fontSize.mobile.p }}>
{product.abstraction}
</p>
</div>
</header>
<div className="mobile-product__abstraction d-flex flex-column">
<h3 style={{ fontSize: fontSize.mobile.h3 }}>خلاصه کتاب</h3>
<p style={{ fontSize: fontSize.mobile.p }}>
{product.abstraction}
</p>
</div>
<div className="mobile-product__modules d-flex flex-column">
<h3 style={{ fontSize: fontSize.mobile.h3 }}>
این کتاب شامل چه مواردی است؟
</h3>
<ul>
{product.modules.map((item, i) => (
<React.Fragment key={i}>
<Item item={item} />
</React.Fragment>
))}
</ul>
</div>
<div className="mobile-product__tips d-flex flex-column">
<h3 style={{ fontSize: fontSize.mobile.h3 }}>
نکاتی که هنگام خرید باید به آن توجه داشته باشید؟
</h3>
<ul>
{product.tips.map((item, i) => (
<React.Fragment key={i}>
<Item item={item} />
</React.Fragment>
))}
</ul>
</div>
<div className="mobile-product__description d-flex">
<p style={{ fontSize: fontSize.mobile.p }}>
{product.description}
</p>
</div>
<div className="mobile-product__comments d-flex flex-column">
<h3 style={{ fontSize: fontSize.mobile.h3 }}>نظرات خریداران</h3>
<div className="mobile-product__comments--list d-flex">
{product.comments.map((item, i) => (
<Comment comment={item} key={i} />
))}
<div className="mobile-product__modules d-flex flex-column">
<h3 style={{ fontSize: fontSize.mobile.h3 }}>
این کتاب شامل چه مواردی است؟
</h3>
<ul>
{product.modules.map((item, i) => (
<React.Fragment key={i}>
<Item item={item} />
</React.Fragment>
))}
</ul>
</div>
<div className="mobile-product__tips d-flex flex-column">
<h3 style={{ fontSize: fontSize.mobile.h3 }}>
نکاتی که هنگام خرید باید به آن توجه داشته باشید؟
</h3>
<ul>
{product.tips.map((item, i) => (
<React.Fragment key={i}>
<Item item={item} />
</React.Fragment>
))}
</ul>
</div>
<div className="mobile-product__description d-flex">
<p style={{ fontSize: fontSize.mobile.p }}>
{product.description}
</p>
</div>
<div className="mobile-product__comments d-flex flex-column">
<h3 style={{ fontSize: fontSize.mobile.h3 }}>
نظرات خریداران
</h3>
<div className="mobile-product__comments--list d-flex">
{product.comments.map((item, i) => (
<Comment comment={item} key={i} />
))}
</div>
</div>
</div>
</>
) : (
<div
className="d-flex justify-content-center align-items-center"
style={{ height: "100vh", width: "100vw" }}
>
<Loader />
</div>
</>
)
) : null}
</>
);
}
}
export default connect(
(state) => ({
info: state.book.info,
// status: state.user.status,
}),
{ getInfo: book.info }
)(Product);
Product.defaultProps = {
supportItems: [
{ title: "ارسال رایگان", icon: product_shipping },

@ -13,6 +13,7 @@
}
img {
height: calc(100vh / 2.7);
border-radius: 10px;
}
h1 {
margin-top: 10px;

@ -28,28 +28,23 @@ export default class Product extends Component {
<>
{window.innerWidth < 1000 ? (
<div className="mobile-products-product d-flex flex-column">
<img src={product.image} alt={"عکس مجصول"} />
<img
src={`https://dnvn.ir/api/v1/file/${product.fileIds}`}
alt={"عکس مجصول"}
/>
<div className="mobile-products-product__info d-flex flex-column">
<h1 style={{ fontSize: fontSize.mobile.h1 }}>{product.title}</h1>
<h1 style={{ fontSize: fontSize.mobile.h1 }}>{product.name}</h1>
</div>
<div className="mobile-products-product__links d-flex mt-2">
<Link
to={`/products/${product.id}`}
style={{ fontSize: fontSize.mobile.a }}
className="mobile-products-product__links--physical"
>
کتاب دیجیتال
{!product.status.digital ? (
اطلاعات بیشتر
{/* {!product.status.digital ? (
<img src={basket} alt="افزودن به سبد خرید" />
) : null}
</Link>
<Link
style={{ fontSize: fontSize.mobile.a }}
className="mobile-products-product__links--ar"
>
واقعیت افزوده
{!product.status.ar ? (
<img src={basket} alt="افزودن به سبد خرید" />
) : null}
) : null} */}
</Link>
</div>
</div>
@ -57,7 +52,7 @@ export default class Product extends Component {
{window.innerWidth > 1000 ? (
<article className="products-product d-flex flex-column align-items">
<Link to={`/products/${product.id}`}>
<img src={product.image} alt={product.title} />
<img src={product.image} alt={product.name} />
<h1 style={{ fontSize: fontSize.desktop.h1 }}>
{product.title + " " + product.subTitle}
</h1>

@ -66,6 +66,7 @@
img {
width: 80%;
margin: 10px auto;
border-radius: 8px;
}
&__info {
width: 80%;
@ -124,6 +125,7 @@
img {
width: 80%;
margin: 10px auto;
border-radius: 8px;
}
&__info {
width: 80%;
@ -184,6 +186,7 @@
img {
width: 80%;
margin: 10px auto;
border-radius: 8px;
}
&__info {
width: 80%;

@ -1,5 +1,8 @@
import React, { Component } from "react";
import FilterListIcon from "@material-ui/icons/FilterList";
import Loader from "~/components/Loader/index";
import { connect } from "react-redux";
import { book } from "~/Redux/actions";
import Navbar from "../Home/Navbar/index";
import Footer from "../Home/Footer/index";
@ -20,13 +23,14 @@ import navbarSearch from "../../assets/icons/navbarSearch.png";
import "./index.scss";
const maxMobileSize = 1250;
const fontSize = {
mobile: {
input: window.innerWidth > maxMobileSize ? 14 : window.innerWidth / 27,
},
};
export default class Products extends Component {
class Products extends Component {
state = {
selectedSort: null,
selectedFilters: {
@ -53,59 +57,96 @@ export default class Products extends Component {
degree: "",
};
componentDidMount() {
this.props.getList();
}
render() {
const { dateFilters, degreeFilters, firstFilters } = this.state;
return (
<>
{window.innerWidth > 1000 ? (
<>
<div className="products d-flex flex-column">
<Navbar page={"products"} />
<Breadcrumbs />
<div className="products__body d-flex">
<Filters parent={this} />
<div className="products__body--left d-flex flex-column">
<Sort parent={this} selectedSort={this.state.selectedSort} />
<List parent={this} />
this.props.list ? (
<>
<div className="products d-flex flex-column">
<Navbar page={"products"} />
<Breadcrumbs />
<div className="products__body d-flex">
<Filters parent={this} />
<div className="products__body--left d-flex flex-column">
<Sort
parent={this}
selectedSort={this.state.selectedSort}
/>
<List parent={this} />
</div>
</div>
</div>
<Footer />
</>
) : (
<div
className="d-flex justify-content-center align-items-center"
style={{ height: "100vh", width: "100vw" }}
>
<Loader />
</div>
<Footer />
</>
)
) : null}
{window.innerWidth < 1000 ? (
<>
<div className="mobile-products d-flex flex-column">
<Navbar page={"products"} />
<div className="mobile-products__search d-flex">
<input
type="search"
style={{ fontSize: fontSize.mobile.input }}
placeholder={"جستجو"}
/>
<img src={navbarSearch} alt="جستجو" />
</div>
<div className="mobile-products__filters d-flex">
<div className="d-flex">
<Select name="first" options={firstFilters} parent={this} />
<Select name="date" options={dateFilters} parent={this} />
<Select name="degree" options={degreeFilters} parent={this} />
this.props.list ? (
<>
<div className="mobile-products d-flex flex-column">
<Navbar page={"products"} />
<div className="mobile-products__search d-flex">
<input
type="search"
style={{ fontSize: fontSize.mobile.input }}
placeholder={"جستجو"}
/>
<img src={navbarSearch} alt="جستجو" />
</div>
<div className="mobile-products__filters d-flex">
<div className="d-flex">
<Select name="first" options={firstFilters} parent={this} />
<Select name="date" options={dateFilters} parent={this} />
<Select
name="degree"
options={degreeFilters}
parent={this}
/>
</div>
<FilterListIcon style={{ fontSize: 40, color: "#a5a5a5" }} />
</div>
<div className="mobile-products__list d-flex flex-wrap">
{this.props.list.map((item, i) => (
<Product product={item} key={i} id={i} />
))}
</div>
<FilterListIcon style={{ fontSize: 40, color: "#a5a5a5" }} />
</div>
<div className="mobile-products__list d-flex flex-wrap">
{this.props.products.map((item, i) => (
<Product product={item} key={i} id={i} />
))}
</div>
</>
) : (
<div
className="d-flex justify-content-center align-items-center"
style={{ height: "100vh", width: "100vw" }}
>
<Loader />
</div>
</>
)
) : null}
</>
);
}
}
export default connect(
(state) => ({
list: state.book.list,
// status: state.user.status,
}),
{ getList: book.list }
)(Products);
Products.defaultProps = {
sortItems: [
"پربازدیدترین",

@ -0,0 +1,35 @@
import React, { Component } from "react";
import "./index.scss";
export default function QRImage(props) {
const list = props.data.fileIds.split(",");
console.log(list);
return (
<>
{window.innerWidth < 1000 ? (
(list.length === 1 ? (
<div className="mobile-qr-image d-flex">
<img
className="mobile-qr-image__single"
src={`https://dnvn.ir/api/v1/file/${list[0]}`}
/>
</div>
) : null,
list.length !== 2 ? (
<div className="mobile-qr-image d-flex">
<img
className="mobile-qr-image__two"
src={`https://dnvn.ir/api/v1/file/${list[0]}`}
/>
<img
className="mobile-qr-image__two"
src={`https://dnvn.ir/api/v1/file/${list[1]}`}
/>
</div>
) : null)
) : (
<p>reza</p>
)}
</>
);
}

@ -0,0 +1,13 @@
.mobile-qr-image {
width: 100%;
justify-content: space-between;
&__single {
width: 100%;
border-radius: 10px;
height: 200px;
}
&__two {
width: 49%;
height: 150px;
}
}

@ -3,6 +3,7 @@ import { Link } from "react-router-dom";
import Navbar from "../Home/Navbar/index";
import Footer from "../Home/Footer/index";
import Loader from "~/components/Loader/index";
import Image from "./Image/index";
import VoiceBox from "./VoiceBox/index.js";
import VideoBox from "./VideoBox/index";
import PDF from "./PDF/index";
@ -50,7 +51,10 @@ class QR extends Component {
componentDidMount() {
if (window.location.search) {
let tail = window.location.search;
let tail = window.location.search.slice(
window.location.search.lastIndexOf("=") + 1,
window.location.search.length
);
this.props.info({ tail: tail });
}
}
@ -272,6 +276,7 @@ const Identifier = (props) => {
{props.data.type === "pdf" ? <PDF data={props.data} /> : null}
{props.data.type === "ppt" ? <PowerPoint data={props.data} /> : null}
{props.data.type === "links" ? <Links data={props.data} /> : null}
{props.data.type === "image" ? <Image data={props.data} /> : null}
</>
);
};

Loading…
Cancel
Save