Friday, October 8, 2010

Mobile location targeting using latitude and longitude

With the rapid growth of mobile advertising, there is a need of knowing more accurately user’s location
Deciding on user location according to it’s ip is not accurate. Especially when user is using WAP, which assign the mobile device with an ip of some gateway.
More and more users allow applications to access their location. Publishers that has mobile device location can pass this information to mobile ad networks, in order to allow advertisers to target their campaigns more accurately.
The device location is defined by 2 parameters: longitude and latitude. These 2 parameters determine your location on the globe. Most modern smartphones can easily get this information. Applications can access this information if permission is granted by user.
So, after you convince your publishers to send you longitude and latitude of the user device (some will be able to send you this information and some won’t), you can start more accurately target your campaign’s geographical location.
How this can be technically done?
When creating a new campaign on your system, a new targeting should be added, allowing users to input this 3 values:
  • latitude
  • longitude
  • radius (in KM or whatever unit that works for you)
These 3 values allows the user to target the campaign for a specific point on the globe. Targeting a campaign for a specific point is not good enough, the radius parameter determines the area around the point for which we would like to target our campaign.
Of course, you can allow your users to define multiple values of latitude, longitude and radius, in order to target campaign simultaneously on several geographical locations.
In addition, you can also replace the input of latitude, longitude and a radius with a more visual way, like putting a map of the world and allowing user to visually drop points on the globe and define radiuses.
Let’s assume, that user inputs only a single set of: latitude, longitude and radius. What else do we need? The latitude and longitude of the user’s mobile device. We will get this information from the publisher. The information is send with the request for an ad as 2 parameters (latitude and longitude) or in whatever way you agreed with the publisher that this information is being passed.
To summarize, so far we have this information:
  • From campaign (defined when campaign is created):
    • Latitude
    • Longitude
    • Radius
  • From publisher (send on the ad request according to the latitude and longitude of user device):
    • Latitude
    • Longitude
What we have left to do?
Simply check if the location we got from the publisher falls in the location and radius defined for the campaign. If the location of the user device (received from publisher) is in the radius defined for campaign we should serve the campaign to the client, otherwise, we should search for another ad to show.
How do we check?
We calculate the distance between the 2 locations we have (the one defined for campaign and the one received from publisher) and see if this distance is smaller or equals to the radius we defined.
In order to calculate the distance between the 2 locations we will use the class Location which I have already write about on this post.
Let’s see how it looks in Java code. Suppose we have the following data
  • locationCampaign - Location of the campaign
  • locationUser – Location of user as it sent from publisher
  • radius - Radius in KM
For example:
Location locationCampaign = new Location(campaignLatitude, campaignLongitude)
Location locationUser = new Location(userLatitude, userLongitude)


the value in “isMatch” will contain “true” if the campaign should be delivered:
double distnace = locationCampaign.distnace(locationUser, KM);
boolean isMatch = ditance <= radius

Thursday, October 7, 2010

Show Java Quartz Scheduler information

Quartz is a great open source project that allows to do Job Scheduling. Quartz is a production stage open source project that has been around long enough to be trusted. You can integrate it in your applications in a very short time and benefit from simple to complex scheduling requirements.
After you integrate Quartz to your project, you don’t really know what is going on. Which job is currently running/not running, when was the last time a job fired, when will the job will fire again.
In order to know the state of your jobs, Quartz provides several informative methods. We will use these methods in order to visually show Quartz scheduler information. The information will be shown using a JSP page that will dynamically gather Quartz information and build a table of all the current existing jobs.
This is an example of how this page looks like:
 
The Quartz data that is shown in the table is:
  • Group – The group of the job (in Quartz every job belongs to a group).
  • Job – The name of the job.
  • Cron Expression – An expression that describes the times in which the job should run. Note, that not all Quartz jobs use cron expressions for their execution. It is also possible to schedule jobs to run according specific intervals.
  • Previous fire time – The last time in which job was executed.
  • Next fire time – The next time a job is scheduled to run.
  • Stateful – An indication if a job is Stateful. When a job is Stateful, no more than a single instance of that job will run at any given time.
  • Interruptable – Indication if the job can be interrupted. A job that can be interrupted should implement InterruptableJob interface.
  • Running – An indication if a job is currently running or not. In parenthesis will be shown the number of instances of the job that are currently running.
  • Actions – This column allows to do 2 actions with Jobs:
    • Exec – Allows to immediately execute a job without waiting for it to be fired.
    • Pause/Resume – Pause/Resume a job. This will prevent the job from being executed by the scheduler.
