Changed loading of JavaScript files.
This commit is contained in:
parent
edf997524e
commit
76250c5851
@ -8,6 +8,10 @@ cache:
|
||||
python:
|
||||
- "3.4"
|
||||
- "3.5"
|
||||
env:
|
||||
- TRAVIS_NODE_VERSION="4"
|
||||
before_install:
|
||||
- "nvm install $TRAVIS_NODE_VERSION"
|
||||
install:
|
||||
- "pip install --upgrade setuptools"
|
||||
- "pip install --upgrade --requirement requirements.txt"
|
||||
|
@ -74,6 +74,10 @@ avoid opening new browser windows::
|
||||
|
||||
$ python manage.py runserver
|
||||
|
||||
Use gulp watch in a second command-line interface::
|
||||
|
||||
$ node_modules/.bin/gulp watch
|
||||
|
||||
|
||||
2. Installation on Windows
|
||||
--------------------------
|
||||
|
41
gulpfile.js
41
gulpfile.js
@ -26,6 +26,8 @@ var argv = require('yargs').argv,
|
||||
mainBowerFiles = require('main-bower-files'),
|
||||
path = require('path'),
|
||||
rename = require('gulp-rename'),
|
||||
sourcemaps = require('gulp-sourcemaps'),
|
||||
templateCache = require('gulp-angular-templatecache'),
|
||||
through = require('through2'),
|
||||
uglify = require('gulp-uglify'),
|
||||
vsprintf = require('sprintf-js').vsprintf;
|
||||
@ -38,13 +40,44 @@ var output_directory = path.join('openslides', 'static');
|
||||
* Default tasks to be run before start.
|
||||
*/
|
||||
|
||||
// Catches all JavaScript files from all core apps and concats them to one
|
||||
// file js/openslides.js. In production mode the file is uglified.
|
||||
gulp.task('js', function () {
|
||||
return gulp.src(path.join('openslides', '*', 'static', 'js', '**', '*.js'))
|
||||
.pipe(sourcemaps.init())
|
||||
.pipe(concat('openslides.js'))
|
||||
.pipe(sourcemaps.write())
|
||||
.pipe(gulpif(argv.production, uglify()))
|
||||
.pipe(gulp.dest(path.join(output_directory, 'js')));
|
||||
});
|
||||
|
||||
// Catches all JavaScript files from all bower components and concats them to
|
||||
// one file js/openslides-libs.js. In production mode the file is uglified.
|
||||
gulp.task('js-libs', function () {
|
||||
return gulp.src(mainBowerFiles({
|
||||
filter: /\.js$/
|
||||
}))
|
||||
.pipe(sourcemaps.init())
|
||||
.pipe(concat('openslides-libs.js'))
|
||||
.pipe(sourcemaps.write())
|
||||
.pipe(gulpif(argv.production, uglify()))
|
||||
.pipe(gulp.dest(path.join(output_directory, 'js')));
|
||||
});
|
||||
|
||||
// Catches all template files from all core apps and concats them to one
|
||||
// file js/openslides-templates.js. In production mode the file is uglified.
|
||||
gulp.task('templates', function () {
|
||||
return gulp.src(path.join('openslides', '*', 'static', 'templates', '**', '*.html'))
|
||||
.pipe(templateCache('openslides-templates.js', {
|
||||
module: 'OpenSlidesApp-templates',
|
||||
standalone: true,
|
||||
moduleSystem: 'IIFE',
|
||||
transformUrl: function (url) {
|
||||
var pathList = url.split(path.sep);
|
||||
pathList.shift();
|
||||
return pathList.join(path.sep);
|
||||
},
|
||||
}))
|
||||
.pipe(gulpif(argv.production, uglify()))
|
||||
.pipe(gulp.dest(path.join(output_directory, 'js')));
|
||||
});
|
||||
@ -117,13 +150,19 @@ gulp.task('translations', function () {
|
||||
});
|
||||
|
||||
// Gulp default task. Runs all other tasks before.
|
||||
gulp.task('default', ['js-libs', 'css-libs', 'fonts-libs', 'tinymce', 'angular-chosen-img', 'translations'], function () {});
|
||||
gulp.task('default', ['js', 'js-libs', 'templates', 'css-libs', 'fonts-libs', 'tinymce', 'angular-chosen-img', 'translations'], function () {});
|
||||
|
||||
|
||||
/**
|
||||
* Extra tasks that have to be called manually. Useful for development.
|
||||
*/
|
||||
|
||||
// Watches changes in JavaScript and templates.
|
||||
gulp.task('watch', ['js', 'templates'], function () {
|
||||
gulp.watch(path.join('openslides', '*', 'static', 'js', '**', '*.js'), ['js']);
|
||||
gulp.watch(path.join('openslides', '*', 'static', 'templates', '**', '*.html'), ['templates']);
|
||||
});
|
||||
|
||||
// Extracts translatable strings using angular-gettext and saves them in file
|
||||
// openslides/locale/angular-gettext/template-en.pot.
|
||||
gulp.task('pot', function () {
|
||||
|
@ -6,7 +6,6 @@ class AgendaAppConfig(AppConfig):
|
||||
verbose_name = 'OpenSlides Agenda'
|
||||
angular_site_module = True
|
||||
angular_projector_module = True
|
||||
js_files = ['js/agenda/base.js', 'js/agenda/site.js', 'js/agenda/projector.js']
|
||||
|
||||
def ready(self):
|
||||
# Load projector elements.
|
||||
|
@ -6,7 +6,6 @@ class AssignmentsAppConfig(AppConfig):
|
||||
verbose_name = 'OpenSlides Assignments'
|
||||
angular_site_module = True
|
||||
angular_projector_module = True
|
||||
js_files = ['js/assignments/base.js', 'js/assignments/site.js', 'js/assignments/projector.js']
|
||||
|
||||
def ready(self):
|
||||
# Load projector elements.
|
||||
|
@ -6,7 +6,6 @@ class CoreAppConfig(AppConfig):
|
||||
verbose_name = 'OpenSlides Core'
|
||||
angular_site_module = True
|
||||
angular_projector_module = True
|
||||
js_files = ['js/core/base.js', 'js/core/site.js', 'js/core/projector.js']
|
||||
|
||||
def ready(self):
|
||||
# Load projector elements.
|
||||
|
@ -10,7 +10,8 @@ angular.module('OpenSlidesApp.core', [
|
||||
'ngSanitize', // TODO: only use this in functions that need it.
|
||||
'ui.bootstrap',
|
||||
'ui.tree',
|
||||
'pdf'
|
||||
'pdf',
|
||||
'OpenSlidesApp-templates',
|
||||
])
|
||||
|
||||
.config([
|
||||
|
@ -869,7 +869,7 @@ angular.module('OpenSlidesApp.core.site', [
|
||||
return {
|
||||
restrict: 'E',
|
||||
scope: true,
|
||||
templateUrl: '/static/templates/config-form-field.html',
|
||||
templateUrl: 'static/templates/config-form-field.html',
|
||||
link: function ($scope, iElement, iAttrs, controller, transcludeFn) {
|
||||
var field = $parse(iAttrs.field)($scope);
|
||||
var config = Config.get(field.key);
|
||||
|
@ -10,6 +10,8 @@
|
||||
<link rel="stylesheet" href="static/css/app.css">
|
||||
<link rel="icon" href="/static/img/favicon.png">
|
||||
<script src="static/js/openslides-libs.js"></script>
|
||||
<script src="static/js/openslides.js"></script>
|
||||
<script src="static/js/openslides-templates.js"></script>
|
||||
|
||||
<div id="wrapper" ng-cloak>
|
||||
|
||||
@ -199,5 +201,4 @@
|
||||
|
||||
</div><!--end wrapper-->
|
||||
|
||||
|
||||
<script src="/angular_js/site/"></script>
|
||||
<script src="/webclient/site/"></script>
|
||||
|
@ -9,6 +9,8 @@
|
||||
<link rel="stylesheet" href="static/css/projector.css">
|
||||
<link rel="icon" href="/static/img/favicon.png">
|
||||
<script src="static/js/openslides-libs.js"></script>
|
||||
<script src="static/js/openslides.js"></script>
|
||||
<script src="static/js/openslides-templates.js"></script>
|
||||
|
||||
<div ng-controller="ProjectorContainerCtrl" class="pContainer">
|
||||
<div>
|
||||
@ -42,4 +44,4 @@
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<script src="/angular_js/projector/"></script>
|
||||
<script src="/webclient/projector/"></script>
|
||||
|
@ -8,6 +8,8 @@
|
||||
<link rel="stylesheet" href="static/css/projector.css">
|
||||
<link rel="icon" href="/static/img/favicon.png">
|
||||
<script src="static/js/openslides-libs.js"></script>
|
||||
<script src="static/js/openslides.js"></script>
|
||||
<script src="static/js/openslides-templates.js"></script>
|
||||
|
||||
<style type="text/css">
|
||||
#header, #footer {
|
||||
@ -55,4 +57,5 @@
|
||||
{{ config('general_event_location') }}
|
||||
</span>
|
||||
</div>
|
||||
<script src="/angular_js/projector/"></script>
|
||||
|
||||
<script src="/webclient/projector/"></script>
|
||||
|
@ -23,9 +23,9 @@ urlpatterns = [
|
||||
views.MediaEncoder.as_view(),
|
||||
name="core_mediaencoding"),
|
||||
|
||||
url(r'^angular_js/(?P<openslides_app>site|projector)/$',
|
||||
views.AppsJsView.as_view(),
|
||||
name='core_apps_js'),
|
||||
url(r'^webclient/(?P<realm>site|projector)/$',
|
||||
views.WebclientJavaScriptView.as_view(),
|
||||
name='core_webclient_javascript'),
|
||||
|
||||
# View for the projectors are handled by angular.
|
||||
url(r'^projector.*$', views.ProjectorView.as_view()),
|
||||
|
@ -5,6 +5,7 @@ import re
|
||||
import uuid
|
||||
from collections import OrderedDict
|
||||
from operator import attrgetter
|
||||
from textwrap import dedent
|
||||
from urllib.parse import unquote
|
||||
|
||||
from django.apps import apps
|
||||
@ -92,72 +93,81 @@ class RealProjectorView(utils_views.View):
|
||||
return HttpResponse(content)
|
||||
|
||||
|
||||
class AppsJsView(utils_views.View):
|
||||
class WebclientJavaScriptView(utils_views.View):
|
||||
"""
|
||||
Returns javascript code to be called in the angular app.
|
||||
|
||||
The javascript code loads all js-files defined by the installed (django)
|
||||
apps and creates the angular modules for each angular app.
|
||||
This view returns JavaScript code for the main entry point in the
|
||||
AngularJS app for the requested realm (site or projector). Also code
|
||||
for plugins is appended. The result is not uglified.
|
||||
"""
|
||||
def get(self, *args, **kwargs):
|
||||
angular_modules = []
|
||||
js_files = []
|
||||
realm = kwargs.get('realm') # Result is 'site' or 'projector'
|
||||
for app_config in apps.get_app_configs():
|
||||
# Add the angular app, if the module has one.
|
||||
if getattr(app_config,
|
||||
'angular_{}_module'.format(kwargs.get('openslides_app')),
|
||||
False):
|
||||
angular_modules.append('OpenSlidesApp.{app_name}.{app}'.format(
|
||||
app=kwargs.get('openslides_app'),
|
||||
app_name=app_config.label))
|
||||
# Add the angular app if the module has one.
|
||||
if getattr(app_config, 'angular_{}_module'.format(realm), False):
|
||||
angular_modules.append('OpenSlidesApp.{app_name}.{realm}'.format(
|
||||
app_name=app_config.label,
|
||||
realm=realm))
|
||||
|
||||
# Add all js files that the module needs
|
||||
try:
|
||||
app_js_files = app_config.js_files
|
||||
except AttributeError:
|
||||
# The app needs no js-files
|
||||
pass
|
||||
else:
|
||||
js_files += [
|
||||
'{static}{path}'.format(
|
||||
static=settings.STATIC_URL,
|
||||
path=path)
|
||||
for path in app_js_files]
|
||||
# Use javascript loadScript function from
|
||||
# Add all JavaScript files that the module needs. Our core apps
|
||||
# are delivered by an extra file js/openslides.js which can be
|
||||
# created via gulp.
|
||||
core_apps = (
|
||||
'openslides.core',
|
||||
'openslides.agenda',
|
||||
'openslides.motions',
|
||||
'openslides.assignments',
|
||||
'openslides.users',
|
||||
'openslides.mediafiles',
|
||||
)
|
||||
if app_config.name not in core_apps:
|
||||
try:
|
||||
app_js_files = app_config.js_files
|
||||
except AttributeError:
|
||||
# The app needs no JavaScript files.
|
||||
pass
|
||||
else:
|
||||
js_files.extend(app_js_files)
|
||||
|
||||
# Use JavaScript loadScript function from
|
||||
# http://balpha.de/2011/10/jquery-script-insertion-and-its-consequences-for-debugging/
|
||||
return HttpResponse(
|
||||
# jQuery is required.
|
||||
content = dedent(
|
||||
"""
|
||||
var loadScript = function (path) {
|
||||
var result = $.Deferred(),
|
||||
script = document.createElement("script");
|
||||
script.async = "async";
|
||||
script.type = "text/javascript";
|
||||
script.src = path;
|
||||
script.onload = script.onreadystatechange = function(_, isAbort) {
|
||||
if (!script.readyState || /loaded|complete/.test(script.readyState)) {
|
||||
if (isAbort)
|
||||
result.reject();
|
||||
else
|
||||
result.resolve();
|
||||
}
|
||||
(function () {
|
||||
var loadScript = function (path) {
|
||||
var result = $.Deferred(),
|
||||
script = document.createElement("script");
|
||||
script.async = "async";
|
||||
script.type = "text/javascript";
|
||||
script.src = path;
|
||||
script.onload = script.onreadystatechange = function(_, isAbort) {
|
||||
if (!script.readyState || /loaded|complete/.test(script.readyState)) {
|
||||
if (isAbort)
|
||||
result.reject();
|
||||
else
|
||||
result.resolve();
|
||||
}
|
||||
};
|
||||
script.onerror = function () { result.reject(); };
|
||||
$("head")[0].appendChild(script);
|
||||
return result.promise();
|
||||
};
|
||||
script.onerror = function () { result.reject(); };
|
||||
$("head")[0].appendChild(script);
|
||||
return result.promise();
|
||||
};
|
||||
""" +
|
||||
"""
|
||||
angular.module('OpenSlidesApp.{app}', {angular_modules});
|
||||
var deferres = [];
|
||||
{js_files}.forEach( function(js_file) {{ deferres.push(loadScript(js_file)); }} );
|
||||
$.when.apply(this,deferres).done(function() {{
|
||||
angular.bootstrap(document,['OpenSlidesApp.{app}']);
|
||||
}} );
|
||||
angular.module('OpenSlidesApp.{realm}', {angular_modules});
|
||||
var deferres = [];
|
||||
{js_files}.forEach( function(js_file) {{ deferres.push(loadScript(js_file)); }} );
|
||||
$.when.apply(this,deferres).done( function() {{
|
||||
angular.bootstrap(document,['OpenSlidesApp.{realm}']);
|
||||
}} );
|
||||
""".format(realm=realm, angular_modules=angular_modules, js_files=js_files) +
|
||||
"""
|
||||
.format(
|
||||
app=kwargs.get('openslides_app'),
|
||||
angular_modules=angular_modules,
|
||||
js_files=js_files))
|
||||
}());
|
||||
""")
|
||||
|
||||
return HttpResponse(content, content_type='application/javascript')
|
||||
|
||||
|
||||
# Viewsets for the REST API
|
||||
|
@ -6,7 +6,6 @@ class MediafilesAppConfig(AppConfig):
|
||||
verbose_name = 'OpenSlides Mediafiles'
|
||||
angular_site_module = True
|
||||
angular_projector_module = True
|
||||
js_files = ['js/mediafiles/base.js', 'js/mediafiles/site.js', 'js/mediafiles/projector.js']
|
||||
|
||||
def ready(self):
|
||||
# Load projector elements.
|
||||
|
@ -7,8 +7,6 @@ class MotionsAppConfig(AppConfig):
|
||||
verbose_name = 'OpenSlides Motion'
|
||||
angular_site_module = True
|
||||
angular_projector_module = True
|
||||
js_files = ['js/motions/base.js', 'js/motions/site.js', 'js/motions/projector.js',
|
||||
'js/motions/linenumbering.js', 'js/motions/diff.js', 'js/motions/motion-services.js']
|
||||
|
||||
def ready(self):
|
||||
# Load projector elements.
|
||||
|
@ -6,7 +6,6 @@ class UsersAppConfig(AppConfig):
|
||||
verbose_name = 'OpenSlides Users'
|
||||
angular_site_module = True
|
||||
angular_projector_module = True
|
||||
js_files = ['js/users/base.js', 'js/users/site.js', 'js/users/projector.js']
|
||||
|
||||
def ready(self):
|
||||
# Load projector elements.
|
||||
|
@ -10,17 +10,19 @@
|
||||
"es6-promise": "~3.0.2",
|
||||
"gulp": "~3.9.0",
|
||||
"gulp-angular-gettext": "~2.1.0",
|
||||
"gulp-angular-templatecache": "^2.0.0",
|
||||
"gulp-concat": "~2.6.0",
|
||||
"gulp-cssnano": "~2.1.0",
|
||||
"gulp-if": "~2.0.0",
|
||||
"gulp-jshint": "~2.0.0",
|
||||
"gulp-rename": "~1.2.2",
|
||||
"gulp-sourcemaps": "~1.6.0",
|
||||
"gulp-uglify": "~1.5.2",
|
||||
"jasmine": "~2.4.1",
|
||||
"jshint": "~2.9.2",
|
||||
"karma": "~1.1.0",
|
||||
"karma-jasmine": "~1.0.2",
|
||||
"karma-chrome-launcher": "~1.0.1",
|
||||
"karma-jasmine": "~1.0.2",
|
||||
"main-bower-files": "~2.11.1",
|
||||
"po2json": "~0.4.1",
|
||||
"sprintf-js": "~1.0.3",
|
||||
|
Loading…
Reference in New Issue
Block a user