Last year I decided there needed to be an open source cannabis API, and early this year in January we developed an MVP using Wordpress. It's great and it works, but Wordpress isn't built to be an API at heart, it's a CMS. That's why after researching and experimenting for seemingly endless hours - we settled on the Directus API.
It's open source, and most importantly, it's a PHP based solution that worked out of the box. No need for developing custom routes using any other 3rd party frameworks like Slim or PHP-CRUD. And rather than developing our own API client libraries for PHP, JS, etc -- we could use the Directus SDK.
So let's do just that, let's connect to the Kushy API using the Directus SDK.
Make your PHP request POT
Our goal is to create a simple web app that connects to the Kushy API, requests data, and sends data back to the API. You'll be able to request data (GET) without an authentication token, but submitting data will require one. You can request an access token from Kushy anytime.
The API
To access API data, you navigate the various routes and filters. Here's an example link for finding all Sativa strains. If you're building a basic app and just need the info, a simple fetch or cURL with the proper params will do. But if you really want to dig into the API, you'll want a client library (like the Directus SDK) to make your life easier.
Installing Directus SDK
First we setup our project. We have to use the Directus SDK, which is built off of several other dependencies. To install these, we use Composer, which handles the management of dependencies (it's like NPM for PHP).
Make a composer.json file in your project root and insert the following:
(gist: gist.github.com/stayregular/ea1edf779321d4…)
Now we need to actually run Composer. If you have it installed locally, just run composer install
in your project directory. If you don't, you can install composer using the instructions on their download page. You'll most likely end up running php composer.phar install
instead.
After running composer, you should have a folder in your project called vendor. This contains all the dependencies, including the Directus SDK. You can easily include all your dependencies at once using require_once 'vendor/autoload.php';
.
Requesting a Dime Bag
Whenever I work with a new API, before I plug it into an existing app or framework, I like to make a test file to get a feel for the functionality and data. Make a file called test.php and add the following code to it:
(gist: gist.github.com/stayregular/b6e8d95b024107…)
We require the composer dependencies before anything. Then we call an instance of the Directus SDK using the Kushy API URL and API version. This is where you'd also put in your access token if you wanted to send data with POST requests.
Once we have an instance of the API, we use it's function getItems
to grab data from the API and store it in a variable. We can also pass parameters through to it, such as the offset or filters, before we call the function. And that's it, we have our data stored in the $strains variable. We loop through it to find our object data, in this case, the strain name.
Stoners Appreciate Style
Over at Kushy, we've adopted our own version of Google's Material Design. To make development fast and easy, we use Google's Material Design Lite framework to quickly transform wireframe projects into full-fledged applications with easy to use CSS-based components. Combine this with the HTML5 Boilerplate by h5bp, and you've got yourself a modernized scaffold for your project.
We grab the Dashboard template from the MDL page and merge it with the HTML5 boilerplate. And we drop in our PHP code in the top. Our final code should look something like this:
(gist:gist.github.com/stayregular/e43a4fcc223aaf…)
It should look something like this:
(image: stayregular.net/content/2-blog/requesting-…)
Google's framework allows us to quickly create components like the header and responsive sidebar menu. And in the content area, we just loop through our data to generate a table. Pretty simple, but let's break some of the new stuff down.
Pagination: We handled this by cheaply using PHP's GET function to pull variables from the URL. If we set a page in the URL (domain.com/?page=2), we store the value in a $page variable, as well as an offset (20 items per page = 20 * page num). The next and previous links are defined by printing the page variable and adding/subtracting 1. And we check if we're on the first page so we don't print out an unusable previous button.
Filters: API content is easily filtered by column (name, type, THC levels, etc). Rather than using GET here like the pagination, we store our filter values in the SESSION. This allows us to traverse page to page without losing our filter data, or making the URL excessively long with data params. We run a simple form check to see if there are any changes, if so, we set the filter to the change. Find more info on filters in the Directus API docs here
The Future of Cannabis
The possibilities are endless with this API. We're looking to create several applications that rely on accurate cannabis data, and this API allows us to focus on making great applications - not data mining for dank.
(image: stayregular.net/content/2-blog/requesting-…)
Puff puff pass
This API is live ⚡️ and publicly accessibly (read only). We have cannabis strains available, as well as cannabis storefronts (dispensaries, headshops, doctors, etc). We'll be adding products, brands, and lab tests soon. You can find a WIP of the Kushy API documentation here on Github (made with GatsbyJS and ReactJS) where you can also contribute!
We're constantly in the process of adding new data, so check back frequently to find updates. The dataset will also be open sourced and available on Github soon! 🍻
Hope that helps!
Stay regular,
Oscar
References:
- (link: kushy.net text: Kushy target: blank)
- (link: kushyapp.github.io/kushy-api-docs/public text: Kushy API Documentation target: blank)
- (link: getdirectus.com text: Directus API target: blank)
- (link: github.com/directus/directus-sdk-php text: Directus SDK target: blank)
- (link: getcomposer.org text: Composer target: blank)
- (link: php.net/manual/en/reserved.variables.get.php text: PHP manual - $_GET target: blank)
- (link: php.net/manual/en/book.session.php text: PHP manual - Sessions target: blank)