Skip to content

Commit

Permalink
feat(plugin-prettier): autoset prettier config for eslint & ide integ…
Browse files Browse the repository at this point in the history
…rations
  • Loading branch information
sbekrin committed Sep 2, 2019
1 parent edfe0af commit 1c29783
Show file tree
Hide file tree
Showing 5 changed files with 69 additions and 25 deletions.
3 changes: 2 additions & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -20,5 +20,6 @@
}
]
]
}
},
"prettier": "spire-plugin-prettier/config"
}
7 changes: 7 additions & 0 deletions packages/spire-plugin-prettier/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,13 @@
- `allowCustomConfig` \<boolean\> Whether to allow user-provided config. If
this option is `false` and there's custom prettier config found it will
throw an error. Defaults to `true`.
- `autosetPrettierConfig` \<boolean\> Whether to automatically set Prettier
config in `package.json` on install or not. Defaults to `true`. _Note_: this
is essential step for eslint-plugin-prettier and IDE integrations. You can
also use `prettier.config.js` to re-export & modify target config, although
not recommended. Prefer
[`prettier` prop](https://prettier.io/docs/en/configuration.html#sharing-configurations)
when possible.
- `prettierIgnore` \<string\> Path to default `.prettierignore`. Defaults to
`.gitignore`
- `allowCustomIgnore` \<boolean\> Whether to allow user-provided
Expand Down
52 changes: 39 additions & 13 deletions packages/spire-plugin-prettier/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,32 +2,58 @@ const execa = require('execa');
const SpireError = require('spire/error');

function prettier(
{ hasFile, hasPackageProp, setState, getState },
{
hasFile,
hasPackageProp,
getPackageProp,
setPackageProp,
setState,
getState,
},
{
command = 'format',
config: defaultPrettierConfig = require.resolve(
'spire-plugin-prettier/config'
),
config: defaultPrettierConfig = 'spire-plugin-prettier/config',
autosetPrettierConfig = true,
allowCustomConfig = true,
prettierIgnore: defaultPrettierIgnore = '.gitignore',
allowCustomIgnore = true,
glob = '**/*.+(js|json|less|css|ts|tsx|md)',
}
) {
async function hasCustomPrettierConfig() {
return (
(await hasFile('.prettierrc')) ||
(await hasFile('.prettierrc.js')) ||
(await hasFile('.prettierrc.json')) ||
(await hasFile('.prettierrc.yaml')) ||
(await hasFile('.prettierrc.yml')) ||
(await hasFile('.prettierrc.toml')) ||
(await hasFile('prettier.config.js')) ||
(await hasPackageProp('prettier'))
);
}
return {
name: 'spire-plugin-prettier',
command,
description: 'format files with Prettier',
async postinstall({ logger }) {
if (autosetPrettierConfig) {
const hasCustomConfig = await hasCustomPrettierConfig();
if (hasCustomConfig) {
const currentPrettierPkgProp = await getPackageProp('prettier');
if (currentPrettierPkgProp !== defaultPrettierConfig) {
return logger.warn(
'Attempted to set Prettier config but it already exists. Please ensure existing config re-exports `%s`.',
defaultPrettierConfig
);
}
}
await setPackageProp('prettier', defaultPrettierConfig);
await execa('prettier', ['--write', 'package.json']);
}
},
async setup({ argv }) {
const hasCustomConfig =
(await hasFile('.prettierrc')) ||
(await hasFile('.prettierrc.js')) ||
(await hasFile('.prettierrc.json')) ||
(await hasFile('.prettierrc.yaml')) ||
(await hasFile('.prettierrc.yml')) ||
(await hasFile('.prettierrc.toml')) ||
(await hasFile('prettier.config.js')) ||
(await hasPackageProp('prettier'));
const hasCustomConfig = await hasCustomPrettierConfig();
const prettierConfig =
allowCustomConfig && hasCustomConfig
? []
Expand Down
30 changes: 21 additions & 9 deletions packages/spire/lib/create-core.js
Original file line number Diff line number Diff line change
@@ -1,18 +1,30 @@
const { join } = require('path');
const { pathExists, readJson } = require('fs-extra');
const { pathExists, readJson, writeJSON } = require('fs-extra');

function createCore({ cwd }, { setState, getState }) {
async function hasFile(file) {
return await pathExists(join(cwd, file));
}
async function getPackageProp(prop) {
const pkgPath = join(cwd, 'package.json');
return await readJson(pkgPath)[prop];
}
async function hasPackageProp(prop) {
return (await getPackageProp(prop)) !== undefined;
}
async function setPackageProp(prop, value) {
const pkgPath = join(cwd, 'package.json');
const currentContents = await readJson(pkgPath);
const nextContents = { ...currentContents, [prop]: value };
await writeJSON(pkgPath, nextContents);
}
return {
setState,
getState,
// Check if project contains specific file
async hasFile(file) {
return await pathExists(join(cwd, file));
},
// Check if project's package.json contains specific prop
async hasPackageProp(prop) {
return (await readJson(join(cwd, 'package.json'))).hasOwnProperty(prop);
},
hasFile,
getPackageProp,
hasPackageProp,
setPackageProp,
};
}

Expand Down
2 changes: 0 additions & 2 deletions prettier.config.js

This file was deleted.

0 comments on commit 1c29783

Please sign in to comment.