3
\$\begingroup\$

I'm building an app that serves videos to a front end client. My stack is Express/Angular/SQLite. The db doesn't hold users, only root. I'm concerned that my controllers are too hardcoded, but I'm wary of the balance between making controllers too dynamic such that I'm merely pigeonholing myself into an over-engineered framework.

Backend project structure:

/server

    app.js                           //creates app-wide express instance and feeds necessary dependencies to child components

    /config
        db.auth.js                   //for sqlite
        paths.js                     //references to location of videos and other assets
        routes.js                    //defines the api the frontend requests

     /controllers

        /recipes
            doSomethingRedundant.js  //many controller methods require this
            index.js                 //exports all recipes

        index.js                     //exports all controllers
        videoController.js           //methods for Video model
        peopleController.js          //methods for Person model
        playlistController.js        //methods for Playlist model
        //etc.

    /database
        sequelize.bootstrap.js       //returns single app-wide instance of db connection
        sqlite.db                    //database

    /middleware
        static.js                    //defining paths to static file locations
        webhooks.js                  //other stuff, like build

    /models
        index.js                     //exports models for easy access to controllers
        Video.js
        Person.js
        Studio.js
        //etc

    /services
        index.js                      //main exporter
        makeReel.js                   //makes preview strip via ffmpeg

    /views
        index.html                    //frontend is SPA, there is only one view, basically

I'm content with this structure. It's easy for me to understand and I know where everything is supposed to go. But, here's what my routes.js file looks like:

var controllers = require("./../controllers/index.js");

module.exports = function(app) {
    //this seems suspicious, but I can't explain lucidly why it feels wrong
    app.get("/videos/:range/some", controllers.videos.getSome); 
    app.get("/videos/:id/one", controllers.videos.getOne);
    app.get("/videos/:id/random", controllers.videos.getRandom);

    app.get("/thumbs/:video/:thumb", controllers.images.getOne);
    app.get("/thumbs/:video/range/:range", controllers.images.getMany);
};

And the video controller:

var async = require("async");
var path = require("path");
var _ = require("lodash");
var util = require("./../services/util.js");
var bootstrap = require("./../database/sequelize.bootstrap.js");
var sequelize = bootstrap.sequelize;
var models = bootstrap.models;
var recipes = bootstrap.recipes;

module.exports = {
    getAll: function(req, res) {
        models.Video.findAll()
            .then(function(rows) {
                res.send(getval(rows));
            })
            .catch(util.err);
    },
    getSome: function(req, res) {
        var range = req.params.id.split(",");
        models.Video.findAll({
            where: {
                id: {
                    $between: [range[0], range[1]]
                }
            }
        }).then(function(rows) {
            res.send(getval(rows));
        }).catch(util.err)
    },

    //get the video ID and all associated model instances
    getOne: function(req, res) {
        recipes.getVideoInfo(req.params.id, function(result) {
            res.send(result);
        });
    },
    getRandom: function(req, res) {
        models.Video.count().then(function(count) {

            (function ran(except, range) {
                var r = _.random(0, range);
                if (r === except)
                    return ran(except);
                recipes.getVideoInfo(r, function(result) {
                    res.send(result);
                });
            })(req.params.id, count);

        }).catch(util.err);
    }
};

function getval(arr) {
    return arr.map(function(obj) {return obj.dataValues;});
}

I feel I'm committing a cardinal sin by splitting up a similar GET request for video info into several similar getRandom, getOne, getSome, getAll methods. Is this a bad idea? Due to lack of experience I can't really tell.

\$\endgroup\$

0

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Browse other questions tagged or ask your own question.