This is a blog post by Sean McKinley, a Senior DevOps Engineer at NWEA, a research-based, not-for-profit organization that supports education around the world. NWEA leverages Pure Storage products to deliver an unrivaled SaaS education platform, utilizing both FlashArray™ and FlashBlade™ devices, and this is what inspired him to write Purest, a Ruby library built on top of FlashArray™ REST API. His team does not deal directly with its FlashArray™ on a day-to-day basis, but underneath the Linux VMs his team manages beats the heart of a Pure Storage FlashArray™. Sean wanted an automated way of interacting with the FlashArray, namely to provision LUNs to be attached as RDMs when a VM is built. As a Ruby fan, this need was what motivated Sean to write Purest:
As I think with most every open source project, Purest was born from the combination of wanting to learn and wanting to build something others could use. Truth be told it started over a year ago, but I became frustrated with myself for not knowing “the best way” to structure the project, write the classes, etc; eventually I just put it on the back burner and later on gave up on it entirely.
Probably eight or so months later, I picked the project back up and everything sort of just clicked – project structure and classes flowed easily, and refactoring was a breeze thanks to writing unit tests. Not to give myself too much credit, I owe a good portion of it to the folks who wrote the Diplomat gem; it served as the inspiration for how I structured the project.
That being said, this project has provided me with many hours of learning and has now blossomed into something entirely usable by anyone who writes in Ruby. Arguably my favorite part, which realistically only turned out to be about 15 minutes worth of research using Google, was figuring out how to implement a set of integration tests with rspec alongside the unit tests.
The first integration test I wrote for the project was pretty simple: use the Pure Storage® FlashArray™ REST API to provision a 10gb volume, verify it existed, and delete it after the fact. Then came the best part – being able to run that integration test against every version of the API and seeing it pass for version 1.1 up to 1.11 was an extremely rewarding and comforting experience. Now I knew that this particular function of the code worked against all versions of the API, up to 1.11 at the time, without having to test each version by hand.
So here we are, up to v1.0.5 and over 1,100 downloads off of RubyGems. I’m still having a blast with it.
Using Purest is pretty simple and straightforward, below I’ll walk you through getting started in a macOS X or Linux environment. For starters, you’ll want to get Ruby installed; my preferred way of doing so is utilizing RVM, and you can follow the instructions to “Install RVM Stable with ruby” here: RVM Installation Instructions. RVM allows you to have multiple versions of Ruby installed at once, and switch between them with ease.
At this point you should have the latest stable ruby installed, which at the time of writing is 2.5.3, and can install Purest by issuing the following command:
1 |
gem install purest |
This reaches out to RubyGems.org, the “community’s gem hosting service”, and downloads the Purest gem along with any of its specified runtime dependencies.
Here is a demo video of how to use Purest in a simple volume provisioning/de-provisioning scenario, before I go on with a written version of it below:
With the Purest gem now installed, it’s available for use – open up your favorite text editor and let’s create a basic script for interacting with your FlashArray.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
#!/usr/bin/env ruby require ‘purest’ Purest.configure do |config| config.api_key = ‘1234-567-89’ config.url = ‘https://flasharray.example.com’ config.options = {ssl: { verify: true }} config.api_version = ‘1.14’ end created_volume = Purest::Volume.create(name: ‘test-vol’, size: ’10G’) puts created_volume |
Let’s step through this, line by line:
1 |
#!/usr/bin/env ruby |
This line is what’s called a shebang, and more or less tells your OS how to run this script- in this case, it’s going to path the fully qualified file path to the ruby interpreter.
1 |
require ‘purest’ |
This includes the Purest gem at runtime, ensuring it’s loaded into memory and that all of its classes/functions are available for use.
1 2 3 4 5 6 |
Purest.configure do |config| config.api_key = ‘1234-567-89’ config.url = ‘https://your-flash-array-url’ config.options = {ssl: { verify: true }} config.api_version = ‘1.14’ end |
The above block is used for configuring how all subsequent API calls will be made.
1 |
created_volume = Purest::Volume.create(name: ‘test-vol’, size: ’10G’) |
This line is what actually “does” the work – it invokes a REST API call to the /volume endpoint, passing along the required parameters to create a volume named ‘test-vol’ with a size of 10GiB. It then assigns the return value, to the created_volume variable.
1 |
puts created_volume |
Save the whole source code above into a CreateFAVolume.rb
file and run ruby CreateFAVolume.rb
from a Terminal command to test it. You should get the following output:
1 |
{:source=>nil, :serial=>“8B39D208A6FA789A00191490”, :created=>“2018-07-08T18:56:26Z”, :name=>“test-vol”, :size=>10737418240} |
Obviously there is far more you can do with Purest besides simply creating a volume, and I implore you to check out all of its documentation.
If you’d like to contribute to the Purest source code (released under the commercially-friendly MIT open source license), don’t hesitate to fork from the main repository and file a pull request. If you have any question about Purest, sign up to join me on the Pure Storage Developer Slack network and reach out to me on its #ruby channel. And if you’re inspired by my journey and would like to create your own FlashArray library, don’t hesitate to contact Pure Storage employees on the Pure Storage Developer Slack network. I can attest that they are there and listening!