Skip to content

Commit 7cb7db0

Browse files
committed
add first version
1 parent 9b08795 commit 7cb7db0

33 files changed

+26073
-0
lines changed

.browserslistrc

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
> 1%
2+
last 2 versions
3+
not dead

.editorconfig

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
root=true
2+
3+
[*]
4+
indent_style = space
5+
indent_size = 2
6+
end_of_line = lf
7+
trim_trailing_whitespace = true
8+
insert_final_newline = true
9+
max_line_length = 100
10+
11+
[*.md]
12+
trim_trailing_whitespace = false

.eslintrc.js

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
module.exports = {
2+
root: true,
3+
env: {
4+
node: true,
5+
},
6+
extends: [
7+
'plugin:vue/essential',
8+
'@vue/airbnb',
9+
],
10+
parserOptions: {
11+
parser: 'babel-eslint',
12+
},
13+
rules: {
14+
'no-console': process.env.NODE_ENV === 'production' ? 'warn' : 'off',
15+
'no-debugger': process.env.NODE_ENV === 'production' ? 'warn' : 'off',
16+
},
17+
};

.gitignore

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
.DS_Store
2+
node_modules
3+
/dist
4+
/pl-public
5+
/dependencyGraph.json
6+
7+
# local env files
8+
.env.local
9+
.env.*.local
10+
11+
# Log files
12+
npm-debug.log*
13+
yarn-debug.log*
14+
yarn-error.log*
15+
16+
# Editor directories and files
17+
.idea
18+
.vscode
19+
*.suo
20+
*.ntvs*
21+
*.njsproj
22+
*.sln
23+
*.sw?

babel.config.js

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
module.exports = {
2+
presets: [
3+
'@vue/cli-plugin-babel/preset',
4+
],
5+
};

buildScripts/PatternlabPlugin.js

