2011年10月18日星期二
How to Use RSS in BlogSpot.com
Or you can use the following url : RSS Default Address
Read and Write XML in JDK1.4 with org.w3c.Dom
well, I admitted that org.w3c.dom (or DOM) is quite difficult to use than the popular dom4j (see here).
But sometimes, it might be problem for us to include new libraries in source code due to library confliction or license issues. For example, a big project is developed by various people independently. If all people use different libraries to parse xml, your product will finally turned out to be very complex to maintain.
So sometimes using the standard package in JDK (like JAXP) is the only choice, though difficult.
Here I demo some examples on how to use it for common purpose.
XMLIOUtilityimport java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;
import javax.xml.transform.OutputKeys;
import javax.xml.transform.Transformer;
import javax.xml.transform.TransformerConfigurationException;
import javax.xml.transform.TransformerException;
import javax.xml.transform.TransformerFactory;
import javax.xml.transform.dom.DOMSource;
import javax.xml.transform.stream.StreamResult;
import org.w3c.dom.Document;
import org.w3c.dom.Node;
import org.xml.sax.SAXException;
/**
Author : ye_m
Date: Oct.18,2011
Company : Works Applications. Co.Ltd.
*/
public class XMLIOUtility {
public static Document readFromFile(String filename) {
FileInputStream ins = null;
Document doc = null;
try {
ins = new FileInputStream(filename);
doc = readFromStream(ins);
} catch (FileNotFoundException e) {
e.printStackTrace();
} finally {
silentClose(ins);
}
return doc;
}
public static Document readFromStream(InputStream ins) {
DocumentBuilderFactory domFactory = DocumentBuilderFactory
.newInstance();
domFactory.setNamespaceAware(true); // never forget this!
DocumentBuilder builder;
Document doc = null;
try {
builder = domFactory.newDocumentBuilder();
doc = builder.parse(ins);
return doc;
} catch (ParserConfigurationException e) {
} catch (SAXException e) {
} catch (IOException e) {
}
return doc;
}
public static void saveToStream(Document doc, OutputStream stream) {
try {
TransformerFactory tFactory = TransformerFactory.newInstance();
Transformer transformer = tFactory.newTransformer();
transformer.setOutputProperty(OutputKeys.INDENT, "yes");
transformer.setOutputProperty(
"{http://xml.apache.org/xslt}indent-amount", "2");
DOMSource source = new DOMSource(doc);
StreamResult result = new StreamResult(stream);
transformer.transform(source, result);
} catch (TransformerConfigurationException tce) {
} catch (TransformerException te) {
}
}
public static void saveToFile(Document doc, String filename) {
FileOutputStream fos = null;
try {
fos = new FileOutputStream(filename);
saveToStream(doc, fos);
} catch (FileNotFoundException e) {
e.printStackTrace();
} finally {
silentClose(fos);
}
}
public static void silentClose(InputStream ins) {
if (ins != null) {
try {
ins.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
public static void silentClose(OutputStream wr) {
if (wr != null) {
try {
wr.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
public static String getNodeText(Node node) {
String value = "";
if (node != null) {
Node first = null;
while ((first = node.getFirstChild()) != null) {
if (first.getNodeType() == Node.TEXT_NODE) {
value = first.getNodeValue().trim();
break;
}
}
}
return value;
}
}
With above code, it becomes easier for you to manipulate XML files.
Here is something important.
Usually, the output format of XML file by DOM is very ugly, with does not change lines or insert indent automatically. So you need to pay attention to the following lines in the method which print out xml files.
XMLIOUtilityTransformer transformer = tFactory.newTransformer();
// create this attribute to enable "auto-line-wrap" function
transformer.setOutputProperty(OutputKeys.INDENT, "yes");
// create this attribute (in JDK1.4 only) to enable "auto indent" function
transformer.setOutputProperty("{http://xml.apache.org/xslt}indent-amount", "2");
OK, I will also paste an example.
XMLResourceBundle class is convinient. But it is only supported by at least JDK1.5. Now I implemented a XMLResourceBundle class by JDK1.4 using DOM.
XMLResourceBundle
import java.io.File;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.Enumeration;
import java.util.Iterator;
import java.util.Properties;
import java.util.ResourceBundle;
import java.util.Vector;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;
import jp.co.worksap.durga.performance.applaunch.tool.HintUtility;
import jp.co.worksap.durga.performance.applaunch.tool.XMLIOUtility;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.w3c.dom.Attr;
import org.w3c.dom.Document;
import org.w3c.dom.DocumentType;
import org.w3c.dom.Element;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
import org.w3c.dom.Text;
/**
Author : ye_m
Date: Oct.18, 2011
Company : Works Applications.
*/
public class XMLResourceBundle extends ResourceBundle {
private File configFile;
private InputStream ins;
private boolean isReady;
private Logger log;
private OutputStream outs;
private Properties props;
public XMLResourceBundle(final String filename) {
this(filename, null);
}
public XMLResourceBundle(final String filename, final Class myLoader) {
super();
log = LoggerFactory.getLogger(getClass());
if (myLoader != null) {
InputStream ins = null;
for (int i = 0; i < 4; i++) {
ins = myLoader.getResourceAsStream(filename);
if (ins != null) {
isReady = init(ins, null);
break;
}
}
if (ins == null) {
isReady = false;
HintUtility.errorHint(false,
"Cannot Find Resource File under filename=" + filename,
"Error", log);
} else {
isReady = true;
}
} else {
if (!checkFile(filename)) {
isReady = false;
return;
}
isReady = init(new File(filename));
}
}
private boolean checkFile(String filename) {
if (!filename.toLowerCase().trim().endsWith(".xml")) {
return false;
}
File test = new File(filename);
if (!test.exists()) {
props = new Properties();
XMLIOUtility.saveToFile(parsePropsToDoc(), filename);
}
if (test.isDirectory()) {
return false;
}
return true;
}
public Enumeration getKeys() {
if (!isReady) {
return null;
}
Vector keys = new Vector();
for (Enumeration srckeys = props.propertyNames(); srckeys
.hasMoreElements();) {
keys.add(srckeys.nextElement().toString());
}
return keys.elements();
}
protected Object handleGetObject(String key) {
if (!isReady) {
return null;
}
return props.getProperty(key);
}
private boolean init(final File file) {
configFile = file;
return loadFromFile();
}
private boolean init(final InputStream configStream,
final OutputStream saveStream) {
ins = configStream;
outs = saveStream;
props = parseDocToProps(XMLIOUtility.readFromStream(ins));
return true;
}
public boolean isReady() {
return isReady;
}
private boolean loadFromFile() {
props = parseDocToProps(XMLIOUtility.readFromFile(configFile.getPath()));
return true;
}
private Properties parseDocToProps(Document doc) {
Properties props = new Properties();
if (doc != null) {
NodeList list = doc.getDocumentElement().getElementsByTagName(
"entry");
for (int i = 0; i < list.getLength(); i++) {
Element ele = (Element) list.item(i);
String key = ele.getAttribute("key").trim();
String value = XMLIOUtility.getNodeText(ele);
props.setProperty(key, value);
}
}
return props;
}
private Document parsePropsToDoc() {
DocumentBuilderFactory domFactory = DocumentBuilderFactory
.newInstance();
Document document = null;
try {
DocumentBuilder builder = domFactory.newDocumentBuilder();
builder.setErrorHandler(null);
DocumentType type = builder.getDOMImplementation()
.createDocumentType("properties", null,
"http://java.sun.com/dtd/properties.dtd");
document = builder.getDOMImplementation().createDocument(
"http://java.sun.com/dtd/properties.dtd", "properties",
type);
Element root = document.getDocumentElement();
Iterator iter = props.keySet().iterator();
String key = null;
while (iter.hasNext()) {
key = (String) iter.next();
String value = (String) props.getProperty(key);
Element child = document.createElement("entry");
Attr keyAttr = document.createAttribute("key");
keyAttr.setValue(key);
child.setAttributeNode(keyAttr);
Text text = document.createTextNode(value);
child.appendChild(text);
root.appendChild(child);
}
document.getDocumentElement().normalize();
} catch (ParserConfigurationException e) {
}
return document;
}
public void save() {
if (configFile != null) {
XMLIOUtility.saveToFile(parsePropsToDoc(), configFile.getPath());
} else if (outs != null) {
XMLIOUtility.saveToStream(parsePropsToDoc(), outs);
} else {
// No perfmit to Write
}
}
public void setNewValue(final String key, final Object obj) {
if ((isReady) && (key != null) && (obj != null)) {
props.put(key, obj.toString());
}
}
public Object removeValue(final String key) {
if ((isReady) && (key != null)) {
return props.remove(key);
}
return null;
}
}
.The Class HintUtility did nothing but invoking System.out.println() to print messages.
2011年10月15日星期六
日本筑波宇航中心一日游
昨天是2011年10月15日,一年一度日本宇航研究中心的对外开放日。该中心位于茨城县つくば市,按照势力范围,应该属于筑波大学城的一部分。
虽然天公不作美,淅淅沥沥雨不停,但是怀着对宇宙的好奇与梦想,我们一家早上7点钟就爬起来,赶接近两个小时的地铁,在10点开门前就赶到了宇航中心。
这地方占地面积很小,建筑物看起来也很普通,门口有两个慈眉善目的老爷爷在指挥进出的车辆,并没有荷枪实弹的警察和军人,没有醒目的标语和口号,房子大多建得四四方方一个样,花园也没啥特色,乍一看怕是还不如浙江的民间工厂气派,更别提中国声明赫赫的几大“航天城”了。没办法,估计是资源贫乏吧,呵呵。
一进门就看见了这个真实的火箭。这不是模型,是真的火箭,发动机啥的都是真家伙。
参观展览馆
我们首先去的是展览馆,这里陈列着各类航天器的实物和模型。而且都配着非常详细的解释。今天是开放日,还有工作人员义务讲解。我在这里的感觉就是极大地开阔了视野。能够如此近距离地接触这些满载人类飞天幻想的器物,并且了解到原来它们的结构和原理其实并不复杂,真是太幸运了。
一进门有一个硕大的地球模型。上面立着一些卫星的航天器的小模型。生动地告诉你这些东西都在什么地方,以及他们的样子,轨道高度,和大概的数量。非常生动。
这是目前正在使用中的,美,日,欧共同开发维护的太空站微缩模型,背后还有一个一比一的大家伙。讲解员很自豪地告诉我们,其中哪里哪里是在这里开发的,目前日本,美国,和欧洲每天分别管理这个太空站8个小时。日本的控制中心就在这里。
这个是安装有排泄物处理系统的宇航员太空行走服。哈哈哈。
大厅里陈列着各式各样的卫星实物和模型。有气象卫星,资源探测卫星,通信中继卫星,暗物质搜索卫星,甚至情报搜集卫星,等等。有的有两层楼那么高,像个巨大的长天线的包装箱,有的又圆圆的像个大垃圾筒,有个小巧玲珑,像电视机的盒子,有的黑乎乎的,里面是什么啥都看不见……
最让我感慨的是这个巨大的一比一真实空间站模型。其实也算是半实物。因为和天上那个是作为备份一起生产的,只不过没有用上,所以一些贵重的设备就拆掉换成模型了。
先看看全貌是什么样子的。
(巨大的机械手)
(进主舱内参观)
(真实的舱内控制台和实验台,我居然在机械臂控制器旁边发现放了一台Thinkpad的电脑,哈哈,哈哈哈。)
(这个模型演示平时航天员的生活和工作场所及方式)
(这个模型很欢乐,寓意五国共同开展空间站事业)
此外,这里还展示了日本独立研发的载人航天器——希望号航天飞船的一比一模型。只不过外表实在太丑,跟神舟号一样,像个巨大的垃圾桶。
还有小的比例模型。
以及陈列在一排的日本产火箭模型。
这里比较让我惊叹的,是真实的液体燃料火箭发动机。旁边还有原理说明图。再加上讲解员的说明,一下就明白了液体燃料喷射发动机的原理。
日本正在积极地开展探月活动,所以这里展示了完整的月球3D模型,和绕月探测器传回来的画面。
参观火箭及航天控制中心
这里据说涉及到机密数据,所以不然带相机进去。
房子里有两个控制室,都是玻璃墙,里面的情况看得很清楚。其中一个是空间站的控制室,里面的大屏幕上显示着空间站的摄像头目前观测到的景象。控制室里摆放着很多工作台,按照职责的不同分成好几个区。零散有几个人,正围着显示器在讨论着什么。房间不大,估计NASA和欧洲航天局那边也差不多。
里面的控制室稍微大一点,这里是日本自主研发的“神舟号”的控制室,感觉和外面那个没有太大区别,有几张桌子上还放着布娃娃玩偶。
因为我不是学这个的,也看不出什么名堂,就觉得有点拥挤,电脑显示器太多了点。另外,墙上没什么标语和口号,工作人员貌似都很休闲。和CCTV上看到的中国航天城控制室的紧张繁忙,“严肃认真”的感觉完全不一样。
这里很小,除了两间控制室就没别的东西了。
参观宇航技术研究开发中心和宇航设备测试中心
这里比较有意思,展出各类宇航用的机器人,探测器,光学电学设备,新材料新工艺等等。
这是个电动模型,台子上有一排按钮,分别表示空间站可以执行的各类动作,比如开舱门太空行走,搬运货物,回收卫星,释放卫星等等。
你按下相应的按钮,里面的模型就开始活动,展示给你看到底是怎么完成的。
很多宇航设备都是用液氮来冷却的。这是用液氮冰冻的棉花糖。我刚一咬,就“啪”一下四分五裂了,一口没吃到,郁闷。
这个也是电动模型。航天器出厂之前要做各类抗震和抗噪声测试。这个模型演示如何进行测试。简单来说,就是把(比如)卫星绑在一个振动台上,不停地上下左右前后地使劲晃荡,看它坏不坏。还要关到一个类似保险箱的地方,用超强的噪声去考验它,看里面的实验器材和电子设备会不会有问题。
还有这个是用在航天器上的万向反射镜头。无论测距激光从哪个角度射过来,都能按原路被折射回去。我不记得本科的时候学没学过这东西,但是看见实物就放在眼前,还是由衷感叹日本光学造诣很深。
(看见我的佳能Kiss5的镜头了吗?)
还有这个吓人的东西,把人绑上去转圈……以前一直听说这是挑选平衡感优秀的飞行员用的。结果这里的负责人很认真的告诉我,这东西只不过是用来甄选身体有缺陷的候选人的。所有进入过太空的航天员,80%的人平衡感都一般般。最后谁能上天,跟在这椅子上的表现没关系。
插曲:遇见学术大牛
这里演示的是在外太空中机器人是如何前进的,因为大家都飘着,不能“走路”,机器人又没有灵活的手脚,所以现在都是像蜘蛛人一样,靠绳索前进。
负责介绍的老先生非常亲切,而且看我们说英文,就用英语给我们做了非常详细介绍,发音标准,口音地道美国腔,非常厉害。后来我们在实验室外面的展板上看见,这位老先生名叫Oda Mitsushige,是日本宇航中心(JAXA)的宇宙机器人开发部负责人,刚刚参加了2011年9月在美国长滩举行的AIAA(美国航空航天学会,参见美国航空航天协会介绍)年会,获颁AIAA宇航自动化及机器人奖章,以表彰其在该领域所作出的卓越研究贡献(参见AIAA年会通信)。
啊呀呀呀,牛人啊牛人啊。只是通行的日本友人都出来了,我就不好意思再排队进去重新握手拍照签名留念。好在刚刚不知情的情况下随手拍了一张。
这个级别的牛人,在国内的话应该算得上是比较牛的院士级别了,行政级别应该至少是航天某院院长级别的人了,还亲自参加旨在大众科普的开放日活动,并且这么慈眉善目地给我们这些航天小白进行细致认真的双语讲解。难得啊难得啊。
这种机会在国内上哪里找去?
发发牢骚:载人航天的大科学家王永志和袁家军同志,我,一介草民,想免费参观真实的神舟系列飞船,并且希望您能亲自给我讲解一下里面的原理和构造,答疑解惑,不知道您有没有时间和这个心情?哪怕两年一次也行,我自己出交通费……
临走以前经过JAXA主楼大厅,一大堆小朋友在工作人员的指导下拼装火箭和卫星的模型。
工作人员问我们有没有兴趣参与载人航天,探索宇宙。我高举双臂,不过同行的日本小孩却表示没兴趣。工作人员让大家把理由写下来贴在宇航中心的迎宾墙上。我写下了“For curiosity and my dream, I want to visit the universe. (出于好奇心和梦想,我希望访问宇宙)”。同行的日本小孩写下了拒绝的理由“スベースシャット爆発かもしれない(太空飞船可能会爆炸)”
我很无语……
结束
从这里离开以后,我一直在感慨,日本这片土地上不缺乏高科技,而且作为普通的民众居然有如此之多之好的机会来接触,学习,亲身体验和实践。只要未来的日本小孩想学,愿意去学,他们取得进步将是非常容易的事情。
而我从小就想接触飞机火箭啥的,却活了26年,才有机会真正了解空间站是怎么工作的,火箭发动机是怎么工作的,太空机器人是怎么运动的。唉……
中国也有高技术,我们有更壮观宏伟气魄的科研基地和硬件设备,可是国民怎么就没有近距离接触它们的机会呢?
我们的高科技研究所为什么基本没有面对普通民众的开放活动?为什么经常让全副武装凶神恶煞的警卫守门?是要将民众拒之千里吗?普通路人连进去上卫生间都不被允许,哪里还有胆量去“窥测国家机密”?还有我们的教授们,什么时候也能够越牛的人越没有架子呢?什么时候也会觉得,将自己工作最精华的部分讲给完全不认识,嘴里还啃着棉花糖的科技小白听也是非常重要的事情呢?
唉,到底是谁缺乏资源?
我虽然还没有踏上过美国和西欧的土地,但是我感觉,这些发达社会政府对于科技和民众教育的态度应该跟日本没区别。
回家前,我对日本同事说“JAXA的研究人员科普工作做的真好!但这样的活动不影响他们自己的工作吗?”,结果日本同事很淡定地回答“是我们在交税,他们的研究和收入都源自国家的税收。他们有义务这么做。”
我再次无语……
How to get the file path of current/target class in JAVA?
I recommend to use the ClassLoader.getResource() method. Because this method can also fetch back the file path even within the jar package.
Now let me show you a simple demo.
Assuming that we have the following folder in Disk D:
| D:\ TestProject |-----> src |-----> bin | ------> testcase |--------> TestCase1.class |--------> TestCase2.class |--------> subfolder |---------> TestCase3.class |
| Class Name | Absolute Path |
| TestCase1.class | D:\TestProject\bin\testcase\TestCase1.class |
| TestCase2.class | D:\TestProject\bin\testcase\TestCase2.class |
| TestCase3.class | D:\TestProject\bin\testcase\subfolder\TestCase3.class |
Reference CodeClassLoader loader = TestCase2.class.getClassLoader(); /** * Code Part 1 */ URL url = loader.getResource(TestCase1.class.getName().replaceAll("\\.","/")+".class"); String path = url.getPath(); // here the output will be "/D:/TestProject/bin/testcase/TestCase1.class" /** * Code Part 2 */ URL url = loader.getResource(TestCase2.class.getName().replaceAll("\\.","/")+".class"); String path = url.getPath(); // here the output will be "/D:/TestProject/bin/testcase/TestCase2.class" /** * Code Part 3 */ String rawPath = "subfolder/"+TestCase3.class.getName(); URL url = loader.getResource(rawPath.replaceAll("\\.","/")+".class"); String path = url.getPath(); // here the output will be "/D:/TestProject/bin/testcase/subfolder/TestCase3.class"
2011年10月14日星期五
How to solve Date Issues in Java
So you can input a String (i.e. “
2001.07.04 AD at 12:08:56 PDT”), and get the Date Object by Java Methods.In contrast, you can also provide a Date Object (or long number, etc.), and print the date as required date format easily.
What you need to done is just define the format String, i.e. “yyyy-mm-dd HH:mm:ss”.
(Pay attention to the capticals, because they mean different format).
Here is a simple demostration.
Reference Codeimport java.text.DateFormat; import java.text.ParseException; import java.text.SimpleDateFormat; import java.util.Date; import java.util.Locale; import junit.framework.TestCase; public class DateFormatTest extends TestCase { private final static String date1 = "2011-10-10 22:12:34"; private final static long dateLong1 = Long.parseLong("1318252354000"); private static DateFormat formatter1 = new SimpleDateFormat( "yyyy-MM-dd HH:mm:ss"); private final static String date2 = "AM 12:34:56 04/09/85 JST"; private final static long dateLong2 = Long.parseLong("481822496000"); private static DateFormat formatter2 = new SimpleDateFormat( "aa hh:mm:ss MM/dd/yy zzz", Locale.ENGLISH); public void test1() throws ParseException { long dateLong = formatter1.parse(date1).getTime(); System.out.println(this.getName() + ": Long Number is " + dateLong); assertEquals(dateLong1, dateLong); } public void test2() throws ParseException { String dateString = formatter1.format(new Date(dateLong1)); System.out.println(this.getName() + ": Formatted Date String is " + dateString); assertEquals(date1, dateString); } public void test3() throws ParseException { long dateLong = formatter2.parse(date2).getTime(); System.out.println(this.getName() + ": Long Number is " + dateLong); assertEquals(dateLong2, dateLong); } public void test4() throws ParseException { String dateString = formatter2.format(new Date(dateLong2)); System.out.println(this.getName() + ": Formatted Date String is " + dateString); assertEquals(date2, dateString); } }
test1: Long Number is 1318252354000 test2: Formatted Date String is 2011-10-10 22:12:34 test3: Long Number is 481822496000 test4: Formatted Date String is AM 12:34:56 04/09/85 JST
From Javadoc of JDK, we can easily learn how to write the format String.
Be careful on how to control the length of the items: i.e. the “yy” means here display the year, and two digits will be displayed.
Also, the “/” or “-” (or others) which are not defined in the table, will mean the separator.
2011年10月10日星期一
Eclipse HotKeys
Ctrl + Shift + O : quickly organize the import sections.
Ctrl + '/' : quickly note/de-node the source code
Ctrl + E : open source file
Ctrl + Alt+ 'up' : copy current line and insert it into current position
Ctrl + Alt + 'down' : copy current line and insert it into next line.
Ctrl + D : delete current line
Ctrl + 'Z' : undo the latest operation
Ctrl + 'Y' : repeat the canceled operation
Ctrl + Alt + '/' : in xml editor, quickly note the SELECTED lines
Ctrl + Alt+ '\' : in xml editor, quickly de-note the SELECTED lines
2011年10月6日星期四
Why java hang when invoking WMIC command
e.getRuntime().exec(.....)).
I use the following code, but unfortunately, my java appears to "deadlock".
public void testWMIC(){ final String command = "cmd /c wmic.exe Process get processid /format:csv"; ProcessExecutor executor = new ProcessExecutor(command, ProcessExecutor.class); executor.start(); executor.waitFor(500); }
I search many web sites, read the instructions about how to use Runtime.exec() in Java, but there was no hint for this issue.
Finally, I found a website, which said that sometimes the program invoked by command does NOT "Stop".
Although I feel it is ridiculous, I tried the following command. This time everything works OK.
final String command = "cmd /c wmic.exe Process get processid /format:csv <NUL";
Reference Code 1
Reference Code import java.io.IOException; import org.slf4j.Logger; import org.slf4j.LoggerFactory; public class ProcessExecutor extends Thread { protected Logger _log; private String command; private Process child; private boolean isValidProcess = true; public ProcessExecutor(String command, Class logType) { _log = LoggerFactory.getLogger(logType); this.command = command; } public Process getChildProcess() { if ((child == null) || (isValidProcess)) { try { Thread.sleep(100); } catch (InterruptedException e) { e.printStackTrace(); } } return child; } public void waitFor(long time) { long times = time / 100; while (isAlive()&&(times>0)) { try { Thread.sleep(100); times--; } catch (InterruptedException e) { e.printStackTrace(); } } } public void run() { child = null; isValidProcess = true; _log.info("New Invocation Command is {}", command); child = exec(command); if (child == null) { isValidProcess = false; return; } final StreamGlobber s1 = new StreamGlobber(_log, java.util.logging.Level.INFO, child.getInputStream()); final StreamGlobber s2 = new StreamGlobber(_log, java.util.logging.Level.SEVERE, child.getErrorStream()); s1.start(); s2.start(); try { if (child != null) { child.waitFor(); } } catch (final InterruptedException e) { e.printStackTrace(); } } private Process exec(String command) { Runtime run = Runtime.getRuntime(); try { return run.exec(command); } catch (IOException e) { _log.error(e.getMessage()); return null; } } }
Reference Code 2
Reference Code import java.io.BufferedReader; import java.io.InputStream; import java.io.InputStreamReader; import java.util.logging.Level; import org.slf4j.Logger; public class StreamGlobber implements Runnable { private Level _level; private InputStream _is; private Thread _thread; private Logger _log; private boolean alive; public StreamGlobber(final Logger log, final Level level, final InputStream is) { this._log = log; this._level = level; this._is = is; } public void start() { _thread = new Thread(this); alive = true; _thread.start(); } public boolean isAlive(){ return alive; } public void run() { try { InputStreamReader isr = new InputStreamReader(_is); BufferedReader br = new BufferedReader(isr); while (true) { String s = br.readLine(); if (s == null) break; if (_level.equals(Level.SEVERE)) { this._log.error(s); } else { this._log.info(s); } } alive = false; _is.close(); } catch (Exception ex) { _log.error(ex.getMessage(), ex); } } }