Wrapping Text and Making Memes

Play with the meme generator here.

The project I’m moving to on Monday is written using a different tech stack than what I’ve done previously. Instead of a web service in Spark or Play, this is a world-facing web app written in Spring Boot. I’m decently comfortable with Spring for dependency injection, so jumping in isn’t too terribly weird. I chopped up their tutorials on form submission and handling uploads and built a feature-poor meme generator.

Captioning images on the server side is a task for ImageMagick, or at least it used to be. I found Im4Java, a Java wrapper last updated in 2012, and hacked together a service method to write some text on the image:

It’s not my favorite code I’ve ever written. The wrapper library is fighting an uphill battle because you’re literally just putting a string together and then executing it as a system command, and that makes it difficult to get useful feedback. You have to call those property methods on the operation object in the correct order, since they’re just concatenating the string together. It’s frustrating. But it kinda sorta worked, and the rest of the application did some file storage and form handling stuff, and it served the purpose of “play with Spring Boot.”

Unfortunately, I didn’t have the means to compute how big the text was going to end up being on the resulting image.

download

When I showed this to my friend Chase Maier, he pointed out that this is a much easier task using an HTML5 Canvas – splat the image onto the canvas, draw your text, and do whatever you want with it. Now, “play with canvas again” doesn’t count for the “play with Spring Boot” part, but we’ll still be able to do our persistence in Spring Boot later.

The full source is here, but let’s focus on the js method that’s doing the equivalent of my java code above:

It’s not that the equivalent js code is much more compact than the Java code was – the important thing is that it’s easier for me to measure the width of the lines for the sake of wrapping:

The results are much prettier:

download-1

Fractal Simplex Noise for Procedural Terrain Generation

Noise is great for procedural generation. Rather than just turning a pixel on or off in a vacuum, we apply a random gradient function over the entire output space, and so each pixel is close to its neighbors. If we interpret the output of Perlin noise as being a brightness value for each pixel, for instance, we get something like this, depending on the scale of our function:

perlinnoise2d1x2x

Like a freeze frame of the static you’d get on an old tube TV tuned to a channel that didn’t exist, kind of.

We can re-scale the noise function’s input so that the gradient bounces back and forth more or less quickly between values. Simplex noise at a very small scale looks like this:

static

Now, neither of the above are particularly believable terrain, at least not on their own. In the past, I’d tried generating terrain by taking relatively course noise, and summing it with some deterministic function, like the distance from the center of the output space, or the distance from the edges. That worked okay, but resulted in very circular or very square islands, with a high peak in the center.

A better approach, at least for rapid development, is to re-scale our noise function so that we have relatively course noise responsible for the general outline of the world, and finer and finer noise functions added to it to create some excitement around the edges.

We can supply whatever value we’d like for the number of iterations – I think 5 is about right, but if you want your terrain to be more chaotic and for your daring adventurer to have less walking between mountains or bodies of water, you can reduce it.

The ‘tectonics’ function is my name for actually grabbing the noise for this iteration and adding the value to a given pixel:

That “maxElevationBeforeRescaling” variable is determined based on how many iterations we’re going to perform:

Running the code above (with the height and width supplied, and something to paint in an html5 canvas) we can get some pretty clouds:

clouds

That’s much nicer than the original static. WIth colors, we can make it clear:

And ultimately we get a pretty convincing distinction between land and water:

islands

You can hit kaiserleib.github.io/islands and refresh to get different coastlines, or view the complete source at github.com/kaiserleib/islands.

The thing that’s most impressive to me about this approach is how compact it is, given how nice the output is. With 50 or so lines of code (assuming we take the Simplex noise function as a given) we get a reasonably believable world, complete with elevation data. The generation process doesn’t mesh at all with real geology, but it’s compatible with algorithms for rainfall and erosion and biome placement and you can get a realistic-looking world out of it.

