* add temporary redirect support * add temporary redirect tests * add ENDYANK comments per @zeke suggestion
192 lines
8.6 KiB
JavaScript
192 lines
8.6 KiB
JavaScript
const { eachOfLimit } = require('async')
|
|
const enterpriseServerReleases = require('../../lib/enterprise-server-releases')
|
|
const { get } = require('../helpers')
|
|
const { getEnterpriseVersionNumber } = require('../../lib/patterns')
|
|
const nonEnterpriseDefaultVersion = require('../../lib/non-enterprise-default-version')
|
|
const restRedirectFixtures = require('../fixtures/rest-redirects')
|
|
const graphqlRedirectFixtures = require('../fixtures/graphql-redirects')
|
|
const developerRedirectFixtures = require('../fixtures/developer-redirects')
|
|
|
|
const MAX_CONCURRENT_REQUESTS = 50
|
|
|
|
describe('developer redirects', () => {
|
|
jest.setTimeout(60 * 1000)
|
|
|
|
beforeAll(async () => {
|
|
// The first page load takes a long time so let's get it out of the way in
|
|
// advance to call out that problem specifically rather than misleadingly
|
|
// attributing it to the first test
|
|
await get('/v4')
|
|
})
|
|
|
|
describe('redirects /v4 requests to /graphql', () => {
|
|
test('graphql homepage', async () => {
|
|
const res = await get('/v4')
|
|
expect(res.statusCode).toBe(301)
|
|
const expectedFinalPath = `/en/${nonEnterpriseDefaultVersion}/graphql`
|
|
expect(res.headers.location).toBe(expectedFinalPath)
|
|
})
|
|
|
|
test('graphql enterprise homepage', async () => {
|
|
const res = await get('/enterprise/v4', { followAllRedirects: true })
|
|
expect(res.statusCode).toBe(200)
|
|
const finalPath = (new URL(res.request.url)).pathname
|
|
const expectedFinalPath = `/en/enterprise-server@${enterpriseServerReleases.latest}/graphql`
|
|
expect(finalPath).toBe(expectedFinalPath)
|
|
})
|
|
|
|
test('graphql overview paths', async () => {
|
|
const oldPath = '/v4/breaking_changes'
|
|
const newPath = `/${nonEnterpriseDefaultVersion}/graphql/overview/breaking-changes`
|
|
const res = await get(oldPath)
|
|
expect(res.statusCode).toBe(301)
|
|
expect(res.headers.location).toBe(`/en${newPath}`)
|
|
|
|
const enterpriseRes = await get(`/enterprise${oldPath}`, { followAllRedirects: true })
|
|
expect(enterpriseRes.statusCode).toBe(200)
|
|
const finalPath = (new URL(enterpriseRes.request.url)).pathname
|
|
const expectedFinalPath = newPath.replace(nonEnterpriseDefaultVersion, `enterprise-server@${enterpriseServerReleases.latest}`)
|
|
expect(finalPath).toBe(`/en${expectedFinalPath}`)
|
|
})
|
|
|
|
test('graphql reference paths with child pages', async () => {
|
|
const sclarRes = await get('/en/v4/scalar/boolean')
|
|
expect(sclarRes.statusCode).toBe(301)
|
|
const sclarResFinalPath = `/en/${nonEnterpriseDefaultVersion}/graphql/reference/scalars#boolean`
|
|
expect(sclarRes.headers.location).toBe(sclarResFinalPath)
|
|
|
|
const enumRes = await get('/en/v4/enum/searchtype')
|
|
expect(enumRes.statusCode).toBe(301)
|
|
const enumResFinalPath = `/en/${nonEnterpriseDefaultVersion}/graphql/reference/enums#searchtype`
|
|
expect(enumRes.headers.location).toBe(enumResFinalPath)
|
|
})
|
|
})
|
|
|
|
test('redirects /v3 requests to /rest', async () => {
|
|
let expectedFinalPath
|
|
let res = await get('/v3')
|
|
expect(res.statusCode).toBe(301)
|
|
expectedFinalPath = `/en/${nonEnterpriseDefaultVersion}/rest`
|
|
expect(res.headers.location).toBe(expectedFinalPath)
|
|
|
|
// REST subresources like activity notifications don't have their own page
|
|
// any more, so redirect to an anchor on the resource page
|
|
res = await get('/en/v3/activity')
|
|
expect(res.statusCode).toBe(301)
|
|
expectedFinalPath = `/en/${nonEnterpriseDefaultVersion}/rest/reference/activity`
|
|
expect(res.headers.location).toBe(expectedFinalPath)
|
|
|
|
// REST subresources like activity notifications don't have their own page
|
|
// any more, so redirect to an anchor on the resource page
|
|
res = await get('/en/v3/activity/notifications')
|
|
expect(res.statusCode).toBe(301)
|
|
expectedFinalPath = `/en/${nonEnterpriseDefaultVersion}/rest/reference/activity#notifications`
|
|
expect(res.headers.location).toBe(expectedFinalPath)
|
|
|
|
// trailing slashes are handled separately by the `slashes` module;
|
|
// any request to a /v3 URL with a trailing slash will be redirected twice
|
|
res = await get('/en/v3/activity/notifications/')
|
|
expect(res.statusCode).toBe(301)
|
|
expect(res.headers.location).toBe('/en/v3/activity/notifications')
|
|
|
|
// non-reference redirects (e.g. guides)
|
|
res = await get('/en/v3/guides/basics-of-authentication')
|
|
expect(res.statusCode).toBe(301)
|
|
expectedFinalPath = `/en/${nonEnterpriseDefaultVersion}/rest/guides/basics-of-authentication`
|
|
expect(res.headers.location).toBe(expectedFinalPath)
|
|
})
|
|
|
|
describe('fixtures', () => {
|
|
// this fixtures file includes paths like /apps and /webhooks, plus /enterprise paths
|
|
test('developer redirects', async () => {
|
|
await eachOfLimit(
|
|
developerRedirectFixtures,
|
|
MAX_CONCURRENT_REQUESTS,
|
|
async (newPath, oldPath) => {
|
|
const res = await get(oldPath)
|
|
expect(res.statusCode, `${oldPath} did not redirect to ${newPath}`).toBe(301)
|
|
expect(res.headers.location).toBe(newPath)
|
|
}
|
|
)
|
|
})
|
|
|
|
// this fixtures file includes /v3 and /enterprise/v3 paths
|
|
test('rest reference redirects', async () => {
|
|
await eachOfLimit(
|
|
restRedirectFixtures,
|
|
MAX_CONCURRENT_REQUESTS,
|
|
async (newPath, oldPath) => {
|
|
// REST and GraphQL developer Enterprise paths with a version are only supported up to 2.21.
|
|
// We make an exception to always redirect versionless paths to the latest version.
|
|
newPath = newPath.replace('/enterprise-server/', `/enterprise-server@${enterpriseServerReleases.latest}/`)
|
|
const res = await get(oldPath)
|
|
expect(res.statusCode, `${oldPath} did not redirect to ${newPath}`).toBe(301)
|
|
expect(res.headers.location).toBe(newPath)
|
|
}
|
|
)
|
|
})
|
|
|
|
// TODO temprarily ensure we redirect old links using the new enterprise format
|
|
// for currently supported enterprise releases only
|
|
// EXAMPLE: /en/enterprise-server@2.20/v3/pulls/comments -> /en/enterprise-server@2.20/rest/reference/pulls#comments
|
|
// We can remove test after we update all the old `/v3` links to point to `/rest`
|
|
test('temporary rest reference enterprise redirects', async () => {
|
|
await eachOfLimit(
|
|
restRedirectFixtures,
|
|
MAX_CONCURRENT_REQUESTS,
|
|
async (newPath, oldPath) => {
|
|
const releaseNumber = oldPath.match(getEnterpriseVersionNumber)
|
|
if (!releaseNumber) return
|
|
if (!enterpriseServerReleases.supported.includes(releaseNumber[1])) return
|
|
|
|
oldPath = oldPath
|
|
.replace(/\/enterprise\/(\d.\d\d)\//, '/enterprise-server@$1/')
|
|
.replace('/user/', '/')
|
|
const res = await get(oldPath)
|
|
expect(res.statusCode, `${oldPath} did not redirect to ${newPath}`).toBe(301)
|
|
expect(res.headers.location).toBe(newPath)
|
|
}
|
|
)
|
|
})
|
|
|
|
// this fixtures file includes /v4 and /enterprise/v4 paths
|
|
test('graphql reference redirects', async () => {
|
|
await eachOfLimit(
|
|
graphqlRedirectFixtures,
|
|
MAX_CONCURRENT_REQUESTS,
|
|
async (newPath, oldPath) => {
|
|
// REST and GraphQL developer Enterprise paths with a version are only supported up to 2.21.
|
|
// We make an exception to always redirect versionless paths to the latest version.
|
|
newPath = newPath.replace('/enterprise-server/', `/enterprise-server@${enterpriseServerReleases.latest}/`)
|
|
const res = await get(oldPath)
|
|
expect(res.statusCode, `${oldPath} did not redirect to ${newPath}`).toBe(301)
|
|
expect(res.headers.location).toBe(newPath)
|
|
}
|
|
)
|
|
})
|
|
|
|
// TODO temprarily ensure we redirect old links using the new enterprise format
|
|
// for currently supported enterprise releases only
|
|
// EXAMPLE: /en/enterprise-server@2.20/v4/interface/actor -> /en/enterprise-server@2.20/graphql/reference/interfaces#actor
|
|
// We can remove test after we update all the old `/v4` links to point to `/graphql`
|
|
test('temporary rest reference enterprise redirects', async () => {
|
|
await eachOfLimit(
|
|
graphqlRedirectFixtures,
|
|
MAX_CONCURRENT_REQUESTS,
|
|
async (newPath, oldPath) => {
|
|
const releaseNumber = oldPath.match(getEnterpriseVersionNumber)
|
|
if (!releaseNumber) return
|
|
if (!enterpriseServerReleases.supported.includes(releaseNumber[1])) return
|
|
|
|
oldPath = oldPath
|
|
.replace(/\/enterprise\/(\d.\d\d)\//, '/enterprise-server@$1/')
|
|
.replace('/user/', '/')
|
|
const res = await get(oldPath)
|
|
expect(res.statusCode, `${oldPath} did not redirect to ${newPath}`).toBe(301)
|
|
expect(res.headers.location).toBe(newPath)
|
|
}
|
|
)
|
|
})
|
|
})
|
|
})
|