Statistics
| Branch: | Revision:

root / src / com / rackspacecloud / android / AddNodesActivity.java @ 01340459

History | View | Annotate | Download (12.7 kB)

1
package com.rackspacecloud.android;
2

    
3
import java.util.ArrayList;
4

    
5
import com.rackspace.cloud.loadbalancer.api.client.Node;
6
import com.rackspace.cloud.servers.api.client.CloudServersException;
7
import com.rackspace.cloud.servers.api.client.Server;
8
import com.rackspace.cloud.servers.api.client.ServerManager;
9

    
10
import android.content.Intent;
11
import android.os.AsyncTask;
12
import android.os.Bundle;
13
import android.util.Log;
14
import android.view.LayoutInflater;
15
import android.view.View;
16
import android.view.View.OnClickListener;
17
import android.view.ViewGroup;
18
import android.widget.ArrayAdapter;
19
import android.widget.Button;
20
import android.widget.CheckBox;
21
import android.widget.CompoundButton;
22
import android.widget.LinearLayout;
23
import android.widget.ListView;
24
import android.widget.CompoundButton.OnCheckedChangeListener;
25
import android.widget.TextView;
26

    
27
public class AddNodesActivity extends CloudListActivity {
28

    
29
        private static final int ADD_NODE_CODE = 178;
30
        private static final int ADD_EXTERNAL_NODE_CODE = 188;
31

    
32
        //servers are what are displayed in the ListView
33
        private ArrayList<Server> servers;
34
        //nodes are the nodes the user has selected
35
        private ArrayList<Node> nodes;
36
        private int lastCheckedPos;
37

    
38
        @SuppressWarnings("unchecked")
39
        @Override
40
        public void onCreate(Bundle savedInstanceState) {
41
                super.onCreate(savedInstanceState);
42
                nodes = (ArrayList<Node>) this.getIntent().getExtras().get("nodes");
43
                setContentView(R.layout.addnodes);
44
                restoreState(savedInstanceState);
45
        }
46

    
47
        @Override
48
        protected void onSaveInstanceState(Bundle outState) {
49
                super.onSaveInstanceState(outState);
50
                outState.putSerializable("nodes", nodes);
51
                outState.putSerializable("servers", servers);
52
        }
53

    
54
        @SuppressWarnings("unchecked")
55
        protected void restoreState(Bundle state) {
56
                super.restoreState(state);
57

    
58
                if (state != null && state.containsKey("nodes")){
59
                        nodes = (ArrayList<Node>) state.getSerializable("nodes");
60
                        if(nodes == null){
61
                                nodes = new ArrayList<Node>();
62
                        }
63
                }
64

    
65
                if (state != null && state.containsKey("servers")) {
66
                        servers = (ArrayList<Server>) state.getSerializable("servers");
67
                        if (servers.size() == 0) {
68
                                displayNoServersCell();
69
                        } else {
70
                                getListView().setDividerHeight(1); // restore divider lines
71
                                setListAdapter(new ServerAdapter());
72
                        }
73
                } else {
74
                        loadServers();
75
                }
76

    
77
                Button submitNodes = (Button) findViewById(R.id.submit_nodes_button);
78
                submitNodes.setOnClickListener(new OnClickListener() {
79

    
80
                        @Override
81
                        public void onClick(View v) {
82
                                Intent viewIntent = new Intent();
83
                                viewIntent.putExtra("nodes", nodes);
84
                                setResult(RESULT_OK, viewIntent);
85
                                finish();
86
                        }
87
                });
88

    
89
                Button addExternalNode = (Button) findViewById(R.id.add_external_node);
90
                addExternalNode.setOnClickListener(new OnClickListener() {
91

    
92
                        @Override
93
                        public void onClick(View v) {
94
                                Intent viewIntent = new Intent(getContext(), AddExternalNodeActivity.class);
95
                                //when first creating a load balancer
96
                                //weighting nodes in not an option
97
                                viewIntent.putExtra("weighted", false);
98
                                startActivityForResult(viewIntent, ADD_EXTERNAL_NODE_CODE);
99
                        }
100
                });
101
        }
102

    
103
        @Override
104
        public void onBackPressed(){
105
                setResult(RESULT_CANCELED);
106
                finish();
107
        }
108

    
109
        protected void onListItemClick(ListView l, View v, int position, long id) {
110
                if (servers != null && servers.size() > 0) {
111
                        LinearLayout linear = (LinearLayout) findViewById(R.id.nodes_linear_layout); 
112
                        ListView serversList = (ListView) linear.findViewById(android.R.id.list);
113
                        View row = serversList.getChildAt(position);
114
                        CheckBox checkBox = (CheckBox)row.findViewById(R.id.add_node_checkbox);
115
                        if(!checkBox.isChecked()){
116
                                //if the checkbox was not previously checked, treat the listItemClick
117
                                //the same as checking the checkbox
118
                                checkBox.setChecked(!checkBox.isChecked());
119
                        } else {
120
                                //if the checkbox was already checked when the listItemClick occurred,
121
                                //then treat it like an edit
122

    
123
                                Server server = servers.get(position);
124

    
125
                                //Need to put all the ip's of the server into one
126
                                //list so they can all be displayed in one spinner
127
                                String[] ipAddresses = getAllIpsOfServer(server);
128

    
129
                                Node node = getNodeFromServer(server);
130

    
131
                                lastCheckedPos = position;
132
                                Intent viewIntent = new Intent(getContext(), AddNodeActivity.class);
133
                                viewIntent.putExtra("ipAddresses", ipAddresses);
134
                                viewIntent.putExtra("name", server.getName());
135
                                if(node != null){
136
                                        viewIntent.putExtra("node", node);
137
                                }
138
                                //weighted is false, because on initial node add
139
                                //weight is not option
140
                                viewIntent.putExtra("weighted", false);
141
                                startActivityForResult(viewIntent, ADD_NODE_CODE);
142
                        }
143

    
144
                }
145
        }
146

    
147
        private void displayNoServersCell() {
148
                String a[] = new String[1];
149
                a[0] = "No Nodes";
150
                setListAdapter(new ArrayAdapter<String>(this, R.layout.noserverscell, R.id.no_servers_label, a));
151
                getListView().setTextFilterEnabled(true);
152
                getListView().setDividerHeight(0); // hide the dividers so it won't look like a list row
153
                getListView().setItemsCanFocus(false);
154
        }
155

    
156
        private void setServerList(ArrayList<Server> servers) {
157
                if (servers == null) {
158
                        servers = new ArrayList<Server>();
159
                }
160
                String[] serverNames = new String[servers.size()];
161
                this.servers = new ArrayList<Server>();
162

    
163
                if (servers != null) {
164
                        for (int i = 0; i < servers.size(); i++) {
165
                                Server server = servers.get(i);
166
                                this.servers.add(i, server);
167
                                serverNames[i] = server.getName();
168
                        }
169
                }
170

    
171
                if (serverNames.length == 0) {
172
                        displayNoServersCell();
173
                } else {
174
                        getListView().setDividerHeight(1); // restore divider lines 
175
                        setListAdapter(new ServerAdapter());
176
                }
177
        }
178

    
179
        private void loadServers() {
180
                new LoadServersTask().execute((Void[]) null);
181
        }
182

    
183
        // * Adapter/
184
        class ServerAdapter extends ArrayAdapter<Server> {
185
                ServerAdapter() {
186
                        super(AddNodesActivity.this, R.layout.listservernodecell, servers);
187
                }
188

    
189
                public View getView(int position, View convertView, ViewGroup parent) {
190

    
191
                        final Server server = servers.get(position);
192
                        LayoutInflater inflater = getLayoutInflater();
193
                        View row = inflater.inflate(R.layout.listservernodecell, parent, false);
194

    
195
                        TextView label = (TextView) row.findViewById(R.id.label);
196
                        label.setText(server.getName());
197

    
198
                        TextView sublabel = (TextView) row.findViewById(R.id.sublabel);
199
                        if(server.getName().equals("External Node")){
200
                                sublabel.setText(server.getPrivateIpAddresses()[0]);
201
                        } else {
202
                                sublabel.setText(server.getFlavor().getName() + " - " + server.getImage().getName());
203
                        }
204

    
205

    
206
                        //Need to put all the ip's of the server into one
207
                        //list so they can all be displayed in one spinner
208
                        final String[] ipAddresses = getAllIpsOfServer(server);
209

    
210
                        final int pos = position;
211
                        CheckBox add = (CheckBox) row.findViewById(R.id.add_node_checkbox);
212

    
213
                        if(inNodeList(server)){
214
                                add.setChecked(true);
215
                        }
216

    
217
                        add.setOnCheckedChangeListener(new OnCheckedChangeListener() {
218

    
219
                                @Override
220
                                public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
221
                                        if(isChecked){
222
                                                lastCheckedPos = pos;
223
                                                Intent viewIntent = new Intent(getContext(), AddNodeActivity.class);
224
                                                viewIntent.putExtra("ipAddresses", ipAddresses);
225
                                                viewIntent.putExtra("name", server.getName());
226
                                                //weighted is false, because on initial node add
227
                                                //weight is not option
228
                                                viewIntent.putExtra("weighted", false);
229
                                                startActivityForResult(viewIntent, ADD_NODE_CODE);
230
                                        }
231
                                        else{
232
                                                removeNodeFromList(server);
233
                                                if(server.getName().equals("External Node")){
234
                                                        servers.remove(server);
235
                                                        setServerList(servers);
236
                                                }
237
                                        }
238
                                }
239
                        });
240

    
241
                        return(row);
242
                }
243

    
244
                //returns true if an ip from server
245
                //is the address of one of the nodes
246
                private boolean inNodeList(Server server){
247
                        for(Node node : nodes){
248
                                String nodeIp = node.getAddress();
249
                                if(serverHasIp(server, nodeIp)){
250
                                        return true;
251
                                }
252
                        }
253
                        return false;
254
                }
255

    
256
                /*
257
                 *  need to remove by id because that is 
258
                 *  what is unique
259
                 */
260
                private void removeNodeFromList(Server server){
261
                        for(int i = 0; i < nodes.size(); i++){
262
                                Node node = nodes.get(i);
263
                                if(serverHasIp(server, node.getAddress())){
264
                                        nodes.remove(i);
265
                                        break;
266
                                }
267
                        }
268
                }
269
        }
