The problem with appeal statistics

So a tweet today from the Refugee Council said:

My first thoughts were that doesn’t add up. A quarter of all decisions wrong first time?
This would mean that 90% of all decisions would have had to have gone to appeal. Surely we are a) granting more than 10% and b) appeals aren’t 100% of all refusals.

So I went to the Office of National Statistics and found the numbers released today.

Looking at Asylum data tables immigration statistics January to March 2015 volume 1 – as_01 we have the following numbers for 2014:

Total initial decisions 19,936
Total grants 8,096
Total refusals 11,840

Straight away we can see that 40% of cases are granted.

Then looking at Asylum data tables immigration statistics January to March 2015 volume 4 – as_14 we get the appeals information

Total appeals determined 6,130
Appeals allowed 1,744
Appeals dismissed 4,047

So the 28% figure has been found from 1,744 in 6,130.

However there were 19,936 decisions made in total in 2014, which results in 8.7%* of all applications being wrong first time.

This isn’t the first time I’ve seen groups take the percentage of successful appeals and then used them as a figure of number of times someone got it wrong, the Disability Living Allowance Assessments springs to mind with Tweets and Facebook posts.

* An issue with this number is that it’s comparing the number of initial application in 2014 with the number of appeals in 2014, it’s highly likely that some of the appeals made in 2014 were based on decisions years earlier, however that data doesn’t appear to be available.

Join NowTV and get a £10 shopping voucher – plus your chance to win more

So I’ve been with NowTV for over a year, and regularly used them since April. For just £6.99 a month I get access to 13 pay channels including Sky Atlantic, Sky One, Sky Living, Sky Arts 1 and Fox (plus the less watched ITV Encore, Discovery, MTV, Comedy Central, Disney, Nickelodeon, NickJr and Gold) through the internet.

Not only do they provide a catchup service for most new shows, but also boxsets of some you might have missed in the past, including The Wire, The West Wing, 24 and Game of Thrones (shows come and go, and some might have every season right now).

If you’ve not had NowTV before, they regularly offer a free £10 voucher to new customers as an incentive, and this time around they are also offering me a £10 voucher to get you to sign up. You just need to follow this special link for both us to be rewarded.

Not interested in TV, but love movies? Find Netflix is just full of old films? Well the reason why Netflix UK doesn’t have the best range possible, is due to a deal Sky signed many years ago with the studios to get them first dibs at pretty much every new films, and to have a 12 month exclusive period as well. This means at Christmas, Frozen, Spiderman 2 and The Lego Movie will all be on. And if those don’t do anything for you there are over 1000 films right now to choose from.

Again the £10 shopping voucher offer is available and not only that new customers get the first 30 days of films for free. Then it’s £9.99 a month after that. Here’s the movie link Don’t fancy paying a tenner every month? With NowTV you can stop and start whenever you want meaning that you could watch every blockbuster from last year for only £40 by dipping in every third month (hint, this is what I do).

NowTV is available on a number of devices, Chromecast, Apple TV, iOS, Android, PC, Mac, PS3/4, XBoxOne/360, Roku and some YouView boxes. Alternatively if you have none of those you can pick up a NowTV box for only £9.99 and it’ll do the trick for you (plus it comes with all the domestic UK catchup services).

Finally not only are NowTV giving away the £10 shopping voucher to my friends, I have a NowTV box plus some monthly vouchers to give away. Just signup via one of the two links and I’ll enter you into the draw.

If you are interested in seeing what new films and boxsets are on NowTV, I have two twitter account which tweet once they spot something new. @NowtvBoxsets and @NowTVFilms

TalkTalk Super Router v3 (HG635) DDNS with Cloudflare

Hopefully you’ve reached this page through Google, otherwise it’s unlikely you’ll have reason to read the rest of this blog post.

I recently received a new TalkTalk Super Router v3, which is made by Huawei and has the model number HG635. I was interested in getting some kind of Dynamic DNS set up and was pleased to see that it had some settings under Internet->Internet Services.

The options available were, TZO and other. As DynDns had just gone down the paid router after many years of being free I was keen to see if I could do something myself with “Other”. From here were a collection of settings including Protocol set to GNUDip.http. After a while of Googling it looked possible to set up my own GNUDip running on Perl speaking to my own DNS server. Except I couldn’t be bother to install Perl and I no longer managed the DNS server but now used CloudFlare.

