-
-
Notifications
You must be signed in to change notification settings - Fork 1.4k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
BREAKING CHANGES: create static option and remove replaced options #2670
Conversation
Codecov Report
@@ Coverage Diff @@
## v4 #2670 +/- ##
==========================================
+ Coverage 92.85% 92.88% +0.02%
==========================================
Files 37 37
Lines 1316 1293 -23
Branches 354 344 -10
==========================================
- Hits 1222 1201 -21
+ Misses 89 88 -1
+ Partials 5 4 -1
Continue to review full report at Codecov.
|
@evilebottnawi Do we need |
lib/options.json
Outdated
"minLength": 1 | ||
}, | ||
{ | ||
"type": "object" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Let's create definition
fro object notation and use here it
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Example:
"anyOf": [
{
"type": "boolean"
},
{
"$ref": "#/definitions/StaticString"
},
{
"$ref": "#/definitions/StaticObject"
},
{
"type": "array",
"items": {
"anyOf": [
{
"$ref": "#/definitions/StaticString"
},
{
"$ref": "#/definitions/StaticObject"
}
]
},
"minItems": 1
}
]
) { | ||
options.static.watch = {}; | ||
} | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think like this:
const defaultOptionsForStatic = {
directory: process.cwd(),
staticOptions: {},
publicPath: ['/'],
serveIndex: { icons: true },
// Respect options from compiler.watchOptions
watch: {
// ...
},
};
if (options.static === 'undefined') {
options.static = [{ defaultOptionsForStatic }];
} else if (typeof options.static === 'boolean') {
options.static = options.static ? [defaultOptionsForStatic] : false;
} else if (typeof options.static === 'string') {
options.static = [
{ ...defaultOptionsForStatic, directory: options.static },
];
} else if (Array.isArray(options.static)) {
options.static = options.static.map((item) => {
if (typeof item === 'string') {
return { ...defaultOptionsForStatic, directory: item };
}
return { ...defaultOptionsForStatic, ...item };
});
} else {
options.static = [{ ...defaultOptionsForStatic, ...options.static }];
}
Note - we should support --no-static
for CLI
bin/cli-flags.js
Outdated
type: Boolean, | ||
describe: 'Enable live-reloading of the content-base.', | ||
describe: 'Enable live-reloading of the static directory.', |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think we should not provide here a lot of stuff, --static=path/to/directory
and --no-static
are enough, for other complex examples you need to use the configuration
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
So we will get rid of the serve-index
CLI flag?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Also, it seems our CLI system does not work well with a no-static
flag, since static
would have to be a string flag, not sure how to work around it without a hacky method
Edit: Never mind, I think I figured it out
lib/Server.js
Outdated
} | ||
|
||
if (staticOption.watch) { | ||
this._watch(staticOption.directory, staticOption.watch); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Let's rename _watch
to watchFiles
lib/utils/normalizeOptions.js
Outdated
const watchOptions = watchOptionsConfig | ||
? watchOptionsConfig.watchOptions | ||
: {}; | ||
console.log(compiler.options.watch); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
console.log
a4e11f0
to
5caa38b
Compare
5caa38b
to
f5597e4
Compare
e3ef515
to
497f35d
Compare
} | ||
}); | ||
it('Should throw exception (number)', (done) => { | ||
it('Should throw exception (external url)', (done) => { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@evilebottnawi Is it correct that I should be throwing if isAbsoluteUrl
for the static option is true?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
No sure, I think we should improve it on schema-utils
side, and support only paths, no URLs
lib/options.json
Outdated
] | ||
} | ||
}, | ||
"required": ["directory"] |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do we need this to be required? It seems unnecessary and may be confusing if the user is just specifying watch options or something.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm going to remove this and let it default to process.cwd()
as usual if not provided, unless you think it is needed
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yep, you are right, we don't need it, because you can set only watchOptions
@@ -75,16 +70,11 @@ const options = { | |||
group: SSL_GROUP, | |||
describe: 'HTTP/2, must be used with HTTPS', | |||
}, | |||
'static-directory': { | |||
static: { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can be multiple
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@evilebottnawi Like --static=example/dir1,example/dir2
?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Like --static=example/dir1 --static=example/dir2
I'm getting |
We need to set https://github.com/paulmillr/chokidar/blob/master/index.js#L325 to true for tests, to avoid it |
lib/Server.js
Outdated
if (this.options.watchContentBase) { | ||
runnableFeatures.push('watchContentBase'); | ||
if (this.options.static) { | ||
runnableFeatures.push('serveIndex', 'watchStatic'); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think we can union static
/serveIndex
/watchStatic
in one method and static
middleware, using one without the other doesn't make sense at all
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@evilebottnawi I tried that but it causes breaking changes when historyApiFallback
is enabled. It seems that the order of middleware things that are enabled surrounding historyApiFallback is important
https://github.com/webpack/webpack-dev-server/blob/master/lib/Server.js#L554-L575
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why do not put static
feature after historyApiFallback
, or maybe we should union historyApiFallback
with static
features?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think it makes sense to add it to static
since it deals with serving static HTML content
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yep, i think we should add the historyApiFallback
option to static
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@evilebottnawi After some searching I figured out that contentBaseFiles
(
webpack-dev-server/lib/Server.js
Line 562 in 4ab1f21
runnableFeatures.push('contentBaseFiles'); |
historyApiFallback
for this reason:
Is it possible that the middleware
feature is added multiple times for a similar reason? Changing it so that there is only 1 middleware
pushed does not seem to break any tests, but maybe tests were not made for it?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think I will not mess with the middleware
runnable feature, but will investigate it later and see if I can add some tests for having it get pushed multiple times.
I have made the 3 features: static
, serveIndex
, and watchStatic
. It would be ideal to have only the static
feature, but it is complicated by the historyApiFallback
feature so having 3 features is the easiest solution at the moment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It is very weird, because if we can't find something in static
and history
we should return 404
, not trying to do it again 😕 maybe I something don't understand
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@evilebottnawi It isn't a matter of finding something or returning a 404, but rather the priority of static
vs history
when they are both trying to serve something from the same path. I still don't know exactly why it works, but placing static
middleware before and after seems to ensure that static files take priority over the history api fallback file.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yep, I see, very weird, but we can't do something here 😞
lib/Server.js
Outdated
this.setupStaticFeature(); | ||
}, | ||
// Todo rename to `serveIndex` in future major release | ||
contentBaseIndex: () => { | ||
serveIndex: () => { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
staticServeIndex
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
and this.setupStaticServeIndexFeature
lib/Server.js
Outdated
this.setupServeIndexFeature(); | ||
}, | ||
// Todo rename to `watchStatic` in future major release | ||
watchContentBase: () => { | ||
watchStatic: () => { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
staticWatch
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
and this.setupStaticWatchFeature
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
To keep static
name feature consistently
lib/Server.js
Outdated
@@ -382,10 +382,10 @@ class Server { | |||
static: () => { | |||
this.setupStaticFeature(); | |||
}, | |||
serveIndex: () => { | |||
staticServeIndex: () => { | |||
this.setupServeIndexFeature(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
And let's rename method names: this.setupStaticServeIndexFeature
, as I written above 🥇
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
And let's rename method names:
this.setupStaticServeIndexFeature
, as I written above
Just did that 👍
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
/cc @hiroppy
Feel free to merge after CI will be green
For Bugs and Features; did you add new tests?
Not yet
Motivation / Use-Case
static
option is replacing many existing options. Seeoptions.json
.Breaking Changes
contentBase
,contentBasePublicPath
,serveIndex
,staticOptions
,watchContentBase
,watchOptions
in favor ofstatic
contentBase
Additional Info