270

    
271
        private String getNameFromIp(String address){
272
                for(Server s: servers){
273
                        if(serverHasIp(s, address)){
274
                                return s.getName();
275
                        }
276
                }
277
                return "";
278
        }
279

    
280
        //returns true if address is an address of
281
        //one of the users cloud servers
282
        private boolean isCloudServerIp(String address){
283
                for(Server s : servers){
284
                        if(serverHasIp(s, address)){
285
                                return true;
286
                        }
287
                }
288
                return false;
289
        }
290

    
291
        //returns true if address is one of server's addresses
292
        private boolean serverHasIp(Server server, String address){
293
                String[] addresses = server.getPrivateIpAddresses();
294
                if(addresses != null){
295
                        for(int i = 0; i < addresses.length; i++){
296
                                if(addresses[i].equals(address)){
297
                                        return true;
298
                                }
299
                        }
300
                }
301
                addresses = server.getPublicIpAddresses();
302
                if(addresses != null){
303
                        for(int i = 0; i < addresses.length; i++){
304
                                if(addresses[i].equals(address)){
305
                                        return true;
306
                                }
307
                        }
308
                }
309
                return false;
310
        }
311

    
312
        //returns the node that is using an ip from server
313
        private Node getNodeFromServer(Server server){
314
                for(Node node : nodes){
315
                        if(serverHasIp(server, node.getAddress())){
316
                                return node;
317
                        }
318
                }
319
                return null;
320
        }
