Cosmic JS Blog Stay tuned for community news, company announcements and updates from the Cosmic JS team.

How to Build a Next.js React Universal App



Next.js is an amazing new addition to the React open-source ecosystem.  It is “a minimalistic framework for universal server-rendered React applications” that makes the process of building these types of applications much faster and easier.  Recently I demoed a new app on the Cosmic JS Apps page that is built using the Next.js framework.  I’ve built a few React Universal apps from scratch before and I found taking the Next.js route to speed things along quite a bit.  And adding content management capability from Cosmic JS to the Next.js structure was very intuitive.

In this tutorial I’m going to show you how I built the Next.js application and integrated content powered by Cosmic JS.  This full app is available on the Cosmic JS Apps page for you to download, hack, install and deploy live.

Getting Started

Let’s get started by creating our app and installing next:

mkdir next.js-website
cd next.js-website
yarn add next

Creating Pages

Now lets create a new folder to hold our pages.

mkdir pages

With Next.js, any page that we add to our pages folder will be available at its corresponding url.  So index.js will be available at / and about.js will be found at /about and so on.  Let’s first create our index.js file.  Add the following to index.js:

import React from 'react'
export default class Home extends React.Component {
  render () {
    return <div>Hello World</div>
  }
}

Now let’s start our next server to see our page:

next

Navigate to http://localhost:3000 to see our Hello World example.  Next let’s add another page to show our about page content.  In a file titled about.js add:

import React from 'react'
export default class Home extends React.Component {
  render () {
    return <div>About me</div>
  }
}

Then run next again.  Now go to http://localhost:3000/about to see this page.

We could hard code the content for all of our pages, but for our purposes, let’s hook up the Cosmic JS API so we can let our team add and edit content using the Cosmic JS CMS API.  For each page we want to be able to pull that specific page from the Cosmic JS API and serve the content to our Next.js application.

Adding Cosmic JS-Powered Content

First install the Cosmic JS NPM module:

yarn add cosmicjs

Then create a new folder titled models and add the following to a file titled cosmic.js:

const config = {
  bucket: {
    slug: 'nextjs-website' // add your bucket slug here
  }
}
import Cosmic from 'cosmicjs'
export default {
  getPage(slug) {
    const data = new Promise(resolve => {
      Cosmic.getObject(config, { slug }, (err, res) => {
        resolve(res)
      })
    })
    return data
  }
}

So the purpose of this piece of code is to take whatever slug is supplied to the "getPage" function and render the Cosmic JS Object.

Dynamic Pages

Let’s create a basic page structure for all of our pages.  Create a folder titled "templates" and addd the following file titled basic-page.js:

import React from 'react'
export default class BasicPage extends React.Component {
  render() {
    const page = this.props.page
    return (
      <div>
        <main>
          <h1>{page.title}</h1>
          <div dangerouslySetInnerHTML={{__html: page.content}}/>
        </main>
      </div>
    )
  }
}

Next let’s edit our index.js file to include the following:

import React from 'react'
import BasicPage from '../templates/basic-page'
import Cosmic from '../models/cosmic'
export default class Home extends React.Component {
  static async getInitialProps () {
    return await Cosmic.getPage('home')
  }
  render () {
    const page = this.props.object
    return <BasicPage page={page}/>
  }
}


Now we have created a basic page template that will render the page title and content.  And in our index.js file, before rendering, the getInitialProps function will fetch the page content from the Cosmic JS API.  Now for our about page, all we need to do is change the slug.  about.js now looks like this:

import React from 'react'
import BasicPage from '../templates/basic-page'
import Cosmic from '../models/cosmic'
export default class Home extends React.Component {
  static async getInitialProps () {
    return await Cosmic.getPage('about')
  }
  render () {
    const page = this.props.object
    return <BasicPage page={page}/>
  }
}

Now run the application:

next

Navigate to / and /about and notice that the Cosmic JS content comes through not only when you view source (server side) but it also renders on the client as a React Universal Application.  

In Conclusion

So when creating a React universal application using the Next.js framework there was a lot of stuff I didn’t have to do:  I didn’t have to set up react-router.  I didn’t have to set up Flux or Redux to manage state.  I didn’t have to do any server-side node.js coding.  I didn't have to do a lot (or any!) webpack configuration for hot-reloading and bundle routing.  So yea, I saved a TON of time on boilerplate setup and config using the Next.js framework to accomplish my universal React needs.  It really is a remarkable piece of tech and I’m looking forward to see where it will go next (no pun intended).

