Extracting the source from apps script project


In Getting your apps scripts to Github I introduced the idea of using Drive JSON API for apps script to get your source code out of the Apps Script environment as a first step to getting it to GitHub. Don't forget you'll need Oauth2 for drive set up as described in Oauth2 step by step - apps script authentication for the Drive JSON API

In this section we'll look at an automated way of extracting your .gs and .html files to ordinary Drive files so they can be processed by a git client. 

Let's assume that you want to extract the source for all scripts stored below a particular folder on Drive. In my case, I store all scripts I would want to make public in a folder called "Published Scripts".

My Projects

What I want to generate is a folder structure like this, one for each project in the folders and subfolders of Published scripts.


Each of these folders will contain the source code for a project, and will look like this once extracted


info.json

In addition, an info.json is created. This is used to contain dependency information (for libraries needed - more of that later), as well as information about each of the source files and the last time a snapshot was taken. Each time you run this, it will detect whether there has been a script update (or a referenced library update), and update the directory with the new source (ready to be committed with git).

Below is a finalized info.json. The dependencies and libraries are calculated using gwt rpc dependency service - see ( Making sense of gwt rpc dependency service)


    {
        "id": "1_RFsA_FFosK4Wl-JsBVBnMoaplNKcPKoO8-rKhcFt_Q9vNA5QIuW4saX",
        "title": "Copy of extractScriptSource",
        "createdDate": 1423393950717,
        "modifiedDate": 1423393964892,
        "version": "724761",
        "exportLinks": {
            "application/vnd.google-apps.script+json": "https://script.google.com/feeds/download/export?id=1_RFsA_FFosK4Wl-JsBVBnMoaplNKcPKoO8-rKhcFt_Q9vNA5QIuW4saX&format=json"
        },
        "noticed": 1423481917212,
        "modules": [
            {
                "id": "3635de89-3f32-4e50-80a0-979c6bdba07f",
                "name": "extractSource",
                "type": "server_js"
            },
            {
                "id": "a429f93c-cc31-48de-9119-a8f6258bf798",
                "name": "oauth2StdPattern",
                "type": "server_js"
            },
            {
                "id": "bb03aede-0658-4767-ae76-286bdec1f905",
                "name": "oauth2OneTime",
                "type": "server_js"
            },
            {
                "id": "1822f694-6a78-4e6c-bfd4-d08e028c9092",
                "name": "oauth2WebInit",
                "type": "server_js"
            },
            {
                "id": "23699245-6703-4412-b9bb-2891910ea1d6",
                "name": "settings",
                "type": "server_js"
            },
            {
                "id": "389e347e-8cfd-4d99-ac1e-b633532b7b82",
                "name": "ScriptExtractor",
                "type": "server_js"
            },
            {
                "id": "488c992a-a479-4dd8-b418-33655afb5cd8",
                "name": "forPublishing",
                "type": "server_js"
            },
            {
                "id": "4e2fba72-fb61-4b42-859e-d22af5dd3c4b",
                "name": "GitJsonApi",
                "type": "server_js"
            },
            {
                "id": "a0f6939b-28e6-4ee1-a45f-cd590dfbdd20",
                "name": "gasgit",
                "type": "server_js"
            },
            {
                "id": "ee565f96-5f95-4bdd-95b6-93904edee9ee",
                "name": "dependencies",
                "type": "server_js"
            },
            {
                "id": "333fb59f-7209-466e-a0a2-cc852115fa8e",
                "name": "gitPrepare",
                "type": "server_js"
            }
        ],
        "fileId": "0B92ExLh4POiZTkZmck5HWTFIOXc",
        "extracted": false,
        "libraries": [
            {
                "version": "2",
                "identifier": "cDependencyService",
                "key": "Me90hDkr73ajS2dd-CDc4V6i_d-phDA33",
                "library": "cDependencyService",
                "sdc": "3f412eceec31aa38",
                "known": false
            },
            {
                "version": "3",
                "identifier": "cUrlResult",
                "key": "M59PE-C_VqcthwNDmXB9gsCz3TLx7pV4j",
                "library": "cUrlResult",
                "sdc": "ed8e4f4e3a7734ce",
                "known": true
            },
            {
                "version": "4",
                "identifier": "cDriveJsonApi",
                "key": "MvIo2UPbHoLDhAVcRHrI-VSz3TLx7pV4j",
                "library": "cDriveJsonApi",
                "sdc": "c7c8a4ff59cea46d",
                "known": false
            },
            {
                "version": "13",
                "identifier": "cEzyOauth2",
                "key": "MSaYlTXSVk7FAqpHNCcqBv6i_d-phDA33",
                "library": "cEzyOauth2",
                "sdc": "649b1069a7822a58",
                "known": false
            },
            {
                "version": "18",
                "identifier": "cUseful",
                "key": "Mcbr-v4SsYKJP7JMohttAZyz3TLx7pV4j",
                "library": "cUseful",
                "sdc": "ecf6642f980ce639"
            }
        ],
        "dependencies": [
            {
                "version": "2",
                "identifier": "cDependencyService",
                "key": "Me90hDkr73ajS2dd-CDc4V6i_d-phDA33",
                "library": "cDependencyService",
                "sdc": "3f412eceec31aa38",
                "known": false
            },
            {
                "version": "3",
                "identifier": "cUrlResult",
                "key": "M59PE-C_VqcthwNDmXB9gsCz3TLx7pV4j",
                "library": "cUrlResult",
                "sdc": "ed8e4f4e3a7734ce",
                "known": true
            },
            {
                "version": "18",
                "identifier": "cUseful",
                "key": "Mcbr-v4SsYKJP7JMohttAZyz3TLx7pV4j",
                "library": "cUseful",
                "sdc": "ecf6642f980ce639",
                "known": true
            },
            {
                "version": "4",
                "identifier": "cDriveJsonApi",
                "key": "MvIo2UPbHoLDhAVcRHrI-VSz3TLx7pV4j",
                "library": "cDriveJsonApi",
                "sdc": "c7c8a4ff59cea46d",
                "known": false
            },
            {
                "version": "13",
                "identifier": "cEzyOauth2",
                "key": "MSaYlTXSVk7FAqpHNCcqBv6i_d-phDA33",
                "library": "cEzyOauth2",
                "sdc": "649b1069a7822a58",
                "known": false
            }
        ],
        "sourceWritten": 1423481924232
    }
    




