Wednesday, December 31, 2008

Java annotations revisit

As previously mentioned, annotation is not a "buzzword" when it is in the Tiger (Java SE 5) specs. But it turns out to be the most excellent feature of Tiger, and it saves Sun reputation from community's complaint about their howlers before (such as EJB1 and EJB2). Now that a little water has flowed under the bridge, I think it is time to revisit Java Annotations.



=== Java Annotations ===


Annotations are presented as metadata – that is data about data. In the case of Java this means that they provide information about various elements of a Java class. For example, they may annotate a method, class or instance variable. One example of an annotation is to note that a method has been deprecated, or that it overrides a method in the superclass. These annotations can then be used by an annotation processing tool (such as APT), or an IDE (such as Eclipse) or indeed a framework, to validate, configure or add to the original Java. For example, if you have annotated a method as overriding a parent class method, then the annotation processing can confirm that you are indeed overriding a method.


There are seven annotations provided in the J2SE 5.0 release (see the annotations guide here; these are provided in two packages, java.lang and java.lang.annotation:



In the package java.lang there is:

@Deprecated – indicates that the associated Java element has been deprecated. It is an alternative to using the Javadoc @deprecated element. A deprecated method or class is essentially one that should no longer be used and that is not guaranteed to be available in future versions of the software. It is thus often useful to know that you are using “old” versions of an API. Although the use of the Javadoc tag already allows many tools (such as Eclipse) to indicate that a language feature is deprecated, the use of the @Deprecated annotation makes this simpler and allows a wider range of tools to report on the use of deprecated features.


@Override - indicates that the method should override a method in the superclass.


@SuppressWarning – directs the compiler to suppress the specified warning.



In the package java.lang.annotaiton:


@Documented – directs tools to automatically generate Javadoc for the annotated element (e.g. a method or variable).


@Inherited – this indicates that the associated annotation is inherited by subclass of the current class.


@Retention – indicates how long annotations with the annotated type are to be retained. For example, a retention type of RUNTIME indicates…


@Target – This indicates the Java element to which associated annotations apply.

It is also possible to extend the set of annotations available by defining your own annotations. This enables project, task and company specific annotations to be created.




=== What are annotations for? ===


Annotations are intended to provide three basic facilities. These facilities are:


• The provision of additional semantics for various class elements. This additional semantic information can help developers to understand the intent behind some feature or implementation detail.


• The execution of additional compile time checks that ensure various constraints are met.


• The support of additional code analysis by annotation-aware tools.


None of these requirements are new and indeed many developers have found ways of overcoming the lack of any annotation-like feature in previous versions of Java.


For example, I have tended to make extensive use of Marker Interfaces over the last few years. These are interfaces that may not contain any methods, but are used to denote a particular concept or entity within an application. This is not a particularly radical idea and indeed there is an example of such an interface in the Java language itself - the java.io.Serializable interface. This interface is a marker interface in that it does not require any methods to be implemented but indicates that a class is capable of being serialized via the Java Serialization mechanism.


Such marker interface can now be replaced with annotations. We can define our own annotation that can be used to mark a class as being a particular concept or entity etc.




=== Using annotations ===


Annotations are straightforward to use; they merely require that an appropriate annotation type be placed directly before the Java language element being annotated. For example:


public class Person {

@Override
public String getName() {
return this.name;
}
}

This means that when this code is compiled, or when it is analysed by tools such as Eclipse, a check can be made to ensure that the method getName() does override a method in the class Person’s superclass. In this particular case, the class Person extends the class Object as a default. The class Object does not contain a method getName() and thus it does not override such a method. This therefore results in an error message being generated. For example, in figure 1 Eclipse has identified that the method getName() should override a method in the parent class and has provided a pop up to this effect.


Screenshot showing Eclipse analysing annotations


However, marking which methods you expect to override parent class methods is probably a step two far for many developers. A rather more useful annotation may be the @SuppressWarnings annotation.


The @SuppressWarnings annotation can be very useful if you have some code that uses a deprecated method or class (possibly because it has been in your system since before that method was deprecated) and you do not want the compiler to churn out lots of warnings about using deprecated APIs. By using the @SuppressWarning annotation and the parameter value “deprecation” it is possible to suppress (turn off) the production of the deprecated warning. For example:


@SuppressWarnings("deprecation")
public static void terminateProcess() {
Thread.currentThread().stop();
}


=== Defining your own annotations ===


You can easily create your own annotations by defining a new annotation type. This is done using a new piece of language syntax, the @interface key word. For example, to define a new annotation @Auditor we would define the following annotation type.


public @interface Auditor {

}

Note that although the syntax for this is almost exactly the same as for a standard interface, the “@” symbol at the start of the keyword changes this to be an annotation declaration. When you compile the resulting Auditor.java file this creates a standard Auditor.class file. If you place this class file on your class path, then you can use this new annotation type within your Java code. For example, if you place the @Auditor just before the class declaration, this marks the class as being of the entity type Auditor. This is illustrated in Figure 2.


A screenshot showing the use of the @Auditor annotation


You can also define parameters that can be used with annotations, and accessor methods for retrieving information about the options specified with an annotation.




=== Drawbacks of Annotations ===


Annotations are not without their drawbacks. Not least of which is that they are not really metadata – that is they are not data about data – they are data about classes, methods, instance and static variables etc.




=== Window dressing ===


As such annotations are syntactic sugar – they coat the elements of a class without actually telling you anything in detail about that class (you can use the reflection API for some of that). Thus they provide guidance to processors, tools and frameworks to help in the analysis, compilation or deployment of that software.

Inheritance


One of the major features of an object-oriented system is inheritance. You can subclass a class, and subclass an interfaces – but you can’t subclass annotations.




=== Null values ===


If a null value should be treated as an un-initialized value then annotations are somewhat awkward in the way they handle these – rely on the developer to provide a way of indicating un-initialised rather than initialised to null.




=== Values in General ===


These are somewhat limited in what you can use – although in the main this is fine.




=== Annotations hold constants ===


The values used with annotations are hard coded rather than variable. Thus if an annotation takes a literal value of 40 – then that value is now hard coded into your program.




=== Annotations and code synchronization ===


Just as with Javadoc comments themselves, annotations need to be maintained to reflect any code changes that may occur. However, as we all know, it is all too easy to change the source code and not to update the associated Javadoc (even when they are next to each other). Exactly the same is true for annotations. If the code relating to an annotation changes, then the associated annotation may also need modification. This may not be as straightforward as it seems. For example, if I rename a method in a class I am working on, then this may impact on another class, that I may know nothing about; if that class requires that one of its methods overrides mine (due to the use the @Override annotation). Of course this may be what is desired or it may not! As you can define your own annotations this situation may become much worse, with significant repercussions for on-going maintenance, clarity and general stability of the code.




=== Summary ===


So where does that leave the question “To Annotate or not to Annotate?”. In essence, as with many things in life, annotations can be very useful but should not be over used or abused. They can add extremely useful additional information to Java code that can be analysed by tools, frameworks, analysers as well as developers themselves – but they should not be used without due consideration.




(main reference: TheRegister)
See also :
http://javabeat.net/articles/30-annotations-in-java-50-1.html
http://www.developer.com/java/other/article.php/10936_3556176_1
http://www.oracle.com/technology/pub/articles/hunter_meta.html
...

Monday, December 29, 2008

JavaCard quick notes [2]

Tiếp tục JavaCard nào


=== Các lỗi thường gặp với JCOP ===

Sau một hai buổi mày mò lăn xả với JCOP, mình trở về với thân thể trầy xước tả tơi, dưới đấy là vài kinh nhiệm mình gặp phải và cách xử lý


1 - Lỗi upload ".cap" file không thành công.
Lý do:
- Build file cap không thành công, không có file .cap để upload.
Xử lý:
- Từ menu Window->Preferences..-> Java->Compiler
- Hiệu chỉnh "Compiler Complance level" -> 1.5
- Build lại project của bạn và Run.


2 - Lỗi không thể send các command.
Thông báo lỗi:
- "CLA value not supported"
- "INS value not supported"
Lý do:
- process() của bạn hiện tại không bắt, xử lý được với các mã CLA/INS lệnh theo yêu cầu.
Thông báo lỗi:
- "Conditions of use not satisfied"
Lý do: bạn phải /select applet mới có thể bắt đầu truyền các command hoặc applet chưa được xác thực (nếu có)


3 - Lỗi "No precise diagnosis"
Đây là lỗi làm "điên người" nhất mà mình tạm cho 1 lý do tạm là .. trình biên dịch JC còn củ chuối. Khi gặp lỗi này, bạn nên xóa mọi hành động vừa mới làm và bắt đầu cẩn thận lại từ bản backup gần nhất :D, nôm na ra là .. bó hand

Vài lỗi nhỏ trên là cơ bản, sẽ còn lỗi nhiều nữa, mình sẽ liệt kê thêm nếu gặp phải



=== Vòng đời của 1 "cardlet" ===

Trước tiên lưu ý: "Cardlet" là cách gọi của mình về applet của JavaCard, chưa phải thuật ngữ chính thức.

Theo đặc điểm kỹ thuật, vòng đời của một JavaCard Applet bắt đầu từ khi "em" được đăng ký vào card với phương thức Applet.register() . JCRE (JavaCard Runtime Environment) sẽ tương tác với applet thông qua các phương thức tĩnh của applet là: install, select, deselect process.


Phương thức install():
Khai báo:
public static void install(
byte[] bArray, short bOffset
, byte bLength )
throws ISOException;
- Khi applet được cài đặt vào JC, phương thức install được thực thi một lần duy nhất cho mỗi thể hiện của applet. Các phương thức khởi dựng không nên được truy cập một cách trực tiếp mà phải thông qua phương thức install. Nhiệm vụ chính của phương thức install là tạo thể hiện của applet thông qua các constructor và đăng ký applet với JCRE thông qua phương thức register(). Chỉ khi được đăng ký thành công, JCRE mới có thể cho phép thao tác lệnh APDU với applet.


Phương thức register(..):
Khai báo:
protected final void register()throws SystemException;
protected final void register(
byte[] bArray,short bOffset
,byte bLength)throws SystemException;
- Phương thức này được dùng để đăng ký một thể hiện của ứng dụng "cardlet" với JCRE với một mã (AID) xác định. Mã AID xác định bởi một chuỗi Hexadecimal, có độ dài trong khoảng 5-11 bytes (1byte = 8bits). Mã AID này là tham số đầu vào cho lệnh Select applet. Thông thường, phương thức register() được gọi từ thân của phương thức install() để applet được đăng ký với JCRE 1 lần cho mỗi card.


Phương thức select():
Khai báo:
public boolean select();
- Phương thức select() cho phép chuyển quyền nhận lệnh cho một thể hiện của Applet. Phương thức select applet được JCRE thực thi khi JCRE nhận được lệnh SELECT FILE APDU cùng một mã Applet từ thiết bị. Việc select Applet sẽ chuyển trạng thái applet từ deselect -> select và cho phép applet nhận các lệnh từ bên ngoài thông qua phương thức process() do JCRE chuyển giao. Tuy nhiên, trước khi select Applet, JCRE sẽ tự động thực hiện hành động deselect() một (hoặc các) applet đã được select trước đó.


Phương thức process():
Khai báo:
public void process(APDU apdu) throws ISOException;
- Sau khi được select(), tất cả các lệnh APDU sẽ được JCRE chuyển cho Applet thông qua phương thước process(). Các nhân xử lý của applet sẽ được thể hiện (hoặc phân hướng xử lý) ở phương thức này. Từ đây, các thao tác dữ liệu, nhận và trả lệnh APDU được thực hiện trên vùng buffer có giới hạn đã được applet đăng ký trong hàm register().


Phương thức deselect():
Khai báo:
public void deselect();
- Phương thức được gọi thực thi bởi JCRE khi có yêu cầu hoặc khi có hành động select một Applet khác. JCRE sẽ tự động thực hiện deselect() Applet hiện tại.
- Khi có lỗi khi thực hiện deselect, JCRE sẽ tiếp nhận lỗi, và tại thời điểm đó, applet đã được deselect.

GoF Design Patterns [5]

Adapter


Decorator


Visitor




(will be updated on demand)

Sunday, December 28, 2008

PureMVC framework notes

PureMVC is a lightweight framework for creating applications based upon the classic Model, View and Controller concept; based upon proven design patterns



This free, open source framework which was originally implemented in the ActionScript 3 language for use with Adobe Flex, Flash and AIR, has now been ported to nearly all major development platforms. It seems PureMVC is more popular in other languages (Java, C#, Ruby, ... ) than its competitor (Cairgorm) .





(to be updated)

Wednesday, December 24, 2008

GoF Design Patterns [4]

Abstract Factory

Proxy

Mediator





(will be updated on demand)

Tuesday, December 23, 2008

JavaCard quick notes

Những ai đã biết đến Java thì chắc hẳn cũng biết Sun đã phân Java ra làm 3 nền (platform) chính: Standard (Java SE), Enterprise (Java EE) và Micro (Java ME) . Tuy nhiên hiện nay có 2 hướng phát triển của Java có thể vươn ra thành 1 platform mới, đó là JavaCard và JavaFX .

Về JavaFX thì đã có giới thiệu sơ trong bài RIA , tuy nhiên triển vọng của JavaFX không khả quan lắm, khi 2 đối thủ cạnh tranh là Silverlight và Flex/OpenLaszlo đã vượt lên hẳn.

Còn JavaCard vẫn là 1 lĩnh vực mới mẻ ở VN , tuy nhiên tiềm năng rất lớn, vì có thể xây dựng hệ thống bán lẻ, hệ thống máy tự động (kiểu ATM cho ngân hàng), cũng như chính phủ điện tử. FYI, công ty lợi nhuận lớn nhất ở Hoa Kỳ năm ngoái là, không phải Microsoft vì MS chỉ đứng khoảng hạng 10, chính là WalMart , hệ thống bán lẻ giá rẻ toàn nước Mỹ. Bây giờ một số công ty VN bắt đầu tính đến thị trường này, và nước ngoài cũng có công ty ngấp nghé nhảy vào làm, vì thế JavaCard có tiềm năng khó lường.


Xin đưa lên vài bài dịch của bạn Trịnh Quốc Hùng để các bạn hiểu hơn về JavaCard .



=== Cài đặt plugin JCOP (3.1) cho Eclipse ===

Xin đặt vài dòng giới thiệu ngắn ngủi, JCOP - JavaCard OpenPlatform - khởi nguồn do IBM nghiên cứu - với tên gốc là JavaCard - là một bộ khung lập trình để phát triển cho công nghệ các loại thẻ thông minh (smart card), cho phép lập trình trên các loại thẻ có chip xử lý nhỏ mà ta đã thấy ứng dụng của chúng trong thực tế ngày nay: sim điện thoại, thẻ ngân hàng, thẻ nhân viên thông minh...
Nhưng sau năm 2007, IBM ngừng đầu tư và chuyển giao công nghệ cho hãng NXP Semiconductors - một trong những tập đoàn hàng đầu thế giới về công nghệ thẻ bao gồm cả thẻ "không tiếp xúc" (contactless). Từ đó, công cụ này có tên mới là JCOP với các version phát triển 1.0, 2.1 , 3.1, 4.1... Ngày nay, công cụ này không còn được tìm thấy trên mạng, mà nó chỉ được chuyền tay qua các thành viên hoặc được cấp từ chính hãng NXP với điền kiện có đăng ký hợp đồng. Dưới đây mình sẽ liệt kê từng bước cài đặt JCOP 3.1 thành công:


Điều kiện :
- Eclipse IDE từ version 3.2 đến 3.3.1, dùng khác các version này không đảm bảo build CAP file thành công.
- JCOP plugin for Eclipse version 3.1.2 , tool này bạn phải tự tìm hoặc đăng ký với NXP Semiconductors.


Thực hiện:
- Sau khi giải nén và khởi động IDE Eclipse.
  1. Chọn menu Help > Software Updates > Find and Install
  2. Trong hộp thoại Install/Update, chọn Search for new features to install và chọn Next
  3. Chọn nút nhấn New Archived Site . . . và chỉ đường dẫn đến file n
  4. Chọn liên tiếp Open -> OK -> Finish
  5. IDE Eclipse sẽ đòi hỏi khởi động lại.
Sau khi khởi động thành công, trong mục New Project sẽ có thêm cấp project "JavaCard Project". Nếu thấy mục này, coi như bạn đã cài đặt thành công plugin JCOP for Eclipse.


=== Tạo một JavaCard Project ===

theo các bước sau
  1. Trong menu New -> Project...
  2. Tại hộp thoại New Project, chọn mục JavaCard Project và chọn Next.
  3. Tại hộp thoại Java Card Project, điền thông tin Project Name và chọn Next.
  4. Tại đây bạn đã có thể chọn Finish. Nhưng mình thì thích đi từng bước hơn.
  5. Nếu chọn Next, bạn sẽ có thể chọn các chuẩn configuration card xác định cho loại project của mình (Java Card 2.2.1, JavaCard 2.1.1, Global Platform, ...)
  6. Chọn Next, chọn mục "Create a JavaCard Application using ...", chọn item "Basic JavaCard applet".
  7. Điền thông tin Package và Applet ClassName. Package là gói chứa đựng các Applet. Applet là gói ứng dụng sẽ được cài lên các chip xử lý.
  8. Chọn Next, điền thông tin PackageAID và AppletAID. Đây là mã xử lý của Package và Applet trên chip. Lưu ý: PackageAID và AppletAID được đặt tên dưới dạng chữ số hexadecimal. Chiều dài cho cả Package AID và AppletAID là 5 bytes. (bạn có thể đọc thêm thông tin trong tài liệu "Smart Card Handbook" để nắm vững hơn)
  9. Chọn Finish.
  10. Tới đây là bước kiểm tra bản quyền của NXP, cử sổ activate code sẽ hiện cho bạn 3 action activate: Đăng ký 1 activate code mới, sử dụng thẻ được cung cấp bới NXP để activate hoặc nhập lại 1 activate code đã được cung cấp bới NXP. Nếu không qua được bước này thì coi như quá trình tìm hiểu JavaCard, cardlet buộc phải chấm dứt.

Xong 9 bước trên vẫn chưa xong, mục đích là phải build được file có đuôi là .cap mới có thể upload vào thẻ. Dưới đây là các bước để Run/Debug project, trong quá trình Run/Debug thành công, file .cap sẽ được build và đặt ở thư mục "../bin" của project.
  1. Trong menu Run -> Open Run/Debug Dialog..
  2. Tạo mới một "JavaCard Application" và đặt các cấu hình phù hợp cho project.
  3. Chọn Run/Debug.

Kết quả trong cửa sổ JCOP Shell:


chú ý dòng : "cm> upload -b 250 .... .cap" là đường dẫn đến file cap đã được build thành công.
"cm> install -i abababab01 -q C9#() abababab00 abababab01"
-
abababab00 là tên packageAID
-
abababab01 là tên appletAID

"cm> card-info" cho thông tin card sau khi upload applet thành công.

Đến đây xem như bạn đã có thể tạo được một card applet (.cap) . Công việc kế tiếp sẽ còn nhiều cam go, nhưng đến đây mình cần phải dừng lại để suy ngẫm, đúc kết lại những gì mình đã làm được. Làm ly cafe nào.

Saturday, December 20, 2008

GoF Design Patterns [3]

Tiếp tục với những design patterns dễ gặp:


Factory Method (creational)

Facade (structural)

Observer (behavioural)





(will be updated on demand)

Friday, December 19, 2008

ActionScript 3 notes

=== Data types ===

Top level types:

- void, int, uint,
- Object, Number, String, Boolean, Null


Complex types:

- Date, Array, ByteArray, Vector, Dictionary, RegExp, Function, Error
- XML, XMLList, BitMap, Shape, MovieClip, Video, SimpleButton, TextField



=== Declaration ===:

Package, import, class:

package com.example {
import flash.net.URLLoader;
import flash.net.URLRequest;
public class Example {
// Class code goes here.
}
}


Access modifiers:

public : accessible outside the class (e.g., from an instance of the class).
private : accessible only within the class.
protected : accessible only within the class and its subclasses.
internal : accessible only within the package.


Variable/constant, field/property:

var myObject: Object = {Param1:"Hi!", Param2:76};
public var myString: String = "ABC";
protected var myNumber: Number = 5;
private var myInt: int = 12;
var myBoolean: Boolean = true;
var myArray: Array = [5,"Hello!",{a:5, b:7}]
private var myDate: Date = new Date();
var myButton: mx.controls.Button = new mx.controls.Button();
static public const MY_TEST: String = "test constant";

var authorsByBook:Object = new Object( );
authorsByBook["Flex"] = "Mediocre, Ninja";
authorsByBook["ActionScript 3"] = "bibo, ninja, mediocre";



Function/method/constructor:

function test( ):void {
var message:String = "function message";
trace(message);
}




=== Formal syntax ===

Expression/Statement/FlowControl

while(total < int =" 0;"> maxTotal + 20) {
total -= 10;
}
else {
total -= 5;
}



Inheritance

package com.example {
import com.example.A;
public class B extends A {
override public function run( ):void {
trace("B");
}
}
}


Interface

package com.example {
public interface IExample {
function a( ):String;
function b(one:String, two:uint):void;
}
}

package com.example {
import com.example.IExample;
public class Example implements IExample {
public function Example( ) {
}
public function a( ):String {
return "a";
}
public function b(one:String, two:uint):void {
trace(one + " " + two);
}
}
}


Handling Event

;lt&mx:Script;gt&
;lt&![CDATA[
import flash.net.FileReference;
private function initializeHandler(event:Event):void {
var file:FileReference = new FileReference( );
file.browse( );
file.browse( );
}
]];gt&
;lt&/mx:Script;gt&


Handling Error

try {
// Code that might throw errors
}
catch (error:IOError) {
// Code in case the specific error occurs
}
catch (error:Error) {
// Code in case a non-specific error occurs
}
finally {
// Code to run in any case
}




(to be updated)

Wednesday, December 17, 2008

GoF Design Patterns [2]

Hãy bắt đầu bằng những Design Pattern đơn giản và dễ gặp nhất :-) .




Singleton (creational)

Bridge (structural)

Command (behavioural)



(will be updated on demand)

Monday, December 15, 2008

Rich Internet Application

Nói đơn giản, Rich Internet applications là những ứng dụng (application) chạy trên mạng máy tính (cụ thể là Internet) mà có nhiều tính năng (rich features) như là ứng dụng chạy stand-alone trên máy không nối mạng (thường gọi là desktop application) .


=== Sự ra đời của RIA ===

Từ những ngày khởi thủy của những ứng dụng trên máy tính đều được thực hiện trên các máy tính lớn (mainframe). Các máy trạm chỉ làm nhiệm vụ hiển thị thông tin được xử lý từ các mainframe. Sau đó, tốc độ phát triển phần cứng cho các máy trạm (terminals - từ đây ta sẽ gọi chung là clients , mặc dù không đúng lắm ) nhanh như vũ bão. Từ tốc độ xử lý, hệ thống lưu trữ, bộ nhớ đến các thành phần khác dành cho clients đều phát triển rất nhanh.Như vậy, nếu chỉ dành toàn bộ việc tính tóan cho mainframe, và các clients chỉ để hiển thị thông tin sẽ vô cùng lãng phí tài nguyên.

Sau đó đến giai đoạn phát triển của các ứng dụng dạng client/server. Lại có vấn đề về hệ thống phân tán. Sẽ mất nhiều công sức cho việc cài đặt, bảo dưỡng các ứng dụng trên clients. Rồi việc đảm bảo các ứng dụng trên clients phải tương thích với các platforms khác nhau.

Vào những năm 90, internet ra đời. Việc sử dụng các web browsers cho các thin clients được áp dụng rất mạnh mẽ và hiệu quả. Nhưng (lại nhưng) kiểu lập trình page-to-page, khiến các nhà phát triển ứng dụng rất khó khăn, mệt mỏi và có rất nhiều hạn chế. Rồi các giao diện người dùng đơn điệu, không hiệu quả. Để cố gắng khắc phục những nhược điểm này, RIA đã ra đời. Vậy RIA có những khả năng gì?
(Về định nghĩa, xin xem lại ở đầu bài này)


=== Khả năng của RIA ===

Có khả năng tương tác với DOM (Document Object Model), xây dựng những ứng dụng chạy trên nhiều loại browsers và platforms.

Có khả năng sử dụng được các đối tượng trên server như web services hay những công nghệ tương tự khác, làm cho các ứng dụng trên clients có thể kết nối với server minh bạch hơn, dễ dung hơn.

Có khả năng làm việc “offline”. Dữ liệu được đưa về clients, xử lý tại clients, sau đó trả lạ cho server, tránh việc quá tải đường truyền cũng như hệ thống xử lý của server.


=== Các khuynh hướng xây dựng RIAs ===

Hiện nay có 4 trường phái xây dựng RIAs : đầu tiên là Ajax (Asynchronous Javascript and XML) : sử các thư viện JavaScript như Dojo, OpenRico, Backbase và Yahoo ToolKit, etc . Tiếp theo là RIAs trên nền Flash Player với các công cụ như Flex, OpenLaszlo ( đây là công cụ Open source). Thứ 3 là Windows Presentation Foundation (WPF) sử dụng .NET framework 3, trong đó quan trọng là Silverlight. Cuối cùng là JavaFX, kết hợp với các công cụ GUI như : AWT/Swing, và Eclipse RCP (SWT/JFace). Trong đó, dường như WPF và JavaFX nhắm vào ứng dụng desktop hơn là RIAs, mặc dù chúng đều có thể phát triển cho RIAs.


Ajax : là 1 thuật ngữ. Nó được các nhà phát triển kết hợp từ nhiều công cụ (HTML,DHTML, Javascript), công nghệ, để chuyển dữ liệu từ server tới client mà không phải reload lại page. Thực ra, trước đây IFrames đã làm được những công việc này. Gần đây, Java script sử dụng XMLHttpRequest để thay thế applets, Iframe.


Flash : Là nền tảng để triển khai RIAs. Trước đây, flash được phát triển nhằm mục đích phục vụ xây dựng animations. Sau nhiều thập kỷ thành công, tới nay có tới 97% (theo Adobe Flex 3 : Training from the Source) các web browsers có cài đặt flash. Adobe nhận ra rằng, với flash có thể làm nhiều hơn việc chỉ phát triển animations. Vì thế Flex đã ra đời.

OpenLaszlo : là phần mềm open source với nền tảng phát triển là Javascript và XML và chạy trên nền flash. Các ứng dụng cũng được biên dịch thành các files SWF. Vì là công cụ open source nên Laszlo cũng gắn bó chặt chẽ với LAMP (Linux, Apache, MySQL và PHP).

Flex : (vì Flex là cái chúng ta đang quan tâm nên mình tách riêng ra 1 mục) được xây dựng với nền tảng là Eclipse. Flex 1 là phần mềm open source. Tuy nhiên, vào giữa năm 2006, Adobe đã thương mại hóa Flex 2, với những tính năng và ưu điểm vượt trội bản Flex 1. Gần đây, Adobe đã chính thức phát hành Flex 3 có những phần đáng chú ý như : Adobe AIR, cải thiện đáng kể hiệu năng của những files SWF. Có khả năng tích hợp các middle layers ngay trong ứng dụng như : PHP, ColdFusion, WebService, Flex Data Server (hay còn gọi là FDS). Từ phiên bản Flex 2 trở đi, các ứng dụng sử dụng ActionScript 3 và chạy trên nền Flash Player 9. Flex cho miễn phí Flex SDK, cũng như AIR SDK, chỉ thương mại Flex Builder (với giá bản full của Flex Builder 3 Pro là 699$). Thêm nữa, Flex là sự kết hợp không thể tách rời của ngôn MXML và ActionScript.


Windows Presentation Foundation (WPF) : là 1 tập hợp các công cụ để xây dựng các ứng dụng RIAs trên nền Windows.

WPF : nền tảng để xây dựng và chạy RIAs.
XAML : ngôn ngữ xây dựng nên RIAs.
Visual C# : IDE để viết ra RIAs


Java (JavaFX) : thật đáng tiếc , cho đến nay thì JavaFX vẫn chưa làm được gì nhiều và có vẻ đang tụt lại đáng kể trong cuộc đua này. Hy vọng Sun dẹp bớt những tham vọng ngu ngốc và hướng tới cộng đồng hơn, khi đó mới có thể hy vọng cạnh tranh thị phần RIA được.



(tạm thế đã , sẽ định dạng bài viết lại sau)

Sunday, December 14, 2008

GoF Design Patterns

Có lẽ không cần giới thiệu nhiều về Design Patterns (Mẫu Thiết kế), cũng như quyển sách kinh điển của Gang of Four (Bộ Tứ - a.k.a Bè lũ 4 tên) vì bây giờ đã quá nổi tiếng rồi.

Việc nắm được các Design Patterns ngoài việc cải thiện tư duy hướng đối tượng, nó giúp dự án nhanh chóng có được thiết kế tốt, vì thế reduce cost & development interval, đồng thời improve productivity & customer satisfaction. Đối với bản thân developer thì ít ra cũng hấp dẫn ở chỗ là có thể làm thay đổi đáng kể mức lương :D .
Do đó bạn nào muốn tìm hiểu kỹ hơn thì nên nghiền ngẫm sách và code nhiều vào, chứ các bài blog như bài này chỉ nêu như cưỡi ngựa xem hoa thôi :D


Trong sách DP của GoF, 23 mẫu được phân thành 3 categories là: Creational (khởi tạo) - 5 mẫu , Structural (cấu trúc) - 7 mẫu, và Behavioural (hành vi) - 11 mẫu còn lại .

Tuy nhiên theo tớ thì không nên tiếp cận các DP the thứ tự tên ABC, hoặc theo từng category như trên, mà nên tiếp cận theo 1 trong 2 hướng: hoặc là dễ hiểu nhất, hoặc là dễ gặp nhất.
Ngoài ra không nên chạy theo các "xxx Design Patterns" khác (VD: Enterprise), vì đa số các pattern dạng này thuộc loại bùng nổ, hầu như cái gì cũng quơ vào làm pattern, hiệu quả thực tế chẳng bao nhiêu mà còn dễ dẫn đến "tẩu hỏa nhập ma" :D .


=== Creational DP ===


C. Singleton

Ensure a class only has one instance, and provide a global point of access to it.



C. Factory Method

Define an interface for creating an object, but let the subclasses decide which class to instantiate. Factory Method lets a class defer instantiation to subclasses.



C. Abstract Factory

Provide an interface for creating families of related or dependent objects without specifying their concrete classes.



C. Prototype

Specify the kinds of objects to create using a prototypical instance, and create new objects by copying this prototype.



C. Builder

Separate the construction of a complex object from its representation so that the same construction processes can create different representations.



=== Structural DP ===


S. Bridge

Decouple an abstraction from its implementation so that the two can vary independently.



S. Facade

Provide a unified interface to a set of interfaces in a system. Façade defines a higher-level interface that makes the subsystem easier to use.



S. Adapter

Convert the interface of a class into another interface clients expect. Adapter lets classes work together that couldn’t otherwise because of incompatibility interfaces.



S. Decorator:

Attach additional responsibilities to an object dynamically. Decorators provide a flexible alternative to subclassing for extending functionality.



S. Proxy

Provide a surrogate or placeholder for another object to control access to it.



S. Composite

Compose objects into tree structures to represent part-whole hierarchies. Composite lets clients treat individual objects and compositions of objects uniformly.



S. Flyweight

Use sharing to support large numbers of fine-grained objects efficiently. A flyweight is a shared object that can be used in multiple contexts simultaneously. The flyweight acts as an independent object in each context; it’s indistinguishable from an instance of the object that’s not shared.



=== Behavioural DP ===


B. Strategy:

Defines a family of algorithms, encapsulates each one, and make them interchangeable. Strategy lets the algorithm vary independently from clients who use it.



B. Chain of Responsibility

Avoid coupling the sender of a request to its receiver by giving more then one object a chance to handle the request. Chain the receiving objects and pass the request along the chain until an object handles it.



B. Template Method

Define a skeleton of an algorithm in an operation, deferring some steps to subclasses. Template Method lets subclasses redefine certain steps of an algorithm without changing the algorithms structure.



B. Iterator

Provide a way to access the elements of an aggregate object sequentially without exposing its underlying representation.



B. Command

Encapsulate a request as an object, thereby letting you parameterize clients with different requests, queue or log requests, and support undoable operations.



S. Observer

Define a one-to-many dependency between objects so that when one object changes state, all its dependents are notified and updated automatically.



B. Mediator

Define an object that encapsulates how a set of objects interact. Mediator promotes loose coupling by keeping objects from referring to each other explicitly, and lets you vary their interaction independently.



B. State

Allow an object to alter its behavior when its internal state changes. The object will appear to change its class.



B. Interpreter

Given a language, define a representation for its grammar along with an interpreter that uses the representation to interpret sentences in the language.



B. Memento

Without violating encapsulation, capture and externalize an object’s internal state so that the object can be restored to this state later.



B. Visitor

Represent an operation to be performed on the elements of an object structure. Visitor lets you define a new operation without changing the classes of the elements on which it operates.



( từ từ tớ sẽ giới thiệu cụ thể từng cái pattern sau... nếu có thời gian :D )

Friday, December 12, 2008

Javascript Libraries Overview

Từ khi những thuật ngữ như AJAX hay RIA xuất hiện, Javascript đã được phát triển mạnh và hình thành các thư viện, hay cũng có thể gọi là các framework để hỗ trợ ứng dụng web.
Hiểu biết về JavaScript đã trở thành 1 skill không thể thiếu với những ai làm lập trình web, và cũng là 1 skill khá quan trọng của các hacker. Tuy nhiên với web-development hiện nay thì lời khuyên là bạn nên nắm vững 1 thư viện nào đó, hơn là đi tìm kiếm các đoạn script mẫu ngắn phục vụ cho 1 mục đích nào đó.

Các thư viện JS mã mở và hữu ích hiện nay có thể kể: jQuery, mooTools, Prototype + Scriptaculous, YUI + ExtJS , Dojo, ...

(ngoài ra còn 1 số công nghệ JS có cả phần server side như : qooxdoo, echo2, GWT, DWR, jMaki, Qcodo, AjaxCFC, ... )



Dưới đây là 1 slideshow so sánh cơ bản các thư viện JS trên để bạn có thể chọn cho mình 1 cái phù hợp :



Have fun :D !

Monday, December 08, 2008

Learning with YouTube

Well, maybe you already know flash-video sites such as MetaCafe , YouTube , Google Video, ... but have you ever used them for learning ?

My favourite lectures come from MIT and Standford :
MIT
Standford

IMHO , this method is quite good if you have enough time.
Try it yourself and see :-)