I already had some code through the CloudFlare API where I opened a webpage from my home wifi, it took the IP I was coming from and update a CloudFlare record, I just needed to get my router to do that bit for me.

So I read through the GNUDip spec, and worked out each stage and created a PHP script which would provide the seed information, verify a change request and then update CloudFlare for me.

The PHP code is below and can be used to not only update CloudFlare, but any DNS provider if they have an API you can call.

Step 1:

In CloudFlare create a new subdomain to be used for your DDNS record. You want to make sure that it’s Off Cloud.


Step 2:

Find your CloudFlare API key


Step 3:

Run this PHP code, it’s only needed once to find the record ID of the subdomain you are using:

table { font-family: sans-serif; }
tr:nth-child(odd) { background: #ddd; }
td, th { padding: 3px; }
tr.header { background: pink; }
<tr class="header">
<th>Record ID</th>
<th>Cloudflare On</th>
$file = file_get_contents(
'' .
'&email=[email protected]'.
$json = json_decode($file,1);
foreach($json['response']['recs']['objs'] as $host) {


Step 4:

Now you’ve found the Record ID (in this case 138325147) you can create this PHP file. This is the one your router will speak to, so it needs to be on a webserver outside of your home network. I’ve also called the file cfddns.php

$timeout = 60; //seconds
$remote_ip = $_SERVER['REMOTE_ADDR'];
$key = 'JKLDlfmmkgkweglrkegj4:fjksd489ikjklJS|Ld'; #random gibberish, I just keyboard smash
$username = 'myddnsuser';
$password = 'reallysafepassword';
$cloudflare_api_key = 'cd9843940935390a03939e9302094b43529ab';
$cloudflare_email = '[email protected]';
$cloudflare_domain = '';
$cloudflare_subdomain = 'ddns';
$cloudflare_record_id = '138325147';
// have we been passed data?
if($_GET['user']) {
$salt = $_GET['salt'];
$time = $_GET['time'];
$sign = $_GET['sign'];
$domn = $_GET['domn'];
$user = $_GET['user'];
$pass = $_GET['pass'];
$reqc = (int)$_GET['reqc'];
$addr = $_GET['addr']; //IP address
log_good("REMOTE IP: " . $remote_ip . " QUERY STRING: " . $_SERVER['QUERY_STRING']);
if($salt && $time && $sign && $domn && $user && $pass) {
//check and update DNS
# validate the signature
if(md5($salt.$time.$key) != $sign) {
log_fail("Invalid signature for " . $user);
# check salt timeout
if(time() > $time + $timeout) {
log_fail("Salt value to old for " . $user);
#confirm request code
if($reqc < 0 || $reqc > 2) {
log_fail("Invalid client request code for " . $user);
# only one user so check
if($user != $username) {
log_fail("Unknown user " . $user);
# only one domain so check
if($domn != $cloudflare_subdomain.'.'.$cloudflare_domain) {
log_fail("Unknown domain " . $domn);
if($pass != md5(md5($password).'.'.$salt)) {
log_fail("Invalid password for " . $user);
if($addr == '' && $reqc = 0) {
$reqc = 1;
if($addr == '' && $reqc = 2) {
$addr = $remote_ip;
if($reqc == 1) {
// No idea what to do with this request so just return back success
html_output(array("retc" => 2), 'Successful offline');
log_good("SUCCESS: Offline request made");
else {
$file = file_get_contents(
'' .
$meta['retc'] = 0;
if($reqc == 2) {
$meta['addr'] = $addr;
html_output($meta, 'Successful update');
log_good("SUCCESS: IP updated to " . $addr);
else {
log_fail("Missing information");
else {
$chars = 'abcdefghijklmnopqrstuvwxyz0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ';
$len = strlen($chars) - 1;
$salt = '';
for($i=0; $i<10; $i++) {
$salt .= $chars[mt_rand(0, $len)];
$meta['time'] = time();
$meta['salt'] = $salt;
$meta['sign'] = md5($salt.$meta['time'].$key);
html_output($meta, 'Salt generated');
log_good("SALT SET: time=".$meta['time']." salt=".$meta['salt']." sign=".$meta['sign'] . " REMOTE IP: ".$remote_ip);
function html_output($meta, $body) {
header("Content-Type: text/html; charset=iso-8859-1");
$body .= "\n<pre>" . print_r($meta,1) . "</pre>";
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
<title>GnuDIP Update Server</title>
foreach($meta as $name => $content) {
<meta name="<?=$name?>" content="<?=$content?>">
<h2>GnuDIP Update Server</h2>
function log_good($text) {
error_log(date("y/m/d H:i:s")." ".$text."\n", 3, "ddns.log");
function log_fail($text) {
error_log(date("y/m/d H:i:s")." ERROR: ".$text."\n", 3, "ddns.log");
html_output(array("retc" => 1), $text);

Step 5:

Get the router to speak to the script


Step 6:

Sit back, hopefully from now onwards your router will update the IP address every time it changes.

One line weather summary

Home ScreenThe following is the relevant code to get Tasker, AutoLocation, Zooper and to display the one line weather summary on your phone.

It’s possible to not need AutoLocation and use the Tasker lat/lng but I was after testing the application, and you could use a different widget tool like Minimalistic Text, or even just a notification in the status bar.

Step 1:
Sign up to the API at
You don’t need to provide card details as the you get 1000 calls per day, and you shouldn’t get close to using them all (my peak is only 84 calls). At worst it would just stop working for the rest of the day.
Make a note of your API key.

Step 2:
Build this profile in Tasker (note you need your API key from step 1 as !!!!YOURAPIKEY!!!!)

Profile: Update Weather Text (46)
State: AutoLocation Location [ Configuration:Location Report Name: Weather ]
Enter: Weather V2 (28)
A1: Flash [ Text:Getting weather Long:Off ] 
A2: HTTP Get [ Server:Port: Path:forecast/!!!!YOURAPIKEY!!!!/%allatitude,%allongitude Attributes:units=uk Cookies: Timeout:10 Mime Type: Output File: Trust Any Certificate:Off ] 
A3: If [ %HTTPR = 200 ]
A4: JavaScriptlet [ Code:var info = JSON.parse(global("HTTPD"));
setGlobal("FORESUM", info.minutely.summary); Libraries: Auto Exit:On Timeout (Seconds):45 ] 
A5: Zooper Widget Pro Variable [ Configuration:#TWEATHERTEXT# = %TIME %FORESUM Package:org.zooper.zwpro Name:Zooper Widget Pro Variable Timeout (Seconds):0 ] 
A6: End If 
A7: AutoLocation Location [ Configuration:Stopping Location Monitor
Location Report Name: Weather
Update Type: No Power Package:com.joaomgcd.autolocation Name:AutoLocation Location Timeout (Seconds):0 ]

Step 3:
Build this profile in Tasker

Profile: Display Unlocked (61)
Event: Display Unlocked
Enter: Get Location For Weather (62)
A1: AutoLocation Location [ Configuration:Starting Location Monitor
Location Report Name: Weather
Update Type: Balanced Package:com.joaomgcd.autolocation Name:AutoLocation Location Timeout (Seconds):0 ]

Step 4:
Have a Zooper widget which has a text field with the content #TWEATHERTEXT#

Step 5:
Turn your phone off, wait a few seconds, then turn back on and unlock.
If the call is working you should first see a toast with “Getting Weather”, followed by the one line text.
You can remove these once you are happy everything is working, they are both in Weather V2, the first is at the top, the second is within the Javascriptlet, just delete flash(info.minutely.summary);

Lincoln Sports Direct

A recent planning application to Lincoln City council is looking at changing the use of the current Sports Direct in Lincoln from retail (A1) to a gym (D2).

Having inspected the plans Pure Gym are looking to have a weights, studio, spin and general areas, plus changing rooms with showers in their new 24 hour gym.


So what does this mean for Sports Direct? I doubt they would be leaving the city, and there is still any empty unit on Station Street where JJB used to be. But as I haven’t contacted anyone for a comment we will have to wait and see.

Of course Sports Direct may have no plans to move, planning applications are just that, a request for permission to change, not intent of action.

Automatically deleting old emails in Gmail

As a follow up to my post Deleting old emails in Gmail 3 years ago, I’ve now found a way to automatically delete old emails from Gmail.
This trick uses the rather unknown Google Scripts, a Javascript engine which runs on Googles servers.

  • Pop to Gmail and test some searches, eg label:webserver older_than:1m this will find all emails labelled webserver and are older than 1 month (full list of search options here.
  • Once you are happy that your search result has found the emails you don’t want, go to
  • Select Create script for GMail
  • Delete all the example code
  • Enter this code
    function deleteOldEmails() {
    var threads ='label:webserver older_than:1m');

    ensuring you replace label:webserver older_than:1m with your search phrase
  • Save you project
  • Press run
  • Once the notification at the top has gone, check back in Gmail to confirm your emails have been deleted.
  • To automate, click on the Clock icon, Add a new trigger. Select your function, you want it Time-driven, and for me I’ve selected Month timer, 1, Midnight to 1:00am

The result will be on the first of every month Gmail deletes all emails older than 1 month from my webserver folder.

o2 and the over zealous family filter?

So if you’ve been on social media this weekend you will have seen a number of tweets like this with people astounded that their site is being blocked by o2.

Did they discover this because they couldn’t access the site on their mobile? No because they followed a link someone else tweeted, entered their URL and saw the word BLOCKED.
So what exactly is “Parental Control”, this page on the o2 website explains:

Parental Control is a service we offer to help parents to protect their children while they’re online. It enables us to restrict children’s web access via their mobile to a limited number of sites which are suitable for children.

It’s opt-in, and mainly aimed for children under the age of 12 who for some reason have their own mobile. As such it’s a whitelist of sites known to be ok. Search for lego and you get this:
Parent control isn’t part of the government “think of the children”, nor “urgh nasty pictures on the internet, that grown adults might get pleasure from”, it’s a service that o2 have been offering for years, but have had very little take up.

The setting which stops naughty websites from appearing on your phone is “Default Safety“. If it’s anything like Vodafone’s “Content Control” this is the default every phone number is set to. You need to opt out of this if you want to view sites such as the one below:
o2 Pornography.
Proof of age in a store, or payment taken on a credit card was what we used to have to deal with and again it’s been like that for years. Mobile networks have had a list of pervy customers before David Cameron started his latest crusade.

Of course your site may be child friendly and even educational, but until you tell o2 that you believe it’s suitable, you’re not going to magically appear on a whitelist.


  • I notice that o2 have added the line (opt in u12 service) to the results page to attempt to clear things up since yesterday.
  • Of course mobile data blocking won’t do much help when most phones have access to WiFi and most public WiFi only restrict adult sites.

NowTV Entertainment Pack

So earlier this week Sky announced that their NowTV service offers the ability to live stream several of their channels, plus get on demand with some back catalogues.
It’s an additional monthly cost on top of the Movies or Sport, but at £4.99 a month with no contract it seemed like a worthwhile trial.

The current channels available are

  • Sky 1
  • Sky Living
  • Sky Atlantic
  • Gold
  • Comedy Central
  • Fox
  • MTV
  • Sky Arts 1
  • Discovery Channel
  • Disney Channel

Continue reading NowTV Entertainment Pack

Tasker, Zooper and my TP-Link M5350

TP Link M5350I mentioned before that I have a MiFi device. It’s a TP-Link M5350. It’s light, portable and easy to use. However one thing I noticed was getting the battery level.
It has an OLED display, which shows the signal bars, number of connected devices, if WiFi is running, the network you are on, the up and down speeds, the current usage and a battery icon.
From quick tests it would always show empty to full animation when on charge and it only had around 4 icons for normal usage.
But what I wanted to know was a percentage level for the device.

Logging in to the web-gui for the router you get more icons along the top, however a title element on the battery shows the current level of charge. Although getting this number to appear on my phone was going to be tricky.
MiFi Homepage

So I wondered if I could get my devices to make a HTTP request to the device, get past the security, find the relevant code and output that in a clear way.
Continue reading Tasker, Zooper and my TP-Link M5350

In praise of Three

Working in mobiles for over 8 years I’ve seen the rise in coverage of 3G networks. I know how they work, unless you are in a major city you are going to have limited coverage. Trying to read Facebook in Toys-r-us in Lincoln? Better make sure your near the window. Going out in to the country? Tough.

So when I got myself a Samba SIM to use with my tablet for a laugh I though I would check the coverage of Three (who Samba use) around me. Samba Coverage I was surprised to see them claim that for almost my whole commute they would provide at least “outdoor” 3G coverage.

So I put it through a test. Continue reading In praise of Three