321

    
322
        //returns an array of all the ip's of server
323
        private String[] getAllIpsOfServer(Server server){
324
                String[] publicIp = server.getPublicIpAddresses();
325
                String[] privateIp = server.getPrivateIpAddresses();
326
                if(publicIp == null){
327
                        publicIp = new String[0];
328
                }
329
                if(privateIp == null){
330
                        privateIp = new String[0];
331
                }
332
                String[] ipAddresses = new String[privateIp.length + publicIp.length];
333
                for(int i = 0; i < privateIp.length; i++){
334
                        ipAddresses[i] = privateIp[i];
335
                }
336
                for(int i = 0; i < publicIp.length; i++){
337
                        ipAddresses[i+privateIp.length] = publicIp[i];
338
                }
339

    
340
                return ipAddresses;
341
        }
342

    
343
        private class LoadServersTask extends AsyncTask<Void, Void, ArrayList<Server>> {
344
                private CloudServersException exception;
345

    
346
                @Override
347
                protected void onPreExecute(){
348
                        showDialog();
349
                }
350

    
351
                @Override
352
                protected ArrayList<Server> doInBackground(Void... arg0) {
353
                        ArrayList<Server> servers = null;
354
                        try {
355
                                servers = (new ServerManager()).createList(true, getContext());
356
                        } catch (CloudServersException e) {
357
                                exception = e;                                
358
                        }
359
                        return servers;
360
                }
361

    
362
                @Override
363
                protected void onPostExecute(ArrayList<Server> result) {
364
                        hideDialog();
365
                        if (exception != null) {
366
                                showAlert("Error", exception.getMessage());
367
                        }
368

    
369
                        //Add the external nodes
370
                        for(int i = 0; i < nodes.size(); i++){
371
                                if(nodes.get(i).getName().equals("External Node")){
372
                                        Server server = new Server();
373
                                        server.setName("External Node");
374
                                        String[] ip = {nodes.get(i).getAddress()};
375
                                        server.setPrivateIpAddresses(ip);
376
                                        result.add(server);
377
                                }
378
                        }
379
                        setServerList(result);
380
                }
381
        }
