mushy 0.0.2 → 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 1a4d1e2d7740622ef1ddc7aaa6dc7bcfb64f1e7e7d5cedd2451f78d601a085f8
4
- data.tar.gz: 5facf81ef9fd26d5ba649739e65cb6017de9afe192d5830279a397716cb93b78
3
+ metadata.gz: 5b0ff90e9b20233f5744ec73d94137a2a117dc5bbdcb1962242caf5d3fdec8f3
4
+ data.tar.gz: dd834f5294cf131393881c7647a25c27d54275e7c510c2b19bac233b9193be43
5
5
  SHA512:
6
- metadata.gz: e7751abc81f9d8f9db91c3cf612901066be0132b07694182cdaf480318df619fe52276974678aee03bc1a1257323c09379ddc9e19838aa6a37752a992d189955
7
- data.tar.gz: dc1b0a45620512cee1dfffb208c44ddef18ea92581ea1188f4c0df2967093f5c1ca21efb67fc92bc17a357a0ecfeb6789e35e8e0609e636b350acc257c2fc3e3
6
+ metadata.gz: 41b4cdfd6d24547838ba11b0bbdb3515ec8baee305ab5b97079d040019951354d29074d9a93c88cf94be9b70c0875220f3b76630097c9cc697ddf4ea4cef550f
7
+ data.tar.gz: 1ec8aab8a0ac9281d1ed036b84add01be639c6223ef46db6f7132d4140f09c10d2ea0a6707bca99aa79b3db024efa2f4cf34ce5430c68e8838953be21f125dd2
@@ -40,14 +40,14 @@ module Mushy
40
40
  {
41
41
  fluxs: Mushy::Flux.all.select { |x| x.respond_to? :details }.map do |flux|
42
42
  details = flux.details
43
- details[:config][:incoming_split] = { type: 'text', description: 'Split an incoming event into multiple events by this key, an each event will be processed independently.', default: '' }
44
- details[:config][:outgoing_split] = { type: 'text', description: 'Split an outgoing event into multiple events by this key.', default: '' }
45
- details[:config][:merge] = { type: 'text', description: 'A comma-delimited list of fields from the event to carry through. Use * to merge all fields.', default: '' }
46
- details[:config][:group] = { type: 'text', description: 'Group events by a field, which is stored in a key. The format is group_by|group_key.', default: '' }
47
- details[:config][:limit] = { type: 'integer', description: 'Limit the number of events to this number.', default: '' }
48
- details[:config][:join] = { type: 'text', description: 'Join all of the events from this flux into one event, under this name.', default: '' }
49
- details[:config][:sort] = { type: 'text', description: 'Sort by this key.', default: '' }
50
- details[:config][:model] = { type: 'keyvalue', description: 'Reshape the outgoing events.', value: {}, default: {} }
43
+ details[:config][:incoming_split] = { type: 'text', shrink: true, description: 'Split an incoming event into multiple events by this key, an each event will be processed independently.', default: '' }
44
+ details[:config][:outgoing_split] = { type: 'text', shrink: true, description: 'Split an outgoing event into multiple events by this key.', default: '' }
45
+ details[:config][:merge] = { type: 'text', shrink: true, description: 'A comma-delimited list of fields from the event to carry through. Use * to merge all fields.', default: '' }
46
+ details[:config][:group] = { type: 'text', shrink: true, description: 'Group events by a field, which is stored in a key. The format is group_by|group_key.', default: '' }
47
+ details[:config][:limit] = { type: 'integer', shrink: true, description: 'Limit the number of events to this number.', default: '' }
48
+ details[:config][:join] = { type: 'text', shrink: true, description: 'Join all of the events from this flux into one event, under this name.', default: '' }
49
+ details[:config][:sort] = { type: 'text', shrink: true, description: 'Sort by this key.', default: '' }
50
+ details[:config][:model] = { type: 'keyvalue', shrink: true, description: 'Reshape the outgoing events.', value: {}, default: {} }
51
51
 
52
52
  details[:config]
53
53
  .select { |_, v| v[:type] == 'keyvalue' }
@@ -12,19 +12,28 @@ module Mushy
12
12
  </head>
13
13
  <body>
14
14
  <div id="app">
15
- <table>
15
+ <table v-if="setup.showFlux == false">
16
+ <tr>
17
+ <th>Name</th>
18
+ <th>Receives Events From</th>
19
+ <th>Actions</th>
20
+ </tr>
16
21
  <tr v-for="flux in flow.fluxs">
17
22
  <td>{{flux.name}}</td>
18
- <td>{{flux.flux}}</td>
19
- <td><a href="#" v-on:click.prevent.stop="edit({ flux: flux, setup: setup, configs: configs })">[Edit]</a></td>
23
+ <td>{{flux_name_for(flux.parent, flow.fluxs)}}</td>
24
+ <td>
25
+ <button v-on:click.prevent.stop="editFlux({ flux: flux, setup: setup, configs: configs })">Edit</button>
26
+ <button v-on:click.prevent.stop="deleteFlux({ flux: flux, flow: flow })">Delete</button>
27
+ </td>
20
28
  </tr>
21
29
  </table>
22
- <a href="#" v-if="setup.id.value == ''" v-on:click.prevent.stop="startNew({ setup: setup, configs: configs })">[New]</a>
23
- <a href="#" v-if="setup.id.value == ''" v-on:click.prevent.stop="saveFlow(flow)">[Save]</a>
24
- <div v-if="setup.id.value">
30
+ <button v-if="setup.showFlux == false" v-on:click.prevent.stop="startNew({ setup: setup, configs: configs })">Start a New Flux</button>
31
+ <button v-if="setup.showFlux == false" v-on:click.prevent.stop="saveFlow({ setup: setup, flow: flow })">Save This Flow</button>
32
+ <button v-if="setup.showFlux" v-on:click.prevent.stop="setup.showFlux = false">&lt; Go Back To List</button>
33
+ <div v-if="setup.showFlux">
25
34
  <mip-heavy :data="setup"></mip-heavy>
26
35
  <mip-heavy v-for="(data, id) in configs" v-show="setup.flux.value === id" :data="data"></mip-heavy>
27
- <div v-if="results.loading">Loading...</div>
36
+ <div v-if="results.errorMessage">{{results.errorMessage}}</div>
28
37
  <div v-else>{{results.length}} result{{results.length == 1 ? "" : "s"}}</div>
29
38
  <mip-heavy v-for="data in results" :data="data"></mip-heavy>
30
39
  </div>
@@ -48,28 +57,48 @@ module Mushy
48
57
 
49
58
  var components = {
50
59
  label: {
51
- props: ['label', 'description'],
52
- template: '<label :for="id" v-if="label != \\'\\'">{{label || ' + fancyName('id') + '}} <i v-show="description">({{description}})</i></label>'
60
+ props: ['label', 'description', 'hide_description'],
61
+ template: '<label :for="id" v-if="label != \\'\\'">{{label || ' + fancyName('id') + '}} <i v-show="description && !hide_description">({{description}})</i></label>'
62
+ },
63
+ h1: {
64
+ props: ['label', 'description', 'hide_description'],
65
+ template: '<h1 v-if="label != \\'\\'">{{label || ' + fancyName('id') + '}} <i v-show="description && !hide_description">({{description}})</i></h1>'
66
+ },
67
+ h2: {
68
+ props: ['label', 'description', 'hide_description'],
69
+ template: '<h2 v-if="label != \\'\\'">{{label || ' + fancyName('id') + '}} <i v-show="description && !hide_description">({{description}})</i></h2>'
70
+ },
71
+ h3: {
72
+ props: ['label', 'description', 'hide_description'],
73
+ template: '<h3 v-if="label != \\'\\'">{{label || ' + fancyName('id') + '}} <i v-show="description && !hide_description">({{description}})</i></h3>'
74
+ },
75
+ h4: {
76
+ props: ['label', 'description', 'hide_description'],
77
+ template: '<h4 v-if="label != \\'\\'">{{label || ' + fancyName('id') + '}} <i v-show="description && !hide_description">({{description}})</i></h4>'
53
78
  },
54
79
  text: {
55
- props: ['label', 'placeholder', 'disabled', 'readonly', 'value', 'description'],
56
- template: '<div><mip-label :id="id" :label="label" :description="description"></mip-label><input type="text" :name="id" :placeholder="placeholder" v-bind:value="value" v-on:input="$emit(\\'update:value\\', $event.target.value);" :disabled="disabled == \\'true\\'" :readonly="readonly == \\'true\\'"></div>'
80
+ props: ['label', 'placeholder', 'disabled', 'readonly', 'value', 'description', 'shrink'],
81
+ template: '<div><mip-label :id="id" :label="label" :description="description" :hide_description="shrink"></mip-label> <a href="#" v-on:click.prevent.stop="shrink=false" v-show="shrink && !value">[^]</a><input type="text" :name="id" v-if="value || !shrink" :placeholder="placeholder" v-bind:value="value" v-on:input="$emit(\\'update:value\\', $event.target.value);" :disabled="disabled == \\'true\\'" :readonly="readonly == \\'true\\'"></div>'
82
+ },
83
+ hide: {
84
+ props: ['label', 'description'],
85
+ template: '<mip-label :id="id" :label="label" :description="description" v-if="false"></mip-label>'
57
86
  },
58
87
  integer: {
59
- props: ['label', 'placeholder', 'disabled', 'readonly', 'value', 'description'],
60
- template: '<div><mip-label :id="id" :label="label" :description="description"></mip-label><input type="text" :name="id" :placeholder="placeholder" v-bind:value="value" v-on:input="$emit(\\'update:value\\', $event.target.value);" :disabled="disabled == \\'true\\'" :readonly="readonly == \\'true\\'"></div>'
88
+ props: ['label', 'placeholder', 'disabled', 'readonly', 'value', 'description', 'shrink'],
89
+ template: '<div><mip-label :id="id" :label="label" :description="description" :hide_description="shrink"></mip-label> <a href="#" v-on:click.prevent.stop="shrink=false" v-show="shrink && !value">[^]</a><input type="text" :name="id" v-if="value || !shrink" :placeholder="placeholder" v-bind:value="value" v-on:input="$emit(\\'update:value\\', $event.target.value);" :disabled="disabled == \\'true\\'" :readonly="readonly == \\'true\\'"></div>'
61
90
  },
62
91
  email: {
63
- props: ['label', 'placeholder', 'disabled', 'readonly', 'value', 'description'],
64
- template: '<div><mip-label :id="id" :label="label" :description="description"></mip-label><input type="email" :name="id" :placeholder="placeholder" v-bind:value="value" v-on:input="$emit(\\'update:value\\', $event.target.value)" :disabled="disabled == \\'true\\'" :readonly="readonly == \\'true\\'"></div>'
92
+ props: ['label', 'placeholder', 'disabled', 'readonly', 'value', 'description', 'shrink'],
93
+ template: '<div><mip-label :id="id" :label="label" :description="description" :hide_description="shrink"></mip-label> <a href="#" v-on:click.prevent.stop="shrink=false" v-show="shrink && !value">[^]</a><input type="email" :name="id" v-if="value || !shrink" :placeholder="placeholder" v-bind:value="value" v-on:input="$emit(\\'update:value\\', $event.target.value)" :disabled="disabled == \\'true\\'" :readonly="readonly == \\'true\\'"></div>'
65
94
  },
66
95
  textarea: {
67
- props: ['label', 'placeholder', 'disabled', 'readonly', 'value', 'description'],
68
- template: '<div><mip-label :id="id" :label="label" :description="description"></mip-label><textarea :name="id" :placeholder="placeholder" v-bind:value="value" v-on:input="$emit(\\'update:value\\', $event.target.value)" :disabled="disabled == \\'true\\'" :readonly="readonly == \\'true\\'"></textarea></div>'
96
+ props: ['label', 'placeholder', 'disabled', 'readonly', 'value', 'description', 'shrink'],
97
+ template: '<div><mip-label :id="id" :label="label" :description="description" :hide_description="shrink"></mip-label> <a href="#" v-on:click.prevent.stop="shrink=false" v-show="shrink && !value">[^]</a><textarea :name="id" v-if="value || !shrink" :placeholder="placeholder" v-bind:value="value" v-on:input="$emit(\\'update:value\\', $event.target.value)" :disabled="disabled == \\'true\\'" :readonly="readonly == \\'true\\'"></textarea></div>'
69
98
  },
70
99
  json: {
71
- props: ['label', 'placeholder', 'disabled', 'readonly', 'value', 'description'],
72
- template: '<div><mip-label :id="id" :label="label" :description="description"></mip-label><pre><code>{{value}}</code></pre><textarea :name="id" :placeholder="placeholder" v-bind:value="value" v-on:input="$emit(\\'update:value\\', $event.target.value)" :disabled="disabled == \\'true\\'" :readonly="readonly == \\'true\\'"></textarea></div>'
100
+ props: ['label', 'placeholder', 'disabled', 'readonly', 'value', 'description', 'shrink'],
101
+ template: '<div><mip-label :id="id" :label="label" :description="description" :hide_description="shrink"></mip-label> <a href="#" v-on:click.prevent.stop="shrink=false" v-show="shrink && !value">[^]</a><textarea :name="id" v-if="value || !shrink" :placeholder="placeholder" v-bind:value="value" v-on:input="$emit(\\'update:value\\', $event.target.value)" :disabled="disabled == \\'true\\'" :readonly="readonly == \\'true\\'"></textarea></div>'
73
102
  },
74
103
  jsonview: {
75
104
  data: function() {
@@ -80,19 +109,23 @@ module Mushy
80
109
  };
81
110
  },
82
111
  props: ['label', 'placeholder', 'disabled', 'readonly', 'value', 'description', 'view'],
83
- template: '<div><mip-label :id="id" :label="label" :description="description"></mip-label> <a href="#" v-on:click.prevent.stop="view=toggle(view)">{{(view == \\'beautiful\\' ? \\'>\\' : \\'^\\')}}</a><a href="#" v-on:click.prevent.stop="copy(view, value)">copy</a><pre><code>{{show(view, value)}}</code></pre></div>'
112
+ template: '<div><mip-h4 :id="id" :label="label" :description="description"></mip-h4> <pre><code>{{show(view, value)}}</code></pre><button :disabled="view==\\'beautiful\\'" v-on:click.prevent.stop="view=toggle(view)">{{(view == \\'beautiful\\' ? \\'View Smaller\\' : \\'View Pretty\\')}}</button><button :disabled="view!=\\'beautiful\\'" v-on:click.prevent.stop="view=toggle(view)">View Smaller</button><button v-on:click.prevent.stop="copy(view, value)">Copy</button></div>'
84
113
  },
85
114
  radio: {
86
- props: ['label', 'value', 'options', 'description'],
87
- template: '<div><mip-label :id="id" :label="label" :description="description"></mip-label><div v-for="option in options"><input type="radio" :name="id" v-bind:value="option" v-on:input="$emit(\\'update:value\\', $event.target.value)" :checked="value == option"> <label for="option">{{option}}</label></div></div>'
115
+ props: ['label', 'value', 'options', 'description', 'shrink'],
116
+ template: '<div><mip-label :id="id" :label="label" :description="description" :hide_description="shrink"></mip-label> <a href="#" v-on:click.prevent.stop="shrink=false" v-show="shrink && !value">[^]</a><div v-for="option in options"><input type="radio" :name="id" v-bind:value="option" v-if="value || !shrink" v-on:input="$emit(\\'update:value\\', $event.target.value)" :checked="value == option"> <label for="option">{{option}}</label></div></div>'
88
117
  },
89
118
  select: {
90
- props: ['label', 'value', 'options', 'description'],
91
- template: '<div><mip-label :id="id" :label="label" :description="description"></mip-label><select :name="id" v-on:input="$emit(\\'update:value\\', $event.target.value)"><option v-for="option in options" v-bind:value="option" :selected="value == option">{{option}}</option></select></div>'
119
+ props: ['label', 'value', 'options', 'description', 'shrink'],
120
+ template: '<div><mip-label :id="id" :label="label" :description="description" :hide_description="shrink"></mip-label> <a href="#" v-on:click.prevent.stop="shrink=false" v-show="shrink && !value">[^]</a><select :name="id" v-if="value || !shrink" v-on:input="$emit(\\'update:value\\', $event.target.value)"><option v-for="option in options" v-bind:value="option" :selected="value == option">{{option}}</option></select></div>'
121
+ },
122
+ selectrecord: {
123
+ props: ['label', 'value', 'options', 'description', 'shrink'],
124
+ template: '<div><mip-label :id="id" :label="label" :description="description" :hide_description="shrink"></mip-label> <a href="#" v-on:click.prevent.stop="shrink=false" v-show="shrink && !value">[^]</a><select :name="id" v-if="value || !shrink" v-on:input="$emit(\\'update:value\\', $event.target.value)"><option v-for="option in options" v-bind:value="option.id" :selected="value == option.id">{{option.name}}</option></select></div>'
92
125
  },
93
126
  boolean: {
94
- props: ['label', 'value', 'options', 'description'],
95
- template: '<div><mip-label :id="id" :label="label" :description="description"></mip-label><select :name="id" v-on:input="$emit(\\'update:value\\', $event.target.value)"><option v-for="option in [true, false]" v-bind:value="option" :selected="value == option">{{option}}</option></select></div>'
127
+ props: ['label', 'value', 'options', 'description', 'shrink'],
128
+ template: '<div><mip-label :id="id" :label="label" :description="description" :hide_description="shrink"></mip-label> <a href="#" v-on:click.prevent.stop="shrink=false" v-show="shrink && !value">[^]</a><select :name="id" v-if="(value != undefined && value != null && value != \\'\\') || !shrink" v-on:input="$emit(\\'update:value\\', $event.target.value)"><option v-for="option in [true, false]" v-bind:value="option" :selected="value == option">{{option}}</option></select></div>'
96
129
  },
97
130
  table: {
98
131
  props: ['value', 'description'],
@@ -113,12 +146,13 @@ module Mushy
113
146
  }
114
147
  };
