The Best Time to Post on Hacker News

Jun 16, 2020

I’m starting a new blog and I have the ambition of attracting high quality traffic very quickly. Marketers recommend scheduling your posts to reach the largest audience possible, so what really are the best hours for Hacker News, a community of night owls?

There are two notable existing analysis: from 2014, and from 2017, but none is up to date, none is being updated continuously and I would expect some patterns to change.

Fortunately, there is no need to scrape anything, as Hacker News items (stories, posts, jobs and polls) are available as a BigQuery public dataset, so we can find a crude answer in an hour, without resorting to R or Python, using only BigQuery and Data Studio.

For the impatient:

(the report as a PDF)

What it shows is the total number of the top 10 daily posts, since 1/1/2017 for each hour (US/Central) and day of week. For example: the 123 top posts were submitted on Wednesday 1PM, and only 39 on Saturday at 4AM. It seems that the best time to post on Hacker News is between 7AM and 1PM, and the ideal time is Tuesday 11AM (why?).

The query:

It creates a new BigQuery table, named maurycy_hn.top_10_since_2017 (please create your own dataset and use it instead of maurycy_hn if you want to play), that contains the top 10 daily posts for each day since 1/1/2017. I then used Data Studio to connect to the data and visualize it using a pivot table with heatmap. Voilà!

The query is not optimal (some mathematics would help!) but the main issue is that it’s possible to be on the front page, as seen on the /front, the Hacker News Wayback, without making it into the daily top 10. The dataset does not provide information directly, but it does not matter, though: the front page is not an end in itself, less busy times deliver fewer visitors (eg: when all night owls sleep).

Updating the report in real time would take removing a temporary table (ie: maurycy_hn.top_10_since_2017) and importing the SELECT directly in Data Studio, but pricing makes it risky. The query processes over ~500MB data, so it quickly adds up and only the first 1TB of query data processed per month is free.

If you’re not exactly a Google Cloud person, please feel free to download the result of the query (as a CSV) and use other tools to play with it.

PS. Honestly, I believe that great content (copywriting?), like this one, always wins, so please take the analysis with a grain of salt.

If you want to be notified about new posts:

Run a Static Site On Google Cloud Run

Jun 21, 2019

Google Cloud Run is a newly announced Google Cloud service. The idea is simple: it’s Docker on serverless. Google Cloud Run is similar to Google Cloud Function: you write code without worrying about infrastructure.

What makes it unique is that Google Cloud Run works directly with Docker containers, exposes Dockerfile, supports any programming language, custom domains and has much longer timeouts (15 minutes). Google Cloud Run on GKE also supports Websockets and GPUs/TPUs making it interesting choice for resource-intensive applications, like machine learning.

In this guide I’m going to show you how to dive into Google Cloud Run by running a simple static site in few minutes, using literally one command. In a word, your own poor man’s Netlify. This is one of the easiest ways to get the taste of the platform, even if there are definitely better use cases. (Please familiarize yourself with the Pricing first, but don’t worry: you likely won’t pay a dime thanks to the Free Tier.)

Let’s start with actually building a static website. There are few options, from creating one from scratch to using a framework, a static site generator, like Jekyll or Hugo. I will go with the latter since I like it but they’re all valid options. I’d gently ask you to familiarize yourself with the Hugo’s Quick Start first:

$ brew install hugo
$ hugo new site static-google-cloud-run
$ cd static-google-cloud-run
$ git init
$ git submodule add themes/ananke
$ echo 'theme = "ananke"' >> config.toml
$ hugo new posts/

Now, using your favourite editor, edit the content/posts/ by adding some content and removing the draft: true line that effectively publishes it:

title: "Hello World"
date: 2019-06-18T03:15:54+02:00
Hello, world!

Also, edit config.toml and customize the site configuration by changing the title and removing from the baseURL:

baseURL = ""
languageCode = "en-us"
title = "Static Site on Google Cloud Run"
theme = "ananke"

We can generate the HTML and run the server now:

$ hugo
$ hugo server

The default URL http://localhost:1313/ should show us the following:

It’s not beautiful but, hey, we’ve spent only a minute on this, right?

Let’s dockerize a static site. The problem with using Hugo not only as a static site generator but also as a server is performance and lack of good Docker images. Nginx is one of the fastest web servers out there, with standard Docker image provided and very little performance footprint.

This our Dockerfile:

# Use a nginx Docker image
FROM nginx
# Copy the static HTMLs to the nginx directory
COPY public /usr/share/nginx/html
# Copy the nginx configuration template to the nginx config directory
COPY nginx/default.template /etc/nginx/conf.d/default.template
# Substitute the environment variables and generate the final config
CMD envsubst < /etc/nginx/conf.d/default.template > /etc/nginx/conf.d/default.conf && exec nginx -g 'daemon off;'

This is our nginx/default.template:

server {
    listen       ${PORT};
    server_name  localhost;
    location / {
        root   /usr/share/nginx/html;
        index  index.html index.htm;

The first two lines of Dockerfile are pretty obvious. Why are we using a configuration template, though? The Google Cloud Run container runtime contract states:

The container must listen for requests on on the port defined by the PORT environment variable.


If so, let’s build and run the image:

$ docker build -t static-google-cloud-run .
$ docker run -p 1312:1312 -e PORT=1312 static-google-cloud-run

The http://localhost:1312/ should return us the same as above:

Still not beautiful but, hey, we’ve spent only two minutes on this, right?

Let’s Google Cloud Run our static site Docker image! This is the final step. I assume that you’ve got Google Cloud SDK installed, enabled Google Cloud Run, and you’re familiar with the gcloud CLI tool. My Google Cloud project name is maurycy-sandbox, so please replace it with any you’re using.

First, let’s build the image using Google Cloud Build:

$ gcloud builds submit --tag

After few minutes, you can deploy the service:

$ gcloud beta run deploy static-google-clod-run --image

The console will output:

Allow unauthenticated invocations to [static-google-clod-run] (y/N)? y
Deploying container to Cloud Run service [static-google-clod-run] in project [maurycy-sandbox] region [us-central1]
⠶ Deploying new service... Creating Resources.
  ⠶ Creating Revision...
  . Routing traffic...
Service [static-google-clod-run] revision [static-google-clod-run-00001] has been deployed and is serving traffic at

The last line is the most important. It will be different for you but this is where the site is hosted unless we set a custom domain:

Not beautiful but, hey, only three minutes, right?

Hurray! We’re done: we’ve got an inifnitely scalable static site on Google Cloud Run. You can now even map your own domain.

PS. Please don’t forget to stop the service, either with the Console or gcloud:

$ gcloud beta run services delete static-google-cloud-run

If you want to be notified about new posts:

Just Send a Notification

Jun 15, 2019

How Slack decides whether to send a notification or not?

Slack flowchart

If you want to be notified about new posts:

About me



Data and backend.

[email protected] or [email protected]