Analytics on your keyboard? Why not?

Intro

I’ve owned a Razer keyboard for a while now. I’ve always loved the fact that the keys light up according to the context of the application. For the most part this means that the keyboard will react to context. Amongst the supported apps there is one cool Adobe Photoshop integration, but mostly it’s games.

This got me thinking: What about the business people? How could they take advantage of this technology? How would someone in my world, the world of analytics, make use of this? What immediately jumps out at me as uses cases are:

  • Alerting
  • Shortcuts
  • Visualizations

Usually these are the things that we dream of when we look at products and we think: “It would be great if someone could make X product do Y”. Well, fortunately Razer has made it very easy for us since their Chroma line of devices has a REST interface. This means you can just tell the device what you want it to do and it will do it. You can read all the Chroma SDK docs here.

Workflow

The jist of it is:

  1. Open a connection (and register your Chroma app)
  2. Update the device or ping the device so it keeps the connection alive.

Let’s start proving the concept by reading a small CSV file with some data and displaying it on the keyboard itself.

The Code

import requests, pandas as pd, numpy as np
from time import sleep

# this function returns an int value from a RGB HEX
def hex2dec(hex):
    return int(hex,16)

csv = 'data.csv'

# we will use this gradient
COLORS = [
    "0C0A3E",
    "7B1E7A",
    "B33F62",
    "F95664F",
    "F3C677"
]

# this is the chroma sdk url. It is a local server
registrationUrl = 'http://localhost:54235/razer/chromasdk'

# the description that will show up in our Razer app
appDescription = {
    'title': 'Keyboard Analytics',
    'description': 'No better use of keyboard lighting!',
    'author': {
        'name': 'Roberto Trevino',
        'contact': 'robtrevino.com'
    },
    'device_supported': ['keyboard'],
    'category': 'application'
}

# register the application
r = requests.post(url = registrationUrl, json = appDescription)

# get back a session
sessionUrl = r.json()['uri']

# grace period
sleep(2)

# keep monitoring the CSV file
while True:
    # read the csv file
    data = pd.read_csv(csv)

    # get max and min values so we can normalize later
    max_y = data['y'].max()

    # chroma has 22 columns by 6 rows, so let's normalize
    # we only want columns 1 through 15, because those are the main keys
    # we only want the top 5 rows, so rows 0 through 4
    data['y'] = np.ceil(data['y'] / max_y * 5).astype(int) # round up

    COLUMNS = 15
    ROWS = 5
    param = [
        [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],
        [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],
        [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],
        [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],
        [0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0],
        [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],
    ]

    # check which keys we're lighting up depending on the data
    for c in range(1,COLUMNS):
        result = data['y'][data['x']==c].values
        for r in range(1,ROWS + 1):
            if result[0] >= r:
                param[ROWS - r] = hex2dec(COLORS[r - 1])

    # build the payload
    payload = {
        "effect" : "CHROMA_CUSTOM",
        "param" : param
    }

    # send the info to they REST server
    r = requests.put(sessionUrl + '/keyboard', json = payload)
    sleep(2)


Voila! As you can see. The keyboard will now light up according to the data that’s in the CSV and will change every 2 seconds. The code itself is very short, and I’m sure someone could make a better version of it. However, for our purposes, it’s enough.

Business Users

What about enterprise business analytics?

In the world of business analytics my technology of choice is MicroStrategy. This is in no small part because I’ve worked with it for most of my professional career. In this case, however, we’re proving the concept of enterprise analytics on your keyboard because it also has a REST interface. Recently, MicroStrategy has also made available their mstrio package for python, which is a wrapper for the requests package tailoring it specifically to their REST interface.

If your not familiar with MicroStrategy or the world of business intelligence, you can think of it as a repository of data that changes constantly and can be queried much like a database. In reality, it offers much more than that, but for our purposes, that’s enough.

This is what a typical report in MicroStrategy looks like.

 

Adding MicroStrategy Support

We’ll now take the code we wrote and add MicroStrategy support. The idea is to try and closely resemble the graph onto the keyboard.

We’ll start by installing the mstrio-py package from MicroStrategy


