synyx / springboot-reactjs-demo

A simple demo app to demonstrate server side rendering with nashorn
Apache License 2.0
18 stars 11 forks source link

Please help me with adding a css files to this project =) #1

Closed serpentcross closed 7 years ago

serpentcross commented 7 years ago

Hello! Your example with reactjs and nashorn is awesome, but unfortunatelly I have no idea how to include a css files for my .jsx components.

for example, I have a file header.jsx and header.css with styles.

My header.jsx file has a code like:

import React from 'react' import 'header.css';

class Header extends React.Component {

render() {
    return (
        <div className="b-page__line">
            <div className="b-head">
                  <LogoType />
            </div>
        </div>
    );
}

}

class LogoType extends React.Component {

render() {
    return (
        <div className="b-head__logo">
            <div className="b-logo">
                <a href="#">
                    <img className="b-logo__img" src="img/Logo.png"/>
                </a>
            </div>
        </div>
    )
}

}

My package.json:

{ "name": "myproject", "version": "2.0.0", "desription": "", "scripts": { "build": "webpack", "postinstall": "npm run build" }, "author": "", "license": "Apache License 2.0", "devDependencies": { "babel-core": "^6.24.0", "babel-loader": "^6.4.1", "babel-preset-es2015": "^6.24.0", "babel-preset-react": "^6.23.0", "css-loader": "^0.26.1", "extract-text-webpack-plugin": "^0.8.1", "postcss-color-rebeccapurple": "^1.1.0", "postcss-loader": "^0.4.3", "react-css-modules": "^4.2.0", "react": "^0.14.8", "react-dom": "^0.14.8", "style-loader": "^0.13.1", "webpack": "^1.14.0" }, "babel": { "presets": [ "es2015", "react" ] } }

My webpack.config.js:

var path = require ('path');

var clientSrcPath = path.resolve (dirname, 'frontend'); var serverSrcPath = path.resolve (dirname, 'src/main/resources/static');

module.exports = { module: { loaders: [ { test: /.jsx?$/, loader: 'babel', exclude: /node_modules/, query: { presets: ['react', 'es2015'] } }, { test: /.css$/, loader: 'style!css?modules&localIdentName=[name]---[local]---[hash:base64:5]' } ] }, entry: clientSrcPath + '/index.jsx', output: { path: serverSrcPath, filename: 'bundle.js' }, resolve: { extensions: ['', '.js', '.jsx'], } };

Exception text:

