/* global __dirname */
/* jshint strict:false */
"use strict";
var express = require('express');
var bodyParser = require('body-parser');
var slug = require('slug');
var beautify = require("json-beautify");
var _ = require('lodash');
var fs = require('fs');
var Promise = require('bluebird');
var Mustache = require('mustache');
var app = express();
// var examplesJSON = __dirname + '/exemples/liste.json';
var sandboxTpml = fs.readFileSync(__dirname + '/html/template.mustache.html').toString();
// var examples = require(examplesJSON);
Promise.promisifyAll(fs);
// Initialize Express app: root folder as static, body parsers
app.use(express.static(__dirname));
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: true }));
function scandir(path, excludes) {
excludes = excludes || [];
return fs.readdirAsync(path)
.then(dirContent => {
excludes.forEach(file => {
var idxInContent = dirContent.indexOf(file);
if(idxInContent !== -1) {
dirContent.splice(idxInContent, 1);
}
});
return dirContent;
})
}
function ExampleStore(path) {
this.rootPath = path;
this.repos = [];
}
ExampleStore.prototype.init = function() {
const loadRepository = this.loadRepository.bind(this);
return scandir(this.rootPath, ['.gitkeep'])
.then(repositories => Promise.map(
repositories, loadRepository
));
};
ExampleStore.prototype.loadRepository = function(repoPath) {
const loadExample = this.loadExample.bind(this);
const fullPath = this.rootPath + '/' + repoPath;
const repoConfig = require(fullPath + '/repo-config.json');
const repoDescriptor = {
title: repoConfig.title,
path: repoPath,
fullPath,
examples: []
};
this.repos.push(repoDescriptor);
return scandir(fullPath, ['.gitkeep', 'repo-config.json'])
.then(examples => Promise.map(
examples, example => loadExample(repoDescriptor, example)
))
.then(() => console.log(this.repos[0]))
};
ExampleStore.prototype.loadExample = function(repo, slug) {
const exampleConfig = require(repo.fullPath + '/' + slug + '/config.json');
repo.examples.push(Object.assign({ slug }, exampleConfig));
return exampleConfig;
};
ExampleStore.prototype.getList = function(path) {
return _.find(this.repos, { path });
}
ExampleStore.prototype.getMenu = function(path) {
const self = this;
return '
' + self.repos.reduce((menu, repo) => {
return '- '+ repo.title + '
';
}, '') + '
';
}
var es = new ExampleStore(__dirname + '/exemples');
es.init()
.then(() => console.log(es.getMenu()));
function addExample(slug, title) {
examples.push({ slug: slug, title: title });
return fs.writeFileAsync(examplesJSON, beautify(examples, null, 2, 100));
}
function readConfigJson(exampleSlug) {
console.log(exampleSlug);
return require('./exemples/jquery/' + exampleSlug + '/config.json');
}
function readFileAsync(file) {
return fs.readFileAsync(file)
.then(buf => (buf.toString()));
}
// function readFilesAsync(path, files) {
// // console.log('reading files', files, 'from path', path);
// return Promise.map(files,
// f => readFileAsync(path + '/' + f)
// );
// }
// function readExampleFiles(slug, config) {
// const exampleDir = __dirname + '/exemples/' + slug;
// const libsCssDir = __dirname + '/css/vendor';
// const libsJsDir = __dirname + '/js/vendor';
// const { html, js, css, libsCss, libsJs } = config;
// return Promise.all([
// readFilesAsync(exampleDir, html),
// readFilesAsync(exampleDir, js),
// readFilesAsync(exampleDir, css),
// readFilesAsync(libsJsDir, libsJs),
// readFilesAsync(libsCssDir, libsCss),
// ]);
// }
app.post('/examples', function(req, res) {
var title = req.body.title;
if(! req.body.title) {
res.status(400).send('Le titre ne peut pas être vide !');
}
var existingTitle = _.find(examples, { title: title });
if(existingTitle) {
res.status(400).send("L'exemple '" + title + "' existe déjà !");
}
var exampleSlug = slug(req.body.title.toLowerCase());
var targetDir = __dirname + '/exemples/' + exampleSlug;
fs.mkdirAsync(targetDir)
.then(() => Promise.map(
['contenu.html', 'script.js'], f => fs.writeFileAsync(targetDir + '/' + f, '')
))
.then(files => addExample(exampleSlug, title))
.then(() => res.json({ slug: exampleSlug, title: title }));
});
app.get('/examples/:slug', function(req, res) {
const { slug } = req.params;
const config = readConfigJson(slug);
const { title, html, js, css, libsCss, libsJs } = config;
readFileAsync(__dirname + '/exemples/' + slug + '/example.html')
.then(body =>
Mustache.render(sandboxTpml, { body, slug, title, js, css, libsCss, libsJs })
)
.then(html => res.send(html));
});
app.get('/menu', (rea, res) => {
res.send(es.getMenu());
});
app.get('/list/:repoPath', function(req, res) {
const { repoPath } = req.params;
const repo = es.getList(repoPath);
if(! repo) {
return res.status(404).send('Repo ' + repoPath + ' not found');
}
console.log('found repo', repo);
const data = repo.examples.map(e => (
{ slug: e.slug, title: e.title }
));
res.json(data);
});
app.put('/examples/:slug', function(req, res) {
var slug = req.params.slug;
var existing = _.find(examples, { slug: slug });
if(! existing) {
res.status(404).send("L'exemple avec l'identifiant '" + slug + "' est introuvable !");
}
var targetDir = __dirname + '/exemples/' + slug;
if(req.body.html) {
fs.writeFileSync(targetDir + '/contenu.html', req.body.html);
}
if(req.body.javascript) {
fs.writeFileSync(targetDir + '/script.js', req.body.javascript);
}
var theDate = new Date();
console.log(theDate.getHours() + ':' + theDate.getMinutes() + " - Sauvegarde de l'exemple '" + existing.title + " effectuée'");
res.json({ success: true });
});
module.exports = app;