Subclasses and Inheritance in Google App Script
Asked Answered
N

4

6

Anyone have any patterns for writing and subclassing objects in Google Apps Script?

I've tried defining subclasses with ParentClass.call(this, args), and putting parent class methods both in the original definition of the parent and assigning them to ParentClass.prototype. But while this code passes unit tests, it fails when used in Google Apps Script.

Necrotomy answered 9/3, 2012 at 0:23 Comment(0)
D
3

it's about class extend ( but javascript doesn't have real 'class' ).you may use Prototype.js or mootool.js or do like this?

function Human () {
    this.init.apply ( this, arguments );
}
Human.prototype = {
    init: function () {
        var optns = arguments[0] || {};
        this.age = optns.age || 0;
        this.name = optns.name || "nameless";
    },
    getName : function () {
        return this.name;
    },
    getAge : function () {
        return this.age;
    }
}

function Man () {
    this.init.apply ( this, arguments );
}
Man.prototype = {
    init : function () {
        Human.prototype.init.apply (this, arguments);
        this.sex = "man";
    },
    getName : Human.prototype.getName,
    getAge : Human.prototype.getAge,
    getSex : function () {
        return this.sex;
    }
}
function Woman () {
    this.init.apply ( this, arguments );
}
Woman.prototype = {
    init : function () {
        Human.prototype.init.apply (this, arguments);
        this.sex = "woman";
    },
    getName : Human.prototype.getName,
    getAge : Human.prototype.getAge,
    getSex : Man.prototype.getSex
}

var human = new Human({age:60,name:"Tom Tomas"}),
    man1 = new Man({age:30,name:"Wood Tomas"}),
    woman1 = new Woman({age:19,name:"Mary Tomas"});

console.log( human.getName() );
console.log( man1.getName() );
console.log( woman1.getName() );

console.log( human.getAge() );
console.log( man1.getAge() );
console.log( woman1.getAge() );

console.log( human.getSex && human.getSex() );
console.log( man1.getSex() );
console.log( woman1.getSex() );

or you could use jQuery's $.extend to do this. wish can help !

Dupleix answered 9/3, 2012 at 1:15 Comment(1)
I'm down with all that, but I can't bring jQuery into Google App script. So Prototype is very unlikely.Necrotomy
V
2

Error: ReferenceError: <class> is not defined

If your code is correct and it still doesn't work on the Google Script platform (getting exception above), try sorting the file. Yes, really, sort it.

But even after sorting, if it throws 'ReferenceError: <class> is not defined' error, try ordering the file manually. Make sure that the undefined class file is evaluated first by renaming the file.

001_Animal.gs < undefined class
002_Rabbit.gs
003_Main.gs

More information about this issue can be found here.

I had a script with no code error, and it didn't work. Also, used @Valentin's code, didn't work either. All I had to do was sort. After that, it worked.

Screenshot-sorting

I'm using the @Valentin's code here. Screenshot-before

Screenshot-after

Vitrescence answered 16/10, 2022 at 15:16 Comment(0)
S
1

It now goes easier! Try this

function test_inheritance() {

  let animal = new Animal("My animal");
  animal.run(22)

  let rabbit = new Rabbit("White Rabbit");

  rabbit.run(5); // White Rabbit runs with speed 5.
  rabbit.hide(); // White Rabbit hides!
}


class Animal {
  constructor(name) {
    this.speed = 0;
    this.name = name;
  }
  run(speed) {
    this.speed = speed;
    console.log(`${this.name} runs with speed ${this.speed}.`);
  }
  stop() {
    this.speed = 0;
    console.log(`${this.name} stands still.`);
  }
}


class Rabbit extends Animal {
  hide() {
    console.log(`${this.name} hides!`);
  }
}
Soothfast answered 17/2, 2021 at 13:23 Comment(0)
D
0

This should get you going:

var ApiService = {

/**
 * @params  {string}   bloggerId   The ID of your Blog
 * @returns {array}                Posted entries
 */
  getPosts: function (blogID) {  
    var feed = sendRequest_(feedUrl+blogID +"/posts/default");
    return feed;
  }
};


/**
 * First ParentClass (top level parent)
 */
ApiService.parent = function (parent) {
    this.parent = parent;
};

var ParentClass = ApiService.parent.prototype;

/**
 *  Gets the title of a post
 *
 * @param   {object)  post  An XML post entry
 * @returns {string}        The title of the post
 */
ParentClass.getTitle = function () {
    return this.parent.getElement('title').getText();
};

You would use it like:

var firstTitle = ApiService.getPosts()[0].getTitle();     
Deportation answered 7/5, 2012 at 18:30 Comment(1)
I don't think this makes sense.Wattmeter

© 2022 - 2024 — McMap. All rights reserved.