Skip to content
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

Can not get it running properly #51

Closed
musicformellons opened this issue Mar 10, 2016 · 12 comments
Closed

Can not get it running properly #51

musicformellons opened this issue Mar 10, 2016 · 12 comments

Comments

@musicformellons
Copy link

I spend a lot of time on setting it up (following amongst others your post here):
http://owaislone.org/blog/webpack-plus-reactjs-and-django/
, tackling several minor issues:

Still it is not working 'as expected'. Part of the problem is I do not exactly know what to expect. The purposes of separating Django world from JS (webpack) world seems sensible to me. But the exact separation is not clear and not working for me. My background is mainly the Django world in which I could get JS and CSS working from a staticfolder. I am not -until recently- very familiar with the npm, webpack, js world of things and I do have a couple of questions that when answered might shed some light on the problems I'm having:

  1. I read in one of the closed issues that Django-webpack-loader solution is aimed at .js and .css ; So not images and other static items. Is that correct y/n? If yes, how should you treat 'other items': the Django way, or the JS way (or choose?). Does it makes sense to just 'build a bridge' for js and css ?
  2. Following the article it says "If you left webpack running in watch mode, it should automatically pick up the changes and compile a new bundle." I tried a simple Django project to make things more clear for myself, but automatic rebuilding is not happening... It just compiles the same bundle once (no new hash), no error... nothing new.
  3. I did manage to have webpack build script run and then have new bundles compiled (when I imported new js libraries), so that seems to work fine; also the bundle-tracker gets new correct hash, so that seems fine. However, I tried to incorporate the js and css into a page, it does not work I think. Part of the problem is I do not know if I test correctly. Your article gives the setup/framework but no real proof of working js or css as far as I can see. In my setup for sure I only see html layout so the css is not coming through from the bundle...
  4. I do not know exactly how the css should work. It seems that it should be included into the main-hash.js bundle and is import into html from that bundle... Is that correct? Could there be a detailed example of how to go about. For example I would like to use bootstrap which consists of bootstrap.js and bootstrap.css; Do I import both from the index.js and then they will be included in the bundle and then using the {% load render_bundle from webpack_loader %} {% render_bundle 'main' %} ? An example with bootstrap and/ or materialcss would be very helpful. Also when I have a custom.css, how do I include it?
  5. I do not really need the react part; I assume that is not a dealbreaker and using django-webpack-loader still makes sense?!
  6. After you made a bundle with webpack and want to go live, do you include the bundle in a 'normal Django static folder'? It seems to be explained somewhere but it is still not really clear to me.

Here is my config:

//Webpack.config.js

var path = require('path');
var webpack = require('webpack');
var BundleTracker = require('webpack-bundle-tracker');
var HtmlWebpackPlugin = require('html-webpack-plugin');
var Clean = require('clean-webpack-plugin');
var bootstrapPath = path.join(__dirname, 'node_modules/bootstrap/dist/css');
var sourcePath = path.join(__dirname, 'assets');