17:48:24,128 ERROR [org.springframework.boot.web.support.ErrorPageFilter] (default task-3) Forwarding to error page from request [/] due to exception [Error: Cannot find module "header.css" in at line number 19846 at column number 142]: javax.script.ScriptException: Error: Cannot find module "header.css" in at line number 19846 at column number 142 at jdk.nashorn.api.scripting.NashornScriptEngine.throwAsScriptException(NashornScriptEngine.java:467) at jdk.nashorn.api.scripting.NashornScriptEngine.evalImpl(NashornScriptEngine.java:451) at jdk.nashorn.api.scripting.NashornScriptEngine.evalImpl(NashornScriptEngine.java:403) at jdk.nashorn.api.scripting.NashornScriptEngine.evalImpl(NashornScriptEngine.java:399) at jdk.nashorn.api.scripting.NashornScriptEngine.eval(NashornScriptEngine.java:150) at javax.script.AbstractScriptEngine.eval(AbstractScriptEngine.java:249) at ru.alfabank.ef.msos.configurations.React.getNashornScriptEngine(React.java:32) at ru.alfabank.ef.msos.configurations.React.renderEntryPoint(React.java:17) at ru.alfabank.ef.msos.controllers.MainController.mainPage(MainController.java:27) at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) at java.lang.reflect.Method.invoke(Method.java:498) at org.springframework.web.method.support.InvocableHandlerMethod.doInvoke(InvocableHandlerMethod.java:205) at org.springframework.web.method.support.InvocableHandlerMethod.invokeForRequest(InvocableHandlerMethod.java:133) at org.springframework.web.servlet.mvc.method.annotation.ServletInvocableHandlerMethod.invokeAndHandle(ServletInvocableHandlerMethod.java:116) at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.invokeHandlerMethod(RequestMappingHandlerAdapter.java:827) at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.handleInternal(RequestMappingHandlerAdapter.java:738) at org.springframework.web.servlet.mvc.method.AbstractHandlerMethodAdapter.handle(AbstractHandlerMethodAdapter.java:85) at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:963) at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:897) at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:970) at org.springframework.web.servlet.FrameworkServlet.doGet(FrameworkServlet.java:861) at javax.servlet.http.HttpServlet.service(HttpServlet.java:687) at org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.java:846) at javax.servlet.http.HttpServlet.service(HttpServlet.java:790) at io.undertow.servlet.handlers.ServletHandler.handleRequest(ServletHandler.java:85) at io.undertow.servlet.handlers.FilterHandler$FilterChainImpl.doFilter(FilterHandler.java:129) at org.springframework.web.filter.RequestContextFilter.doFilterInternal(RequestContextFilter.java:99) at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) at io.undertow.servlet.core.ManagedFilter.doFilter(ManagedFilter.java:61) at io.undertow.servlet.handlers.FilterHandler$FilterChainImpl.doFilter(FilterHandler.java:131) at org.springframework.web.filter.HttpPutFormContentFilter.doFilterInternal(HttpPutFormContentFilter.java:105) at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) at io.undertow.servlet.core.ManagedFilter.doFilter(ManagedFilter.java:61) at io.undertow.servlet.handlers.FilterHandler$FilterChainImpl.doFilter(FilterHandler.java:131) at org.springframework.web.filter.HiddenHttpMethodFilter.doFilterInternal(HiddenHttpMethodFilter.java:81) at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) at io.undertow.servlet.core.ManagedFilter.doFilter(ManagedFilter.java:61) at io.undertow.servlet.handlers.FilterHandler$FilterChainImpl.doFilter(FilterHandler.java:131) at org.springframework.web.filter.CharacterEncodingFilter.doFilterInternal(CharacterEncodingFilter.java:197) at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) at io.undertow.servlet.core.ManagedFilter.doFilter(ManagedFilter.java:61) at io.undertow.servlet.handlers.FilterHandler$FilterChainImpl.doFilter(FilterHandler.java:131) at org.springframework.boot.web.support.ErrorPageFilter.doFilter(ErrorPageFilter.java:115) at org.springframework.boot.web.support.ErrorPageFilter.access$000(ErrorPageFilter.java:59) at org.springframework.boot.web.support.ErrorPageFilter$1.doFilterInternal(ErrorPageFilter.java:90) at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) at org.springframework.boot.web.support.ErrorPageFilter.doFilter(ErrorPageFilter.java:108) at io.undertow.servlet.core.ManagedFilter.doFilter(ManagedFilter.java:61) at io.undertow.servlet.handlers.FilterHandler$FilterChainImpl.doFilter(FilterHandler.java:131) at io.undertow.servlet.handlers.FilterHandler.handleRequest(FilterHandler.java:84) at io.undertow.servlet.handlers.security.ServletSecurityRoleHandler.handleRequest(ServletSecurityRoleHandler.java:62) at io.undertow.servlet.handlers.ServletDispatchingHandler.handleRequest(ServletDispatchingHandler.java:36) at org.wildfly.extension.undertow.security.SecurityContextAssociationHandler.handleRequest(SecurityContextAssociationHandler.java:78) at io.undertow.server.handlers.PredicateHandler.handleRequest(PredicateHandler.java:43) at io.undertow.servlet.handlers.security.SSLInformationAssociationHandler.handleRequest(SSLInformationAssociationHandler.java:131) at io.undertow.servlet.handlers.security.ServletAuthenticationCallHandler.handleRequest(ServletAuthenticationCallHandler.java:57) at io.undertow.server.handlers.PredicateHandler.handleRequest(PredicateHandler.java:43) at io.undertow.security.handlers.AbstractConfidentialityHandler.handleRequest(AbstractConfidentialityHandler.java:46) at io.undertow.servlet.handlers.security.ServletConfidentialityConstraintHandler.handleRequest(ServletConfidentialityConstraintHandler.java:64) at io.undertow.security.handlers.AuthenticationMechanismsHandler.handleRequest(AuthenticationMechanismsHandler.java:60) at io.undertow.servlet.handlers.security.CachedAuthenticatedSessionHandler.handleRequest(CachedAuthenticatedSessionHandler.java:77) at io.undertow.security.handlers.NotificationReceiverHandler.handleRequest(NotificationReceiverHandler.java:50) at io.undertow.security.handlers.AbstractSecurityContextAssociationHandler.handleRequest(AbstractSecurityContextAssociationHandler.java:43) at io.undertow.server.handlers.PredicateHandler.handleRequest(PredicateHandler.java:43) at org.wildfly.extension.undertow.security.jacc.JACCContextIdHandler.handleRequest(JACCContextIdHandler.java:61) at io.undertow.server.handlers.PredicateHandler.handleRequest(PredicateHandler.java:43) at io.undertow.server.handlers.PredicateHandler.handleRequest(PredicateHandler.java:43) at io.undertow.servlet.handlers.ServletInitialHandler.handleFirstRequest(ServletInitialHandler.java:292) at io.undertow.servlet.handlers.ServletInitialHandler.access$100(ServletInitialHandler.java:81) at io.undertow.servlet.handlers.ServletInitialHandler$2.call(ServletInitialHandler.java:138) at io.undertow.servlet.handlers.ServletInitialHandler$2.call(ServletInitialHandler.java:135) at io.undertow.servlet.core.ServletRequestContextThreadSetupAction$1.call(ServletRequestContextThreadSetupAction.java:48) at io.undertow.servlet.core.ContextClassLoaderSetupAction$1.call(ContextClassLoaderSetupAction.java:43) at io.undertow.servlet.api.LegacyThreadSetupActionWrapper$1.call(LegacyThreadSetupActionWrapper.java:44) at io.undertow.servlet.api.LegacyThreadSetupActionWrapper$1.call(LegacyThreadSetupActionWrapper.java:44) at io.undertow.servlet.api.LegacyThreadSetupActionWrapper$1.call(LegacyThreadSetupActionWrapper.java:44) at io.undertow.servlet.api.LegacyThreadSetupActionWrapper$1.call(LegacyThreadSetupActionWrapper.java:44) at io.undertow.servlet.api.LegacyThreadSetupActionWrapper$1.call(LegacyThreadSetupActionWrapper.java:44) at io.undertow.servlet.handlers.ServletInitialHandler.dispatchRequest(ServletInitialHandler.java:272) at io.undertow.servlet.handlers.ServletInitialHandler.access$000(ServletInitialHandler.java:81) at io.undertow.servlet.handlers.ServletInitialHandler$1.handleRequest(ServletInitialHandler.java:104) at io.undertow.server.Connectors.executeRootHandler(Connectors.java:202) at io.undertow.server.HttpServerExchange$1.run(HttpServerExchange.java:805) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617) at java.lang.Thread.run(Thread.java:745)