Sunday, December 07, 2008

VIM vs Notepad++

Ngoài 1 số điểm mà notepad-plus plus kết hợp plugins đuổi kịp VIM, vẫn còn một số ưu điểm không thể không nhắc đến của vim :


1/ Mở file lớn. (bạn thử mở 1 file > 100 MB bằng vim với Notepad++ coi sao)


2/ Xử lý nhiều cụm từ trong 1 file lớn (VD: thay thế vài ngàn từ bằng vim và Notepad++)


3/ Hỗ trợ highlight nhiều hơn (syntax on hoặc syntax enable), hiện nay Notepad++ đã được tăng nhiều nhưng vẫn chưa bằng vim (thử mở các file text như .conf, .cnf, .lst , .cnt , .*rc , ... )


4/ Customize màu sắc dễ hơn, adapt không chỉ 1 ngôn ngữ lập trình (colorscheme, set background, set foreground, set guifont, tự chỉnh các file .vim , ... )


5/ Customized macro: recording các thao tác , chẳng hạn bạn đang viết blog đến từ "CSS", muốn link Wiki chỉ bấm 1, hoặc 2 phím đã recorded thành macro thì chữ CSS đó đã trở thành <a href="http://en.wikipedia.org/wiki/CSS">CSS</a> ,


6/ Customized hotkey: nếu macro không quá phức tạp mà lại hay dùng thì thường người ta ánh xạ hotkey, hầu như không có giới hạn nào cả. Chẳng hạn nếu muốn thì Ctrl+B có thể là cặp thẻ (cho HTML) , Ctrl+W rồi phím b là cặp thẻ [b] (cho forum BBcode) .


