ทำไมต้องใช้ Script Language
จริงๆแล้วเราสามารถเขียนโปรแกรมให้ทำงานอยู่ในสิ่งแวดล้อมของจาวาทั้งหมด แต่บางครั้งเราอาจต้องการใช้งานโปรแกรมเล็กๆ ที่เราได้สร้างแล้วด้วย Script Language ใดๆ ทำให้เราสามารถนำโค้ดที่มีอยู่มาใช้ให้เกิดประโยชน์ได้ โดยปกติ Script Language มักจะพัฒนาได้ง่ายกว่า เนื่องจากมีระบบที่ไม่ซับซ้อน เช่น เราอาจสร้างตัวแปรขึ้นมา โดยไม่ต้องกำหนดชนิดตัวแปร และสามารถนำไปใช้กับข้อมูลได้หลากหลายชนิด เมื่อเรานำจาวาและ script มาใช้งานร่วมกัน ก็จะทำให้เราสามารถใช้คุณสมบัติของทั้งคู่ร่วมกันได้ เนื่องจากแต่ละภาษาก็อาจจะมีจุดเด่นและด้อยต่างกัน นอกจากนั้นเราอาจนำ script มาใช้เพื่อให้ผู้ใช้งานสามารถเพิ่มคุณสมบัติของโปรแกรมได้ด้วยตนเอง โดยใช้ภาษาที่ตนเองถนัดและไม่จำเป็นต้องรู้ภาษาจาวาเลย จากที่กล่าวมาเราจะพบว่าเป็นคุณสมบัติที่น่าสนใจเป็นอย่างยิ่ง และหวังว่าผู้อ่านจะนำไปใช้ให้เกิดประโยชน์ได้ต่อไป
เริ่มต้นจาก Hello World
ตัวอย่างแรกจะแสดงการนำ Javascript ที่แสดงข้อความ Hello World มาแสดงผลในโปรแกรมที่เขียนด้วยจาวา โดยให้เขียนโค้ดดังนี้
import javax.script.ScriptEngine;
import javax.script.ScriptEngineManager;
import javax.script.ScriptException;
public class Hello {
public static void main(String[] args) {
ScriptEngineManager mgr = new ScriptEngineManager();
ScriptEngine jsEngine = mgr.getEngineByName("JavaScript");
try {
jsEngine.eval("print('Hello, world!')");
} catch (ScriptException ex) {
ex.printStackTrace();
}
}
}
จากตัวอย่างเราจะเริ่มต้นจาก ScriptEngineManager ซึ่งสามารถนำมาใช้ในการตรวจสอบว่ามี Script Engine อะไรบ้างอยู่ภายในเครื่องของเรา และสามารถคืนค่าเป็น Object ของ ScriptEngine เพื่อใช้ในการแปล script ซึ่งเรานำมาใช้งานได้ผ่านฟังชั่น eval() ดังตัวอย่างนั่นเอง จากตัวอย่างเราใช้ mgr.getEngineByName(JavaScript) เนื่องจากเรารู้ว่ามี Javascript Engine อยู่ในเครื่องเราอยู่แล้ว หากท่านได้ติดตั้ง Script Engine อื่นๆ ก็สามารถระบุชื่อ Script Engine ที่ต้องการได้ ณ จุดนี้
ในกรณีที่เราต้องการให้โปรแกรมเรียกใช้งานจากไฟล์ที่มี Javascript เราสามารถเขียนได้ในลักษณะดังนี้ โดยสมมติว่าเราได้เก็บไฟล์ Javascript ที่ชื่อ hello.js ไว้ภายใต้ directory ที่ชื่อ scripts
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.Reader;
import javax.script.ScriptEngine;
import javax.script.ScriptEngineManager;
import javax.script.ScriptException;
public class Main {
public static void main(String[] args) {
ScriptEngineManager engineMgr = new ScriptEngineManager();
ScriptEngine engine = engineMgr.getEngineByName("JavaScript");
InputStream is = null;
try {
is = new FileInputStream("scripts/hello.js");
Reader reader = new InputStreamReader(is);
engine.eval(reader);
} catch (FileNotFoundException ex) {
ex.printStackTrace();
} catch (ScriptException ex) {
ex.printStackTrace();
}
}
}
บางครั้งเราอาจต้องการเรียกใช้งานบางฟังชั่นที่อยู่ใน script เราก็สามารถเรียกใช้งานได้โดย cast ScriptEngine ให้เป็น Invocable จากนั้นให้เรียกใช้ฟังชั่น invokeFunction() ดังตัวอย่าง
import javax.script.ScriptEngine;
import javax.script.ScriptEngineManager;
import javax.script.ScriptException;
import javax.script.Invocable;
public class Hello {
public static void main(String[] args) {
ScriptEngineManager mgr = new ScriptEngineManager();
ScriptEngine jsEngine = mgr.getEngineByName("JavaScript");
try {
jsEngine.eval("function hello(){ print('Hello, world!'); }");
Invocable invoke = (Invocable) jsEngine;
invoke.invokeFunction("hello");
} catch (ScriptException ex) {
ex.printStackTrace();
}catch (NoSuchMethodException ex) {
ex.printStackTrace();
}
}
}
ถ้าเราต้องการนำ java object มาใช้งานใน script ก็สามารถทำได้โดยเรียกใช้ฟังชั่น put ผ่านทาง ScriptEngine ดังตัวอย่าง
import javax.script.ScriptEngine;
import javax.script.ScriptEngineManager;
import javax.script.ScriptException;
import java.util.ArrayList;
import java.util.List;
public class Hello {
public static void main(String[] args) {
List<String> namesList = new ArrayList<String>();
namesList.add("Jill");
namesList.add("Bob");
namesList.add("Laureen");
ScriptEngineManager mgr = new ScriptEngineManager();
ScriptEngine jsEngine = mgr.getEngineByName("JavaScript");
jsEngine.put("namesListKey", namesList);
try {
jsEngine.eval("var x;" + "namesListKey.add(\"Dana\");" +
"var names = namesListKey.toArray();" +
"for(x in names) {" +
" println(names[x]);" +
"}" );
} catch (ScriptException ex) {
ex.printStackTrace();
}
}
}
จากตัวอย่างเราจะเห็นว่านอกจากเรียกใช้งาน java object ได้แล้ว เรายังสามารถแก้ไขข้อมูลของ java object ได้อีกด้วย โดยในตัวอย่างมีการเพิ่มข้อมูลชื่อ Dana เข้าไปใน List นั่นเอง
ตัวอย่างต่อไปจะเป็นการแสดงการผ่านค่าตัวแปรจาก java object ไปยัง script โดยใช้ Invocable ซึ่งจะให้ผลลัพธ์เดียวกันกับตัวอย่างก่อนหน้าี้
import javax.script.ScriptEngine;
import javax.script.ScriptEngineManager;
import javax.script.ScriptException;
import javax.script.Invocable;
import java.util.ArrayList;
import java.util.List;
public class Hello {
public static void main(String[] args) {
List<String> namesList = new ArrayList<String>();
namesList.add("Jill");
namesList.add("Bob");
namesList.add("Laureen");
ScriptEngineManager mgr = new ScriptEngineManager();
ScriptEngine jsEngine = mgr.getEngineByName("JavaScript");
jsEngine.put("namesListKey", namesList);
try {
Invocable invocableEngine = (Invocable)jsEngine;
jsEngine.eval("function printNames1(namesList) {" +
" var x;" +
" var names = namesList.toArray();" +
" for(x in names) {" +
" println(names[x]);" +
" }" +
"}" +
"function addName(namesList, name) {" +
" namesList.add(name);" +
"}");
invocableEngine.invokeFunction("addName", namesList, "Dana");
invocableEngine.invokeFunction("printNames1", namesList);
} catch (ScriptException ex) {
ex.printStackTrace();
}catch (NoSuchMethodException ex) {
ex.printStackTrace();
}
}
นอกจากนั้นถ้าเราต้องการสร้าง java object ใน script ก็สามารถทำได้โดยการ import package ที่ต้องการ ทำให้เราสามารถใช้งาน class ใดๆของจาวาก็ได้ ภายใน script ของเราดังตัวอย่าง
import javax.script.ScriptEngine;
import javax.script.ScriptEngineManager;
import javax.script.ScriptException;
public class Hello {
public static void main(String[] args) {
ScriptEngineManager mgr = new ScriptEngineManager();
ScriptEngine jsEngine = mgr.getEngineByName("JavaScript");
try {
jsEngine.eval("importPackage(javax.swing);" +
"var optionPane = " +
" JOptionPane.showMessageDialog(null, 'Hello, world!');");
} catch (ScriptException ex) {
ex.printStackTrace();
}
}
}
สุดท้ายนี้หวังว่าท่านคงจะได้ประโยชน์จากบทความนี้บ้างไม่มากก็น้อย และสามารถนำไปประยุกต์ใช้เพื่อให้เกิดประโยชน์ต่อไป