課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

110
講師:Jollen Chen <[email protected]> Bloghttp://www.jollen.org/blog 課程:http://www.moko365.com 課程專案:鴻海科技集團贊助課程 課程名稱:屏雲時代來臨 教你HTML5六時打通關(3) 課程期:2013/3/13 () 課程時間:10:00~17:00 講義版本:v2.3.0 八屏一雲時代來臨 教你HTML5六小時打通關(3) Copyright (C) 2013 Moko365 Inc. All Rights Reserved. 本教材由仕橙3G教室製作與維護 1

Transcript of 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

Page 1: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

講師:Jollen Chen <[email protected]>Blog:http://www.jollen.org/blog課程:http://www.moko365.com

課程專案:鴻海科技集團贊助課程課程名稱:⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關(3)課程⽇日期:2013/3/13 (三)課程時間:10:00~17:00講義版本:v2.3.0

八屏一雲時代來臨 教你HTML5六小時打通關(3)

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

本教材由仕橙3G教室製作與維護

1

Page 2: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

http://www.moko365.com/enterprise/html5-nodejs

2

Page 3: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

LICENSE NOTICEThis work is licensed under a Creative Commons Attribution-NoDerivs 3.0 Unported License.

You are free:• to Share — to copy, distribute and transmit the work• to make commercial use of the work

Under the following conditions:• Attribution — You must attribute the work in the manner specified by the author or licensor (but not in any

way that suggests that they endorse you or your use of the work).• No Derivative Works — You may not alter, transform, or build upon this work.

With the understanding that:

• Waiver — Any of the above conditions can be waived if you get permission from the copyright holder.• Public Domain — Where the work or any of its elements is in the public domain under applicable law, that

status is in no way affected by the license.• Other Rights — In no way are any of the following rights affected by the license:◦ Your fair dealing or fair use rights, or other applicable copyright exceptions and limitations;◦ The author's moral rights;◦ Rights other persons may have either in the work itself or in how the work is used, such as publicity or

privacy rights.• Notice — For any reuse or distribution, you must make clear to others the license terms of this work. The

best way to do this is with a link to this web page.

3

Page 4: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

本教材由仕橙3G教室製作與維護 仕橙研策科技有限公司版權所有

Data Push 架構設計

4

Page 5: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Live Messenger

5

Page 6: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

基本功能聊天室 (Chat)

通訊錄 (Contact)

圖⽚片傳送 (File Transfer)

6

Page 7: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

基礎架構與建設

Feature Architect Infrastructure

聊天室 Real-time Data Push Device & Cloud

通訊錄 Database Device

圖片傳送 Real-time Data Push Device & Cloud

7

Page 8: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Device/Cloud InteractiveData Pull

Data Push

Asynchronous Data Pull

8

Page 9: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Data PullClient Server

Synchronous

Return

9

Page 10: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Asynchronous Data Pull (AJAX)Client Server

Return

Async Message

10

Page 11: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Data PushClient Server

Create WebSocket

Return

Data

11

Page 12: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Data Push using WebSocket (HTML5)

Client Server

Create WebSocket

onopen()

onmessage()

12

Page 13: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

WebSocket 與 HTTP API

Native

BrowserWebSocket

Socket (TCP/IP)

HTML5HTTP API

13

Page 14: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

HTTP API 與 WebSocket 是主流

Application Layer Language Technology

HTML5 Front-end HTML HTTP API

Browser JavaScript WebSocket

Native Apps C/C++/Java Socket

14

Page 15: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

HTTP APIThe HTTP Server API enables applications to communicate over HTTP.

Servers will receive HTTP requests, and send HTTP responses.

With SSL support.

In the form of URL, one of the format of URI.

15

Page 16: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

HTTP API 的形式

http://localhost:8888/send?m=hello&u=jollen

API Query string

16

Page 17: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

HTTP API 的格式

http://localhost:8888/send?m=hello&u=jollen

API Query string

Pathname URL

17

Page 18: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Client Requests

GET /index.html HTTP/1.1Host: www.moko365.com

18

Page 19: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Server Responses HTTP/1.1 200 OK Date: Sun, 10 June 2012 00:00:00 GMT Server: Apache/1.3.3.7 (Unix) (Red-Hat/Linux) Last-Modified: Fri, 01 June 2012 22:11:55 GMT Etag: "3481d-2c6-7d1ab33e" Accept-Ranges: none Content-Length: 568 Connection: close Content-Type: text/html; charset=UTF-8

...

19

Page 20: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Response ContentHTML Document

XML Document

JSON Data

Base64 encode (⽤用於 Binary 檔案)

亦可⾃自定

20

Page 21: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Open API 定義Open API is over HTTP:

➡ http://svn.moko365.com:8888/start,連接伺服器並接收即時訊息

➡ http://svn.moko365.com:8888/send,送出⽂文字訊息