module.exports = {
    devtool: 'eval-source-map',
    context: __dirname,
    entry: './assets/js/index', // entry point of our app. .assets/js/index.js should require other js modules and dependencies it needs
    output: {
        path: path.resolve('./assets/bundles/'),
        filename: '[name]-[hash].js'
    },
    node: {
        console: true,
        fs: 'empty'
    },
    plugins: [
        new webpack.ProvidePlugin({
            $: 'jquery',
            jQuery: 'jquery'
        }),
        new BundleTracker({filename: './webpack-stats.json'}),
        new webpack.BannerPlugin('Banner!!!! todo'),
        new HtmlWebpackPlugin({
            template: __dirname + '/assets/index.tmpl.html'
        }),
        new webpack.HotModuleReplacementPlugin(),
        new Clean(['assets/bundles'])
    ],
    module: {
        loaders: [
            {
                test: /\.js[x]?$/,
                loader: 'babel',
                exclude: /(node_modules|bower-components)/,
                query: {
                    presets: ['es2015', 'stage-0']
                }
            },
            {
                test: /\.json$/,
                loader: 'json-loader'
            },
            {
                test: /\.js$/,
                include: path.resolve(__dirname, 'node_modules/mapbox-gl/js/render/shaders.js'),
                loader: 'transform/cacheable?brfs'
            },
            {
                test: /\.js$/,
                include: path.resolve(__dirname, 'node_modules/webworkify/index.js'),
                loader: 'worker'
            },
            {
                test: /\.css$/,
                loader: 'style!css?modules!postcss'
            },
            {
                test: /\.scss$/,
                loaders: ['style', 'css?sourceMap', 'sass?sourceMap']
            },
            {test: /\.woff(\?v=\d+\.\d+\.\d+)?2?$/, loader: 'url-loader'},
            {test: /\.ttf(\?v=\d+\.\d+\.\d+)?$/, loader: 'url-loader'},
            {test: /\.eot(\?v=\d+\.\d+\.\d+)?$/, loader: 'url-loader'},
            {test: /\.svg(\?v=\d+\.\d+\.\d+)?$/, loader: 'url-loader'}
        ]
    },
    postcss: [
        require('autoprefixer')
    ],
    resolve: {
        modulesDirectories: ['node_modules', 'bower_components', bootstrapPath, sourcePath],
        extensions: ['', '.js', '.jsx', '.css'],
        alias: {
            webworkify: 'webworkify-webpack',
            '$': 'jquery',
            'jQuery': 'jquery'
        }
    },
    devServer: {
        contentBase: './assets',
        colors: true,
        historyApiFallback: true,
        inline: true,
        hot: true
    }
};




//index.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="utf-8">
    <title>Webpack Sample Project</title>
</head>
<body>
<div id='root'>
</div>
<script src="main-4809d8e09cbc474f2d6a.js"></script></body>
</html>



//assets/js/index.js

import '../star-rating';
import '../../node_modules/turf/turf';
import '../ie10-viewport-bug-workaround';
import '../../node_modules/jquery/src/jquery.js';
//import '../../node_modules/materialize-css/dist/js/materialize.js';
//import '../../node_modules/materialize-css/dist/css/materialize.css';
//import '../../node_modules/materialize-css/js/init.js';
import '../../node_modules/bootstrap/dist/js/bootstrap.js';
import '../../node_modules/bootstrap/dist/css/bootstrap.min.css';
import '../css/custom';


//head_css.html

{% load staticfiles %}

{% load render_bundle from webpack_loader %}

{% render_bundle 'main' %}

<link href="{% static 'css/font-awesome.min.css' %}" rel="stylesheet">

