aims_project 0.3.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.
- data/README +5 -0
- data/bin/AimsCalc +367 -0
- data/bin/AimsProject +88 -0
- data/bin/AimsProjectManager +39 -0
- data/lib/aims_project.rb +158 -0
- data/lib/aims_project/aims_project_exception.rb +42 -0
- data/lib/aims_project/aims_project_geometry.rb +52 -0
- data/lib/aims_project/app_controller.rb +298 -0
- data/lib/aims_project/atom.rb +95 -0
- data/lib/aims_project/calculation.rb +406 -0
- data/lib/aims_project/calculation_tree.rb +65 -0
- data/lib/aims_project/calculation_window.rb +141 -0
- data/lib/aims_project/crystal_viewer.rb +981 -0
- data/lib/aims_project/crystal_viewer_options.rb +103 -0
- data/lib/aims_project/geometry_editor.rb +111 -0
- data/lib/aims_project/geometry_file.rb +184 -0
- data/lib/aims_project/geometry_window.rb +172 -0
- data/lib/aims_project/green_arrow.jpg +0 -0
- data/lib/aims_project/inspector.rb +183 -0
- data/lib/aims_project/material.rb +30 -0
- data/lib/aims_project/octree.rb +5 -0
- data/lib/aims_project/pan.gif +0 -0
- data/lib/aims_project/project.rb +102 -0
- data/lib/aims_project/project_tree.rb +62 -0
- data/lib/aims_project/rotate.gif +0 -0
- data/lib/aims_project/thread_callback_event.rb +19 -0
- data/lib/aims_project/zoom.gif +0 -0
- data/skeleton/Capfile +37 -0
- data/skeleton/config/aims.sh +58 -0
- data/skeleton/config/tasks.rb +145 -0
- data/skeleton/config/user_variables.rb +37 -0
- data/skeleton/control/example.erb +41 -0
- data/skeleton/geometry/example +1 -0
- metadata +136 -0
|
Binary file
|
|
@@ -0,0 +1,183 @@
|
|
|
1
|
+
module AimsProject
|
|
2
|
+
class Inspector < Wx::Frame
|
|
3
|
+
|
|
4
|
+
include Wx
|
|
5
|
+
|
|
6
|
+
class << self
|
|
7
|
+
def control_value_accessor(*args)
|
|
8
|
+
args.each do |cb|
|
|
9
|
+
class_eval <<-EOS
|
|
10
|
+
def #{cb.to_s}
|
|
11
|
+
@#{cb.to_s}.get_value
|
|
12
|
+
end
|
|
13
|
+
EOS
|
|
14
|
+
end
|
|
15
|
+
end
|
|
16
|
+
end
|
|
17
|
+
|
|
18
|
+
control_value_accessor :bond_length
|
|
19
|
+
control_value_accessor :show_bonds, :show_lighting, :show_cell
|
|
20
|
+
control_value_accessor :show_clip_planes, :show_xclip, :show_yclip, :show_zclip
|
|
21
|
+
control_value_accessor :x_repeat, :y_repeat, :z_repeat
|
|
22
|
+
control_value_accessor :correct
|
|
23
|
+
control_value_accessor :transparent_bg
|
|
24
|
+
|
|
25
|
+
attr_accessor :update_unit_cell
|
|
26
|
+
|
|
27
|
+
def initialize(app, frame)
|
|
28
|
+
|
|
29
|
+
super(frame, :style => (CLOSE_BOX | CAPTION | FRAME_FLOAT_ON_PARENT))
|
|
30
|
+
|
|
31
|
+
@app = app
|
|
32
|
+
|
|
33
|
+
# Array to track the inspector windows being shown
|
|
34
|
+
@windows = []
|
|
35
|
+
|
|
36
|
+
self.sizer = BoxSizer.new(VERTICAL)
|
|
37
|
+
set_auto_layout(true)
|
|
38
|
+
self.sizer.set_size_hints(self)
|
|
39
|
+
self.sizer.fit(self)
|
|
40
|
+
|
|
41
|
+
self.update_unit_cell = false
|
|
42
|
+
self.evt_close {|event| self.hide }
|
|
43
|
+
end
|
|
44
|
+
|
|
45
|
+
# Create a window to show in the inspector. Default is to not show this window.
|
|
46
|
+
# call show_inspector_window() to show it
|
|
47
|
+
# options are Wx:Sizer options
|
|
48
|
+
# return the window so that caller can add controls to it
|
|
49
|
+
def add_inspector_window(options = {})
|
|
50
|
+
window = Panel.new(self)
|
|
51
|
+
@windows << window
|
|
52
|
+
self.sizer.add_item(window, options)
|
|
53
|
+
self.sizer.show(window, false)
|
|
54
|
+
return window
|
|
55
|
+
end
|
|
56
|
+
|
|
57
|
+
# Show the inspector window
|
|
58
|
+
def show_inspector_window(window)
|
|
59
|
+
@windows.each {|w|
|
|
60
|
+
self.sizer.show(w, w == window)
|
|
61
|
+
}
|
|
62
|
+
self.sizer.fit(self)
|
|
63
|
+
end
|
|
64
|
+
|
|
65
|
+
# The view options
|
|
66
|
+
def view_options_panel(parent)
|
|
67
|
+
|
|
68
|
+
# Default padding around each element
|
|
69
|
+
border = 5
|
|
70
|
+
|
|
71
|
+
panel = Wx::VBoxSizer.new
|
|
72
|
+
parent.sizer = panel
|
|
73
|
+
|
|
74
|
+
# Panel 1
|
|
75
|
+
panel1 = Wx::VBoxSizer.new
|
|
76
|
+
|
|
77
|
+
@show_bonds = Wx::CheckBox.new(parent, :label => 'Show Bonds')
|
|
78
|
+
panel1.add_item(@show_bonds, :flag => ALL,:border => border)
|
|
79
|
+
|
|
80
|
+
@show_lighting = Wx::CheckBox.new(parent, :label => 'Show Lighting')
|
|
81
|
+
panel1.add_item(@show_lighting, :flag => ALL, :border => border)
|
|
82
|
+
|
|
83
|
+
@show_cell = Wx::CheckBox.new(parent, :label => "Show Unit Cell")
|
|
84
|
+
panel1.add_item(@show_cell, :flag => ALL, :border => border)
|
|
85
|
+
|
|
86
|
+
@correct = Wx::CheckBox.new(parent, :label => "Correct Geometry")
|
|
87
|
+
panel1.add_item(@correct, :flag => ALL, :border => border)
|
|
88
|
+
|
|
89
|
+
@transparent_bg = Wx::CheckBox.new(parent, :label => "Transparent BG")
|
|
90
|
+
panel1.add_item(@transparent_bg, :flag => ALL, :border => border)
|
|
91
|
+
|
|
92
|
+
gsizer = GridSizer.new(2,1)
|
|
93
|
+
gsizer.add(StaticText.new(parent, :label => "Bond Length"))
|
|
94
|
+
@bond_length = SpinCtrl.new(parent, :min => 1, :max => 100, :value => "4")
|
|
95
|
+
gsizer.add_item(@bond_length, :flag => EXPAND)
|
|
96
|
+
panel1.add_item(gsizer)
|
|
97
|
+
|
|
98
|
+
evt_checkbox(@show_bonds) {|evt| @app.update_viewer}
|
|
99
|
+
evt_checkbox(@show_lighting) {|evt| @app.update_viewer}
|
|
100
|
+
evt_checkbox(@show_cell) {|evt| @app.update_viewer}
|
|
101
|
+
evt_checkbox(@transparent_bg) {|evt| @app.update_viewer}
|
|
102
|
+
evt_checkbox(@correct) {|evt|
|
|
103
|
+
self.update_unit_cell = true
|
|
104
|
+
@app.update_viewer
|
|
105
|
+
}
|
|
106
|
+
evt_spinctrl(@bond_length) {|evt| @app.update_viewer }
|
|
107
|
+
|
|
108
|
+
# Panel 2 : Clip Planes
|
|
109
|
+
panel2 = Wx::VBoxSizer.new
|
|
110
|
+
panel2.add_item(StaticText.new(parent, -1, "Clip Planes:", :style => ALIGN_LEFT))
|
|
111
|
+
@show_xclip = Wx::CheckBox.new(parent, :label => 'x')
|
|
112
|
+
panel2.add_item(@show_xclip, 0, Wx::ALIGN_CENTER, border)
|
|
113
|
+
@show_yclip = Wx::CheckBox.new(parent, :label => 'y')
|
|
114
|
+
panel2.add_item(@show_yclip, 0, Wx::ALIGN_CENTER, border)
|
|
115
|
+
@show_zclip = Wx::CheckBox.new(parent, :label => 'z')
|
|
116
|
+
panel2.add_item(@show_zclip, 0, Wx::ALIGN_CENTER, border)
|
|
117
|
+
|
|
118
|
+
|
|
119
|
+
evt_checkbox(@show_xclip) {|evt| @app.update_viewer}
|
|
120
|
+
evt_checkbox(@show_yclip) {|evt| @app.update_viewer}
|
|
121
|
+
evt_checkbox(@show_zclip) {|evt| @app.update_viewer}
|
|
122
|
+
|
|
123
|
+
# Panel 3: Repeat
|
|
124
|
+
panel3 = Wx::VBoxSizer.new
|
|
125
|
+
panel3.add_item(StaticText.new(parent, -1, "Repeat:", :style => ALIGN_LEFT), 0, EXPAND)
|
|
126
|
+
|
|
127
|
+
panel3grid = GridSizer.new(3,2, border, border)
|
|
128
|
+
|
|
129
|
+
@x_repeat = Wx::SpinCtrl.new(parent, :value => "1", :min => 1, :max => 100, :initial => 1)
|
|
130
|
+
@y_repeat = Wx::SpinCtrl.new(parent, :value => "1", :min => 1, :max => 100, :initial => 1)
|
|
131
|
+
@z_repeat = Wx::SpinCtrl.new(parent, :value => "1", :min => 1, :max => 100, :initial => 1)
|
|
132
|
+
|
|
133
|
+
evt_spinctrl(@x_repeat) {|evt|
|
|
134
|
+
self.update_unit_cell = true
|
|
135
|
+
@app.update_viewer
|
|
136
|
+
}
|
|
137
|
+
evt_spinctrl(@y_repeat) {|evt|
|
|
138
|
+
self.update_unit_cell = true
|
|
139
|
+
@app.update_viewer
|
|
140
|
+
}
|
|
141
|
+
evt_spinctrl(@z_repeat) {|evt|
|
|
142
|
+
self.update_unit_cell = true
|
|
143
|
+
@app.update_viewer
|
|
144
|
+
}
|
|
145
|
+
|
|
146
|
+
panel3grid.add(StaticText.new(parent, :label => "x", :style => ALIGN_RIGHT),1, EXPAND)
|
|
147
|
+
panel3grid.add(@x_repeat,2)
|
|
148
|
+
|
|
149
|
+
panel3grid.add(StaticText.new(parent, :label => "y",:style => ALIGN_RIGHT),1, EXPAND)
|
|
150
|
+
panel3grid.add(@y_repeat,2)
|
|
151
|
+
|
|
152
|
+
panel3grid.add(StaticText.new(parent, :label => "z",:style => ALIGN_RIGHT),1, EXPAND)
|
|
153
|
+
panel3grid.add(@z_repeat,2)
|
|
154
|
+
|
|
155
|
+
panel3.add(panel3grid, 0, EXPAND | ALIGN_CENTER)
|
|
156
|
+
|
|
157
|
+
# Add sub-panels
|
|
158
|
+
panel.add(panel1, 0, Wx::ALL)
|
|
159
|
+
panel.add_spacer(5)
|
|
160
|
+
panel.add(panel2, 0, Wx::EXPAND)
|
|
161
|
+
panel.add_spacer(5)
|
|
162
|
+
panel.add(panel3, 0, Wx::EXPAND)
|
|
163
|
+
|
|
164
|
+
|
|
165
|
+
end
|
|
166
|
+
|
|
167
|
+
# Called when a new file is loaded
|
|
168
|
+
def update(viewer)
|
|
169
|
+
@show_bonds.set_value(viewer.show_bonds)
|
|
170
|
+
@show_lighting.set_value(viewer.lighting)
|
|
171
|
+
@show_cell.set_value(viewer.show_supercell)
|
|
172
|
+
@correct.set_value(false)
|
|
173
|
+
@show_xclip.set_value(viewer.show_xclip)
|
|
174
|
+
@show_yclip.set_value(viewer.show_yclip)
|
|
175
|
+
@show_zclip.set_value(viewer.show_zclip)
|
|
176
|
+
@bond_length.set_value(viewer.bond_length)
|
|
177
|
+
@x_repeat.set_value(1)
|
|
178
|
+
@y_repeat.set_value(1)
|
|
179
|
+
@z_repeat.set_value(1)
|
|
180
|
+
end
|
|
181
|
+
|
|
182
|
+
end
|
|
183
|
+
end
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
module AimsProject
|
|
2
|
+
class Material
|
|
3
|
+
|
|
4
|
+
include Gl
|
|
5
|
+
|
|
6
|
+
attr_accessor :r, :g, :b, :alpha
|
|
7
|
+
|
|
8
|
+
def Material.black
|
|
9
|
+
Material.new(0,0,0)
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
def initialize(r,g,b,alpha=1)
|
|
13
|
+
self.r = r
|
|
14
|
+
self.g = g
|
|
15
|
+
self.b = b
|
|
16
|
+
self.alpha = alpha
|
|
17
|
+
end
|
|
18
|
+
|
|
19
|
+
def apply(lighting = true)
|
|
20
|
+
if lighting
|
|
21
|
+
glMaterialfv(GL_FRONT, GL_AMBIENT_AND_DIFFUSE, [self.r, self.g, self.b, self.alpha])
|
|
22
|
+
glMaterialfv(GL_FRONT, GL_SPECULAR, [self.r, self.g, self.b, self.alpha])
|
|
23
|
+
glMaterialf(GL_FRONT, GL_SHININESS, 50)
|
|
24
|
+
else
|
|
25
|
+
glColor3f(self.r, self.g, self.b)
|
|
26
|
+
end
|
|
27
|
+
end
|
|
28
|
+
end
|
|
29
|
+
|
|
30
|
+
end
|
|
Binary file
|
|
@@ -0,0 +1,102 @@
|
|
|
1
|
+
require 'fileutils'
|
|
2
|
+
|
|
3
|
+
module AimsProject
|
|
4
|
+
|
|
5
|
+
class Project
|
|
6
|
+
|
|
7
|
+
# A project is a collection of calculations
|
|
8
|
+
# and tools for managing the execution and analysis of the calculations
|
|
9
|
+
|
|
10
|
+
# The name of this project
|
|
11
|
+
attr_accessor :name
|
|
12
|
+
|
|
13
|
+
# Load a Project from the serialized yaml file
|
|
14
|
+
def Project.load(filename)
|
|
15
|
+
yamlfile = [filename, filename+".yaml"].find{|f| File.exists?(f)}
|
|
16
|
+
|
|
17
|
+
File.open(yamlfile, 'r') do |f|
|
|
18
|
+
YAML.load(f)
|
|
19
|
+
end
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
# Create a new Project with the given name
|
|
23
|
+
# This will also create the directory structure
|
|
24
|
+
# for the project. Returns true if successful, false otherwise
|
|
25
|
+
def Project.create(name)
|
|
26
|
+
|
|
27
|
+
return nil unless name
|
|
28
|
+
|
|
29
|
+
p = Project.new(name)
|
|
30
|
+
|
|
31
|
+
# Create the project directory
|
|
32
|
+
FileUtils.mkdir(p.relative_path)
|
|
33
|
+
p.save(p.relative_path)
|
|
34
|
+
#
|
|
35
|
+
# # Create the config directory
|
|
36
|
+
# FileUtils.mkdir(File.join(p.relative_path, "config"))
|
|
37
|
+
#
|
|
38
|
+
# # Create the geometry directory
|
|
39
|
+
# FileUtils.mkdir(File.join(p.relative_path, AimsProject::GEOMETRY_DIR))
|
|
40
|
+
#
|
|
41
|
+
# # Create the control directory
|
|
42
|
+
# FileUtils.mkdir(File.join(p.relative_path, AimsProject::CONTROL_DIR))
|
|
43
|
+
#
|
|
44
|
+
# # Create the calculations directory
|
|
45
|
+
# FileUtils.mkdir(File.join(p.relative_path, AimsProject::CALCULATION_DIR))
|
|
46
|
+
|
|
47
|
+
return p
|
|
48
|
+
end
|
|
49
|
+
|
|
50
|
+
# Initialize a new project object with the given name.
|
|
51
|
+
# This does not create the project directory structure, use create for that.
|
|
52
|
+
def initialize(name)
|
|
53
|
+
self.name = name
|
|
54
|
+
end
|
|
55
|
+
|
|
56
|
+
# Return the binding for this project
|
|
57
|
+
def get_binding
|
|
58
|
+
binding
|
|
59
|
+
end
|
|
60
|
+
|
|
61
|
+
# The path of this project relative to project_root_dir
|
|
62
|
+
def relative_path
|
|
63
|
+
name
|
|
64
|
+
end
|
|
65
|
+
|
|
66
|
+
# The filename of the serialized yaml file representing this project
|
|
67
|
+
def serialized_filename
|
|
68
|
+
"#{self.name}.yaml"
|
|
69
|
+
end
|
|
70
|
+
|
|
71
|
+
# The full path to this project locally
|
|
72
|
+
def full_path
|
|
73
|
+
File.dirname(File.expand_path(serialized_filename))
|
|
74
|
+
end
|
|
75
|
+
|
|
76
|
+
# Serialize this project to a yaml file named after this project
|
|
77
|
+
# in the given directory
|
|
78
|
+
def save(dir = ".")
|
|
79
|
+
File.open(File.join(dir, "#{name}.yaml"), 'w') do |f|
|
|
80
|
+
f.print YAML.dump(self)
|
|
81
|
+
end
|
|
82
|
+
end
|
|
83
|
+
|
|
84
|
+
# Retreive the calcluations managed by this project.
|
|
85
|
+
# This array is loaded directly from serialized yaml
|
|
86
|
+
# files in each calculation directory
|
|
87
|
+
def calculations
|
|
88
|
+
calc_status_files = Dir.glob(File.join(AimsProject::CALCULATION_DIR, "*", AimsProject::CALC_STATUS_FILENAME))
|
|
89
|
+
# pick up sub-calculations
|
|
90
|
+
calc_status_files += Dir.glob(File.join(AimsProject::CALCULATION_DIR, "*", "*", AimsProject::CALC_STATUS_FILENAME))
|
|
91
|
+
calc_status_files.collect{|f|
|
|
92
|
+
Calculation.load(File.dirname(f))
|
|
93
|
+
}
|
|
94
|
+
end
|
|
95
|
+
|
|
96
|
+
# Retreive the geometries managed by this project.
|
|
97
|
+
def geometries
|
|
98
|
+
Dir.glob(File.join(AimsProject::GEOMETRY_DIR, "*"))
|
|
99
|
+
end
|
|
100
|
+
|
|
101
|
+
end
|
|
102
|
+
end
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
module AimsProject
|
|
2
|
+
|
|
3
|
+
class ProjectTree < Wx::ScrolledWindow
|
|
4
|
+
|
|
5
|
+
include Wx
|
|
6
|
+
|
|
7
|
+
ROOT = "Root"
|
|
8
|
+
GEOMETRY = "Geometry"
|
|
9
|
+
CONTROL = "Control"
|
|
10
|
+
CALCULATIONS = "Calculations"
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
attr_accessor :app, :treeControl
|
|
14
|
+
|
|
15
|
+
def initialize(app, window)
|
|
16
|
+
super(window)
|
|
17
|
+
self.app = app
|
|
18
|
+
|
|
19
|
+
init_project_tree
|
|
20
|
+
|
|
21
|
+
sizer = BoxSizer.new(VERTICAL)
|
|
22
|
+
sizer.add(self.treeControl, 1, EXPAND | ALL, 5)
|
|
23
|
+
|
|
24
|
+
set_auto_layout(true)
|
|
25
|
+
set_sizer(sizer)
|
|
26
|
+
end
|
|
27
|
+
|
|
28
|
+
def init_project_tree
|
|
29
|
+
@treeControl = Wx::TreeCtrl.new(self)
|
|
30
|
+
@tree_map = {}
|
|
31
|
+
if self.app.project
|
|
32
|
+
@tree_map[ROOT] = self.treeControl.add_root(self.app.project.name)
|
|
33
|
+
@tree_map[GEOMETRY] = self.treeControl.append_item(@tree_map[ROOT], GEOMETRY)
|
|
34
|
+
@tree_map[CONTROL] = self.treeControl.append_item(@tree_map[ROOT], CONTROL)
|
|
35
|
+
@tree_map[CALCULATIONS] = self.treeControl.append_item(@tree_map[ROOT], CALCULATIONS)
|
|
36
|
+
|
|
37
|
+
self.app.project.geometries.each{|geom|
|
|
38
|
+
self.treeControl.append_item(@tree_map[GEOMETRY], geom)
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
self.app.project.calculations.each{|calc|
|
|
42
|
+
calcid = self.treeControl.append_item(@tree_map[CALCULATIONS], calc.name)
|
|
43
|
+
@tree_map[calcid] = calc
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
evt_tree_sel_changed(self.treeControl) {|evt|
|
|
47
|
+
itemid = evt.get_item
|
|
48
|
+
if @tree_map[GEOMETRY] == self.treeControl.get_item_parent(itemid)
|
|
49
|
+
self.app.open_file(self.treeControl.get_item_text(itemid))
|
|
50
|
+
elsif @tree_map[CALCULATIONS] == self.treeControl.get_item_parent(itemid)
|
|
51
|
+
calc = @tree_map[itemid]
|
|
52
|
+
self.app.show_calculation(calc)
|
|
53
|
+
end
|
|
54
|
+
}
|
|
55
|
+
else
|
|
56
|
+
@tree_map[ROOT] = self.treeControl.add_root(ROOT)
|
|
57
|
+
end
|
|
58
|
+
@treeControl.expand(@tree_map[ROOT])
|
|
59
|
+
end
|
|
60
|
+
|
|
61
|
+
end
|
|
62
|
+
end
|
|
Binary file
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
module AimsProject
|
|
2
|
+
class ThreadCallbackEvent < Wx::CommandEvent
|
|
3
|
+
|
|
4
|
+
@@event_type_id = 0
|
|
5
|
+
|
|
6
|
+
def ThreadCallbackEvent.set_event_type(id)
|
|
7
|
+
@@event_type_id = id
|
|
8
|
+
end
|
|
9
|
+
|
|
10
|
+
def ThreadCallbackEvent.event_type
|
|
11
|
+
@@event_type_id
|
|
12
|
+
end
|
|
13
|
+
|
|
14
|
+
def initialize
|
|
15
|
+
super(@@event_type_id)
|
|
16
|
+
end
|
|
17
|
+
|
|
18
|
+
end
|
|
19
|
+
end
|
|
Binary file
|
data/skeleton/Capfile
ADDED
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
require 'aims_project'
|
|
2
|
+
|
|
3
|
+
load 'config/tasks.rb'
|
|
4
|
+
|
|
5
|
+
# The name of this project
|
|
6
|
+
set :project_name, '__PROJECT_NAME__'
|
|
7
|
+
|
|
8
|
+
# The following settings apply to calculations occuring on the remote host
|
|
9
|
+
|
|
10
|
+
# The base directory on the remote host
|
|
11
|
+
set :remote_project_dir, 'AimsProjects'
|
|
12
|
+
|
|
13
|
+
# Query the user for the number of parallel nodes when queueing calculations
|
|
14
|
+
set(:nodes) {Capistrano::CLI.ui.ask("How many compute nodes?: ")}
|
|
15
|
+
|
|
16
|
+
# The memory for each calculation
|
|
17
|
+
set :memory, 1024
|
|
18
|
+
|
|
19
|
+
# The time limit for each calculation
|
|
20
|
+
set :time, 24
|
|
21
|
+
|
|
22
|
+
# Set the qstat command
|
|
23
|
+
set :qstat_cmd, "qstat -u jns"
|
|
24
|
+
|
|
25
|
+
# The qsub command to execute
|
|
26
|
+
# There are some extra commands in here to forward SIGUSR1 and SIGUSR2 to aims_script
|
|
27
|
+
# so that the job status can be properly updated if the job is aborted
|
|
28
|
+
# aims_script is predefined to be 'aims.sh', if this is unsuitable
|
|
29
|
+
# it can be reset with: set :aims_script, 'foo'
|
|
30
|
+
set(:qsub) {
|
|
31
|
+
"parallel.q -n #{nodes} -d #{memory} -t #{time} -ns -k #{aims_script}; sed '/\\btime\\b/ i\\ trap : SIGUSR1 SIGUSR2' #{aims_script}.cmd > #{aims_script}.cmd.new; mv #{aims_script}.cmd.new #{aims_script}.cmd; qsub -notify #{aims_script}.cmd"
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
# The remote host for data transfer of large files
|
|
35
|
+
role :data_transfer, "Your Data Transfer Server Here"
|
|
36
|
+
# The remote host for job submission
|
|
37
|
+
role :queue_submission, "Your Compute Cluster Server Here"
|