In addition to this data, note that a running job is marked as bold and a paused job is marked in red bold.
Let’s have a look at the JSP file that creates this table. It mainly contains 2 parts:
  • The first part is a Java code that handles the 2 actions: Exec and Pause/Resume. It is responsible of executing a job if the Exec action was pressed or Pausing/Resuming a job if a job was paused/resumed.
  • The second part, is the part that actually gets all the jobs information from Quartz and shows it as a table.
The JSP file that creates this table, gets an instance of Quartz Scheduler class from a singleton named: SchedulerSingleton. You can replace this line of code with whatever way you use to get access to your Scheduler instance.
And here is how the code looks like:
<%@ page import="com.todacell.management.SchedulerSingleton" %>
<%@ page import="org.quartz.*" %>
<%@ page import="java.util.Arrays" %>
<%@ page import="java.util.Date" %>
<%@ page import="java.util.List" %>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<%
try
{
  Scheduler scheduler = SchedulerSingleton.instance();
  String action = request.getParameter("action");
  if (action != null)
  {
    String groupParam = request.getParameter("group");
    String jobParam = request.getParameter("job");
    if (groupParam != null && jobParam != null) 
    {
      if ("exec".equals(action))
      {
        scheduler.triggerJob(jobParam, groupParam);
      }
      else if ("pause".equals(action))
      {
        if (scheduler.getTriggerState(jobParam, groupParam) == Trigger.STATE_PAUSED)
        {
          scheduler.resumeTrigger(jobParam, groupParam);
        }
        else
        {
          scheduler.pauseTrigger(jobParam, groupParam);
        }
      }
      response.sendRedirect("jobs.jsp");
      return;
    }
  }
%>
<head>
<title>Management Jobs</title>
<link rel="stylesheet" type="text/css" href="css.css">
</head>
<body>
<h1>Jobs Information</h1>
Current Time: <b><%= new Date() %></b><br/>
Scheduler State: <b><%= scheduler.isStarted() ? "Running" : "Not Running" %></b><br/><br/>
<table class="tableBorder" cellpadding="4" cellspacing="0">
<tr>
<td class="tdBorder bold center">
Group
</td>
<td class="tdBorder bold center">
Job
</td>
<td class="tdBorder bold center">
Cron Expression
</td>
<td class="tdBorder bold center">
Previous Fire Time
</td>
<td class="tdBorder bold center">
Next Fire Time
</td>
<td class="tdBorder bold center">
Stateful
</td>
<td class="tdBorder bold center">
Interruptable
</td>
<td class="tdBorder bold center">
Running
</td>
<td class="tdBorder bold center">
Actions
</td>
</tr>
<%
  String[] groups = scheduler.getJobGroupNames();
  Arrays.sort(groups);
  List<JobExecutionContext> executingJobs = scheduler.getCurrentlyExecutingJobs();
  for (String group : groups)
  {
    String[] jobs = scheduler.getJobNames(group);
    Arrays.sort(jobs);
    int i = 0;
    for (String job : jobs)
    {
      Trigger trigger = scheduler.getTrigger(job, group);
      JobDetail jobDetail = scheduler.getJobDetail(job, group);
      int numInstances = 0;
      for (JobExecutionContext jobExecutionContext : executingJobs)
      {
        JobDetail execJobDetail = jobExecutionContext.getJobDetail();
        if (execJobDetail.getKey().equals(jobDetail.getKey()))
        {
          numInstances++;
        }
      }
      boolean isPaused = scheduler.getTriggerState(job, group) == Trigger.STATE_PAUSED;
%>
<tr>
<%
if (i == 0)
{
%>
<td class="tdBorder" rowspan="<%= jobs.length %>">
<%= group %>
</td>
<%
}
%>
<td class="tdBorder <%= isPaused ? "error bold" : "" %>">
<%= job %>
</td>
<td class="tdBorder">
<%= trigger != null && trigger instanceof CronTrigger ? ((CronTrigger)trigger).getCronExpression() : "N/A" %>
</td>
<td class="tdBorder">
<%= trigger != null ? (trigger.getPreviousFireTime() != null ? trigger.getPreviousFireTime()  : "N/A") : "N/A" %>
</td>
<td class="tdBorder">
<%= trigger != null ? trigger.getNextFireTime() : "&nbsp;" %>
</td>
<td class="tdBorder center">
<%= StatefulJob.class.isAssignableFrom(jobDetail.getJobClass()) ? "YES" : "NO" %>
</td>
<td class="tdBorder center">
<%= InterruptableJob.class.isAssignableFrom(jobDetail.getJobClass()) ? "YES" : "NO" %>
</td>
<td class="tdBorder center">
<%= numInstances > 0 ? "<b>YES (" + numInstances + ")</b>" : "NO" %>
</td>
<td class="tdBorder center">
<a href="jobs.jsp?action=exec&group=<%= group %>&job=<%= job %>">Exec</a>&nbsp;|&nbsp;<a
href="jobs.jsp?action=pause&group=<%= group %>&job=<%= job %>"><%= isPaused ? "Resume" : "Pause" %></a>
</td>
</tr>
<%
i++;
}
}
%>
</table>
</body>
<%
}
catch (SchedulerException se) {
  se.printStackTrace();
}
%>
</html>

