Move Docusaurus 1 files into directory (#966)

* Move Docusaurus 1 into v1 directory

* Update Circle CI commands for new v1 dir

* Remove OC

* Fix tests
This commit is contained in:
Yangshun Tay 2018-09-18 00:58:07 +08:00 committed by GitHub
parent 9d4a5d5359
commit f2927a9fc4
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
291 changed files with 7591 additions and 6532 deletions

View file

@ -0,0 +1,11 @@
---
title: Docusaurus
author: Endilie
authorURL: https://github.com/endiliey
authorFBID: 100000251103620
authorTwitter: endiliey
---
![Docusaurus](/img/slash-introducing.png)
We are very happy to introduce [Docusaurus](https://github.com/facebook/Docusaurus) to help you manage one or many open source websites.

View file

@ -0,0 +1,21 @@
---
id: doc1
title: Document 1
---
Docusaurus is the best :)
![image1](assets/image1.png)
```js
console.log("Docusaurus");
```
![image2](assets/image2.jpg)
![image3](assets/image3.gif)
Don't replace the one below
```md
![image4](assets/image4.bmp)
```

View file

@ -0,0 +1,29 @@
---
id: doc2
title: Document 2
---
### Existing Docs
- [doc1](doc1.md)
- [doc2](./doc2.md)
### Non-existing Docs
- [hahaha](hahaha.md)
## Repeating Docs
- [doc1](doc1.md)
- [doc2](./doc2.md)
## Do not replace this
```md
![image1](assets/image1.png)
```
```js
const doc1 = foo();
console.log("[image2](assets/image2.jpg)");
const testStr = `![image3](assets/image3.gif)`;
```

View file

@ -0,0 +1,116 @@
module.exports = {
'en-doc1': {
id: 'en-doc1',
title: 'Document 1',
source: 'doc1.md',
version: 'next',
permalink: 'docs/en/next/doc1.html',
localized_id: 'doc1',
language: 'en',
sidebar: 'docs',
category: 'Test',
next_id: 'doc2',
next: 'en-doc2',
next_title: 'Document 2',
},
'en-doc2': {
id: 'en-doc2',
title: 'Document 2',
source: 'doc2.md',
version: 'next',
permalink: 'docs/en/next/doc2.html',
localized_id: 'doc2',
language: 'en',
sidebar: 'docs',
category: 'Test',
previous_id: 'doc1',
previous: 'en-doc1',
previous_title: 'Document 1',
},
'ko-doc1': {
id: 'ko-doc1',
title: '문서 1',
source: 'doc1.md',
version: 'next',
permalink: 'docs/ko/next/doc1.html',
localized_id: 'doc1',
language: 'ko',
sidebar: 'docs',
category: 'Test',
next_id: 'doc2',
next: 'ko-doc2',
next_title: '문서 2',
},
'ko-doc2': {
id: 'ko-doc2',
title: '문서 2',
source: 'doc2.md',
version: 'next',
permalink: 'docs/ko/next/doc2.html',
localized_id: 'doc2',
language: 'ko',
sidebar: 'docs',
category: 'Test',
previous_id: 'doc1',
previous: 'ko-doc1',
previous_title: '문서 1',
},
'en-version-1.0.0-doc1': {
id: 'en-version-1.0.0-doc1',
original_id: 'doc1',
title: 'Document 1',
source: 'version-1.0.0/doc1.md',
version: '1.0.0',
permalink: 'docs/en/doc1.html',
localized_id: 'version-1.0.0-doc1',
language: 'en',
sidebar: 'version-1.0.0-docs',
category: 'Test',
next_id: 'doc2',
next: 'en-version-1.0.0-doc2',
next_title: 'Document 2',
},
'en-version-1.0.0-doc2': {
id: 'en-version-1.0.0-doc2',
original_id: 'doc2',
title: 'Document 2',
source: 'version-1.0.0/doc2.md',
version: '1.0.0',
permalink: 'docs/en/doc2.html',
localized_id: 'version-1.0.0-doc2',
language: 'en',
sidebar: 'version-1.0.0-docs',
category: 'Test',
previous_id: 'doc1',
previous: 'en-version-1.0.0-doc1',
previous_title: 'Document 1',
},
'ko-version-1.0.0-doc1': {
id: 'ko-version-1.0.0-doc1',
title: '문서 1',
source: 'version-1.0.0/doc1.md',
version: '1.0.0',
permalink: 'docs/ko/doc1.html',
localized_id: 'version-1.0.0-doc1',
language: 'ko',
sidebar: 'version-1.0.0-docs',
category: 'Test',
next_id: 'doc2',
next: 'ko-version-1.0.0-doc2',
next_title: '문서 2',
},
'ko-version-1.0.0-doc2': {
id: 'ko-version-1.0.0-doc2',
title: '문서 2',
source: 'version-1.0.0/doc2.md',
version: '1.0.0',
permalink: 'docs/ko/doc2.html',
localized_id: 'version-1.0.0-doc2',
language: 'ko',
sidebar: 'version-1.0.0-docs',
category: 'Test',
previous_id: 'doc1',
previous: 'ko-version-1.0.0-doc1',
previous_title: '문서 1',
},
};

View file

@ -0,0 +1,24 @@
/**
* Copyright (c) 2017-present, Facebook, Inc.
*
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*/
.hljs {
margin-left: -15px;
margin-right: -15px;
border: 1px solid #eee;
border-radius: 6px;
padding: 15px;
font-size: 15px;
max-width: 50rem;
}
.hljs.javascript {
background-color: rgba(247, 223, 30, 0.03);
}
.hljs .comment {
opacity: 0.7;
}
::placeholder {
color: gray;
}

View file

@ -0,0 +1,26 @@
---
title: This is not a css
---
This is a markdown, not a css
.homeWrapperInner .homeCodeSnippet > div:nth-child(1) {
display: none;
}
@media (max-width: 480px) {
.projectTitle {
font-size: 30px;
}
.homeCodeSnippet .hljs {
font-size: 13px;
padding: 0;
}
.homeWrapperInner .homeCodeSnippet > div:nth-child(1) {
display: block;
}
.homeWrapperInner .homeCodeSnippet > div:nth-child(2) {
display: none;
}
}

View file

@ -0,0 +1,17 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP
exports[`getMetadata blog file 1`] = `
Object {
"author": "Endilie",
"authorFBID": 100000251103620,
"authorTwitter": "endiliey",
"authorURL": "https://github.com/endiliey",
"content": "
![Docusaurus](/img/slash-introducing.png)
We are very happy to introduce [Docusaurus](https://github.com/facebook/Docusaurus) to help you manage one or many open source websites.",
"id": "Docusaurus",
"path": "2018/08/17/docusaurus.html",
"title": "Docusaurus",
}
`;

View file

@ -0,0 +1,97 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP
exports[`mdToHtmlify transform nothing 1`] = `
"
Docusaurus is the best :)
![image1](assets/image1.png)
\`\`\`js
console.log(\\"Docusaurus\\");
\`\`\`
![image2](assets/image2.jpg)
![image3](assets/image3.gif)
Don't replace the one below
\`\`\`md
![image4](assets/image4.bmp)
\`\`\`"
`;
exports[`mdToHtmlify transform to correct link 1`] = `
"
### Existing Docs
- [doc1](/docs/en/next/doc1)
- [doc2](/docs/en/next/doc2)
### Non-existing Docs
- [hahaha](hahaha.md)
## Repeating Docs
- [doc1](/docs/en/next/doc1)
- [doc2](/docs/en/next/doc2)
## Do not replace this
\`\`\`md
![image1](assets/image1.png)
\`\`\`
\`\`\`js
const doc1 = foo();
console.log(\\"[image2](assets/image2.jpg)\\");
const testStr = \`![image3](assets/image3.gif)\`;
\`\`\`"
`;
exports[`replaceAssetsLink does not transform document without valid assets link 1`] = `
"
### Existing Docs
- [doc1](doc1.md)
- [doc2](./doc2.md)
### Non-existing Docs
- [hahaha](hahaha.md)
## Repeating Docs
- [doc1](doc1.md)
- [doc2](./doc2.md)
## Do not replace this
\`\`\`md
![image1](assets/image1.png)
\`\`\`
\`\`\`js
const doc1 = foo();
console.log(\\"[image2](assets/image2.jpg)\\");
const testStr = \`![image3](assets/image3.gif)\`;
\`\`\`"
`;
exports[`replaceAssetsLink transform document with valid assets link 1`] = `
"
Docusaurus is the best :)
![image1](/docs/assets/image1.png)
\`\`\`js
console.log(\\"Docusaurus\\");
\`\`\`
![image2](/docs/assets/image2.jpg)
![image3](/docs/assets/image3.gif)
Don't replace the one below
\`\`\`md
![image4](assets/image4.bmp)
\`\`\`"
`;

View file

@ -0,0 +1,42 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP
exports[`server utils autoprefix css 1`] = `
"/**
* Copyright (c) 2017-present, Facebook, Inc.
*
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*/
.hljs {
margin-left: -15px;
margin-right: -15px;
border: 1px solid #eee;
border-radius: 6px;
padding: 15px;
font-size: 15px;
max-width: 50rem;
}
.hljs.javascript {
background-color: rgba(247, 223, 30, 0.03);
}
.hljs .comment {
opacity: 0.7;
}
::-webkit-input-placeholder {
color: gray;
}
:-ms-input-placeholder {
color: gray;
}
::-ms-input-placeholder {
color: gray;
}
::placeholder {
color: gray;
}
"
`;
exports[`server utils minify css 1`] = `".hljs{margin-left:-15px;margin-right:-15px;border:1px solid #eee;border-radius:6px;padding:15px;font-size:15px;max-width:50rem}.hljs.javascript{background-color:rgba(247,223,30,.03)}.hljs .comment{opacity:.7}::placeholder{color:gray}"`;
exports[`server utils minify css 2`] = `[Error: Unexpected "space" found.]`;

View file

@ -0,0 +1,68 @@
/**
* Copyright (c) 2017-present, Facebook, Inc.
*
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*/
const path = require('path');
const fs = require('fs-extra');
const blog = require('../blog');
const testFile = path.join(
__dirname,
'__fixtures__',
'2018-08-17-docusaurus.md',
);
fs.existsSync = jest.fn().mockReturnValue(true);
describe('getMetadata', () => {
test('file does not exist', () => {
fs.existsSync.mockReturnValueOnce(null);
expect(blog.getMetadata('/this/path/does-not-exist/')).toBeNull();
});
test('null/undefined', () => {
expect(blog.getMetadata(null)).toBeNull();
expect(blog.getMetadata(undefined)).toBeNull();
});
test('blog file', () => {
const metadata = blog.getMetadata(testFile);
expect(metadata).toMatchSnapshot();
expect(metadata).not.toBeNull();
expect(metadata).toHaveProperty('id');
expect(metadata).toHaveProperty('path');
expect(metadata).toHaveProperty('content');
});
});
describe('fileToUrl', () => {
test('invalid file path', () => {
expect(blog.fileToUrl(null)).toBeNull();
expect(blog.fileToUrl(undefined)).toBeNull();
expect(blog.fileToUrl(true)).toBeNull();
fs.existsSync.mockReturnValueOnce(null);
expect(blog.fileToUrl('2018-03-02-this-does-not-exist.md')).toBeNull();
});
test('valid filepath', () => {
expect(blog.fileToUrl(testFile)).toEqual('2018/08/17/docusaurus.html');
});
});
describe('urlToSource', () => {
test('invalid url path', () => {
expect(blog.urlToSource(null)).toBeNull();
expect(blog.urlToSource(undefined)).toBeNull();
expect(blog.urlToSource(true)).toBeNull();
});
test('valid url path', () => {
expect(blog.urlToSource(`${blog.fileToUrl(testFile)}`)).toEqual(
'2018-08-17-docusaurus.md',
);
expect(blog.urlToSource('2018/03/04/test-name-lol.html')).toEqual(
'2018-03-04-test-name-lol.md',
);
});
});

View file

@ -0,0 +1,165 @@
/**
* Copyright (c) 2017-present, Facebook, Inc.
*
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*/
// simulate cwd to website so all require (CWD+'/siteConfig.js') will work
const originalCwd = process.cwd();
if (!/website$/.test(originalCwd)) {
process.chdir(process.cwd() + '/website');
}
const path = require('path');
const fs = require('fs-extra');
const docs = require('../docs');
const metadataUtils = require('../metadataUtils');
jest.mock('../env', () => ({
translation: {
enabled: true,
enabledLanguages: () => [
{
enabled: true,
name: 'English',
tag: 'en',
},
{
enabled: true,
name: '한국어',
tag: 'ko',
},
],
},
versioning: {
enabled: true,
defaultVersion: '1.0.0',
latestVersion: '1.0.0',
},
}));
const Metadata = require(path.join(__dirname, '__fixtures__', 'metadata.js'));
const doc1 = fs.readFileSync(
path.join(__dirname, '__fixtures__', 'doc1.md'),
'utf8',
);
const doc2 = fs.readFileSync(
path.join(__dirname, '__fixtures__', 'doc2.md'),
'utf8',
);
const rawContent1 = metadataUtils.extractMetadata(doc1).rawContent;
const rawContent2 = metadataUtils.extractMetadata(doc2).rawContent;
describe('mdToHtmlify', () => {
const mdToHtml = metadataUtils.mdToHtml(Metadata, '/');
test('transform nothing', () => {
const content1 = docs.mdToHtmlify(
rawContent1,
mdToHtml,
Metadata['en-doc1'],
);
expect(content1).not.toContain('/docs/en/next/');
expect(content1).toMatchSnapshot();
expect(content1).toEqual(rawContent1);
});
test('transform to correct link', () => {
const content2 = docs.mdToHtmlify(
rawContent2,
mdToHtml,
Metadata['en-doc2'],
);
expect(content2).toContain('/docs/en/next/');
expect(content2).toMatchSnapshot();
expect(content2).not.toEqual(rawContent2);
});
});
describe('getFile', () => {
const fakeContent = {
'v1/website/translated_docs/ko/doc1.md': '이건 가짜 야',
'v1/website/versioned_docs/version-1.0.0/doc2.md': 'Document 2 is not good',
'v1/website/translated_docs/ko/version-1.0.0/doc1.md':
'이것은 오래된 가짜입니다.',
'docs/doc1.md': 'Just another document',
};
fs.existsSync = jest.fn().mockReturnValue(true);
fs.readFileSync = jest.fn().mockImplementation(file => {
const fakePath = file.replace(
process.cwd().replace(/v1\/website\/?$/, ''),
'',
);
const normalizedPath = fakePath.replace(/\\/g, '/');
return fakeContent[normalizedPath];
});
test('docs does not exist', () => {
const metadata = Metadata['en-doc1'];
fs.existsSync.mockReturnValueOnce(null);
expect(docs.getFile(metadata)).toBeNull();
});
test('null/undefined metadata', () => {
expect(docs.getFile(null)).toBeNull();
expect(docs.getFile(undefined)).toBeNull();
});
test('translated docs', () => {
const metadata = Metadata['ko-doc1'];
expect(docs.getFile(metadata)).toEqual(
fakeContent['v1/website/translated_docs/ko/doc1.md'],
);
});
test('versioned docs', () => {
const metadata = Metadata['en-version-1.0.0-doc2'];
expect(docs.getFile(metadata)).toEqual(
fakeContent['v1/website/versioned_docs/version-1.0.0/doc2.md'],
);
});
test('translated & versioned docs', () => {
const metadata = Metadata['ko-version-1.0.0-doc1'];
expect(docs.getFile(metadata)).toEqual(
fakeContent['v1/website/translated_docs/ko/version-1.0.0/doc1.md'],
);
});
test('normal docs', () => {
const metadata = Metadata['en-doc1'];
expect(docs.getFile(metadata)).toEqual(fakeContent['docs/doc1.md']);
});
});
describe('replaceAssetsLink', () => {
test('transform document with valid assets link', () => {
const content1 = docs.replaceAssetsLink(rawContent1);
expect(content1).toMatchSnapshot();
expect(content1).toContain('![image1](/docs/assets/image1.png)');
expect(content1).toContain('![image2](/docs/assets/image2.jpg)');
expect(content1).toContain('![image3](/docs/assets/image3.gif)');
expect(content1).toContain('![image4](assets/image4.bmp)');
expect(content1).not.toContain('![image1](assets/image1.png)');
expect(content1).not.toContain('![image2](assets/image2.jpg)');
expect(content1).not.toContain('![image3](assets/image3.gif)');
expect(content1).not.toContain('![image4](/docs/assets/image4.bmp)');
expect(content1).not.toEqual(rawContent1);
});
test('does not transform document without valid assets link', () => {
const content2 = docs.replaceAssetsLink(rawContent2);
expect(content2).toMatchSnapshot();
expect(content2).not.toContain('![image1](/docs/assets/image1.png)');
expect(content2).not.toContain('![image2](/docs/assets/image2.jpg)');
expect(content2).not.toContain('![image3](/docs/assets/image3.gif)');
expect(content2).toEqual(rawContent2);
});
});
afterAll(() => {
process.chdir(originalCwd);
});

View file

@ -0,0 +1,26 @@
/**
* Copyright (c) 2017-present, Facebook, Inc.
*
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*/
jest.mock('gaze');
jest.mock('../readMetadata.js');
jest.mock('tiny-lr');
// When running Jest the siteConfig import fails because siteConfig doesn't exist
// relative to the cwd of the tests. Rather than mocking out cwd just mock
// siteConfig virtually.
jest.mock(`${process.cwd()}/siteConfig.js`, () => jest.fn(), {virtual: true});
const liveReloadServer = require('../liveReloadServer.js');
describe('get reload script', () => {
test('when server started, returns url with correct port', () => {
const port = 1234;
liveReloadServer.start(port);
const expectedUrl = `http://localhost:${port}/livereload.js`;
expect(liveReloadServer.getReloadScriptUrl()).toBe(expectedUrl);
});
});

View file

@ -0,0 +1,187 @@
/**
* Copyright (c) 2017-present, Facebook, Inc.
*
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*/
const routing = require('../routing');
describe('Blog routing', () => {
const blogRegex = routing.blog('/');
const blogRegex2 = routing.blog('/react/');
test('valid blog', () => {
expect('/blog/test.html').toMatch(blogRegex);
expect('/react/blog/test.html').toMatch(blogRegex2);
});
test('invalid blog', () => {
expect('/react/blog/test.html').not.toMatch(blogRegex);
expect('/blog/test.html').not.toMatch(blogRegex2);
});
test('assets not classified as blog', () => {
expect('/blog/assets/any.png').not.toMatch(blogRegex);
expect('/react/blog/assets/any.png').not.toMatch(blogRegex2);
});
test('docs not classified as blog', () => {
expect('/docs/en/blog.html').not.toMatch(blogRegex);
expect('/docs/en/blog/blog.html').not.toMatch(blogRegex);
expect('/react/docs/en/blog.html').not.toMatch(blogRegex2);
expect('/react/docs/en/blog/blog.html').not.toMatch(blogRegex2);
});
});
describe('Docs routing', () => {
const docsRegex = routing.docs('/');
const docsRegex2 = routing.docs('/reason/');
test('valid docs', () => {
expect('/docs/en/test.html').toMatch(docsRegex);
expect('/reason/docs/en/test.html').toMatch(docsRegex2);
});
test('invalid docs', () => {
expect('/reason/docs/en/test.html').not.toMatch(docsRegex);
expect('/docs/en/test.html').not.toMatch(docsRegex2);
});
test('assets not classified as docs', () => {
expect('/docs/en/notvalid.png').not.toMatch(docsRegex);
expect('/reason/docs/en/notvalid.png').not.toMatch(docsRegex2);
});
test('blog not classified as docs', () => {
expect('/blog/docs.html').not.toMatch(docsRegex);
expect('/blog/docs/docs.html').not.toMatch(docsRegex);
expect('/reason/blog/docs.html').not.toMatch(docsRegex2);
expect('/reason/blog/docs/docs.html').not.toMatch(docsRegex2);
});
});
describe('Dot routing', () => {
const dotRegex = routing.dotfiles();
test('valid url with dot after last slash', () => {
expect('/docs/en/test.23').toMatch(dotRegex);
expect('/robots.hai.2').toMatch(dotRegex);
expect('/blog/1.2.3').toMatch(dotRegex);
expect('/this.is.my').toMatch(dotRegex);
});
test('html file is invalid', () => {
expect('/docs/en.html').not.toMatch(dotRegex);
expect('/users.html').not.toMatch(dotRegex);
expect('/blog/asdf.html').not.toMatch(dotRegex);
expect('/end/1234/asdf.html').not.toMatch(dotRegex);
expect('/test/lol.huam.html').not.toMatch(dotRegex);
});
test('extension-less url is not valid', () => {
expect('/reason/test').not.toMatch(dotRegex);
expect('/asdff').not.toMatch(dotRegex);
expect('/blog/asdf.ghg/').not.toMatch(dotRegex);
expect('/end/1234.23.55/').not.toMatch(dotRegex);
});
});
describe('Feed routing', () => {
const feedRegex = routing.feed('/');
const feedRegex2 = routing.feed('/reason/');
test('valid feed url', () => {
expect('/blog/atom.xml').toMatch(feedRegex);
expect('/blog/feed.xml').toMatch(feedRegex);
expect('/reason/blog/atom.xml').toMatch(feedRegex2);
expect('/reason/blog/feed.xml').toMatch(feedRegex2);
});
test('invalid feed url', () => {
expect('/blog/blog/feed.xml').not.toMatch(feedRegex);
expect('/blog/test.xml').not.toMatch(feedRegex);
expect('/reason/blog/atom.xml').not.toMatch(feedRegex);
expect('/reason/blog/feed.xml').not.toMatch(feedRegex);
expect('/blog/feed.xml/test.html').not.toMatch(feedRegex);
expect('/blog/atom.xml').not.toMatch(feedRegex2);
expect('/blog/feed.xml').not.toMatch(feedRegex2);
expect('/reason/blog/test.xml').not.toMatch(feedRegex2);
expect('/reason/blog/blog/feed.xml').not.toMatch(feedRegex2);
expect('/reason/blog/blog/atom.xml').not.toMatch(feedRegex2);
});
test('not a feed', () => {
expect('/blog/atom').not.toMatch(feedRegex);
expect('/reason/blog/feed').not.toMatch(feedRegex2);
});
});
describe('Extension-less url routing', () => {
const noExtRegex = routing.noExtension();
test('valid no extension url', () => {
expect('/test').toMatch(noExtRegex);
expect('/reason/test').toMatch(noExtRegex);
});
test('url with file extension', () => {
expect('/robots.txt').not.toMatch(noExtRegex);
expect('/reason/robots.txt').not.toMatch(noExtRegex);
expect('/docs/en/docu.html').not.toMatch(noExtRegex);
expect('/reason/robots.html').not.toMatch(noExtRegex);
expect('/blog/atom.xml').not.toMatch(noExtRegex);
expect('/reason/sitemap.xml').not.toMatch(noExtRegex);
expect('/main.css').not.toMatch(noExtRegex);
expect('/reason/custom.css').not.toMatch(noExtRegex);
});
});
describe('Page routing', () => {
const pageRegex = routing.page('/');
const pageRegex2 = routing.page('/reason/');
test('valid page url', () => {
expect('/index.html').toMatch(pageRegex);
expect('/en/help.html').toMatch(pageRegex);
expect('/reason/index.html').toMatch(pageRegex2);
expect('/reason/ro/users.html').toMatch(pageRegex2);
});
test('docs not considered as page', () => {
expect('/docs/en/test.html').not.toMatch(pageRegex);
expect('/reason/docs/en/test.html').not.toMatch(pageRegex2);
});
test('blog not considered as page', () => {
expect('/blog/index.html').not.toMatch(pageRegex);
expect('/reason/blog/index.html').not.toMatch(pageRegex2);
});
test('not a page', () => {
expect('/yangshun.jpg').not.toMatch(pageRegex);
expect('/reason/endilie.png').not.toMatch(pageRegex2);
});
});
describe('Sitemap routing', () => {
const sitemapRegex = routing.sitemap('/');
const sitemapRegex2 = routing.sitemap('/reason/');
test('valid sitemap url', () => {
expect('/sitemap.xml').toMatch(sitemapRegex);
expect('/reason/sitemap.xml').toMatch(sitemapRegex2);
});
test('invalid sitemap url', () => {
expect('/reason/sitemap.xml').not.toMatch(sitemapRegex);
expect('/reason/sitemap.xml.html').not.toMatch(sitemapRegex);
expect('/sitemap/sitemap.xml').not.toMatch(sitemapRegex);
expect('/reason/sitemap/sitemap.xml').not.toMatch(sitemapRegex);
expect('/sitemap.xml').not.toMatch(sitemapRegex2);
});
test('not a sitemap', () => {
expect('/sitemap').not.toMatch(sitemapRegex);
expect('/reason/sitemap').not.toMatch(sitemapRegex2);
});
});

View file

@ -0,0 +1,138 @@
/**
* Copyright (c) 2017-present, Facebook, Inc.
*
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*/
const program = require('commander');
const openBrowser = require('react-dev-utils/openBrowser');
const portFinder = require('portfinder');
const liveReloadServer = require('../liveReloadServer.js');
const server = require('../server.js');
const siteConfig = require(`${process.cwd()}/siteConfig.js`);
// When running Jest the siteConfig import fails because siteConfig doesn't exist
// relative to the cwd of the tests. Rather than mocking out cwd just mock
// siteConfig virtually.
jest.mock(`${process.cwd()}/siteConfig.js`, () => jest.fn(), {virtual: true});
jest.mock('commander');
jest.mock('react-dev-utils/openBrowser');
jest.mock('portfinder');
jest.mock('../liveReloadServer.js');
jest.mock('../server.js');
jest.mock('process');
console.log = jest.fn();
const start = require('../start.js');
beforeEach(() => jest.resetAllMocks());
describe('start live reload', () => {
test('uses inital port 35729', () => {
portFinder.getPortPromise.mockResolvedValue();
start.startLiveReloadServer();
expect(portFinder.getPortPromise).toHaveBeenCalledWith({port: 35729});
});
test('when an unused port is found, starts the live reload server on that port', () => {
expect.assertions(1);
const unusedPort = 1234;
portFinder.getPortPromise.mockResolvedValue(unusedPort);
return start.startLiveReloadServer().then(() => {
expect(liveReloadServer.start).toHaveBeenCalledWith(unusedPort);
});
});
test('when no unused port found, returns error', () => {
expect.assertions(1);
const unusedPortError = new Error('no unused port');
portFinder.getPortPromise.mockRejectedValue(unusedPortError);
return expect(start.startLiveReloadServer()).rejects.toEqual(
unusedPortError,
);
});
});
describe('start server', () => {
test('when custom port provided as parameter, uses as inital port', () => {
const customPort = 1234;
program.port = customPort;
portFinder.getPortPromise.mockResolvedValue();
start.startServer();
expect(portFinder.getPortPromise).toBeCalledWith({port: customPort});
delete program.port;
});
test('when port environment variable set and no custom port, used as inital port', () => {
const customPort = '4321';
process.env.PORT = customPort;
portFinder.getPortPromise.mockResolvedValue();
start.startServer();
expect(portFinder.getPortPromise).toBeCalledWith({port: customPort});
delete process.env.PORT;
});
test('when no custom port specified, uses port 3000', () => {
portFinder.getPortPromise.mockResolvedValue();
start.startServer();
expect(portFinder.getPortPromise).toBeCalledWith({port: 3000});
});
test('when unused port found, starts server on that port', () => {
expect.assertions(1);
const port = 1357;
portFinder.getPortPromise.mockResolvedValue(port);
return start.startServer().then(() => {
expect(server).toHaveBeenCalledWith(port);
});
});
test('when unused port found, opens browser to server address', () => {
expect.assertions(1);
const baseUrl = '/base_url';
siteConfig.baseUrl = baseUrl;
const port = 2468;
portFinder.getPortPromise.mockResolvedValue(port);
const expectedServerAddress = `http://localhost:${port}${baseUrl}`;
return start.startServer().then(() => {
expect(openBrowser).toHaveBeenCalledWith(expectedServerAddress);
});
});
});
describe('start docusaurus', () => {
test('when watch enabled, starts live reload server', () => {
expect.assertions(1);
program.watch = true;
portFinder.getPortPromise.mockResolvedValue();
return start.startDocusaurus().then(() => {
expect(liveReloadServer.start).toBeCalled();
});
});
test('when live reload fails to start, server still started', () => {
expect.assertions(1);
program.watch = true;
console.warn = jest.fn();
portFinder.getPortPromise
.mockRejectedValueOnce('could not find live reload port')
.mockResolvedValueOnce();
return start.startDocusaurus().then(() => {
expect(server).toBeCalled();
});
});
test('live reload disabled, only starts docusarus server', () => {
expect.assertions(2);
program.watch = false;
portFinder.getPortPromise.mockResolvedValue();
return start.startDocusaurus().then(() => {
expect(liveReloadServer.start).not.toBeCalled();
expect(server).toBeCalled();
});
});
});

View file

@ -0,0 +1,91 @@
/**
* Copyright (c) 2017-present, Facebook, Inc.
*
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*/
const path = require('path');
const fs = require('fs');
const utils = require('../utils');
jest.mock('../env', () => ({
translation: {
enabled: true,
enabledLanguages: () => [
{
enabled: true,
name: 'English',
tag: 'en',
},
{
enabled: true,
name: '日本語',
tag: 'ja',
},
],
},
}));
describe('server utils', () => {
test('minify css', () => {
const testCss = fs.readFileSync(
path.join(__dirname, '__fixtures__', 'test.css'),
'utf8',
);
const notCss = fs.readFileSync(
path.join(__dirname, '__fixtures__', 'test.md'),
'utf8',
);
utils.minifyCss(testCss).then(css => expect(css).toMatchSnapshot());
utils.minifyCss(notCss).catch(e => expect(e).toMatchSnapshot());
});
test('autoprefix css', () => {
const testCss = fs.readFileSync(
path.join(__dirname, '__fixtures__', 'test.css'),
'utf8',
);
utils.autoPrefixCss(testCss).then(css => expect(css).toMatchSnapshot());
});
test('getLanguage', () => {
const testDocEnglish = path.join('translated_docs', 'en', 'test.md');
const testDocJapanese = path.join('translated_docs', 'ja', 'test.md');
const testDocJapaneseInSubfolder = path.join(
'translated_docs',
'ja',
'en',
'test.md',
);
const testDocInSubfolder = path.join('docs', 'ro', 'test.md');
const testDocNoLanguage = path.join('docs', 'test.md');
expect(utils.getLanguage(testDocEnglish, 'translated_docs')).toBe('en');
expect(utils.getLanguage(testDocJapanese, 'translated_docs')).toBe('ja');
expect(
utils.getLanguage(testDocJapaneseInSubfolder, 'translated_docs'),
).toBe('ja');
expect(utils.getLanguage(testDocInSubfolder, 'docs')).toBeNull();
expect(utils.getLanguage(testDocNoLanguage, 'docs')).toBeNull();
});
test('getSubdir', () => {
const docA = path.join('docs', 'endiliey', 'a.md');
const docB = path.join('docs', 'nus', 'hackers', 'b.md');
const docC = path.join('docs', 'c.md');
const docD = path.join('website', 'translated_docs', 'wow', 'd.md');
const docE = path.join('website', 'translated_docs', 'lol', 'lah', 'e.md');
const docsDir = path.join('docs');
const translatedDir = path.join('website', 'translated_docs');
expect(utils.getSubDir(docA, docsDir)).toEqual('endiliey');
expect(utils.getSubDir(docA, translatedDir)).toBeNull();
expect(utils.getSubDir(docB, docsDir)).toEqual('nus/hackers');
expect(utils.getSubDir(docB, translatedDir)).toBeNull();
expect(utils.getSubDir(docC, docsDir)).toBeNull();
expect(utils.getSubDir(docC, translatedDir)).toBeNull();
expect(utils.getSubDir(docD, docsDir)).toBeNull();
expect(utils.getSubDir(docD, translatedDir)).toEqual('wow');
expect(utils.getSubDir(docE, docsDir)).toBeNull();
expect(utils.getSubDir(docE, translatedDir)).toEqual('lol/lah');
});
});