1 | var fs = require('fs');
|
2 | var util = require('util');
|
3 | var path = require('path');
|
4 |
|
5 | var AWS = require('../');
|
6 | var apis = require('../lib/api_loader');
|
7 | var metadata = require('../apis/metadata');
|
8 | var ClientCreator = require('./client-creator');
|
9 |
|
10 | var clientCreator = new ClientCreator();
|
11 | var defaultServices = clientCreator.getDefaultServices().join(',');
|
12 | var sanitizeRegex = /[^a-zA-Z0-9,-]/;
|
13 |
|
14 | var serviceClasses = {};
|
15 | Object.keys(AWS).forEach(function(name) {
|
16 | if (AWS[name].serviceIdentifier) {
|
17 | serviceClasses[AWS[name].serviceIdentifier] = AWS[name];
|
18 | }
|
19 | });
|
20 |
|
21 | function getServiceHeader(service) {
|
22 | if (service === 'all') {
|
23 | return Object.keys(serviceClasses).map(function(name) {
|
24 | return getServiceHeader(name);
|
25 | }).join('\n');
|
26 | }
|
27 |
|
28 | if (!serviceClasses[service]) return null;
|
29 | var versions = serviceClasses[service].apiVersions.map(function(version) {
|
30 | return version.indexOf('*') >= 0 ? null : version;
|
31 | }).filter(function(c) { return c !== null; });
|
32 |
|
33 | var file = util.format(
|
34 | 'if (!Object.prototype.hasOwnProperty.call(AWS, \'' + metadata[service].name + '\')) {\n' +
|
35 | ' AWS.apiLoader.services[\'%s\'] = {};\n' +
|
36 | ' AWS.%s = AWS.Service.defineService(\'%s\', %s);\n',
|
37 | service, metadata[service].name, service, util.inspect(versions));
|
38 | var svcPath = path.join(__dirname, '..', 'lib', 'services', service + '.js');
|
39 | if (fs.existsSync(svcPath)) {
|
40 | file += ' require(\'./services/' + service + '\');\n';
|
41 | }
|
42 | file += '}\n';
|
43 |
|
44 | return file;
|
45 | }
|
46 |
|
47 | function getService(service, version) {
|
48 | if (service === 'all') {
|
49 | return Object.keys(serviceClasses).map(function(name) {
|
50 | var out = serviceClasses[name].apiVersions.map(function(svcVersion) {
|
51 | if (svcVersion.indexOf('*') >= 0) return null;
|
52 | return getService(name, svcVersion);
|
53 | }).filter(function(c) { return c !== null; }).join('\n');
|
54 |
|
55 | return out;
|
56 | }).join('\n');
|
57 | }
|
58 |
|
59 | var svc, api;
|
60 | if (!serviceClasses[service]) {
|
61 | return null;
|
62 | }
|
63 |
|
64 | try {
|
65 | var ClassName = serviceClasses[service];
|
66 | svc = new ClassName({apiVersion: version, endpoint: 'localhost'});
|
67 | api = svc.api;
|
68 | } catch (e) {
|
69 | return null;
|
70 | }
|
71 |
|
72 | var serviceFileName = metadata[service].prefix || service;
|
73 | var lines = [];
|
74 | var line = util.format(
|
75 | 'AWS.apiLoader.services[\'%s\'][\'%s\'] = %s;\n',
|
76 | service, svc.api.apiVersion, 'require(\'../apis/' + serviceFileName + '-' + svc.api.apiVersion + '.min\')');
|
77 | lines.push(line);
|
78 | if (Object.prototype.hasOwnProperty.call(api, 'paginators') && Object.keys(api.paginators).length) {
|
79 | line = util.format(
|
80 | 'AWS.apiLoader.services[\'%s\'][\'%s\'].paginators = %s;\n',
|
81 | service, svc.api.apiVersion, 'require(\'../apis/' + serviceFileName + '-' + svc.api.apiVersion + '.paginators\').pagination');
|
82 | lines.push(line);
|
83 | }
|
84 | if (Object.prototype.hasOwnProperty.call(api, 'waiters') && Object.keys(api.waiters).length) {
|
85 | line = util.format(
|
86 | 'AWS.apiLoader.services[\'%s\'][\'%s\'].waiters = %s;\n',
|
87 | service, svc.api.apiVersion, 'require(\'../apis/' + serviceFileName + '-' + svc.api.apiVersion + '.waiters2\').waiters');
|
88 | lines.push(line);
|
89 | }
|
90 | return lines.join('');
|
91 | }
|
92 |
|
93 | function ServiceCollector(services) {
|
94 | var builtServices = {};
|
95 |
|
96 | function buildService(name, usingDefaultServices) {
|
97 | var match = name.match(/^(.+?)(?:-(.+?))?$/);
|
98 | var service = match[1], version = match[2] || 'latest';
|
99 | var contents = [];
|
100 | var lines, err;
|
101 |
|
102 | if (!builtServices[service]) {
|
103 | builtServices[service] = {};
|
104 |
|
105 | lines = getServiceHeader(service);
|
106 | if (lines === null) {
|
107 | if (!usingDefaultServices) {
|
108 | err = new Error('Invalid module: ' + service);
|
109 | err.name = 'InvalidModuleError';
|
110 | throw err;
|
111 | }
|
112 | } else {
|
113 | contents.push(lines);
|
114 | }
|
115 | }
|
116 |
|
117 | if (!builtServices[service][version]) {
|
118 | builtServices[service][version] = true;
|
119 |
|
120 | lines = getService(service, version);
|
121 | if (lines === null) {
|
122 | if (!usingDefaultServices) {
|
123 | err = new Error('Invalid module: ' + service + '-' + version);
|
124 | err.name = 'InvalidModuleError';
|
125 | throw err;
|
126 | }
|
127 | } else {
|
128 | contents.push(lines);
|
129 | }
|
130 | }
|
131 |
|
132 | return contents.join('');
|
133 | }
|
134 |
|
135 | var serviceCode = '';
|
136 | var usingDefaultServicesToggle = false;
|
137 | if (!services) {
|
138 | usingDefaultServicesToggle = true;
|
139 | services = defaultServices;
|
140 | }
|
141 | if (services.match(sanitizeRegex)) {
|
142 | throw new Error('Incorrectly formatted service names');
|
143 | }
|
144 |
|
145 | var invalidModules = [];
|
146 | var stsIncluded = false;
|
147 | services.split(',').sort().forEach(function(name) {
|
148 | if (name.match(/^sts\b/) || name === 'all') stsIncluded = true;
|
149 | try {
|
150 | serviceCode += buildService(name, usingDefaultServicesToggle) + '\n';
|
151 | } catch (e) {
|
152 | if (e.name === 'InvalidModuleError') invalidModules.push(name);
|
153 | else throw e;
|
154 | }
|
155 | });
|
156 |
|
157 | if (!stsIncluded) {
|
158 | serviceCode += buildService('sts') + '\n';
|
159 | }
|
160 |
|
161 | if (invalidModules.length > 0) {
|
162 | throw new Error('Missing modules: ' + invalidModules.join(', '));
|
163 | }
|
164 |
|
165 | return serviceCode;
|
166 | }
|
167 |
|
168 | module.exports = ServiceCollector;
|