Thursday, February 2, 2012

Add custom application launcher in Fedora 16/Gnome 3

The application launchers that appear when you bring up the Activities Overview when pressing the windows button, can be customized by adding or modifying desktop entry files.

There are two places where you can add new desktop entry files depending on whether the launcher icon should be available for all users or only a single user.

For example, to create a launcher for the eclipse IDE:

Global (all users) -
/usr/share/applications/eclipse.desktop

Local (single user) -
/home/myusername/.local/share/applications/eclipse.desktop

Assuming that eclipse is installed to /opt/eclipse, the eclipse.desktop file would look something like this:
[Desktop Entry]
Name=eclipse
Type=Application
Categories=Development
Exec=/opt/eclipse/eclipse
Icon=/opt/eclipse/icon.xpm
Terminal=false

Hope this helps!

Tuesday, November 22, 2011

Signed and Unsigned

Here are some quick scripts to sign every jar in a directory, and then unsign every jar.

Sign

find . -name "*.jar" -exec jarsigner -keystore /path/to/your/key -storepass yourpassword '{}' yourkeystorename \;

Unsign

find . -type f -iname '*.jar' -exec zip -d '{}' META-INF/*.{SF,RSA} \;

Tuesday, April 19, 2011

Http Proxy Server

How does an HTTP proxy server work? I learned a little about this recently while trying to implement one using Apache, mod_python, and Python. HTTP is a relatively simple protocol. A connection is opened to a server, and a request in the form of a string is sent. For example, to get a web page, you just send a simple get request and wait for the web page (or an error code) to be sent back to you.

GET /path/to/file/index.html HTTP/1.0

However, there is no server information in this request, so how does a proxy server know what you want? After you configure your browser or other client to use a proxy, the client opens a connection to the proxy server for each request, and sends a slightly different get request for each page.

GET http://someserver:80/path/to/file/index.html HTTP/1.0

Notice that this get request includes the full URL (including the server and port). This tells the proxy server which server contains the actual content. So the proxy server connects to the specified server, and pipes the appropriate content back to you.

The problem I face is that I need a way to track groups of requests coming from a particular client process. For example, let's say the user has two browsers and I want a separate log file containing all the downloads made by each browser. I can't track by IP address (they are the same), I can't track by modification to the URL since most client apps don't support adding information other than the servername and port. So this leaves the authentication mechanism. Each browser will need to send a unique username, and that username will be used to track which client is making the request. For now, that's the solution I'm going with.

For more information, there is a nice introduction to HTTP here:
http://www.jmarshall.com/easy/http/
And for even more details, look at RFC 2616
http://www.w3.org/Protocols/rfc2616/rfc2616.html

Thursday, February 3, 2011

Extend TestCase and use annotations in JUnit 4

JUnit 3 required that test classes extend, directly or indirectly, the class junit.framework.TestCase, and that each test method begin with the word "test". In contrast, JUnit 4 uses @Test annotations for each test method and does not require the test class to extend junit.framework.TestCase. But what if we have some JUnit 3 and some JUnit 4 tests? JUnit 4 automatically treats classes that extend TestCase as a JUnit 3 test, and therefore ignores the @Test notation. So let's say there is a class like the following.

public class MyTests extends TestCase
{
@Test
public testOne()
{
//do stuff
}

@Test
public anotherTest()
{
//do stuff
}
}

Using JUnit 4, it would appear that both these tests are run, but actually only the first one runs. Why? Because the class extends TestCase, so JUnit 4 will handle this class using a JUnit 3 compatibility mode. This means that the @Test tag is ignored and the method names are examined for the pattern "test*". This can be fixed in two ways. The first is by removing "extends TestCase". This will cause JUnit 4 to run the test in normal mode instead of backwards compat mode.

The second option is to use a class annotation to force the class to be treated as a JUnit 4 test case. It looks like this:

@RunWith(JUnit4.class)
public class MyTests extends TestCase
{
...
}

This forces JUnit 4 to locate tests using annotations instead of using the older method name convention.

The solution using @RunWith was found in the JUnit yahoo group.

Friday, February 26, 2010

No %%Pages: comment in header!

After being able to print successfully for several months, I got this error message today while printing from my laptop with Fedora 10: "No %%Pages: comment in header!". I have no idea what it means, but after searching around there was a simple fix for me. From the printer properties GUI I noticed that the "Print Test Page" button was disabled. In the policies tab the printer state "enabled" box was unchecked. I checked the box to re-enable the printer, and voila, I was able to print again.

Monday, February 15, 2010

MojoFailureException vs. MojoExecutionException

There are two types of wrapper exceptions commonly used in Maven plugins, the MojoFailureException and MojoExecutionException. It's not obvious which one is the correct one to use, so here is a simple explanation. A MojoExecutionException typically means that an unexpected and unrecoverable error happened while running the plugin. This would be something like a NullPointerException or other RuntimeException that the plugin developer did not expect and/or can not handle. It's basically a plugin crash.

A MojoFailureException means that there was a problem in the build which the plugin detected, and the plugin is now notifying you of that failure. This would be something like a Java source file that couldn't compile. The build can not continue, but the plugin is still working normally.

More information can be found in the Sonatype Maven book.

Wednesday, January 6, 2010

Perl multiline search/replace

Quick perl program to do a multi-line search and replace.

open(INPUT,"<$ARGV[0]") or die;
$/ = "%%\n";

$theFile=<INPUT>;
#print $theFile;
close(INPUT);

#$theFile =~ s# \true\<\/optional\>\n##ig ;
$theFile =~ s# \<\/dependency\># \true\<\/optional\>\n \<\/dependency\>#ig;

open(OUTPUT,">$ARGV[1]") or die;
print(OUTPUT $theFile);
close(OUTPUT);