Monday, 28 August 2023

HTML form won't submit (Angular)

 It turns out if you mix normal HTML forms with Angular ones (i.e. using FormsModule) Angular will disable the default behaviour of forms on submit (so no POST request). To override this all you need to do is add a ngNoForm tag to the form you want to have the normal behaviour.

Saturday, 6 May 2023

Why won't my Angular app include cookies in a POST request?

 Recently while working on an Angular web app operating with CORS on localhost against a SpringBoot server I had an issue where my GET requests were fine, but the POST requests (in this case for logout) did not include a cookie. At first I though I had some kind of problem with my CORS config - but this was fine:


        var corsConfig = new CorsConfiguration();
        corsConfig.setAllowedOriginPatterns(List.of(
                "http://localhost:4200",
                "http://localhost:8080"));
        corsConfig.applyPermitDefaultValues();
        corsConfig.setAllowCredentials(true);


It turns out the signature for the POST request use by Angular is slightly different! The second argument is actually for a body. So in my case:

    return this.http.post<void>(this.logoutUrl, null, {withCredentials: true});


This might help someone who is starting to question their understanding of CORS (again)

Sunday, 24 May 2020

AWS Keyspaces - Managed Cassandra review

AWS recently went live with Keyspaces, their managed version of Cassandra (https://aws.amazon.com/keyspaces/). This service is primarily aimed at users who have been managing their own Cassandra clusters and are looking to move to a managed solution. Billing is available on an ad-hoc or reserved capacity basis and it's simple to connect using existing Cassandra applications or drivers. However, there are a few issues that I've noticed that make Keyspaces currently a poor replacement for your Cassandra cluster:

  • TTL (automatic time-based record expiry) is currently not supported by AWS keyspaces. This alone makes it difficult to port standard Cassandra data models over.
  • No cross-region support (yet)
  • 1 mb row size limit (similar to DyanmoDb's 400kb item limit). This may be related to the fact that Keyspaces is more closely related to DynamoDb than true Cassandra (as noted by Scilla at https://www.scylladb.com/2019/12/04/managed-cassandra-on-aws-our-take/)
In short, AWS Keyspaces seems to be more of a beta than a real GA release. Once they add support for TTL it looks like a promising service, however it will have to compete with Datastax's own managed Cassandra offering, Datastax Astra (https://www.datastax.com/products/datastax-astra). This was launched only about 3 weeks after Keyspaces (and maybe explaining Keyspaces short preview stage and rush to release while still missing support for fundamental pieces of Cassandra).

Sunday, 13 January 2019

Sending an SMS via Intent in Android

Alchemy allows users to donate to their chose charities via text message, which it used to do automatically using Android's SmsManager functionality. Unfortunately, Google have recently updated the Play Store's terms and conditions to restrict SMS_READ and SMS_SEND to applications whose primary purpose is to act as an alternative SMS application on Android (replacing the usual Messages app for example).

I applied for an excemption for Alchemy, but this wasn't granted. This is understandable I think - Android security has a lot of issues, and excess permissions is definitely one of them - Alchemy is a good citizen and only interacts with a single SMS number, but a malicious applicaiton could easily use the same permissions for nefarious purposes.

Without an exemption, there was no choice but to update Alchemy to avoid using SmsManager. This meant instead requesting an existing SMS app to send the donation SMS instead - via an intent. It took me some time to find out exactly how to do this, but the code required to pre-populate an SMS for a user to send is


Uri uri = Uri.parse("smsto:" + charity.getNumber());
Intent intent = new Intent(Intent.ACTION_SENDTO, uri);
intent.setData(uri);
intent.putExtra("address", charity.getNumber());
intent.putExtra("sms_body", keyword);
intent.putExtra("exit_on_sent", true);
if (intent.resolveActivity(getPackageManager()) != null) {
    startActivityForResult(intent, 1);
    donationViewModel.recordDonation(this.donations, charity.getName(), smsKeywordToDonation(charity.getCost(keyword)));
} else {
    Toast.makeText(this, "No SMS provider found", Toast.LENGTH_SHORT).show();
}

The full code can be found on Github. Note that, unfortunately, SMS applications generally do not seem to respect the "exit on sent" request, so the user must navigate back manually. A bonus for this change is that Alchemy now doesn't require any additional permissions from the user. Previous donations must now be stored in Alchemy itself, instead of using SMS history. This may cause some loss of data in the migration, but should result in more robust behaviour from now on.

Sunday, 4 March 2018

Faster python for data science and scientific computing



Scientific computing and HPC developers will probably be familiar with  Intel's C/C++ compiler suite, which can be used to compile your C, C++ and Fortran code instead of the free GCC compilers and can often result in significant performance improvements without changing a single line. Further improvements can be made by swapping out (generally fantastic) open source C maths libraries such as ATLAS or BLAS for equivalent functionality in Intels MKL (Math Kernal Language). Again - this is usually simply a matter of compiling your existing code against Intel's library and can result in very impressive speed gains for very little work.

What has this to do with Python? Most of Python's most famous data science and scientific computing libraries are written in C/C++, with a simple wrapper allowing them to be called easily from python. If you've ever wondered why Numpy, SciPy, scikit-learn and pandas are so much faster than trying to write the same code yourself in native Python, it's because all of the work in a function like np.multiply() is actually carried out in C "under the hood".

Previously, if you had a licence for Intel's  compiler suite you could compile these python libraries yourself and take advantage of Intel's speed boost in your python applications, but this required both familiarly with C code compilation, as well as an expensive licence. However Intel have now made available a free pre-compiled Python distribution with all the major packages (numpy, scipy, pandas etc.) based on the popular Anaconda distribution.  According to kdnuggets Intel have also re-written some common functions entirely for further optimization - in particular it looks like numpy and scipy's FFT (Fast Fourier Transform) functions have been enhanced significantly. Depending on your workload, using this distribution could boost the execution speed of these libraries by 10-50% without the need for any code change.

If you're interested in optimizing Python code that you wrote yourself and isn't available in any existing (C-implemented) library check out Cython as a way of implementing the most performance sensitive parts of your code in C. Unlike using the Intel distribution linked above, converting part of your code to use Cython can take some development work, however even when using the free GCC compilers you'll see a significant increase in speed over native python code.

Monday, 5 February 2018

Pip unable to download packages running in a Ubuntu docker image on kubernetes

I recently ran into a problem where pip was unable to download packages while running in a docker image on a kubernetes pod. The issue seemed to be that it could not find the actual repo to download from - likely due to some kind of networking issue within either docker or kubernetes. The solution turned out to be to create a file at /etc/docker/daemon.json and enter google's DNS servers as follows:

{ "dns": ["8.8.8.8", "8.8.4.4"] }

I was working from a Ubuntu base image, so I created the file as above before installing and starting docker. Keep in mind that as docker images usually don't contain systemmd, it's not all that easy to restart docker once you have installed it, so creating the configuration first is pretty useful. You can find more information on this at https://development.robinwinslow.uk/2016/06/23/fix-docker-networking-dns/

Wednesday, 21 June 2017

Alchemy app released (in beta)

I've finally published the beta version of Alchemy on the play store. It's still in beta, but it seems to be working well. Give it a shot if you're looking for a different way to donate to charity!

HTML form won't submit (Angular)

 It turns out if you mix normal HTML forms with Angular ones (i.e. using FormsModule) Angular will disable the default behaviour of forms on...