115
148
  },
116
- props: ['value', 'editors', 'label', 'description'],
117
- template: '<div><mip-label :id="id" :label="label" :description="description"></mip-label><table><tr><th v-for="(d, i) in value[0]">{{' + fancyName('i') + '}}</th></tr><tr v-for="(v, z) in value"><td v-for="(d, i) in v">{{d}}</td><td><a href="#" v-on:click.prevent.stop="removeRecord(v, value, z)">[x]</a></td></tr><tr><td v-for="editor in editors"><mip-thing :data="editor.field" :id="editor.id"></mip-thing></td><td><a href="#" v-on:click.prevent.stop="addRecord(editors, value)">[Add]</a></td></tr></table></div>'
149
+ props: ['value', 'editors', 'label', 'description', 'shrink'],
150
+ template: '<div><mip-label :id="id" :label="label" :description="description" :hide_description="shrink"></mip-label> <a href="#" v-on:click.prevent.stop="shrink=false" v-show="shrink && value.length == 0">[^]</a><table v-if="value.length > 0 || !shrink"><tr><th v-for="(d, i) in value[0]">{{' + fancyName('i') + '}}</th></tr><tr v-for="(v, z) in value"><td v-for="(d, i) in v">{{d}}</td><td><a href="#" v-on:click.prevent.stop="removeRecord(v, value, z)">[x]</a></td></tr><tr><td v-for="editor in editors"><mip-thing :data="editor.field" :id="editor.id"></mip-thing></td><td><a href="#" v-on:click.prevent.stop="addRecord(editors, value)">[Add]</a></td></tr></table></div>'
118
151
  },