Lines changed: 145 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,145 @@
1+
const globby = require('globby');
2+
const minimatch = require('minimatch');
3+
const { resolve, join } = require('path');
4+
const fs = require('fs-extra');
5+
const { info, warn } = require('@vue/cli-shared-utils');
6+
const patternlabCore = require('@pattern-lab/core');
7+
8+
const VueService = process.VUE_CLI_SERVICE;
9+
10+
const plConfig = require('../patternlab-config.json');
11+
const contentBaseDir = join(VueService.context, plConfig.paths.public.root);
12+
13+
class PatternlabPlugin {
14+
constructor() {
15+
this.pluginName = 'PatternlabPlugin';
16+
this.startTime = Date.now();
17+
this.prevTimestamps = new Map();
18+
this.patternlab = patternlabCore(plConfig);
19+
this.PlPatternPath = resolve(VueService.context, plConfig.paths.source.patterns);
20+
21+
// fix html webpack plugin error child compilation failed
22+
// due to missing index.html inside the content base dir
23+
// because patternlab build not finished before html plugin init :(
24+
// create index.html
25+
fs.ensureFileSync(join(contentBaseDir, 'index.html'));
26+
}
27+
28+
apply(compilation) {
29+
this.initHooks(compilation);
30+
}
31+
32+
initHooks(compilation) {
33+
if (compilation.hooks) {
34+
compilation.hooks.afterCompile.tap(this.pluginName, this.addPatternLabFiles.bind(this));
35+
compilation.hooks.watchRun.tap(this.pluginName, this.watchRun.bind(this));
36+
}
37+
}
38+
39+
addPatternLabFiles(compilation) {
40+
const patternFiles = this.getPatternlabFiles();
41+
patternFiles.forEach(item => {
42+
compilation.fileDependencies.add(item);
43+
});
44+
info('addPatternLabFiles', 'aftercompile');
45+
46+
if (compilation.contextDependencies && !compilation.contextDependencies.has(this.PlPatternPath)) {
47+
compilation.contextDependencies.add(this.PlPatternPath);
48+
}
49+
}
50+
51+
getPatternlabFiles() {
52+
const allWatchFiles = this.getWatchFileGlobs();
53+
54+
const files = [];
55+
allWatchFiles.forEach(globPath => {
56+
const patternFiles = globby
57+
.sync(globPath);
58+
patternFiles.forEach(item => {
59+
files.push(item);
60+
});
61+
});
62+
63+
return files;
64+
}
65+
66+
getWatchFileGlobs() {
67+
const supportedTemplateExtensions = this.patternlab.getSupportedTemplateExtensions();
68+
const templateFilePaths = supportedTemplateExtensions.map(
69+
function (extension) {
70+
return `${plConfig.paths.source.patterns}**/*${extension}`;
71+
}
72+
);
73+
74+
// pattern lab watch file globs
75+
const watchFiles = [
76+
...templateFilePaths,
77+
`${plConfig.paths.source.patterns}**/*.(json|md|yaml|yml)`,
78+
`${plConfig.paths.source.data}**/*.(json|md|yaml|yml)`,
79+
`${plConfig.paths.source.meta}**/*`,
80+
`${plConfig.paths.source.annotations}**/*`
81+
]
82+
.map(el => VueService.context + (el.startsWith('.') ? el.substr(1) : el));
83+
84+
return watchFiles;
85+
}
86+
87+
matchesWatchFileGlob(paths = []) {
88+
const globs = this.getWatchFileGlobs();
89+
let matches = [];
90+
for (let globIndex = 0; globIndex < globs.length; globIndex++) {
91+
matches = minimatch.match(paths, globs[globIndex]);
92+
if (!!matches.length) {
93+
break;
94+
}
95+
}
96+
97+
return !!matches.length;
98+
}
99+
100+
watchRun(compilation, callback) {
101+
info('watchRun');
102+
const changedFiles = Array.from(compilation.fileTimestamps.keys()).filter(
103+
watchfile => {
104+
return (
105+
(this.prevTimestamps.get(watchfile) || this.startTime)
106+
< (compilation.fileTimestamps.get(watchfile) || Infinity)
107+
);
108+
}
109+
);
110+
111+
const hasChangedPLSourceFiles = !!changedFiles.length && this.matchesWatchFileGlob(changedFiles);
112+
const removedFiles = Array.from(compilation.removedFiles);
113+
const hasDeletedPLSourceFiles = !!removedFiles.length && this.matchesWatchFileGlob(removedFiles);
114+
115+
if (hasChangedPLSourceFiles || hasDeletedPLSourceFiles) {
116+
this.buildPatternlab();
117+
}
118+
119+
this.prevTimestamps = compilation.fileTimestamps;
120+
121+
if (callback) { callback(); }
122+
}
123+
124+
buildPatternlab() {
125+
const { cleanPublic } = plConfig;
126+
const options = { 'cleanPublic': cleanPublic };
127+
128+
if (!this.patternlab.isBusy()) {
129+
try {
130+
this.patternlab.build(options)
131+
.then(r => {
132+
info('Patternlab build complete');
133+
})
134+
.catch((error) => {
135+
warn(`Patternlab build error: ${error}`);
136+
});
137+
} catch (e) {
138+
warn(`Patternlab build error: ${e}`);
139+
}
140+
}
141+
}
142+
143+
}
144+
145+
module.exports = PatternlabPlugin;
Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
const PatternLabPlugin = require('./PatternlabPlugin');
2+
3+
const { getIfUtils } = require('webpack-config-utils');
4+
const { join } = require('path');
5+
const VueService = process.VUE_CLI_SERVICE;
6+
7+
const plConfig = require('../patternlab-config.json');
8+
const { ifDevelopment } = getIfUtils(process.env.NODE_ENV);
9+
const contentBaseDir = join(VueService.context, plConfig.paths.public.root);
10+
11+
const patternLabPlugin = new PatternLabPlugin();
12+
const patternlabWebpackPlugins = [
13+
ifDevelopment(
14+
patternLabPlugin,
15+
),
16+
];
17+
18+
if (ifDevelopment()) { patternLabPlugin.buildPatternlab();}
19+
20+
exports.patternlabWebpackPlugins = patternlabWebpackPlugins;
21+
22+
const patternlabVuePluginConfig = (config) => {
23+
config
24+
.plugin('html')
25+
.tap(args => {
26+
args[0].template = join(contentBaseDir, 'index.html');
27+
return args;
28+
});
29+
30+
config.devServer.contentBase(contentBaseDir);
31+
};
32+
33+
exports.patternlabVuePluginConfig = patternlabVuePluginConfig;

0 commit comments

Comments
 (0)