blob: 818d4f59bc0dbd6267b3a8f2b4f8e0dc4884d5d0 [file] [log] [blame]
Matteo Scandolo4208f112016-08-10 17:02:02 -07001'use strict';
2
3angular.module('xos.UITutorial', [
4 'ngResource',
5 'ngCookies',
6 'ui.router',
7 'xos.helpers'
8])
9.config(($stateProvider) => {
10 $stateProvider
11 .state('shell', {
12 url: '/',
13 template: '<js-shell></js-shell>'
14 });
15})
16.config(function($httpProvider){
17 $httpProvider.interceptors.push('NoHyperlinks');
18})
19.directive('jsShell', function(){
20 return {
21 restrict: 'E',
22 scope: {},
23 bindToController: true,
24 controllerAs: 'vm',
25 templateUrl: 'templates/js-shell.tpl.html',
26 controller: function($injector){
27 var history = new Josh.History({ key: 'helloworld.history'});
28 var shell = Josh.Shell({history: history});
29
30 shell.onNewPrompt(function(callback) {
31 callback('[ngXosLib] $ ');
32 });
33
34 const errorHandler = (msg, done) => {
35 const errorTpl = _.template(`<span class="error">[ERROR] <%= msg %></span>`);
36 done(errorTpl({msg: msg}));
37 }
38
39 const parseResponse = (res, done) => {
40
41 // TODO @Arpit format res (it can be an array or an object),
42 // it is better if the output is a valid JSON (that we can copy and paste)
43 // TODO handle 204/No-Content response
44 if(angular.isArray(res)){
45 res = res.map(i => {
46 return JSON.stringify(i, ['id', 'name', 'max_instances'], 2) + '<br/>';
47 });
48 }
49 else {
50 res = JSON.stringify(res, ['id', 'name', 'max_instances'], 2);
51 }
52
53 done(res);
54 }
55
56 const getAvailableResources = () => {
57 return angular.module('xos.helpers')._invokeQueue
58 .filter((d) => {
59 if(d[1] !== 'service'){
60 return false;
61 }
62 const serviceDeps = d[2][1];
63 return serviceDeps.indexOf('$resource') !== -1;
64 })
65 .reduce((list, i) => list.concat([i[2][0]]), []);
66 }
67
68 const listAvailableResources = (done) => {
69 const resources = getAvailableResources()
70 .reduce((html, i) => `${html}${i}<br/>`, '');
71 done(resources);
72 }
73
74 const consumeResource = (resourceName, method, args, done) => {
75
76 if(getAvailableResources().indexOf(resourceName) === -1){
77 return errorHandler(`Resource "${resourceName}" does not exists`, done);
78 }
79
80 if(['query', 'get', 'save', '$save', 'delete'].indexOf(method) === -1){
81 return errorHandler(`Method "${method}" not allowed`, done);
82 }
83
84 let Resource;
85 try{
86 Resource = $injector.get(resourceName);
87
88 // TODO @Teo if get/delete check for arguments
89 let params = {};
90
91 // if the method require arguments checks for them
92 if(['get', '$save', 'delete'].indexOf(method) !== -1){
93 if(args.length === 0){
94 return errorHandler(`Method "${method}" require parameters`, done);
95 }
96 }
97
98 // if there are arguments parse them
99 if(args.length > 0){
100 params = eval(`(${args[0]})`);
101 }
102
103 // if it is a query is not possible to use id as parameter
104 if(method === 'query' && angular.isDefined(params.id)){
105 return errorHandler(`Is not possible to use "id" as filter in method "${method}", use "get" instead!`, done);
106 }
107
108 Resource[method](params).$promise
109 .then(res => {
110 return parseResponse(res, done);
111 });
112 }
113 catch(e){
114 console.log(e);
115 return errorHandler(`Failed to inject resource "${resourceName}"`, done);
116 }
117 }
118
119 shell.setCommandHandler('resource', {
120 exec: (cmd, args, done) => {
121 switch(args[0]){
122 case 'list':
123 return listAvailableResources(done);
124 break;
125 default:
126 // use the resource
127 const resourceName = args.shift();
128 const method = args.shift();
129 return consumeResource(resourceName, method, args, done);
130 }
131 },
132 completion: function(cmd, arg, line, callback) {
133 const args = ['list'].concat(getAvailableResources());
134 if(line.text.match(/resource\s[A-Z][a-z]+\s/)){
135 // if arg is a resource, then return available methods
136 if(args.indexOf(arg) !== -1){
137 arg = '';
138 }
139 const methods = ['query', 'get', 'save', '$save', 'delete'];
140 return callback(shell.bestMatch(arg, methods));
141 }
142 return callback(shell.bestMatch(arg, args));
143 }
144 })
145
146 shell.setCommandHandler('slices', {
147 exec: (cmd, args, done) => {
148 Slices.query().$promise
149 .then(res => {
150 res = res.map(i => {
151 return JSON.stringify(i, ['id', 'name', 'max_instances'], 2);
152 });
153
154 res = res.reduce((response, item) => {
155 return `${response},<br>${item}`;
156 });
157
158 done(res);
159 })
160 .catch(err => {
161 console.log(err);
162 done('An error occurred');
163 })
164 }
165 });
166
167 shell.activate();
168 }
169 };
170});