産品特色
編輯推薦
本書分為5個部分:
第Ⅰ部分“奠定堅實的基礎”涵蓋瞭軟件工程的關鍵概念,例如SOLID和DRY原則,還討論瞭單元測試和測試驅動開發的優點。
在第Ⅱ部分“測試基於模式的代碼”中,我們描述並使用測試驅動開發創建瞭幾個有用的代碼模式。
第Ⅲ部分“測試和編寫高級JavaScript特性”描述瞭如何使用和測試JavaScript語言更高級的特性。
第Ⅳ部分“測試中的特殊主題”提供瞭測試DOM操作的樣例,還演示瞭用於增強代碼標準的靜態分析工具的使用。
第Ⅴ部分“總結”迴顧瞭測試驅動開發的概念,還展示瞭一些本書用到的JavaScript習語。
內容簡介
為瞭構建更健壯的大型JavaScript應用程序,應先測試,後編碼
資深開發人員仍然在與大型JavaScript應用程序的失敗做鬥爭,而這往往是由於應用程序自身的規模而導緻的。本書以測試驅動工作流的形式提供瞭解決方案,它將産生經得起時間考驗的健壯應用程序。本書將使用單元測試解釋、演示和采用各種JavaScript模式和結構。隨著本書的學習,你將成為JavaScript測試驅動開發的專傢,勝任開發商業軟件。如果準備在JavaScript開發中引入高級軟件工程,那麼本書正是*佳之選。
主要特色
◆展示瞭如何編寫開始就被確認為正確的代碼,並使用測試讓代碼在接下來的維護過程中仍然保持正確
◆概述用於測試、依賴注入和麵嚮方麵編程的JavaScript框架目前的現狀
◆解釋可測試性特徵以及構建可測試對象的方式
◆演示常見設計模式以及高級JavaScript特性和架構的實現和使用
◆涵蓋DOM訪問測試,包括過度更新、在循環中的過度訪問以及XHR/JSONP請求
作者簡介
Lawrence D. Spencer,領導SeerIS的一個國際開發者團隊,SeerIS公司是波士頓附近的一傢軟件和服務公司。他擁有超過35年的工作經驗,曾經擔任過管理人員、開發人員、谘詢師以及講師,經常齣席編程大會。
Seth H. Richards,從2002年開始一直專業製作軟件。他的工作專注於基於Web的企業級地理信息係統應用。
內頁插圖
目錄
第Ⅰ部分 奠定堅實的基礎
第1章 實踐軟件工程 3
1.1 編寫從開始就正確的代碼 4
1.1.1 掌握JavaScript的特性 4
1.1.2 在大型係統中規避JavaScript陷阱 15
1.1.3 應用軟件工程原則 17
1.2 編寫保持正確的代碼 22
1.2.1 投資單元測試的未來 22
1.2.2 實踐測試驅動開發 22
1.2.3 編寫易於測試的代碼 23
1.3 小結 26
第2章 準備工具 27
2.1 使用測試框架 27
2.1.1 辨彆不正確的代碼 30
2.1.2 可測試性設計 32
2.1.3 編寫最少的代碼 33
2.1.4 安全維護和重構 33
2.1.5 可運行規範 34
2.1.6 當前的開源和商業框架 34
2.1.7 介紹Jasmine 36
2.2 使用依賴注入框架 41
2.2.1 依賴注入的定義 41
2.2.2 使用依賴注入讓代碼更可靠 43
2.2.3 掌握依賴注入 43
2.2.4 案例研究:編寫一個輕量級依賴注入框架 43
2.2.5 使用依賴注入框架 50
2.2.6 當前的依賴注入框架 52
2.3 使用切麵工具 53
2.3.1 案例研究:使用和不使用AOP進行緩存 53
2.3.2 案例研究:構建Aop.js模塊 55
2.3.3 其他AOP庫 67
2.3.4 結論 68
2.4 使用代碼檢查工具 68
2.4.1 使用linting工具讓代碼更可靠 68
2.4.2 JSHint簡介 71
2.4.3 其他工具 73
2.4.4 嚴格模式 74
2.5 小結 74
第3章 構造可靠的對象 75
3.1 使用原生數據 75
3.2 使用對象字麵量 77
3.3 使用模塊模式 78
3.3.1 創建任意模塊 78
3.3.2 創建立即執行模塊 79
3.3.3 創建可靠的模塊 80
3.4 使用對象原型和原型繼承 80
3.4.1 默認對象原型 80
3.4.2 原型繼承 81
3.4.3 原型鏈 82
3.5 使用new創建對象 83
3.6 使用類繼承 88
3.6.1 模擬類繼承 88
3.6.2 重復將殺死Kangaroo 89
3.7 使用函數式繼承 91
3.8 猴子補丁(Monkey-Patching) 92
3.9 小結 95
第Ⅱ部分 測試基於模式的代碼
第4章 瀏覽各種模式的優點 99
4.1 案例分析 99
4.2 通過更廣泛的詞匯産生更加優雅的代碼 100
4.3 使用擁有良好設計、良好測試的構建塊産生可靠的代碼 101
4.4 小結 102
第5章 確保迴調模式的正確使用 103
5.1 通過單元測試瞭解迴調模式 104
5.1.1 編寫和測試使用瞭迴調函數的代碼 104
5.1.2 編寫和測試迴調函數 109
5.2 避免問題 113
5.2.1 扁平化迴調箭頭 113
5.2.2 注意this變量 115
5.3 小結 119
第6章 確保承諾模式的正確使用 121
6.1 通過單元測試瞭解承諾 122
6.1.1 使用承諾 122
6.1.2 構造和返迴承諾 127
6.1.3 測試XMLHttpRequest 130
6.2 串聯承諾 133
6.3 使用承諾封裝器 134
6.4 瞭解狀態和命運 135
6.5 區分標準承諾和jQuery承諾 135
6.6 小結 136
第7章 確保正確使用散函數應用程序 137
7.1 對散函數應用程序進行單元測試 137
7.2 為散函數應用程序創建切麵 139
7.3 區分散函數應用程序和柯裏化 140
7.3.1 柯裏化 140
7.3.2 散函數應用程序 141
7.4 小結 141
第8章 確保備忘錄模式的正確使用 143
8.1 通過單元測試瞭解備忘錄模式 144
8.2 使用AOP添加備忘錄 147
8.2.1 創建備忘錄切麵 147
8.2.2 為restaurantApi應用returnValueCache切麵 150
8.3 小結 152
第9章 確保單例模式的正確實現 153
9.1 通過單元測試瞭解單例模式 154
9.1.1 使用對象字麵量實現單例共享緩存 154
9.1.2 使用模塊實現單例共享緩存 158
9.2 小結 162
第10章 確保工廠模式的正確實現 163
10.1 為工廠編寫單元測試 163
10.2 實現工廠模式 169
10.3 考慮其他工廠類型 171
10.4 小結 171
第11章 確保沙箱模式的正確實現和使用 173
11.1 通過單元測試瞭解沙箱模式 173
11.1.1 創建部件沙箱 174
11.1.2 創建和測試沙箱工具 187
11.1.3 創建與沙箱一起使用的函數 191
11.2 小結 193
第12章 確保裝飾器模式的正確實現 195
12.1 使用測試驅動的方式開發裝飾器 196
12.1.1 為被裝飾的對象編寫一個假對象 197
12.1.2 為錯誤的傳遞編寫測試 198
12.1.3 編寫空白裝飾器 199
12.1.4 添加傳遞功能到裝飾器 200
12.1.5 驗證成功傳遞 202
12.1.6 添加裝飾器的特性 204
12.1.7 通用化裝飾器 210
12.2 小結 211
第13章 確保策略模式的正確實現 213
13.1 通過單元測試瞭解該模式 213
13.1.1 在不使用策略模式的情況下實現transportScheduler 214
13.1.2 使用策略模式實現transportScheduler 216
13.2 小結 227
第14章 確保代理模式的正確實現 229
14.1 通過測試驅動的方式開發代理 230
14.2 小結 245
第15章 確保正確實現可鏈接方法 247
15.1 通過單元測試瞭解該模式 248
15.2 鏈接then方法 255
15.3 小結 257
第Ⅲ部分 測試和編寫高級JavaScript特性
第16章 在無接口語言中遵守接口 261
16.1 瞭解接口的優點 262
16.2 瞭解接口隔離原則 263
16.3 使用測試驅動開發創建契約注冊錶 265
16.3.1 定義契約 266
16.3.2 判斷是否履行瞭契約 267
16.3.3 斷言契約被履行瞭 271
16.3.4 繞過契約執行 273
16.3.5 創建在被返迴(創建)的對象上實施契約的切麵 273
16.4 小結 277
第17章 確保正確的參數類型 279
17.1 瞭解JavaScript無類型參數帶來的機會和風險 280
17.2 擴展ContractRegistry檢查參數 280
17.2.1 界定任務範圍 280
17.2.2 判斷集閤中的所有變量是否都履行瞭它的契約 281
17.2.3 斷言集閤中的所有變量都履行瞭它的契約 289
17.2.4 在切麵中打包參數檢查功能 290
17.3 支持契約庫 292
17.4 綜閤起來 293
17.4.1 創建契約模塊 293
17.4.2 創建應用程序的ContractRegistry 296
17.4.3 為生産發布繞過契約 297
17.5 比較麵嚮切麵的解決方案和靜態解決方案 297
17.5.1 考慮TypeScript的優點 297
17.5.2 考慮切麵的優點 297
17.6 小結 298
第18章 確保正確使用call、apply和bind 299
18.1 瀏覽this是如何綁定的 299
18.1.1 默認綁定 300
18.1.2 隱式綁定 302
18.1.3 new綁定 303
18.1.4 顯式綁定 305
18.2 創建和測試使用call、apply和bind的代碼 305
18.2.1 使用call和apply 305
18.2.2 使用測試驅動開發創建一個Array.prototype.forEach Polyfill 307
18.2.3 使用bind 316
18.3 小結 321
第19章 確保正確使用方法藉用 323
19.1 確保藉用對象符閤需求 324
19.1.1 讓被藉用的函數驗證藉用者的資格 324
19.1.2 嚮被藉用的對象附加切麵 326
19.1.3 使用borrow()方法 329
19.1.4 在ContractRegistry中添加對象驗證器 330
19.2 預期藉用者的副作用 331
19.2.1 考慮被隔離函數的副作用 331
19.2.2 考慮調用其他函數的函數的副作用 332
19.3 預期捐贈者對象的副作用 338
19.4 小結 339
第20章 確保正確使用混閤 341
20.1 創建和使用混閤 343
20.1.1 創建和使用傳統混閤 344
20.1.2 創建和使用函數式混閤 361
20.2 小結 367
第21章 測試高級程序架構 369
21.1 確保觀察者模式的可靠使用 369
21.1.1 檢查觀察者模式 370
21.1.2 增強觀察者模式的可靠性 376
21.2 確保中介者模式的可靠使用 380
21.2.1 瞭解中介者模式 381
21.2.2 增強基於中介者代碼的可靠性 382
21.3 小結 395
第Ⅳ部分 測試中的特殊主題
第22章 測試DOM訪問 399
22.1 對UI進行單元測試 399
22.1.1 檢查難於測試的UI代碼 400
22.1.2 使用TDD創建UI組件 401
22.2 使用分析器優化代碼 411
22.2.1 檢測低效代碼 411
22.2.2 避免不成熟的優化 418
22.3 小結 418
第23章 確保符閤標準 419
23.1 使用ESLint 420
23.1.1 安裝ESLint 420
23.1.2 運行ESLint 424
23.1.3 使用ESLint實施代碼標準 427
23.2 實施架構分離 432
23.2.1 傢庭秘密技術 433
23.2.2 銘記技術 435
23.2.3 不可能任務(Mission Impossible)技術 437
23.2.4 魔術棒(Magic Wand)
技術 441
23.2.5 不要使用調用棧技術 442
23.2.6 其他技術 442
23.2.7 其他架構 442
23.3 小結 443
第Ⅴ部分 總結
第24章 測試驅動開發原則的總結 447
24.1 迴顧值得使用測試驅動開發的原因 447
24.2 練習測試驅動開發 448
24.3 編寫可單元測試的代碼 448
24.4 掌握測試驅動開發的
技術 448
24.4.1 在編碼之前編寫測試 448
24.4.2 保持測試DRY 449
24.4.3 首先測試錯誤條件 449
24.4.4 測試要先易後難 449
24.4.5 具體 449
24.4.6 隻測試一件事情 450
24.4.7 測試數據如同測試一樣重要 450
24.4.8 高效地使用Jasmine 450
24.5 測試本書描述的模式 450
24.5.1 測試麵嚮切麵編程 450
24.5.2 測試對象構造 451
24.5.3 測試迴調 451
24.5.4 測試基於承諾的代碼 451
24.5.5 測試散函數應用程序 451
24.5.6 測試備忘錄模式 452
24.5.7 測試單例模式 452
24.5.8 測試工廠模式 452
24.5.9 測試沙箱 452
24.5.10 測試裝飾器模式 453
24.5.11 測試策略模式 453
24.5.12 測試代理模式 453
24.5.13 測試可鏈接方法 453
24.5.14 測試接口一緻性 453
24.5.15 測試call和apply的
使用 453
24.5.16 測試方法藉用模式 454
24.5.17 測試混閤 454
24.5.18 測試中介者和觀察者模式 454
24.5.19 測試DOM訪問 454
24.5.20 實施架構分離的測試 454
24.6 小結 455
第25章 本書JavaScript習語的總結 457
25.1 迴顧對象 457
25.1.1 可以添加和刪除的對象屬性 457
25.1.2 可以將對象用作詞典 458
25.2 迴顧變量 459
25.2.1 提升變量聲明 459
25.2.2 變量有函數作用域 460
25.3 迴顧函數 463
25.3.1 函數是對象 463
25.3.2 提升函數聲明 463
25.3.3 函數沒有返迴類型 464
25.3.4 函數可以是匿名的 465
25.3.5 函數可以被嵌套 465
25.3.6 函數調用可以使用任意數量的參數 466
25.3.7 函數可以立即被調用 467
25.4 迴顧布爾操作 468
25.4.1 在測試相等性時類型可能會被強製轉換 468
25.4.2 值可以是真或假 469
25.5 小結 469
前言/序言
當我們與開發者同仁分享本書的書名《編寫可靠的JavaScript代碼》時,我們收到瞭如下反饋:
“‘可靠的’和‘JavaScript代碼’這兩個詞現在能放在一塊?”
“這一定是一本非常薄的書。”
“我是否會在書店的小說區域John Grisham最近的驚悚小說附近找到它?”
不,本書不是小說。
我們收到的關於本書書名的反饋錶明瞭一些具有經典的、編譯語言經驗的開發者對於JavaScript的普遍看法:JavaScript被用於創建華麗的作品集網站或者簡單的應用程序,它與任務關鍵的企業應用程序沒有關係。
在過去這種觀點是事實,但現在已經改變瞭。
JavaScript作為一流語言崛起
JavaScript作為野孩子的聲譽是應得的,在接下來的兩個小節中我們將揭示它的一些漏洞。不過,就像被寵壞的繼承者一樣,在繼承瞭傢族事業之後,通過提齣挑戰讓所有人都感到震驚。但最近他變得嚴肅和負責,顯示齣真正偉大的能力。
JavaScript早期僅僅被托付一些短“腳本”任務。任務非常簡單:如果所需的字段未被填充,就將它標記為紅色;如果按鈕被單擊瞭,就應該將另一個頁麵帶入視圖。盡管它的責任有限,但易於相處。到今天為止,大多數程序員使用JavaScript的經驗都是此類。
接著,在重新定義JavaScript的變革中,世界轉嚮瞭Web。這一直是JavaScript遊樂場,當The Old Boys Club的成員在服務器上完成真正的工作時,他就在Web中娛樂自己。
在20世紀90年代末期,當微軟引入iframes和XMLHTTP時,變革開始被阻礙。而當Google在2004年和2005年分彆使Ajax成為Gmail應用程序和Google Maps的一部分時,變革開始崩潰。世界突然注意到當瀏覽器被賦予更多任務時(不隻是顯示服務器分配的內容),Web體驗可以如此豐富。
所以JavaScript被賦予瞭更多的責任,超齣瞭任何人的計劃。JavaScript需要得到幫助。
此時幫助也應運而來,以工具包和框架的形式存在,例如jQuery、 Ext JS、 Ember.js、 Knockout、Backbone和AngularJS。這些有價值的顧問完成瞭所有他們能做的事情,為JavaScript帶來瞭準則和結構。
使用JavaScript編寫真正糟糕的代碼是非常簡單的
問題的部分原因是JavaScript作為頁麵腳本語言存在多年。在那個有限的範圍內,使用全局變量或全局函數並沒有問題。如果變量拼寫錯誤,影響非常有限、也易於追蹤(另外,影響可能是創建瞭另一個全局變量)。如果架構非常草率……那麼有多少架構甚至可以隻存在於一個Web頁麵上呢?
編譯器的缺少隱藏瞭潛在的錯誤。使用C#或Java編寫的服務器端程序在運行之前至少可以保證語法上是正確的。而JavaScript則必須啓動,然後就隻能預祝好運瞭。拼寫錯誤的變量或者調用不存在的函數都可能潛伏在代碼中數月之久,直到遵循瞭特定的執行路徑。
接著就是JavaScript的怪癖,一些可愛的、瘋狂的怪癖。
這個列錶的頂部一定就是==(使用類型強製轉換的相等)和===(不使用類型強製轉換的相等)。這是一個好想法,但是對於主要使用其他語言的程序員來說是如此難以適應!
JavaScript擁有“真”和“假”的概念,它們讓很多人感到糊塗。0是假值,因此多虧瞭類型強製轉換(type coercion),錶達式:
false == '0'
的結果是真。值false被強製轉換成一個數字,也就是0(真被轉換為1)。接下來,字符串‘0’也被強製轉換成數字,也是0,所以錶達式的結果是真。
不過,false == 'false'的結果是假,因為左側的false再次被強製轉換成0,與右側字符串‘false’相比,也被強製轉換成數字。因為‘false’根本不是數字,所以第二個轉換將産生NaN(Not a Number),相等性檢測失敗。
如果聲明瞭下麵的函數:
function letsHaveFun(me, you) {
// Fun things happening between me and you
}
然後調用它,因此:
letsHaveFun(me);
JavaScript將在變量you未定義的情況下執行調用,隻是為瞭開心地看著你與某個不存在的人玩耍。
這個代碼清單可以不斷擴展下去。還有令人吃驚的作用域規則、獨特的“原型”繼承機製、自動的和有時不正確的分號插入、一個對象從另一個完全無關的對象藉用函數的功能等 。
伴隨著全局變量的不請自來、幾乎完全缺少的架構設計、與真理的可疑關係以及比動漫大會上發現的更多的怪癖,JavaScript能做到如此好的地步真是一個奇跡。
無論你相信與否,它在變好之前會變得更糟糕。即使你是正確的,它也可能會非常容易齣現問題。
JavaScript代碼容易被無意間破壞
JavaScript有一種病態的幽默感。在一門穩重的編譯語言中,如果有一行完全正確的調試代碼在生産環境中運行得非常完美,例如:
myVariable = myObject.myProperty;
這時如果不小心碰到瞭鍵盤上的x鍵,那麼它就變成瞭:
myVariable = myObject.myPropxerty;
編譯器就會立即發齣一條嚴厲的消息,警告下次一定要更加小心。而JavaScript則會高興地運行該代碼,並將undefined的值賦給myVariable。
當你希望改變屬性的名稱時,JavaScript喜歡玩捉迷藏。你可能會認為在整個源目錄中搜索.myProperty就可以找到所有需要改動的地方。“不,不,不!”JavaScript笑著說。“你忘瞭搜索['myProperty']。”
實際上,應該使用正則錶達式進行搜索,允許在括號和引號之間含有空格。你曾經這樣做過嗎?我們都沒有。
你還應該搜索下麵這樣的結構:
var prop = 'myProperty';
// . . .
myObject[prop] = something;
即使是如此小的重構也很難完成,因此可以想象錯誤的産生是多麼容易。不適閤重構的代碼幾乎是單詞“脆弱”的定義。
如何纔能避免這些問題呢?如果有一個我們希望在本書進行宣揚並實踐的概念,那麼就是測試驅動開發。在不存在編譯器的情況下,測試是針對錯誤的最佳防禦。
JavaScript也更加適用於按照軟件工程的規則進行開發。實際上,由於JavaScript具有創造性,因此比其他語言更需要這些規則。
我們見過許多開發人員都對這個信息抱著開放的態度,並且希望學習更多相關知識。我們希望你是其中一員。
本書麵嚮的讀者
因為本書不是一本JavaScript入門書籍,所以我們假設你已經有一些JavaScript經驗。下麵勾勒瞭本書理想讀者的特點。
從其他語言轉嚮JavaScript的開發人員
我們的職業生涯都不是從JavaScript開發人員開始的,可能也不是當JavaScript遇到大規模應用開發時纔進入程序開發領域的。
JavaScript與我們曾經使用過的任何語言都大不相同。我們來自於編譯的、靜態類型語言C#的舒適世界。
當我們在保持C#程序員的架構和準則,並擁抱JavaScript的動態特性時,JavaScript就會容易掌握。
如果你具有使用JavaScript之外的語言(例如C#或Java)進行思考和編程的背景的話,本書是適閤你的。數據結構和架構方麵的知識將為你掌握JavaScript的大規模開發提供牢固的基礎。
許多小節都演示瞭C#和Java中的語言特性(例如繼承和接口)是如何對應於JavaScript中的功能的。我們還強調瞭JavaScript和其他語言之間的許多主要區彆,例如作用域規則和類型強製轉換相等性比較。掌握JavaScript功能和特性的相關知識將改善你用JavaScript思考的能力。
本書的另一個關注點是如何將C#和Java開發中更常見的軟件工程概念和實踐應用到JavaScript中,例如設計模式、單元測試和測試驅動開發。閤理的軟件工程可以緩和JavaScript的本性,創建可靠的和可維護的代碼。
具有小規模JavaScript經驗的開發人員
在我們努力為團隊增加具有JavaScript經驗的開發人員時,我們遇到瞭許多候選人,都覺得具有小規模JavaScript開發經驗(例如輸入域驗證和jQuery元素轉換)就值得將“JavaScript”列在簡曆的重要位置。
在麵試中,判斷這樣的候選人不需要花費太多時間:可能在ASP.NET Web Forms應用程序中,他們可以輕鬆地使用按鈕處理程序,但是創建一個JavaScript模塊,並在其中使用防止被外部操作的變量就比較睏難瞭。
隨著機構對JavaScript使用的進一步深化,我們對擁有JavaScript經驗的定義也隨之嚴格。數年之前,如果開發人員有點jQuery經驗,我們就會對他的JavaScript經驗非常滿意瞭。
不過,現在我們需要更多的經驗。使用JavaScript編寫整個應用程序已經不再是鳳毛麟角瞭。在所謂的單頁麵應用(Single-Page Application,SPA)中,JavaScript代碼將組成整個應用程序,與過去瞬間的單擊處理程序相比,現在它承擔著更多的責任。為瞭參與大規模JavaScript應用程序的開發,開發人員必須知道如何以結構化和規定的方式使用該語言,並同時使用它的許多獨特功能和特性。
通過本書的樣例,我們希望你——小規模JavaScript開發人員——能夠參與大規模JavaScript應用程序的開發。
負責為新項目挑選編程語言的開發人員
可能你已經聽過這個諺語:“沒有人會因為購買IBM産品而被解雇”。這個諺語反映瞭一種感覺:在為IT項目選擇技術閤作夥伴時,選擇穩定的、有信譽的公司(例如IBM)是不會受到質疑的。即使項目費用超支、逾期或完全失敗,選擇IBM也是無可指責的。
如果你正處於為新應用選擇開發語言的位置,那麼就處於與IT管理者選擇技術閤作夥伴一樣的位置。有許多具有悠久曆史並經過眾人嘗試和驗證的語言,例如C#和Java,它們都是由大型、穩定的技術公司所支持的,已經被用於構建Web和桌麵應用超過十年。沒有人會因為選擇C#被解雇。
從新程序設計項目的安全選擇來看,尤其是企業級的項目,JavaScript明顯與C#不同。JavaScript不是一門成熟、穩定、正式的編程語言。
與C#和Java這樣的語言相比,它沒有大規模軟件項目的、長期的成功記錄。這不是說使用C#和Java的項目就一定成功。不過,如果使用瞭其中一種語言的項目不成功,語言的選擇可能不會被包含在失敗的原因中。
如我們在之前小節中所提到的,使用JavaScript非常容易編寫齣災難性的代碼。這為它帶來瞭一點糟糕的名聲,降低瞭選擇它的可能性。
不應該因為JavaScript的聲譽而自動將它排除在項目的考慮之外,因為我們可以從它的強大功能中獲益。Node.js——一個服務器端的JavaScript引擎——是輕量級的並且高度可伸縮的;對於實時和數據敏感應用程序來說是非常完美的選擇。JavaScript可以被用於在瀏覽器中創建富用戶界麵。客戶端框架(例如Ember和AngularJS)可以被用於構建完整的、基於瀏覽器的應用程序,可以通過將展示邏輯轉移到客戶端的方式減輕Web服務器的負擔。
盡管我們不能保證它會成功,但是接下來的章節將展示如何通過應用我們在自己項目中所學到的教訓,在下一個項目選擇JavaScript時降低風險。
成功不是偶然的,尤其是在使用JavaScript時。它要求牢固掌握軟件工程原則,這是第1章的主題。
本書的組織結構
我們將本書劃分為5個部分。
第Ⅰ部分“奠定堅實的基礎”涵蓋瞭軟件工程的關鍵概念,例如SOLID和DRY原則,還討論瞭單元測試和測試驅動開發的優點。第Ⅰ部分還介紹瞭本書使用的工具和JavaScript庫。最後,討論瞭JavaScript中的對象和它們的可測試性。
在第Ⅱ部分“測試基於模式的代碼”中,我們描述並使用測試驅動開發創建瞭幾個有用的代碼模式。其中一些模式(例如單例)可能與其他你所熟悉的語言中的模式類似。其他(例如承諾)主要是與JavaScript相關的。
第Ⅲ部分“測試和編寫高級JavaScript特性”描述瞭如何使用和測試JavaScript語言更高級的特性。它還涵蓋瞭使用瞭高級編程架構的應用的創建和測試,例如中介者和觀察者模式。
第Ⅳ部分“測試中的特殊主題”提供瞭測試DOM操作的樣例,還演示瞭用於增強代碼標準的靜態分析工具的使用。
第Ⅴ部分“總結”迴顧瞭測試驅動開發的概念,還展示瞭一些本書用到的JavaScript習語。
使用本書所需的工具
為瞭運行本書的樣例,需要使用下列工具:
● 文本編輯器
● Web瀏覽器
樣例的源代碼可以從Wrox網站下載:
www.wrox.com/go/reliablejavascript
基於本書的開源軟件可以在GitHub上找到:
www.github.com/reliablejavascript
源代碼
當你瀏覽本書的樣例時,可能會選擇手動輸入所有代碼,或者使用隨書提供的源代碼。本書使用的所有源代碼都可以從www.wrox.com和www.tupwk.com.cn/downpage下載。對於本書來說,代碼下載文件在下麵網址的Download Code選項卡中:
www.wrox.com/go/reliablejavascript
也可以在www.wrox.com中通過ISBN搜索本書找到代碼。所有當前Wrox圖書的代碼下載的完整文件列錶在www.wrox.com/dynamic/books/download.aspx 中。
www.wrox.com的大多數代碼都采用.ZIP、.RAR或者適用於特定平颱的類似歸檔模式進行瞭壓縮。下載瞭代碼之後,隻需要使用適當的壓縮工具解壓即可。
注意:
因為許多書都有相似的書名,所以你可能發現使用ISBN搜索是最容易的;本書英文版的ISBN是978-1-119-02872-7。
勘誤錶
盡管我們竭盡所能來確保在正文和代碼中沒有錯誤,但人無完人,錯誤難免會發生。如果你在Wrox齣版的書中發現瞭錯誤(例如拼寫錯誤或代碼錯誤),我們將非常感謝你的反饋。發送勘誤錶將節省其他讀者的時間,同時也會幫助我們提供更高質量的信息。
要找到本書的勘誤頁麵,可以進入www.wrox.com,使用Search搜索框或書名列錶找到本書,然後在本書的詳細信息頁麵上單擊Book Errata鏈接。在這個頁麵上可以查看為本書提交的、Wrox編輯粘貼上去的所有錯誤。完整的書名列錶(包括每本書的勘誤錶)也可以從www.wrox.com/misc-pages/booklist.shtml上獲得。
如果在本書的勘誤頁麵上沒有看到你發現的錯誤,則可以到www.wrox.com/contact/ techsupport.shtml 上填寫錶單,把你發現的錯誤發給我們。我們會檢查這些信息,如果屬實,就把它添加到本書的勘誤頁麵上,並在本書隨後的版本中更正錯誤。
p2p.wrox.com
如果想和作者或同行進行討論,請加入p2p.wrox.com 上的P2P論壇。該論壇是一個基於Web的係統,你可以發布有關Wrox圖書及相關技術的消息,與其他讀者或技術人員交流。該論壇提供瞭訂閱功能,當你感興趣的主題有新帖子發布時,係統會郵件通知。Wrox的作者、編輯、其他業界專傢和像你一樣的讀者都會齣現在這些論壇中。
在p2p.wrox.com網站上,你會找到很多不同的論壇,它們不但有助於你閱讀本書,還有助於你開發自己的應用程序。加入論壇的步驟如下:
(1) 進入p2p.wrox.com,單擊Register鏈接。
(2) 閱讀使用條款,然後單擊Agree按鈕。
(3) 填寫加入該論壇必需的信息和其他你願意提供的信息,單擊Submit按鈕。
(4) 你將收到一封電子郵件,描述如何驗證你的賬戶和完成加入過程。
加入之後,就可以發布新的消息和迴復其他用戶發布的消息。可以隨時在Web上閱讀論壇裏的消息。如果想讓某個論壇的新消息以電子郵件的方式發給你,可以單擊論壇列錶中論壇名稱旁邊的Subscribe to this Forum圖標。
要瞭解如何使用Wrox P2P的更多信息,請閱讀P2P FAQ,其中迴答瞭論壇軟件如何使用的問題,以及許多與P2P和Wrox圖書相關的問題。要閱讀FAQ,單擊任何P2P頁麵上的FAQ鏈接即可。
……