Note that this JSP file uses a style shit file named “css.css”. This css file gives a bit nicer look to the Jobs information page. You can download the “jobs.jsp” file as well as the “css.css” file from here.

Tuesday, October 5, 2010

How to calculate the distance between 2 locations (latitude and longitude) in Java

In this post I wrote how the distance between 2 ips can be calculated using Maxmind. Calculating distance between 2 ips is not accurate, since Maxmind actually extracts for each ip an estimated latitude and longitude and then does distance calculation. The extracted values of latitude and longitude don’t stand for the real location of the user, but for the location of the ip, which is most likely, the location of the isp/organization that owns the ip.
Modern mobile devices are capable of knowing the exact location of the user in terms of latitude and longitude. This opens a whole new set of business opportunities for services and applications. One of many of the needs of these services and applications is calculating the distance between 2 locations. Of course, each location, is described using latitude and longitude.
In order to calculate the distance between 2 locations we will create a class named: Location. The class will mainly contain:
  • Inner enumeration named: Unit, which defines 3 possible units in which the distance can be calculated:
  • 2 members:
    • longitude
    • latitude
  • 2 static conversion methods:
    • deg2rad – Convert digress to radians.
    • rad2deg – Convert radians to degrees.
  • 2 overloaded methods name distance:
    • First method calculates the distance for a given latitude and longitude.
    • Second method uses the first method to calculated the distance for a given Location instance.
The actual calculation of the distance takes advantage of the trigonometry functions: sin and cos (we will not get to the mathematical explanation).
Let’s have a look at the Location class:
package com.bashan.blog.geo;
 
