Skip to content

Commit 1d992e0

Browse files
committed
SchemaProvider: Create a common BaseSchemaProvider class
1 parent d20460f commit 1d992e0

File tree

2 files changed

+69
-53
lines changed

2 files changed

+69
-53
lines changed

lib/github_provider.js

Lines changed: 8 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -19,10 +19,10 @@ const crypto = require('crypto');
1919

2020
const axios = require('axios');
2121

22-
const ResourceCache = require('./resource_cache').ResourceCache;
2322
const Template = require('./template').Template;
24-
const { BaseTemplateProvider } = require('./template_provider');
23+
const { BaseSchemaProvider } = require('./schema_provider');
2524
const { BaseDataProvider } = require('./data_provider');
25+
const { BaseTemplateProvider } = require('./template_provider');
2626
const { stripExtension } = require('./utils');
2727

2828
class GitHubContentsApi {
@@ -76,27 +76,21 @@ class GitHubContentsApi {
7676
/**
7777
* SchemaProvider that fetches data from a GitHub repository
7878
*/
79-
class GitHubSchemaProvider {
79+
class GitHubSchemaProvider extends BaseSchemaProvider {
8080
constructor(repo, schemaRootPath, options) {
81+
super();
82+
8183
options = options || {};
8284

8385
this._rootDir = `/${schemaRootPath}`;
8486
this._contentsApi = new GitHubContentsApi(repo, {
8587
apiToken: options.apiToken
8688
});
87-
88-
this.cache = new ResourceCache(schemaName => Promise.resolve()
89-
.then(() => this._contentsApi.getContentsData(`${this._rootDir}/${schemaName}.json`)));
9089
}
9190

92-
/**
93-
* Get the schema associated with the supplied key
94-
*
95-
* @param {string} key
96-
* @returns {object}
97-
*/
98-
fetch(key) {
99-
return this.cache.fetch(key);
91+
_loadSchema(schemaName) {
92+
return Promise.resolve()
93+
.then(() => this._contentsApi.getContentsData(`${this._rootDir}/${schemaName}.json`));
10094
}
10195

10296
/**

lib/schema_provider.js

Lines changed: 61 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -20,20 +20,25 @@ const fs = require('fs');
2020
const ResourceCache = require('./resource_cache').ResourceCache;
2121

2222
/**
23-
* SchemaProvider that fetches data from the file system
23+
* Abstract base class for SchemaProvider classes
2424
*/
25-
class FsSchemaProvider {
26-
/**
27-
* @param {string} schemaRootPath - a path to a directory containing schema files
28-
*/
29-
constructor(schemaRootPath) {
30-
this.schema_path = schemaRootPath;
31-
this.cache = new ResourceCache(schemaName => new Promise((resolve, reject) => {
32-
fs.readFile(`${schemaRootPath}/${schemaName}.json`, (err, data) => {
33-
if (err) return reject(err);
34-
return resolve(data.toString('utf8'));
35-
});
36-
}));
25+
class BaseSchemaProvider {
26+
constructor() {
27+
if (new.target === BaseSchemaProvider) {
28+
throw new TypeError('Cannot instantiate Abstract BaseSchemaProvider');
29+
}
30+
31+
const abstractMethods = [
32+
'_loadSchema',
33+
'list'
34+
];
35+
abstractMethods.forEach((method) => {
36+
if (this[method] === undefined) {
37+
throw new TypeError(`Expected ${method} to be defined`);
38+
}
39+
});
40+
41+
this.cache = new ResourceCache(schemaName => this._loadSchema(schemaName));
3742
}
3843

3944
/**
@@ -45,6 +50,29 @@ class FsSchemaProvider {
4550
fetch(key) {
4651
return this.cache.fetch(key);
4752
}
53+
}
54+
55+
/**
56+
* SchemaProvider that fetches data from the file system
57+
*/
58+
class FsSchemaProvider extends BaseSchemaProvider {
59+
/**
60+
* @param {string} schemaRootPath - a path to a directory containing schema files
61+
*/
62+
constructor(schemaRootPath) {
63+
super();
64+
65+
this.schema_path = schemaRootPath;
66+
}
67+
68+
_loadSchema(schemaName) {
69+
return new Promise((resolve, reject) => {
70+
fs.readFile(`${this.schema_path}/${schemaName}.json`, (err, data) => {
71+
if (err) return reject(err);
72+
return resolve(data.toString('utf8'));
73+
});
74+
});
75+
}
4876

4977
/**
5078
* List all schema known to the provider
@@ -67,41 +95,34 @@ class FsSchemaProvider {
6795
/**
6896
* SchemaProvider that fetches data from an atg-storage DataStore
6997
*/
70-
class DataStoreSchemaProvider {
98+
class DataStoreSchemaProvider extends BaseSchemaProvider {
7199
/**
72100
* @param {object} datastore - an atg-storage DataStore
73101
* @param {string} tsName - the key to use to access the schema in the provided DataStore
74102
*/
75103
constructor(datastore, tsName) {
104+
super();
105+
76106
this.storage = datastore;
77107
this.tsName = tsName;
78-
this.cache = new ResourceCache(
79-
schemaName => this.storage.hasItem(this.tsName)
80-
.then((result) => {
81-
if (result) {
82-
return Promise.resolve();
83-
}
84-
return Promise.reject(new Error(`Could not find template set "${this.tsName}" in data store`));
85-
})
86-
.then(() => this.storage.getItem(this.tsName))
87-
.then(ts => ts.schemas[schemaName])
88-
.then((schema) => {
89-
if (typeof schema === 'undefined') {
90-
return Promise.reject(new Error(`Failed to find schema named "${schemaName}"`));
91-
}
92-
return Promise.resolve(schema);
93-
})
94-
);
95108
}
96109

97-
/**
98-
* Get the schema associated with the supplied key
99-
*
100-
* @param {string} key
101-
* @returns {object}
102-
*/
103-
fetch(key) {
104-
return this.cache.fetch(key);
110+
_loadSchema(schemaName) {
111+
return this.storage.hasItem(this.tsName)
112+
.then((result) => {
113+
if (result) {
114+
return Promise.resolve();
115+
}
116+
return Promise.reject(new Error(`Could not find template set "${this.tsName}" in data store`));
117+
})
118+
.then(() => this.storage.getItem(this.tsName))
119+
.then(ts => ts.schemas[schemaName])
120+
.then((schema) => {
121+
if (typeof schema === 'undefined') {
122+
return Promise.reject(new Error(`Failed to find schema named "${schemaName}"`));
123+
}
124+
return Promise.resolve(schema);
125+
});
105126
}
106127

107128
/**
@@ -123,6 +144,7 @@ class DataStoreSchemaProvider {
123144
}
124145

125146
module.exports = {
147+
BaseSchemaProvider,
126148
FsSchemaProvider,
127149
DataStoreSchemaProvider
128150
};

0 commit comments

Comments
 (0)