Now, it’s not terribly runtime-efficient. You have to compute Simplex noise five times for each pixel, which adds up fast. But it’s a comprehensible approach.

Selectively Disable-able Java CSRF Filters in Play! 2.5

I’ve written a little bit about CSRF (Cross-Site Request Forgery) protection before. Play provides strong CSRF protection out of the box, which is one of the things I like about the framework. To enable across-the-board CSRF protection, you create the following file, at app/filters/Filters.java:

Then enable the CSRF filter in application.conf:

And add a dependency for filters to build.sbt:

This will apply Play’s default, strong CSRF protection to every request which contains any cookies in the header.

In some cases, though, it’s important to be able to let cross-site requests happen for some (but not all) requests. In this case, ‘forgery’ is a misnomer, because we want the user to be able to make a request from our world-facing app, hit a microservice (for, say, authentication), and see results rather than being unceremoniously kicked out by an error message.

The most straightforward way to do that is with a blacklist: instead of you add an @RequireCSRFCheck annotation to all the form post methods which require CSRF filtering, and an @AddCSRFToken annotation to the action methods which generate those forms. This is tedious if you have many methods which require CSRF filtering and few that don’t. It’s also error-prone, and any oversight results in your security failing open rather than closed, which is not what we want.

Fortunately, although it’s not quite as straightforward, we do still have the ability to selectively disable a global CSRF filter, with just a little work. Moreover, we can do it in Java!

Steve Chaloner provides an excellent answer on StackOverflow detailing how to decorate Play’s routes file with comments to disable CSRF on a per-action basis. At SoFi, we like annotations, so we did it a little bit differently.

First, define an annotation:

We’ll use this annotation on any action method we don’t want to protect against CSRF.

Having defined the annotation, we then define a custom CSRF filter, which will replace the CSRFFilter in Filters.java. Save it as app/filters/AnnotationDisablableCSRFFilter.java:

The important distinction between my solution here and Steve’s solution from the stackoverflow answer is that we’re grabbing the class and method to which the request was made, then inspecting it for the presence of our @DisableCSRFCheck annotation.

Having implemented our custom filter, we then update the constructor of Filters.java, replacing the default CSRFFilter with our AnnotationDisablableCSRFFilter:

Whereupon we can go through and apply the @DisableCSRFCheck annotation to the action methods we wish to open to cross-site requests.

Play 2.5: java.lang.NoClassDefFoundError: play/mvc/Results$Status

Upgrading one of our apps from Play 2.3 to Play 2.5, I got the following:

This is maddening, in part because I’m able to hit many of the routes in the application just fine; only some of them barf. When they do, there’s no way to set a breakpoint: the JVM shuts down before hitting any of our code.

Ultimately, the issue is that we have a library that bundles the older version of Play. Migrating the library to 2.5 should solve the issue, but it’s not abundantly clear what the problem was based on the stack trace.

For this particular library, the Play dependency makes sense – we’re dealing with Play’s request and response objects using Play’s API, and it’s targeted exclusively for our Play apps. That being said, it’s a reminder of why in general we should avoid bringing framework code into libraries.

How to make money

In order to make money, you have to convince someone somewhere that he’d be happier giving his money to you than keeping it for himself. We can move further up the ladder of abstractions, describing supply and demand and competitive advantage and goods and services. I am not an economist. That ladder is not my area of expertise.

Instead, the abstraction that I’d like to talk about is the silver bullet – the thing that you do that allows your business model to flourish when other people pursuing a seemingly-identical model might fail. A silver bullet should be difficult to copy, either because it’s a secret or because it’s hard to make, otherwise your competitors will use their own silver bullets and your business will be a commodity.

A restaurant’s silver bullet is convenience. You can eat monkey chow and survive, or cook for yourself and have a better meal, or go socialize with your friends or take in a show, but the restaurant is the most convenient way to achieve the entertainment and nourishment simultaneously. The restaurant’s business model is that they sell food for more than it costs them to buy, prepare and deliver it.