public class Location {
 
private double latitude;
private double longitude;
 
public Location() {
 
public Location(double latitude, double longitude) {
  this.latitude = latitude;
  this.longitude = longitude;
 
public double distance(double latitude, double longitude, Unit unit) {
  double theta = this.longitude - longitude;
  double dist = Math.sin(deg2rad(this.latitude)) * Math.sin(deg2rad(latitude)) +
  Math.cos(deg2rad(this.latitude)) * Math.cos(deg2rad(latitude)) *
  Math.cos(deg2rad(theta));
  dist = Math.acos(dist);
  dist = rad2deg(dist) * 60 * 1.1515;
  switch (unit) {
   case KM:
     dist = dist * 1.609344;
     break;
   case MILE:
    dist = dist * 0.8684;
    break;
   }
  return (dist);
 
public double distance(Location location, Unit unit) {
  return distance(location.getLatitude(), location.getLongitude(), unit);
 
public static double deg2rad(double deg) {
  return (deg * Math.PI / 180.0);
 
public static double rad2deg(double rad) {
  return (rad * 180.0 / Math.PI);
 
public double getLatitude() {
  return latitude;
 
public void setLatitude(double latitude) {
  this.latitude = latitude;
 
public double getLongitude() {
  return longitude;
 
public void setLongitude(double longitude) {
  this.longitude = longitude;
 
@Override
public String toString() {
  return "Location{" +
  "latitude=" + latitude +
  ", longitude=" + longitude +
  '}';
 
public static enum Unit {
  KM, MILE, NAUTICAL_MILE
}
}

The Location class can be downloaded from here.

Let’s have a look at a small test program showing how the Location class is used. We will create 2 Location instances, one of Israel and one of Unites States. The location is more or less at the center of each country.
public static void main(String[] args)
{
  Location locationIsrael = new Location(31.5, 34.75); // Latitude and longitude of Israel
  Location locationUS = new Location(38, -97); // Latitude and longitude of United States
  System.out.print("The distance between Israel and US is: " +
  locationIsrael.distance(locationUS, Unit.KM) + " Kilometers");
}

And the output of this program:
The distance between Israel and US is: 10810.089569538533 Kilometers

Monday, October 4, 2010

How to take a Screenshot on iPhone

iPhone allows taking a screenshot very easily. In order to take a screenshot on your iPhone follow these steps:

1) Press the top right button of your iPhone.

2) While holding the top right button, press the main iPhone button.

Here is exactly where you have to press:

Untitled

You can find you screenshot by pressing the “Photos”. It is categorized under: “Camera Roll” album.

Sunday, October 3, 2010

Create folders on iPhone OS 4

iPhone that has OS 4 allows creating folders. If you have several applications that share the same category, you can easily put them under the same folder. This reduces the need to do paging on the iphone, if you have large number of applications. Each folder can hold up to 12 applications. I believe that more than 12 applications will really miss the point of easy and fast access.

The steps need to be done in order to create a folder are:

1) Point with your finger on an application from which you would like to create a folder (hold your finger on the applications). After about a second all the applications (icons) will start rotating and have “x” on their top left. It should look like this:

photo

2) Drag the application from which you would like to create a folder and drop it on another application that you wish to be on that same folder:

photo 3

3) Release your finger or wait a second or 2 and a folder will be opened. A name for the folder will be automatically suggested according to the category of the application for which you wanted to create a folder:

photojj

4) Edit the name of the folder if you want, then press on the folder in order to close it and finally the press the iPhone main button in order to release it from “reordering mode”:

photo lk2

Friday, October 1, 2010

Open Task Manager on a Remote Desktop session within a Remote Desktop session

Opening the Task Manager on your local machine is done by: <ctrl> + <alt> + <delete>

Opening the Task Manager on a remote desktop session is done by: <ctrl> + <alt> + <end>

So far, so good. But what if you are opening a remote desktop session inside a remote desktop session?

The following combination should do the work: <ctrl> + <shift> + <escape>

Thursday, September 30, 2010

iTunes software update – Network connection timeout

I wanted to update my new iPhone with a new version. Things seemed to be running fine. But when the download was finished I got this error:

"There was a problem downloading the iPhone software for the iPhone. The network connection timed out"

I tried running the update for several more times with no luck and exactly the same “Network connection timeout” error.

Finally, I got that the problem was due to the fact I was using Kaspersky Anti Virus. Pausing Kaspersky and running the update again solved the problem. I assume other anti viruses might cause the same problem.

Wednesday, September 15, 2010

Rename all files from one extension to another using DOS command line

I was looking for a fast way of massively renaming files from one extension to another. Apparently, DOS command line was pretty handy solving this issue.

For example, in order to rename all the files with extension “jpg” to “test” on the directory named “C:\My Pics” you should do:

ren "C:\My Pics\*.jpg" *.test

This is how it looks on the DOS command line:

1

Disable password complexity on Windows 2008 Server

Windows 2008 server enforces by default a pretty hard restrictive policy for defining user passwords. Actually, it is so hard, that after 15 minutes of trying to define a new password I simply gave up. Instead, I simply disabled the password complexity requirements.

Here is how you can easily disable password complexity on Windows 2008 Server:

First, you have to load a program named “gpedit”. Press on Windows “Start” button, and on the text box write: “gpedit.msc”. This is how it should look:

1

When “gpedit” is loaded, on the tree, go to: Computer Configuration –> Windows Settings –> Security Settings –> Account Policies –> Password Policy. This is how it looks:

2

On the right pane, you will see list of policies. Search for a policy named: “Password must meet complexity requirments”. It should be “Enabled”. In order to disable it, double click on the policy. A dialog will open:

3

Choose: “Disabled” value and press “OK”. That’s it. Now you will be able easily define/change passwords on Windows 2008 server.

Sunday, September 12, 2010

EXIF Eraser – Free EXIF/IPTC/XMP erasing software

A long time ago, I was using Delphi to write all of my software. I think Delphi was and still is the best choice for rapidly developing Windows UI applications (though I have to admit, I have superficial familiarity with Visual Basic and C#, that I believe are also good candidates for Windows UI development). The biggest problem with Delphi, is that you have to write in Pascal, which is kind of an anachronistic language.

Anyway, a month ago, I decided It will be a nice thing, to have a look at Delphi again, and check what way it did along the years I left it. I downloaded the latest Delphi version from http://www.embarcadero.com/, which I believe is currently the company that maintains and develops the future of Delphi. Back then, Delphi was strongly identified with Borland. I was surprised to find, that things didn’t changed much along the years. Many features of modern IDEs were added, but the main idea was pretty much identical.

In order to refresh my Delphi development skills, I decided to write a small utility program, that wipes EXIF, IPTC and XMP meta data from image files. EXIF (Exchangeable Image File) data is a record of what camera settings were used to take a photograph. This data is recorded into the actual image file. Therefore each photograph has its own unique data. EXIF data stores information like camera model, exposure, aperture, ISO, what camera mode was used and whether or not a flash fired. IPTC and XMP are also additional meta data that are attached to image files.

I named the utility: Free EXIF Eraser. The nice thing is, that it deletes EXIF, IPTC and XMP meta data without doing any modifications to the original image. That means, the quality of the original image is kept untouched.

It was so fun and easy to get back to Delphi development, that I decided to put a bit more effort on my small utility: I dedicated for it a special domain and created a home page. If you need a small and lightweight utility, that will easily erase EXIF, IPTC and XMP meta data, you can check: http://www.exiferaser.com