Skip to content

Commit

Permalink
Make sure to error when setting too large of preview data (#10831)
Browse files Browse the repository at this point in the history
* Make sure to error when setting too large of preview data

* Update to check size after signing and limit to 2KB
  • Loading branch information
timneutkens committed Mar 4, 2020
1 parent a4eef95 commit 0f0398c
Show file tree
Hide file tree
Showing 5 changed files with 40 additions and 2 deletions.
8 changes: 8 additions & 0 deletions packages/next/next-server/server/api-utils.ts
Expand Up @@ -377,6 +377,14 @@ function setPreviewData<T>(
}
)

// limit preview mode cookie to 2KB since we shouldn't store too much
// data here and browsers drop cookies over 4KB
if (payload.length > 2048) {
throw new Error(
`Preview data is limited to 2KB currently, reduce how much data you are storing as preview data to continue`
)
}

const { serialize } = require('cookie') as typeof import('cookie')
const previous = res.getHeader('Set-Cookie')
res.setHeader(`Set-Cookie`, [
Expand Down
11 changes: 10 additions & 1 deletion test/integration/getserversideprops-preview/pages/api/preview.js
@@ -1,4 +1,13 @@
export default (req, res) => {
res.setPreviewData(req.query)
if (req.query.tooBig) {
try {
res.setPreviewData(new Array(2000).fill('a').join(''))
} catch (err) {
return res.status(500).end('too big')
}
} else {
res.setPreviewData(req.query)
}

res.status(200).end()
}
Expand Up @@ -156,6 +156,12 @@ function runTests(startServer = nextStart) {
expect(cookies[1]).not.toHaveProperty('Max-Age')
})

it('should throw error when setting too large of preview data', async () => {
const res = await fetchViaHTTP(appPort, '/api/preview?tooBig=true')
expect(res.status).toBe(500)
expect(await res.text()).toBe('too big')
})

/** @type import('next-webdriver').Chain */
let browser
it('should start the client-side browser', async () => {
Expand Down
11 changes: 10 additions & 1 deletion test/integration/prerender-preview/pages/api/preview.js
@@ -1,4 +1,13 @@
export default (req, res) => {
res.setPreviewData(req.query)
if (req.query.tooBig) {
try {
res.setPreviewData(new Array(2000).fill('a').join(''))
} catch (err) {
return res.status(500).end('too big')
}
} else {
res.setPreviewData(req.query)
}

res.status(200).end()
}
6 changes: 6 additions & 0 deletions test/integration/prerender-preview/test/index.test.js
Expand Up @@ -63,6 +63,12 @@ function runTests(startServer = nextStart) {
expect(pre).toBe('undefined and undefined')
})

it('should throw error when setting too large of preview data', async () => {
const res = await fetchViaHTTP(appPort, '/api/preview?tooBig=true')
expect(res.status).toBe(500)
expect(await res.text()).toBe('too big')
})

let previewCookieString
it('should enable preview mode', async () => {
const res = await fetchViaHTTP(appPort, '/api/preview', { lets: 'goooo' })
Expand Down

0 comments on commit 0f0398c

Please sign in to comment.