neptune 0.2.2 → 0.2.3

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.
@@ -170,6 +170,18 @@ cluttering up <a href="Object.html">Object</a> or Kernel’s namespace.</p>
170
170
  <dd class="description">
171
171
 
172
172
 
173
+ <dt id="GET_CPU_INFO">GET_CPU_INFO
174
+
175
+ <dd class="description"><p>The command that we can run to get information about the number and speed
176
+ of CPUs on this machine.</p>
177
+
178
+
179
+ <dt id="NEPTUNE_DATA_DIR">NEPTUNE_DATA_DIR
180
+
181
+ <dd class="description"><p>The location on this machine where we can read and write profiling
182
+ information about jobs.</p>
183
+
184
+
173
185
  <dt id="OPTIMIZE_FOR_CHOICES">OPTIMIZE_FOR_CHOICES
174
186
 
175
187
  <dd class="description">
@@ -208,7 +220,7 @@ cluttering up <a href="Object.html">Object</a> or Kernel’s namespace.</p>
208
220
 
209
221
 
210
222
  <div class="method-source-code" id="average-source">
211
- <pre><span class="ruby-comment"># File lib/exodus.rb, line 268</span>
223
+ <pre><span class="ruby-comment"># File lib/exodus.rb, line 316</span>
212
224
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">average</span>(<span class="ruby-identifier">vals</span>)
213
225
  <span class="ruby-identifier">sum</span> = <span class="ruby-identifier">vals</span>.<span class="ruby-identifier">reduce</span>(<span class="ruby-value">0.0</span>) { <span class="ruby-operator">|</span><span class="ruby-identifier">running_total</span>, <span class="ruby-identifier">val</span><span class="ruby-operator">|</span>
214
226
  <span class="ruby-identifier">running_total</span> <span class="ruby-operator">+</span> <span class="ruby-identifier">val</span>
@@ -246,7 +258,7 @@ href="BadConfigurationException.html">BadConfigurationException</a> if
246
258
 
247
259
 
248
260
  <div class="method-source-code" id="convert_clouds_to_use_to_array-source">
249
- <pre><span class="ruby-comment"># File lib/exodus.rb, line 123</span>
261
+ <pre><span class="ruby-comment"># File lib/exodus.rb, line 138</span>
250
262
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">convert_clouds_to_use_to_array</span>(<span class="ruby-identifier">job</span>)
251
263
  <span class="ruby-identifier">clouds_class</span> = <span class="ruby-identifier">job</span>[<span class="ruby-value">:clouds_to_use</span>].<span class="ruby-identifier">class</span>
252
264
  <span class="ruby-keyword">if</span> <span class="ruby-identifier">clouds_class</span> <span class="ruby-operator">==</span> <span class="ruby-constant">Symbol</span>
@@ -290,7 +302,7 @@ standard format for Neptune jobs.</p>
290
302
 
291
303
 
292
304
  <div class="method-source-code" id="ensure_all_jobs_are_hashes-source">
293
- <pre><span class="ruby-comment"># File lib/exodus.rb, line 95</span>
305
+ <pre><span class="ruby-comment"># File lib/exodus.rb, line 110</span>
294
306
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">ensure_all_jobs_are_hashes</span>(<span class="ruby-identifier">jobs</span>)
295
307
  <span class="ruby-identifier">jobs</span>.<span class="ruby-identifier">each</span> { <span class="ruby-operator">|</span><span class="ruby-identifier">job</span><span class="ruby-operator">|</span>
296
308
  <span class="ruby-keyword">if</span> <span class="ruby-identifier">job</span>.<span class="ruby-identifier">class</span> <span class="ruby-operator">!=</span> <span class="ruby-constant">Hash</span>
@@ -327,7 +339,7 @@ missing params.</p>
327
339
 
328
340
 
329
341
  <div class="method-source-code" id="ensure_all_params_are_present-source">
330
- <pre><span class="ruby-comment"># File lib/exodus.rb, line 107</span>
342
+ <pre><span class="ruby-comment"># File lib/exodus.rb, line 122</span>
331
343
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">ensure_all_params_are_present</span>(<span class="ruby-identifier">job</span>)
332
344
  <span class="ruby-keyword">if</span> <span class="ruby-identifier">job</span>[<span class="ruby-value">:clouds_to_use</span>].<span class="ruby-identifier">nil?</span>
333
345
  <span class="ruby-identifier">raise</span> <span class="ruby-constant">BadConfigurationException</span>.<span class="ruby-identifier">new</span>(<span class="ruby-string">&quot;:clouds_to_use was not specified&quot;</span>)
@@ -364,7 +376,7 @@ missing params.</p>
364
376
 
365
377
 
366
378
  <div class="method-source-code" id="ensure_credentials_are_in_correct_format-source">
367
- <pre><span class="ruby-comment"># File lib/exodus.rb, line 165</span>
379
+ <pre><span class="ruby-comment"># File lib/exodus.rb, line 180</span>
368
380
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">ensure_credentials_are_in_correct_format</span>(<span class="ruby-identifier">job</span>)
369
381
  <span class="ruby-keyword">if</span> <span class="ruby-identifier">job</span>[<span class="ruby-value">:credentials</span>].<span class="ruby-identifier">nil?</span>
370
382
  <span class="ruby-identifier">raise</span> <span class="ruby-constant">BadConfigurationException</span>.<span class="ruby-identifier">new</span>(<span class="ruby-string">&quot;No credentials were specified.&quot;</span>)
@@ -401,7 +413,7 @@ missing params.</p>
401
413
 
402
414
 
403
415
  <div class="method-source-code" id="find_optimal_cloud_for_task-source">
404
- <pre><span class="ruby-comment"># File lib/exodus.rb, line 277</span>
416
+ <pre><span class="ruby-comment"># File lib/exodus.rb, line 325</span>
405
417
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">find_optimal_cloud_for_task</span>(<span class="ruby-identifier">job</span>, <span class="ruby-identifier">profiling_info</span>)
406
418
  <span class="ruby-identifier">raise</span> <span class="ruby-constant">NotImplementedError</span>
407
419
  <span class="ruby-keyword">end</span></pre>
@@ -431,7 +443,7 @@ missing params.</p>
431
443
 
432
444
 
433
445
  <div class="method-source-code" id="generate_babel_tasks-source">
434
- <pre><span class="ruby-comment"># File lib/exodus.rb, line 282</span>
446
+ <pre><span class="ruby-comment"># File lib/exodus.rb, line 330</span>
435
447
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">generate_babel_tasks</span>(<span class="ruby-identifier">job</span>, <span class="ruby-identifier">clouds_to_run_task_on</span>)
436
448
  <span class="ruby-identifier">tasks</span> = []
437
449
 
@@ -480,7 +492,7 @@ missing params.</p>
480
492
 
481
493
 
482
494
  <div class="method-source-code" id="get_clouds_to_run_task_on-source">
483
- <pre><span class="ruby-comment"># File lib/exodus.rb, line 227</span>
495
+ <pre><span class="ruby-comment"># File lib/exodus.rb, line 275</span>
484
496
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">get_clouds_to_run_task_on</span>(<span class="ruby-identifier">job</span>, <span class="ruby-identifier">profiling_info</span>)
485
497
  <span class="ruby-identifier">optimize_for</span> = <span class="ruby-identifier">job</span>[<span class="ruby-value">:optimize_for</span>]
486
498
  <span class="ruby-keyword">if</span> <span class="ruby-identifier">optimize_for</span> <span class="ruby-operator">==</span> <span class="ruby-value">:performance</span> <span class="ruby-keyword">or</span> <span class="ruby-identifier">optimize_for</span> <span class="ruby-operator">==</span> <span class="ruby-value">:cost</span>
@@ -515,9 +527,9 @@ missing params.</p>
515
527
 
516
528
 
517
529
  <div class="method-source-code" id="get_key_from_job_data-source">
518
- <pre><span class="ruby-comment"># File lib/exodus.rb, line 222</span>
530
+ <pre><span class="ruby-comment"># File lib/exodus.rb, line 270</span>
519
531
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">get_key_from_job_data</span>(<span class="ruby-identifier">job</span>)
520
- <span class="ruby-keyword">return</span> <span class="ruby-identifier">job</span>[<span class="ruby-value">:code</span>]
532
+ <span class="ruby-keyword">return</span> <span class="ruby-identifier">job</span>[<span class="ruby-value">:code</span>].<span class="ruby-identifier">gsub</span>(<span class="ruby-regexp">%r[\/\.]/</span>, <span class="ruby-string">&quot;&quot;</span>)
521
533
  <span class="ruby-keyword">end</span></pre>
522
534
  </div><!-- get_key_from_job_data-source -->
523
535
 
@@ -545,7 +557,7 @@ missing params.</p>
545
557
 
546
558
 
547
559
  <div class="method-source-code" id="get_minimum_val_in_data-source">
548
- <pre><span class="ruby-comment"># File lib/exodus.rb, line 237</span>
560
+ <pre><span class="ruby-comment"># File lib/exodus.rb, line 285</span>
549
561
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">get_minimum_val_in_data</span>(<span class="ruby-identifier">job</span>, <span class="ruby-identifier">profiling_info</span>)
550
562
  <span class="ruby-identifier">min_cloud</span> = <span class="ruby-keyword">nil</span>
551
563
  <span class="ruby-identifier">min_val</span> = <span class="ruby-value">1_000_000</span> <span class="ruby-comment"># infinity</span>
@@ -600,11 +612,44 @@ missing params.</p>
600
612
 
601
613
 
602
614
  <div class="method-source-code" id="get_profiling_info-source">
603
- <pre><span class="ruby-comment"># File lib/exodus.rb, line 214</span>
615
+ <pre><span class="ruby-comment"># File lib/exodus.rb, line 229</span>
604
616
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">get_profiling_info</span>(<span class="ruby-identifier">job</span>)
605
617
  <span class="ruby-identifier">key</span> = <span class="ruby-keyword">self</span>.<span class="ruby-identifier">get_key_from_job_data</span>(<span class="ruby-identifier">job</span>)
606
- <span class="ruby-identifier">neptune_manager</span> = <span class="ruby-constant">BabelHelper</span>.<span class="ruby-identifier">get_neptune_manager_client</span>(<span class="ruby-identifier">job</span>)
607
- <span class="ruby-keyword">return</span> <span class="ruby-identifier">neptune_manager</span>.<span class="ruby-identifier">get_profiling_info</span>(<span class="ruby-identifier">key</span>)
618
+
619
+ <span class="ruby-keyword">if</span> <span class="ruby-operator">!</span><span class="ruby-constant">File</span>.<span class="ruby-identifier">exists?</span>(<span class="ruby-constant">NEPTUNE_DATA_DIR</span>)
620
+ <span class="ruby-constant">FileUtils</span>.<span class="ruby-identifier">mkdir</span>(<span class="ruby-constant">NEPTUNE_DATA_DIR</span>)
621
+ <span class="ruby-keyword">end</span>
622
+
623
+ <span class="ruby-identifier">profiling_info_file</span> = <span class="ruby-node">&quot;#{NEPTUNE_DATA_DIR}/#{key}.json&quot;</span>
624
+ <span class="ruby-keyword">if</span> <span class="ruby-constant">File</span>.<span class="ruby-identifier">exists?</span>(<span class="ruby-identifier">profiling_info_file</span>)
625
+ <span class="ruby-identifier">contents</span> = <span class="ruby-constant">File</span>.<span class="ruby-identifier">open</span>(<span class="ruby-identifier">profiling_info_file</span>) { <span class="ruby-operator">|</span><span class="ruby-identifier">f</span><span class="ruby-operator">|</span> <span class="ruby-identifier">f</span>.<span class="ruby-identifier">read</span>() }
626
+ <span class="ruby-keyword">return</span> <span class="ruby-constant">JSON</span>.<span class="ruby-identifier">load</span>(<span class="ruby-identifier">contents</span>)
627
+ <span class="ruby-keyword">end</span>
628
+
629
+ <span class="ruby-comment"># If we don't have any profiling info on this job, run it locally and</span>
630
+ <span class="ruby-comment"># gather the data ourselves.</span>
631
+
632
+ <span class="ruby-identifier">start_time</span> = <span class="ruby-constant">Time</span>.<span class="ruby-identifier">now</span>
633
+ <span class="ruby-comment"># TODO(cgb): exec the user's code</span>
634
+ <span class="ruby-identifier">end_time</span> = <span class="ruby-constant">Time</span>.<span class="ruby-identifier">now</span>
635
+
636
+ <span class="ruby-comment"># To find out how fast this computer is, just check the file that has</span>
637
+ <span class="ruby-comment"># this info on it and take the first processor. This should be fine</span>
638
+ <span class="ruby-comment"># since we assume the user's code is not-multi-core aware and that</span>
639
+ <span class="ruby-comment"># all processors on this box are the same speed.</span>
640
+ <span class="ruby-identifier">cpu_speed</span> = <span class="ruby-constant">Float</span>(<span class="ruby-constant">CommonFunctions</span>.<span class="ruby-identifier">shell</span>(<span class="ruby-constant">GET_CPU_INFO</span>).
641
+ <span class="ruby-identifier">scan</span>(<span class="ruby-regexp">%rcpu MHz\s*:\s*(\d+\.\d+)/</span>).<span class="ruby-identifier">flatten</span>[<span class="ruby-value">0</span>])
642
+
643
+ <span class="ruby-identifier">json_info</span> = {
644
+ <span class="ruby-string">&quot;total_execution_time&quot;</span> =<span class="ruby-operator">&gt;</span> <span class="ruby-identifier">end_time</span> <span class="ruby-operator">-</span> <span class="ruby-identifier">start_time</span>,
645
+ <span class="ruby-string">&quot;cpu_speed&quot;</span> =<span class="ruby-operator">&gt;</span> <span class="ruby-identifier">cpu_speed</span>
646
+ }
647
+
648
+ <span class="ruby-constant">File</span>.<span class="ruby-identifier">open</span>(<span class="ruby-identifier">profiling_info_file</span>, <span class="ruby-string">&quot;w+&quot;</span>) { <span class="ruby-operator">|</span><span class="ruby-identifier">file</span><span class="ruby-operator">|</span>
649
+ <span class="ruby-identifier">file</span>.<span class="ruby-identifier">write</span>(<span class="ruby-constant">JSON</span>.<span class="ruby-identifier">dump</span>(<span class="ruby-identifier">json_info</span>))
650
+ }
651
+
652
+ <span class="ruby-keyword">return</span> <span class="ruby-identifier">json_info</span>
608
653
  <span class="ruby-keyword">end</span></pre>
609
654
  </div><!-- get_profiling_info-source -->
610
655
 
@@ -634,7 +679,7 @@ the job does not specify it.</p>
634
679
 
635
680
 
636
681
  <div class="method-source-code" id="propogate_credentials_from_environment-source">
637
- <pre><span class="ruby-comment"># File lib/exodus.rb, line 180</span>
682
+ <pre><span class="ruby-comment"># File lib/exodus.rb, line 195</span>
638
683
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">propogate_credentials_from_environment</span>(<span class="ruby-identifier">job</span>)
639
684
  <span class="ruby-constant">CLOUD_CREDENTIALS</span>.<span class="ruby-identifier">each</span> { <span class="ruby-operator">|</span><span class="ruby-identifier">cloud_name</span>, <span class="ruby-identifier">credential_list</span><span class="ruby-operator">|</span>
640
685
  <span class="ruby-identifier">credential_list</span>.<span class="ruby-identifier">each</span> { <span class="ruby-operator">|</span><span class="ruby-identifier">cred</span><span class="ruby-operator">|</span>
@@ -670,7 +715,7 @@ the job does not specify it.</p>
670
715
 
671
716
 
672
717
  <div class="method-source-code" id="run_job-source">
673
- <pre><span class="ruby-comment"># File lib/exodus.rb, line 306</span>
718
+ <pre><span class="ruby-comment"># File lib/exodus.rb, line 354</span>
674
719
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">run_job</span>(<span class="ruby-identifier">tasks_to_run</span>)
675
720
  <span class="ruby-keyword">return</span> <span class="ruby-identifier">babel</span>(<span class="ruby-identifier">tasks_to_run</span>)
676
721
  <span class="ruby-keyword">end</span></pre>
@@ -702,7 +747,7 @@ credentials needed to use that cloud.</p>
702
747
 
703
748
 
704
749
  <div class="method-source-code" id="validate_clouds_to_use-source">
705
- <pre><span class="ruby-comment"># File lib/exodus.rb, line 144</span>
750
+ <pre><span class="ruby-comment"># File lib/exodus.rb, line 159</span>
706
751
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">validate_clouds_to_use</span>(<span class="ruby-identifier">job</span>)
707
752
  <span class="ruby-keyword">self</span>.<span class="ruby-identifier">ensure_credentials_are_in_correct_format</span>(<span class="ruby-identifier">job</span>)
708
753
  <span class="ruby-keyword">self</span>.<span class="ruby-identifier">propogate_credentials_from_environment</span>(<span class="ruby-identifier">job</span>)
@@ -748,7 +793,7 @@ credentials needed to use that cloud.</p>
748
793
 
749
794
 
750
795
  <div class="method-source-code" id="validate_files_argv_executable-source">
751
- <pre><span class="ruby-comment"># File lib/exodus.rb, line 205</span>
796
+ <pre><span class="ruby-comment"># File lib/exodus.rb, line 220</span>
752
797
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">validate_files_argv_executable</span>(<span class="ruby-identifier">job</span>)
753
798
  [<span class="ruby-value">:code</span>, <span class="ruby-value">:argv</span>, <span class="ruby-value">:executable</span>].<span class="ruby-identifier">each</span> { <span class="ruby-operator">|</span><span class="ruby-identifier">param</span><span class="ruby-operator">|</span>
754
799
  <span class="ruby-keyword">if</span> <span class="ruby-identifier">job</span>[<span class="ruby-identifier">param</span>].<span class="ruby-identifier">nil?</span>
@@ -782,7 +827,7 @@ credentials needed to use that cloud.</p>
782
827
 
783
828
 
784
829
  <div class="method-source-code" id="validate_optimize_for_param-source">
785
- <pre><span class="ruby-comment"># File lib/exodus.rb, line 191</span>
830
+ <pre><span class="ruby-comment"># File lib/exodus.rb, line 206</span>
786
831
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">validate_optimize_for_param</span>(<span class="ruby-identifier">job</span>)
787
832
  <span class="ruby-keyword">if</span> <span class="ruby-identifier">job</span>[<span class="ruby-value">:optimize_for</span>].<span class="ruby-identifier">nil?</span>
788
833
  <span class="ruby-identifier">raise</span> <span class="ruby-constant">BadConfigurationException</span>.<span class="ruby-identifier">new</span>(<span class="ruby-string">&quot;:optimize_for needs to be &quot;</span> <span class="ruby-operator">+</span>
@@ -186,7 +186,7 @@ indicates whether or not the compilation was successful.</p>
186
186
 
187
187
 
188
188
  <div class="method-source-code" id="compile_code-source">
189
- <pre><span class="ruby-comment"># File lib/neptune.rb, line 458</span>
189
+ <pre><span class="ruby-comment"># File lib/neptune.rb, line 459</span>
190
190
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">compile_code</span>(<span class="ruby-identifier">job_data</span>, <span class="ruby-identifier">ssh_args</span>, <span class="ruby-identifier">shadow_ip</span>)
191
191
  <span class="ruby-identifier">compiled_location</span> = <span class="ruby-identifier">controller</span>.<span class="ruby-identifier">compile_code</span>(<span class="ruby-identifier">job_data</span>)
192
192
  <span class="ruby-identifier">copy_to</span> = <span class="ruby-identifier">job_data</span>[<span class="ruby-string">&quot;@copy_to&quot;</span>]
@@ -278,7 +278,7 @@ job succeeded and if it failed, the reason for it.</p>
278
278
 
279
279
 
280
280
  <div class="method-source-code" id="get_input-source">
281
- <pre><span class="ruby-comment"># File lib/neptune.rb, line 406</span>
281
+ <pre><span class="ruby-comment"># File lib/neptune.rb, line 407</span>
282
282
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">get_input</span>(<span class="ruby-identifier">job_data</span>, <span class="ruby-identifier">ssh_args</span>, <span class="ruby-identifier">shadow_ip</span>, <span class="ruby-identifier">controller</span>)
283
283
  <span class="ruby-identifier">result</span> = {<span class="ruby-value">:result</span> =<span class="ruby-operator">&gt;</span> <span class="ruby-value">:success</span>}
284
284
 
@@ -335,7 +335,7 @@ NeptuneManager.</p>
335
335
 
336
336
 
337
337
  <div class="method-source-code" id="get_job_data-source">
338
- <pre><span class="ruby-comment"># File lib/neptune.rb, line 313</span>
338
+ <pre><span class="ruby-comment"># File lib/neptune.rb, line 314</span>
339
339
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">get_job_data</span>(<span class="ruby-identifier">params</span>)
340
340
  <span class="ruby-identifier">job_data</span> = {}
341
341
  <span class="ruby-identifier">params</span>.<span class="ruby-identifier">each</span> { <span class="ruby-operator">|</span><span class="ruby-identifier">k</span>, <span class="ruby-identifier">v</span><span class="ruby-operator">|</span>
@@ -411,7 +411,7 @@ not the job completed successfully (success = no errors).</p>
411
411
 
412
412
 
413
413
  <div class="method-source-code" id="get_std_out_and_err-source">
414
- <pre><span class="ruby-comment"># File lib/neptune.rb, line 486</span>
414
+ <pre><span class="ruby-comment"># File lib/neptune.rb, line 487</span>
415
415
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">get_std_out_and_err</span>(<span class="ruby-identifier">location</span>)
416
416
  <span class="ruby-identifier">result</span> = {}
417
417
 
@@ -458,7 +458,7 @@ engines can be found by contacting an AppScale node.</p>
458
458
 
459
459
 
460
460
  <div class="method-source-code" id="preprocess_babel-source">
461
- <pre><span class="ruby-comment"># File lib/neptune.rb, line 261</span>
461
+ <pre><span class="ruby-comment"># File lib/neptune.rb, line 262</span>
462
462
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">preprocess_babel</span>(<span class="ruby-identifier">job_data</span>, <span class="ruby-identifier">controller</span>)
463
463
  <span class="ruby-keyword">self</span>.<span class="ruby-identifier">require_param</span>(<span class="ruby-string">&quot;@code&quot;</span>, <span class="ruby-identifier">job_data</span>)
464
464
  <span class="ruby-keyword">self</span>.<span class="ruby-identifier">require_param</span>(<span class="ruby-string">&quot;@engine&quot;</span>, <span class="ruby-identifier">job_data</span>)
@@ -731,7 +731,8 @@ it does not, throws an exception.</p>
731
731
  <span class="ruby-keyword">if</span> <span class="ruby-identifier">controller</span>.<span class="ruby-identifier">does_file_exist?</span>(<span class="ruby-identifier">file</span>, <span class="ruby-identifier">job_data</span>)
732
732
  <span class="ruby-keyword">return</span>
733
733
  <span class="ruby-keyword">else</span>
734
- <span class="ruby-identifier">raise</span> <span class="ruby-constant">FileNotFoundException</span>
734
+ <span class="ruby-identifier">raise</span> <span class="ruby-constant">FileNotFoundException</span>.<span class="ruby-identifier">new</span>(<span class="ruby-node">&quot;Expecting file #{file} to exist &quot;</span> <span class="ruby-operator">+</span>
735
+ <span class="ruby-string">&quot;in the remote datastore, which did not exist.&quot;</span>)
735
736
  <span class="ruby-keyword">end</span>
736
737
  <span class="ruby-keyword">end</span></pre>
737
738
  </div><!-- require_file_to_exist-source -->
@@ -762,7 +763,7 @@ raising an exception if the named file does exist.</p>
762
763
 
763
764
 
764
765
  <div class="method-source-code" id="require_file_to_not_exist-source">
765
- <pre><span class="ruby-comment"># File lib/neptune.rb, line 246</span>
766
+ <pre><span class="ruby-comment"># File lib/neptune.rb, line 247</span>
766
767
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">require_file_to_not_exist</span>(<span class="ruby-identifier">file</span>, <span class="ruby-identifier">job_data</span>, <span class="ruby-identifier">controller</span>)
767
768
  <span class="ruby-keyword">begin</span>
768
769
  <span class="ruby-keyword">self</span>.<span class="ruby-identifier">require_file_to_exist</span>(<span class="ruby-identifier">file</span>, <span class="ruby-identifier">job_data</span>, <span class="ruby-identifier">controller</span>)
@@ -832,7 +833,7 @@ as well as information about the node to send the request to.</p>
832
833
 
833
834
 
834
835
  <div class="method-source-code" id="run_job-source">
835
- <pre><span class="ruby-comment"># File lib/neptune.rb, line 536</span>
836
+ <pre><span class="ruby-comment"># File lib/neptune.rb, line 537</span>
836
837
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">run_job</span>(<span class="ruby-identifier">job_data</span>, <span class="ruby-identifier">ssh_args</span>, <span class="ruby-identifier">shadow_ip</span>, <span class="ruby-identifier">secret</span>)
837
838
  <span class="ruby-identifier">controller</span> = <span class="ruby-constant">NeptuneManagerClient</span>.<span class="ruby-identifier">new</span>(<span class="ruby-identifier">shadow_ip</span>, <span class="ruby-identifier">secret</span>)
838
839
 
@@ -893,7 +894,7 @@ with Cicero jobs. It requires the AppScale tools to be installed.</p>
893
894
 
894
895
 
895
896
  <div class="method-source-code" id="upload_app_for_cicero-source">
896
- <pre><span class="ruby-comment"># File lib/neptune.rb, line 507</span>
897
+ <pre><span class="ruby-comment"># File lib/neptune.rb, line 508</span>
897
898
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">upload_app_for_cicero</span>(<span class="ruby-identifier">job_data</span>)
898
899
  <span class="ruby-keyword">if</span> <span class="ruby-operator">!</span><span class="ruby-identifier">job_data</span>[<span class="ruby-string">&quot;@app&quot;</span>]
899
900
  <span class="ruby-comment"># Kernel.puts &quot;No app specified, not uploading...&quot; </span>
@@ -948,7 +949,7 @@ parameter is missing.</p>
948
949
 
949
950
 
950
951
  <div class="method-source-code" id="validate_storage_params-source">
951
- <pre><span class="ruby-comment"># File lib/neptune.rb, line 366</span>
952
+ <pre><span class="ruby-comment"># File lib/neptune.rb, line 367</span>
952
953
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">validate_storage_params</span>(<span class="ruby-identifier">job_data</span>)
953
954
  <span class="ruby-identifier">job_data</span>[<span class="ruby-string">&quot;@storage&quot;</span>] <span class="ruby-operator">||=</span> <span class="ruby-string">&quot;appdb&quot;</span>
954
955
 
@@ -1012,7 +1013,7 @@ location.</p>
1012
1013
 
1013
1014
 
1014
1015
  <div class="method-source-code" id="wait_for_compilation_to_finish-source">
1015
- <pre><span class="ruby-comment"># File lib/neptune.rb, line 437</span>
1016
+ <pre><span class="ruby-comment"># File lib/neptune.rb, line 438</span>
1016
1017
  <span class="ruby-keyword">def</span> <span class="ruby-keyword">self</span>.<span class="ruby-identifier">wait_for_compilation_to_finish</span>(<span class="ruby-identifier">ssh_args</span>, <span class="ruby-identifier">shadow_ip</span>, <span class="ruby-identifier">compiled_location</span>)
1017
1018
  <span class="ruby-identifier">loop</span> {
1018
1019
  <span class="ruby-identifier">ssh_command</span> = <span class="ruby-node">&quot;ssh #{ssh_args} root@#{shadow_ip} 'ls #{compiled_location}' 2&gt;&amp;1&quot;</span>
@@ -329,7 +329,7 @@ select the best cloud for their job and run it there.</p>
329
329
 
330
330
 
331
331
  <div class="method-source-code" id="exodus-source">
332
- <pre><span class="ruby-comment"># File lib/exodus.rb, line 15</span>
332
+ <pre><span class="ruby-comment"># File lib/exodus.rb, line 20</span>
333
333
  <span class="ruby-keyword">def</span> <span class="ruby-identifier">exodus</span>(<span class="ruby-identifier">jobs</span>)
334
334
  <span class="ruby-keyword">if</span> <span class="ruby-identifier">jobs</span>.<span class="ruby-identifier">class</span> <span class="ruby-operator">==</span> <span class="ruby-constant">Hash</span>
335
335
  <span class="ruby-identifier">job_given_as_hash</span> = <span class="ruby-keyword">true</span>
@@ -1,10 +1,10 @@
1
- Mon, 30 Jul 2012 17:12:01 -0700
2
- bin/neptune Sun, 12 Feb 2012 16:12:33 -0800
3
- lib/exodus.rb Mon, 28 May 2012 21:02:31 -0700
4
- lib/task_info.rb Mon, 28 May 2012 16:24:14 -0700
5
- lib/babel.rb Mon, 30 Jul 2012 17:10:06 -0700
6
- lib/neptune_manager_client.rb Mon, 04 Jun 2012 13:53:07 -0700
7
- lib/common_functions.rb Sun, 12 Feb 2012 16:18:14 -0800
8
- lib/neptune.rb Mon, 30 Jul 2012 17:09:09 -0700
1
+ Fri, 28 Sep 2012 13:17:21 -0700
2
+ lib/babel.rb Sat, 01 Sep 2012 13:14:23 -0700
3
+ lib/exodus.rb Tue, 25 Sep 2012 12:38:28 -0700
9
4
  lib/custom_exceptions.rb Mon, 28 May 2012 16:23:52 -0700
10
- lib/exodus_task_info.rb Mon, 28 May 2012 21:03:03 -0700
5
+ lib/neptune_manager_client.rb Sat, 01 Sep 2012 13:14:23 -0700
6
+ lib/exodus_task_info.rb Mon, 30 Jul 2012 17:40:12 -0700
7
+ lib/common_functions.rb Sat, 01 Sep 2012 13:14:23 -0700
8
+ lib/neptune.rb Fri, 28 Sep 2012 13:12:58 -0700
9
+ lib/task_info.rb Mon, 28 May 2012 16:24:14 -0700
10
+ bin/neptune Sat, 01 Sep 2012 13:14:23 -0700
@@ -119,10 +119,10 @@
119
119
 
120
120
  <li class="method"><a href="ExodusTaskInfo.html#method-c-new">::new &mdash; ExodusTaskInfo</a>
121
121
 
122
- <li class="method"><a href="NeptuneManagerClient.html#method-c-new">::new &mdash; NeptuneManagerClient</a>
123
-
124
122
  <li class="method"><a href="TaskInfo.html#method-c-new">::new &mdash; TaskInfo</a>
125
123
 
124
+ <li class="method"><a href="NeptuneManagerClient.html#method-c-new">::new &mdash; NeptuneManagerClient</a>
125
+
126
126
  <li class="method"><a href="NeptuneHelper.html#method-c-preprocess_babel">::preprocess_babel &mdash; NeptuneHelper</a>
127
127
 
128
128
  <li class="method"><a href="NeptuneHelper.html#method-c-preprocess_compile">::preprocess_compile &mdash; NeptuneHelper</a>
@@ -147,12 +147,12 @@
147
147
 
148
148
  <li class="method"><a href="NeptuneHelper.html#method-c-require_param">::require_param &mdash; NeptuneHelper</a>
149
149
 
150
+ <li class="method"><a href="ExodusHelper.html#method-c-run_job">::run_job &mdash; ExodusHelper</a>
151
+
150
152
  <li class="method"><a href="BabelHelper.html#method-c-run_job">::run_job &mdash; BabelHelper</a>
151
153
 
152
154
  <li class="method"><a href="NeptuneHelper.html#method-c-run_job">::run_job &mdash; NeptuneHelper</a>
153
155
 
154
- <li class="method"><a href="ExodusHelper.html#method-c-run_job">::run_job &mdash; ExodusHelper</a>
155
-
156
156
  <li class="method"><a href="CommonFunctions.html#method-c-scp_file">::scp_file &mdash; CommonFunctions</a>
157
157
 
158
158
  <li class="method"><a href="CommonFunctions.html#method-c-scp_to_shadow">::scp_to_shadow &mdash; CommonFunctions</a>
@@ -211,10 +211,10 @@
211
211
 
212
212
  <li class="method"><a href="TaskInfo.html#method-i-to_json">#to_json &mdash; TaskInfo</a>
213
213
 
214
- <li class="method"><a href="ExodusTaskInfo.html#method-i-to_s">#to_s &mdash; ExodusTaskInfo</a>
215
-
216
214
  <li class="method"><a href="TaskInfo.html#method-i-to_s">#to_s &mdash; TaskInfo</a>
217
215
 
216
+ <li class="method"><a href="ExodusTaskInfo.html#method-i-to_s">#to_s &mdash; ExodusTaskInfo</a>
217
+
218
218
  </ul>
219
219
 
220
220
 
@@ -2,7 +2,12 @@
2
2
  # Programmer: Chris Bunch
3
3
 
4
4
 
5
+ require 'rubygems'
6
+ require 'json'
7
+
8
+
5
9
  require 'babel'
10
+ require 'common_functions'
6
11
  require 'custom_exceptions'
7
12
  require 'exodus_task_info'
8
13
 
@@ -87,6 +92,16 @@ module ExodusHelper
87
92
  }
88
93
 
89
94
 
95
+ # The location on this machine where we can read and write profiling
96
+ # information about jobs.
97
+ NEPTUNE_DATA_DIR = File.expand_path("~/.neptune")
98
+
99
+
100
+ # The command that we can run to get information about the number and speed
101
+ # of CPUs on this machine.
102
+ GET_CPU_INFO = "cat /proc/cpuinfo"
103
+
104
+
90
105
  OPTIMIZE_FOR_CHOICES = [:performance, :cost, :auto]
91
106
 
92
107
 
@@ -213,14 +228,47 @@ module ExodusHelper
213
228
 
214
229
  def self.get_profiling_info(job)
215
230
  key = self.get_key_from_job_data(job)
216
- neptune_manager = BabelHelper.get_neptune_manager_client(job)
217
- return neptune_manager.get_profiling_info(key)
231
+
232
+ if !File.exists?(NEPTUNE_DATA_DIR)
233
+ FileUtils.mkdir(NEPTUNE_DATA_DIR)
234
+ end
235
+
236
+ profiling_info_file = "#{NEPTUNE_DATA_DIR}/#{key}.json"
237
+ if File.exists?(profiling_info_file)
238
+ contents = File.open(profiling_info_file) { |f| f.read() }
239
+ return JSON.load(contents)
240
+ end
241
+
242
+ # If we don't have any profiling info on this job, run it locally and
243
+ # gather the data ourselves.
244
+
245
+ start_time = Time.now
246
+ # TODO(cgb): exec the user's code
247
+ end_time = Time.now
248
+
249
+ # To find out how fast this computer is, just check the file that has
250
+ # this info on it and take the first processor. This should be fine
251
+ # since we assume the user's code is not-multi-core aware and that
252
+ # all processors on this box are the same speed.
253
+ cpu_speed = Float(CommonFunctions.shell(GET_CPU_INFO).
254
+ scan(/cpu MHz\s*:\s*(\d+\.\d+)/).flatten[0])
255
+
256
+ json_info = {
257
+ "total_execution_time" => end_time - start_time,
258
+ "cpu_speed" => cpu_speed
259
+ }
260
+
261
+ File.open(profiling_info_file, "w+") { |file|
262
+ file.write(JSON.dump(json_info))
263
+ }
264
+
265
+ return json_info
218
266
  end
219
267
 
220
268
 
221
269
  # TODO(cgb): what is a job's key?
222
270
  def self.get_key_from_job_data(job)
223
- return job[:code]
271
+ return job[:code].gsub(/[\/\.]/, "")
224
272
  end
225
273
 
226
274
 
@@ -236,7 +236,8 @@ module NeptuneHelper
236
236
  if controller.does_file_exist?(file, job_data)
237
237
  return
238
238
  else
239
- raise FileNotFoundException
239
+ raise FileNotFoundException.new("Expecting file #{file} to exist " +
240
+ "in the remote datastore, which did not exist.")
240
241
  end
241
242
  end
242
243
 
@@ -36,6 +36,8 @@ class TestExodus < Test::Unit::TestCase
36
36
  :S3_URL => "http://s3.url",
37
37
  :S3_bucket_name => "bazbucket"
38
38
  }
39
+
40
+ flexmock(FileUtils).should_receive(:mkdir).and_return()
39
41
  end
40
42
 
41
43
 
@@ -223,16 +225,38 @@ class TestExodus < Test::Unit::TestCase
223
225
  :executable => "ruby"
224
226
  }
225
227
 
226
- # mock out the SOAP call for get_profiling_info
227
- no_job_data = {
228
- }
229
- flexmock(NeptuneManagerClient).new_instances { |instance|
230
- instance.should_receive(:get_profiling_info).with(job[:code]).
231
- and_return(no_job_data)
232
- }
228
+ # let's say they've never run an exodus job before, so they have
229
+ # no profiling data stored locally
230
+ flexmock(File).should_receive(:exists?).
231
+ with(ExodusHelper::NEPTUNE_DATA_DIR).and_return(false)
232
+ flexmock(FileUtils).should_receive(:mkdir).
233
+ with(ExodusHelper::NEPTUNE_DATA_DIR).and_return()
234
+
235
+ # mock out the gathering of profiling info
236
+ profiling_filename = "#{ExodusHelper::NEPTUNE_DATA_DIR}/#{ExodusHelper.get_key_from_job_data(job)}.json"
237
+ flexmock(File).should_receive(:exists?).
238
+ with(profiling_filename).and_return(false)
239
+
240
+ # mock out timing the user's code
241
+ flexmock(Time).should_receive(:now).and_return(1.0, 2.0)
233
242
 
234
- profiling_info = ExodusHelper.get_profiling_info(job)
235
- assert_equal(true, profiling_info.empty?)
243
+ # then mock out exec'ing the user's code
244
+ # TODO(cgb): do this
245
+
246
+ # mock out getting cpuinfo
247
+ flexmock(CommonFunctions).should_receive(:shell).
248
+ with(ExodusHelper::GET_CPU_INFO).and_return("cpu MHz: 666.66")
249
+
250
+ # finally, mock out writing the profiling information
251
+ flexmock(File).should_receive(:open).with(profiling_filename, "w+", Proc).
252
+ and_return()
253
+
254
+ expected = {
255
+ "total_execution_time" => 1.0,
256
+ "cpu_speed" => 666.66
257
+ }
258
+ actual = ExodusHelper.get_profiling_info(job)
259
+ assert_equal(expected, actual)
236
260
  end
237
261
 
238
262
 
@@ -526,10 +550,6 @@ class TestExodus < Test::Unit::TestCase
526
550
 
527
551
  # mock out calls to the NeptuneManager
528
552
  flexmock(NeptuneManagerClient).new_instances { |instance|
529
- # for this test, let's say there's no data on this task right now
530
- instance.should_receive(:get_profiling_info).with(String).
531
- and_return({})
532
-
533
553
  # let's say that all checks to see if temp files exist tell us that
534
554
  # the files don't exist
535
555
  instance.should_receive(:does_file_exist?).
@@ -562,6 +582,31 @@ class TestExodus < Test::Unit::TestCase
562
582
  # we'll say that our code does exist
563
583
  flexmock(File).should_receive(:exists?).with("/foo").and_return(true)
564
584
 
585
+ # let's say that we have a neptune profiling directory
586
+ flexmock(File).should_receive(:exists?).
587
+ with(ExodusHelper::NEPTUNE_DATA_DIR).and_return(true)
588
+
589
+ # and let's say that we've never run the job before
590
+ # start by mocking out its filesystem reads
591
+ key = ExodusHelper.get_key_from_job_data(job)
592
+ profiling_key = "#{ExodusHelper::NEPTUNE_DATA_DIR}/#{key}.json"
593
+ flexmock(File).should_receive(:exists?).
594
+ with(profiling_key).and_return(false)
595
+
596
+ # mock out timing the user's code
597
+ flexmock(Time).should_receive(:now).and_return(1.0, 2.0)
598
+
599
+ # then mock out exec'ing the user's code
600
+ # TODO(cgb): do this
601
+
602
+ # mock out getting cpuinfo
603
+ flexmock(CommonFunctions).should_receive(:shell).
604
+ with(ExodusHelper::GET_CPU_INFO).and_return("cpu MHz: 666.66")
605
+
606
+ # finally, mock out writing the profiling information
607
+ flexmock(File).should_receive(:open).with(profiling_key, "w+", Proc).
608
+ and_return()
609
+
565
610
  # mock out scp calls - assume they go through with no problems
566
611
  flexmock(CommonFunctions).should_receive(:shell).with(/\Ascp/).
567
612
  and_return()
@@ -605,12 +650,24 @@ class TestExodus < Test::Unit::TestCase
605
650
 
606
651
  job2 = job.dup
607
652
 
653
+ # let's say that we have a neptune profiling directory
654
+ flexmock(File).should_receive(:exists?).
655
+ with(ExodusHelper::NEPTUNE_DATA_DIR).and_return(true)
656
+
657
+ # and let's say that we've run the job before
658
+ key = ExodusHelper.get_key_from_job_data(job)
659
+ profiling_filename = "#{ExodusHelper::NEPTUNE_DATA_DIR}/#{key}.json"
660
+ dumped_data = JSON.dump({
661
+ "total_execution_time" => 60.00,
662
+ "cpu_speed" => 666.66
663
+ })
664
+ flexmock(File).should_receive(:exists?).
665
+ with(profiling_filename).and_return(true)
666
+ flexmock(File).should_receive(:open).
667
+ with(profiling_filename, Proc).and_return(dumped_data)
668
+
608
669
  # mock out calls to the NeptuneManager
609
670
  flexmock(NeptuneManagerClient).new_instances { |instance|
610
- # for this test, let's say there's no data on this task right now
611
- instance.should_receive(:get_profiling_info).with(String).
612
- and_return({})
613
-
614
671
  # let's say that all checks to see if temp files exist tell us that
615
672
  # the files don't exist
616
673
  instance.should_receive(:does_file_exist?).
metadata CHANGED
@@ -1,13 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: neptune
3
3
  version: !ruby/object:Gem::Version
4
- hash: 19
4
+ hash: 17
5
5
  prerelease:
6
6
  segments:
7
7
  - 0
8
8
  - 2
9
- - 2
10
- version: 0.2.2
9
+ - 3
10
+ version: 0.2.3
11
11
  platform: ruby
12
12
  authors:
13
13
  - Chris Bunch
@@ -15,7 +15,7 @@ autorequire: neptune
15
15
  bindir: bin
16
16
  cert_chain: []
17
17
 
18
- date: 2012-07-31 00:00:00 Z
18
+ date: 2012-09-28 00:00:00 Z
19
19
  dependencies:
20
20
  - !ruby/object:Gem::Dependency
21
21
  name: promise