🔥 Cleanups
- Remove unused files - Remove usage of lodash, query-string and momentjs - Don't bundle svg and eot fonts from fontawesome
This commit is contained in:
1 parent
a94bbed03b
commit
77d7d0af99
22 files changed
+204
-976
No files matched your search
@@ -1,107 +0,0 @@
|
||||
'use strict';
|
||||
|
||||
var gulp = require('gulp');
|
||||
var $ = require('gulp-load-plugins')();
|
||||
var del = require('del');
|
||||
var browserSync = require('browser-sync').create();
|
||||
var reload = browserSync.reload;
|
||||
|
||||
gulp.task('styles', function () {
|
||||
return gulp.src('app/styles/main.scss')
|
||||
.pipe($.sass({
|
||||
includePaths: ['.'],
|
||||
sourceComments: 'map'
|
||||
}).on('error', $.sass.logError))
|
||||
|
||||
.pipe($.autoprefixer('last 1 version'))
|
||||
.pipe(gulp.dest('dist/styles'))
|
||||
.pipe(browserSync.stream());
|
||||
});
|
||||
|
||||
gulp.task('scripts', function () {
|
||||
return gulp.src('app/scripts/**/*.js')
|
||||
.pipe($.jshint())
|
||||
.pipe($.jshint.reporter(require('jshint-stylish')))
|
||||
.pipe(gulp.dest('dist/scripts'))
|
||||
});
|
||||
gulp.task('vendorscripts', function() {
|
||||
var vendorScripts = [
|
||||
'node_modules/jquery/dist/jquery.min.js',
|
||||
'node_modules/underscore/underscore-min.js',
|
||||
'node_modules/nunjucks/browser/nunjucks-slim.min.js',
|
||||
'node_modules/moment/min/moment.min.js',
|
||||
'node_modules/moment/locale/nb.js',
|
||||
'node_modules/bootstrap-sass/assets/javascripts/bootstrap/alert.js',
|
||||
'node_modules/bootstrap-sass/assets/javascripts/bootstrap/dropdown.js',
|
||||
'node_modules/bootstrap-sass/assets/javascripts/bootstrap/collapse.js',
|
||||
'node_modules/pnotify/dist/pnotify.js',
|
||||
'node_modules/query-string/query-string.js'
|
||||
];
|
||||
return gulp.src(vendorScripts)
|
||||
.pipe($.concat('vendor.js'))
|
||||
.pipe(gulp.dest('dist/scripts'));
|
||||
});
|
||||
|
||||
gulp.task('images', function () {
|
||||
return gulp.src('app/images/**/*')
|
||||
.pipe($.imagemin({
|
||||
optimizationLevel: 3,
|
||||
progressive: true,
|
||||
interlaced: true
|
||||
}))
|
||||
.pipe(gulp.dest('dist/images'))
|
||||
});
|
||||
|
||||
gulp.task('fonts', function () {
|
||||
return gulp.src(['node_modules/bootstrap-sass/assets/fonts/**/*'])
|
||||
.pipe($.filter('**/*.{eot,svg,ttf,woff,woff2}'))
|
||||
.pipe($.flatten())
|
||||
.pipe(gulp.dest('dist/fonts'))
|
||||
});
|
||||
gulp.task('templates', function () {
|
||||
return gulp.src('app/templates/*.html')
|
||||
.pipe($.nunjucks())
|
||||
.pipe($.concat('templates.js'))
|
||||
.pipe(gulp.dest('dist/scripts'))
|
||||
});
|
||||
|
||||
gulp.task('extras', function () {
|
||||
return gulp.src(['app/*.*', '!app/*.html', '!app/templates/*.html', '!app/styles/*.scss'], { dot: true })
|
||||
.pipe(gulp.dest('dist'));
|
||||
});
|
||||
|
||||
gulp.task('clean', del.bind(null, ['dist']));
|
||||
|
||||
gulp.task('build', ['styles', 'scripts', 'vendorscripts', 'templates', 'images', 'fonts', 'extras'],
|
||||
function() {
|
||||
return gulp.src('dist/**/*').pipe($.size({title: 'build', gzip: true}));
|
||||
}
|
||||
);
|
||||
|
||||
gulp.task('default', ['clean'], function () {
|
||||
gulp.start('build');
|
||||
});
|
||||
|
||||
gulp.task('serve', ['styles', 'scripts'], function () {
|
||||
require('opn')('http://localhost:3000');
|
||||
});
|
||||
|
||||
|
||||
gulp.task('watch', ['serve'], function () {
|
||||
browserSync.init({
|
||||
proxy: 'localhost:8000'
|
||||
});
|
||||
|
||||
// watch for changes
|
||||
gulp.watch([
|
||||
'../../templates/**/*.html',
|
||||
'app/templates/*.html',
|
||||
'dist/scripts/**/*.js',
|
||||
'dist/images/**/*'
|
||||
]).on('change', reload);
|
||||
|
||||
gulp.watch('app/styles/**/*.scss', ['styles']);
|
||||
gulp.watch('app/scripts/**/*.js', ['scripts']);
|
||||
gulp.watch('app/images/**/*', ['images']);
|
||||
gulp.watch('app/templates/**/*.html', ['templates']);
|
||||
});
|
||||
+4
-27
@@ -3357,7 +3357,8 @@
|
||||
"decode-uri-component": {
|
||||
"version": "0.2.0",
|
||||
"resolved": "https://registry.npmjs.org/decode-uri-component/-/decode-uri-component-0.2.0.tgz",
|
||||
"integrity": "sha1-6zkTMzRYd1y4TNGh+uBiEGu4dUU="
|
||||
"integrity": "sha1-6zkTMzRYd1y4TNGh+uBiEGu4dUU=",
|
||||
"dev": true
|
||||
},
|
||||
"deep-equal": {
|
||||
"version": "1.1.1",
|
||||
@@ -7289,7 +7290,8 @@
|
||||
"lodash": {
|
||||
"version": "4.17.15",
|
||||
"resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.15.tgz",
|
||||
"integrity": "sha512-8xOcRHvCjnocdS5cpwXQXVzmmh5e5+saE2QGoeQmbKmRS6J3VQppPOIt0MnmE+4xlZoumy0GPG0D0MVIQbNA1A=="
|
||||
"integrity": "sha512-8xOcRHvCjnocdS5cpwXQXVzmmh5e5+saE2QGoeQmbKmRS6J3VQppPOIt0MnmE+4xlZoumy0GPG0D0MVIQbNA1A==",
|
||||
"dev": true
|
||||
},
|
||||
"lodash.isfinite": {
|
||||
"version": "3.3.2",
|
||||
@@ -7684,11 +7686,6 @@
|
||||
}
|
||||
}
|
||||
},
|
||||
"moment": {
|
||||
"version": "2.24.0",
|
||||
"resolved": "https://registry.npmjs.org/moment/-/moment-2.24.0.tgz",
|
||||
"integrity": "sha512-bV7f+6l2QigeBBZSM/6yTNq4P2fNpSWj/0e7jQcy87A8e7o2nAfP/34/2ky5Vw4B9S446EtIhodAzkFCcR4dQg=="
|
||||
},
|
||||
"move-concurrently": {
|
||||
"version": "1.0.1",
|
||||
"resolved": "https://registry.npmjs.org/move-concurrently/-/move-concurrently-1.0.1.tgz",
|
||||
@@ -9603,16 +9600,6 @@
|
||||
"resolved": "https://registry.npmjs.org/qs/-/qs-6.9.1.tgz",
|
||||
"integrity": "sha512-Cxm7/SS/y/Z3MHWSxXb8lIFqgqBowP5JMlTUFyJN88y0SGQhVmZnqFK/PeuMX9LzUyWsqqhNxIyg0jlzq946yA=="
|
||||
},
|
||||
"query-string": {
|
||||
"version": "6.9.0",
|
||||
"resolved": "https://registry.npmjs.org/query-string/-/query-string-6.9.0.tgz",
|
||||
"integrity": "sha512-KG4bhCFYapExLsUHrFt+kQVEegF2agm4cpF/VNc6pZVthIfCc/GK8t8VyNIE3nyXG9DK3Tf2EGkxjR6/uRdYsA==",
|
||||
"requires": {
|
||||
"decode-uri-component": "^0.2.0",
|
||||
"split-on-first": "^1.0.0",
|
||||
"strict-uri-encode": "^2.0.0"
|
||||
}
|
||||
},
|
||||
"querystring": {
|
||||
"version": "0.2.0",
|
||||
"resolved": "https://registry.npmjs.org/querystring/-/querystring-0.2.0.tgz",
|
||||
@@ -11066,11 +11053,6 @@
|
||||
}
|
||||
}
|
||||
},
|
||||
"split-on-first": {
|
||||
"version": "1.1.0",
|
||||
"resolved": "https://registry.npmjs.org/split-on-first/-/split-on-first-1.1.0.tgz",
|
||||
"integrity": "sha512-43ZssAJaMusuKWL8sKUBQXHWOpq8d6CfN/u1p4gUzfJkM05C8rxTmYrkIPTXapZpORA6LkkzcUulJ8FqA7Uudw=="
|
||||
},
|
||||
"split-string": {
|
||||
"version": "3.1.0",
|
||||
"resolved": "https://registry.npmjs.org/split-string/-/split-string-3.1.0.tgz",
|
||||
@@ -11214,11 +11196,6 @@
|
||||
"limiter": "^1.0.5"
|
||||
}
|
||||
},
|
||||
"strict-uri-encode": {
|
||||
"version": "2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/strict-uri-encode/-/strict-uri-encode-2.0.0.tgz",
|
||||
"integrity": "sha1-ucczDHBChi9rFC3CdLvMWGbONUY="
|
||||
},
|
||||
"string-width": {
|
||||
"version": "1.0.2",
|
||||
"resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz",
|
||||
|
||||
@@ -23,12 +23,9 @@
|
||||
"graphql-anywhere": "^4.2.6",
|
||||
"graphql-tag": "^2.10.1",
|
||||
"jquery": "^3.4.1",
|
||||
"lodash": "^4.17.15",
|
||||
"moment": "^2.24.0",
|
||||
"pnotify": "^4.0.0",
|
||||
"popper.js": "^1.16.0",
|
||||
"qs": "^6.9.1",
|
||||
"query-string": "^6.9.0",
|
||||
"react": "^16.12.0",
|
||||
"react-dom": "^16.12.0"
|
||||
},
|
||||
|
||||
@@ -1,112 +0,0 @@
|
||||
/*
|
||||
Author : Hunter Perrin
|
||||
Version : 3.0.0
|
||||
Link : http://sciactive.com/pnotify/
|
||||
*/
|
||||
/* -- Notice */
|
||||
.ui-pnotify {
|
||||
top: 36px;
|
||||
right: 36px;
|
||||
position: absolute;
|
||||
height: auto;
|
||||
z-index: 2;
|
||||
}
|
||||
body > .ui-pnotify {
|
||||
/* Notices in the body context should be fixed to the viewport. */
|
||||
position: fixed;
|
||||
/* Ensures notices are above everything */
|
||||
z-index: 100040;
|
||||
}
|
||||
.ui-pnotify-modal-overlay {
|
||||
background-color: rgba(0, 0, 0, .4);
|
||||
top: 0;
|
||||
left: 0;
|
||||
position: absolute;
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
z-index: 1;
|
||||
}
|
||||
body > .ui-pnotify-modal-overlay {
|
||||
position: fixed;
|
||||
z-index: 100039;
|
||||
}
|
||||
.ui-pnotify.ui-pnotify-in {
|
||||
display: block !important;
|
||||
}
|
||||
.ui-pnotify.ui-pnotify-move {
|
||||
transition: left .5s ease, top .5s ease, right .5s ease, bottom .5s ease;
|
||||
}
|
||||
.ui-pnotify.ui-pnotify-fade-slow {
|
||||
transition: opacity .6s linear;
|
||||
opacity: 0;
|
||||
}
|
||||
.ui-pnotify.ui-pnotify-fade-slow.ui-pnotify.ui-pnotify-move {
|
||||
transition: opacity .6s linear, left .5s ease, top .5s ease, right .5s ease, bottom .5s ease;
|
||||
}
|
||||
.ui-pnotify.ui-pnotify-fade-normal {
|
||||
transition: opacity .4s linear;
|
||||
opacity: 0;
|
||||
}
|
||||
.ui-pnotify.ui-pnotify-fade-normal.ui-pnotify.ui-pnotify-move {
|
||||
transition: opacity .4s linear, left .5s ease, top .5s ease, right .5s ease, bottom .5s ease;
|
||||
}
|
||||
.ui-pnotify.ui-pnotify-fade-fast {
|
||||
transition: opacity .2s linear;
|
||||
opacity: 0;
|
||||
}
|
||||
.ui-pnotify.ui-pnotify-fade-fast.ui-pnotify.ui-pnotify-move {
|
||||
transition: opacity .2s linear, left .5s ease, top .5s ease, right .5s ease, bottom .5s ease;
|
||||
}
|
||||
.ui-pnotify.ui-pnotify-fade-in {
|
||||
opacity: 1;
|
||||
}
|
||||
.ui-pnotify .ui-pnotify-shadow {
|
||||
-webkit-box-shadow: 0px 6px 28px 0px rgba(0,0,0,0.1);
|
||||
-moz-box-shadow: 0px 6px 28px 0px rgba(0,0,0,0.1);
|
||||
box-shadow: 0px 6px 28px 0px rgba(0,0,0,0.1);
|
||||
}
|
||||
.ui-pnotify-container {
|
||||
background-position: 0 0;
|
||||
padding: .8em;
|
||||
height: 100%;
|
||||
margin: 0;
|
||||
}
|
||||
.ui-pnotify-container:after {
|
||||
content: " "; /* Older browser do not support empty content */
|
||||
visibility: hidden;
|
||||
display: block;
|
||||
height: 0;
|
||||
clear: both;
|
||||
}
|
||||
.ui-pnotify-container.ui-pnotify-sharp {
|
||||
-webkit-border-radius: 0;
|
||||
-moz-border-radius: 0;
|
||||
border-radius: 0;
|
||||
}
|
||||
.ui-pnotify-title {
|
||||
display: block;
|
||||
margin-bottom: .4em;
|
||||
margin-top: 0;
|
||||
}
|
||||
.ui-pnotify-text {
|
||||
display: block;
|
||||
}
|
||||
.ui-pnotify-icon, .ui-pnotify-icon span {
|
||||
display: block;
|
||||
float: left;
|
||||
margin-right: .2em;
|
||||
}
|
||||
/* Alternate stack initial positioning. */
|
||||
.ui-pnotify.stack-topleft, .ui-pnotify.stack-bottomleft {
|
||||
left: 25px;
|
||||
right: auto;
|
||||
}
|
||||
.ui-pnotify.stack-bottomright, .ui-pnotify.stack-bottomleft {
|
||||
bottom: 25px;
|
||||
top: auto;
|
||||
}
|
||||
.ui-pnotify.stack-modal {
|
||||
left: 50%;
|
||||
right: auto;
|
||||
margin-left: -150px;
|
||||
}
|
||||
@@ -1,10 +1,10 @@
|
||||
import React from 'react';
|
||||
import { groupBy, sortBy } from 'lodash';
|
||||
import { useQuery } from '@apollo/react-hooks';
|
||||
|
||||
import { GET_ALIASES, GET_DOMAINS } from '../queries';
|
||||
import AliasList from './AliasList';
|
||||
import AliasListCreate from './AliasListCreate';
|
||||
import { groupBy } from '../utils';
|
||||
|
||||
const MainArea = ({ query, selectedOrgUnit, orgUnits }) => {
|
||||
const { data, loading, error } = useQuery(GET_ALIASES);
|
||||
@@ -23,8 +23,8 @@ const MainArea = ({ query, selectedOrgUnit, orgUnits }) => {
|
||||
const domain = domainData.domains[0];
|
||||
|
||||
const lists = groupBy(
|
||||
sortBy(data.aliases, (alias) => alias.source),
|
||||
(alias) => alias.source
|
||||
data.aliases.sort((a, b) => a.source.localeCompare(b.source)),
|
||||
'source'
|
||||
);
|
||||
|
||||
const listPrefixes = selectedOrgUnit && orgUnits.find(({ id }) => id === selectedOrgUnit).prefixesRegex;
|
||||
|
||||
@@ -6,7 +6,6 @@ import React from 'react';
|
||||
import { render } from 'react-dom';
|
||||
|
||||
import './index.scss';
|
||||
import '@fortawesome/fontawesome-free/css/all.css';
|
||||
|
||||
import App from './App';
|
||||
|
||||
|
||||
@@ -1,461 +0,0 @@
|
||||
/* global moment, _, $, queryString, nunjucks, notify */
|
||||
|
||||
import { parseEmails, setQueryString } from './utils';
|
||||
|
||||
const API_URL = {
|
||||
ALIASES: '/api/aliases/',
|
||||
OU_LIST: '/api/orgunits/',
|
||||
ME: '/api/me/',
|
||||
EMAIL_DOMAIN: '/api/emaildomain/'
|
||||
};
|
||||
let csrfToken;
|
||||
|
||||
function filterLists(queryTerm, withMembers) {
|
||||
const lists = $('.fwdlist').not('.new-list');
|
||||
if ($.trim(queryTerm) === '') {
|
||||
$(lists)
|
||||
.find('.alias-row')
|
||||
.removeClass('highlight');
|
||||
$(lists).removeClass('hidden');
|
||||
return;
|
||||
}
|
||||
|
||||
/* Filter lists */
|
||||
const reTerm = new RegExp(queryTerm);
|
||||
lists.each(function() {
|
||||
const listName = $(this).attr('data-list-name');
|
||||
const members = $(this).find('.js-destination');
|
||||
let hits = 0;
|
||||
if (withMembers) {
|
||||
hits = _.filter(members, function(el) {
|
||||
const matches = reTerm.test($(el).text());
|
||||
if (matches) {
|
||||
$(el)
|
||||
.parent()
|
||||
.parent()
|
||||
.addClass('highlight');
|
||||
} else {
|
||||
$(el)
|
||||
.parent()
|
||||
.parent()
|
||||
.removeClass('highlight');
|
||||
}
|
||||
return matches;
|
||||
});
|
||||
} else {
|
||||
$('.alias-row').removeClass('highlight');
|
||||
}
|
||||
|
||||
if (reTerm.test(listName) || (hits.length !== 0 && withMembers)) {
|
||||
$(this).removeClass('hidden');
|
||||
} else {
|
||||
$(this).addClass('hidden');
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
function filterListsByOrgUnit(id, prefix) {
|
||||
if (!prefix) {
|
||||
prefix = $(`.orgunit-list a[data-id="${id}"]`).attr('data-prefix');
|
||||
}
|
||||
// eslint-disable-next-line no-use-before-define
|
||||
setActiveOrgUnit(id);
|
||||
filterLists(prefix);
|
||||
let queryParams = { orgunit: id };
|
||||
if (id === '') {
|
||||
queryParams = null;
|
||||
}
|
||||
setQueryString(queryParams);
|
||||
}
|
||||
|
||||
function updateNumEmails(event) {
|
||||
const el = $(event.target);
|
||||
const emails = parseEmails(el.val());
|
||||
const listName = el.attr('data-list-name');
|
||||
const counter = $(`.fwdlist[data-list-name="${listName}"] .email-counter`);
|
||||
|
||||
if (emails.length > 0) {
|
||||
counter.text(emails.length);
|
||||
} else {
|
||||
counter.text('');
|
||||
}
|
||||
}
|
||||
function createAliases(newAliases, onSuccess, onError) {
|
||||
$.ajax({
|
||||
url: API_URL.ALIASES,
|
||||
type: 'POST',
|
||||
headers: { 'X-CSRFToken': csrfToken },
|
||||
dataType: 'json',
|
||||
contentType: 'application/json; charset=utf-8',
|
||||
data: JSON.stringify(newAliases),
|
||||
success: onSuccess,
|
||||
error: onError
|
||||
});
|
||||
}
|
||||
function setActiveOrgUnit(id) {
|
||||
/* Reset active */
|
||||
$('.orgunit-list li').removeClass('active');
|
||||
|
||||
/* Set current */
|
||||
const orgUnit = $(`.orgunit-list li a[data-id="${id}"]`);
|
||||
orgUnit.parent().toggleClass('active');
|
||||
$('.orgunits-select').val(id); // <select>
|
||||
|
||||
/* Reset search field */
|
||||
$('.js-lists-filter-field').val('');
|
||||
}
|
||||
function setPrefixesRegex(ous) {
|
||||
ous = _.map(ous, function(ou) {
|
||||
const prefixes = _.map(ou.prefixes, function(prefix) {
|
||||
return `^${prefix}-|^${prefix}@`;
|
||||
});
|
||||
ou.prefixes_regex = prefixes.join('|');
|
||||
|
||||
return ou;
|
||||
});
|
||||
|
||||
return ous;
|
||||
}
|
||||
function resetActiveOrgUnit() {
|
||||
$('.orgunit-list li').removeClass('active');
|
||||
$('.orgunit-list li:first-child').toggleClass('active');
|
||||
}
|
||||
|
||||
$(document).ready(function() {
|
||||
csrfToken = $('meta[name=x-csrf-token]').attr('content');
|
||||
const forwardsContainer = $('.forwards-container');
|
||||
nunjucks.configure({ autoescape: true });
|
||||
moment.locale('nb');
|
||||
/* Add filter |datefromnow and |date to nunjucks */
|
||||
const nunjucksEnv = new nunjucks.Environment();
|
||||
|
||||
nunjucksEnv.addFilter('datefromnow', function(str) {
|
||||
return moment(str).fromNow();
|
||||
});
|
||||
|
||||
nunjucksEnv.addFilter('date', function(str, strformat) {
|
||||
return moment(str).format(strformat);
|
||||
});
|
||||
|
||||
/* Lists view (home) */
|
||||
if ($('body.home').length) {
|
||||
$('.js-lists-filter-field').focus();
|
||||
/* Load orgunits */
|
||||
$.getJSON(API_URL.OU_LIST, function(data) {
|
||||
data = setPrefixesRegex(data);
|
||||
|
||||
const ouHtml = nunjucksEnv.render('orgunits.html', { orgunits: data });
|
||||
$('.orgunit-list').append(ouHtml);
|
||||
const ousHtml = nunjucksEnv.render('orgunits_select.html', { orgunits: data });
|
||||
$('.orgunit-select-container').html(ousHtml);
|
||||
|
||||
/* If searching then set q */
|
||||
const qs = queryString.parse(window.location.search);
|
||||
if (qs.q) {
|
||||
resetActiveOrgUnit();
|
||||
$('.js-lists-filter-field').val(qs.q);
|
||||
}
|
||||
if (qs.orgunit) {
|
||||
setActiveOrgUnit(qs.orgunit);
|
||||
}
|
||||
|
||||
/* Load email domain */
|
||||
$.getJSON(API_URL.EMAIL_DOMAIN, function(emailDomain) {
|
||||
emailDomain = emailDomain.domain;
|
||||
|
||||
/* New list */
|
||||
const newListHtml = nunjucksEnv.render('new_list.html', {
|
||||
orgunits: data,
|
||||
api_urls: API_URL,
|
||||
email_domain: emailDomain
|
||||
});
|
||||
$('.new-list').html(newListHtml);
|
||||
|
||||
/* New list: List name (source) */
|
||||
$('.new-list .js-new-list-name').on('keyup', function() {
|
||||
let newListName = $('.new-list .js-new-list-name')
|
||||
.val()
|
||||
.trim();
|
||||
if (newListName === '') {
|
||||
$('.js-new-list-preview').html('Ny liste');
|
||||
return;
|
||||
}
|
||||
const prefix = $('.new-list .prefix-select .active').attr('data-value');
|
||||
const source = `${prefix + newListName}@${emailDomain.name}`;
|
||||
let labelHtml = '<span class="label label-success">Ny</span> ';
|
||||
const existingList = $(`.fwdlist[data-list-name="${source}"]`).length;
|
||||
|
||||
if (existingList) {
|
||||
labelHtml = '<span class="label label-primary">Eksisterende</span> ';
|
||||
}
|
||||
|
||||
newListName = labelHtml + source;
|
||||
$('.js-new-list-preview').html(newListName);
|
||||
});
|
||||
|
||||
/* New list: Select prefix */
|
||||
$('.new-list .prefix-select a').on('click', function() {
|
||||
$('.new-list .prefix-select a')
|
||||
.parent()
|
||||
.removeClass('active');
|
||||
$(this)
|
||||
.parent()
|
||||
.addClass('active');
|
||||
const prefix = $(this)
|
||||
.parent()
|
||||
.attr('data-value');
|
||||
$('.new-list .prefix-btn').html(`${prefix} <span class="caret"></span>`);
|
||||
});
|
||||
|
||||
$('.new-list textarea').on('keyup', updateNumEmails);
|
||||
|
||||
/* New list: Add list with aliases */
|
||||
$('.js-add-list').on('click', function(e) {
|
||||
e.preventDefault();
|
||||
/* Validate */
|
||||
const newListName = $('.new-list .js-new-list-name').val();
|
||||
if (newListName.length === 0) {
|
||||
notify('Ny epostliste', 'Navn på epostliste mangler', 'error');
|
||||
return;
|
||||
}
|
||||
const text = $('.new-list textarea').val();
|
||||
const emails = parseEmails(text);
|
||||
if (emails.length === 0) {
|
||||
notify('Ny epostliste', 'Ingen eposter i epost-feltet...', 'error');
|
||||
return;
|
||||
}
|
||||
// Valid form
|
||||
const prefix = $('.new-list .prefix-select .active').attr('data-value');
|
||||
const source = `${prefix + newListName}@${emailDomain.name}`;
|
||||
|
||||
const newAliases = _.map(emails, function(el) {
|
||||
return {
|
||||
source,
|
||||
destination: el,
|
||||
domain: emailDomain.id
|
||||
};
|
||||
});
|
||||
|
||||
createAliases(
|
||||
newAliases,
|
||||
function(aliases) {
|
||||
$('.new-list textarea').val('');
|
||||
$('.new-list .js-new-list-name').val('');
|
||||
$('.js-new-list-preview').html('Ny liste');
|
||||
$('.new-list .email-counter').html('');
|
||||
const listName = aliases[0].source;
|
||||
const listEl = $(`.fwdlist[data-list-name="${listName}"]`);
|
||||
|
||||
if (listEl.length) {
|
||||
/* Append to existing list */
|
||||
notify('Oppdatert', `Oppdatert: ${listName} er oppdatert`, 'success');
|
||||
const listHtml = nunjucksEnv.render('aliases.html', { aliases });
|
||||
listEl
|
||||
.find('tbody .alias-row')
|
||||
.last()
|
||||
.after(listHtml);
|
||||
return;
|
||||
}
|
||||
|
||||
/* Add new list on top */
|
||||
notify('Lagt til', `Ny liste: ${listName} lagt til`, 'success');
|
||||
const newList = _.groupBy(aliases, function(alias) {
|
||||
return alias.source;
|
||||
});
|
||||
const addedListHtml = nunjucksEnv.render('list.html', { lists: newList });
|
||||
forwardsContainer.prepend(addedListHtml);
|
||||
},
|
||||
function(xhr) {
|
||||
const error = xhr.responseJSON;
|
||||
const msg = error && error[0].non_field_errors ? error[0].non_field_errors[0] : '';
|
||||
notify('Ikke oppdatert', `Kunne ikke legge til nye eposter.\n${msg}`, 'error');
|
||||
}
|
||||
);
|
||||
});
|
||||
|
||||
/* Filter lists by orgunit */
|
||||
$('.orgunit-list a').on('click', function(e) {
|
||||
e.preventDefault();
|
||||
const id = $(this).attr('data-id');
|
||||
const prefix = $(this).attr('data-prefix');
|
||||
filterListsByOrgUnit(id, prefix);
|
||||
});
|
||||
$('.orgunits-select').on('change', function() {
|
||||
const id = $(this).val();
|
||||
const prefix = $(this)
|
||||
.find(':selected')
|
||||
.attr('data-prefix');
|
||||
filterListsByOrgUnit(id, prefix);
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
/* Load forwards from API and put on page */
|
||||
$.getJSON(API_URL.ALIASES, function(data) {
|
||||
let errMsg;
|
||||
if (data && data.length === 0) {
|
||||
errMsg = 'Fant ingen tilhørende lister';
|
||||
notify('Ingen lister.', errMsg, 'info');
|
||||
forwardsContainer.html(errMsg);
|
||||
return;
|
||||
}
|
||||
if (data && 'error' in data) {
|
||||
errMsg = `Klarte ikke hente epostlister fra APIet: ${data.error}`;
|
||||
notify('Oops!', errMsg, 'error');
|
||||
forwardsContainer.html(errMsg);
|
||||
return;
|
||||
}
|
||||
|
||||
let lists = _.sortBy(data, function(alias) {
|
||||
return alias.source;
|
||||
});
|
||||
lists = _.groupBy(lists, function(alias) {
|
||||
return alias.source;
|
||||
});
|
||||
const fwHtml = nunjucksEnv.render('list.html', { lists });
|
||||
|
||||
forwardsContainer.html(fwHtml);
|
||||
|
||||
/* Filter lists by search term from query string */
|
||||
const qs = queryString.parse(window.location.search);
|
||||
if (qs.q) {
|
||||
filterLists(qs.q, true);
|
||||
} else if (qs.orgunit) {
|
||||
filterListsByOrgUnit(qs.orgunit);
|
||||
}
|
||||
});
|
||||
|
||||
/* Mark row red for deletion and show delete button if applicable */
|
||||
forwardsContainer.on('click', '[name=fwd-delete]', function() {
|
||||
$(this)
|
||||
.parent()
|
||||
.parent()
|
||||
.parent()
|
||||
.toggleClass('danger');
|
||||
const tbody = $(this).closest('tbody');
|
||||
const numSelected = tbody.find('[name=fwd-delete]:checked').length;
|
||||
if (numSelected > 0) {
|
||||
tbody.find('.link-del').addClass('visible');
|
||||
} else {
|
||||
tbody.find('.link-del').removeClass('visible');
|
||||
}
|
||||
});
|
||||
|
||||
/* Delete selected aliases */
|
||||
forwardsContainer.on('click', '.js-del-selected', function() {
|
||||
const listName = $(this).attr('data-delete-list-name');
|
||||
const listEl = $(`.fwdlist[data-list-name="${listName}"]`);
|
||||
const checked = listEl.find('[name="fwd-delete"]:checked');
|
||||
|
||||
const deleteThese = _.map(checked, function(el) {
|
||||
return {
|
||||
source: $(el).attr('data-source'),
|
||||
destination: $(el).attr('data-destination'),
|
||||
domain: parseInt($(el).attr('data-domain'), 10)
|
||||
};
|
||||
});
|
||||
function success() {
|
||||
const checkedFormatted = _.map(deleteThese, function(el) {
|
||||
return el.destination;
|
||||
}).join(', ');
|
||||
checked.closest('tr').remove();
|
||||
/* remove list if no more rows */
|
||||
if (listEl.find('.alias-row').length === 0) {
|
||||
listEl.remove();
|
||||
}
|
||||
listEl.find('.link-del').removeClass('visible');
|
||||
notify('Slettet', checkedFormatted, 'success');
|
||||
}
|
||||
function error(res) {
|
||||
notify('Kunne ikke slette', res.detail, 'error');
|
||||
}
|
||||
const data = {
|
||||
type: 'DELETE',
|
||||
headers: { 'X-CSRFToken': csrfToken },
|
||||
url: API_URL.ALIASES,
|
||||
data: JSON.stringify(deleteThese),
|
||||
contentType: 'application/json; charset=utf-8',
|
||||
success,
|
||||
error
|
||||
};
|
||||
$.ajax(data);
|
||||
});
|
||||
|
||||
/* Toggle button for add emails textarea */
|
||||
forwardsContainer.on('click', '.js-toggle-email-textarea', function(e) {
|
||||
e.preventDefault();
|
||||
const row = $(this)
|
||||
.closest('tbody')
|
||||
.find('.textarea-row');
|
||||
row.toggleClass('visible');
|
||||
|
||||
$(this)
|
||||
.closest('tbody')
|
||||
.find('textarea')
|
||||
.focus();
|
||||
});
|
||||
|
||||
/* Add emails to current list */
|
||||
forwardsContainer.on('click', '.js-new-email', function(e) {
|
||||
e.preventDefault();
|
||||
const source = $(this).attr('data-list-name');
|
||||
const textarea = $(`textarea[data-list-name="${source}"]`);
|
||||
const emails = parseEmails(textarea.val());
|
||||
if (emails.length === 0) {
|
||||
notify('Ny epostliste', 'Ingen eposter i epost-feltet...', 'error');
|
||||
return;
|
||||
}
|
||||
const listEl = $(`.fwdlist[data-list-name="${source}"]`);
|
||||
const newAliases = _.map(emails, function(el) {
|
||||
return {
|
||||
source,
|
||||
destination: el,
|
||||
domain: parseInt(listEl.attr('data-domain'), 10)
|
||||
};
|
||||
});
|
||||
|
||||
createAliases(
|
||||
newAliases,
|
||||
function(aliases) {
|
||||
const aliasesFormatted = _.map(aliases, function(el) {
|
||||
return el.destination;
|
||||
}).join(', ');
|
||||
notify(`Oppdatert ${aliases[0].source}`, `La til epostene: ${aliasesFormatted}.`, 'success');
|
||||
textarea.val('');
|
||||
listEl.find('.email-counter').text('');
|
||||
/* Append to existing list */
|
||||
const addedListHtml = nunjucksEnv.render('aliases.html', { aliases });
|
||||
listEl
|
||||
.find('tbody .alias-row')
|
||||
.last()
|
||||
.after(addedListHtml);
|
||||
},
|
||||
function(xhr) {
|
||||
const error = xhr.responseJSON;
|
||||
const msg = error && error[0].non_field_errors ? error[0].non_field_errors[0] : '';
|
||||
notify('Ikke oppdatert', `Kunne ikke legge til nye eposter.\n${msg}`, 'error');
|
||||
}
|
||||
);
|
||||
});
|
||||
|
||||
/* Update num emails for all list textarea's */
|
||||
forwardsContainer.on('keyup', '.js-add-list-textarea, .new-list textarea', updateNumEmails);
|
||||
|
||||
/* Filter by search query */
|
||||
$('.js-lists-filter-field').on('keyup change', function() {
|
||||
const term = $(this).val();
|
||||
filterLists(term, true);
|
||||
resetActiveOrgUnit();
|
||||
let queryParams = { q: term };
|
||||
if (term === '') {
|
||||
queryParams = null;
|
||||
}
|
||||
setQueryString(queryParams);
|
||||
});
|
||||
|
||||
/* New list toggle display button */
|
||||
$('.new-list-btn').on('click', function() {
|
||||
$('.new-list').toggleClass('visible');
|
||||
});
|
||||
}
|
||||
});
|
||||
@@ -1,178 +1,8 @@
|
||||
$icon-font-path: "../fonts/";
|
||||
|
||||
@import "~bootstrap/scss/bootstrap";
|
||||
@import "pnotify.core";
|
||||
|
||||
@import "./animations";
|
||||
@import "./sidebar";
|
||||
|
||||
.login-form {
|
||||
margin: 0 auto;
|
||||
max-width: 300px;
|
||||
float: none;
|
||||
input[type=submit] {
|
||||
float: right;
|
||||
}
|
||||
}
|
||||
|
||||
/* Sticky footer styles */
|
||||
.footer {
|
||||
margin-top: 40px;
|
||||
}
|
||||
|
||||
/* Lists */
|
||||
.del-cell {
|
||||
text-align: right;
|
||||
width: 54px;
|
||||
padding: 2px 0 0 !important;
|
||||
vertical-align: middle;
|
||||
}
|
||||
.del-label {
|
||||
display: block;
|
||||
height: 30px;
|
||||
margin: 0;
|
||||
text-align: center;
|
||||
|
||||
input {
|
||||
margin: 0;
|
||||
position: relative;
|
||||
top: 6px;
|
||||
}
|
||||
}
|
||||
|
||||
.badge-list-total {
|
||||
float: right;
|
||||
position: relative;
|
||||
top: 3px;
|
||||
}
|
||||
|
||||
.new-list-btn {
|
||||
margin-bottom: 1rem;
|
||||
}
|
||||
.new-list {
|
||||
display: none;
|
||||
margin-bottom: 1rem;
|
||||
|
||||
&.visible {
|
||||
display: block;
|
||||
}
|
||||
}
|
||||
.new-list-name {
|
||||
padding-bottom: 5px;
|
||||
}
|
||||
.btn-add-list {
|
||||
margin-top: 1rem;
|
||||
}
|
||||
/* Forward list */
|
||||
.panel-heading {
|
||||
font-weight: bold;
|
||||
font-size: 16px;
|
||||
}
|
||||
.icon-faded {
|
||||
position: relative;
|
||||
top: 1px;
|
||||
margin-right: 4px;
|
||||
color: #ccc;
|
||||
}
|
||||
.table-condensed {
|
||||
margin-bottom: 0;
|
||||
|
||||
> tbody > tr > td {
|
||||
padding: 5px;
|
||||
|
||||
&:first-child {
|
||||
padding-left: 20px;
|
||||
padding-right: 20px;
|
||||
}
|
||||
}
|
||||
|
||||
> tbody > tr.action-row > td {
|
||||
padding: 0;
|
||||
|
||||
&:first-child {
|
||||
padding: 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
.custom-control-label:after, .custom-control-label:before {
|
||||
width: 1.3rem;
|
||||
height: 1.3rem;
|
||||
}
|
||||
.action-row {
|
||||
.link-add {
|
||||
display: block;
|
||||
}
|
||||
.link-del {
|
||||
white-space: nowrap;
|
||||
display: none;
|
||||
|
||||
&.visible {
|
||||
display: block;
|
||||
}
|
||||
}
|
||||
a {
|
||||
padding: 10px;
|
||||
padding-left: 16px;
|
||||
&:hover {
|
||||
background-color: #f5f5f5;
|
||||
}
|
||||
}
|
||||
textarea {
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
}
|
||||
.textarea-row {
|
||||
display: none;
|
||||
td {
|
||||
padding-right: 16px;
|
||||
}
|
||||
&.visible {
|
||||
display: table-row;
|
||||
}
|
||||
.btn-add-list {
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
}
|
||||
.highlight .alias:before {
|
||||
width: 7px;
|
||||
height: 7px;
|
||||
border-radius: 50% 50%;
|
||||
background-color: #00d000;
|
||||
content: '';
|
||||
display: inline-block;
|
||||
position: absolute;
|
||||
left: 20px;
|
||||
margin-top: 7px;
|
||||
}
|
||||
|
||||
.card-header {
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
/* Responsive fixes */
|
||||
@media(max-width: map-get($grid-breakpoints, "sm")){
|
||||
.card-header {
|
||||
font-size: 13px;
|
||||
}
|
||||
.card-header .icon-faded {
|
||||
display: none;
|
||||
}
|
||||
td {
|
||||
font-size: 13px;
|
||||
}
|
||||
.highlight .alias:before {
|
||||
margin-top: 5px;
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
.love {
|
||||
color: #faafba;
|
||||
}
|
||||
.credits {
|
||||
margin-top: 25px;
|
||||
margin-bottom: 25px;
|
||||
text-align: center;
|
||||
color: #666;
|
||||
font-size: 12px;
|
||||
}
|
||||
@import "./styles/animations";
|
||||
@import "./styles/mainarea";
|
||||
@import "./styles/sidebar";
|
||||
@import "./styles/fonts";
|
||||
@import "./styles/login";
|
||||
@import "./styles/footer";
|
||||
File renamed without changes.
@@ -0,0 +1,21 @@
|
||||
$fa-font-path: "../node_modules/@fortawesome/fontawesome-free/webfonts";
|
||||
|
||||
@import "~@fortawesome/fontawesome-free/scss/fontawesome";
|
||||
|
||||
// Skip EOT and SVG fonts, ref:
|
||||
// @import "~@fortawesome/fontawesome-free/scss/solid";
|
||||
@font-face {
|
||||
font-family: 'Font Awesome 5 Free';
|
||||
font-style: normal;
|
||||
font-weight: 900;
|
||||
font-display: $fa-font-display;
|
||||
src: url('#{$fa-font-path}/fa-solid-900.woff2') format('woff2'),
|
||||
url('#{$fa-font-path}/fa-solid-900.woff') format('woff'),
|
||||
url('#{$fa-font-path}/fa-solid-900.ttf') format('truetype'),
|
||||
}
|
||||
|
||||
.fa,
|
||||
.fas {
|
||||
font-family: 'Font Awesome 5 Free';
|
||||
font-weight: 900;
|
||||
}
|
||||
Whitespace-only changes.
@@ -0,0 +1,9 @@
|
||||
.login-form {
|
||||
margin: 0 auto;
|
||||
max-width: 300px;
|
||||
float: none;
|
||||
|
||||
input[type=submit] {
|
||||
float: right;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,143 @@
|
||||
/* Lists */
|
||||
.del-cell {
|
||||
text-align: right;
|
||||
width: 54px;
|
||||
padding: 2px 0 0 !important;
|
||||
vertical-align: middle;
|
||||
}
|
||||
.del-label {
|
||||
display: block;
|
||||
height: 30px;
|
||||
margin: 0;
|
||||
text-align: center;
|
||||
|
||||
input {
|
||||
margin: 0;
|
||||
position: relative;
|
||||
top: 6px;
|
||||
}
|
||||
}
|
||||
.badge-list-total {
|
||||
float: right;
|
||||
position: relative;
|
||||
top: 3px;
|
||||
}
|
||||
|
||||
.new-list-btn {
|
||||
margin-bottom: 1rem;
|
||||
}
|
||||
.new-list {
|
||||
display: none;
|
||||
margin-bottom: 1rem;
|
||||
|
||||
&.visible {
|
||||
display: block;
|
||||
}
|
||||
}
|
||||
.new-list-name {
|
||||
padding-bottom: 5px;
|
||||
}
|
||||
.btn-add-list {
|
||||
margin-top: 1rem;
|
||||
}
|
||||
/* Forward list */
|
||||
.panel-heading {
|
||||
font-weight: bold;
|
||||
font-size: 16px;
|
||||
}
|
||||
.icon-faded {
|
||||
position: relative;
|
||||
top: 1px;
|
||||
margin-right: 4px;
|
||||
color: #ccc;
|
||||
}
|
||||
.table-condensed {
|
||||
margin-bottom: 0;
|
||||
|
||||
> tbody > tr > td {
|
||||
padding: 5px;
|
||||
|
||||
&:first-child {
|
||||
padding-left: 20px;
|
||||
padding-right: 20px;
|
||||
}
|
||||
}
|
||||
|
||||
> tbody > tr.action-row > td {
|
||||
padding: 0;
|
||||
|
||||
&:first-child {
|
||||
padding: 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
.custom-control-label:after, .custom-control-label:before {
|
||||
width: 1.3rem;
|
||||
height: 1.3rem;
|
||||
}
|
||||
.action-row {
|
||||
.link-add {
|
||||
display: block;
|
||||
}
|
||||
.link-del {
|
||||
white-space: nowrap;
|
||||
display: none;
|
||||
|
||||
&.visible {
|
||||
display: block;
|
||||
}
|
||||
}
|
||||
a {
|
||||
padding: 10px;
|
||||
padding-left: 16px;
|
||||
&:hover {
|
||||
background-color: #f5f5f5;
|
||||
}
|
||||
}
|
||||
textarea {
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
}
|
||||
.textarea-row {
|
||||
display: none;
|
||||
td {
|
||||
padding-right: 16px;
|
||||
}
|
||||
&.visible {
|
||||
display: table-row;
|
||||
}
|
||||
.btn-add-list {
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
}
|
||||
|
||||
.card-header {
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
/* Responsive fixes */
|
||||
@media(max-width: map-get($grid-breakpoints, "sm")){
|
||||
.card-header {
|
||||
font-size: 13px;
|
||||
}
|
||||
.card-header .icon-faded {
|
||||
display: none;
|
||||
}
|
||||
td {
|
||||
font-size: 13px;
|
||||
}
|
||||
}
|
||||
|
||||
.footer {
|
||||
margin-top: 40px;
|
||||
}
|
||||
.love {
|
||||
color: #faafba;
|
||||
}
|
||||
.credits {
|
||||
margin-top: 25px;
|
||||
margin-bottom: 25px;
|
||||
text-align: center;
|
||||
color: #666;
|
||||
font-size: 12px;
|
||||
}
|
||||
File renamed without changes.
@@ -1,4 +0,0 @@
|
||||
<div class="alert alert-{{ alertClass }}">
|
||||
<a class="close" data-dismiss="alert">×</a>
|
||||
{% if iconClass %}<span class="fas fa-{{ iconClass }}"></span> {% endif %}{{ msg }}
|
||||
</div>
|
||||
@@ -1,8 +0,0 @@
|
||||
{% for alias in aliases %}
|
||||
<tr class="alias-row">
|
||||
<td class="alias"><span class="js-destination" title="Lagt til {{ alias.created|datefromnow }} ({{ alias.created|date('LLLL') }})">{{ alias.destination }}</span></td>
|
||||
<td class="del-cell">
|
||||
<label class="del-label" for="{{alias.id}}"><input id="{{alias.id}}" type="checkbox" name='fwd-delete' value="{{alias.id}}" data-source="{{alias.source}}" data-destination="{{alias.destination}}" data-domain="{{alias.domain}}"/></label>
|
||||
</td>
|
||||
</tr>
|
||||
{% endfor %}
|
||||
@@ -1,30 +0,0 @@
|
||||
{% for list,aliases in lists %}
|
||||
<div class="fwdlist" data-list-name="{{ list }}" data-domain="{{aliases[0].domain}}">
|
||||
<div class="panel panel-default">
|
||||
<div class="panel-heading"><span class="fas fa-list-alt icon-faded" aria-hidden="true"></span> {{ list }} <span class="badge badge-list-total">{{aliases|length}}</span></div>
|
||||
<table class="table table-condensed">
|
||||
<tbody>
|
||||
<!-- Aliases -->
|
||||
{% include "aliases.html" %}
|
||||
<!-- Actions: Add/Remove -->
|
||||
<tr class="action-row">
|
||||
<td>
|
||||
<a href="#" class="link-add js-toggle-email-textarea"><span class="fas fa-plus" aria-hidden="true"></span> Legg til</a>
|
||||
</td>
|
||||
<td>
|
||||
<a href="#" class="link-del js-del-selected" type="button" data-delete-list-name="{{ list }}"><span class="fas fa-remove" aria-hidden="true"></span> Slett</a>
|
||||
</td>
|
||||
</tr>
|
||||
<tr class="textarea-row">
|
||||
<td colspan="2">
|
||||
<h4>Eposter <span class="badge email-counter"></span></h4>
|
||||
<textarea class="form-control js-add-list-textarea" data-list-name="{{ list }}" placeholder="asdf@studentersamfundet.no, qwerty@studentersamfundet.no f.eks. Klipp og lim så mye du orker" rows="4"></textarea>
|
||||
<button type="button" class="btn btn-primary btn-add-list js-new-email" data-list-name="{{list}}"><span class="fas fa-plus js-new-email" aria-hidden="true"></span> Legg til</button>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
<div class="result-alert"></div>
|
||||
</div>
|
||||
</div>
|
||||
{% endfor %}
|
||||
@@ -1,23 +0,0 @@
|
||||
<div class="panel panel-default">
|
||||
<div class="panel-heading"><span class="fas fa-list-alt icon-faded" aria-hidden="true"></span> <span class="js-new-list-preview">Ny liste</span></div>
|
||||
<div class="panel-body">
|
||||
<div class="input-group">
|
||||
<span class="input-group-btn">
|
||||
<button type="button" class="btn btn-default prefix-btn dropdown-toggle" data-toggle="dropdown" aria-expanded="false">{{ orgunits[0].prefixes[0] }}- <span class="caret"></span></button>
|
||||
<ul class="dropdown-menu prefix-select">
|
||||
{% set first = true %}
|
||||
{% for ou in orgunits %}
|
||||
{% for prefix in ou.prefixes %}
|
||||
<li{% if first %} class="active"{% set first = false %}{% endif %} data-value="{{ prefix }}-"><a href="#">{{prefix}}-</a></li>
|
||||
{% endfor %}
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</span>
|
||||
<input type="text" class="form-control js-new-list-name">
|
||||
<span class="input-group-addon">@{{email_domain.name}}</span>
|
||||
</div>
|
||||
<h4>Eposter <span class="badge email-counter"></span></h4>
|
||||
<textarea class="form-control" data-list-name='newlist@example.com' placeholder="asdf@studentersamfundet.no, qwerty@studentersamfundet.no f.eks. Klipp og lim så mye du orker" rows="4"></textarea>
|
||||
<button type="button" class="btn btn-primary btn-add-list js-add-list"><span class="fas fa-plus js-add-list" aria-hidden="true"></span> Opprett liste</button>
|
||||
</div>
|
||||
</div>
|
||||
@@ -1,4 +0,0 @@
|
||||
<li class="active"><a href="/lists/" data-id="" data-prefix=".+">Alle</a></li>
|
||||
{% for ou in orgunits %}
|
||||
<li><a href="/lists/?orgunit={{ ou.id }}" data-prefix="{{ ou.prefixes_regex }}" data-id="{{ ou.id }}">{{ ou.name }}</a></li>
|
||||
{% endfor %}
|
||||
@@ -1,6 +0,0 @@
|
||||
<select class="orgunits-select form-control">
|
||||
<option value="" data-prefix=".+">Alle</option>
|
||||
{% for ou in orgunits %}
|
||||
<option value="{{ ou.id }}" data-prefix="{{ou.prefixes_regex }}">{{ ou.name }}</option>
|
||||
{% endfor %}
|
||||
</select>
|
||||
@@ -1,6 +1,4 @@
|
||||
import PNotify from 'pnotify/dist/es/PNotify';
|
||||
import PNotifyButtons from 'pnotify/dist/es/PNotifyButtons';
|
||||
import * as queryString from 'query-string';
|
||||
|
||||
export function parseEmails(text) {
|
||||
if (text === undefined || text === '') {
|
||||
@@ -24,11 +22,17 @@ export function parseEmails(text) {
|
||||
return [...new Set(emails)];
|
||||
}
|
||||
|
||||
export const qsStringify = (obj) => {
|
||||
const str = [];
|
||||
for (const prop in obj)
|
||||
if (obj.hasOwnProperty(prop)) {
|
||||
str.push(`${encodeURIComponent(prop)}=${encodeURIComponent(obj[prop])}`);
|
||||
}
|
||||
return str.join('&');
|
||||
};
|
||||
|
||||
export function setQueryString(obj) {
|
||||
let qs = '';
|
||||
if (obj) {
|
||||
qs = `?${queryString.stringify(obj)}`;
|
||||
}
|
||||
const qs = obj ? `?${qsStringify(obj)}` : '';
|
||||
window.history.pushState(null, null, `/lists/${qs}`);
|
||||
}
|
||||
|
||||
@@ -63,3 +67,10 @@ export function getCookie(name) {
|
||||
}
|
||||
return cookieValue;
|
||||
}
|
||||
|
||||
export const groupBy = (xs, key) => {
|
||||
return xs.reduce((rv, x) => {
|
||||
(rv[x[key]] = rv[x[key]] || []).push(x);
|
||||
return rv;
|
||||
}, {});
|
||||
};
|
||||
@@ -19,11 +19,7 @@ module.exports = (env, argv) => {
|
||||
plugins: [
|
||||
new MiniCssExtractPlugin(),
|
||||
env === 'production' ? new webpack.IgnorePlugin(/^\.\/locale$/, /moment$/) : null,
|
||||
env !== 'production' ? new HtmlWebpackPlugin({ template: './src/index.html' }) : null,
|
||||
new webpack.ProvidePlugin({
|
||||
$: 'jquery',
|
||||
_: 'lodash'
|
||||
})
|
||||
env !== 'production' ? new HtmlWebpackPlugin({ template: './src/index.html' }) : null
|
||||
].filter(Boolean),
|
||||
module: {
|
||||
rules: [
|
||||
|
||||
Reference in new issue
Block a user