7/ Thao tác trên từng word, dòng, ..., di chuyển... bằng các phím cực nhanh. Chẳng hạn file có 1234 dòng, bạn muốn cut 543 dòng đầu tiên đem xuống cuối file rồi paste lại thì chỉ cần chuyển qua Normal mode rồi bấm (nhắm mắt luôn) :
gg543ddGp
hoặc gõ tương ứng các lệnh đó rồi Enter cũng được


8/ Viết script: vim có hỗ trợ cả các cú pháp if, else, func... Chẳng hạn có thể viết 1 function rồi map cho "Ctrl+/" : khi gặp file java, C, C++,... thì comment out cả đoạn bằng " // " , khi gặp file Perl, Shell,... thì comment out bằng " # " , gặp hợp ngữ thì comment bằng " ; " khi gặp file VIM thì comment out bằng " " " , ...


9/ Kích hoạt shell command: bằng dấu "!" ngay sau dấu ":" , chẳng hạn
:!ps
Một ví dụ tổng hợp: chẳng hạn dùng để map hotkey (kết hợp shellscript & perl) để mở Xterm tra dữ liệu từ điển Hồ Ngọc Đức trong vim console bằng phím F9 (gần giống kiểu click & see)


10/ "DIFF" 2 hoặc 3 file cùng lúc bằng lệnh
$ vimdiff copyBTL1.txt copyBTL2.txt
hoặc
$ vim -d copyBTL2.txt copyBTL1.txt copyBTL3.txt


... more to come (vimrc, multiple buffer, multiple session, multiple split, vimshell, external edit ... ), làm biếng nghĩ tiếp quá



have fun geeks !