Google’s silver bullet, originally, was map-reduce. There were other search engines. Map-reduce made search good. They had clean UI, too, but you’d have used a search engine that looked like Yahoo if it worked as well as Google did. That gave them time to steal AJAX from Microsoft and build gmail and maps. Google’s business model is that they sell the eyeballs of the people who search for things to advertisers.

SoFi’s silver bullet is a willingness to refinance student loans. Banks can’t do it because they’re not allowed to. We have some very cool technology, too. And our CEO can raise money and sell securities very effectively. Inventing the student loan refinancing product was a necessary precondition for that to matter. We’re trying all sorts of other things and making sure to tell the press, and I think there’s a good chance some of the new efforts will be our gmail or our maps, but student loan refinancing was the silver bullet.

I’m not a business guy. But if I could figure out a silver bullet I would be.

How can we identify silver bullets?

sql2o’s speedy vindication

Yesterday I wrote about a problem I’d run into with sql2o’s getKey() method. The sql2o developer responded to me on twitter, and pointed out that since sql2o is just calling the JDBC PreparedStatement.getGeneratedKeys() method, this isn’t wrong with sql2o per se: it’s a problem with the underlying JDBC driver and ultimately with postgres itself. Even people using straight JDBC have to do workarounds, and many of those workarounds end up being slower (requiring multiple queries) than simply guaranteeing that the leftmost column contains the generated value we’re after.

Much thanks to sql2o for the speedy response!

sql2o’s getKey() and postgres

sql2o is not the cause of this issue. It’s a problem with postgres’s JDBC driver. I retract any expressed or implied criticism of the sql2o project represented by this post’s previous title or the paragraphs below.

I’m using sql2o for persistence on my current project, a microservice written in Spark. Sql2o is a good fit both because it’s fast and tiny and because it minimizes configuration. It’s great (and I’ll write about how to use it later), but it has at least one really frustrating caveat: the Connection.getKey() method.

getKey() is supposed to give us the generated primary key of a newly-inserted record. In ORMs like Hibernate, we don’t need to do that: the object’s field corresponding to the key gets populated when we persist it. But it’s not so bad:

And for several hours today, it worked wonderfully.

My issue happened when I realized that I’d set up my table’s ID column as an integer instead of a bigint. This might be one of the occasions where we’d blow past MAX_INT. So I dropped and re-added the column, as you do:

And when I made another request to my microservice, I got an exception:

That right there is pretty darn un-google-able. There’s a stackoverflow answer that’s specific to PostGIS, but nothing that had to do with the apparent discrepancy between a Java Long and what should have been Postgres’s direct equivalent.

Thinking I was very clever, I decided to hammer a very duct-tape converter in there:

Which fortunately came back with a much more explicit exception:

I thought at first that the giant JSON object was the entire record, serialized, and that somehow I’d lost track of what the key should be and postgres or sql2o or an intermediate gremlin was relying on some mishmash of the entire record as a composite key. I re-created the key as an integer, making sure to specify that yes it was the primary key and yes the generation strategy and so forth. That didn’t help.

Staring at the exception, I realized that the String we were failing to parse as a Long wasn’t the entire object: it was the json representation of one of the child objects I’m persisting for this model. In fact, it was the second field specified in the model, and the second column I’d specified in my original CREATE statement. This leaves one very promising conclusion: that the leftmost column is the “key,” at least for sql2o’s “getKey()” call. Dropping and re-creating the primary key column the way I did moved it all the way to the right, so it wasn’t being returned by getKey() any more.

Dropping the entire table and re-creating it re-ordered the columns appropriately, and since the leftmost column was now the primary key again, everything worked.

Touch Events: Doodling from Mobile Browsers

Mouse events are not exactly the same as touch events, although they’re similar. That meant that my websocket canvas drawing app only did half its job on mobile pbrowsers: you could see the lines drawn by people on desktop browsers, but you couldn’t draw anything back. Here’s how to hook up a very simple touch event handler. MDN has a more complete reference.

