I want to restructure Nodejs Express Project that contains v1 and v2 folders inside routes directory.
when restructuring the code to MVC approach, should i have MVC structure for v1 and another MVC structure under v2?
Ideally controllers should be versioned as v1, v2, etc., as they will contain your application logic, which is going to change from time to time, and you'll need to support users using the logic of older version of your application (fallback compatibility).
Models will contain schema for records stored in your database, which should remain consistent across all versions of your controllers. Therefore it should remain outside of your v1, v2, etc. (Like, User will contain same fields regardless of the difference in application logic versions). Changes in models are generally not drastic, as you'll have to define them in a way which doesn't require huge changes later on. In case of a drastic change, you'll have to update the logic across all versions of your controllers accordingly.
Views, can either be versioned or not, depending upon whether you'd like to serve separate views depending upon api version.
Overall, the project structure may look like this
src/
models/
ModelA.js
ModelB.js
...
routes/
v1/
index.js
...
v2/
...
views/
index.ejs
...
server.js
package.json
Related
Context:
I have an express web server which I'm using as a sort of 'template' to create solutions for customers. The needs and use-cases of customers in the industry I work in are all somewhat similar, and therefore most static resources (images, es6 modules etc.) are shared between them. These are all in the root /static/ folder. There are cases where the customers needs necessitate individualized scripts and resources in which case I place them under their respective solution folder, e.g. solutions/solutionA/static/def.js for customer A. In server.js, the express launcher script, I set two static directories through middleware. /static (for shared stuff), and /solutions/ACTIVE SOLUTION/static (for solution specific stuff), where ACTIVE SOLUTION is a constant string specified at the top of the file.
node_modules/
static/
abc.js
solutions/
solutionA/
static/
def.ts
solutionB/
static/
ghi.ts
solutionC/
static/
server.ts
tsconfig.json
Problem:
My problem lies with typescript complaining about es6 import statements. From within say solutions/solutionA/static/def.ts, I cannot do
import abc from "./abc.js"
even though this is correct in-browser, as I have set the root /static as a static folder.
Is there any way I can indicate to typescript via tsconfig.json or other means, that I would like it to also search in a particular directory for said files (in this case, the root /static?). I do not want the resulting js files to have their import paths changed, as /abc.js will indeed be valid due to the express middleware.
Current situation:
As the imports are correct when loaded in browser, my solution is currently "working". The issue lies in the fact both visual studio code and tsc rightfully complain of the incorrect import path. This is a fairly recent refactoring, the merging of like solutions to stop splintering. It seemed like a good idea, only now my entire project is littered with errors.... Other people are going to be working on my solution eventually, and I don't want to give them something with copious amounts of worrying warnings.
Situation
I am building a set of applications based on a NestJS monorepo.
I have severals apps that relies on severals shared libs.
Those apps are similar to one another, but may still differ on some features, so the monorepo totally makes sense.
Some of the libs provides #Controller(), which #Render() views for common features.
Assomptions
Template files should live in the module.
Since there is a high coupling between the controller and the rendered template,
I believe it makes sense to store the views template files (.hbs, .ejs, whatever) in the libs module providing the #Controller,
Only relevant templates should be shipped in dist/ when I build an app
I have some business/legal/security constraints that force me to avoid the presence of some libs in some apps production environment.
eg. my-secret-algo-lib should not be present in my-public-unsecure-internet-app
So it makes a file structure like this :
monorepo/
apps/
my-first-app/
src/
main.ts <-- nest bootstrap function is here
...
my-second-app/
...
libs/
my-first-lib/
src/
my-first-lib.module.ts
my-first-lib.controller.ts <-- #Render('my-view')
...
views/
my-view.ejs <-- the view
...
Goal
I want to achieve a build that produce the following file structure :
dist/
apps/
my-first-app/
main.js
views/
my-first-lib/
my-view.ejs
Assuming that:
my-first-app imports my-first-lib
Views that may exists in unused libs should not be included in dist/
Questions
Is this possible with existing tools?
Would this be considered an anti-pattern? if so how should I structure things ?
If the answer to both is "no", should I build something myself or join any existing effort?
Another part of the problem is NestJS application module configuration, but I guess this comes last...
Most Node examples and tutorials suggest setting up directories for Model, Views and Controllers and an "app.js" as a main file of the app. It seems a bit messy, since the app.js insn't really any of the MVC trio. It is actually quite a good candidate to be a controller, which works with the model and view modules.
So: Is it rule or convention breaker to go ahead with a M+V+app.js scenario, in case not more then one controller module is needed?
The ideal file structure for your node application is the structure that best fits your needs. There is no absolute rule about how to structure your app.
MVC is a generic template to structure your application, which you are free to use, or not.
By convention, the root file of your node application is an app.js or an index.js file.
If your application logic is simple enough that you to do not need to put your controllers files in a separate directory, you can stay with your app.js file alone.
That will not break the MVC paradigm as MVC is a pattern, not a directory structure.
I am starting a new project in which the idea is to organize the project file/folder structure in to different modules (.csproj) and finally once deployed these modules would be loaded to one AppHost of MainModule (these sub modules would act as plugins).
However, for better physical file management (SVN/VCS) and effective organization of my project files these modules would be maintained as separate projects in SVN too. Thought is to have views, assets etc. specific to each module in its own module directory scope. (Refer screenshot).
Main Module
SubModuleOne
Views
ModuleOneDefault.cshtml
SubModuleTwo
Views
ModuleTwoDefault.cshtml
Views
Shared
_Layout.cshtml
Hello.cshtml
Module specific files would be copied as post build action into root project path rather than /Views directly (if copied then it messes up with Main module's Views folder).
Problem is with how ServiceStack loads and handles Razor views from /Views folder and anything outside is considered to be content pages. More about this, explained here...!
With VirtualFileSystem in place I was thinking aloud to maintain module specific views in respective "/ModuleOne/Views/" folder but outside the root "/Views". Somehow, this doesn't seem to work, trying to seek help on how this could be achieved or handled appropriately.
PS: Am aware that anything outside Views folder is content pages, however the idea is still to maintain as Views folder but in different hierarchy - Hoping that ServiceStack Razor feature anyway handles nested (DEEP) structure well but within root /Views folder and not from the entire Project Root folder i.e. "/".
Question is, can this be achieved as is by default without any heavy lifting? or Should I be having custom VirtualPathProvider implementation etc.?
Opinion and thoughts are greatly appreciated!
Thanks!
All Razor Views must be in the /Views folder but otherwise they can be any hierarchy as any levels of nesting doesn't affect how they're resolved, they just need to be uniquely named, e.g:
/Views
/SubModuleOne
ModuleOneDefault.cshtml
/SubModuleTwo
ModuleTwoDefault.cshtml
/Shared
_Layout.cshtml
I have a question regarding the node app that I want to build.
Before starting on the development, I've written a clear document that splits up my app into different components:
Home
Search
User profile
Dashboard
etc...
Each of these modules may in turn consist of different submodules.
As every module in my app works quite independently (although there are common, reusable components), I decided to render the main page for each of the modules from the server using Express.
Each of the pages that I want to render is highly interactive in the field of DOM interaction and event driven view updates, so I want to go with Backbone for this (using push state for loading submodules dynamically for the nested url's), in combination with requirejs for asynchronous module loading.
The thing I wonder about is if it is okay to include a minified file for each of the pages that I render from the server with express. It seems that this causes quite some overhead, because for each module loaded all the libraries need to be included again (backbone, underscore, jquery, and others).
Is there a common solution to this problem, and will this (in your experience) cause unacceptable performance issues?
What we end up doing with a similar multi page app structure is we break the build to separate "common.js" file that contains all the shared modules, and "main-[module-name].js" files for page specific code, and load it with 2 separate script tags per page
I don't know that it has actual significant perf impact. I am guessing that not really, unless you have some large libraries in your project
Take a look at the multi page config example for requirejs
My $0.02