I hope you enjoyed this tutorial.  If you have any questions about setting up your Cosmic JS-powered Next.js Universal App reach our to us in our Slack community or on Twitter.

You may also like



Cosmic JS now gives you the ability to add different user roles to your bucket.  The different roles available are:

Admin
Has access to settings, users and developer features.

Developer
Has access to developer features and editor features.

Editor
Can add, edit and delete content with developer features hidden.

As an Admin or Developer, this makes it easier to share Cosmic JS with the Editor on your team.  For the Editor role, the powerful developer features are hidden and allows them to focus on their job of managing content.  Sign in to your Cosmic JS account to add your team and collaborate on building something great, now even easier.

Cosmic JS is a powerful CMS API that allows you to manage content for your websites and applications faster and easier.  But did you know that you can also use Cosmic JS to deploy code to your website (in any language) from any GitHub repository?  In addition to deploying content and code, starting today you can also add unlimited domains to your deployed application.  This is revolutionary because it means that moving forward all you need to launch your website is a git repository, a domain name provider and Cosmic JS!  No more hosting server necessary!  I’ve added a couple of screencasts for your viewing.  Let’s get started.

Create a Bucket

After logging in to your Cosmic JS account, create a new bucket.  After creating your new bucket, you will be prompted to install an app.

Install an App

Let's go ahead and install an app, but you could just as easily skip this step and deploy your own application pointed to your Cosmic JS bucket.  After installing your app, you will be prompted to deploy the application.

Deploy the App

Next click "Deploy Web App" to launch the web application to http://[your-bucket-slug].cosmicapp.co.  Once you do this it will take about a minute for the application to deploy on a custom instance of the Cosmic JS app server.  While this is working its magic, let's add our custom domains…

Add Custom Domains

The Cosmic app server subdomain is great for development and staging, but when you go live, you're going to want to add our own custom domains.  Cosmic JS makes this incredibly easy by providing the option to add custom domains to your deployed application.  Here are the 4 easy steps:

1. Go to Settings > Deploy Web App > Add Custom Domains (upgrade your account if needed)
2. Add your custom domains
3. Click "Set Domains"
4. Go to your domain name registrar's website and point your A Name Records to the Cosmic JS app server located at 162.243.13.186

Now navigate to your domain and notice that you now have your application hosted at your custom domain!  Add as many domains / subdomains as you need!  Whenever you need to deploy changes to the app, just push the changes up to your GitHub repository and click "Redeploy Web App".

Cosmic JS now gives you the power to deploy a website faster and more nimbly than any other system.  And all you need is a git repository, a domain name provider and Cosmic JS!

In the frenzy surrounding new tech, simplicity gets forgotten. Services like Cosmic JS challenge this. So in the spirit of doing the opposite, we're going to build a sleek real estate listing app (with a social flavor) that's as easy to use as a Wordpress blog.

A very interesting article was published to one of my favorite web dev blogs today. Where Content Management Systems Fit Into the Process goes into a discussion which I think is seldom in the limelight in the development community, what is the best process in connecting your site to a CMS?  The author Geoff Graham presents three options in building a dynamic, CMS-powered website:

Option 1: The CMS Comes First Method


Option 2: The All-At-Once Method


Option 3: The CMS Comes Last Method


Previously, when building sites using other CMS platforms I would prefer to use the "CMS Comes Last Method" because I would be able to work out a lot of bugs, change my mind and add new features in the static HTML/CSS build phase before pouring in the more time-consuming programming / CMS phase.  

But with Cosmic JS I can use any one of these methods and feel confident that I can easily make edits, change my mind and add new features to a CMS-powered website.  There's power and reassurance in flexibility and Cosmic JS offers the most flexible way to add content to your website.

Sign up to get a private beta invite to begin checking out how easy it is to add dynamic content to your website or app.

We are excited to announce that you can now use all of the Cosmic JS features in a full demo before signing up for an official Cosmic JS account.

Cosmic JS is an API-first cloud-based content management platform that makes it easy for teams of developers and content editors to collaborate for projects and clients.