/* Copyright 2008-2010 Gephi Authors : Mathieu Bastian <mathieu.bastian@gephi.org> Website : http://www.gephi.org This file is part of Gephi. Gephi is free software: you can redistribute it and/or modify it under the terms of the GNU Affero General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. Gephi is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for more details. You should have received a copy of the GNU Affero General Public License along with Gephi. If not, see <http://www.gnu.org/licenses/>. */ package org.gephi.branding.desktop.reporter; import java.awt.Dimension; import java.awt.GraphicsEnvironment; import java.awt.Toolkit; import java.io.BufferedInputStream; import java.io.File; import java.io.FileInputStream; import java.io.InputStreamReader; import java.io.LineNumberReader; import java.io.OutputStreamWriter; import java.io.StringReader; import java.io.StringWriter; import java.lang.management.ManagementFactory; import java.lang.management.MemoryMXBean; import java.lang.management.OperatingSystemMXBean; import java.net.URL; import java.net.URLConnection; import java.net.URLEncoder; import java.text.MessageFormat; import java.util.MissingResourceException; import java.util.logging.Handler; import java.util.logging.Logger; import javax.xml.parsers.DocumentBuilder; import javax.xml.parsers.DocumentBuilderFactory; import javax.xml.transform.OutputKeys; import javax.xml.transform.Transformer; import javax.xml.transform.TransformerFactory; import javax.xml.transform.dom.DOMSource; import javax.xml.transform.stream.StreamResult; import org.netbeans.api.progress.ProgressHandle; import org.netbeans.api.progress.ProgressHandleFactory; import org.openide.DialogDisplayer; import org.openide.NotifyDescriptor; import org.openide.modules.ModuleInfo; import org.openide.modules.SpecificationVersion; import org.openide.util.Lookup; import org.openide.util.NbBundle; import org.w3c.dom.Document; /** * * @author Mathieu Bastian */ public class ReportController { private static final String POST_URL = "http://gephi.org/crashreporter/report.php"; public void sendReport(final Report report) { Thread thread = new Thread(new Runnable() { public void run() { ProgressHandle handle = ProgressHandleFactory.createHandle(NbBundle.getMessage(ReportController.class, "ReportController.status.sending")); try { handle.start(); Document doc = buildReportDocument(report); if (doc != null) { if (sendDocument(doc)) { handle.finish(); DialogDisplayer.getDefault().notify( new NotifyDescriptor.Message(NbBundle.getMessage(ReportController.class, "ReportController.status.sent"), NotifyDescriptor.INFORMATION_MESSAGE)); return; } } } catch (Exception e) { e.printStackTrace(); } handle.finish(); DialogDisplayer.getDefault().notify( new NotifyDescriptor.Message(NbBundle.getMessage(ReportController.class, "ReportController.status.failed"), NotifyDescriptor.WARNING_MESSAGE)); } }, "Exception Reporter"); thread.start(); } public Document buildReportDocument(Report report) { logMessageLog(report); logVersion(report); logScreenSize(report); logCPU(report); logMemoryInfo(report); logJavaInfo(report); logGLInfo(report); //logModules(report); return buildXMLDocument(report); } public boolean sendDocument(Document document) { try { //Get String from Document TransformerFactory factory = TransformerFactory.newInstance(); Transformer transformer = factory.newTransformer(); transformer.setOutputProperty(OutputKeys.INDENT, "yes"); transformer.setOutputProperty(OutputKeys.ENCODING, "UTF-8"); StringWriter sw = new StringWriter(); StreamResult result = new StreamResult(sw); DOMSource source = new DOMSource(document); transformer.transform(source, result); String xmlString = "report=" + URLEncoder.encode(sw.toString(), "UTF-8"); URL url = new URL(POST_URL); URLConnection con = url.openConnection(); // specify that we will send output and accept input con.setDoInput(true); con.setDoOutput(true); con.setUseCaches(false); con.setDefaultUseCaches(false); // tell the web server what we are sending //con.setRequestProperty("Content-Type", "text/xml"); //con.setRequestProperty("Content-Type", "application/x-www-form-urlencoded"); OutputStreamWriter writer = new OutputStreamWriter(con.getOutputStream()); writer.write(xmlString); writer.flush(); writer.close(); // reading the response InputStreamReader reader = new InputStreamReader(con.getInputStream()); StringBuilder buf = new StringBuilder(); char[] cbuf = new char[2048]; int num; while (-1 != (num = reader.read(cbuf))) { buf.append(cbuf, 0, num); } String serverResult = buf.toString(); System.err.println("\nResponse from server:\n" + serverResult); return true; } catch (Exception e) { e.printStackTrace(); } return false; } private Document buildXMLDocument(Report report) { try { DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); DocumentBuilder builder = factory.newDocumentBuilder(); Document document = builder.newDocument(); document.setXmlVersion("1.0"); document.setXmlStandalone(true); report.writeXml(document); return document; } catch (Exception e) { e.printStackTrace(); } return null; } private void logScreenSize(Report report) { Dimension screenSize = Toolkit.getDefaultToolkit().getScreenSize(); report.setScreenSize(screenSize); GraphicsEnvironment ge = GraphicsEnvironment.getLocalGraphicsEnvironment(); report.setScreenDevices(ge.getScreenDevices().length); } private void logCPU(Report report) { OperatingSystemMXBean bean = ManagementFactory.getOperatingSystemMXBean(); report.setNumberOfProcessors(bean.getAvailableProcessors()); String unknown = "unknown"; // NOI18N String str = System.getProperty("os.name", unknown) + ", " + // NOI18N System.getProperty("os.version", unknown) + ", " + // NOI18N System.getProperty("os.arch", unknown); // NOI18N report.setOs(str); } private void logMemoryInfo(Report report) { MemoryMXBean bean = ManagementFactory.getMemoryMXBean(); report.setHeapMemoryUsage(bean.getHeapMemoryUsage().toString()); report.setNonHeapMemoryUsage(bean.getNonHeapMemoryUsage().toString()); } private void logJavaInfo(Report report) { String str = System.getProperty("java.vm.name", "unknown") + ", " // NOI18N + System.getProperty("java.vm.version", "") + ", " // NOI18N + System.getProperty("java.runtime.name", "unknown") + ", " // NOI18N + System.getProperty("java.runtime.version", ""); // NOI18N report.setVm(str); } private void logVersion(Report report) { String str = ""; // NOI18N try { str = MessageFormat.format( NbBundle.getBundle("org.netbeans.core.startup.Bundle").getString("currentVersion"), // NOI18N new Object[]{System.getProperty("netbeans.buildnumber")} // NOI18N ); report.setVersion(str); } catch (MissingResourceException ex) { } } private void logGLInfo(Report report) { String output = report.getLog(); try { LineNumberReader lineNumberReader = new LineNumberReader(new StringReader(output)); String line; while ((line = lineNumberReader.readLine()) != null) { if (line.startsWith("GL_VENDOR:")) { report.setGlVendor(line.substring(11)); } else if (line.startsWith("GL_RENDERER:")) { report.setGlRenderer(line.substring(13)); } else if (line.startsWith("GL_VERSION:")) { report.setGlVersion(line.substring(12)); break; } } lineNumberReader.close(); } catch (Exception e) { } } private void logModules(Report report) { for (ModuleInfo m : Lookup.getDefault().lookupAll(ModuleInfo.class)) { String moduleStr = ""; SpecificationVersion specVersion = m.getSpecificationVersion(); if (specVersion != null) { moduleStr = m.getCodeName() + " [" + specVersion.toString() + "]"; } else { moduleStr = m.getCodeName(); } if (m.isEnabled()) { report.addEnabledModule(moduleStr); } else { report.addDisabledModule(moduleStr); } } } private void logMessageLog(Report report) { System.err.flush(); System.out.flush(); String ud = System.getProperty("netbeans.user"); // NOI18N if (ud == null || "memory".equals(ud)) { // NOI18N return; } Handler[] handlers = Logger.getLogger("").getHandlers(); handlers[0].flush(); File userDir = new File(ud); // NOI18N File directory = new File(new File(userDir, "var"), "log"); File messagesLog = new File(directory, "messages.log"); String log = ""; try { byte[] buffer = new byte[(int) messagesLog.length()]; BufferedInputStream f = new BufferedInputStream(new FileInputStream(messagesLog)); f.read(buffer); log = new String(buffer); } catch (Exception e) { } report.setLog(log); } }