Skip to content

Commit

Permalink
fix(service): supports glob import in typescript files
Browse files Browse the repository at this point in the history
  • Loading branch information
Emilien Escalle committed Apr 22, 2020
1 parent 3738e21 commit a454599
Show file tree
Hide file tree
Showing 18 changed files with 471 additions and 162 deletions.
1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,7 @@
"husky": "^4.2.3",
"jest": "^25.2.7",
"mock-fs": "^4.11.0",
"mock-spawn": "^0.2.6",
"prettier": "^2.0.4",
"rimraf": "^3.0.0",
"ts-jest": "^25.3.1",
Expand Down
7 changes: 5 additions & 2 deletions src/actions/add-versioning/adapters/AbstractVersioning.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,6 @@ import { GitService } from '../../../services/git/GitService';
import { AbstractAdapter } from '../../AbstractAdapter';
import { IVersioningAdapter } from '../IVersioningAdapter';
import { ConsoleService } from '../../../services/ConsoleService';
import { TemplateService } from '../../../services/TemplateService';
import { ConventionalCommitsService } from '../../../services/git/ConventionalCommitsService';

@injectable()
Expand Down Expand Up @@ -64,7 +63,11 @@ export default abstract class AbstractVersioning extends AbstractAdapter
},
});

if (!this.conventionalCommitsService.hasConventionalCommits(realpath)) {
const hasConventionalCommits = await this.conventionalCommitsService.hasConventionalCommits(
realpath
);

if (!hasConventionalCommits) {
const { conventionalCommits } = await prompt([
{
type: 'confirm',
Expand Down
56 changes: 25 additions & 31 deletions src/actions/create-react-app/CreateReactApp.spec.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import CreateReactApp from './CreateReactApp';
import mock from 'mock-fs';
import { join } from 'path';
import inquirer from 'inquirer';

import container from '../../container';
import { restoreMockFs, mockDir, mockDirPath } from '../../tests/mock-fs';
import CreateReactApp from './CreateReactApp';

describe('CreateReactApp', () => {
let createReactApp: CreateReactApp;
Expand All @@ -13,77 +13,71 @@ describe('CreateReactApp', () => {
jest.mock('inquirer');
});

afterEach(mock.restore);
afterEach(restoreMockFs);
afterAll(jest.resetAllMocks);

describe('checkIfReactAppExistsAlready', () => {
it('should return false if the given realpath is not an existing directory', async () => {
const dirPath = 'test/dir/path';

mock({ [dirPath]: {} });
mockDir();

const result = await createReactApp.checkIfReactAppExistsAlready(
join(dirPath, 'app')
join(mockDirPath, 'app')
);
expect(result).toEqual(false);
});

it('should require confirmation for overriding existing directory', async () => {
const dirPath = 'test/dir/path';

mock({ [dirPath]: {} });
mockDir();

(inquirer.prompt as any) = jest.fn().mockResolvedValue({});
await createReactApp.checkIfReactAppExistsAlready(dirPath);
await createReactApp.checkIfReactAppExistsAlready(mockDirPath);
expect(inquirer.prompt).toHaveBeenCalled();
});

it('should return undefined if user do not want overriding existing directory', async () => {
const dirPath = 'test/dir/path';

mock({ [dirPath]: {} });
mockDir();

(inquirer.prompt as any) = jest
.fn()
.mockResolvedValue({ override: false });
const result = await createReactApp.checkIfReactAppExistsAlready(dirPath);
const result = await createReactApp.checkIfReactAppExistsAlready(
mockDirPath
);
expect(result).toBeUndefined();
});

it('should return false if directory exists but do not have expected files', async () => {
const dirPath = 'test/dir/path';

mock({ [dirPath]: {} });
mockDir();

(inquirer.prompt as any) = jest
.fn()
.mockResolvedValue({ override: true });

const result = await createReactApp.checkIfReactAppExistsAlready(dirPath);
const result = await createReactApp.checkIfReactAppExistsAlready(
mockDirPath
);
expect(result).toEqual(false);
});

it('should return true if directory exists and have expected files', async () => {
const dirPath = 'test/dir/path';

mock({
[dirPath]: {
'package.json': JSON.stringify({
dependencies: {
react: '1.0.0',
},
}),
src: {
'react-app-env.d.ts': '',
mockDir({
'package.json': JSON.stringify({
dependencies: {
react: '1.0.0',
},
}),
src: {
'react-app-env.d.ts': '',
},
});

(inquirer.prompt as any) = jest
.fn()
.mockResolvedValue({ override: true });

const result = await createReactApp.checkIfReactAppExistsAlready(dirPath);
const result = await createReactApp.checkIfReactAppExistsAlready(
mockDirPath
);
expect(result).toEqual(true);
});
});
Expand Down
15 changes: 7 additions & 8 deletions src/services/file/StdFile.spec.ts
Original file line number Diff line number Diff line change
@@ -1,18 +1,17 @@
import mock from 'mock-fs';
import { StdFile } from './StdFile';
import { join } from 'path';
import { readFileSync } from 'fs';
import inquirer from 'inquirer';

import container from '../../container';
import { restoreMockFs, mockDir, mockDirPath } from '../../tests/mock-fs';
import { CliService } from '../CliService';
import { FileService } from './FileService';
import { FileFactory } from './FileFactory';

describe('Services - File - StdFile', () => {
const dirPath = 'test/dir/path';
const fileName = 'test.txt';
const filePath = join(dirPath, fileName);
const filePath = join(mockDirPath, fileName);

let cliService: CliService;
let fileService: FileService;
Expand All @@ -26,12 +25,12 @@ describe('Services - File - StdFile', () => {
fileFactory = container.get(FileFactory);
});

afterEach(mock.restore);
afterEach(restoreMockFs);
afterAll(jest.resetAllMocks);

describe('saveFile', () => {
it('should save a new file', async () => {
mock({ [dirPath]: {} });
mockDir();

const fileContent = 'test content';
const file = new StdFile(
Expand All @@ -51,7 +50,7 @@ describe('Services - File - StdFile', () => {
});

it('should override an existing file', async () => {
mock({ [dirPath]: { [fileName]: 'test original content' } });
mockDir({ [fileName]: 'test original content' });

(inquirer.prompt as any) = jest
.fn()
Expand All @@ -76,7 +75,7 @@ describe('Services - File - StdFile', () => {
it('should not override an existing file', async () => {
const originalContent = 'test original content';

mock({ [dirPath]: { [fileName]: originalContent } });
mockDir({ [fileName]: originalContent });

(inquirer.prompt as any) = jest
.fn()
Expand Down Expand Up @@ -105,7 +104,7 @@ describe('Services - File - StdFile', () => {
line 3 content
line 4 content
`;
mock({ [dirPath]: { [fileName]: originalContent } });
mockDir({ [fileName]: originalContent });

(inquirer.prompt as any) = jest
.fn()
Expand Down
14 changes: 7 additions & 7 deletions src/services/file/TypescriptFile.spec.ts
Original file line number Diff line number Diff line change
@@ -1,17 +1,16 @@
import mock from 'mock-fs';
import { join } from 'path';
import { readFileSync } from 'fs';

import container from '../../container';
import { restoreMockFs, mockDir, mockDirPath } from '../../tests/mock-fs';
import { CliService } from '../CliService';
import { FileService } from './FileService';
import { FileFactory } from './FileFactory';
import { TypescriptFile } from './TypescriptFile';

describe('Services - File - TypescriptFile', () => {
const dirPath = 'test/dir/path';
const fileName = 'test.ts';
const filePath = join(dirPath, fileName);
const filePath = join(mockDirPath, fileName);

let cliService: CliService;
let fileService: FileService;
Expand All @@ -25,14 +24,15 @@ describe('Services - File - TypescriptFile', () => {
fileFactory = container.get(FileFactory);
});

afterEach(mock.restore);
afterEach(restoreMockFs);
afterAll(jest.resetAllMocks);

describe('getContent', () => {
it('should retrieve file content', async () => {
mock({ [dirPath]: {} });
it.only('should retrieve file content', async () => {
mockDir();

const fileContent = `import * as serviceWorker from './serviceWorker';
const fileContent = `import { App as CoreApp, IAppProps } from '@reactionable/core';
import * as serviceWorker from './serviceWorker';
ReactDOM.render(
<React.StrictMode>
Expand Down
9 changes: 7 additions & 2 deletions src/services/file/TypescriptFile.ts
Original file line number Diff line number Diff line change
Expand Up @@ -28,13 +28,18 @@ export class TypescriptFile extends StdFile {
importType = TypescriptImport.defaultImport;
moduleName = specifier.local.name;
break;

case AST_NODE_TYPES.ImportNamespaceSpecifier:
importType = specifier.local.name;
moduleName = TypescriptImport.globImport;
break;

default:
importType = '';
moduleName = specifier.local.name;
importType =
specifier.local.name !== specifier.imported.name
? specifier.local.name
: '';
moduleName = specifier.imported.name;
}

this.addImports([
Expand Down
26 changes: 24 additions & 2 deletions src/services/file/TypescriptImport.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import { TypescriptImport } from './TypescriptImport';

describe('Services - File - TypescriptImport', () => {
describe('fromString', () => {
it('should retrieve an instance of TypescriptImport from given string', async () => {
it('should retrieve an instance of TypescriptImport from a given "glob" import string', async () => {
const importString = `import * as serviceWorker from './serviceWorker';`;

const typescriptImport = TypescriptImport.fromString(importString)!;
Expand All @@ -11,10 +11,20 @@ describe('Services - File - TypescriptImport', () => {
expect(typescriptImport.modules).toEqual({ '*': 'serviceWorker' });
expect(typescriptImport.toString()).toEqual(importString);
});

it('should retrieve an instance of TypescriptImport from given an "aliased" import string', async () => {
const importString = `import { App as CoreApp } from '@reactionable/core';`;

const typescriptImport = TypescriptImport.fromString(importString)!;

expect(typescriptImport.packageName).toEqual('@reactionable/core');
expect(typescriptImport.modules).toEqual({ App: 'CoreApp' });
expect(typescriptImport.toString()).toEqual(importString);
});
});

describe('toString', () => {
it('should retrieve an import string', async () => {
it('should retrieve a "glob" import string', async () => {
const typescriptImport = new TypescriptImport('./serviceWorker', {
'*': 'serviceWorker',
});
Expand All @@ -25,5 +35,17 @@ describe('Services - File - TypescriptImport', () => {
`import * as serviceWorker from './serviceWorker';`
);
});

it('should retrieve an "aliased" import string', async () => {
const typescriptImport = new TypescriptImport('@reactionable/core', {
App: 'CoreApp',
});

const importString = typescriptImport.toString();

expect(importString).toEqual(
`import { App as CoreApp } from '@reactionable/core';`
);
});
});
});
Loading

0 comments on commit a454599

Please sign in to comment.