119
152
  keyvalue: {
120
153
  data: function() {
121
154
  return {
155
+ actionText: function(value, others) { found = false; for(var i in others){ if (i == value) found = true; } return found ? 'Replace' : 'Add'; },
122
156
  removeRecord: function(data, key) { Vue.delete(data, key) },
123
157
  addRecord: function(editors, data) {
124
158
  Vue.set(data, editors[0].field.value, editors[1].field.value)
@@ -127,12 +161,12 @@ module Mushy
127
161
  }
128
162
  };
129
163
  },
130
- props: ['value', 'label', 'editors', 'description'],
131
- template: '<div><mip-label :id="id" :label="label" :description="description"></mip-label><table><tr v-for="(v, k) in value"><td>{{k}}</td><td>{{v}}</td><td><a href="#" v-on:click.prevent.stop="removeRecord(value, k)">[x]</a></td></tr><tr><td v-for="editor in editors"><mip-thing :data="editor.field" :id="editor.id"></mip-thing></td><td><a href="#" v-on:click.prevent.stop="addRecord(editors, value)" v-show="editors[0].field.value">[Add]</a></td></tr></table></div>'
164
+ props: ['value', 'label', 'editors', 'description', 'shrink'],
165
+ template: '<div><mip-label :id="id" :label="label" :description="description" :hide_description="shrink"></mip-label> <a href="#" v-on:click.prevent.stop="shrink=false" v-show="shrink">[^]</a><table v-if="JSON.stringify(value) != \\'{}\\' || !shrink"><tr v-for="(v, k) in value"><td>{{k}}</td><td>{{v}}</td><td><button v-on:click.prevent.stop="removeRecord(value, k)">Remove {{k}}</button></td></tr><tr><td v-for="editor in editors"><mip-thing :data="editor.field" :id="editor.id"></mip-thing></td><td><button v-on:click.prevent.stop="addRecord(editors, value)" v-show="editors[0].field.value">{{actionText(editors[0].field.value, value)}} {{editors[0].field.value}}</button></td></tr></table></div>'
132
166
  },
