a4a50e84acf482db5e8f35b10d54c8bbee2e1b48
[phpeclipse.git] / archive / net.sourceforge.phpeclipse.quantum.sql / src / com / quantum / model / Bookmark.java
1 package com.quantum.model;
2
3 import java.beans.PropertyChangeListener;
4 import java.beans.PropertyChangeSupport;
5 import java.sql.Connection;
6 import java.sql.SQLException;
7 import java.util.ArrayList;
8 import java.util.Arrays;
9 import java.util.Collections;
10 import java.util.HashSet;
11 import java.util.Hashtable;
12 import java.util.List;
13 import java.util.Map;
14 import java.util.Set;
15
16 import com.quantum.IQuantumConstants;
17 import com.quantum.QuantumPlugin;
18 import com.quantum.adapters.AdapterFactory;
19 import com.quantum.adapters.DatabaseAdapter;
20 import com.quantum.sql.ConnectionEstablisher;
21 import com.quantum.sql.MultiSQLServer;
22
23 import org.eclipse.jface.preference.IPreferenceStore;
24
25 /**
26  * Class Bookmark holds the "static" information of a bookmark, that is the data that
27  * is saved and loaded from the external file and describes a bookmark. This info will
28  * be filled up by the end user.
29  * 
30  * @author root
31  */
32 public class Bookmark implements Displayable {
33         
34         public static final int SCHEMA_RULE_USE_ALL = 1;
35         public static final int SCHEMA_RULE_USE_DEFAULT = 2;
36         public static final int SCHEMA_RULE_USE_SELECTED = 3;
37     
38     private PropertyChangeSupport propertyChangeSupport = new PropertyChangeSupport(this);
39         private String name = ""; //$NON-NLS-1$
40         private String username = ""; //$NON-NLS-1$
41     private String password = ""; //$NON-NLS-1$
42     private String connectionUrl = ""; //$NON-NLS-1$
43     private JDBCDriver driver;
44     
45     private int schemaRule = SCHEMA_RULE_USE_ALL;
46     
47     /**
48      * A quick list is a list of favourite tables that a person might want to view
49      * without having to look at the entire list of tables.
50      */
51     private Map quickList = new Hashtable();
52         private Set schemas = new HashSet();   
53         private Connection connection = null;
54     private ConnectionEstablisher connectionEstablisher;
55     private boolean changed = true;
56     private List queries = Collections.synchronizedList(new ArrayList());
57     private boolean promptForPassword = false;
58     private boolean autoCommit = true;
59     private String autoCommitPreference = IQuantumConstants.autoCommitTrue;
60         
61         public Bookmark() {
62         this(MultiSQLServer.getInstance());
63         }
64     
65     public Bookmark(ConnectionEstablisher connectionEstablisher) {
66         this.connectionEstablisher = connectionEstablisher;
67     }
68
69         public Bookmark(Bookmark data) {
70                 this();
71                 setName(data.getName());
72                 setUsername(data.getUsername());
73                 setPassword(data.getPassword());
74                 setConnect(data.getConnect());
75                 setJDBCDriver(data.getJDBCDriver());
76         setPromptForPassword(data.getPromptForPassword());
77         setAutoCommit(data.isAutoCommit());
78         setAutoCommitPreference(data.getAutoCommitPreference());
79         
80         this.schemas.addAll(data.schemas);
81         this.quickList = new Hashtable(data.quickList);
82         }
83
84         /**
85          * Returns the JDBC URL.
86          * @return String
87          */
88         public String getConnect() {
89                 return this.connectionUrl;
90         }
91
92         /**
93          * Returns the password.
94          * @return String
95          */
96         public String getPassword() {
97                 if (this.promptForPassword) {
98                         return null;
99                 } else {
100                         return this.password;
101                 }
102         }
103
104         /**
105          * Returns the username.
106          * @return String
107          */
108         public String getUsername() {
109                 return username;
110         }
111
112         /**
113          * Sets the connect.
114          * @param connectionUrl The connect to set
115          */
116         public void setConnect(String connectionUrl) {
117                 if (connectionUrl == null) {
118                         connectionUrl = ""; //$NON-NLS-1$
119                 }
120                 this.connectionUrl = connectionUrl;
121         }
122
123         /**
124          * Sets the password.
125          * @param password The password to set
126          */
127         public void setPassword(String password) {
128                 if (password == null) {
129                         password = ""; //$NON-NLS-1$
130                 }
131                 this.password = password;
132         }
133
134         /**
135          * Sets the username.
136          * @param username The username to set
137          */
138         public void setUsername(String username) {
139                 if (username == null) {
140                         username = ""; //$NON-NLS-1$
141                 }
142                 this.username = username;
143         }
144
145         /**
146          * Returns the name.
147          * @return String
148          */
149         public String getName() {
150                 return name;
151         }
152
153         /**
154          * Sets the name.
155          * @param name The name to set
156          */
157         public void setName(String name) {
158                 if (name == null) {
159                         name = ""; //$NON-NLS-1$
160                 }
161         if (!name.equals(this.name)) {
162          
163             String oldName = this.name;
164             this.name = name;
165             this.propertyChangeSupport.firePropertyChange("name", oldName, this.name);
166             this.changed = true;
167         }
168         }
169
170         public boolean isEmpty() {
171                 if (name.equals("") && //$NON-NLS-1$
172                 username.equals("") && //$NON-NLS-1$
173                 password.equals("") && //$NON-NLS-1$
174                 connectionUrl.equals("") && //$NON-NLS-1$
175                 driver.equals("") && //$NON-NLS-1$
176                 driver == null) {
177                         return true;
178                 }
179                 return false;
180         }
181         public String toString() {
182                 StringBuffer buffer = new StringBuffer();
183                 buffer.append("["); //$NON-NLS-1$
184                 buffer.append("name="); //$NON-NLS-1$
185                 buffer.append(name);
186                 buffer.append(", "); //$NON-NLS-1$
187                 buffer.append("username="); //$NON-NLS-1$
188                 buffer.append(username);
189                 buffer.append(", "); //$NON-NLS-1$
190                 buffer.append("password=****"); //$NON-NLS-1$
191                 buffer.append(", "); //$NON-NLS-1$
192                 buffer.append("connect="); //$NON-NLS-1$
193                 buffer.append(connectionUrl);
194                 buffer.append(", "); //$NON-NLS-1$
195                 buffer.append("driver="); //$NON-NLS-1$
196                 buffer.append(driver);
197                 buffer.append("]"); //$NON-NLS-1$
198                 return buffer.toString();
199         }
200         
201     public Connection connect(PasswordFinder passwordFinder) throws ConnectionException {
202         boolean isConnected = isConnected();
203         if (this.connection == null) {
204             this.connection = this.connectionEstablisher.connect(this, passwordFinder);
205         }
206         
207         if (isConnected() != isConnected) {
208             this.propertyChangeSupport.firePropertyChange(
209                 "connected", isConnected, isConnected());
210         }
211         return this.connection;
212     }
213
214     /**
215          * Returns the connection object. 
216          * @return the Connection object associated with the current JDBC source.
217          * 
218          */
219     public Connection getConnection() throws NotConnectedException {
220         if (this.connection == null) {
221             throw new NotConnectedException();
222         }
223         return this.connection;
224     }
225
226     /**
227          * @return true if the BookmarkNode is connected to a JDBC source
228          */
229     public boolean isConnected() {
230         return (connection != null);
231     }
232
233     /**
234          * Sets the connection member. From that moment on the BookmarkNode is "connected" (open)
235          * @param connection : a valid connection to a JDBC source
236          */
237     public void setConnection(Connection connection) {
238         this.connection = connection;
239     }
240
241     public void disconnect() throws ConnectionException {
242         boolean isConnected = isConnected();
243         try {
244             if (this.connection != null) {
245                 this.connectionEstablisher.disconnect(this.connection);
246             }
247         } finally {
248             this.connection = null;
249             if (isConnected() != isConnected) {
250                 this.propertyChangeSupport.firePropertyChange(
251                     "connected", isConnected, isConnected());
252             }
253         }
254     }
255     public void addSchema(String schema) {
256         if (schema != null && schema.trim().length() > 0) {
257             addSchema(new Schema(schema));
258         }
259     }
260
261     public void addSchema(Schema qualifier) {
262         if (qualifier != null) {
263             this.schemas.add(qualifier);
264             this.changed = true;
265             this.propertyChangeSupport.firePropertyChange("schemas", null, null);
266         }
267     }
268
269     public void setSchemaSelections(Schema[] schemas) {
270         this.schemas.clear();
271         for (int i = 0, length = (schemas == null) ? 0 : schemas.length;
272             i < length;
273             i++) {
274             this.schemas.add(schemas[i]);
275             
276         }
277         this.changed = true;
278         this.propertyChangeSupport.firePropertyChange("schemas", null, null);
279     }
280
281     /**
282      * @return a list of all the schemas that have been set up.
283      */
284     public Schema[] getSchemaSelections() {
285         List list = new ArrayList(this.schemas);
286         Collections.sort(list);
287         return (Schema[]) list.toArray(new Schema[list.size()]);
288     }
289     
290     public Schema[] getSchemas() throws NotConnectedException, SQLException {
291         Schema[] schemas = null;
292         if (useUsernameAsSchema()) {
293                 // do nothing
294         } else if (useAllSchemas()) {
295                 schemas = getDatabase().getSchemas();
296         } else {
297                 schemas = verifySchemas(getSchemaSelections());
298         }
299         return (schemas == null || schemas.length == 0) 
300                                 ? new Schema[] { getDefaultSchema() } 
301                         : schemas;
302     }
303
304         /**
305          * @param schemaSelections
306          * @return
307          * @throws SQLException
308          * @throws NotConnectedException
309          */
310         private Schema[] verifySchemas(Schema[] schemaSelections) 
311                         throws NotConnectedException, SQLException {
312                 Schema[] schemasFromDatabase = getDatabase().getSchemas();
313                 List list = Arrays.asList(schemasFromDatabase);
314                 for (int i = 0, length = schemaSelections == null ? 0 : schemaSelections.length; 
315                                 i < length; i++) {
316                         schemaSelections[i].setExists(list.contains(schemaSelections[i]));
317                 }
318                 return schemaSelections;
319         }
320
321         /**
322          * @return
323          * @throws NotConnectedException
324          * @throws SQLException
325          */
326         private Schema getDefaultSchema() throws NotConnectedException, SQLException {
327                 String username = getDatabase().getUsername();
328                 String actual = getAdapter().getDefaultSchema(username);
329                 return new Schema(actual, username, true);
330         }
331
332         /**
333          * @see java.lang.Object#equals(java.lang.Object)
334          */
335         public boolean equals(Object obj) {
336                 if (!(obj instanceof Bookmark)) return false;
337                 String name = ((Bookmark)obj).getName();
338                 if (name.equals(this.getName())) return true;
339                 return false;
340         }
341
342     /**
343      * @param listener
344      */
345     public synchronized void addPropertyChangeListener(PropertyChangeListener listener) {
346         this.propertyChangeSupport.addPropertyChangeListener(listener);
347     }
348
349     /**
350      * @param listener
351      */
352     public synchronized void removePropertyChangeListener(PropertyChangeListener listener) {
353         this.propertyChangeSupport.removePropertyChangeListener(listener);
354     }
355
356     public void addQuickListEntry(String type, String schemaName, String name) {
357         Entity entity = EntityFactory.getInstance().create(this, schemaName, name, type);
358         this.quickList.put(entity.getQualifiedName(), entity);
359         this.propertyChangeSupport.firePropertyChange("quickList", null, null);
360         this.changed = true;
361     }
362     
363     public void addQuickListEntry(Entity entity) {
364         addQuickListEntry(entity.getType(), entity.getSchema(), entity.getName());
365     }
366     
367     public void removeQuickListEntry(Entity entity) {
368         if (entity != null  && this.quickList.containsKey(entity.getQualifiedName())) {
369             this.quickList.remove(entity.getQualifiedName());
370             this.propertyChangeSupport.firePropertyChange("quickList", null, null);
371             this.changed = true;
372         }
373     }
374     
375     public Entity[] getQuickListEntries() {
376         return (Entity[]) this.quickList.values().toArray(new Entity[this.quickList.size()]);
377     }
378     
379     public boolean hasQuickList() {
380         return !this.quickList.isEmpty();
381     }
382     /**
383      * @return
384      */
385     public boolean isChanged() {
386         return changed;
387     }
388
389     /**
390      * @param b
391      */
392     public void setChanged(boolean b) {
393         changed = b;
394     }
395     
396     public Database getDatabase() throws NotConnectedException {
397         if (!isConnected()) {
398             throw new NotConnectedException();
399         }
400         return new Database(this);
401     }
402     
403     public DatabaseAdapter getAdapter() {
404         return this.driver == null 
405                                 ? null 
406                                 : AdapterFactory.getInstance().getAdapter(this.driver.getType());
407     }
408
409     public Entity[] getEntitiesForSchema(Schema schema, String type) throws SQLException {
410         try {
411             Entity[] entities = getDatabase().getEntities(this, schema, type);
412             return entities;
413         } catch (NotConnectedException e) {
414             return new Entity[0];
415         }
416     }
417     
418     public Entity getEntity(Schema schema, String name) throws SQLException {
419         Entity result = null;
420         if (schema != null && name != null) {
421             Entity[] entities = getEntitiesForSchema(schema, null);
422             for (int i = 0, length = (entities == null) ? 0 : entities.length;
423                 result == null && i < length;
424                 i++) {
425                 if (schema.equals(entities[i].getSchema()) &&
426                     name.equals(entities[i].getName())) {
427                     result = entities[i];
428                 }
429             }
430         }
431         return result;
432     }
433     
434     public boolean isInQuickList(Entity entity) {
435         return this.quickList.containsKey(entity.getQualifiedName());
436     }
437     
438     /**
439      * 
440      * @param queryString
441      */
442     public void addQuery(String queryString) {
443         if (this.queries.contains(queryString)) {
444             this.queries.remove(queryString);
445         }
446         this.queries.add(queryString);
447         
448         int size = getQueryHistorySize();
449         
450         while (this.queries.size() > size) {
451             this.queries.remove(0);
452         }
453         this.propertyChangeSupport.firePropertyChange("queries", null, null);
454         this.changed = true;
455     }
456     
457     public String[] getQueries() {
458         return (String[]) this.queries.toArray(new String[this.queries.size()]);
459     }
460     
461     private int getQueryHistorySize() {
462         IPreferenceStore store =
463             QuantumPlugin.getDefault().getPreferenceStore();
464         return store.getInt(getClass().getName() + ".queryHistorySize"); //$NON-NLS-1$
465     }
466     /**
467      * @return
468      */
469     public boolean getPromptForPassword() {
470         return promptForPassword;
471     }
472
473     /**
474      * @param b
475      */
476     public void setPromptForPassword(boolean b) {
477         promptForPassword = b;
478     }
479
480         /**
481          * @return
482          */
483         public boolean isAutoCommit() {
484                 return autoCommit;
485         }
486
487         /**
488          * @return
489          */
490         public String getAutoCommitPreference() {
491                 return autoCommitPreference;
492         }
493
494         /**
495          * @param b
496          */
497         public void setAutoCommit(boolean b) {
498                 autoCommit = b;
499         }
500
501         /**
502          * @param string
503          */
504         public void setAutoCommitPreference(String string) {
505                 autoCommitPreference = string;
506         }
507
508         // Returns true or false indicating whether this bookmark must be set to AutoCommit on connection or not 
509         public boolean getDefaultAutoCommit(){
510                 if (autoCommitPreference.equals(IQuantumConstants.autoCommitTrue)) return true;
511                 else if (autoCommitPreference.equals(IQuantumConstants.autoCommitFalse)) return false;
512                 else if (autoCommitPreference.equals(IQuantumConstants.autoCommitSaved)) return autoCommit;
513                 
514                 return true;    
515         }
516         
517         public void setJDBCDriver(JDBCDriver jdbcDriver) {
518                 this.driver = BookmarkCollection.getInstance().findDriver(jdbcDriver);
519         this.changed = true;
520         }
521         
522         public JDBCDriver getJDBCDriver() {
523                 return this.driver;
524         }
525         public boolean useAllSchemas() {
526                 return this.schemaRule == SCHEMA_RULE_USE_ALL;
527         }
528         public boolean useUsernameAsSchema() {
529                 return this.schemaRule == SCHEMA_RULE_USE_DEFAULT;
530         }
531         public boolean useSelectedSchemas() {
532                 return this.schemaRule == SCHEMA_RULE_USE_SELECTED;
533         }
534         public int getSchemaRule() {
535                 return this.schemaRule;
536         }
537         public void setSchemaRule(int schemaRule) {
538         if (this.schemaRule != schemaRule) {
539             this.schemaRule = schemaRule;
540             this.propertyChangeSupport.firePropertyChange("schemas", null, null);
541         }
542         }
543
544         public String getDisplayName() {
545                 return this.name;
546         }
547 }