Labels

continuous integration (7) hudson (7) jenkins (7) mac os x (5) git (4) maven (4) android (3) charles (3) launchd (3) scm (3) bitbucket (2) dvcs (2) jnlp (2) mercurial (2) ant (1) apple (1) basex (1) chrome (1) cloud server (1) cobertura (1) css (1) cvs (1) firefox (1) general (1) hardy (1) http (1) iptables (1) java (1) javascript (1) linux (1) lucid (1) python (1) stresstest (1) subversion (1) svn (1) ubuntu (1) xen (1) xml (1) xpath (1) yui2 (1)

2011/06/30

javax.net.ssl.SSLPeerUnverifiedException after installation of a new JDK on MacOSX


  • After installing the new JDK (1.6.0_26) as normal user having the authentication dialog pop up for my admin account. I had loads of problems with javax.net.ssl.SSLPeerUnverifiedException popping up.
  • I even was not able to start the /Applications/Utilities/Java\ Preferences.app/ and got a strange error.
  • Logging in as admin did not help either, I still was not able to start the preference app.
  • I downloaded the JDK as admin again and repeated the installation.
  • I rebooted my system and now was able to open the preference app, reset to default options and the javax.net.ssl.SSLPeerUnverifiedException were gone.

2011/01/26

Using maven-release-plugin and maven-scm-plugin to tag all submodules of a multimodule project

I just created a sample multi module maven project in which by using the maven-release-plugin and the maven-scm-plugin I achieved my goal to create additional tags for the module artifacts as well. For a rationale see the included README.

There are two branches, one working with git and one with Subversion (in the master branch).

2011/01/02

cobertura plugin and maven3 in a Hudson Installation

Now that Hudson 1.392 supports Maven3 I switched my first job to Maven3. One small caveat: you need a new, not released version of the Cobertura Plugin, more information is found in HUDSON-8362.

2010/11/28

Triggering Hudson parameterized builds which include a file parameter using curl

My final goal is to run mvn release:prepare on my local machine to have greater control and trigger the actual mvn release:perform on Hudson, which will do the deployment in a controlled environment and archive the build log.

To achieve this, I want to upload the generated release.properties to the Hudson instance. This should be possible using the Parameterized Trigger Plugin. The tricky part is that the proposed solution on the plugin's Wikipage using buildWithParameters seems not to work, I always got HTTP/400 or HTTP/500 responses. After some tries and an analyze of the traffic with Charles I came up with two solutions, one using token authentication, the other one basic authentication. The important part seems to be to include the parameters json and Submit as well. Note that the file parameter is numbered, i.e. it is called file0.

Token authentication

curl -i -Fname=release.properties -Ffile0=@FILE_TO_UPLOAD  -Fjson='{"parameter": {"name": "release.properties", "file": "file0"}}' -FSubmit=Build  'http://HUDSON/hudson/job/JOBNAME/build?token=TOKEN'

The advantage of this is that no further user interaction is required, however you do not know who triggered the build.

Basic HTTP authentication

curl -i -uUSERNAME -Fname=release.properties -Ffile0=@FILE_TO_UPLOAD -Fjson='{"parameter": {"name": "release.properties", "file": "file0"}}' -FSubmit=Build  'http://HUDSON/hudson/job/JOBNAME/build'

The advantage of this is you know who triggered the build.

2010/11/12

Using iptables on Android to redirect HTTP connections to a running Charles proxy instance

During development it is often desirable to inspect the HTTP requests from your applications. As reported in Android Issue 1273 there is no easy way to set a HTTP proxy when using WIFI. In this article I describe how to use Charles as a Webproxy at least for unencrypted connections.

Unfortunately, you have to root your telephone, as otherwise you are not allowed to call iptables. Rooting is easy to do, visit unrevoked and follow the instructions. If you want to install a custom rom with Froyo just follow the instructions on Wildpuzzle (or any other) ROM for HTC Wildfire.

Then install Charles, see my article on Using BaseX and Charles. Start it up and configure Charles to be a transparent HTTP proxy in Proxy/Proxy Settings....

I assume you installed the Android SDK (for Mac OS X use Homebrew, see my article on starting an Android emulator via LaunchAgent for specifics).

On your device allow USB Debugging (Settings/Applications/Development/USB Debugging). Now connect your rooted device via USB. Enter adb shell, you should be greeted with a sh-3.2 prompt. In this example 192.168.51.9 is the address of the computer running Charles, 8888 is the port.

sh-3.2# iptables -t nat -A OUTPUT -p tcp -o eth0 --dport 80 -j DNAT --to 192.168.51.9:8888
FIX ME! implement getprotobyname() bionic/libc/bionic/stubs.c:378

You may ignore the error.

sh-3.2# iptables -t nat -L -nvx
Chain PREROUTING (policy ACCEPT 19 packets, 4832 bytes)
    pkts      bytes target     prot opt in     out     source               destination         

Chain POSTROUTING (policy ACCEPT 1068 packets, 65421 bytes)
    pkts      bytes target     prot opt in     out     source               destination         

Chain OUTPUT (policy ACCEPT 1050 packets, 63721 bytes)
    pkts      bytes target     prot opt in     out     source               destination         
       8      472 DNAT       tcp  --  *      eth0    0.0.0.0/0            0.0.0.0/0           tcp dpt:80 to:192.168.51.9:8888 

