Hacking the CryptoKitties Genome

Written by abhishekchadha | Published 2017/12/07
Tech Story Tags: ethereum | cryptokitties | react | blockchain | svg

TLDRvia the TL;DR App

My friend Anshul recently told me about CryptoKitties. I had heard about it clogging up the ETH pipes and causing the price to drop but had not realized what an amazing design the CryptoKitties team had realized. CryptoKitties are basically breed-able beanie babies built on top of the ethereum blockchain. And yet, they are also so much more than that: CryptoKitties are a digital playground where programmers, geneticists, and experts in economics, bioinformatics, machine learning and game theory can come together to learn and play.

Studying cryptokitties

For those of you new to CryptoKitties, have a look at the Mashable guide; this will teach you the basics of the CryptoKitties game system. To get a better view of exactly just what a kitty is you can go through the CryptokittiesCore contract. You’ll find that a CryptoKitty is basically a struct on the EVM that looks like this.

struct Kitty {uint256 genes;uint64 birthTime;uint64 cooldownEndBlock;uint32 matronId;uint32 sireId;uint32 siringWithId;uint16 cooldownIndex;uint16 generation;}

We see some other interesting things too…

modifier onlyCEO() {require(msg.sender == ceoAddress);_;}

and…

/// @title SEKRETOOOOcontract GeneScienceInterface {function isGeneScience() public pure returns (bool);

/// @dev given genes of kitten 1 & 2, return a genetic combination - may have a random factor/// @param genes1 genes of mom/// @param genes2 genes of sire/// @return the genes that are supposed to be passed down the childfunction mixGenes(uint256 genes1, uint256 genes2, uint256 targetBlock) public returns (uint256);}

Wow a secret. This is THE secret. If you’ve been playing cryptokitties you know this is how kitties are produced. You’ll notice that siring kitties produces offspring in a manner that feels intuitive: features get passed on from parents to offspring sometimes but not always, sometimes skipping generations. This is the code that runs at the conception of cryptokitties with non-zero generations.

A brief genetics remedial from your 10th grade biology class

A phenotype (from Greek phainein , meaning ‘to show ‘, and typos , meaning ‘type’) is the composite of an organism’s observable characteristics or traits, such as its morphology, development, biochemical or physiological properties, behavior, and products of behavior (such as a bird’s nest). A phenotype results from the expression of an organism’s genetic code, its genotype, as well as the influence of environmental factors and the interactions between the two. When two or more clearly different phenotypes exist in the same population of a species, the species is called polymorphic. A well-documented polymorphism is Labrador Retriever coloring; while the coat color depends on many genes, it is clearly seen in the environment as yellow, black and brown.

Managing all the features in my head was difficult. I needed somewhere to organize my thoughts so I created a spreadsheet do do some of the totesbasic math. From the currently features that are being served up by the crypokitties.co API we know that a CryptoKitty has up to 1.15792×10⁷⁷ phenotypes. Given that the ‘genotype’ for a CryptoKitty is a 256-bit integer there are 2²⁵⁶ possible genotypes for a CryptoKitty. Going to cryptokittydex I was able to see the genotypes for each kitty and block addresses! What fun!

The API at CryptoKitties.co serves the public data needed to create the game around this blockchain. It creates the images, names the “features” serves then via the API and facilitates the ethereum transactions required to play the game using MetaMask.

Inspecting the browser while playing cryptokitties, you’ll find that the requests to cryptokitties.co are serving results related to the features expressed in the phenotype and familial relationships. Running

curl 'https://api.cryptokitties.co/kitties/123606'

gives

{"id": 123606,"name": null,"generation": 4,"created_at": "2017-12-07T06:54:46.000Z","image_url": "https://storage.googleapis.com/ck-kitty-image/0x06012c8cf97bead5deae237070f9587f8e7a266d/123606.svg","color": "topaz","bio": "What's up! I'm Kitty #123606. I've never told anyone this, but I once pawed at a dog. I once got in a fight with a moose, and won. We can be friends, but keep the ultra purrsonal stuff to yourself, please.","is_fancy": false,"is_exclusive": false,"fancy_type": null,"status": {"is_ready": true,"is_gestating": false,"cooldown": 1512636431155,"cooldown_index": 3},"auction": {},"owner": {"address": "0xb464f93be01bde143c92176d921c1d0d533bc3ca","image": "17","nickname": "KittyHodlr"},"matron": {"id": 123288,"name": null,"generation": 3,"owner_wallet_address": "0x8081ecb6f3350fe5ed46f1bd74d5ada62c62e740","created_at": "2017-12-07T06:30:08.000Z","image_url": "https://storage.googleapis.com/ck-kitty-image/0x06012c8cf97bead5deae237070f9587f8e7a266d/123288.svg","color": "topaz","is_fancy": false,"is_exclusive": false,"fancy_type": null,"status": {"is_ready": true,"is_gestating": false,"cooldown": 1512635143445}},"sire": {"id": 96883,"name": "Gen 3 Purple Sizzurp","generation": 3,"owner_wallet_address": "0x8081ecb6f3350fe5ed46f1bd74d5ada62c62e740","created_at": "2017-12-05T23:09:11.000Z","image_url": "https://storage.googleapis.com/ck-kitty-image/0x06012c8cf97bead5deae237070f9587f8e7a266d/96883.svg","color": "sizzurp","is_fancy": false,"is_exclusive": false,"fancy_type": null,"status": {"is_ready": false,"is_gestating": false,"cooldown": 1512641108913}},"children": [],"cattributes": [{"description": "orangesoda","type": null}, {"description": "simple","type": null}, {"description": "granitegrey","type": null}, {"description": "coffee","type": null}, {"description": "pouty","type": null}, {"description": "totesbasic","type": null}, {"description": "topaz","type": null}, {"description": "cymric","type": null}]}