pip install mstrio-py

We’ll now add a few variables that we’ll need:

  1. MSTR REST url
  2. Login
  3. Password
  4. Project Name
  5. Report Id
  6. Our login mode (in my case LDAP)

Fortunately for us, MicroStrategy uses pandas dataframes, which we used in our csv example. This will make adapting our code easy.

Here is a quick explanation of the changes:

  • Line 5 through 9: login info
  • Line 11 and 12: connect to mstr
  • Line 54: read data from our report
  • Line 56: convert the x axis datatype to int. This is because MSTR will default to a string since it’s an attribute.

The Code

import requests, pandas as pd, numpy as np
from time import sleep
from mstrio import microstrategy

mstrUrl = 'https://URL_AND_PORT/MicroStrategyLibrary/api'
userid = 'username'
password = 'password'
projectName = 'project name'
reportId = 'report id'

conn = microstrategy.Connection(base_url=mstrUrl, username=userid, password=password, project_name=projectName, login_mode=16, ssl_verify=False)
conn.connect()

# this function returns an int value from a RGB HEX
def hex2dec(hex):
    return int(hex,16)

# we will use this gradient
COLORS = [
    "0C0A3E",
    "7B1E7A",
    "B33F62",
    "F95664F",
    "F3C677"
]

# this is the chroma sdk url. It is a local server
registrationUrl = 'http://localhost:54235/razer/chromasdk'

# the description that will show up in our Razer app
appDescription = {
    'title': 'Keyboard Analytics',
    'description': 'No better use of keyboard lighting!',
    'author': {
        'name': 'Roberto Trevino',
        'contact': 'robtrevino.com'
    },
    'device_supported': ['keyboard'],
    'category': 'application'
}

# register the application
r = requests.post(url = registrationUrl, json = appDescription)

# get back a session
sessionUrl = r.json()['uri']

# grace period
sleep(2)

# keep monitoring the CSV file
while True:
    # read the csv file
    data = conn.get_report(report_id=reportId)
    #convert datatype of x to int.
    data['x'] = data['x'].astype(int)

    # get max and min values so we can normalize later
    max_y = data['y'].max()

    # chroma has 22 columns by 6 rows, so let's normalize
    # we only want columns 1 through 15, because those are the main keys
    # we only want the top 5 rows, so rows 0 through 4
    data['y'] = np.ceil(data['y'] / max_y * 5).astype(int) # round up

    COLUMNS = 15
    ROWS = 5
    param = [
        [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],
        [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],
        [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],
        [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],
        [0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0],
        [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],
    ]

    # check which keys we're lighting up depending on the data
    for c in range(1,COLUMNS):
        result = data['y'][data['x']==c].values
        for r in range(1,ROWS + 1):
            if result[0] >= r:
                param[ROWS - r] = hex2dec(COLORS[r - 1])

    # build the payload
    payload = {
        "effect" : "CHROMA_CUSTOM",
        "param" : param
    }

    # send the info to they REST server
    r = requests.put(sessionUrl + '/keyboard', json = payload)
    sleep(2)


End Result

What do you think? In my opinion it looks great! You can quickly glance at the keyboard, even a bit away from the desk and get an idea of what’s going on with your favorite report.

Expanding the Concept

Although the MicroStrategy REST API is not perfect, it does have a ton of functionality that we can leverage to expand our concept. We can:

  • Add threshold support: make the keyboard light up a certain color (even read it from MicroStrategy) depending on the value.
  • Make use of the keyboard’s shortcut keys so that they dynamically link us to reports that require our attention.
  • Have the keyboard blink when a new version of our report is ready.
  • And many more.

Conclusion

To recap, I just showed you how simple it is to bring business analytics to your keyboard. No need to open email, turn on your cellphone, or anything else. Get instantly alerted to business conditions you predefined and act upon them right then and there. This is just one more example of how we can have analytics blend seamlessly into our daily lives and make our jobs easier.

Hopefully this sparked your curiosity and got your ideas flowing. Be sure to send me a note if you have questions or need help!

Leave a Reply

Your email address will not be published. Required fields are marked *