133
167
  button: {
134
- props: ['click', 'description'],
135
- template: '<button v-on:click.prevent.stop="click(pull(this))">{{id}}</button>'
168
+ props: ['click', 'description', 'name'],
169
+ template: '<button v-on:click.prevent.stop="click(pull(this), thisComponent())">{{name || id}}</button>'
136
170
  }
137
171
  };
138
172
 
@@ -152,6 +186,7 @@ module Mushy
152
186
  return {
153
187
  console: console,
154
188
  pull: function(x) { return thingToData(foundIt.data); },
189
+ thisComponent: function() { return foundIt.data; },
155
190
  }
156
191
  },
157
192
  props: props,
@@ -184,32 +219,6 @@ module Mushy
184
219
  template: '<div><mip-thing v-for="(d, id) in data" :data="d" :id="id"></mip-thing></div>',
185
220
  });
186
221
 
187
- var sample = {
188
- email: { type: 'email', value: 'darren@cauthon.com' },
189
- first_name: { type: 'text', value: 'Darren' },
190
- description: { type: 'textarea', value: 'more data' },
191
- size: { type: 'select', value: 'medium', options: ['small', 'medium', 'large']},
192
- heynow: { type: 'keyvalue',
193
- value: {
194
- first_name: 'John',
195
- last_name: 'Doe',
196
- },
197
- editors: [
198
- { id: 'new_key', target: 'key', field: { type: 'text', value: '', default: '' } },
199
- { id: 'new_value', target: 'value', field: { type: 'text', value: '', default: '' } }
200
- ] },
201
- past: { type: 'editgrid',
202
- value: [
203
- { name: 'Godzilla', quantity: 1 },
204
- { name: 'Mothra', quantity: 2 },
205
- ],
206
- editors: [
207
- { id: 'new_name', target: 'name', field: { type: 'text', value: '', default: '' } },
208
- { id: 'new_quantity', target: 'quantity', field: { type: 'select', value: '1', options: [1, 2, 3], default: 1 } }
209
- ] },
210
- super_action: { type: 'button', click: function(x) { console.log(x) } },
211
- };
212
-
213
222
  var app = null;
