Builder Book
Builder Book is an open source web app built with React/Material-UI/Next/Express/Mongoose/MongoDB.
How can you use this app?
- as a boilerplate for React/Material-UI/Next/Express/Mongoose/MongoDB stack;
- as learning material for third-party APIs such as Google, Github, AWS SES, Mailchimp, Stripe;
- as a production-ready web app;
- write content, e.g. documentation, on Github but display the content on a web app;
- write a book with markdown and sell it on your own website;
Contents
Screenshots
Chapter excerpt with Buy Button for Pubilc/Guest visitor:
Chapter content for book Customer:
Add-book/Edit-book page for Admin user:
Book-detail page for Admin user:
Live demo
Log in with Google. You'll be logged in as an Admin (book author): link.
Introduction chapter without Buy button: link.
Chapter-1 with Buy button: link.
After logging in, you can connect Github and create a book:
- click the
Add book
button - enter book details and select a Github repo with a non-empty
introduction.md
file at the root - click
Save
, then click the book's title in your dashboard - you are now on the book's detail page, click the
Sync with Github
button - refresh the page and click
Introduction
to see the chapter's content
Run locally
-
Clone the project and run
yarn
to add packages. -
Before you start the app, create a
.env
file at the app's root. This file must have at least three env variables:MONGO_URL_TEST
,Google_clientID
,Google_clientSecret
. We recommend free MongoDB at mLab.To use all features and third-party integrations (such as Stripe, Google OAuth, Mailchimp), add values to all env variables in
.env
file:.env
:MONGO_URL="XXXXXX" MONGO_URL_TEST="XXXXXX" Google_clientID="XXXXXX" Google_clientSecret="XXXXXX" Amazon_accessKeyId="XXXXXX" Amazon_secretAccessKey="XXXXXX" EMAIL_SUPPORT_FROM_ADDRESS="XXXXXX" Github_Test_ClientID="XXXXXX" Github_Test_SecretKey="XXXXXX" Github_Live_ClientID="XXXXXX" Github_Live_SecretKey="XXXXXX" Stripe_Test_SecretKey="XXXXXX" Stripe_Live_SecretKey="XXXXXX" MAILCHIMP_API_KEY="XXXXXX" MAILCHIMP_REGION="XXXXXX" MAILCHIMP_PREORDERED_LIST_ID="XXXXXX" MAILCHIMP_ORDERED_LIST_ID="XXXXXX"
-
Before you start the app, create a
env-config.js
file at the app's root. This file makes Stripe's public keys (keys that start withpk
) available on client. Content of this file:env-config.js
:const dev = process.env.NODE_ENV !== 'production'; module.exports = { StripePublishableKey: dev ? 'pk_test_XXXXXX' : 'pk_live_XXXXXX', };
-
Start the app with
yarn dev
. -
The first registered user in the app becomes an Admin user (
"isAdmin": true
).
Deploy
-
Install now:
npm install -g now
-
Point your domain to Zeit world nameservers: three steps
-
Check the
now.json
file. If you are usingdotenv
and.env
for env variables, no need to changenow.json
. If you make changes to the app, check up how to configure now. -
Make sure you updated
ROOT_URL
inpackage.json
andlib/getRootURL.js
. -
Check that you have all production-level env variables in
.env
. -
In your terminal, deploy the app by running
now
. -
Now outputs your deployment's URL, for example:
builderbook-zomcvzgtvc.now.sh
. -
Point successful deployment to your domain, for example:
now ln builderbook-demo-zomcvzgtvc.now.sh builderbook.org
.
Built with
Core stack
Third party APIs
- AWS SES
- Github
- Google OAuth
- Stripe
- MailChimp
Check out package.json.
Project structure
.
├── components # React components
│ ├── admin # Components used on Admin pages
│ │ ├── EditBook.js # Edit title, price, and repo of book
│ │ ├── GiveFreeBook.js # Give free book to user
│ ├── customer # Components used on Customer pages
│ │ ├── Bookmark.js # Bookmark a section within a book chapter
│ │ ├── BuyButton.js # Buy book
│ ├── Header.js # Header component
│ ├── HomeFooter.js # Footer component on homepage
│ ├── HomeHeader.js # Header component on homepage
│ ├── MenuDrop.js # Dropdown menu
│ ├── Notifier.js # In-app notifications for app's users
│ ├── SharedStyles.js # List of _reusable_ styles
│ ├── TOC.js # Table of Contents
├── lib # Code available on both client and server
│ ├── api # Client-side API methods
│ │ ├── admin.js # Admin user methods
│ │ ├── customer.js # Customer user methods
│ │ ├── getRootURL.js # Returns ROOT_URL
│ │ ├── public.js # Public user methods
│ │ ├── sendRequest.js # Reusable code for all GET and POST requests
│ ├── context.js # Context for Material-UI integration
│ ├── notifier.js # Contains notify() function that loads Notifier component
│ ├── withAuth.js # HOC that passes user to pages and more
│ ├── withLayout.js # HOC for SSR with Material-UI and more
├── pages # Pages
│ ├── admin # Admin pages
│ │ ├── add-book.js # Page to add a new book
│ │ ├── book-detail.js # Page to view book details and sync content with Github
│ │ ├── edit-book.js # Page to update title, price, and repo of book
│ │ ├── index.js # Main Admin page that has all books and more
│ ├── customer # Customer pages
│ │ ├── my-books.js # Customer's dashboard
│ ├── public # Public pages (accessible to logged out users)
│ │ ├── login.js # Login page
│ │ ├── read-chapter.js # Page with chapter's content
│ │ ├── terms.js # Terms of Service page
│ ├── _document.js # Allows to customize pages (feature of Next.js)
│ ├── index.js # Homepage
├── server # Server code
│ ├── api # Express routes, route-level middleware
│ │ ├── admin.js # Admin routes
│ │ ├── customer.js # Customer routes
│ │ ├── index.js # Mounts all Express routes on server
│ │ ├── public.js # Public routes
│ ├── models # Mongoose models
│ │ ├── Book.js # Book model
│ │ ├── Chapter.js # Chapter model
│ │ ├── EmailTemplate.js # Email Template model
│ │ ├── Purchase.js # Purchase model
│ │ ├── User.js # User model
│ ├── utils # Server-side util
│ │ ├──sanitizeHtml.js # Sanitizes HTML
│ │ ├──slugify.js # Generates slug for any Model
│ ├── app.js # Custom Express/Next server
│ ├── aws.js # AWS SES API
│ ├── github.js # Github API
│ ├── google.js # Google OAuth API
│ ├── logs.js # Logger
│ ├── mailchimp.js # MailChimp API
│ ├── routesWithSlug.js # Express routes that contain slug
│ ├── stripe.js # Stripe API
├── static # Static resources
│ ├── nprogress.css # Styles for Nprogress
├── test/server/utils # Tests
│ ├── slugify.test.js # Unit test for generateSlug() function
├── .babelrc # Config for Babel
├── .eslintrc.js # Config for Eslint
├── .gitignore # List of ignored files and directories
├── env-config.js # Make Stripe's public keys available on client
├── now.json # Settings for now from Zeit
├── package.json # List of packages and scripts
├── tos.md # Content from Terms of Service
├── yarn.lock # Exact versions of packages
Contributing
We welcome suggestions and pull requests, especially for issues labeled as "discussion" and "contributions welcome".
By participating in this project, you are expected to uphold Builder Book's Code of Conduct.
Team
License
All code in this repository is provided under the MIT License.