Excel liberation is all about being able to step outside Excel, whether it’s getting public data, integrating with other platforms or in the case of today’s post, interacting with and delegating processing to the cloud on a completely different environment.
In today’s post, I’ll describe where I’ve got to in bringing together a bunch of topics I’ve been posting on from time to time. The general theme is to have a single place where a library of scripts, rest API queries, mashups, API keys and other things could be accessible from multiple platforms (well Excel, javaScript and Google Apps Script at least), and where possible, sharing code. Here are the various threads I can finally pull together.
- Managing and sharing libraries in Google Apps Script
- Automating silos in scriptDB
- Using Google Apps ScriptDB as a lockbox
- Google Caching and faking jsonp
- Keeping Google apps shortcuts under control
- Using Content Service as a rest server
- Somewhere to keep API keys
- Letting Google apps script do the work
- Urbarama API mashup
- Excel rest library migration to Google Apps Script
- Using Google apps script as a wrapper for multiple APIS
- … and various others on the Excel liberation site
So here’s where I’ve got to.
Google Apps Script Published apps receive requests, sometimes that need to get data from either private or public lockboxes, sometimes they do the processing, and in other examples they return raw lockbox data. In all cases, REST requests are made and json or jsonP responses are provided using the Google Apps Script Content Service. This means that Google Apps Script acts as a kind of switchboard for all my needs, regardless of the platform. I use it store my API keys, various reference libraries, for mashups, even to provide a directory of itself.
Here are some examples. You’ll find this in the cDataSet.xlsm workbook downloadable from the Excel liberation site, or Google Apps versions here. There are more examples in the links given previously.
Mashups.
In a previous post, I covered the urbarama mashup. This was combining a couple of APIS- urbarama and yahoo geocoding. I initially coded it in Google Apps Script, and then in VBA. I realized though that I just needed to code it once in Google Apps Script, publish it, pass the query from Excel, and get the combined results from the Google Apps Script version.
This is all that is now needed in Excel since the code all happens in Google Apps Script
Public Sub testUrbaramaPseudoRest() generalQuery "urbaramamashup", "urbaramamashup", _ InputBox("Enter any geocodable address around which to search"), , , _ "&within=" & InputBox("distance in km within which to look") End Sub
Google ‘shortcuts’
One of the annoying things about Google Published Scripts is that the link for them is pretty indigestible. I decided to keep a library of what was published in the public lockbox. It was then pretty straightforward to create a publisher for that library and make an entry for the publisher in the rest library. It looks like this
w = cj.add("publicstuff"); w.add ("restType", ERRESTTYPE.erSingleQuery); w.add ("url", "https://script.google.com/a/macros/mcpher.com/s/AKfycbzLXr1aQKQVK2imlIJp9C6m_HEBAmLBiYM28mfnLn_3oIe3c2kN/exec?entry="); w.add ("results", "results"); w.add ("treeSearch", false); w.add ("ignore");
And here’s how to get them into Excel
Public Sub testPublicStuff() generalQuery "publicstuff", "publicstuff", "", , True End Sub
And into Google Apps Script
function testPublicStuff() { mcpher.generalQuery ("publicstuff", "publicstuff", "", undefined, true); }
Which give a result as below. Now I can forget all about those long names, and just refer to these apps by their names, indirectly through a rest query.
Indirection
Going back to the Rest library, which itself can be served up into Excel or Google Docs worksheet – a snippet below, we can now use indirection to find out the publisher Url
To do this, we simply use an indirection name instead of a URL in the rest library entry. Here’s urbarama mashup using indirection, where publicstuff is the same entry we used earlier.
w = cj.add("urbaramamashup"); w.add ("restType", ERRESTTYPE.erSingleQuery); w.add ("url", "?address="); w.add ("results", "projects"); w.add ("treeSearch", false); w.add ("ignore"); w.add ("indirect","publicstuff");
So what’s happening here ?
- The indirection causes a lookup on the indirection value- in this case ‘publicstuff’ in the rest library, with the key ‘urbaramamashup’
- public stuff will return the real Url for urbarama mashup, and after that short interlude, we resume the process using the real URL.
- It’s a rather small piece of code to do this, and thanks to the wonders of recursion, multiple levels of indirection are possible. In the snippet below, we are already in the restQuery function, trying to figure out the Url for urbaramamashup.
// this is using an indirect lockbox for the published uri if (cj.childExists("indirect")) { if (cj.child("indirect").toString()) { // could be recursive var crIndirect = restQuery("", cj.child("indirect").toString(), sEntry, undefined ,undefined ,undefined , false) ; if (!crIndirect) return null; sUrl = crIndirect.jObject().children("results").child("1.mystuff.publish").toString() + sUrl; } }
- The urbarama mashup will itself call multiple APIS, consolidates the response, and return some jSon with the results.
Here's the step by step guide on how to do this. https://ramblings.mcpher.com/Home/excelquirks/gasproxy