214
223
 
215
224
  axios.get('/fluxs')
@@ -232,31 +241,25 @@ module Mushy
232
241
  options.push(fluxTypes[type]);
233
242
 
234
243
  var setup = {
235
- event: { type: 'json', value: '{}' },
236
- id: { type: 'text', value: '' },
244
+ showFlux: false,
245
+ id: { type: 'hide', value: '' },
237
246
  name: { type: 'text', value: '' },
238
247
  flux: { type: 'select', value: fluxdata.fluxs[0].name, options: options},
248
+ parent: { type: 'selectrecord', label: 'Receive Events From', value: '', options: flowdata.fluxs },
239
249
  };
240
250
 
241
251
  for (var key in configs)
242
252
  {
243
- configs[key].go = { type: 'button', click: function(c) {
244
- app.results = [];
245
- Vue.set(app.results, 'loading', true);
246
- axios.post('/run', { config: c, setup: thingToData(app.setup) })
247
- .then(function(r){
248
- Vue.set(app.results, 'loading', false);
249
- for (var key in r.data.result)
250
- app.results.push({darren: { type:'jsonview', value: r.data.result[key], view: 'thin' }});
251
- });
252
- } };
253
-
254
- configs[key].save = { type: 'button', click: function(config) {
253
+ configs[key].save = { type: 'button', name: 'Save This Flux', click: function(config, hey) {
254
+ var nameOfTheSaveButton = hey.save.name;
255
+ Vue.set(hey.save, 'name', 'Saving');
256
+ delete config.test_event;
255
257
  var setup = thingToData(app.setup);
256
258
  var flux = {
257
259
  id: setup.id,
258
260
  name: setup.name,
259
261
  flux: setup.flux,
262
+ parent: setup.parent,
260
263
  config: config,
261
264
  };
262
265
  var index = -1;
@@ -268,16 +271,53 @@ module Mushy
268
271
  else
269
272
  app.flow.fluxs[index] = flux;
270
273
 
271
- app.setup.id.value = '';
274
+ setTimeout(function(){
275
+ Vue.set(hey.save, 'name', nameOfTheSaveButton);
276
+ app.setup.id.value = '';
277
+
278
+ Vue.set(app.setup, 'showFlux', false);
279
+ }, 500);
272
280
  }
273
281
  };
282
+
283
+ configs[key].test_event = { type: 'json', value: '{}', default: '{}' };
284
+
285
+ configs[key].run_test = { type: 'button', name: 'Test Run This Flux', click: function(c, hey) {
286
+ var previousName = hey.run_test.name;
287
+ Vue.set(hey.run_test, 'name', 'Loading');
288
+ app.results = [];
289
+ Vue.set(app.results, 'errorMessage', '');
290
+ var the_setup = thingToData(app.setup);
291
+ the_setup.event = c.test_event;
292
+ axios.post('/run', { config: c, setup: the_setup })
293
+ .then(function(r){
294
+ var index = 1;
295
+ for (var key in r.data.result)
296
+ {
297
+ var result = {};
298
+ result['event_' + index] = { type: 'jsonview', label: 'Event ' + index + ' of ' + r.data.result.length, value: r.data.result[key], view: 'thin' };
299
+ app.results.push(result);
300
+ index += 1;
301
+ }
302
+ }).catch(function(r){
303
+ console.log(r);
304
+ Vue.set(app.results, 'errorMessage', 'This app failed while trying to execute your flux.');
305
+ }).then(function(){
306
+ Vue.set(hey.run_test, 'name', previousName);
307
+ });
308
+ } };
274
309
  }
275
310
 
276
- var loadThisFlux = function(flux, setup, config)
311
+ var loadThisFlux = function(args)
277
312
  {
313
+ var flux = args.flux;
314
+ var setup = args.setup;
315
+ var config = args.config;
316
+
278
317
  Vue.set(setup.id, 'value', flux.id);
279
318
  Vue.set(setup.name, 'value', flux.name);
280
319
  Vue.set(setup.flux, 'value', flux.flux);
320
+ Vue.set(setup.parent, 'value', flux.parent);
281
321
 
282
322
  var applicable_config = configs[flux.flux];
283
323
  for(var key in applicable_config)
@@ -285,35 +325,60 @@ module Mushy
285
325
  Vue.set(applicable_config[key], 'value', flux.config[key]);
286
326
  else
287
327
  Vue.set(applicable_config[key], 'value', applicable_config[key].default);
328
+
329
+ if (applicable_config)
330
+ Vue.set(applicable_config.test_event, 'value', '{}');
331
+
332
+ options = flowdata.fluxs.filter(function(x){ return x.id != flux.id });
333
+ options.unshift( { id: '', name: '' } );
334
+ setup.parent.options = options;
335
+
336
+ Vue.set(setup, 'showFlux', true);
337
+ app.results = [];
288
338
  };
289
339
 
340
+ function uuidv4() {
341
+ return ([1e7]+-1e3+-4e3+-8e3+-1e11).replace(/[018]/g, c =>
342
+ (c ^ crypto.getRandomValues(new Uint8Array(1))[0] & 15 >> c / 4).toString(16)
343
+ );
344
+ }
345
+
290
346
  app = new Vue({
291
347
  el: '#app',
292
348
  data: {
293
349
  flow: flowdata,
294
350
  startNew: function(x) {
295
351
  flux = {
296
- id: 'hey',
297
- name: 'you',
352
+ id: uuidv4(),
353
+ name: '',
298
354
  config: {}
299
355
  };
300
- loadThisFlux(flux, x.setup, x.configs);
356
+ loadThisFlux({ flux: flux, setup: x.setup, configs: x.configs });
301
357
  },
302
- edit: function(x) {
358
+ editFlux: function(x) {
303
359
  var flux = x.flux;
304
360
 
305
- loadThisFlux(x.flux, x.setup, x.configs);
361
+ loadThisFlux({ flux: x.flux, setup: x.setup, configs: x.configs });
306
362
  },
307
- saveFlow: function(flow)
363
+ deleteFlux: function(x) {
364
+ var set = x.flow.fluxs.filter( function(v){ return v.id != x.flux.id } );
365
+ Vue.set(x.flow, 'fluxs', set);
366
+ },
367
+ saveFlow: function(input)
308
368
  {
309
- console.log(flow);
369
+ var setup = input.setup;
370
+ var flow = input.flow;
310
371
  axios.post('/save', flow)
311
372
  .then(function(result){
312
- console.log(result);
373
+ Vue.set(setup, 'showFlux', false);
313
374
  });
314
375
  },
315
376
  configs: configs,
316
377
  setup: setup,
378
+ flux_name_for: function(id, fluxes) {
379
+ var flux = fluxes.filter(function(x){ return x.id == id })[0];
380
+ return flux != undefined ? flux.name : '';
381
+ },
317
382
  results: [],
318
383
  }
319
384
  });
data/lib/mushy/flow.rb CHANGED
@@ -26,9 +26,11 @@ module Mushy
26
26
 
27
27
  def self.parse data
28
28
  data = JSON.parse data
29
- flow = new
30
29
 
31
30
  data_fluxs = data['fluxs'] || []
31
+ data_fluxs.select { |x| x['parent'] }.map { |r| r["parent_fluxs"] = [r["parent"]] }
32
+
33
+ flow = new
32
34
 
33
35
  flow.fluxs = data_fluxs.map { |s| build_flux s }
34
36
 
data/lib/mushy/flux.rb CHANGED
@@ -40,17 +40,18 @@ module Mushy
40
40
 
41
41
  event = incoming_event
42
42
 
43
- mashed_config = masher.mash config, event
44
-
45
- incoming_split = mashed_config[:incoming_split]
43
+ incoming_split = masher.mash(config, event)[:incoming_split]
44
+ config_considering_an_imcoming_split = config
45
+ .reject { |x, _| incoming_split && x.to_s == 'join' }
46
+ .reduce({}) { |t, i| t[i[0]] = i[1]; t }
46
47
 
47
48
  events = incoming_split ? incoming_event[incoming_split] : [event]
48
49
 
49
- results = events.map { |e| execute_single_event e, config }
50
+ results = events.map { |e| execute_single_event e, config_considering_an_imcoming_split }
50
51
 
51
52
  return results.first unless incoming_split
52
53
 
53
- results = join_these_results(results, event, config[:join]) if config[:join]
54
+ results = join_these_results([results].flatten, event, config[:join]) if config[:join]
54
55
 
55
56
  results.flatten
56
57
  end
@@ -67,7 +68,7 @@ module Mushy
67
68
  returned_one_result = results.is_a?(Hash)
68
69
 
69
70
  results = standardize_these results
70
- results = shape_these results, event, mashed_config
71
+ results = shape_these results, event, config
71
72
 
72
73
  return results.first if the_original_join
73
74
 
@@ -17,16 +17,19 @@ module Mushy
17
17
  headless: {
18
18
  description: 'Run this browser headless.',
19
19
  type: 'boolean',
20
+ shrink: true,
20
21
  value: 'true',
21
22
  },
22
23
  execute: {
23
24
  description: 'Javascript to run after the page is loaded.',
24
25
  type: 'textarea',
26
+ shrink: true,
25
27
  value: '',
26
28
  },
27
29
  cookies: {
28
30
  description: 'Cookies for the web request. These can be received from a previous browser event with {{cookies}}, or can be typed manually.',
29
31
  type: 'editgrid',
32
+ shrink: true,
30
33
  value: [],
31
34
  editors: [
32
35
  { id: 'name', target: 'name', field: { type: 'text', value: '', default: '' } },
@@ -40,23 +43,31 @@ module Mushy
40
43
  { id: 'sameSite', target: 'sameSite', field: { type: 'text', value: 'None', default: 'None' } },
41
44
  { id: 'priority', target: 'priority', field: { type: 'text', value: 'Medium', default: 'Medium' } },
42
45
  ],
43
- #{"name":"1P_JAR","value":"2021-01-21-13","domain":".google.com","path":"/","expires":1613828458.870408,"size":19,"httpOnly":false,"secure":true,"session":false,"sameSite":"None","priority":"Medium"
44
46
  },
45
47
  carry_cookies_from: {
46
48
  description: 'Carry the cookies from this path in the event.',
47
49
  type: 'text',
50
+ shrink: true,
48
51
  value: 'cookies',
49
52
  },
50
53
  headers: {
51
54
  description: 'Headers for the web request. These can be received from a previous browser event with {{headers}}, or can be typed manually.',
52
55
  type: 'keyvalue',
56
+ shrink: true,
53
57
  value: {},
54
58
  },
55
59
  carry_headers_from: {
56
60
  description: 'Carry the headers from this path in the event.',
57
61
  type: 'text',
62
+ shrink: true,
58
63
  value: 'headers',
59
64
  },
65
+ wait_before_closing: {
66
+ description: 'Wait this many seconds before closing the browser.',
67
+ type: 'integer',
68
+ shrink: true,
69
+ value: '',
70
+ },
60
71
  },
61
72
  }
62
73
  end
@@ -73,6 +84,8 @@ module Mushy
73
84
 
74
85
  browser.execute(config[:execute]) if config[:execute]
75
86
 
87
+ sleep(config[:wait_before_closing].to_i) if config[:wait_before_closing] && config[:wait_before_closing].to_i > 0
88
+
76
89
  result = {
77
90
  url: browser.url,
78
91
  cookies: browser.cookies.all.map { |k, v| v.instance_variable_get('@attributes') },
@@ -0,0 +1,19 @@
1
+ module Mushy
2
+
3
+ class Format < Flux
4
+
5
+ def self.details
6
+ {
7
+ name: 'Format',
8
+ description: 'Return the event passed to it. This opens the opportunity to further alter results.',
9
+ config: {},
10
+ }
11
+ end
12
+
13
+ def process event, config
14
+ event
15
+ end
16
+
17
+ end
18
+
19
+ end
data/mushy.gemspec CHANGED
@@ -4,7 +4,7 @@ require 'mushy/version'
4
4
 
5
5
  Gem::Specification.new do |s|
6
6
  s.name = 'mushy'
7
- s.version = '0.0.2'
7
+ s.version = '0.1.0'
8
8
  s.date = '2020-11-23'
9
9
  s.summary = 'Process streams of work using common modules.'
10
10
  s.description = 'This tool assists in the creation and processing of workflows.'
@@ -17,9 +17,11 @@ Gem::Specification.new do |s|
17
17
  s.license = 'MIT'
18
18
 
19
19
  s.add_development_dependency 'minitest'
20
+ s.add_runtime_dependency 'sinatra'
21
+ s.add_runtime_dependency 'symbolized'
20
22
  s.add_runtime_dependency 'thor'
21
23
  s.add_runtime_dependency 'liquid'
22
24
  s.add_runtime_dependency 'ferrum'
23
25
  s.add_runtime_dependency 'nokogiri'
24
26
  s.add_runtime_dependency 'faraday'
25
- end
27
+ end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: mushy
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.2
4
+ version: 0.1.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Darren Cauthon
@@ -24,6 +24,34 @@ dependencies:
24
24
  - - ">="
25
25
  - !ruby/object:Gem::Version
26
26
  version: '0'
27
+ - !ruby/object:Gem::Dependency
28
+ name: sinatra
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - ">="
32
+ - !ruby/object:Gem::Version
33
+ version: '0'
34
+ type: :runtime
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ">="
39
+ - !ruby/object:Gem::Version
40
+ version: '0'
41
+ - !ruby/object:Gem::Dependency
42
+ name: symbolized
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - ">="
46
+ - !ruby/object:Gem::Version
47
+ version: '0'
48
+ type: :runtime
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - ">="
53
+ - !ruby/object:Gem::Version
54
+ version: '0'
27
55
  - !ruby/object:Gem::Dependency
28
56
  name: thor
29
57
  requirement: !ruby/object:Gem::Requirement
@@ -116,6 +144,7 @@ files:
116
144
  - lib/mushy/fluxs/build_csv.rb
117
145
  - lib/mushy/fluxs/collection.rb
118
146
  - lib/mushy/fluxs/filter.rb
147
+ - lib/mushy/fluxs/format.rb
119
148
  - lib/mushy/fluxs/get.rb
120
149
  - lib/mushy/fluxs/ls.rb
121
150
  - lib/mushy/fluxs/parse_html.rb