<!--Import materialize.css-->
{#<link type="text/css" rel="stylesheet" href="css/materialize.min.css" media="screen,projection"/>#}

{#<link rel="stylesheet" href="{% static 'css/bootstrap.min.css' %}">#}
{#<link rel="stylesheet" href="http://maxcdn.bootstrapcdn.com/bootstrap/3.3.5/css/bootstrap.min.css">#}
<!-- Custom styles for this template -->
{#<link href="{% static 'css/navbar-static-top.css' %}" rel="stylesheet">#}
{#    <link href="{% static 'css/star-rating.min.css'%}" media="all" rel="stylesheet" type="text/css">#}
{#<link href="{% static 'css/star-rating.css' %}" media="all" rel="stylesheet" type="text/css">#}
{#<link href="{% static 'css/custom.css' %}" rel="stylesheet">#}



//settings/common.py



# -*- coding: utf-8 -*-
"""
Django settings for myapp project.

For more information on this file, see
https://docs.djangoproject.com/en/dev/topics/settings/

For the full list of settings and their values, see
https://docs.djangoproject.com/en/dev/ref/settings/
"""
# from __future__ import absolute_import, unicode_literals   # python 3 toch?
import environ  # in baserequirements as django-environ

ROOT_DIR = environ.Path(__file__) - 3  # (/a/b/myfile.py - 3 = /)
APPS_DIR = ROOT_DIR.path('myapp')

env = environ.Env()
environ.Env.read_env()

# WEBPACK LOADER CONFIG
WEBPACK_LOADER = {
    'DEFAULT': {
        'BUNDLE_DIR_NAME': 'bundles/',
        'STATS_FILE': str(ROOT_DIR.path('webpack-stats.json'))
    }
}

# print(WEBPACK_LOADER['STATS_FILE'])

# APP CONFIGURATION
# ------------------------------------------------------------------------------
DJANGO_APPS = (
    # Default Django apps:
    'django.contrib.auth',
    'django.contrib.contenttypes',
    'django.contrib.sessions',
    'django.contrib.sites',
    'django.contrib.messages',
    'django.contrib.staticfiles',

    # category: Admin apps
    'flat',
    'django.contrib.admin',
)

THIRD_PARTY_APPS = (
    'crispy_forms',  # Form layouts
    'allauth',  # registration
    'allauth.account',  # registration
    'allauth.socialaccount',  # registration

    'webpack_loader',  # Django-webpack-loader

    'localflavor'
)

# Apps specific for this project go here.
LOCAL_APPS = (
    'myapp.users',  # custom users app
    # Your stuff: custom apps go here
    'newsletter',
    'jobs',
    'likes',
    'matches',
    'profiles',
    'questions',
)


# See: https://docs.djangoproject.com/en/dev/ref/settings/#installed-apps
INSTALLED_APPS = DJANGO_APPS + THIRD_PARTY_APPS + LOCAL_APPS + ALLAUTH_PROVIDER_APPS

# MIDDLEWARE CONFIGURATION
# ------------------------------------------------------------------------------
MIDDLEWARE_CLASSES = (
    # Make sure djangosecure.middleware.SecurityMiddleware is listed first
    'django.contrib.sessions.middleware.SessionMiddleware',
    'django.middleware.common.CommonMiddleware',
    'django.middleware.csrf.CsrfViewMiddleware',
    'django.contrib.auth.middleware.AuthenticationMiddleware',
    'django.contrib.messages.middleware.MessageMiddleware',
    'django.middleware.clickjacking.XFrameOptionsMiddleware',
)

# MIGRATIONS CONFIGURATION
# ------------------------------------------------------------------------------
MIGRATION_MODULES = {
    'sites': 'myapp.contrib.sites.migrations'
}

# DEBUG
# ------------------------------------------------------------------------------
# See: https://docs.djangoproject.com/en/dev/ref/settings/#debug
DEBUG = env.bool("DJANGO_DEBUG", False)

# FIXTURE CONFIGURATION
# ------------------------------------------------------------------------------
# See: https://docs.djangoproject.com/en/dev/ref/settings/
# std:setting-FIXTURE_DIRS
FIXTURE_DIRS = (
    str(APPS_DIR.path('fixtures')),
)


# TEMPLATE CONFIGURATION
# ------------------------------------------------------------------------------
# See: https://docs.djangoproject.com/en/dev/ref/settings/#templates
TEMPLATES = [
    {
        # See: https://docs.djangoproject.com/en/dev/ref/settings/#std:setting-TEMPLATES-BACKEND
        'BACKEND': 'django.template.backends.django.DjangoTemplates',
        # See: https://docs.djangoproject.com/en/dev/ref/settings/#template-dirs
        'DIRS': [
            str(APPS_DIR.path('templates')),
        ],
        'OPTIONS': {
            # See: https://docs.djangoproject.com/en/dev/ref/settings/#template-debug
            'debug': DEBUG,
            # See: https://docs.djangoproject.com/en/dev/ref/settings/#template-loaders
            # https://docs.djangoproject.com/en/dev/ref/templates/api/#loader-types
            'loaders': [
                'django.template.loaders.filesystem.Loader',
                'django.template.loaders.app_directories.Loader',
            ],
            # See: https://docs.djangoproject.com/en/dev/ref/settings/#template-context-processors
            'context_processors': [
                'django.template.context_processors.debug',
                'django.template.context_processors.request',
                'django.contrib.auth.context_processors.auth',
                'django.template.context_processors.i18n',
                'django.template.context_processors.media',
                'django.template.context_processors.static',
                'django.template.context_processors.tz',
                'django.contrib.messages.context_processors.messages',
                # Your stuff: custom template context processors go here
            ],
        },
    },
]

# See: http://django-crispy-forms.readthedocs.org/en/latest/install.html#template-packs
CRISPY_TEMPLATE_PACK = 'bootstrap3'

# STATIC FILE CONFIGURATION
# ------------------------------------------------------------------------------
# See: https://docs.djangoproject.com/en/dev/ref/settings/#static-root
# Dit is waar uiteindelijk de staticfiles 'echt heen gaan' op de server (dmv collectstatic).
STATIC_ROOT = str(ROOT_DIR.path('staticfiles'))

# See: https://docs.djangoproject.com/en/dev/ref/settings/#static-url
# This is the URL reference:
STATIC_URL = '/static/'

# See: https://docs.djangoproject.com/en/dev/ref/contrib/staticfiles/#std:setting-STATICFILES_DIRS
# Dit zijn de staticfiles 'als onderdeel van je project development'; collectstatic copieert van
# STATICFILES_DIRS naar STATIC_ROOT !!
STATICFILES_DIRS = (
    str(APPS_DIR.path('static')),
    '/home/usr/myapp/assets/bundles')

# See: https://docs.djangoproject.com/en/dev/ref/contrib/staticfiles/#staticfiles-finders
STATICFILES_FINDERS = (
    'django.contrib.staticfiles.finders.FileSystemFinder',
    'django.contrib.staticfiles.finders.AppDirectoriesFinder',
)

# MEDIA CONFIGURATION
# ------------------------------------------------------------------------------
# See: https://docs.djangoproject.com/en/dev/ref/settings/#media-root
MEDIA_ROOT = str(APPS_DIR('media'))

# See: https://docs.djangoproject.com/en/dev/ref/settings/#media-url
MEDIA_URL = '/media/'

# URL Configuration
# ------------------------------------------------------------------------------
ROOT_URLCONF = 'config.urls'








@owais
Copy link
Collaborator

owais commented Mar 10, 2016

  1. I read in one of the closed issues that Django-webpack-loader solution is aimed at .js and .css ; So not images and other static items. Is that correct y/n? If yes, how should you treat 'other items': the Django way, or the JS way (or choose?). Does it makes sense to just 'build a bridge' for js and css ?

In modern day application, JS and CSS (or even just JS) are the "entry points" of your frontend applications. They will internally load and use other things like images, videos, etc. Only case where Django would need direct access to images or other files is when you want to reference them directly in a django template and not inside JS/CSS. To address this, we have an undocumented template tag. It is undocumented because I'm not sure yet what to name it exactly and how it should work. You can check an example here: https://github.com/owais/django-webpack-loader/blob/b91c62b57c23784c8f2554437909da4cacd2df80/tests/app/templates/home.html#L12-L13
Also, the idea is that the result of your webpack bundle will be collected by django usng collectstatic so all files generated/managed by webpack should be available to django's static tag as well.

@owais
Copy link
Collaborator

owais commented Mar 10, 2016

  1. I read in one of the closed issues that Django-webpack-loader solution is aimed at .js and .css ; So not images and other static items. Is that correct y/n? If yes, how should you treat 'other items': the Django way, or the JS way (or choose?). Does it makes sense to just 'build a bridge' for js and css ?
  2. Following the article it says "If you left webpack running in watch mode, it should automatically pick up the changes and compile a new bundle." I tried a simple Django project to make things more clear for myself, but automatic rebuilding is not happening... It just compiles the same bundle once (no new hash), no error... nothing new.

This is not really a problem specific to webpack-loader. It is directly related to webpack. I'd suggest to check webpack docs and ask this on webpack repo for better help (I'll check your example and try to help shortly)

@owais
Copy link
Collaborator

owais commented Mar 10, 2016

  1. I did manage to have webpack build script run and then have new bundles compiled (when I imported new js libraries), so that seems to work fine; also the bundle-tracker gets new correct hash, so that seems fine. However, I tried to incorporate the js and css into a page, it does not work I think. Part of the problem is I do not know if I test correctly. Your article gives the setup/framework but no real proof of working js or css as far as I can see. In my setup for sure I only see html layout so the css is not coming through from the bundle...

As long as {% webpack_static 'my-image.png' %} produces the correct URL for the bundle, it can be considered to be working.

@owais
Copy link
Collaborator

owais commented Mar 10, 2016

  1. I do not know exactly how the css should work. It seems that it should be included into the main-hash.js bundle and is import into html from that bundle... Is that correct? Could there be a detailed example of how to go about. For example I would like to use bootstrap which consists of bootstrap.js and bootstrap.css; Do I import both from the index.js and then they will be included in the bundle and then using the {% load render_bundle from webpack_loader %} {% render_bundle 'main' %} ? An example with bootstrap and/ or materialcss would be very helpful. Also when I have a custom.css, how do I include it?

Normally webpack will create a single bundle for JS and CSS. JS bundle will then automatically load the CSS into the page. You can use https://github.com/webpack/extract-text-webpack-plugin to split your bundles in JS and CSS.

@owais
Copy link
Collaborator

owais commented Mar 10, 2016

  1. I do not really need the react part; I assume that is not a dealbreaker and using django-webpack-loader still makes sense?!

webpack-loader knows nothing about react or even webpack. It just reads a manifest file and render <script> and/or tags for URLs found in the file. It would work if you made browserify or even rails sprockets generate a valid manifest file.

@owais
Copy link
Collaborator

owais commented Mar 10, 2016

  1. After you made a bundle with webpack and want to go live, do you include the bundle in a 'normal Django static folder'? It seems to be explained somewhere but it is still not really clear to me.

That is the simplest solution for most cases, yes but you are not limited to it.

@owais
Copy link
Collaborator

owais commented Mar 10, 2016

<script src="main-4809d8e09cbc474f2d6a.js"></script></body>

This looks like your STATIC_URL was not picked up because it should have started with /static. What I would suggest to try add publicPath: '/static' to webpack config and see if that works. Google "webpack publicPath"

@musicformellons
Copy link
Author

Thanks for you helpful comments. I added publicPath: '/static' to webpack config and now it indeed starts with /static/main-etc in the index.html However my css is still not appearing in my pages..., so what else is wrong?

So regarding question 4, you mention: "JS bundle will then automatically load the CSS into the page". How are CSS files included in the JS bundle? By importing them in index.js ?
And what/how loads the CSS automatically, as this is not happening in my case?

@owais
Copy link
Collaborator

owais commented Mar 10, 2016

So regarding question 4, you mention: "JS bundle will then automatically load the CSS into the page". How are CSS files included in the JS bundle? By importing them in index.js ?

Yes, by importing them as if they were JS modules. This would be a better question to ask in the webpack community as you'd get better answers there. You should also read this: https://webpack.github.io/docs/stylesheets.html

@musicformellons
Copy link
Author

Ok, so the css is included in the bundle, but how is the bundle loaded into my Django html templates?

@owais
Copy link
Collaborator

owais commented Mar 10, 2016

Ok, so the css is included in the bundle, but how is the bundle loaded into my Django html templates?

https://github.com/owais/django-webpack-loader#templates

@owais owais closed this as completed Mar 10, 2016
@musicformellons
Copy link
Author

Works now. Seems the "import '../star-rating';"; was causing problems somehow... Furthermore I left out the "publicPath: '/static' " to make it work.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants