Skip to content

Commit

Permalink
feat(2135): Add new APIs to create pipeline templates (#596)
Browse files Browse the repository at this point in the history
* feat(2135): Added create() functions for both pipelineTemplateFactory.js and versionsFactory

* feat(2135): V2 created new factories for job and pipeline tags and created templateMetaFactory.js

* feat(2135): Pushed changes made during debugging in screwdriver/node_modules

* fix issues

* feat: add tests, create template version logic

* update template version create logic, tests

* add getInstance and tests

---------

Co-authored-by: aishwaryanair04 <[email protected]>
Co-authored-by: ppaul <[email protected]>
  • Loading branch information
3 people authored Nov 17, 2023
1 parent d37365a commit 6855e98
Show file tree
Hide file tree
Showing 16 changed files with 763 additions and 10 deletions.
8 changes: 0 additions & 8 deletions .prettierrc

This file was deleted.

12 changes: 11 additions & 1 deletion index.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,11 @@ const TemplateTagFactory = require('./lib/templateTagFactory');
const TokenFactory = require('./lib/tokenFactory');
const TriggerFactory = require('./lib/triggerFactory');
const UserFactory = require('./lib/userFactory');
const PipelineTemplateFactory = require('./lib/pipelineTemplateFactory');
const PipelineTemplateVersionFactory = require('./lib/pipelineTemplateVersionFactory');
const TemplateMetaFactory = require('./lib/templateMetaFactory');
const PipelineTemplateVersion = require('./lib/pipelineTemplateVersion');
const TemplateMeta = require('./lib/templateMeta');

module.exports = {
BannerFactory,
Expand All @@ -35,5 +40,10 @@ module.exports = {
TemplateTagFactory,
TokenFactory,
TriggerFactory,
UserFactory
UserFactory,
PipelineTemplateFactory,
PipelineTemplateVersionFactory,
TemplateMetaFactory,
PipelineTemplateVersion,
TemplateMeta
};
2 changes: 1 addition & 1 deletion lib/baseFactory.js
Original file line number Diff line number Diff line change
Expand Up @@ -279,7 +279,7 @@ class BaseFactory {
* Cleanup
*/
cleanUp() {
// no-op when not implemted by extender
// no-op when not implemented by extender
}

/**
Expand Down
31 changes: 31 additions & 0 deletions lib/jobTemplateTagFactory.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
'use strict';

const BaseFactory = require('./baseFactory');
const TemplateTagFactory = require('./templateTagFactory');

let instance;

class JobTemplateTagFactory extends TemplateTagFactory {
/**
* Get the template type
* @returns {string}
*/
_getTemplateType() {
return 'JOB';
}

/**
* Get an instance of the JobTemplateTagFactory
* @method getInstance
* @param {Object} config
* @param {Datastore} config.datastore
* @return {JobTemplateTagFactory}
*/
static getInstance(config) {
instance = BaseFactory.getInstance(JobTemplateTagFactory, instance, config);

return instance;
}
}

module.exports = JobTemplateTagFactory;
7 changes: 7 additions & 0 deletions lib/pipelineTemplate.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
'use strict';

const TemplateMetaModel = require('./templateMeta');

class PipelineTemplate extends TemplateMetaModel {}

module.exports = PipelineTemplate;
31 changes: 31 additions & 0 deletions lib/pipelineTemplateFactory.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
'use strict';

const TemplateMetaFactory = require('./templateMetaFactory');
const BaseFactory = require('./baseFactory');

let instance;

class PipelineTemplateFactory extends TemplateMetaFactory {
/**
* Get the template type
* @returns {string}
*/
_getTemplateType() {
return 'PIPELINE';
}

/**
* Get an instance of the PipelineTemplateFactory
* @method getInstance
* @param {Object} config
* @param {Datastore} config.datastore
* @return {PipelineTemplateFactory}
*/
static getInstance(config) {
instance = BaseFactory.getInstance(PipelineTemplateFactory, instance, config);

return instance;
}
}

module.exports = PipelineTemplateFactory;
31 changes: 31 additions & 0 deletions lib/pipelineTemplateTagFactory.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
'use strict';

const BaseFactory = require('./baseFactory');
const TemplateTagFactory = require('./templateTagFactory');

let instance;

class PipelineTemplateTagFactory extends TemplateTagFactory {
/**
* Get the template type
* @returns {string}
*/
_getTemplateType() {
return 'PIPELINE';
}

/**
* Get an instance of the PipelineTemplateTagFactory
* @method getInstance
* @param {Object} config
* @param {Datastore} config.datastore
* @return {PipelineTemplateTagFactory}
*/
static getInstance(config) {
instance = BaseFactory.getInstance(PipelineTemplateTagFactory, instance, config);

return instance;
}
}

module.exports = PipelineTemplateTagFactory;
24 changes: 24 additions & 0 deletions lib/pipelineTemplateVersion.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
'use strict';

const BaseModel = require('./base');

class PipelineTemplateVersionModel extends BaseModel {
/**
* Construct a PipelineTemplateVersionModel object
* @method constructor
* @param {Object} config
* @param {Datastore} config.datastore Object that will perform operations on the datastore
* @param {String} config.name The template name
* @param {String} config.namespace The template namespace
* @param {String} config.version Version of the template
* @param {String} config.description Description of the template
* @param {String} config.maintainer Maintainer's email
* @param {Object} config.config Config of the screwdriver-template.yaml
* @param {String} config.pipelineId pipelineId of the template
*/
constructor(config) {
super('pipelineTemplateVersions', config);
}
}

module.exports = PipelineTemplateVersionModel;
147 changes: 147 additions & 0 deletions lib/pipelineTemplateVersionFactory.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,147 @@
'use strict';

const schema = require('screwdriver-data-schema');
const BaseFactory = require('./baseFactory');
const PipelineTemplateVersionModel = require('./pipelineTemplateVersion');

const EXACT_VERSION_REGEX = schema.config.regex.EXACT_VERSION;
const VERSION_REGEX = schema.config.regex.VERSION;
let instance;

class PipelineTemplateVersionFactory extends BaseFactory {
/**
* Construct a TemplateFactory object
* @method constructor
* @param {Object} config
* @param {Datastore} config.datastore Object that will perform operations on the datastore
*/
constructor(config) {
super('pipelineTemplateVersions', config);
}

/**
* Instantiate a PipelineTemplateVersionModel class
* @method createClass
* @param {Object} config Template data
* @param {Datastore} config.datastore Object that will perform operations on the datastore
* @param {String} config.name The template name
* @param {String} config.namespace The template namespace
* @param {String} config.version Version of the template
* @param {String} config.description Description of the template
* @param {String} config.maintainer Maintainer's email
* @param {Object} config.config Config of the screwdriver-template.yaml
* @param {String} config.pipelineId pipelineId of the template
* @return {PipelineTemplateVersionModel}
*/
createClass(config) {
return new PipelineTemplateVersionModel(config);
}

/**
* Create a new template of the correct version (See schema definition)
* @method create
* @param {Object} config Config object
* @param templateMetaFactory
* @param {Datastore} config.datastore Object that will perform operations on the datastore
* @param {String} config.name The template name
* @param {String} config.namespace The template namespace
* @param {String} config.version Version of the template
* @param {String} config.description Description of the template
* @param {String} config.maintainer Maintainer's email
* @param {Object} config.config Config of the screwdriver-template.yaml
* @param {String} config.pipelineId pipelineId of the template
* @return {Promise}
*/
async create(config, templateMetaFactory) {
const createTime = new Date().toISOString();
const [, configMajor, configMinor] = VERSION_REGEX.exec(config.version);

// get the template meta
let pipelineTemplateMeta = await templateMetaFactory.get({
name: config.name,
namespace: config.namespace
});

// if template meta doesn't exist, create one
if (!pipelineTemplateMeta) {
pipelineTemplateMeta = await templateMetaFactory.create({
pipelineId: config.pipelineId,
namespace: config.namespace,
name: config.name,
maintainer: config.maintainer,
createTime,
updateTime: createTime
});
}

let newVersion = configMinor ? `${configMajor}${configMinor}.0` : `${configMajor}.0.0`;

if (pipelineTemplateMeta.latestVersion) {
// list all the versions of the template
const pipelineTemplateVersions = await super.list({
params: {
templateId: pipelineTemplateMeta.id,
sort: 'descending',
sortBy: 'createTime'
}
});

if (pipelineTemplateVersions.length > 0) {
// get latest version that have version starting with config.version
const pipelineTemplateVersion = pipelineTemplateVersions.find(template => {
const [, major, minor] = VERSION_REGEX.exec(template.version);

return major === configMajor && minor === configMinor;
});

if (pipelineTemplateVersion) {
const [, targetMajor, targetMinor, targetPatch] = VERSION_REGEX.exec(
pipelineTemplateVersion.version
);
const patch = parseInt(targetPatch.slice(1), 10) + 1;

newVersion = `${targetMajor}${targetMinor}.${patch}`;
}
}
}

const newPipelineTemplateVersion = await super.create({
templateId: pipelineTemplateMeta.id,
description: config.description,
config: config.config,
createTime,
version: newVersion
});

const latestVersion = pipelineTemplateMeta.latestVersion || '0.0.0';
const [, latestMajor, latestMinor, latestPatch] = EXACT_VERSION_REGEX.exec(latestVersion);
const [, major, minor, patch] = EXACT_VERSION_REGEX.exec(newVersion);

if (
major > latestMajor ||
(major === latestMajor && minor >= latestMinor) ||
(major === latestMajor && minor === latestMinor && patch > latestPatch)
) {
pipelineTemplateMeta.latestVersion = newPipelineTemplateVersion.version;
pipelineTemplateMeta.updateTime = new Date().toISOString();
await pipelineTemplateMeta.update();
}

return newPipelineTemplateVersion;
}

/**
* Get an instance of the PipelineTemplateVersionFactory
* @method getInstance
* @param {Object} config
* @param {Datastore} config.datastore
* @return {PipelineTemplateVersionFactory}
*/
static getInstance(config) {
instance = BaseFactory.getInstance(PipelineTemplateVersionFactory, instance, config);

return instance;
}
}

module.exports = PipelineTemplateVersionFactory;
24 changes: 24 additions & 0 deletions lib/templateMeta.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
'use strict';

const BaseModel = require('./base');

class TemplateMeta extends BaseModel {
/**
* Construct a TemplateModel object
* @method constructor
* @param {Object} config
* @param {Datastore} config.datastore Object that will perform operations on the datastore
* @param {String} config.name The template name
* @param {String} config.namespace The template namespace
* @param {String} config.version Version of the template
* @param {String} config.description Description of the template
* @param {String} config.maintainer Maintainer's email
* @param {Object} config.config Config of the screwdriver-template.yaml
* @param {String} config.pipelineId pipelineId of the template
*/
constructor(config) {
super('templateMeta', config);
}
}

module.exports = TemplateMeta;
47 changes: 47 additions & 0 deletions lib/templateMetaFactory.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
'use strict';

const BaseFactory = require('./baseFactory');
const TemplateMeta = require('./templateMeta');

class TemplateMetaFactory extends BaseFactory {
/**
* Construct a TemplateFactory object
* @method constructor
* @param {Object} config
* @param {Datastore} config.datastore Object that will perform operations on the datastore
*/
constructor(config) {
super('templateMeta', config);
}

/**
*
* @param config
* @returns {TemplateMeta}
*/
createClass(config) {
return new TemplateMeta(config);
}

create(config) {
config.templateType = this._getTemplateType();

return super.create(config);
}

get(config) {
config.templateType = this.getTemplateType();

return super.get(config);
}

getTemplateType() {
return this._getTemplateType();
}

_getTemplateType() {
throw new Error('Not implemented');
}
}

module.exports = TemplateMetaFactory;
1 change: 1 addition & 0 deletions lib/templateTagFactory.js
Original file line number Diff line number Diff line change
Expand Up @@ -129,6 +129,7 @@ class TemplateTagFactory extends BaseFactory {
const nameObj = parseTemplateConfigName(config);
const result = hoek.applyToDefaults(config, nameObj);

result.templateType = this.getTemplateType();
result.createTime = new Date().toISOString();

return super.create(result);
Expand Down
Loading

0 comments on commit 6855e98

Please sign in to comment.