80 votes

Création d'une application d'entreprise avec Node / Express

J'essaie de comprendre comment la structure de l'entreprise d'application avec Node/Express/Mongo (en fait, l'aide MOYENNE de la pile).

Après la lecture de 2 livres et quelques recherches sur google (y compris semblable StackOverflow questions), je ne pouvais pas trouver tout bon exemple de structuration de grandes applications à l'aide de l'Express. Toutes les sources que j'ai lu suggèrent de fractionnement de l'application par les entités suivantes:

  • itinéraires
  • les contrôleurs de
  • modèles

Mais le principal problème que je vois avec cette structure est que les contrôleurs sont comme dieu objets, ils connaît req, res objets, responsable de la validation et avoir une logique d'entreprise inclus dans.

À l'autre côté, les routes me semble que le génie car tout ce qu'il fait est la cartographie des points de terminaison(chemins d'accès) à contrôleur de méthodes.

J'ai Scala/Java arrière-plan, donc j'ai l'habitude de séparer la logique en 3 niveaux - contrôleur/service/dao.

Pour moi énoncés suivants sont idéales:

  • Les contrôleurs ne sont responsables que pour l'interaction avec la partie WEB, c'est à dire marshalling/unmarshalling, une simple validation (obligatoire, min, max, e-mail regex etc);

  • La couche de Service (qui, en fait, j'ai raté en NodeJS/Express apps) est responsable uniquement de la logique d'entreprise, certaines entreprises de validation. La couche de Service ne sais rien à propos de WEB (par exemple, ils peuvent être appelés à partir d'un autre lieu de l'application, non seulement du contexte web);

  • Quant à la couche DAO est clair du tout pour moi. Mangouste modèles sont en fait des DAO, donc le plus clair chose pour moi ici.

Je pense que les exemples que j'ai vu sont très simple, et il affiche uniquement les concepts de Node/Express, mais j'ai envie de regarder quelques-l'exemple du monde réel, avec une grande partie de la logique métier/validation.

EDIT:

Une autre chose n'est pas clair pour moi est absent de la DTO des objets. Considérons cet exemple:

const mongoose = require('mongoose');
const Article = mongoose.model('Article');
exports.create = function(req, res) {
    // Create a new article object
    const article = new Article(req.body);
    // saving article and other code
}

Il y a bien un objet JSON à partir d' req.body est passé comme paramètre pour la création de Mongo document. Ça sent mauvais pour moi. Je voudrais travailler avec les classes de béton, pas de la matière première JSON

Merci.

6voto

rohit salaria Points 103

Tout le monde a sa propre façon de diviser le projet en certains dossiers. la structure que j'utilise est

  • config
  • les journaux
  • itinéraires
  • les contrôleurs de
  • modèles
  • services
  • utils
  • app.js/server.js/index.js (n'importe quel nom u préférez)

dossier config contient les fichiers de configuration de la base de données les paramètres de connexion pour toutes les phases de développement comme "production","développement","les essais"

exemple

'use strict'
var dbsettings = {
    "production": {
//your test settings
    },
    "test": {

    },
    "development": {
        "database": "be",
        "username": "yourname",
        "password": "yourpassword",
        "host": "localhost",
        "connectionLimit": 100
    }
}
module.exports = dbsettings

dossier du journal de contenir vos journaux de connexion des journaux d'erreur pour le débogage

contrôleur pour la validation de votre req données et la logique métier

exemple

const service = require("../../service")
const async = require("async")
exports.techverify = (data, callback) => {

    async.series([
        (cb) => {
            let searchObject = { accessToken: data.accessToken }
            service.admin.get(searchObject, (err, result) => {
                if (err || result.length == 0) {
                    callback(err, { message: "accessToken is invalid" })
                } else {
                    delete data.accessToken
                    service.tech.update(data, { verified: true }, (err, affe, res) => {
                        if (!err)
                            callback(err, { message: "verification done" })
                        else
                            callback(err, { message: "error occured" })
                    })
                }
            })
        }
    ])
}

modèles pour la définition de votre base de données de schéma

exemple mongoDb schéma

'use strict'
let mongoose = require('mongoose');
let schema = mongoose.Schema;
let user = new schema({
    accesstoken: { type: String },
    firstname: { type: String },
    lastname: { type: String },
    email: { type: String, unique: true },
    image: { type: String },
    phoneNo: { type: String },
    gender: { type: String },
    deviceType: { type: String },
    password: { type: String },
    regAddress: { type: String },
    pincode: { type: String },
    fbId: { type: String, default: 0 },
    created_at: { type: Date, default: Date.now },
    updated_at: { type: Date, default: Date.now },
    one_time_password: { type: String },
    forgot_password_token: { type: String },
    is_block: { type: Boolean, default: 0 },
    skin_type: { type: String },
    hair_length: { type: String },
    hair_type: { type: String },
    credits: { type: Number, default: 0 },
    invite_code: { type: String },
    refered_by: { type: String },
    card_details: [{
        card_type: { type: String },
        card_no: { type: String },
        card_cv_no: { type: String },
        created_at: { type: Date }
    }]
});
module.exports = mongoose.model('user', user);

services pour la rédaction de votre base de données de requête d'éviter d'écrire des requêtes au contrôleur d'essayer d'écrire une requête dans ce dossier, et de l'appeler dans le contrôleur

requêtes à l'aide de la mangouste

'use strict'
const modelUser = require('../../models/user');
exports.insert = (data, callback) => {
    console.log('mongo log for insert function', data)
    new modelUser(data).save(callback)
}
exports.get = (data, callback) => {
    console.log('mongo log for get function', data)
    modelUser.find(data, callback)
}
exports.update = (data, updateData, callback) => {
    console.log('mongo log for update function', data)
    modelUser.update(data, updateData, callback);
}
exports.getWithProjection = (data, projection, callback) => {
    console.log('mongo log for get function', data)
    modelUser.find(data, projection, callback)
}

utils pour la commune de la fonction d'utilité qui est couramment utilisé dans votre projet peut-être comme crypter,décrypter le mot de passe etc

exemple

exports.checkPassword = (text, psypherText) => {
    console.log("checkPassword executed")
    console.log(text, psypherText)
    return bcrypt.compareSync(text, psypherText)
}
exports.generateToken = (userEmail) => {
    return jwt.sign({ unique: userEmail, timeStamp: Date.now }, config.keys.jsonwebtoken)
}

0voto

Imperator Points 8

rohit salaria réponse fondamentalement, explique la même application de la structure que vous êtes habitué à java.

  • Les contrôleurs sont les Contrôleurs en Java
  • Les modèles sont de la Couche d'Accès aux Données
  • Les Services sont la Couche de Service

J'ai quelques remarques cependant. Le premier et le plus important, c'est que ce n'est pas Java. Il peut paraître évident, mais il suffit de regarder votre question et de voir que vous êtes à la recherche de la même expérience de développement avec les mêmes concepts que vous avez utilisé dans le monde Java. Mes remarques qui suivent sont juste l'explication de ce phénomène.

Manquant Otd. En Java, ils sont juste nécessaire, période. Dans une application web Java, où vous stockez vos données dans une base de données relationnelle, l'envoi et la réception de données pour le front-end en JSON, il est naturel que vous convertissez les données en un objet Java. Cependant, dans un Nœud de l'application de tout ce qui est javascript et JSON. C'est l'un des points forts de la plate-forme. Avec JSON étant le format de données commun, il n'est pas nécessaire d'écrire du code ou de dépendre de bibliothèques pour faire la conversion entre le format de données de vos calques.

En passant de l'objet de données directement à partir de la demande pour le modèle. Pourquoi pas? Ayant JSON comme format de données commun à partir de la face avant de la base de données vous permet de synchroniser facilement le modèle de données de votre application entre tous vos calques. Bien sûr, vous n'avez pas à aller dans cette voie, mais elle est suffisante la plupart du temps, alors pourquoi ne pas l'utiliser? Comme pour la validation, il est fait dans le modèle, là où il appartient, selon le MVC théorie (et pas dans le contrôleur de la paresse et de pragmatisme met souvent :)).

Pour la dernière pensée que je veux ajouter, que ce n'est pas la meilleure plate-forme quand il s'agit de la taille du projet de mise à l'échelle. Il est nod chauve-souris à tous, mais Java est mieux dans cet aspect.

0voto

manish kumar Points 906

simple et règle de base

  1. Gardez les éléments associés proches les uns des autres.

  2. Diviser la page en composants et de travail

  3. Tous les composants dépendants doivent être ensemble

  4. partagé choses devraient être gardés indépendant de tous les autres composants .

Enfin, chaque langue est douce. C'est juste la façon dont vous vous serez familiarisé avec la langue.Vous pouvez seulement gagner la bataille si vous familier avec vous à l'épée.

je suis en train d'élaborer Angular2 application à l'aide de NodeJS,Angular2 je vais vous aider avec ma structure de répertoire.

main Module

"le principal module` 

subModule

 "le sous-module de structure

shared Module

"garder le dossier partagé comme un module séparé`

Espérons que cela aide :)

-1voto

Bradley Points 651

J'ai accompli ce que vous essayez de faire. Essentiellement, il y a une couche qui manque dans le Parcours traditionnel/Contrôleur/structure du Modèle. La réponse courte est que cela n'a pas évolué dans le nœud de domaine comment vous voulez encore - il y a donc venir personnalisé de choses à faire, si vous voulez être la manipulation d'objets.

Quelques suggestions pour commencer avec:

  • Utilisation de la Machine au lieu de stock JavaScript
  • Remplacer Express avec HapiJS

Le moyen le plus efficace que j'ai trouvée pour atteindre cet objectif est d'avoir un objet qui a des méthodes statiques que l'accès le modèle, puis de les importer dans vos contrôleurs. Aujourd'hui - cela prend plus de temps à mettre en place que juste après les docs sur le nœud serveurs mais une fois que vous avez fait c'est hyper simple à entretenir et la division du travail pour les grandes équipes, c'est fantastique (une fois que l'équipe peut littéralement être dédié aux routes/contrôleurs tandis que l'autre gère la DAO/modèles).

// controller
import Article from 'models/Article';
export ArticleController {

    class GET {
        handler( req, res ){
            return Article.find(req.params.id);
        }
    }

    class POST {

        validator: {
            // this is where you ensure req.payload is going to be sufficient for the article constructor
            payload: {
                name: joi.string().required()
            }
        }

        handler( req, res ){
            const oArticle = new Article(req.payload);
            oArticle.save();
        }
    }

}

//Article
export class Article {
    public id: string;
    public name: string;

    constructor(data){
        // over-simplified logic to load data into object for example
        // there are some edge cases you need to figure out
        Object.assign(this, data);
    }

    public static find( id ){
       // get the article from your DAO - pseudo code
       const data = DAO.getArticleDataById(id);
       return new Article(data);
    }

    public save(){
        // save this object using DAO
    }
}

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X