像asp.net Mvc同樣開發nodejs+express Mvc站點

像asp.net Mvc同樣開發nodejs+express Mvc站點

首先,我是個c#碼農。從事Mvc開發已然4個年頭了,這兩年前端MVC的興起,我也跟風學了一些,對前端的框架也瞭解一些,angularJsrequirejscommonJsbackbone等等前端的mvc框架也異常流行,與這些前端的流行框架一同火起來的還有node.js. Node.jsjavascript做爲服務器端的代碼開發,由其語言特性(單線程,異步)等以高效率高吞吐著稱。這裏不會去討論node.js的好的壞的。有興趣的自行googlejavascript

隨着node.js流行,一個些快速開發 的框架也出現了,express算是一個web開始開發的框架。關於express的更多知識呢,同志們自行google吧(哎,篇幅太有限,水太深,不敢深趟,T.T.css

前面說了幾個基礎框架,那麼咱們就要用這些框架作什麼呢?我想從事過Asp.Net Mvc開發的同窗們都清楚.Net Mvc框架的站點結構,這裏我也給大夥截個圖,html

 

 

簡單說下這個目錄結構:前端

app_start:文件下通常放置應用程序啓動時的執行代碼如路由註冊,bundle註冊,ViewEngineValueProvider等通用功能的註冊java

Content:通常放置cssimage等靜態資源node

Controller:這是控制器代碼放置的位置web

Models:實體代碼問題express

Views:視圖模板位置c#

其實還有個Area的目錄,Area目錄則是放置區域代碼內含有controllerviews目錄服務器

對於習慣了這個目錄結構的同窗們,對每一個目錄的功能都很清楚了吧,這裏就很少說了。

那麼在Nodejs+expressjs的狀況下是什麼樣的目錄呢?

 

也簡單的說說這個目錄吧,

Bin目錄實際上是express框架啓動的腳本所在,

Node_modules則是express核心代碼全部目錄

Public是公共資源的所在目錄,相似與.netMvc中的content目錄,不過腳本資源也會在這個目錄下,這個目錄下的文件是靜態匹配的,不通過路由的,固然你也能夠經過配置改成其它的目錄。

Routes:是路由註冊的地方,其實也能夠認爲是代碼所在的地方,從命令行生成項目後,routes目錄下有index.jsuser.js兩個文件,能夠看出這裏應該就是業務邏輯處理的地方

Views.netMvc同樣,是視圖模板所在的地方。

App.js則是整個站點的入口,事實上是在bin目錄下名爲www的文件啓動的

哎呀呀,前面講了這麼多,還沒入主題呢,這結構真夠拖沓的。

Ok ,咱們儘快進入主題。

前面講了目錄結構上的差別,如今講講開發模式上的差別。

打開express站點的routes目錄下index.js代碼:

var express  = require('express');

var router = express.Router();

 

/* GET home page. */

router.get('/', function (req, res) { // 註冊默認路由/,的處理器

    res.render('index', { title: 'Express' });  // 輸出views

});

 

module.exports = router

 

 

從代碼上解讀,咱們很容易知道,以上代碼的意思(見上面的註釋 //後面的內容)。若是您還不能理解上面的代碼,您能夠去googlenodejsexpress吧,那樣會幫助你理解。

expressrouter提供了getpostall等模式的註冊。Get即處理get請求,post即處理post的請求,all則接受全部的請求。而對於.NetMvc則是將路由註冊和相應處理邏輯分離。在.netMvc中的實現是這樣的

Globel.asmx

 

 RouteConfig.RegisterRoutes(RouteTable.Routes);

 

App_start\RouteConfig.cs

 

  public static void RegisterRoutes(RouteCollection routes)

        {

            routes.IgnoreRoute("{resource}.axd/{*pathInfo}");

 

            routes.MapRoute(

                name: "Default",

                url: "{controller}/{action}/{id}",

                defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional }

            );

        }

 

最後在controller\HomeController中實現業務邏輯

 

 public ActionResult Index()

        {

            return View();

        }

 

 

 

.NetMVC中,路由註冊時會在請求時自動映射處處理器上。事實上,在NetMvc是和express同樣的實現邏輯,只不過,NetMvc提供了自動映射的封裝。

好了。今天的重點就是這個了。對於Asp.Net Mvc的開發人員而言這個邏輯清晰(實際上是用久了理解一點都不費力,不得不說,若是第一次接觸,仍是蠻很差理解的,沒有express那麼直觀),因此如今就對express進行二次開發,讓它也能支持這種統一路由並自動映射處處理器的功能,同時將.NetMvc提供的一些功能加上,,例如Areawebconfig,可以實現配置在業務請求添加攔截器(httpHandlerhttpModule)的功能等,讓express的開發過程和開發模式儘量的和Asp.Net一致。

 

目前已改造的功能有:

一、路由配置和處理器分離,自動映射

RouteConfig.js


1
this.registerRoute = function (route) { 2 route.mapRoute({ 3 name: "defaults", 4 url: "/:area?/:controller/:action/:id?", 5 defaults: { controller: "home", action: "index" }, 6 namespace: "" 7 }); 8 };

SSOContoller.js

module.exports = function () {

    this.login = function (model) {

        console.log("ssoController:login:start");

        console.log(model);

 

        if (model.userUid == "admin" && model.password == "111111") {

            this.context.response.cookie("ticket", "djaskdfjskjdfjsd");

            return this.redirectToAction("index", "home");

        }

        this.ViewBag.returnUrl = model.ReturnUrl

        return this.view({title:"單點登錄",name:""});

    }

}

 

 

二、支持webconfig配置,添加自定義HttpHanlder,目前只是簡單的Handler的配置,後面會添加url匹配

Webconfig.js

module.exports = {

    "server.web": {

        modules: {

            handlers: [

                { name: "sso", handler: "./SSOHandler.js",rules=」*」 },

                { name: "default", handler: "./DefaultHandler.js" rules=」*」 },

                { name: "AttachmentDownloadHandler", handler: "./DownLoadHandler.js" rules=」*/AttachmentDownload.handler」 }

            ]

        }

    },

    appsetings: {

        ssoLogin: "/sso/login?ReturnUrl=",

        ssoLogout: "/sso/logout"

        ,controllerFix:"controller"

    }

}

 

三、實現BaseController中提供ViewResultRedirectResultActionResult的實現

四、在Views中使用ModelViewBagHtmlHelper等,模板採用ejs

因爲javascript沒有強類型概念,因此沒法獲取元數據,因而ModelBinder中數據驗證,htmlhelper中被閹割了許多功能,後面將進一步考慮如何實現。

<!DOCTYPE html>

<html>

  <head>

    <title><%= model.title %></title>

    <link rel='stylesheet' href='/stylesheets/style.css' />

  </head>

  <body>

    <h1><%= model.title %></h1>

    <p>Welcome, <%= model.name %></p>

<p>今年<%=viewbag.age %></p>

<p><%-html.textBoxFor(model.name) %></p>

</form>

  </body>

</html>

 

 

改造還會繼續,歡迎你們提供意見,以上講的有什麼不對的地方還請不吝指出。

附上源碼,供你們參考(代碼還未作整理,目錄結構有些不合理,先這樣吧,過兩天把結構整整了,大神不要吐槽~)。

若是您以爲還有什麼地方能夠添加的功能實現,也歡迎給我留言。

若是您以爲不錯,歡迎點下推薦,支持一下,您的鼓勵是我寫博的動力,感謝。

源碼

相關文章
相關標籤/搜索