First, we need to hook up the event listeners:

Then we write the event handlers. Since we want touch events to do the same thing mouse events are already doing, I extracted the mouse event handlers’ method bodies, and had both the touch event and the mouse event call the same function:

 

Note that our handleTouchMove function refers to an array of touches, e.changedTouches, using only the 0th element. The changedTouches array supports multi-touch, which is incompatible with our single-pen doodling paradigm.

Deploying a Spark application built with SBT to Heroku

Heroku is a cloud application platform that takes care of many operational concerns – since I have to serve as my own devops for extracurricular projects, that’s pretty appealing. Spark has a tutorial for Heroku deployment, but Spark’s tutorials assume you’re using Maven, and I’m using SBT. Fortunately, Heroku provides an SBT plugin and a reference. Between the two of ’em, we can figure out what to do to deploy a Spark app (in this case, my websocket canvas doodler) to Heroku.

  1. Sign up for a Heroku account, and install the Heroku toolbelt.
  2. Set up your SBT and Spark app.
  3. Add the sbt-heroku and sbt-native-packager plugins to plugins.sbt. Note that the version of sbt-native-packager is different from that described in the Heroku reference:
  4. Add this method to your Spark app, and call port(getHerokuAssignedPort()); in your main() method to determine the port assigned by Heroku:
  5. Create your Heroku app, using the -n flag to avoid adding a git remote:
  6. Add enablePlugins(JavaAppPackaging) and herokuAppName to build.sbt, replacing “your-app-123” with the name Heroku assigned your app:
  7. Finally, deploy the app:

Having completed these steps, you can navigate to your app at http://your-app-123.herokuapp.com, replacing “your-app-123” with the name assigned in step 4.

Spark Doodle: <canvas> and websockets

The source code for this post is on github here. You can play with the app on Heroku here. This app was based on David Ase’s chat tutorial and on Code and Coffee’s node.js example.

Websockets allow duplex communication over a single TCP connection – in other words, they let the web browser constantly speak and listen to a server instead of doing everything through atomized HTTP requests. Before websockets, if you wanted (for instance) a chat app in the web browser, you’d use polling to constantly ask the server whether anything changed. Websockets allow the server to push information to the browser without waiting to be asked.

In this post, I’ll show you how to use websockets to build a simple shared doodling app. Users will see all the lines that other users draw while they are logged in, but they won’t see lines that were drawn before they arrived, nor will they see their own lines reappear if they close and re-open the browser window. The server will use Spark, and the client will be pure, no-library-having Javascript.

The main() method of a Spark application traditionally sets up the routes, but here, all our requests go to the index.html page in /src/main/resources/public, as indicated by the staticFileLocation() call. The webSocket() call sets up the websocket, running at “/doodle” and handling responses using the DoodleWebSocket class. Finally, I put the list of sessions and the broadcastMessage() methods inside this Application class.

Our websocket handler implementation is spartan indeed! Spark uses Jetty’s websocket implementation directly, including Jetty’s annotations. All we do here is add and remove sessions and call the Application controller to broadcast our message out to the clients.

That’s all the java code for this application!

We need some HTML to give ourselves a canvas to draw on:

We have a <canvas> and we include the js source.

Finally, the javascript:

The conceptual implementation is directly from Code and Coffee’s post: if the mouse has moved in the past 25 milliseconds and the mouse button is clicked, we broadcast the instruction to draw a line between our mouse pointer’s current position and the previous position.

The meat of my change is:

  • Switch from a socket.io socket to a plain vanilla websocket
  • add the line to re-create the websocket when the mouse is clicked
  • add the proxy function to wait for the socket to be ready before sending a message.

Re-creating the websocket on mouse clicks is to resolve an issue where the websockets would time out on heroku. The proxy function is there because otherwise we’d be trying to broadcast messages to a socket that wasn’t open yet.