Skip to content

Commit

Permalink
Refactored file-loading into its own thing
Browse files Browse the repository at this point in the history
  • Loading branch information
jdan committed Aug 26, 2013
1 parent addf70b commit 2b0d841
Show file tree
Hide file tree
Showing 6 changed files with 89 additions and 58 deletions.
91 changes: 36 additions & 55 deletions lib/cleaver.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,30 +4,41 @@ var path = require('path');
var md = require('node-markdown').Markdown;
var yaml = require('js-yaml');
var mustache = require('mustache');
var helper = require('./helper');

function Cleaver(options) {
if (!options.file) throw "!! Please specify a file with the --file option";

// filenames which will be used to read in data
// TODO: refactor templating and static files into its own thing
this.stylesheetFile = Cleaver.ROOT_DIR + 'styles/default.css';
this.mainTemplateFile = Cleaver.ROOT_DIR + 'templates/layout.mustache';
this.authorTemplateFile = Cleaver.ROOT_DIR + 'templates/_author.mustache';
this.jqueryFile = Cleaver.ROOT_DIR + 'resources/jquery.min.js';
this.navigationFile = Cleaver.ROOT_DIR + 'resources/navigation.js';
this.authorTemplateFile = Cleaver.ROOT_DIR + 'templates/author.mustache';

// user-specified files
// TODO: user-defined style

// TODO: make these constants?
this.templates = {
main: 'layout.mustache'
};

this.resources = {
style: 'default.css',
jquery: 'jquery.min.js',
navigation: 'navigation.js'
};

this.external = {
document: options.file,
style: options.style
};

this.metadata = null;

// // user-specified files
this.documentFile = options.file;
this.userStylesheetFile = options.style;

// data, empty for now
// // data, empty for now
this.document = null;
this.slides = [];
this.stylesheets = [];
this.mainTemplate = null;
this.jquery = null;
this.navigation = null;
this.metadata = null;
}


Expand All @@ -45,8 +56,8 @@ Cleaver.prototype._parseDocument = function () {
var self = this;

return Q.all([
this._loadSingleAsset(this.documentFile),
this._loadSingleAsset(this.authorTemplateFile)
helper.loadSingle(this.documentFile),
helper.loadSingle(this.authorTemplateFile)
])
.then(function (data) {
self.document = data[0];
Expand All @@ -66,44 +77,13 @@ Cleaver.prototype._parseDocument = function () {
/**
* Loads the templates, default stylesheet, and any external stylesheets
* as defined by the user.
* @return {Promise.<Array.<Object>>}
*/
Cleaver.prototype._loadAssets = function () {
var promises = [
this._loadSingleAsset(this.mainTemplateFile),
this._loadSingleAsset(this.jqueryFile),
this._loadSingleAsset(this.navigationFile),
this._loadSingleAsset(this.stylesheetFile)
];

if (this.userStylesheetFile) {
promises.push(this._loadSingleAsset(this.userStylesheetFile));
}

var self = this;
return Q.all(promises)
.then(function (data) {
// TODO: refactor this into its own helper method?
self.mainTemplate = data[0];
self.jquery = data[1];
self.navigation = data[2];

for (var i = 3; i < data.length; i++) {
self.stylesheets.push(data[i]);
}
})
.fail(function (err) {
throw err
});
}


/**
* Loads a single static asset. Returns a promise.
* @param {string} filename The name and location of the file to load
* @return {Promise.<string>} The file contents
*/
Cleaver.prototype._loadSingleAsset = function (filename) {
return Q.nfcall(fs.readFile, filename, 'utf-8');
return Q.all([
helper.load(this.templates, 'templates'),
helper.load(this.resources, 'resources')
]);
}


Expand All @@ -116,13 +96,13 @@ Cleaver.prototype._renderSlideshow = function () {
title: this.metadata.title,
// TODO: read --nocontrols from argv
controls: true,
styles: this.stylesheets,
jquery: this.jquery,
navigation: this.navigation
style: this.resources.loaded.style,
jquery: this.resources.loaded.jquery,
navigation: this.resources.loaded.navigation
};

// TODO: output to --output=????? (default, output.html)
console.log(mustache.render(this.mainTemplate, slideData));
console.log(mustache.render(this.templates.loaded.main, slideData));
}


Expand Down Expand Up @@ -158,6 +138,7 @@ Cleaver.prototype._slice = function(document) {
*/
Cleaver.prototype.run = function () {
var self = this;

Q.all([this._parseDocument(), this._loadAssets()])
.then(self._renderSlideshow.bind(self))
.fail(function (err) {
Expand Down
52 changes: 52 additions & 0 deletions lib/helper.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
var Q = require('q');
var fs = require('fs');
var path = require('path');


/**
* Root directory so that asset loaders know where to look
* @constant {string}
*/
var ROOT_DIR = path.normalize(__dirname + '/../');


/**
* Loads a single static asset. Returns a promise.
* @param {string} filename The name and location of the file to load
* @return {Promise.<string>} The file contents
*/
function loadSingle(filename) {
return Q.nfcall(fs.readFile, filename, 'utf-8');
}


/**
* Loads files from a given map and places them in that map's `loaded` field
* @param {Object} map The map of labels to filenames
* @param {?string} opt_prefix The prefix to search in for files
* @return {Promise.<Array.<Object>>} The same map with a `loaded` field populated with file contents
*/
function load(map, opt_prefix) {
var promises = [];
map.loaded = {};

for (var key in map) {
if (key == 'loaded') continue;

var filename;
if (opt_prefix) filename = ROOT_DIR + opt_prefix + '/' + map[key];
else filename = ROOT_DIR + opt_prefix + map[key];

promises.push(loadSingle(filename)
.then((function (_key) {
return function (data) {
map.loaded[_key] = data;
}
})(key)));
}

return Q.all(promises);
}

exports.loadSingle = loadSingle;
exports.load = load;
File renamed without changes.
File renamed without changes.
File renamed without changes.
4 changes: 1 addition & 3 deletions templates/layout.mustache
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,7 @@
<head>
<title>{{title}}</title>
<style type="text/css">
{{#styles}}
{{{.}}}
{{/styles}}
{{{style}}}
</style>
</head>
<body>
Expand Down

0 comments on commit 2b0d841

Please sign in to comment.