Discover how to seamlessly syndicate your data to a partner site with this detailed Ruby on Rails tutorial, covering critical topics like converting product info into JSON, creating an XML file, and using Active Admin to export CSV.
This exercise is excerpted from Noble Desktop’s past web development training materials. Noble Desktop now teaches JavaScript and the MERN Stack in our Full Stack Development Certificate. To learn current skills in web development, check out our coding bootcamps in NYC and live online.
Topics covered in this Ruby on Rails tutorial:
Converting product info into JSON, Creating an XML file, Using Active Admin to export CSV
Exercise Overview
In this exercise, we’ll learn how we can syndicate our data out to a partner.
-
If you completed the previous exercises, you can skip the following sidebar. We recommend you finish the previous exercises (8A–11B) before starting this one. If you haven’t finished them, do the following sidebar.
If You Did Not Do the Previous Exercises (8A–11B)
- Close any files you may have open.
- Open the Finder and navigate to Class Files > yourname-Rails Class
- Open Terminal.
- Type
cd
and a single space (do NOT press Return yet). - Drag the yourname-Rails Class folder from the Finder to the Terminal window and press ENTER.
- Run
rm -rf nutty
to delete your copy of the nutty site. - Run
git clone https://bitbucket.org/noble-desktop/nutty.git
to copy the That Nutty Guy git repository. - Type
cd nutty
to enter the new directory. - Type
git checkout 11B
to bring the site up to the end of the previous exercise. - Run
bundle
to install any necessary gems. - Run
yarn install --check-files
to install JavaScript dependencies.
Converting Product Info into a JSON feed
Let’s say that hypothetically, we’ve struck a deal with a comedy blog that’s going to feature our products on their website. We don’t want to make them add all our product info manually, nor would we want them to show out-of-date info if data on our site changes. We’ve seen how easy it is to receive data as JSON onto our site; let’s share our products as JSON with another site.
-
For this exercise we’ll continue working with the nutty folder located in Desktop > Class Files > yourname-Rails Class > nutty
If you haven’t already done so, we suggest opening the nutty folder in your code editor if it allows you to (like Sublime Text does).
-
You should still have a window with two tabs open in Terminal from the last exercise, the first of which is running the server. If you don’t, complete the following sidebar.
Restarting the Rails Server
- In Terminal,
cd
into the nutty folder:
- Type
cd
and a space. - Drag the nutty folder from Desktop > Class Files > yourname-Rails Class onto the Terminal window (so it will type out the path for you).
- In Terminal, hit Return to change directory.
-
In Terminal, type the following:
rails s
- Open a new tab (Cmd–T) leaving our server running in the old tab.
- In the new tab,
cd
into the nutty folder:
- Type
cd
and a space. - Drag the nutty folder from Desktop > Class Files > yourname-Rails Class onto the Terminal window (so it will type out the path for you).
- In Terminal, hit Return to change directory.
- In Terminal,
-
In your code editor, open nutty > app > controllers > products_controller.rb
We want to be able to render all of the products on our site as JSON. In order to do that, we can use the existing
index
action for products. -
Starting around line 7, add the following bold code:
def index @get_nutty = true @products = Product.all respond_to do |format| format.html format.json { render json: @products } end end
NOTE: This is where we use the
respond_to
helper that you might recall from scaffolding exercise earlier. Basically, any controller action can respond to different formats of a request and render its output in different ways. Save the file and leave it open.
In the browser go to our products page at: localhost:3000/products
-
In the browser go to: localhost:3000/products.json
Now you should see a JSON feed with all our product info we saw in the previous step. We can access this the same way as anything else from the Rails console.
-
In Terminal, type the following to start the Rails console:
rails c
-
In Terminal, type the following to return a nice, long JSON response:
r = HTTParty.get('http://localhost:3000/products.json')
-
We can do all the same things here as with the bitpay.com API, so try typing:
r.count r.first['title']
You should get back the number of objects (
8
) and the title of the first object (Tinfoil Hat
).If our partner site is fortunate enough to be using Ruby on Rails, they’ll have an easy time working with our data. However, there are a few reservations we have about this. For one, we’re exposing all the data about every product. There’s nothing super-secret here at the moment, but what if we added sensitive values like cost or MAP price in the future?
Fortunately, we can specify which properties are displayed. Go back to products_controller.rb in your code editor.
-
Add the following bold code around line 9:
format.json { render json: @products, only: [:title, :sku, :price] }
Save the file and leave it open.
-
In the browser reload: localhost:3000/products.json
Now it should list just the title, SKU, and price of each product. So much cleaner!
Adding a Model Method
Let’s give our partner a simple link to promote each product.
In your code editor, open nutty > app > models > product.rb
-
Around line 15, create a method to send the path to the image:
friendly_id :title, use: [:slugged, :finders] def partner_link "https://www.thatnuttyguy.com/products/#{slug}" end end
Save the file and close it.
In your code editor, open nutty > app > controllers > products_controller.rb
-
Add the bold code around line 9 (don’t miss the comma):
format.json { render json: @products, only: [:title, :sku, :price], methods: [:partner_link] }
Save the file.
-
In the browser reload: localhost:3000/products.json
Great, now the full URLs for the products are included.
Creating an XML File
Now, let’s say our partner site just told us their CMS (content management system) can’t parse JSON at all and have requested XML instead. Rails makes this easy!
Switch back to your code editor and the products_controller.rb file.
-
Copy the line of code for JSON (around line 9) and paste a copy directly underneath, editing the new line by simply replacing
json
withxml
as shown:format.json { render json: @products, only: [:title, :sku, :price], methods: [:partner_link] } format.xml { render xml: @products.as_json(only: [:title, :sku, :price], methods: [:partner_link]) }
Save the file.
-
In the browser, navigate to: localhost:3000/products.xml
We have an XML file! (Yes, we are cheating a little bit by rendering the product to JSON first, and then rendering the JSON as XML.) This is the kind of thing Rails excels at: sharing data between sites and being interactive. In other programming languages, getting these results might take much more work.
CSV Exports
Now the accounting department is requesting a CSV export for orders. Fortunately, Active Admin offers some great CSV export tools. First, we need to add orders as a resource to Active Admin.
-
In Terminal, quit the Rails console, then generate a new resource:
exit rails g active_admin:resource order
To check if this worked, we need to place an order. In the browser, navigate to: localhost:3000
Add a couple products to your cart (unless it already has products in it).
Go to the Cart page if you’re not already there, and click Checkout.
Navigate to: localhost:3000/admin
-
Sign in if prompted. If you do not have an account or started from a prepared folder, complete the following sidebar to log in.
Creating a Login
-
Log in with the following:
Email: admin@example.com Password: password At the top of the Dashboard, in the gray bar, click Admin Users.
To the far right of admin@example.com (the only user), click Edit.
-
Set the following:
Email: your email address (Use an account you can access in class!) Password: student1 Click the Update Admin user button.
- Log in again with your new info.
-
-
If you have trouble logging in, try the following workaround:
Creating User Info in Terminal
- In Terminal, open a new tab Ctrl–C
- Enter the console by typing
rails c
-
Type the following to create an admin username and password (all on one line in Terminal):
AdminUser.create :email => 'admin@example.com', :password => 'password', :password_confirmation => 'password'
- In the browser return to http://localhost:3000/admin. You should be able to log in.
Complete steps 2–6 from the sidebar above.
At the top, click the Orders link.
Below the order, notice there are Download links to CSV, XML, and JSON provided by default.
Click the CSV link.
-
If it doesn’t automatically open in the browser, go into your computer’s Downloads folder and open it in Excel if you have it.
It’s a decent start, but we would really like more info here. We could improve this by editing the index page (and we already know how to do that), but what if we want our order export to be different than the index page?
In your code editor, open nutty > app > admin > order.rb
Delete the commented out code.
-
Add the code shown in bold:
ActiveAdmin.register Order do csv do column :id column :email column :total column("Products") { |o| o.products.collect(&:title).join(", ") } column("Order Date") { |o| o.created_at.strftime("%-m/%-d/%Y %-I:%M%p") } end end
NOTE: By default, the time was displayed in military time, but we’d rather customize it to show the month/day/year and hour/minute/am or pm.
Save the file.
-
In the browser, reload: localhost:3000/admin/orders.csv
(or reload the Orders page and click the CSV download link.)Now we have our custom order info ready for export!
Leave Terminal, your code editor, and browser open as we will continue to work with them in the following exercise.