This is what a CryptoKitty looks like according to the API. We can see the owners address, and the features of Kitty #123606. Most importantly we get an image of an amazing, fluffly cat.

So cute and fluffly!

Each cat has cattributes, based on its genes. Remember that 256 bit uint ? That determines what your kitty looks like.

Ignoring the auction system, we can think about the genetic aspect of the system as having two parts

  • genes X **— (cryptokitties.co)→ (**phenotype X, image X)
  • genes matron+ genes sire —( mixGenes )→ genes offspring

where mixGenes is our secret sauce function. Could we study the reproductive patterns of cryptokitties to be able to predict breeding outcomes better than chance?

We want to be able to get data about the genomes of these mystical creatures by inspecting the ethereum blockchain. We could write code to download and parse all cryptokitties transactions so far but that would be slow and ain’t nobody got time for cat. I decided to quickly write a scraper to collect the current set of cats available on cryptokitties.co and cryptokittydex.com.

I wrote this code to use a headless Chrome instance to ‘visit’ cryptokittydex.com and put the genomes of all the cats, their owners and their images in an S3 bucket (or on disk). I let it run till it downloaded about 100k cats and their images.

The next day I decided to study the sample of cryptokitties I had scraped. I quickly noticed that fancy kittys had .png extensions while normal kitties were saved as .svg. I began to notice patterns and learnt the basics of each cryptokitty attribute by trial and error and referring to reddit guides. It became obvious which features were exclusive and I slowly felt I was becoming better at categorizing cryptokitties. By the end of the night I felt I could soon be the Gregor Mendel of cryptokitties.

Cryptokitty basics

There are 3 basic feature types. Excluding ‘fancy’, there are 7 or 8 visible features for each cat. There are 2 reproductive features for each cat that are not visual.

  1. Body Features (4): BodyType, PatternType, MouthType, EyeType,
  2. Colors Features (4): Primary, Secondary, Tertiary, Eye
  3. Reproductive: CoolDown, Generation

Some patterns I noticed while going through the cats.

  1. Totesbasic cats do not express their tertiary color but do have the gene
  2. The beard is the only mouth feature that contains color. It uses the primary color.
  3. The eye color is also the color of the background
  4. The primary color is the main color of the cats fur
  5. The secondary color is the color of the cats fur patch(s) / stripes if their pattern type has 2 colors
  6. Tertiary colors are expressed in the cats fur for some pattern types with 3 colors

Now the question was — which kitties had not been discovered yet? And could we somehow do a cryptokitty genetic test to see what these kitties would look like before they are born? Opening up the SVGs it was easy to see the different parts of the kitty.

Grepping around I looked for the aquamarine color in this kitty and searched for it in another. It was the same across all the files! However continuing through the dataset I found not all fur patterns used all 3 colors and some were pretty convoluted making it difficult to manipulate the svgs directly with JSDom. I decided to just treat the svgs as strings and create three sets of images. The first would be a set of 48 images that would have cats of every possible BodyType and PatternType combination. The second was a set of 8 cats with all Mouth combinations. The third — you guessed it — the set of all possible eyes. Isolating the svg elements for each of these ‘genes’ allowed me build a quick React.js prototype that was able to render a kitty of any possible phenotype.

<Cryptokittybody={body}mouth={mouth}eye={eye}pattern={pattern}colors={[c.Primary[primary],c.Secondary[secondary],c.Tertiary[tertiary],c.EyeColor[eyeColor]]}/>

Adding some simple controls, I had a very early prototype for my cryptokitty genetic testing company. Meow all I have to do is find a cool person with some good venchair carpetal.

Tell me what you think! PRs are highly encouraged.

CryptoKitty Designer:

https://bytesforbites.github.io/cryptokitty-designer/#/

Source:

https://github.com/BytesForBites/cryptokitty-designer.

Send kittehs and tips to 0x02Ee97a13e434717e3FFa12758a235D1a1680775

Please sir, I’m just a dev cat that needs to pay for my new mouse


Published by HackerNoon on 2017/12/07