Hint: On Mac OS X you have to allow incoming connections to your computer e.g. by going to System Settings/Security and disabling the firewall. Now you should see all your unencrypted HTTP connections going through Charles.

To disable using Charles as a proxy enter:

sh-3.2# iptables -t nat -F OUTPUT

This will reset the routing again and all HTTP connections will go directly to the hosts again.

Unfortunately this approach will not work for encrypted connections right now, I am still investigating this.

2010/10/15

Using BaseX to grep through Charles output

BaseX is a fantastic tool to grep through large XML files by creating indices for text, attributes and path summaries. I use this to analyze data generated by Charles, an HTTP proxy / HTTP monitor / Reverse Proxy. Both tools are written in Java, so you should have no problems running them. While the latter is not OSS, it comes at a reasonable price and may be used in a trial version for 30 days after which you get a nagging dialog.

Charles may be used as a simple tool to run stress tests. Just choose it as a proxy, run your usual usecases and export the data to xml. Two of the power features Charles offers are Man in the middle for SSL connections by importing the Charles Root CA certificate and modifying your requests on the fly to use test systems of new software instead of the live ones. Afterwards you may check the output by grepping your expected results using BaseX using XQuery or XPath. An example:

  • Start Firefox creating a new profile /Applications/Firefox.app/Contents/MacOS/firefox-bin -profileManager called Charles.
  • Download and install Charles' Firefox extension by visiting the download site and restart Firefox after installation.
  • In the Tools menu of Firefox Charles offers to install the CA certificate.
  • Make sure you have Charles running and choose to proxy Firefox in it's Proxy menu.
  • Enable Charles in the Tools menu of Firefox, now you should see requests coming through Charles.
  • Search for hgkit in Google.
  • Drill down in Charles tree view and find the http://www.google.de/search?client=firefox-a&rls=org.mozilla%3Aen-US%3Aofficial&channel=s&hl=de&source=hp&q=hgkit&meta=&btnG=Google-Suche request.
  • From the context menu of this request choose Repeat advanced and enter 100 iterations with 5 concurrent requests making sure to use a new session.
  • Export the new session in Charles as google-hgkit.xml.
  • Now start BaseX and create a new database referencing google-hgkit.xml. If you encounter an error Invalid byte 1 of 1-byte UTF-8 sequence make sure to use the built in parser in the Parsing tab. Make sure you chose Options/Realtime execution.
  • Analyze your data:
    • A search for /charles-session/transaction should result in 100 hits.
    • A search for /charles-session/transaction/response[@status="200"] should result in 100 hits.
    • As the html returned by the search is escaped in the body, you need to use XML escaping in your search through the body.
    • A search for /charles-session/transaction/response[@status="200"]/body[contains(text(), "this_surely_will_not_show_up_will_it_dsddada")] should result in 0 hits.
    • A search for /charles-session/transaction/response[@status="200"]/body[contains(text(), "<a href="http://hgkit.berlios.de/")] should result in 100 hits.
    • The Xquery for $y in (for $x in /charles-session/transaction where $x/response/@status="200" return ( $x/@endTimeMillis - $x/@startTimeMillis)) order by $y descending return $y will return the times for successful requests in milliseconds in descending order.
    • Return all requests taking more than 300 milliseconds: for $y in (for $x in /charles-session/transaction where $x/response/@status="200" return ( $x/@endTimeMillis - $x/@startTimeMillis)) where $y > 300 order by $y descending return $y.
    • Return the count for the above requests:
      let $times := (for $x in /charles-session/transaction 
        where $x/response/@status="200" 
        return ($x/@endTimeMillis - $x/@startTimeMillis))
      let $slowQueries := for $y in ($times) where $y > 300 return $y
      return count($slowQueries)
      

You could try to trigger a second search with a different searchterm and analyze that the search results are not mixed up by querying, e.g.
/charles-session/transaction[contains(@query, "q=hgkit")]/response[@status="200"]/body[contains(text(), "<a href="http://hgkit.berlios.de/")]. You may select more than one request in Charles for repetition. For further instructions on XPath I recommend w3school's tutorial.

2010/09/27

Starting an Android emulator automatically on MacOSX after Login via LaunchAgent

Homebrew offers a simple means to install additional software packages on your MacOSX computer. After initial installation of brew as admin user execute:

brew install android-sdk # will install the newest SDK starter package
android update sdk # this will open the UI, now install all platforms
chgrp -R staff /usr/local/Cellar/android-sdk/r7 # otherwise the ANDROID_HOME will be owned by the wheel group and you may not start anything as non admin user.

To use tools like the emulator add ANDROID_HOME and ANDROID_SDK_ROOT to your $HOME/.profile or $HOME/.bash_profile (if the latter exists, use this):

ANDROID_SDK_ROOT=/usr/local/Cellar/android-sdk/r7
ANDROID_HOME=$ANDROID_SDK_ROOT
export ANDROID_SDK_ROOT ANDROID_HOME

Create an emulator called Wildfire using the android command. Now if you want the emulator to be started automatically after you login, put the following into $HOME/Library/LaunchAgents/emulator-wildfire.plist:

After you saved the file, execute launchctl load $HOME/Library/LaunchAgents/emulator-wildfire.plist. From now on the emulator starts whenever you (or your CI user) logs in.