382

    
383
        protected void onActivityResult(int requestCode, int resultCode, Intent data){
384
                int pos = lastCheckedPos;
385
                if(requestCode == ADD_NODE_CODE && resultCode == RESULT_OK){
386
                        //data will be null is user back out on edit
387
                        //we dont need to do anything then
388
                        //if new node added data won't be null
389
                        //so create the new node and add it to the list
390
                        if(data != null){
391
                                Node node = new Node();
392
                                node.setAddress(data.getStringExtra("nodeIp"));
393
                                node.setCondition(data.getStringExtra("nodeCondition"));
394
                                node.setName(servers.get(pos).getName());
395
                                node.setPort(data.getStringExtra("nodePort"));
396
                                node.setWeight(data.getStringExtra("nodeWeight"));
397
                                nodes.add(node);
398
                        }
399
                }
400
                else if(requestCode == ADD_NODE_CODE && resultCode == RESULT_CANCELED){
401
                        //uncheck the node at lastCheckedPos
402
                        LinearLayout linear = (LinearLayout) findViewById(R.id.nodes_linear_layout); 
403
                        ListView serversList = (ListView) linear.findViewById(android.R.id.list);
404
                        View row = serversList.getChildAt(pos);
405
                        CheckBox checkBox = (CheckBox)row.findViewById(R.id.add_node_checkbox);
406
                        checkBox.setChecked(false);
407
                }
408

    
409
                else if(requestCode == ADD_EXTERNAL_NODE_CODE && resultCode == RESULT_OK){
410
                        Node node = new Node();
411
                        node.setAddress(data.getStringExtra("nodeIp"));
412
                        node.setCondition(data.getStringExtra("nodeCondition"));
413
                        node.setName("External Node");
414
                        node.setPort(data.getStringExtra("nodePort"));
415
                        node.setWeight(data.getStringExtra("nodeWeight"));
416

    
417
                        /*
418
                         * If the ip is from a cloud server, alert to user
419
                         * so they can select it from there
420
                         */        
421
                        if(!isCloudServerIp(node.getAddress())){
422
                                nodes.add(node);
423
                                //Add it to server list so it display in the listview
424
                                Server server = new Server();
425
                                server.setName("External Node");
426
                                String[] ip = {data.getStringExtra("nodeIp")};
427
                                server.setPrivateIpAddresses(ip);
428
                                servers.add(server);
429
                                setServerList(servers);
430
                        } else {
431
                                showAlert("Error", "This IP belongs to a cloud server: \"" + getNameFromIp(node.getAddress()) 
432
                                                + "\", please select it from the list.");
433
                        }
434
                }
435
                Log.d("info", "number of nodes is " + nodes.size());
436
        }
437

    
438

    
439
}