service-collector.js (5137B)
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;