Please help!!!!

bseber commented 7 years ago

hi @serpentcross

I've updated the demo with css support. in short these are two steps:

I hope this helps :)

serpentcross commented 7 years ago

@bseber Thank you, that you've responded so quickly to my request! Ok, I will test it out.

I have one more question - what if I want to use .jsx files instead .js? Could you please provide webpack configuration for this case?

serpentcross commented 7 years ago

@bseber unfortunatelly, the same issue =(

ERROR in ./frontend/components/header/header.css Module parse failed: W:\test-projects\azon-react\frontend\components\header\header.css Unexpected token (1:0) You may need an appropriate loader to handle this file type. SyntaxError: Unexpected token (1:0) at Parser.pp$4.raise (W:\test-projects\azon-react\node_modules\webpack\node_modules\acorn\dist\acorn.js:2221:15) at Parser.pp.unexpected (W:\test-projects\azon-react\node_modules\webpack\node_modules\acorn\dist\acorn.js:603:10) at Parser.pp$3.parseExprAtom (W:\test-projects\azon-react\node_modules\webpack\node_modules\acorn\dist\acorn.js:1822:12) at Parser.pp$3.parseExprSubscripts (W:\test-projects\azon-react\node_modules\webpack\node_modules\acorn\dist\acorn.js:1715:21) at Parser.pp$3.parseMaybeUnary (W:\test-projects\azon-react\node_modules\webpack\node_modules\acorn\dist\acorn.js:1692:19) at Parser.pp$3.parseExprOps (W:\test-projects\azon-react\node_modules\webpack\node_modules\acorn\dist\acorn.js:1637:21) at Parser.pp$3.parseMaybeConditional (W:\test-projects\azon-react\node_modules\webpack\node_modules\acorn\dist\acorn.js:1620:21) at Parser.pp$3.parseMaybeAssign (W:\test-projects\azon-react\node_modules\webpack\node_modules\acorn\dist\acorn.js:1597:21) at Parser.pp$3.parseExpression (W:\test-projects\azon-react\node_modules\webpack\node_modules\acorn\dist\acorn.js:1573:21) at Parser.pp$1.parseStatement (W:\test-projects\azon-react\node_modules\webpack\node_modules\acorn\dist\acorn.js:727:47) at Parser.pp$1.parseTopLevel (W:\test-projects\azon-react\node_modules\webpack\node_modules\acorn\dist\acorn.js:638:25) at Parser.parse (W:\test-projects\azon-react\node_modules\webpack\node_modules\acorn\dist\acorn.js:516:17) at Object.parse (W:\test-projects\azon-react\node_modules\webpack\node_modules\acorn\dist\acorn.js:3098:39) at Parser.parse (W:\test-projects\azon-react\node_modules\webpack\lib\Parser.js:902:15) at DependenciesBlock. (W:\test-projects\azon-react\node_modules\webpack\lib\NormalModule.js:104:16) at DependenciesBlock.onModuleBuild (W:\test-projects\azon-react\node_modules\webpack-core\lib\NormalModuleMixin.js:310:10) at nextLoader (W:\test-projects\azon-react\node_modules\webpack-core\lib\NormalModuleMixin.js:275:25) at W:\test-projects\azon-react\node_modules\webpack-core\lib\NormalModuleMixin.js:259:5 at Storage.finished (W:\test-projects\azon-react\node_modules\enhanced-resolve\lib\CachedInputFileSystem.js:38:16) at W:\test-projects\azon-react\node_modules\graceful-fs\graceful-fs.js:78:16 at FSReqWrap.readFileAfterClose [as oncomplete] (fs.js:446:3) @ ./frontend/components/header/header.jsx 13:14-37

My package.json

{ "name": "project", "version": "2.0.0", "desription": "test Version based on React JS", "scripts": { "build": "webpack", "postinstall": "npm run build" }, "author": "Benjamin Seber <seber@synyx.de>", "license": "Apache License 2.0", "devDependencies": { "babel-core": "^6.24.0", "babel-loader": "^6.4.1", "babel-preset-es2015": "^6.24.0", "babel-preset-react": "^6.23.0", "css-loader": "^0.26.1", "extract-text-webpack-plugin": "^0.8.1", "postcss-color-rebeccapurple": "^1.1.0", "postcss-loader": "^0.4.3", "react-css-modules": "^4.2.0", "react": "^0.14.8", "react-dom": "^0.14.8", "style-loader": "^0.12.3", "webpack": "^1.14.0" }, "babel": { "presets": [ [ "es2015", { "modules": false } ], "react" ] } }

my webpack.config.js

`var path = require ('path'); var ExtractTextPlugin = require ('extract-text-webpack-plugin');

var clientSrcPath = path.resolve (dirname, 'frontend'); var serverSrcPath = path.resolve (dirname, 'src/main/resources/static');

module.exports = {

entry: clientSrcPath + '/' + 'index.jsx',

output: {
    path: serverSrcPath,
    filename: 'bundle.js'
},

plugins: [
    new ExtractTextPlugin('styles.css'),
],

module: {
    rules: [
        {
            test: /\.jsx?$/,
            exclude: /node_modules/,
            loader: 'babel-loader'
        },
        {
            test: /.css/,
            exclude: /node_modules/,
            use: ExtractTextPlugin.extract(
                {
                    fallback: 'style-loader',
                    use: [
                        {
                            loader: 'css-loader',
                            options: {
                                modules: true
                            }
                        }
                    ]
                }
            )
        }
    ]
},
resolve: {
    extensions: ['', '.js', '.jsx'],
}

};`

my header.jsx

`import React from 'react' import styles from './header.css';

class Header extends React.Component {

render() {
    return (
        <div className="b-page__line">
            <div className="b-head">
                <LogoType />
                <HeadSearchBar />
            </div>
        </div>
    );
}

}

class LogoType extends React.Component {

render() {
    return (
        <div className="b-head__logo">
            <div className="b-logo">
                <a href="#">
                    <img className="b-logo__img" src="img/Logo.png"/>
                </a>
            </div>
        </div>
    )
}

}

class HeadSearchBar extends React.Component {

render() {
    return (
        <div className="b-head__search">
            <div className="b-search">
                <div className="b-search__input">
                    <input type="text" className="b-input b-input_search" placeholder="Search"/>
                </div>
                <div className="b-search__input">
                    <div className="b-button">GO</div>
                </div>
            </div>
        </div>
    )
}

}

export default Header; `

bseber commented 7 years ago

@serpentcross please update your npm modules. it should work afterwards :) note that you don't need the empty string in your webpack.conf resolve.extensions anymore with webpack v2

serpentcross commented 7 years ago

Dear @bseber ! Thank you very much! Vielen Dank aus Russland! :D ))) Now everything works very fine)))

unfortunatelly, I couldn't make it work with BEM Metodology (example styleName like 'b-head__part'), but it works fine with names like bHeadPart. It's ok. It's fully suitable solution.

p.s.

Do you know some ways, how to rebuild / repack application "on fly" more quickly? Cause now I have to rebuild it completely from beginning, each time I change something in my code.

But anyway even without it - everything works and this issue is completely closed! Thanks!!! =)