Code preparation for Hash Code 2022 with Apps Script

Stéphane Giron
4 min readFeb 23, 2022

--

This year like previous years I will participate to Google Hash Code. This event is a great way to spend time with Valentin C. and the others guys of Devoteam G Cloud Lyon to do some code.

Previous years we did submissions in Node.js or Python but this year I will try to do it with Apps Script. The concept of Hash Code is simple, you have to resolve a problem and to validate your solution you need to test it on different files and generate output files. For that when you run the code locally you don’t have to deal with API but with Apps Script we will need to manage files with the Drive. That is why I prepare some code in order to facilitate the development. For testing you can check the practice round, link.

If you don’t do Hash Code, you will find there useful code to manage CSV files on Drive with Apps Script and how to get your Apps Script source code as txt file :-)

Retrieve CSV files with Apps Script and read data

The CSV files will be in a Drive folder, so we need to parse the folder and get content of each files as an array.

  var folderIn = 'FOLDER_ID';
var files;
var pageToken; var json = {}
do {
files = Drive.Files.list({
q: "'" + folderIn + "' in parents",
maxResults: 100,
pageToken: pageToken
});
if (files.items && files.items.length > 0) {
for (var i = 0; i < files.items.length; i++) {
var file = files.items[i];
json[file.id] = { id: file.id, name: file.title }
// Here is where the magic happens :-)
// See next section
}
} else {
Logger.log('No files found.');
}
pageToken = files.nextPageToken;
} while (pageToken);

Hash Code challenge is not built on the way you will manage files but during the time of the competition you will need to process lot ot times the csv files and generate new files. To save time you need to automate output files generation and extraction.

Treat the CSV files for Hash Code

To treat the files you need to :

  • Get CSV file
  • Extract data
  • Parse data
// Here the magic var csvData = getCsvFile(file.id);
var csvOut = doSomeStuf(csvData)
function getCsvFile(id) {
var csv = DriveApp.getFileById(id)
var csvBlob = csv.getBlob().getDataAsString();
return Utilities.parseCsv(csvBlob, ",");
}
function doSomeStuf(csvData) {
var header = csvData.shift(); //if needed to remove first line
var odd = []; //impair
var even = []; //pair
for (var i = 0; i < csvData.length; i++) {
console.log(csvData[i])
if (isOdd_(i + 1)) {
odd.push(csvData[i])
} else {
even.push(csvData[i])
}
}
// Here the code to solve the problem console.log(odd)
console.log(even)
return toCSV_(odd); // just to return something for testing
}

Some explanation, to get the csv file we need the file ID and in Google Apps Script there is a custom function to parse the CSV Utilities.parseCsv(csvBlob, “,”), it will ease the parsing :-)

Next you need to process the file, here come the doSomeStuf() function. In Hash Code most of the time the input data are splited in 2 lines :

Hashcode sample data

That is why in the for loop I split data in odd/even, to have the ability to split it easily. For now I put the data in an array but not sure it will be relevant for the competition. Anyway I have the code to split the input data.

Create ouput CSV files

From the function doSomeStuf() I will get a CSV content. So now I need to generate CSV files with Apps Script and store the data on Google Drive.

var folderOut = 'ID_FOLDER_OUTPUT';function pushCsvToFolderOut(csvOut, title) {
var newFile = DriveApp.createFile('out_' + title, csvOut, MimeType.PLAIN_TEXT);
newFile.moveTo(DriveApp.getFolderById(folderOut))
}

Now I have the full process ready, I can grab files from a Drive folder folder, read CSV files and treat them and push solution files to an output folder.

Bonus, create a txt file with the code of your apps script file

Hashcode submission form

In the submission process of Hash Code you need to push the source code of your program. When you are locally it is easy the source file is accessible directly, with Apps Script we will need to generate it ;-)

function createAppsScriptTxt_() {
// credit https://issuetracker.google.com/issues/36765129#comment8
var script = Drive.Files.get(appsScriptFile)
var url = script.exportLinks['application/vnd.google-apps.script+json'];
var response = UrlFetchApp.fetch(url, {
headers: {
'Authorization': 'Bearer ' + ScriptApp.getOAuthToken()
}
});
var blob = response.getBlob();
var json = JSON.parse(blob.getDataAsString());
var txt = '';
for(var key in json.files){
var file = json.files[key];
txt += 'Name : '+file.name + '\n\n';
txt += 'Type : '+file.type + '\n\n';
txt += 'Code : ' + Utilities.formatString('%s', file.source) + '\n\n';
}
var newFile = DriveApp.createFile('code_' + script.title+'.txt', txt, MimeType.PLAIN_TEXT);
newFile.moveTo(DriveApp.getFolderById(folderOut))
}

I decided to ceate a simple txt file with all the content of the Apps Script file. Special credit to Eric Koleda ;-) that share the snippet to get the json version of an Apps Script file.

Final part

Now we have the full code to manage input and ouput CSV files for Hashcode 2022. We just need to produce the best code ever.

The full code is availale there : view on github

--

--