API 參數 (Query String) 的部份後續再做定義

以 JSON 格式打包回傳資料

21

Page 22: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Apache with NodeJS

Apache(Document)

index.html

NodeJS(Application)

APIs Platform

WebSocket Connection

DataPush

http://svn.moko365.com:8080/send

http://svn.moko365.com:8080/start

22

Page 23: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

本教材由仕橙3G教室製作與維護 仕橙研策科技有限公司版權所有

使用 JSON

23

Page 24: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

JSON 簡介JSON (play /ˈdʒeɪsən/), or

JavaScript Object Notation

a lightweight text-based open standard designed for human-readable data interchange.

It is derived from the JavaScript scripting language for representing simple data structures and associative arrays, called objects.

Despite its relationship to JavaScript, it is language-independent, with parsers available for many languages.

Source: http://en.wikipedia.org/wiki/JSON

24

Page 25: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Basic TypesNumber (type not specified, but in practice double precision floating-point format, as this is how JavaScript in Web browsers treats it)

String (double-quoted Unicode (UTF-8 by default), with backslash escaping)

Boolean (true or false)

Array (an ordered sequence of values, comma-separated and enclosed in square brackets; the values do not need to be of the same type)

Object (an unordered collection of key:value pairs with the ':' character separating the key and the value, comma-separated and enclosed in curly braces; the keys must be strings and should be distinct from each other)

null (empty)

25

Page 26: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Schema

var o = [ 100, 500, 300, 200, 400 ]

Array

Array (an ordered sequence of values, comma-separated and enclosed in square brackets; the values do not need to be of the same type)

26

Page 27: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Schema

var o ={

height: 100, width: 500,

}

Single RowObject

Object (an unordered collection of key:value pairs with the ':' character separating the key and the value, comma-separated and enclosed in curly braces; the keys must be strings and should be distinct from each other)

27

Page 28: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Example 1[! {

! ! color: "red",

! ! value: "#f00"

! },! {

! ! color: "green",

! ! value: "#0f0"! },! {

! ! color: "blue",

! ! value: "#00f"! },! {

! ! color: "cyan",

! ! value: "#0ff"! }

]

color

red

green

blue

cyan

value

#f00

#0f0

#00f

#0ff

28

Page 29: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Example 2[! {! ! name: "Jollen",! ! score: 80! },! {! ! name: "Paul",! ! score: 170! },! {! ! name: "Peter",! ! score: 250! },! {! ! name: "Ellaine",! ! score: 580! }

]

name

Jollen

Paul

Peter

Ellaine

score

80

170

250

580

29

Page 30: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Example 2

{! "id": "0001",! "type": "donut",! "name": "Cake",! "image":! ! {! ! ! "url": "images/0001.jpg",! ! ! "width": 200,! ! ! "height": 200! ! }}

id type name image.url image.width image.height

1 donut Cake images/0001.jpg 200 200

30

Page 31: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Android App 解析 JSON使⽤用 org.json.*;

import org.json.JSONArray;import org.json.JSONException;import org.json.JSONObject;

[! { "name": “jollen”, "age": “30”, "address": “Unknown”},! { "name": “Paul”, "age": “30”, "address": “Unknown”},! { "name": “Peter”, "age": “30”, "address": “Unknown”}! ]

31

Page 32: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

