mirror of
https://github.com/terribleplan/next.js.git
synced 2024-01-19 02:48:18 +00:00
Merge branch 'canary'
This commit is contained in:
commit
c5ddfea689
1
.gitignore
vendored
1
.gitignore
vendored
|
@ -5,6 +5,7 @@ dist
|
|||
# dependencies
|
||||
node_modules
|
||||
package-lock.json
|
||||
test/node_modules
|
||||
|
||||
# logs
|
||||
*.log
|
||||
|
|
|
@ -10,7 +10,7 @@
|
|||
language: "node_js",
|
||||
node_js: ["6"],
|
||||
cache: {
|
||||
directories: ["node-modules"]
|
||||
directories: ["node_modules"]
|
||||
},
|
||||
before_install: [
|
||||
"rm yarn.lock",
|
||||
|
@ -22,6 +22,7 @@
|
|||
deploy: {
|
||||
provider: "npm",
|
||||
email: "leo@zeit.co",
|
||||
tag: "canary",
|
||||
api_key: {
|
||||
secure:
|
||||
"br9gLncKeLSoL7iOq0PXFeD1Gp3jRI8QMCSNIrGdZg/MuLeuwYPv36kmMgf7aGIfpjFLtU2/eVrOHSB+T5g1nKgOsqmWsfZE1tQYWph0//ookd/sj+IyxIx8nVLbUV/C4ctYOhX/efotRgNn56w5Av5hWc1IQLmW9mSN8ijrQnM+GzRI8QitiofeY2EP3N1eO8vC8E2oGkOsAdcypiX6lFG908zyWt7X2SD+iOsK2eAHjxoAEUdrxE5a8gTDhcTH6qnmtBs9rCeEKbO3JZjEy5dvccxlX3Nd+2GC1rckayk6o5L/zveTilsUx6Auqqbwn1dT5ffQuYsV4RPofs8IMrhnizc8y+OfUcCCpBJ4ia4w7N8FEP56TnRNTFoFBGJL5Y6NfeT0HHAlClxUWMG9pRGWGN+sskODDQ9FEntGZoqwV396ogs+3YhkxbY0AIr84QOctflsFcPtOgr/CoBeOsjbB+o9+Rlsqwlf3u3B7qhtU9eV6KcMfK4x9qW+2cwTllK+gD8S9wILx5BChkfx99g/7u/Rg1PCym64tTsDOBtqTVC2YCqeYYvjmpw4Vl3ofLrFsoNQnbmb6Q5+JSpOcJ/bEj7P/FuZdlU0fNV28tFhElu5caKhSCJz/avUlXG7NeveW1Ee8gjhURC4V/l4ryacyjA2vcDY/4RRkWtHNr4="
|
||||
|
|
18
bin/next
18
bin/next
|
@ -1,10 +1,7 @@
|
|||
#!/usr/bin/env node
|
||||
|
||||
import { join, resolve } from 'path'
|
||||
import { join } from 'path'
|
||||
import { spawn } from 'cross-spawn'
|
||||
import { watchFile } from 'fs'
|
||||
import pkg from '../../package.json'
|
||||
import getConfig from '../server/config'
|
||||
|
||||
if (pkg.peerDependencies) {
|
||||
Object.keys(pkg.peerDependencies).forEach(dependency => {
|
||||
|
@ -27,13 +24,18 @@ const commands = new Set([
|
|||
])
|
||||
|
||||
let cmd = process.argv[2]
|
||||
let args
|
||||
let args = []
|
||||
let nodeArgs = []
|
||||
|
||||
if (new Set(['--version', '-v']).has(cmd)) {
|
||||
console.log(`next.js v${pkg.version}`)
|
||||
process.exit(0)
|
||||
}
|
||||
|
||||
if (new Set(process.argv).has('--inspect')) {
|
||||
nodeArgs.push('--inspect')
|
||||
}
|
||||
|
||||
if (new Set(['--help', '-h']).has(cmd)) {
|
||||
console.log(`
|
||||
Usage
|
||||
|
@ -61,7 +63,7 @@ process.env.NODE_ENV = process.env.NODE_ENV || defaultEnv
|
|||
const bin = join(__dirname, 'next-' + cmd)
|
||||
|
||||
const startProcess = () => {
|
||||
const proc = spawn(bin, args, { stdio: 'inherit', customFds: [0, 1, 2] })
|
||||
const proc = spawn('node', [...nodeArgs, ...[bin], ...args], { stdio: 'inherit', customFds: [0, 1, 2] })
|
||||
proc.on('close', (code, signal) => {
|
||||
if (code !== null) {
|
||||
process.exit(code)
|
||||
|
@ -83,10 +85,10 @@ const startProcess = () => {
|
|||
}
|
||||
|
||||
let proc = startProcess()
|
||||
const { pagesDirectory = resolve(process.cwd(), 'pages') } = getConfig(process.cwd())
|
||||
|
||||
if (cmd === 'dev') {
|
||||
watchFile(`${resolve(pagesDirectory, '..')}/next.config.js`, (cur, prev) => {
|
||||
const {watchFile} = require('fs')
|
||||
watchFile(`${process.cwd()}/next.config.js`, (cur, prev) => {
|
||||
if (cur.size > 0 || prev.size > 0) {
|
||||
console.log('\n> Found a change in next.config.js, restarting the server...')
|
||||
// Don't listen to 'close' now since otherwise parent gets killed by listener
|
||||
|
|
|
@ -1,11 +1,9 @@
|
|||
#!/usr/bin/env node
|
||||
import 'source-map-support/register'
|
||||
import { resolve, join } from 'path'
|
||||
import parseArgs from 'minimist'
|
||||
import { existsSync, readFileSync } from 'fs'
|
||||
import Server from '../server'
|
||||
import { printAndExit } from '../lib/utils'
|
||||
import pkgUp from 'pkg-up'
|
||||
|
||||
const argv = parseArgs(process.argv.slice(2), {
|
||||
alias: {
|
||||
|
@ -64,7 +62,7 @@ srv.start(argv.port, argv.hostname)
|
|||
.catch((err) => {
|
||||
if (err.code === 'EADDRINUSE') {
|
||||
let errorMessage = `Port ${argv.port} is already in use.`
|
||||
const pkgAppPath = pkgUp.sync('.')
|
||||
const pkgAppPath = require('pkg-up').sync('.')
|
||||
const appPackage = JSON.parse(readFileSync(pkgAppPath, 'utf8'))
|
||||
const nextScript = Object.entries(appPackage.scripts).find(scriptLine => scriptLine[1] === 'next')
|
||||
if (nextScript) errorMessage += `\nUse \`npm run ${nextScript[0]} -- -p <some other port>\`.`
|
||||
|
|
|
@ -6,6 +6,7 @@ import EventEmitter from '../lib/EventEmitter'
|
|||
import App from '../lib/app'
|
||||
import { loadGetInitialProps, getURL } from '../lib/utils'
|
||||
import PageLoader from '../lib/page-loader'
|
||||
import * as asset from '../lib/asset'
|
||||
|
||||
// Polyfill Promise globally
|
||||
// This is needed because Webpack2's dynamic loading(common chunks) code
|
||||
|
@ -29,6 +30,12 @@ const {
|
|||
location
|
||||
} = window
|
||||
|
||||
// With dynamic assetPrefix it's no longer possible to set assetPrefix at the build time
|
||||
// So, this is how we do it in the client side at runtime
|
||||
__webpack_public_path__ = `${assetPrefix}/_next/webpack/` //eslint-disable-line
|
||||
// Initialize next/asset with the assetPrefix
|
||||
asset.setAssetPrefix(assetPrefix)
|
||||
|
||||
const asPath = getURL()
|
||||
|
||||
const pageLoader = new PageLoader(buildId, assetPrefix)
|
||||
|
@ -93,10 +100,7 @@ export default async ({ ErrorDebugComponent: passedDebugComponent, stripAnsi: pa
|
|||
}
|
||||
|
||||
export async function render (props) {
|
||||
// There are some errors we should ignore.
|
||||
// Next.js rendering logic knows how to handle them.
|
||||
// These are specially 404 errors
|
||||
if (props.err && !props.err.ignore) {
|
||||
if (props.err) {
|
||||
await renderError(props.err)
|
||||
return
|
||||
}
|
||||
|
@ -159,7 +163,8 @@ async function doRender ({ Component, props, hash, err, emitter: emitterProp = e
|
|||
|
||||
let isInitialRender = true
|
||||
function renderReactElement (reactEl, domEl) {
|
||||
if (isInitialRender) {
|
||||
// The check for `.hydrate` is there to support React alternatives like preact
|
||||
if (isInitialRender && typeof ReactDOM.hydrate === 'function') {
|
||||
ReactDOM.hydrate(reactEl, domEl)
|
||||
isInitialRender = false
|
||||
} else {
|
||||
|
|
|
@ -1,10 +1,11 @@
|
|||
import 'react-hot-loader/patch'
|
||||
import stripAnsi from 'strip-ansi'
|
||||
import initNext, * as next from './'
|
||||
import ErrorDebugComponent from '../lib/error-debug'
|
||||
import initOnDemandEntries from './on-demand-entries-client'
|
||||
import initWebpackHMR from './webpack-hot-middleware-client'
|
||||
|
||||
require('@zeit/source-map-support/browser-source-map-support')
|
||||
|
||||
window.next = next
|
||||
|
||||
initNext({ ErrorDebugComponent, stripAnsi })
|
||||
|
|
|
@ -3,6 +3,12 @@
|
|||
import Router from '../lib/router'
|
||||
import fetch from 'unfetch'
|
||||
|
||||
const {
|
||||
__NEXT_DATA__: {
|
||||
assetPrefix
|
||||
}
|
||||
} = window
|
||||
|
||||
export default () => {
|
||||
Router.ready(() => {
|
||||
Router.router.events.on('routeChangeComplete', ping)
|
||||
|
@ -10,16 +16,16 @@ export default () => {
|
|||
|
||||
async function ping () {
|
||||
try {
|
||||
const url = `/_next/on-demand-entries-ping?page=${Router.pathname}`
|
||||
const url = `${assetPrefix}/_next/on-demand-entries-ping?page=${Router.pathname}`
|
||||
const res = await fetch(url, {
|
||||
credentials: 'same-origin'
|
||||
credentials: 'omit'
|
||||
})
|
||||
const payload = await res.json()
|
||||
if (payload.invalid) {
|
||||
// Payload can be invalid even if the page is not exists.
|
||||
// So, we need to make sure it's exists before reloading.
|
||||
const pageRes = await fetch(location.href, {
|
||||
credentials: 'same-origin'
|
||||
credentials: 'omit'
|
||||
})
|
||||
if (pageRes.status === 200) {
|
||||
location.reload()
|
||||
|
|
|
@ -1,7 +1,19 @@
|
|||
import webpackHotMiddlewareClient from 'webpack-hot-middleware/client?overlay=false&reload=true&path=/_next/webpack-hmr'
|
||||
import webpackHotMiddlewareClient from 'webpack-hot-middleware/client?autoConnect=false'
|
||||
import Router from '../lib/router'
|
||||
|
||||
const {
|
||||
__NEXT_DATA__: {
|
||||
assetPrefix
|
||||
}
|
||||
} = window
|
||||
|
||||
export default () => {
|
||||
webpackHotMiddlewareClient.setOptionsAndConnect({
|
||||
overlay: false,
|
||||
reload: true,
|
||||
path: `${assetPrefix}/_next/webpack-hmr`
|
||||
})
|
||||
|
||||
const handlers = {
|
||||
reload (route) {
|
||||
if (route === '/_error') {
|
||||
|
|
30
errors/build-dir-not-writeable.md
Normal file
30
errors/build-dir-not-writeable.md
Normal file
|
@ -0,0 +1,30 @@
|
|||
# Build directory not writeable
|
||||
|
||||
#### Why This Error Occurred
|
||||
|
||||
The filesystem does not allow writing to the specified directory. A common cause for this error is starting a [custom server](https://github.com/zeit/next.js#custom-server-and-routing) in development mode on a production server, for example, [now.sh](https://zeit.co) which [doesn't allow you to write to the filesystem after your app is built](https://zeit.co/docs/deployment-types/node#file-system-specifications).
|
||||
|
||||
#### Possible Ways to Fix It
|
||||
|
||||
When using a custom server with a server file, for example called `server.js`, make sure you update the scripts key in `package.json` to:
|
||||
|
||||
```json
|
||||
{
|
||||
"scripts": {
|
||||
"dev": "node server.js",
|
||||
"build": "next build",
|
||||
"start": "NODE_ENV=production node server.js"
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
and the custom server starts Next in production mode when `NODE_ENV` is `production`
|
||||
|
||||
```js
|
||||
const dev = process.env.NODE_ENV !== 'production'
|
||||
const app = next({ dev })
|
||||
```
|
||||
|
||||
### Useful Links
|
||||
|
||||
- [Custom Server documentation + examples](https://github.com/zeit/next.js#custom-server-and-routing)
|
15
errors/powered-by-header-option-removed.md
Normal file
15
errors/powered-by-header-option-removed.md
Normal file
|
@ -0,0 +1,15 @@
|
|||
# The poweredByHeader has been removed
|
||||
|
||||
#### Why This Error Occurred
|
||||
|
||||
Starting at Next.js version 5.0.0 the `poweredByHeader` option has been removed.
|
||||
|
||||
#### Possible Ways to Fix It
|
||||
|
||||
If you still want to remove `x-powered-by` you can use one of the custom-server examples.
|
||||
|
||||
And then manually remove the header using `res.removeHeader('x-powered-by')`
|
||||
|
||||
### Useful Links
|
||||
|
||||
- [Custom Server documentation + examples](https://github.com/zeit/next.js#custom-server-and-routing)
|
40
examples/active-class-name/README.md
Normal file
40
examples/active-class-name/README.md
Normal file
|
@ -0,0 +1,40 @@
|
|||
[![Deploy to now](https://deploy.now.sh/static/button.svg)](https://deploy.now.sh/?repo=https://github.com/zeit/next.js/tree/master/examples/active-class-name)
|
||||
|
||||
# activeClassName example
|
||||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example active-class-name active-class-name-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/active-class-name
|
||||
cd active-class-name
|
||||
```
|
||||
|
||||
Install it and run:
|
||||
|
||||
```bash
|
||||
npm install
|
||||
npm run dev
|
||||
```
|
||||
|
||||
Deploy it to the cloud with [now](https://zeit.co/now) ([download](https://zeit.co/download))
|
||||
|
||||
```bash
|
||||
now
|
||||
```
|
||||
|
||||
## The idea behind the example
|
||||
|
||||
ReactRouter has a convenience property on the `Link` element to allow an author to set the _active_ className on a link. This example replicates that functionality using Next's own `Link`.
|
18
examples/active-class-name/components/Link.js
Normal file
18
examples/active-class-name/components/Link.js
Normal file
|
@ -0,0 +1,18 @@
|
|||
import { withRouter } from 'next/router'
|
||||
import Link from 'next/link'
|
||||
import React, { Children } from 'react'
|
||||
|
||||
const ActiveLink = ({ router, children, ...props }) => {
|
||||
const child = Children.only(children)
|
||||
|
||||
let className = child.props.className || ''
|
||||
if (router.pathname === props.href && props.activeClassName) {
|
||||
className = `${className} ${props.activeClassName}`.trim()
|
||||
}
|
||||
|
||||
delete props.activeClassName
|
||||
|
||||
return <Link {...props}>{React.cloneElement(child, { className })}</Link>
|
||||
}
|
||||
|
||||
export default withRouter(ActiveLink)
|
30
examples/active-class-name/components/Nav.js
Normal file
30
examples/active-class-name/components/Nav.js
Normal file
|
@ -0,0 +1,30 @@
|
|||
import Link from './Link'
|
||||
|
||||
export default () => (
|
||||
<nav>
|
||||
<style jsx>{`
|
||||
.active:after {
|
||||
content: ' (current page)';
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
text-decoration: none;
|
||||
padding: 10px;
|
||||
display: block;
|
||||
}
|
||||
`}</style>
|
||||
|
||||
<ul>
|
||||
<li>
|
||||
<Link activeClassName='active' href='/'>
|
||||
<a className='nav-link home-link'>Home</a>
|
||||
</Link>
|
||||
</li>
|
||||
<li>
|
||||
<Link activeClassName='active' href='/about'>
|
||||
<a className='nav-link'>About</a>
|
||||
</Link>
|
||||
</li>
|
||||
</ul>
|
||||
</nav>
|
||||
)
|
16
examples/active-class-name/package.json
Normal file
16
examples/active-class-name/package.json
Normal file
|
@ -0,0 +1,16 @@
|
|||
{
|
||||
"name": "active-class-name",
|
||||
"version": "1.0.0",
|
||||
"scripts": {
|
||||
"dev": "next",
|
||||
"build": "next build",
|
||||
"start": "next start"
|
||||
},
|
||||
"author": "Remy Sharp <remy@leftlogic.com>",
|
||||
"dependencies": {
|
||||
"next": "latest",
|
||||
"react": "^16.0.0",
|
||||
"react-dom": "^16.0.0"
|
||||
},
|
||||
"license": "ISC"
|
||||
}
|
8
examples/active-class-name/pages/about.js
Normal file
8
examples/active-class-name/pages/about.js
Normal file
|
@ -0,0 +1,8 @@
|
|||
import Nav from '../components/Nav'
|
||||
|
||||
export default () => (
|
||||
<div>
|
||||
<Nav />
|
||||
<p>Hello, I'm About.js</p>
|
||||
</div>
|
||||
)
|
8
examples/active-class-name/pages/index.js
Normal file
8
examples/active-class-name/pages/index.js
Normal file
|
@ -0,0 +1,8 @@
|
|||
import Nav from '../components/Nav'
|
||||
|
||||
export default () => (
|
||||
<div>
|
||||
<Nav />
|
||||
<p>Hello, I'm the home page</p>
|
||||
</div>
|
||||
)
|
|
@ -4,10 +4,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example basic-css basic-css-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/basic-css
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/basic-css
|
||||
cd basic-css
|
||||
```
|
||||
|
||||
|
|
|
@ -4,10 +4,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example custom-server-express custom-server-express-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/custom-server-express
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/custom-server-express
|
||||
cd custom-server-express
|
||||
```
|
||||
|
||||
|
|
|
@ -5,5 +5,13 @@ export default () => (
|
|||
<ul>
|
||||
<li><Link href='/b' as='/a'><a>a</a></Link></li>
|
||||
<li><Link href='/a' as='/b'><a>b</a></Link></li>
|
||||
<li>
|
||||
<Link
|
||||
href={{pathname: '/posts', query: { id: '2' }}}
|
||||
as='/posts/2'
|
||||
>
|
||||
<a>post #2</a>
|
||||
</Link>
|
||||
</li>
|
||||
</ul>
|
||||
)
|
||||
|
|
17
examples/custom-server-express/pages/posts.js
Normal file
17
examples/custom-server-express/pages/posts.js
Normal file
|
@ -0,0 +1,17 @@
|
|||
import React, { Component } from 'react'
|
||||
|
||||
export default class extends Component {
|
||||
static getInitialProps ({ query: { id } }) {
|
||||
return { postId: id }
|
||||
}
|
||||
|
||||
render () {
|
||||
return <div>
|
||||
<h1>My blog post #{this.props.postId}</h1>
|
||||
<p>
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod
|
||||
tempor incididunt ut labore et dolore magna aliqua.
|
||||
</p>
|
||||
</div>
|
||||
}
|
||||
}
|
|
@ -18,6 +18,10 @@ app.prepare()
|
|||
return app.render(req, res, '/a', req.query)
|
||||
})
|
||||
|
||||
server.get('/posts/:id', (req, res) => {
|
||||
return app.render(req, res, '/posts', { id: req.params.id })
|
||||
})
|
||||
|
||||
server.get('*', (req, res) => {
|
||||
return handle(req, res)
|
||||
})
|
||||
|
|
|
@ -4,10 +4,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example custom-server-fastify custom-server-fastify-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/custom-server-fastify
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/custom-server-fastify
|
||||
cd custom-server-fastify
|
||||
```
|
||||
|
||||
|
|
|
@ -4,10 +4,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example custom-server-hapi custom-server-hapi-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/custom-server-hapi
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/custom-server-hapi
|
||||
cd custom-server-hapi
|
||||
```
|
||||
|
||||
|
|
|
@ -1,13 +1,19 @@
|
|||
const pathWrapper = (app, pathName, opts) => ({ raw, query }, hapiReply) =>
|
||||
app.renderToHTML(raw.req, raw.res, pathName, query, opts)
|
||||
.then(hapiReply)
|
||||
const { parse } = require('url')
|
||||
|
||||
const defaultHandlerWrapper = app => {
|
||||
const nextHandlerWrapper = app => {
|
||||
const handler = app.getRequestHandler()
|
||||
return ({ raw, url }, hapiReply) =>
|
||||
handler(raw.req, raw.res, url)
|
||||
.then(() => {
|
||||
hapiReply.close(false)
|
||||
})
|
||||
return async ({ raw, url }, h) => {
|
||||
await handler(raw.req, raw.res, url)
|
||||
return h.close
|
||||
}
|
||||
}
|
||||
module.exports = { pathWrapper, defaultHandlerWrapper }
|
||||
const defaultHandlerWrapper = app => async ({ raw: { req, res }, url }) => {
|
||||
const { pathname, query } = parse(url, true)
|
||||
return app.renderToHTML(req, res, pathname, query)
|
||||
}
|
||||
|
||||
const pathWrapper = (app, pathName, opts) => async ({ raw, query, params }) => {
|
||||
return app.renderToHTML(raw.req, raw.res, pathName, { ...query, ...params }, opts)
|
||||
}
|
||||
|
||||
module.exports = { pathWrapper, defaultHandlerWrapper, nextHandlerWrapper }
|
||||
|
|
|
@ -7,11 +7,9 @@
|
|||
"start": "NODE_ENV=production node server.js"
|
||||
},
|
||||
"dependencies": {
|
||||
"hapi": "^16.1.0",
|
||||
"hapi": "^17.1.1",
|
||||
"next": "latest",
|
||||
"react": "^16.0.0",
|
||||
"react-dom": "^16.0.0",
|
||||
"good": "^7.1.0",
|
||||
"good-console": "^6.2.0"
|
||||
"react-dom": "^16.0.0"
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,55 +1,46 @@
|
|||
const next = require('next')
|
||||
const Hapi = require('hapi')
|
||||
const Good = require('good')
|
||||
const { pathWrapper, defaultHandlerWrapper } = require('./next-wrapper')
|
||||
const { pathWrapper, defaultHandlerWrapper, nextHandlerWrapper } = require('./next-wrapper')
|
||||
|
||||
const port = parseInt(process.env.PORT, 10) || 3000
|
||||
const dev = process.env.NODE_ENV !== 'production'
|
||||
const app = next({ dev })
|
||||
const server = new Hapi.Server()
|
||||
|
||||
// add request logging (optional)
|
||||
const pluginOptions = [
|
||||
{
|
||||
register: Good,
|
||||
options: {
|
||||
reporters: {
|
||||
console: [{
|
||||
module: 'good-console'
|
||||
}, 'stdout']
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
|
||||
app.prepare()
|
||||
.then(() => {
|
||||
server.connection({ port })
|
||||
server.register(pluginOptions)
|
||||
.then(() => {
|
||||
server.route({
|
||||
method: 'GET',
|
||||
path: '/a',
|
||||
handler: pathWrapper(app, '/a')
|
||||
})
|
||||
|
||||
server.route({
|
||||
method: 'GET',
|
||||
path: '/b',
|
||||
handler: pathWrapper(app, '/b')
|
||||
})
|
||||
|
||||
server.route({
|
||||
method: 'GET',
|
||||
path: '/{p*}', /* catch all route */
|
||||
handler: defaultHandlerWrapper(app)
|
||||
})
|
||||
|
||||
server.start().catch(error => {
|
||||
console.log('Error starting server')
|
||||
console.log(error)
|
||||
}).then(() => {
|
||||
console.log(`> Ready on http://localhost:${port}`)
|
||||
})
|
||||
})
|
||||
const server = new Hapi.Server({
|
||||
port
|
||||
})
|
||||
|
||||
app
|
||||
.prepare()
|
||||
.then(async () => {
|
||||
server.route({
|
||||
method: 'GET',
|
||||
path: '/a',
|
||||
handler: pathWrapper(app, '/a')
|
||||
})
|
||||
|
||||
server.route({
|
||||
method: 'GET',
|
||||
path: '/b',
|
||||
handler: pathWrapper(app, '/b')
|
||||
})
|
||||
|
||||
server.route({
|
||||
method: 'GET',
|
||||
path: '/_next/{p*}', /* next specific routes */
|
||||
handler: nextHandlerWrapper(app)
|
||||
})
|
||||
|
||||
server.route({
|
||||
method: 'GET',
|
||||
path: '/{p*}', /* catch all route */
|
||||
handler: defaultHandlerWrapper(app)
|
||||
})
|
||||
|
||||
try {
|
||||
await server.start()
|
||||
console.log(`> Ready on http://localhost:${port}`)
|
||||
} catch (error) {
|
||||
console.log('Error starting server')
|
||||
console.log(error)
|
||||
}
|
||||
})
|
||||
|
|
|
@ -4,10 +4,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example custom-server-koa custom-server-koa-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/custom-server-koa
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/custom-server-koa
|
||||
cd custom-server-koa
|
||||
```
|
||||
|
||||
|
|
|
@ -4,10 +4,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example custom-server-micro custom-server-micro-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/custom-server-micro
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/custom-server-micro
|
||||
cd custom-server-micro
|
||||
```
|
||||
|
||||
|
|
|
@ -1,17 +1,18 @@
|
|||
{
|
||||
"main": "server.js",
|
||||
"scripts": {
|
||||
"dev": "node server.js",
|
||||
"dev": "micro-dev --watch server.js",
|
||||
"build": "next build",
|
||||
"start": "NODE_ENV=production node server.js"
|
||||
"start": "NODE_ENV=production micro"
|
||||
},
|
||||
"dependencies": {
|
||||
"micro": "^8.0.1",
|
||||
"micro": "^9.1.0",
|
||||
"micro-route": "^2.4.0",
|
||||
"next": "^3.0.3",
|
||||
"react": "^15.6.1",
|
||||
"react-dom": "^15.6.1"
|
||||
"next": "latest",
|
||||
"react": "^16.1.1",
|
||||
"react-dom": "^16.1.1"
|
||||
},
|
||||
"devDependencies": {
|
||||
"micro-dev": "^1.1.2"
|
||||
"micro-dev": "^2.2.0"
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,29 +1,31 @@
|
|||
const micro = require('micro')
|
||||
const match = require('micro-route/match')
|
||||
const { parse } = require('url')
|
||||
const match = require('micro-route/match')
|
||||
const next = require('next')
|
||||
|
||||
const port = parseInt(process.env.PORT, 10) || 3000
|
||||
const dev = process.env.NODE_ENV !== 'production'
|
||||
|
||||
const app = next({ dev })
|
||||
const handle = app.getRequestHandler()
|
||||
|
||||
const server = micro(async (req, res) => {
|
||||
const isA = req => match(req, '/a')
|
||||
const isB = req => match(req, '/b')
|
||||
|
||||
async function main (req, res) {
|
||||
const parsedUrl = parse(req.url, true)
|
||||
const { query } = parsedUrl
|
||||
|
||||
if (match(req, '/a')) {
|
||||
if (isA(req)) {
|
||||
return app.render(req, res, '/b', query)
|
||||
} else if (match(req, '/b')) {
|
||||
} else if (isB(req)) {
|
||||
return app.render(req, res, '/a', query)
|
||||
}
|
||||
|
||||
return handle(req, res, parsedUrl)
|
||||
})
|
||||
}
|
||||
|
||||
app.prepare().then(() => {
|
||||
server.listen(port, err => {
|
||||
if (err) throw err
|
||||
console.log(`> Ready on http://localhost:${port}`)
|
||||
})
|
||||
})
|
||||
async function setup (handler) {
|
||||
await app.prepare()
|
||||
return handler
|
||||
}
|
||||
|
||||
module.exports = setup(main)
|
||||
|
|
40
examples/custom-server-nodemon/README.md
Normal file
40
examples/custom-server-nodemon/README.md
Normal file
|
@ -0,0 +1,40 @@
|
|||
[![Deploy to now](https://deploy.now.sh/static/button.svg)](https://deploy.now.sh/?repo=https://github.com/zeit/next.js/tree/master/examples/custom-server-nodemon)
|
||||
|
||||
# Custom server with Nodemon example
|
||||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example custom-server-nodemon custom-server-nodemon-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/custom-server-nodemon
|
||||
cd custom-server-nodemon
|
||||
```
|
||||
|
||||
Install it and run:
|
||||
|
||||
```bash
|
||||
npm install
|
||||
npm run dev
|
||||
```
|
||||
|
||||
Deploy it to the cloud with [now](https://zeit.co/now) ([download](https://zeit.co/download))
|
||||
|
||||
```bash
|
||||
now
|
||||
```
|
||||
|
||||
## The idea behind the example
|
||||
|
||||
The example shows how you can apply [Nodemon](https://nodemon.io/) to a custom server to have live reload of the server code without being affected by the Next.js universal code.
|
3
examples/custom-server-nodemon/nodemon.json
Normal file
3
examples/custom-server-nodemon/nodemon.json
Normal file
|
@ -0,0 +1,3 @@
|
|||
{
|
||||
"watch": ["server/**/*.js"]
|
||||
}
|
15
examples/custom-server-nodemon/package.json
Normal file
15
examples/custom-server-nodemon/package.json
Normal file
|
@ -0,0 +1,15 @@
|
|||
{
|
||||
"scripts": {
|
||||
"dev": "nodemon server/index.js",
|
||||
"build": "next build",
|
||||
"start": "NODE_ENV=production node server/index.js"
|
||||
},
|
||||
"dependencies": {
|
||||
"next": "latest",
|
||||
"react": "^16.2.0",
|
||||
"react-dom": "^16.2.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"nodemon": "^1.12.1"
|
||||
}
|
||||
}
|
3
examples/custom-server-nodemon/pages/a.js
Normal file
3
examples/custom-server-nodemon/pages/a.js
Normal file
|
@ -0,0 +1,3 @@
|
|||
import React from 'react'
|
||||
|
||||
export default () => <div>a</div>
|
3
examples/custom-server-nodemon/pages/b.js
Normal file
3
examples/custom-server-nodemon/pages/b.js
Normal file
|
@ -0,0 +1,3 @@
|
|||
import React from 'react'
|
||||
|
||||
export default () => <div>b</div>
|
9
examples/custom-server-nodemon/pages/index.js
Normal file
9
examples/custom-server-nodemon/pages/index.js
Normal file
|
@ -0,0 +1,9 @@
|
|||
import React from 'react'
|
||||
import Link from 'next/link'
|
||||
|
||||
export default () => (
|
||||
<ul>
|
||||
<li><Link href='/b' as='/a'><a>a</a></Link></li>
|
||||
<li><Link href='/a' as='/b'><a>b</a></Link></li>
|
||||
</ul>
|
||||
)
|
28
examples/custom-server-nodemon/server/index.js
Normal file
28
examples/custom-server-nodemon/server/index.js
Normal file
|
@ -0,0 +1,28 @@
|
|||
const { createServer } = require('http')
|
||||
const { parse } = require('url')
|
||||
const next = require('next')
|
||||
|
||||
const port = parseInt(process.env.PORT, 10) || 3000
|
||||
const dev = process.env.NODE_ENV !== 'production'
|
||||
const app = next({ dev })
|
||||
const handle = app.getRequestHandler()
|
||||
|
||||
app.prepare()
|
||||
.then(() => {
|
||||
createServer((req, res) => {
|
||||
const parsedUrl = parse(req.url, true)
|
||||
const { pathname, query } = parsedUrl
|
||||
|
||||
if (pathname === '/a') {
|
||||
app.render(req, res, '/b', query)
|
||||
} else if (pathname === '/b') {
|
||||
app.render(req, res, '/a', query)
|
||||
} else {
|
||||
handle(req, res, parsedUrl)
|
||||
}
|
||||
})
|
||||
.listen(port, (err) => {
|
||||
if (err) throw err
|
||||
console.log(`> Ready on http://localhost:${port}`)
|
||||
})
|
||||
})
|
15
examples/custom-server-polka/package.json
Normal file
15
examples/custom-server-polka/package.json
Normal file
|
@ -0,0 +1,15 @@
|
|||
{
|
||||
"name": "custom-server-polka",
|
||||
"version": "1.0.0",
|
||||
"scripts": {
|
||||
"dev": "node server.js",
|
||||
"build": "next build",
|
||||
"start": "NODE_ENV=production node server.js"
|
||||
},
|
||||
"dependencies": {
|
||||
"next": "latest",
|
||||
"polka": "0.2.3",
|
||||
"react": "16.2.0",
|
||||
"react-dom": "16.2.0"
|
||||
}
|
||||
}
|
3
examples/custom-server-polka/pages/a.js
Normal file
3
examples/custom-server-polka/pages/a.js
Normal file
|
@ -0,0 +1,3 @@
|
|||
import React from 'react'
|
||||
|
||||
export default () => <div>a</div>
|
3
examples/custom-server-polka/pages/b.js
Normal file
3
examples/custom-server-polka/pages/b.js
Normal file
|
@ -0,0 +1,3 @@
|
|||
import React from 'react'
|
||||
|
||||
export default () => <div>b</div>
|
17
examples/custom-server-polka/pages/index.js
Normal file
17
examples/custom-server-polka/pages/index.js
Normal file
|
@ -0,0 +1,17 @@
|
|||
import React from 'react'
|
||||
import Link from 'next/link'
|
||||
|
||||
export default () => (
|
||||
<ul>
|
||||
<li>
|
||||
<Link href='/b' as='/a'>
|
||||
<a>a</a>
|
||||
</Link>
|
||||
</li>
|
||||
<li>
|
||||
<Link href='/a' as='/b'>
|
||||
<a>b</a>
|
||||
</Link>
|
||||
</li>
|
||||
</ul>
|
||||
)
|
21
examples/custom-server-polka/server.js
Normal file
21
examples/custom-server-polka/server.js
Normal file
|
@ -0,0 +1,21 @@
|
|||
const polka = require('polka')
|
||||
const next = require('next')
|
||||
|
||||
const port = parseInt(process.env.PORT, 10) || 3000
|
||||
const dev = process.env.NODE_ENV !== 'production'
|
||||
const app = next({ dev })
|
||||
const handle = app.getRequestHandler()
|
||||
|
||||
app.prepare().then(() => {
|
||||
const server = polka()
|
||||
|
||||
server.get('/a', (req, res) => app.render(req, res, '/b', req.query))
|
||||
|
||||
server.get('/b', (req, res) => app.render(req, res, '/a', req.query))
|
||||
|
||||
server.get('*', (req, res) => handle(req, res))
|
||||
|
||||
server
|
||||
.listen(port)
|
||||
.then(() => console.log(`> Ready on http://localhost:${port}`))
|
||||
})
|
|
@ -4,10 +4,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example custom-server custom-server-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/custom-server
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/custom-server
|
||||
cd custom-server
|
||||
```
|
||||
|
||||
|
|
|
@ -4,10 +4,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example data-fetch data-fetch-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/data-fetch
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/data-fetch
|
||||
cd data-fetch
|
||||
```
|
||||
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
"start": "next start"
|
||||
},
|
||||
"dependencies": {
|
||||
"isomorphic-fetch": "^2.2.1",
|
||||
"isomorphic-unfetch": "^2.0.0",
|
||||
"next": "latest",
|
||||
"react": "^16.0.0",
|
||||
"react-dom": "^16.0.0"
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
|
||||
import React from 'react'
|
||||
import Link from 'next/link'
|
||||
import 'isomorphic-fetch'
|
||||
import 'isomorphic-unfetch'
|
||||
|
||||
export default class MyPage extends React.Component {
|
||||
static async getInitialProps () {
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
|
||||
import React from 'react'
|
||||
import Link from 'next/link'
|
||||
import 'isomorphic-fetch'
|
||||
import 'isomorphic-unfetch'
|
||||
|
||||
export default class MyPage extends React.Component {
|
||||
static async getInitialProps () {
|
||||
|
|
|
@ -4,10 +4,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example form-handler form-handler-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/form-handler
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/form-handler
|
||||
cd form-handler
|
||||
```
|
||||
|
||||
|
|
|
@ -14,11 +14,11 @@
|
|||
"license": "ISC",
|
||||
"dependencies": {
|
||||
"express": "^4.15.4",
|
||||
"next": "^3.2.2",
|
||||
"next": "latest",
|
||||
"react": "^16.1.1",
|
||||
"react-dom": "^16.1.1",
|
||||
"next-redux-wrapper": "^1.3.2",
|
||||
"react": "^15.6.1",
|
||||
"react-bootstrap": "^0.31.3",
|
||||
"react-dom": "^15.6.1",
|
||||
"react-redux": "^5.0.6",
|
||||
"redux": "^3.7.2",
|
||||
"redux-thunk": "^2.2.0"
|
||||
|
|
8
examples/gh-pages/.babelrc
Normal file
8
examples/gh-pages/.babelrc
Normal file
|
@ -0,0 +1,8 @@
|
|||
{
|
||||
"presets": [
|
||||
"next/babel"
|
||||
],
|
||||
"plugins": [
|
||||
["transform-define", "./env-config.js"]
|
||||
]
|
||||
}
|
2
examples/gh-pages/.gitignore
vendored
Normal file
2
examples/gh-pages/.gitignore
vendored
Normal file
|
@ -0,0 +1,2 @@
|
|||
node_modules
|
||||
.next
|
57
examples/gh-pages/README.md
Normal file
57
examples/gh-pages/README.md
Normal file
|
@ -0,0 +1,57 @@
|
|||
# gh-pages Hello World example
|
||||
|
||||
## How to use
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/gh-pages
|
||||
cd gh-pages
|
||||
```
|
||||
|
||||
Install it and run:
|
||||
|
||||
```bash
|
||||
npm install
|
||||
npm run dev
|
||||
```
|
||||
|
||||
### Deploy it to github
|
||||
|
||||
Edit ```env-config.js``` and replace ```'Next-gh-page-example'``` by your project name.
|
||||
|
||||
Edit ```next.config.js``` and replace ```'Next-gh-page-example'``` by your project name.
|
||||
|
||||
1. Create repository.
|
||||
2. Link it to your github account.
|
||||
3. Publish your master branch.
|
||||
|
||||
```bash
|
||||
npm run deploy
|
||||
```
|
||||
|
||||
Test it:
|
||||
|
||||
Replace 'github-user-name' and 'github-project-name'
|
||||
|
||||
```bash
|
||||
|
||||
https://github-user-name.github.io/github-project-name/
|
||||
|
||||
```
|
||||
|
||||
Example:
|
||||
|
||||
```bash
|
||||
|
||||
https://github.com/thierryc/Next-gh-page-example/
|
||||
|
||||
https://thierryc.github.io/Next-gh-page-example/
|
||||
|
||||
```
|
||||
|
||||
## The idea behind the example
|
||||
|
||||
This example shows the most basic idea behind Next. We have 2 pages: `pages/index.js` and `pages/about.js`. The former responds to `/` requests and the latter to `/about`. Using `next/link` you can add hyperlinks between them with universal routing capabilities.
|
5
examples/gh-pages/env-config.js
Normal file
5
examples/gh-pages/env-config.js
Normal file
|
@ -0,0 +1,5 @@
|
|||
const prod = process.env.NODE_ENV === 'production'
|
||||
|
||||
module.exports = {
|
||||
'process.env.BACKEND_URL': prod ? '/Next-gh-page-example' : ''
|
||||
}
|
15
examples/gh-pages/next.config.js
Normal file
15
examples/gh-pages/next.config.js
Normal file
|
@ -0,0 +1,15 @@
|
|||
// This file is not going through babel transformation.
|
||||
// So, we write it in vanilla JS
|
||||
// (But you could use ES2015 features supported by your Node.js version)
|
||||
|
||||
const debug = process.env.NODE_ENV !== 'production'
|
||||
|
||||
module.exports = {
|
||||
exportPathMap: function () {
|
||||
return {
|
||||
'/': { page: '/' },
|
||||
'/about': { page: '/about' }
|
||||
}
|
||||
},
|
||||
assetPrefix: !debug ? '/Next-gh-page-example/' : ''
|
||||
}
|
20
examples/gh-pages/package.json
Normal file
20
examples/gh-pages/package.json
Normal file
|
@ -0,0 +1,20 @@
|
|||
{
|
||||
"name": "gh-pages",
|
||||
"version": "1.0.0",
|
||||
"scripts": {
|
||||
"dev": "next",
|
||||
"build": "next build",
|
||||
"start": "next start",
|
||||
"export": "next export",
|
||||
"deploy": "rm -rf node_modules/.cache && next build && next export && touch out/.nojekyll && git add out/ && git commit -m \"Deploy Next.js to gh-pages\" && git subtree push --prefix out origin gh-pages"
|
||||
},
|
||||
"dependencies": {
|
||||
"next": "latest",
|
||||
"react": "^16.0.0",
|
||||
"react-dom": "^16.0.0"
|
||||
},
|
||||
"license": "ISC",
|
||||
"devDependencies": {
|
||||
"babel-plugin-transform-define": "^1.3.0"
|
||||
}
|
||||
}
|
7
examples/gh-pages/pages/about.js
Normal file
7
examples/gh-pages/pages/about.js
Normal file
|
@ -0,0 +1,7 @@
|
|||
import Link from 'next/link'
|
||||
export default () => (
|
||||
<div>
|
||||
<div>About us</div>
|
||||
<div>Back to <Link href='/' as={process.env.BACKEND_URL + '/'}><a>Home</a></Link></div>
|
||||
</div>
|
||||
)
|
4
examples/gh-pages/pages/index.js
Normal file
4
examples/gh-pages/pages/index.js
Normal file
|
@ -0,0 +1,4 @@
|
|||
import Link from 'next/link'
|
||||
export default () => (
|
||||
<div>Hello World. <Link href='/about' as={process.env.BACKEND_URL + '/about'}><a>About</a></Link></div>
|
||||
)
|
|
@ -4,10 +4,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example head-elements head-elements-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/head-elements
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/head-elements
|
||||
cd head-elements
|
||||
```
|
||||
|
||||
|
|
|
@ -4,10 +4,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example hello-world hello-world-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/hello-world
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/hello-world
|
||||
cd hello-world
|
||||
```
|
||||
|
||||
|
|
3
examples/hello-world/pages/about2.js
Normal file
3
examples/hello-world/pages/about2.js
Normal file
|
@ -0,0 +1,3 @@
|
|||
export default () => (
|
||||
<div>About 2</div>
|
||||
)
|
3
examples/hello-world/pages/day/index.js
Normal file
3
examples/hello-world/pages/day/index.js
Normal file
|
@ -0,0 +1,3 @@
|
|||
export default () => (
|
||||
<div>Hello Day</div>
|
||||
)
|
|
@ -4,10 +4,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example layout-component layout-component-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/layout-component
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/layout-component
|
||||
cd layout-component
|
||||
```
|
||||
|
||||
|
|
|
@ -4,10 +4,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example nested-components nested-components-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/nested-components
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/nested-components
|
||||
cd nested-components
|
||||
```
|
||||
|
||||
|
|
27
examples/only-client-render-external-dependencies/README.md
Normal file
27
examples/only-client-render-external-dependencies/README.md
Normal file
|
@ -0,0 +1,27 @@
|
|||
# Hello World example
|
||||
|
||||
## Only client render for external dependencies
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/only-client-render-external-dependencies
|
||||
cd only-client-render-external-dependencies
|
||||
```
|
||||
|
||||
Install it and run:
|
||||
|
||||
```bash
|
||||
npm install
|
||||
npm run dev
|
||||
```
|
||||
|
||||
Deploy it to the cloud with [now](https://zeit.co/now) ([download](https://zeit.co/download))
|
||||
|
||||
```bash
|
||||
now
|
||||
```
|
||||
|
||||
## The idea behind the example
|
||||
|
||||
This example shows how to use an external dependency that only allows client-render.
|
|
@ -0,0 +1,16 @@
|
|||
{
|
||||
"name": "only-client-render-external-dependencies",
|
||||
"version": "1.0.0",
|
||||
"scripts": {
|
||||
"dev": "next",
|
||||
"build": "next build",
|
||||
"start": "next start"
|
||||
},
|
||||
"dependencies": {
|
||||
"next": "latest",
|
||||
"react": "^16.0.0",
|
||||
"react-dom": "^16.0.0",
|
||||
"recharts": "^1.0.0-beta.0"
|
||||
},
|
||||
"license": "ISC"
|
||||
}
|
|
@ -0,0 +1,44 @@
|
|||
import React from 'react'
|
||||
let LineChart
|
||||
let Line
|
||||
class Chart extends React.Component {
|
||||
constructor () {
|
||||
super()
|
||||
this.state = {
|
||||
chart: false,
|
||||
data: [
|
||||
{name: 'Page A', uv: 4000, pv: 2400, amt: 2400},
|
||||
{name: 'Page B', uv: 3000, pv: 1398, amt: 2210},
|
||||
{name: 'Page C', uv: 2000, pv: 9800, amt: 2290},
|
||||
{name: 'Page D', uv: 2780, pv: 3908, amt: 2000},
|
||||
{name: 'Page E', uv: 1890, pv: 4800, amt: 2181},
|
||||
{name: 'Page F', uv: 2390, pv: 3800, amt: 2500},
|
||||
{name: 'Page G', uv: 3490, pv: 4300, amt: 2100}
|
||||
]
|
||||
}
|
||||
}
|
||||
|
||||
componentDidMount () {
|
||||
LineChart = require('recharts').LineChart
|
||||
Line = require('recharts').Line
|
||||
|
||||
this.setState({
|
||||
chart: true
|
||||
})
|
||||
}
|
||||
|
||||
render () {
|
||||
return (
|
||||
<div>
|
||||
<h1>Another chart</h1>
|
||||
{this.state.chart &&
|
||||
<LineChart width={400} height={400} data={this.state.data}>
|
||||
<Line type='monotone' dataKey='uv' stroke='#8884d8' />
|
||||
</LineChart>
|
||||
}
|
||||
</div>
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
export default Chart
|
|
@ -0,0 +1,47 @@
|
|||
import React from 'react'
|
||||
import Link from 'next/link'
|
||||
let LineChart
|
||||
let Line
|
||||
|
||||
class Index extends React.Component {
|
||||
constructor () {
|
||||
super()
|
||||
this.state = {
|
||||
chart: false,
|
||||
data: [
|
||||
{name: 'Page A', uv: 1000, pv: 2400, amt: 2400},
|
||||
{name: 'Page B', uv: 3000, pv: 1398, amt: 2210},
|
||||
{name: 'Page C', uv: 2000, pv: 9800, amt: 2290},
|
||||
{name: 'Page D', uv: 2780, pv: 3908, amt: 2000},
|
||||
{name: 'Page E', uv: 1890, pv: 4800, amt: 2181},
|
||||
{name: 'Page F', uv: 2390, pv: 3800, amt: 2500},
|
||||
{name: 'Page G', uv: 3490, pv: 4300, amt: 2100}
|
||||
]
|
||||
}
|
||||
}
|
||||
|
||||
componentDidMount () {
|
||||
LineChart = require('recharts').LineChart
|
||||
Line = require('recharts').Line
|
||||
|
||||
this.setState({
|
||||
chart: true
|
||||
})
|
||||
}
|
||||
|
||||
render () {
|
||||
return (
|
||||
<div>
|
||||
<h1>Chart</h1>
|
||||
<Link href='/chart'><a>Go to another chart</a></Link>
|
||||
{this.state.chart &&
|
||||
<LineChart width={400} height={400} data={this.state.data}>
|
||||
<Line type='monotone' dataKey='uv' stroke='#8884d8' />
|
||||
</LineChart>
|
||||
}
|
||||
</div>
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
export default Index
|
|
@ -4,10 +4,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example page-transitions page-transitions-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/page-transitions
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/page-transitions
|
||||
cd page-transitions
|
||||
```
|
||||
|
||||
|
|
|
@ -4,10 +4,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example parameterized-routing parameterized-routing-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/parameterized-routing
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/parameterized-routing
|
||||
cd parameterized-routing
|
||||
```
|
||||
|
||||
|
|
50
examples/pass-server-data/README.md
Normal file
50
examples/pass-server-data/README.md
Normal file
|
@ -0,0 +1,50 @@
|
|||
[![Deploy to now](https://deploy.now.sh/static/button.svg)](https://deploy.now.sh/?repo=https://github.com/zeit/next.js/tree/master/examples/pass-server-data)
|
||||
|
||||
# Pass Server Data Directly to a Next.js Page during SSR
|
||||
|
||||
## How to use
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/pass-server-data
|
||||
cd pass-server-data
|
||||
```
|
||||
|
||||
Install it and run:
|
||||
|
||||
```bash
|
||||
npm install
|
||||
npm run dev
|
||||
```
|
||||
|
||||
Deploy it to the cloud with [now](https://zeit.co/now) ([download](https://zeit.co/download))
|
||||
|
||||
```bash
|
||||
now
|
||||
```
|
||||
|
||||
## The idea behind the example
|
||||
|
||||
If you already have a custom server which has local data (for instance cached data from an API call, or data read
|
||||
from a file at startup) that you wish to make available in the Next.js page, you can pass that data in the query
|
||||
parameter of `nextApp.render()`.
|
||||
|
||||
This is not the only way to pass data. You could also expose an endpoint and make a `fetch()` call to localhost, or you could
|
||||
import server-side code with `eval` (necessary to prevent webpack from trying to package your server code). However both
|
||||
solutions leave something to be desired in either performance or elegance.
|
||||
|
||||
This example shows the express server at `server.js` reading in a file at load time with static data (this could also have been
|
||||
data cached from an API call) in `operations/get-item.js`. It has two routes: a home page, and an item page. The item page uses
|
||||
data from the get-item operation, passed as a query parameter in `routes/item.js`.
|
||||
|
||||
We use this data in `pages/item.js` if rendered server-side, or make a fetch request if rendered client-side.
|
||||
The server knows whether or not to use next.js to render the route based on the Accept header, which will be
|
||||
`application/json` when we fetch client-side.
|
||||
|
||||
Take a look at the following files:
|
||||
|
||||
* server.js
|
||||
* routes/item.js
|
||||
* pages/item.js
|
||||
* operations/get-item.js
|
5
examples/pass-server-data/data/item.json
Normal file
5
examples/pass-server-data/data/item.json
Normal file
|
@ -0,0 +1,5 @@
|
|||
{
|
||||
"title": "Now",
|
||||
"subtitle": "Realtime global deployments",
|
||||
"seller": "Zeit"
|
||||
}
|
12
examples/pass-server-data/operations/get-item.js
Normal file
12
examples/pass-server-data/operations/get-item.js
Normal file
|
@ -0,0 +1,12 @@
|
|||
const fs = require('fs')
|
||||
|
||||
// In this case, data read from the fs, but it could also be a cached API result.
|
||||
const data = fs.readFileSync('./data/item.json', 'utf8')
|
||||
const parsedData = JSON.parse(data)
|
||||
|
||||
function getItem () {
|
||||
console.log('Requested Item Data:', data)
|
||||
return parsedData
|
||||
}
|
||||
|
||||
module.exports = { getItem }
|
16
examples/pass-server-data/package.json
Normal file
16
examples/pass-server-data/package.json
Normal file
|
@ -0,0 +1,16 @@
|
|||
{
|
||||
"name": "pass-server-data",
|
||||
"version": "1.0.0",
|
||||
"scripts": {
|
||||
"dev": "node server.js",
|
||||
"build": "next build",
|
||||
"start": "NODE_ENV=production node server.js"
|
||||
},
|
||||
"dependencies": {
|
||||
"express": "^4.14.0",
|
||||
"isomorphic-fetch": "^2.2.1",
|
||||
"next": "latest",
|
||||
"react": "^15.4.2",
|
||||
"react-dom": "^15.4.2"
|
||||
}
|
||||
}
|
8
examples/pass-server-data/pages/index.js
Normal file
8
examples/pass-server-data/pages/index.js
Normal file
|
@ -0,0 +1,8 @@
|
|||
import React from 'react'
|
||||
import Link from 'next/link'
|
||||
|
||||
export default () => (
|
||||
<ul>
|
||||
<li><Link href='/item'><a>View Item</a></Link></li>
|
||||
</ul>
|
||||
)
|
33
examples/pass-server-data/pages/item.js
Normal file
33
examples/pass-server-data/pages/item.js
Normal file
|
@ -0,0 +1,33 @@
|
|||
import {Component} from 'react'
|
||||
import Link from 'next/link'
|
||||
import fetch from 'isomorphic-fetch'
|
||||
|
||||
export default class extends Component {
|
||||
static async getInitialProps ({ req, query }) {
|
||||
const isServer = !!req
|
||||
|
||||
console.log('getInitialProps called:', isServer ? 'server' : 'client')
|
||||
|
||||
if (isServer) {
|
||||
// When being rendered server-side, we have access to our data in query that we put there in routes/item.js,
|
||||
// saving us an http call. Note that if we were to try to require('../operations/get-item') here,
|
||||
// it would result in a webpack error.
|
||||
return { item: query.itemData }
|
||||
} else {
|
||||
// On the client, we should fetch the data remotely
|
||||
const res = await fetch('/_data/item', {headers: {'Accept': 'application/json'}})
|
||||
const json = await res.json()
|
||||
return { item: json }
|
||||
}
|
||||
}
|
||||
|
||||
render () {
|
||||
return (
|
||||
<div className='item'>
|
||||
<div><Link href='/'><a>Back Home</a></Link></div>
|
||||
<h1>{this.props.item.title}</h1>
|
||||
<h2>{this.props.item.subtitle} - {this.props.item.seller}</h2>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
}
|
39
examples/pass-server-data/server.js
Normal file
39
examples/pass-server-data/server.js
Normal file
|
@ -0,0 +1,39 @@
|
|||
const express = require('express')
|
||||
const next = require('next')
|
||||
const api = require('./operations/get-item')
|
||||
|
||||
const dev = process.env.NODE_ENV !== 'production'
|
||||
const app = next({ dev })
|
||||
const handle = app.getRequestHandler()
|
||||
|
||||
app.prepare().then(() => {
|
||||
const server = express()
|
||||
|
||||
// Set up home page as a simple render of the page.
|
||||
server.get('/', (req, res) => {
|
||||
console.log('Render home page')
|
||||
return app.render(req, res, '/', req.query)
|
||||
})
|
||||
|
||||
// Serve the item webpage with next.js as the renderer
|
||||
server.get('/item', (req, res) => {
|
||||
const itemData = api.getItem()
|
||||
app.render(req, res, '/item', { itemData })
|
||||
})
|
||||
|
||||
// When rendering client-side, we will request the same data from this route
|
||||
server.get('/_data/item', (req, res) => {
|
||||
const itemData = api.getItem()
|
||||
res.json(itemData)
|
||||
})
|
||||
|
||||
// Fall-back on other next.js assets.
|
||||
server.get('*', (req, res) => {
|
||||
return handle(req, res)
|
||||
})
|
||||
|
||||
server.listen(3000, (err) => {
|
||||
if (err) throw err
|
||||
console.log('> Ready on http://localhost:3000')
|
||||
})
|
||||
})
|
|
@ -3,10 +3,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example progressive-render progressive-render-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/progressive-render
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/progressive-render
|
||||
cd progressive-render
|
||||
```
|
||||
|
||||
|
|
|
@ -4,10 +4,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example root-static-files root-static-files-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/custom-server
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/custom-server
|
||||
cd custom-server
|
||||
```
|
||||
|
||||
|
|
|
@ -3,10 +3,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example shared-modules shared-modules-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/shared-modules
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/shared-modules
|
||||
cd shared-modules
|
||||
```
|
||||
|
||||
|
|
|
@ -4,10 +4,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example ssr-caching ssr-caching-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/ssr-caching
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/ssr-caching
|
||||
cd ssr-caching
|
||||
```
|
||||
|
||||
|
|
|
@ -4,10 +4,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example svg-components svg-components-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/svg-components
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/svg-components
|
||||
cd svg-components
|
||||
```
|
||||
|
||||
|
|
|
@ -7,7 +7,9 @@
|
|||
"start": "next start"
|
||||
},
|
||||
"dependencies": {
|
||||
"next": "latest"
|
||||
"next": "latest",
|
||||
"react": "latest,
|
||||
"react-dom": "latest"
|
||||
},
|
||||
"devDependencies": {
|
||||
"babel-plugin-inline-react-svg": "^0.2.0"
|
||||
|
|
|
@ -4,10 +4,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example using-inferno using-inferno-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/using-inferno
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/using-inferno
|
||||
cd using-inferno
|
||||
```
|
||||
|
||||
|
|
|
@ -4,10 +4,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example using-preact using-preact-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/using-preact
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/using-preact
|
||||
cd using-preact
|
||||
```
|
||||
|
||||
|
|
|
@ -1,16 +1,3 @@
|
|||
module.exports = {
|
||||
webpack: function (config, { dev }) {
|
||||
// For the development version, we'll use React.
|
||||
// Because, it supports react hot loading and so on.
|
||||
if (dev) {
|
||||
return config
|
||||
}
|
||||
const withPreact = require('@zeit/next-preact')
|
||||
|
||||
config.resolve.alias = {
|
||||
'react': 'preact-compat/dist/preact-compat',
|
||||
'react-dom': 'preact-compat/dist/preact-compat'
|
||||
}
|
||||
|
||||
return config
|
||||
}
|
||||
}
|
||||
module.exports = withPreact()
|
||||
|
|
|
@ -7,16 +7,10 @@
|
|||
"start": "NODE_ENV=production node server.js"
|
||||
},
|
||||
"dependencies": {
|
||||
"module-alias": "^2.0.0",
|
||||
"@zeit/next-preact": "0.0.4",
|
||||
"next": "latest",
|
||||
"preact": "^7.2.0",
|
||||
"preact-compat": "^3.14.0",
|
||||
"react": "^16.0.0",
|
||||
"react-dom": "^16.0.0"
|
||||
"preact": "8.2.7",
|
||||
"preact-compat": "3.18.0"
|
||||
},
|
||||
"license": "ISC",
|
||||
"devDependencies": {
|
||||
"react": "~15.6.1",
|
||||
"react-dom": "~15.6.1"
|
||||
}
|
||||
"license": "ISC"
|
||||
}
|
||||
|
|
|
@ -1,13 +1,7 @@
|
|||
const port = parseInt(process.env.PORT, 10) || 3000
|
||||
const dev = process.env.NODE_ENV !== 'production'
|
||||
const moduleAlias = require('module-alias')
|
||||
|
||||
// For the development version, we'll use React.
|
||||
// Because, it support react hot loading and so on.
|
||||
if (!dev) {
|
||||
moduleAlias.addAlias('react', 'preact-compat')
|
||||
moduleAlias.addAlias('react-dom', 'preact-compat')
|
||||
}
|
||||
require('@zeit/next-preact/alias')()
|
||||
|
||||
const { createServer } = require('http')
|
||||
const { parse } = require('url')
|
||||
|
|
|
@ -3,10 +3,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example using-router using-router-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/using-router
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/using-router
|
||||
cd using-router
|
||||
```
|
||||
|
||||
|
|
|
@ -3,10 +3,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example using-with-router using-with-router-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/using-with-router
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/using-with-router
|
||||
cd using-with-router
|
||||
```
|
||||
|
||||
|
|
|
@ -2,10 +2,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example with-absolute-imports with-absolute-imports-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/with-absolute-import
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/with-absolute-import
|
||||
cd with-absolute-import
|
||||
```
|
||||
|
||||
|
|
|
@ -6,8 +6,8 @@
|
|||
},
|
||||
"dependencies": {
|
||||
"babel-plugin-module-resolver": "^2.7.1",
|
||||
"next": "^3.0.6",
|
||||
"react": "^15.6.1",
|
||||
"react-dom": "^15.6.1"
|
||||
"next": "latest",
|
||||
"react": "^16.1.1",
|
||||
"react-dom": "^16.1.1"
|
||||
}
|
||||
}
|
||||
|
|
|
@ -4,10 +4,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example with-algolia-react-instantsearch with-algolia-react-instantsearch-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/with-algolia-react-instantsearch
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/with-algolia-react-instantsearch
|
||||
cd with-algolia-react-instantsearch
|
||||
```
|
||||
|
||||
|
|
|
@ -7,11 +7,11 @@
|
|||
},
|
||||
"dependencies": {
|
||||
"css-loader": "^0.28.1",
|
||||
"next": "^2.4.7",
|
||||
"prop-types": "^15.5.10",
|
||||
"qs": "^6.4.0",
|
||||
"react": "^15.5.4",
|
||||
"react-dom": "^15.5.4",
|
||||
"next": "latest",
|
||||
"react": "^16.1.1",
|
||||
"react-dom": "^16.1.1",
|
||||
"react-instantsearch": "beta",
|
||||
"react-instantsearch-theme-algolia": "beta",
|
||||
"style-loader": "^0.17.0"
|
||||
|
|
|
@ -4,10 +4,21 @@
|
|||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example with-amp with-amp-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js.git):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/master | tar -xz --strip=2 next.js-master/examples/with-amp
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/with-amp
|
||||
cd with-amp
|
||||
```
|
||||
|
||||
|
|
40
examples/with-analytics/README.md
Normal file
40
examples/with-analytics/README.md
Normal file
|
@ -0,0 +1,40 @@
|
|||
[![Deploy to now](https://deploy.now.sh/static/button.svg)](https://deploy.now.sh/?repo=https://github.com/zeit/next.js/tree/master/examples/with-analytics)
|
||||
|
||||
# Example app with analytics
|
||||
|
||||
## How to use
|
||||
|
||||
### Using `create-next-app`
|
||||
|
||||
Download [`create-next-app`](https://github.com/segmentio/create-next-app) to bootstrap the example:
|
||||
|
||||
```
|
||||
npm i -g create-next-app
|
||||
create-next-app --example with-analytics with-analytics-app
|
||||
```
|
||||
|
||||
### Download manually
|
||||
|
||||
Download the example [or clone the repo](https://github.com/zeit/next.js):
|
||||
|
||||
```bash
|
||||
curl https://codeload.github.com/zeit/next.js/tar.gz/canary | tar -xz --strip=2 next.js-canary/examples/with-analytics
|
||||
cd with-analytics
|
||||
```
|
||||
|
||||
Install it and run:
|
||||
|
||||
```bash
|
||||
yarn
|
||||
yarn dev
|
||||
```
|
||||
|
||||
Deploy it to the cloud with [now](https://zeit.co/now) ([download](https://zeit.co/download))
|
||||
|
||||
```bash
|
||||
now
|
||||
```
|
||||
|
||||
## The idea behind the example
|
||||
|
||||
This example shows how to use Next.js along with [Segment Analytics](https://segment.com). A custom document is used in inject the [Segment snippet](https://github.com/segmentio/snippet) into the `<head>` and components fire ["track"](https://segment.com/docs/spec/track/) events based on user actions.
|
14
examples/with-analytics/components/Header.js
Normal file
14
examples/with-analytics/components/Header.js
Normal file
|
@ -0,0 +1,14 @@
|
|||
import React from 'react'
|
||||
import Link from 'next/link'
|
||||
|
||||
export default () => (
|
||||
<header>
|
||||
<nav>
|
||||
<ul>
|
||||
<li><Link href='/'><a>Home</a></Link></li>
|
||||
<li><Link href='/about'><a>About</a></Link></li>
|
||||
<li><Link href='/contact'><a>Contact</a></Link></li>
|
||||
</ul>
|
||||
</nav>
|
||||
</header>
|
||||
)
|
14
examples/with-analytics/package.json
Normal file
14
examples/with-analytics/package.json
Normal file
|
@ -0,0 +1,14 @@
|
|||
{
|
||||
"name": "with-analytics",
|
||||
"scripts": {
|
||||
"dev": "next",
|
||||
"build": "next build",
|
||||
"start": "next start"
|
||||
},
|
||||
"dependencies": {
|
||||
"@segment/snippet": "^4.0.1",
|
||||
"next": "latest",
|
||||
"react": "^16.2.0",
|
||||
"react-dom": "^16.2.0"
|
||||
}
|
||||
}
|
44
examples/with-analytics/pages/_document.js
Normal file
44
examples/with-analytics/pages/_document.js
Normal file
|
@ -0,0 +1,44 @@
|
|||
import React from 'react'
|
||||
import Document, { Head, Main, NextScript } from 'next/document'
|
||||
import * as snippet from '@segment/snippet'
|
||||
|
||||
const {
|
||||
// This write key is associated with https://segment.com/nextjs-example/sources/nextjs.
|
||||
ANALYTICS_WRITE_KEY = 'NPsk1GimHq09s7egCUlv7D0tqtUAU5wa',
|
||||
NODE_ENV = 'development'
|
||||
} = process.env
|
||||
|
||||
export default class extends Document {
|
||||
static getInitialProps ({ renderPage }) {
|
||||
const { html, head, errorHtml, chunks } = renderPage()
|
||||
return { html, head, errorHtml, chunks }
|
||||
}
|
||||
|
||||
renderSnippet () {
|
||||
const opts = {
|
||||
apiKey: ANALYTICS_WRITE_KEY,
|
||||
page: true // Set this to `false` if you want to manually fire `analytics.page()` from within your pages.
|
||||
}
|
||||
|
||||
if (NODE_ENV === 'development') {
|
||||
return snippet.max(opts)
|
||||
}
|
||||
|
||||
return snippet.min(opts)
|
||||
}
|
||||
|
||||
render () {
|
||||
return (
|
||||
<html>
|
||||
<Head>
|
||||
{/* Inject the Segment snippet into the <head> of the document */}
|
||||
<script dangerouslySetInnerHTML={{ __html: this.renderSnippet() }} />
|
||||
</Head>
|
||||
<body>
|
||||
<Main />
|
||||
<NextScript />
|
||||
</body>
|
||||
</html>
|
||||
)
|
||||
}
|
||||
}
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Reference in a new issue