Skip to content

Commit

Permalink
Merge pull request #7 from zakhenry/feat/refactor-use-commander
Browse files Browse the repository at this point in the history
refactor(Lib): Use commander library rather than minimist for more
  • Loading branch information
maxime1992 authored Aug 26, 2019
2 parents 9f563bf + 9a8d1d1 commit 1d7a972
Show file tree
Hide file tree
Showing 6 changed files with 88 additions and 33 deletions.
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -4,3 +4,4 @@ dist
coverage
bin
.rpt2_cache
.idea
5 changes: 3 additions & 2 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -123,9 +123,10 @@
"typescript": "^3.0.3"
},
"dependencies": {
"chalk": "^2.4.2",
"commander": "^2.20.0",
"dotenv": "8.0.0",
"front-matter": "3.0.2",
"got": "9.6.0",
"minimist": "1.2.0"
"got": "9.6.0"
}
}
7 changes: 7 additions & 0 deletions src/dev-to-git.interface.ts
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,13 @@ export enum UpdateStatus {
FAILED_TO_EXTRACT_FRONT_MATTER = 'FailedToExtractFrontMatter',
}

export interface ConfigurationOptions {
silent: boolean;
config: string; // the config file path
devToToken: string;
repository: Repository;
}

export type ArticlePublishedStatus = {
articleId: number;
} & (
Expand Down
96 changes: 67 additions & 29 deletions src/dev-to-git.ts
Original file line number Diff line number Diff line change
@@ -1,58 +1,94 @@
import minimist from 'minimist';
import fs from 'fs';
import chalk from 'chalk';
import program from 'commander';
import dotenv from 'dotenv';
import { ArticleConfig, ArticleConfigFile, Repository, ArticlePublishedStatus } from './dev-to-git.interface';
import fs from 'fs';
import { Article } from './article';
import { formatArticlePublishedStatuses } from './helpers';
import {
ArticleConfig,
ArticleConfigFile,
ArticlePublishedStatus,
ConfigurationOptions,
Repository,
} from './dev-to-git.interface';
import { formatArticlePublishedStatuses, logBuilder, Logger } from './helpers';

export const DEFAULT_CONFIG_PATH: string = './dev-to-git.json';

const repositoryRe: RegExp = /.*\/(.*)\/(.*)\.git/;

export class DevToGit {
private configPath: string = DEFAULT_CONFIG_PATH;
private token: string = '';
private repository: Repository = { username: '', name: '' };
private configuration: ConfigurationOptions;

public logger: Logger;

constructor() {
dotenv.config();

const { config } = minimist(process.argv.slice(2));
const pkg = require('../package.json');

program
.version(pkg.version)
.arguments('[...files]')
.option('--config <path>', `Pass custom path to .dev-to-git.json file`, DEFAULT_CONFIG_PATH)
.option(
'--dev-to-token <token>',
'Token for publishing to dev.to',
userValue => userValue || process.env.DEV_TO_GIT_TOKEN,
)
.option('--repository-url <url>', 'Url of your repository you keep your articles in.')
.option('--silent', `No console output`)
.parse(process.argv);

const configuration: ConfigurationOptions = (program as unknown) as ConfigurationOptions;
this.configuration = configuration;

if (config && typeof config === 'string') {
this.configPath = config;
this.logger = logBuilder(this.configuration);

this.configuration.repository = this.parseRepository(program.repositoryUrl) || this.extractRepository();

if (!this.configuration.devToToken) {
this.logger(chalk.red('DEV_TO_GIT_TOKEN environment variable, or --dev-to-token argument is required'));
process.exit(1);
}
}

this.extractRepository();
private parseRepository(repo: string): Repository | null {
const match = repo.match(repositoryRe);

if (!process.env.DEV_TO_GIT_TOKEN) {
throw new Error('Token is required');
if (!match) {
return null;
}

this.token = process.env.DEV_TO_GIT_TOKEN;
return {
username: match![1],
name: match![2],
};
}

private extractRepository(): void {
private extractRepository(): Repository {
try {
const packageJson = JSON.parse(fs.readFileSync('./package.json').toString());

const matchRepositoryUrl = (packageJson.repository.url as string).match(repositoryRe);
const repo = this.parseRepository(packageJson.repository.url);

if (matchRepositoryUrl) {
const [_, username, name] = matchRepositoryUrl;
this.repository = { username, name };
} else {
throw new Error();
if (!repo) {
throw Error();
}

return repo;
} catch (error) {
throw new Error(
'You must have within your "package.json" a "repository" attribute which is an object and contains itself an attribute "url" like the following: https://github-gitlab-whatever.com/username/repository-name.git - this will be used to generate images links if necessary',
this.logger(
chalk.red(
'If you do not specify --repository-url, you must have within your "package.json" a "repository" attribute which is an object and contains itself an attribute "url" like the following: https://github-gitlab-whatever.com/username/repository-name.git - this will be used to generate images links if necessary',
),
);
process.exit(1);
}
throw new Error('Should not be reached');
}

public getConfigPath(): string {
return this.configPath;
return this.configuration.config;
}

public readConfigFile(): ArticleConfig[] {
Expand All @@ -64,7 +100,7 @@ export class DevToGit {

return articleConfigFiles.map(articleConfigFile => ({
...articleConfigFile,
repository: this.repository,
repository: this.configuration.repository,
}));
}

Expand All @@ -74,7 +110,7 @@ export class DevToGit {
return Promise.all(
articles.map(articleConf => {
const article = new Article(articleConf);
return article.publishArticle(this.token);
return article.publishArticle(this.configuration.devToToken);
}),
);
}
Expand All @@ -85,7 +121,9 @@ const devToGit = new DevToGit();
devToGit
.publishArticles()
.then(formatArticlePublishedStatuses)
.then(console.log)
.catch(() => {
throw new Error(`An error occured while publishing the articles`);
.then(statuses => devToGit.logger(statuses))
.catch(err => {
devToGit.logger(chalk.red(`An error occurred while publishing the articles`));
console.error(err);
process.exit(1);
});
10 changes: 9 additions & 1 deletion src/helpers.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { ArticlePublishedStatus, UpdateStatus } from './dev-to-git.interface';
import { ArticlePublishedStatus, ConfigurationOptions, UpdateStatus } from './dev-to-git.interface';

export const formatArticlePublishedStatuses = (articlePublishedStatuses: ArticlePublishedStatus[]): string => {
return articlePublishedStatuses
Expand Down Expand Up @@ -33,3 +33,11 @@ class UnreachabelCase {
// tslint:disable-next-line:no-empty
constructor(payload: never) {}
}

export type Logger = (...messages: string[]) => void;

export const logBuilder = (options: ConfigurationOptions): Logger => (...messages: string[]) => {
if (!options.silent) {
console.log(...messages);
}
};
2 changes: 1 addition & 1 deletion yarn.lock
Original file line number Diff line number Diff line change
Expand Up @@ -2114,7 +2114,7 @@ combined-stream@^1.0.6, combined-stream@~1.0.6:
dependencies:
delayed-stream "~1.0.0"

commander@^2.12.1, commander@^2.14.1, commander@^2.9.0, commander@~2.20.0:
commander@^2.12.1, commander@^2.14.1, commander@^2.20.0, commander@^2.9.0, commander@~2.20.0:
version "2.20.0"
resolved "https://registry.yarnpkg.com/commander/-/commander-2.20.0.tgz#d58bb2b5c1ee8f87b0d340027e9e94e222c5a422"
integrity sha512-7j2y+40w61zy6YC2iRNpUe/NwhNyoXrYpHMrSunaMG64nRnaf96zO/KMQR4OyN/UnE5KLyEBnKHd4aG3rskjpQ==
Expand Down

0 comments on commit 1d7a972

Please sign in to comment.