How does it work?

First we need a couple of settings to describe the environment. So in my case I want  to find all the scripts in /Published Scripts and create a directory structure for each project in /Extraction/Scripts on my Drive. We'll deal with the dependency setting later on. 

var SETTINGS= {
  EXTRACT: { // where to put the sources to
    TO:"/Extraction/Scripts"
  },
  PARENT: {  // where to start looking for scripts
    SCRIPTS:"/Published Scripts"
  },
  DEPENDENCY: { // things for dependency management
    LIST: {
      URL: "https://script.google.com/macros/s/AKfycbwZ2Hht93wTNzvRmYINYF7obaOHciBXWcP_wAiEtyGq70_x3cI/exec"
    }
  }
};

The main code is fairly straightforward, and shouldn't need any changes.

This uses the Drive JSON API for apps script, along with a new class ScriptExtractor, , and again - it shouldn't need any changes.

For more on drive SDK see Using Drive SDK

You want to learn Google Apps Script?

Learning Apps Script, (and transitioning from VBA) are covered comprehensively in my my book, Going Gas - from VBA to Apps script, All formats are available from O'ReillyAmazon and all good bookshops. You can also read a preview on O'Reilly

If you prefer Video style learning I also have two courses available. also published by O'Reilly.
Google Apps Script for Developers and Google Apps Script for Beginners.

Comments