範例 private void parseJSON() { // Download JSON cache file String JSONCache = “simple.json”;

try { mJsonArray = new JSONArray(JSONCache); } catch (JSONException e) { e.printStackTrace(); }

for (int i = 0; i < mJsonArray.length(); i++) { try { JSONObject jsonObject = mJsonArray.getJSONObject(i); String url = jsonObject.getString("name"); String expires = jsonObject.getString("age"); String tags = jsonObject.getString("address"); } catch (JSONException e) { // TODO Auto-generated catch block e.printStackTrace(); } } }

32

Page 33: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

JSON Stringify and Parse

var o = [ 15 ]; // Array (type)

var o = "[ 15 ]"; // string

[ 15 ] --> "[ 15 ]" // Stringify: JSON.stringify()“[ 15 ]” --> [ 15 ] // Parse: JSON.parse()

33

Page 34: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Platform: Open APIAPI: Get prefetch list

➡ http://singletoapp.com/jollen-php-json

Return (JSON):”

➡ “url”: The prefetch URL

➡ “expires”: Document expire

➡ “tag”: Keywords

34

Page 35: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

JavaScript 解析 JSON使⽤用 json.js (json2.js)

➡ http://www.JSON.org/js.html

Open source JSON parser for JavaScript

35

Page 36: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

JSON+jQuery TmplMVC

➡ Model: Server

➡ View: Device (Client)

➡ Control: Server

36

Page 37: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

範例<html><head><title>Parsing Message using JSON in JavaScript</title><script language="javascript" src="json.js"></script><script language="javascript" >var students = { "ClassA" : [! { "name": "jollen", "age": “30”, "address": "Unknown"},! { "name": "Paul", "age": “30”, "address": "Unknown"},! { "name": "Peter", "age": “30”, "address": "Unknown"}! ] }var i = 0var arrayObject = new Array();

for(i = 0;i < students.ClassA.length; i++){ arrayObject.push(students.ClassA[i].name); arrayObject.push(students.ClassA[i].age); arrayObject.push(students.ClassA[i].address);}

alert("Parsing JSON Message Example ");alert(arrayObject.toJSONString().parseJSON());</script>

</head><body> Parsing Message using JSON in JavaScript</body></html>

37

Page 38: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Javascript 與 JSON 實例使⽤用 Javascript 解析 JSON

➡ JSON 的優點在此完全展現

搭配 jquery.tmpl.js 使⽤用

➡ https://github.com/jquery/jquery-tmpl

<script>var movies = [ { Name: "Meet Joe Black", Languages: ["French"] }, { Name: "The Mighty", Languages: [] }, { Name: "City Hunter", Languages: ["Mandarin", "Cantonese"] }];

/* Render the template with the movies data */$( "#movieTemplate" ).tmpl( movies ) .appendTo( "#movieList" );</script>

JSON

38

Page 39: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Table 列表: Javascript+JSON<!DOCTYPE html><html><head> <script src="http://code.jquery.com/jquery-latest.min.js"></script> <script src="http://ajax.microsoft.com/ajax/jquery.templates/beta1/jquery.tmpl.min.js"> </script> <link rel="stylesheet" type="text/css" media="all" href="style2.css" /></head><body> <script id="movieTemplate" type="text/x-jquery-tmpl"> ! ! <tr>! ! ! <td>{id}</td>! ! ! <td>${Languages}</td>! ! ! <td>${Name}</td>! ! ! <td>{image.width}</td>! ! ! <td>{image.height}</td>! ! ! <td>{image.url}</td>! ! </tr></script>

39

Page 40: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

cont...<div>! <table class="dataTable" id="movieList">! ! <tr>! ! ! <th>id</th>! ! ! <th>語⾔言</th>! ! ! <th>名字</th>! ! ! <th>image.width</th>! ! ! <th>image.height</th>! ! ! <th>image.url</th>! ! </tr>! </table></div>

<script>var movies = [ { Name: "Meet Joe Black", Languages: ["French"] }, { Name: "The Mighty", Languages: [] }, { Name: "City Hunter", Languages: ["Mandarin", "Cantonese"] }];

/* Render the template with the movies data */$( "#movieTemplate" ).tmpl( movies ) .appendTo( "#movieList" );</script>

</body></html>

40

Page 41: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

顯⽰示結果

41

Page 42: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

JSON 的未來性第⼀一代 Browser

➡ HTML Browser

➡ All from Internet

第⼆二代 Browser

➡ JSON Browser

➡ Local: HTML5 Tempalte/CSS3/JavaScript Library

➡ Data in JSON format comes from Server side

42

Page 43: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

本教材由仕橙3G教室製作與維護 仕橙研策科技有限公司版權所有

使用 HTML5 的 WebSocket

43

Page 44: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

關於 “WebSocket” 物件注意瀏覽器的⽀支援性

使⽤用 DOM 的 “WebSocket” 物件

採⽤用 JavaScript 撰寫程式碼

推薦的⼊入⾨門⽂文章

➡ http://www.html5rocks.com/en/tutorials/websockets/basics/

➡ https://developer.mozilla.org/en-US/docs/WebSockets

44

Page 45: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

第⼀一次寫 WebSocket 8 <script type="text/javascript"> 9 function WebSocketTest() 10 { 11 if ("WebSocket" in window) 12 { 13 // Let us open a web socket 14 var ws = new WebSocket("ws://svn.moko365.com:8080/", "echo-protocol"); 15 ws.onopen = function(evt) 16 { 17 alert("open"); 18 }; 19 ws.onclose = function(evt) 20 { 21 alert("close"); 22 }; 23 } 24 else 25 { 26 // The browser doesn't support WebSocket 27 alert("WebSocket NOT supported by your Browser!"); 28 } 29 } 30 </script>

45

Page 46: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

WebSocket:瀏覽器的⽀支援性請參考 http://en.wikipedia.org/wiki/WebSocket

46

Page 47: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

主要瀏覽器的 WebSocket ⽀支援Firefox 6 以後

Google Chrome 14 以後

Internet Explorer 10 Developer Preview 以後

Opera 11 以後⽀支援舊版 WebSocket 實作

Safari 5 以後⽀支援舊版 WebSocket 實作

iOS 4.2 以後⽀支援舊版 WebSocket 實作

Android 4.x 內建瀏覽器不⽀支援 WebSocket

47

Page 48: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

本教材由仕橙3G教室製作與維護 仕橙研策科技有限公司版權所有

NodeJS 與 Open API

48

Page 49: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Nonblocking I/O

49

Page 50: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

hello.js

var http = require('http');

http.createServer(function (req, res) { res.writeHead(200, {'Content-Type': 'text/html'}); res.end('<h1>Hello World</h1>\n');}).listen(1234, '127.0.0.1');console.log('Server running at http://127.0.0.1:1234/');

50

Page 51: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

執⾏行 hello.js

% node hello.jsServer running at http://127.0.0.1:1234/

51

Page 52: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

NodeJS 的 HTTP APIs

var http = require('http');

http.createServer(function (req, res) { res.writeHead(200, {'Content-Type': 'text/html'}); res.end('<h1>Hello World</h1>\n');}).listen(1234, '127.0.0.1');console.log('Server running at http://127.0.0.1:1234/');

http.createServer([requestListener])

52

Page 53: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

requestListener

var http = require('http');

http.createServer(function (req, res) { res.writeHead(200, {'Content-Type': 'text/html'}); res.end('<h1>Hello World</h1>\n');}).listen(1234, '127.0.0.1');console.log('Server running at http://127.0.0.1:1234/');

function (request, response) { }

53

Page 54: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

HTTP Headersvar http = require('http');

http.createServer(function (req, res) { res.writeHead(200, {'Content-Type': 'text/html'}); res.end('<h1>Hello World</h1>\n');}).listen(1234, '127.0.0.1');console.log('Server running at http://127.0.0.1:1234/');

{ 'content-length': '123', 'content-type': 'text/plain', 'connection': 'keep-alive', 'accept': '*/*' }

54

Page 55: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

HTTP Headersvar http = require('http');

http.createServer(function (req, res) { res.writeHead(200, {'Content-Type': 'text/html'}); res.end('<h1>Hello World</h1>\n');}).listen(1234, '127.0.0.1');console.log('Server running at http://127.0.0.1:1234/');

server.listen(port, [hostname], [callback])

55

Page 56: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Server PushServer Push 的重要性遠勝於 Client Pull

➡ Real-Time Web Application

使⽤用 NodeJs + Web Socket

Web Socket 是 HTML5 的新技術

56

Page 57: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Web Socket 的⽤用途Web 的 Socket

Client 建⽴立⼀一個連線通道 (Socket) 到 Web Server

“using NodeJS will push the notification to the clients which are connected to this server through Web Socket”

57

Page 58: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Push ServerClient 與 Server 端的實作

Client:

➡ HTML5 App (⼿手機端)

➡ 建⽴立 WebSocket 到 Server

Server:

➡ Server 以 JSON 推送資料給 Client

➡ 不使⽤用 Apache Server、改⽤用 NodeJS Server

➡ NodeJS 可搭配 Apache+PHP

58

Page 59: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Client: 建⽴立 WebSocket 連線var trigger = "updateContent";

$(document).ready(function(){ host = "localhost:8000"; conn = new WebSocket("ws://"+host+"/"); conn.onmessage = function(evt) { // Make an Ajax call to the server to update the content if (evt.data == "update"){ // Call the trigger function when there is an update window[trigger](); } };

conn.onerror = function() { };

conn.onclose = function() { conn = false; };

conn.onopen = function() { // alert("You are connected"); postMessage("You are connected"); }; }

59

Page 60: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Server: 啟動並監聽 WebSocketvar server = ws.createServer({ server: httpServer});

server.addListener("listening", function(){ sys.log("Listening for connections.");});

// Handle WebSocket Requestsserver.addListener("connection", function(conn){ console.log('[*] open');

conn.addListener("message", function(message){ if (message == 'close') { console.log('[-] close requested') conn.close(); } else { console.log('[+] ', (new Buffer(message)).inspect()); server.broadcast("update"); } }); conn.addListener("close", function(){ console.log('[*] close'); })});

server.addListener("disconnect", function(conn){ });

server.listen(8000);

60

Page 61: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Routers

http://localhost:8888/start?u=android&m=moko365

url.parse(string).pathname url.parse(string).query

querystring(string)["u"]

querystring(string)["m"]

61

Page 62: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

start.js

var http = require("http");var url = require("url");

function start() { function onRequest(request, response) { var pathname = url.parse(request.url).pathname; console.log("Request for " + pathname + " received."); response.writeHead(200, {"Content-Type": "text/plain"}); response.write("Hello World"); response.end(); }

http.createServer(onRequest).listen(8888); console.log("Server has started.");}

exports.start = start;

62

Page 63: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

route.js

function route(pathname) { console.log("About to route a request for " + pathname);}

exports.route = route;

63

Page 64: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Revision 2 of start.jsvar http = require("http");var url = require("url");

function start(route) { function onRequest(request, response) { var pathname = url.parse(request.url).pathname; console.log("Request for " + pathname + " received."); route(pathname);

response.writeHead(200, {"Content-Type": "text/plain"}); response.write("Hello World"); response.end(); }

http.createServer(onRequest).listen(8888); console.log("Server has started.");}

exports.start = start;

64

Page 65: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

index.jsvar server = require("./server");var router = require("./router");

server.start(router.route);

$ node index.js

65

Page 66: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

使⽤用 Request Handler

var server = require("./server");var router = require("./router");var requestHandlers = require("./requestHandlers");

var handle = {}handle["/"] = requestHandlers.start;handle["/start"] = requestHandlers.start;

server.start(router.route, handle);

66

Page 67: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Revision 3 of start.jsvar http = require("http");var url = require("url");

function start(router, handle) { function onRequest(request, response) { var pathname = url.parse(request.url).pathname; console.log("Request for " + pathname + " received."); route(handle, pathname);

response.writeHead(200, {"Content-Type": "text/plain"}); response.write("Hello World"); response.end(); }

http.createServer(onRequest).listen(8888); console.log("Server has started.");}

exports.start = start;

67

Page 68: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Revision 2 of route.jsfunction route(handle, pathname) { console.log("About to route a request for " + pathname); if (typeof handle[pathname] === 'function') { handle[pathname](); } else { console.log("No request handler found for " + pathname); }}

exports.route = route;

68

Page 69: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Revision 3 of route.jsfunction route(handle, pathname) { console.log("About to route a request for " + pathname); if (typeof handle[pathname] === 'function') { return handle[pathname](); } else { console.log("No request handler found for " + pathname); return “Not found”; }}

exports.route = route;

69

Page 70: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Revision 4 of start.jsvar http = require("http");var url = require("url");

function start(router, handle) { function onRequest(request, response) { var pathname = url.parse(request.url).pathname; console.log("Request for " + pathname + " received."); response.writeHead(200, {"Content-Type": "text/plain"}); var respond = route(handle, pathname); response.write(respond); response.end(); }

http.createServer(onRequest).listen(8888); console.log("Server has started.");}

exports.start = start;

70

Page 71: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

進階 NodeJS 技術Non-blocking requests

Node.js process

Spawn child process

Proxying Node.js

Protocol parser

Advanced I/O handling

技術發展性

➡ Native service /daemon/ server -> Nodejs

➡ Hardware service is web service

71

Page 72: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

本教材由仕橙3G教室製作與維護 仕橙研策科技有限公司版權所有

Device & Cloud 整合

72

Page 73: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

⼿手機聊天:Device Side<!DOCTYPE html><head><script type='text/javascript' src="./json2.js"></script><script type='text/javascript' src="./jquery.min.js"></script><script type='text/javascript' src="./jquery.websocket.js?v=0.2.2"></script></head><body><div id="message"></div>

<div id="admin"><form method="GET" action="http://svn.moko365.com:8080/send"><input type="hidden" name="u" value="jollen" /><input id="msg" type="text" name="m" value="Input message" /><button type="submit" id="send">Send</button></form></div>

<script type="text/javascript"> $("#message").createWebSocket();</script></body></html>

DOM is built on full filename

73

Page 74: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

傳送聊天訊息<!DOCTYPE html><head><script type='text/javascript' src="./json2.js"></script><script type='text/javascript' src="./jquery.min.js"></script><script type='text/javascript' src="./jquery.websocket.js?v=0.2.1"></script></head><body><div id="message"></div>

<div id="admin"><form method="GET" action="http://svn.moko365.com:8080/send"><input type="hidden" name="u" value="jollen" /><input id="msg" type="text" name="m" value="Input message" /><button type="submit" id="send">Send</button></form></div>

<script type="text/javascript"> $("#message").createWebSocket();</script></body></html>

74

Page 75: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

HTTP GETGET 與 POST ⼆二種⽅方式

GET 以 URL 傳遞

<form method="GET" action="http://svn.moko365.com:8080/send"><input type="hidden" name="u" value="jollen" /><input id="msg" type="text" name="m" value="Input message" /><button type="submit" id="send">Send</button></form>

http://svn.moko365.com:8080/send?u=jollen&m=hello

75

Page 76: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

使⽤用 Ajax Submit<div id="message"></div><script type="text/javascript">$(document).ready(function(){! $("#message").createWebSocket();! initSubmitForm();});

var initSubmitForm = function () { $("#submit_form").submit(function () { var $form = $("#submit_form"); var $submit = $("#submit"); $.ajax({ url: $form.attr("action") + "send", type: "GET", dataType: "json", data: {! ! ! ! m: $("#text").val(),! ! ! ! u: $("#username").val(), }, }); return false; }); };</script>

76

Page 77: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

NodeJS 如何處理 Query Stringvar querystring = require('querystring');

/** * Global variables */var history = [ ];

function send(response, query, clients) { console.log("Handler 'send' is started."); console.log("Query string is: " + query);

var parsedstring = querystring.parse(query);

var obj = { message: parsedstring.m, username: parsedstring.u, timestamp: (new Date()).getTime() };

history.push(obj);}

77

Page 78: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

細說 createServer()第3⾏行

➡ 呼叫http模組的createServer()函數來建⽴立⼀一個Web server

➡ reateServer()執⾏行成功後傳回Web server物件

➡ 參數requestListener是⼀一個Request function,⽤用來處理request事件

1 var http = require('http'); 2 3 var httpServer = http.createServer(function (req, res) { 4 res.writeHead(200, {'Content-Type': 'text/html'}); 5 res.end('<h1>Hello World</h1>\n'); 6 }); 7 8 httpServer.listen(1234, '127.0.0.1'); 9 10 console.log('Server running at http://127.0.0.1:1234/');

78

Page 79: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Request Callback當request事件發⽣生時,Request function將被Callback

➡ req:http.ServerRequest的實例化(instance)

➡ res:http.ServerResponse的實例化

79

Page 80: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

NodeJS 模組化JavaScript⽐比較講求模組化

將Web server的部份獨⽴立成⼀一個模組

➡ index.js:主程式

➡ server.js:啟動Web server的模組

80

Page 81: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

File: server.js只能匯出函數

1 var http = require("http"); 2 3 function start() { 4 function onRequest(request, response) { 5 console.log("Request for " + pathname + " received."); 6 7 response.writeHead(200, {"Content-Type": "text/plain"}); 8 response.write("Hello World"); 9 response.end(); 10 } 11 12 http.createServer(onRequest).listen(8888); 13 console.log("Server has started."); 14 } 15 16 // Export functions 17 exports.start = start;

81

Page 82: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

NodeJS 模組的觀念並不需要將函數寫成模組

Client-side與Server-side都能⽤用JavaScript語⾔言開發軟體,沒想到觀念與設計模組並不同,並無法完全相通

exports是NodeJS的⼀一個Global object(但並不完全是),⽤用途就是匯出該模組裡的函數。

82

Page 83: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Callback FunctionsNodeJS的事件處理機制,採⽤用典型的Callback functions(回呼函數)做法

83

Page 84: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Routing處理URL(HTTP Request)與Query string的核⼼心觀念

Client-side的JavaScript不太會使⽤用Route的觀念,這是Server-side JavaScript的必殺技之⼀一

主要⽤用途是處理URL,所以我們利⽤用url模組來取出URL裡的pathname,並將pathname交給route()函數

84

Page 85: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

File: server.js 1 var http = require("http"); 2 var url = require("url"); 3 4 function start(route) { 5 function onRequest(request, response) { 6 var pathname = url.parse(request.url).pathname; 7 console.log("Request for " + pathname + " received."); 8 console.log("Request url: " + request.url); 9 10 route(pathname); 11 12 response.writeHead(200, {"Content-Type": "text/plain"}); 13 response.write("Hello World"); 14 response.end(); 15 } 16 17 http.createServer(onRequest).listen(8888); 18 console.log("Server has started."); 19 } 20 21 // Export functions 22 exports.start = start;

85

Page 86: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

函數即物件函數就是物件

把route物件交給start()函數,讓start()函數去使⽤用物件

直接在start()裡呼叫route()函數也可以,為什麼不這樣做?

因為這不是JavaScript的觀念,倒是有點像是標準C語⾔言呼叫函數的觀念,同時也會降低程式碼的可維護性

86

Page 87: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Request HandlerFile: index.js

1 var server = require("./server"); 2 var router = require("./router"); 3 var handlers = require("./requestHandlers"); 4 5 // 使⽤用 Object 來對應 pathname 與 request handlers 6 var handlers = { 7 "/": handlers.start, 8 "/start": handlers.start, 9 "/send": handlers.send 10 }; 11 12 // 傳遞 request handler 13 server.start(router.route, handlers);

87

Page 88: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

cont...模組匯出start()與send()函數

分別處理相對應的pathname

主程式在第6⾏行到第10⾏行的地⽅方,利⽤用handlers物件來對應這個關係

呼叫start()時,再將handlers物件傳⼊入

88

Page 89: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

再探 JavaScript 物件模型JavaScript雖然不是物件導向式語⾔言,但仍要以物件的觀念來撰寫

將handlers以var定義成object

很多時候,或許也能以associative array來實作,但並不是很建議

89

Page 90: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

HTTP API許多Developer Platform,像是:Google API、Facebook API等,提供了許多好⽤用的API供開發者使⽤用

基於HTTP的API將是HTML5應⽤用開發的核⼼心技術。

呼叫HTTP API的⽅方式,可使⽤用GET與POST⼆二種⽅方式,這⼆二種⽅方式都是定義在HTTP裡的標準

⽤用⼾戶端(Caller)是瀏覽器

以Android的WebView組件,來製作與NodeJS整合的應⽤用程式

90

Page 91: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Open API 定義Open API is over HTTP:

➡ http://svn.moko365.com:8888/start,連接伺服器並接收即時訊息

➡ http://svn.moko365.com:8888/send,送出⽂文字訊息

分別要處理⼆二個pathname如下:

➡ /start,由start() Handler處理

➡ /send,由send() Handler處理

91

Page 92: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

Open API 參數說明/start,建⽴立與Client的WebSocket連線。Query string的參數:

➡ username,使⽤用者名稱

/send,送出訊息。Query string的參數:

➡ m,訊息主體

➡ u,username

➡ to,對某⼈人說話

92

Page 93: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

回傳的 JSON Data

{! "type":"message",! "data":!{! ! "message":"jollen",! ! "username":"jollen",! ! "timestamp":1351050127283! ! }}

93

Page 94: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

⼀一個 Use Case1. 使⽤用者點擊ItsApp,應⽤用程式⾃自動連線到http://itsapp.moko365.com/api/start?username=jollen

2. Server建⽴立與⼿手機的WebSocket連線

3. 使⽤用者進⼊入主畫⾯面,使⽤用者可輸⼊入訊息;並且,可透過WebSocket即時更新訊息

4. 使⽤用者輸⼊入訊息,並呼叫API:http://itsapp.moko365.com/send?m=hello

5. 伺服器收到⽤用⼾戶端訊息,透過WebSocket將訊息Push給所有的⽤用⼾戶端

94

Page 95: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

解析 Query String瀏覽器呼叫伺服器所提供的API,所以,現在的關鍵是如何解析Query string

先將”querystring”程式庫匯⼊入,並呼叫parse()函數:

➡ var querystring = require('querystring');

➡ var parsedstring = querystring.parse(“m=helll&u=jollen”);

95

Page 96: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

儲存結果解析後的結果存放於parsedstring物件

➡ { m: 'hello', u: 'jollen' }

96

Page 97: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

修改 requestHandler.js 13 function send(response, query) { 14 console.log("Handler 'send' is started."); 15 console.log("Query string is: " + query); 16 17 var parsedstring = querystring.parse(query); 18 19 var obj = { 20 message: parsedstring.m, 21 username: parsedstring.u, 22 timestamp: (new Date()).getTime() 23 }; 24 25 history.push(obj); 26 27 //////// DEBUG //////// 28 for (var i = 0; i < history.length; i++) { 29 console.log("["+i+"]: " + history[i].message); 30 } 31 }

97

Page 98: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

cont...利⽤用了⼀一個全域陣列history來儲存訊息

將收到的訊息封裝成物件後, 再使⽤用標準的陣列操作將物件放到陣列裡

將⼀一個時間記號(Timestamp)⼀一併封裝⾄至該物件裡

98

Page 99: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

使⽤用 NodeJS + WebSocketWebSocket是HTML5制定的標準,它是⼀一個基於HTTP的協定(Over HTTP)

原則上,我們應該⾃自⾏行處理這⼀一系列的HTTP headers

⺫⽬目前有許多專⾨門WebSocket的NodeJS模組可使⽤用

⾮非NodeJS的官⽅方模組,要使⽤用npm⼯工具另外安裝

99

Page 100: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

安裝 WebSocket-Nodehttps://github.com/Worlize/WebSocket-Node

利⽤用npm安裝WebSocket-Node:

➡ $ npm install websocket

100

Page 101: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

引⼊入模組需要,引⼊入不同的模組,總計4個:

➡ var WebSocketServer = require('websocket').server;

➡ var WebSocketClient = require('websocket').client;

➡ var WebSocketFrame = require('websocket').frame;

➡ var WebSocketRouter = require('websocket').router;

101

Page 102: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

傳送 JSON Data學會處理Query string與WebSocket後,下⼀一個⼯工作就是JSON

NodeJS服務器將資料打成為JSON格式後,再透過WebSocket回傳給Client

102

Page 103: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

File: server.js第19~26⾏行:將原本的HTTP server封裝成WebSocket server,物件名為wsServer

第48⾏行:在wsServer裡註冊⼀一個Request handler,即onWsRequest()函數

第40⾏行:當WebSocket連線請求發⽣生時,回呼此函數

第41⾏行:接受此連線,第⼀一個參數是WebSocket protocol,這是⼀一個⾃自定的協定名稱,⽤用途由開發者定義

第44~45⾏行:為此連線註冊Message handler與Close handler函數

第28⾏行:收到⽤用⼾戶端傳送過來的訊息時,回呼此函數,後續將繼續擴充此函數,將收到的訊息儲存,並將訊息即時(Real-time)推送(Push)到所有的⽤用⼾戶端

第36⾏行:WebSocket連線關閉後,回呼此函數

103

Page 104: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

File: server.js 1 var http = require("http"); 2 var url = require("url"); 3 var WebSocketServer = require('websocket').server; 4 5 function start(route, handlers) { 6 function onRequest(request, response) { 7 var pathname = url.parse(request.url).pathname; 8 var query = url.parse(request.url).query; 9 10 console.log("Request for " + pathname + " received."); 11 12 route(pathname, handlers, response, query); 13 14 response.writeHead(200, {"Content-Type": "text/plain"}); 15 response.write("Hello World"); 16 response.end(); 17 } 18 19 var server = http.createServer(onRequest).listen(8888, function() { 20 console.log("Server has started and is listening on port 8888."); 21 }); 22 23 wsServer = new WebSocketServer({ 24 httpServer: server, 25 autoAcceptConnections: false 26 }); 27

104

Page 105: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

cont... 28 function onWsConnMessage(message) { 29 if (message.type == 'utf8') { 30 console.log('Received message: ' + message.utf8Data); 31 } else if (message.type == 'binary') { 32 console.log('Received binary data.'); 33 } 34 } 35 36 function onWsConnClose(reasonCode, description) { 37 console.log(' Peer disconnected with reason: ' + reasonCode); 38 } 39 40 function onWsRequest(request) { 41 var connection = request.accept('echo-protocol', request.origin); 42 console.log("WebSocket connection accepted."); 43 44 connection.on('message', onWsConnMessage); 45 connection.on('close', onWsConnClose); 46 } 47 48 wsServer.on('request', onWsRequest); 49 } 50 51 // Export functions 52 exports.start = start;

105

Page 106: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

製作⽤用⼾戶端 1 <!DOCTYPE html> 2 <head> 3 </head> 4 <body> 5 <div id="header"></div> 6 <button onClick="WebSocketTest();">Get News</button> 7 8 <script type="text/javascript"> 9 function WebSocketTest() 10 { 11 if ("WebSocket" in window) 12 { 13 // Let us open a web socket 14 var ws = new WebSocket("ws://svn.moko365.com:8888/", "echo-protocol"); 15 ws.onopen = function(evt) 16 { 17 alert("open"); 18 }; 19 ws.onclose = function(evt) 20 { 21 alert("close"); 22 }; 23 } 24 else 25 { 26 // The browser doesn't support WebSocket 27 alert("WebSocket NOT supported by your Browser!"); 28 } 29 } 30 </script> 31 </body> 32 </html>

106

Page 107: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

重構為 jQuery 模式 8 <script type="text/javascript"> 9 (function($) { 10 $.fn.createWebSocket = function () { 11 12 // This 'this' is '#message' object according to this sample 13 var div = this; 14 15 if ("WebSocket" in window) 16 { 17 alert("WebSocket is supported by your Browser!"); 18 // Let us open a web socket 19 var ws = new WebSocket("ws://localhost:8888/start"); 20 ws.onopen = function() 21 { 22 // Web Socket is connected, send data using send() 23 // eg, ws.send("Message to send"); 24 }; 25 ws.onmessage = function (evt) 26 { 27 var received_msg = evt.data; 28 div.html(received_msg); 29 };

107

Page 108: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

cont... 30 ws.onclose = function() 31 { 32 // websocket is closed. 33 34 // 'this' here is [Object WebSocket] 35 div.html("<h1>onclose</h1>"); 36 }; 37 ws.onerror = function() 38 { 39 // 'this' here is [Object WebSocket] 40 div.html("<h1>onerror</h1>"); 41 }; 42 } 43 else 44 { 45 // The browser doesn't support WebSocket 46 alert("WebSocket NOT supported by your Browser!"); 47 } 48 }; 49 50 })($); 51 52 $("#message").createWebSocket(); 53 </script>

108

Page 109: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

How to Send MessageAPI: http://svn.moko365.com:8080/send?u=<username>&m=<message>

➡ 1. HTML <form>

➡ 2. jQuery.ajax();

➡ 3. XmlHttpRequest

➡ 4. WebSocket.send();

109

Page 110: 課程名稱:八屏一雲時代來臨 教你HTML5六小時打通(3)

《⼋八屏⼀一雲時代來臨 教你HTML5六⼩小時打通關 》

Copyright (C) 2013 Moko365 Inc. All Rights Reserved.

更多的技術與想法1. client[] 位於 server.js,理論上不應在 requestHandler.js 裡直接使⽤用。

➡ 如何解決 ?

2. 加⼊入⼀一個命令 ‘list’,讓⽤用⼾戶端可以列出「前 50 筆」歷史資訊。

➡ 提⽰示:

➡ 1) 使⽤用 “message type” ...

➡ 2) 50 筆1個 JSON data,或 50 個 JSON data ?

➡ 3) ⽤用⼾戶端使⽤用 HTTP API 做請求,或直接傳送 JSON ?

110