diff options
Diffstat (limited to 'Source')
-rw-r--r-- | Source/SPConstants.h | 1 | ||||
-rw-r--r-- | Source/SPConstants.m | 1 | ||||
-rw-r--r-- | Source/SPTableData.h | 2 | ||||
-rw-r--r-- | Source/SPTableData.m | 33 | ||||
-rw-r--r-- | Source/SPTableTriggers.h | 69 | ||||
-rw-r--r-- | Source/SPTableTriggers.m | 515 | ||||
-rw-r--r-- | Source/TableDocument.h | 1 | ||||
-rw-r--r-- | Source/TableDocument.m | 24 |
8 files changed, 646 insertions, 0 deletions
diff --git a/Source/SPConstants.h b/Source/SPConstants.h index 0c237e17..86753569 100644 --- a/Source/SPConstants.h +++ b/Source/SPConstants.h @@ -189,6 +189,7 @@ extern NSString *SPMainToolbarTableContent; extern NSString *SPMainToolbarCustomQuery; extern NSString *SPMainToolbarTableInfo; extern NSString *SPMainToolbarTableRelations; +extern NSString *SPMainToolbarTableTriggers; extern NSString *SPMainToolbarUserManager; // Preferences toolbar diff --git a/Source/SPConstants.m b/Source/SPConstants.m index 90fd0e2b..42859673 100644 --- a/Source/SPConstants.m +++ b/Source/SPConstants.m @@ -157,6 +157,7 @@ NSString *SPMainToolbarTableContent = @"SwitchToTableContentToolbar NSString *SPMainToolbarCustomQuery = @"SwitchToRunQueryToolbarItemIdentifier"; NSString *SPMainToolbarTableInfo = @"SwitchToTableInfoToolbarItemIdentifier"; NSString *SPMainToolbarTableRelations = @"SwitchToTableRelationsToolbarItemIdentifier"; +NSString *SPMainToolbarTableTriggers = @"SwitchToTableTriggersToolbarItemIdentifier"; NSString *SPMainToolbarUserManager = @"SwitchToUserManagerToolbarItemIdentifier"; // Preferences toolbar diff --git a/Source/SPTableData.h b/Source/SPTableData.h index c4e7495a..eb1ae6d4 100644 --- a/Source/SPTableData.h +++ b/Source/SPTableData.h @@ -33,6 +33,7 @@ NSMutableArray *columns; NSMutableArray *columnNames; NSMutableArray *constraints; + NSMutableArray *triggers; NSMutableDictionary *status; NSString *tableEncoding; @@ -49,6 +50,7 @@ - (NSArray *) columnNames; - (NSDictionary *) columnAtIndex:(NSInteger)index; - (NSArray *) getConstraints; +- (NSArray *) triggers; - (BOOL) columnIsBlobOrText:(NSString *)colName; - (NSString *) statusValueForKey:(NSString *)aKey; - (void)setStatusValue:(NSString *)value forKey:(NSString *)key; diff --git a/Source/SPTableData.m b/Source/SPTableData.m index a0a4d860..1c00758a 100644 --- a/Source/SPTableData.m +++ b/Source/SPTableData.m @@ -44,6 +44,7 @@ columnNames = [[NSMutableArray alloc] init]; constraints = [[NSMutableArray alloc] init]; status = [[NSMutableDictionary alloc] init]; + triggers = [[NSMutableArray alloc] init]; tableEncoding = nil; tableCreateSyntax = nil; @@ -117,6 +118,11 @@ return constraints; } +- (NSArray *) triggers +{ + return (NSArray *)triggers; +} + /* * Retrieve a column with a specified name, using or refreshing the cache as appropriate. */ @@ -558,6 +564,31 @@ [createTableParser release]; [fieldParser release]; + + // Triggers + theResult = [mySQLConnection queryString:[NSString stringWithFormat:@"/*!50003 SHOW TRIGGERS WHERE `Table` = %@ */;", + [tableName tickQuotedString]]]; + [theResult setReturnDataAsStrings:YES]; + + // Check for any errors, but only display them if a connection still exists + if (![[mySQLConnection getLastErrorMessage] isEqualToString:@""]) { + if ([mySQLConnection isConnected]) { + SPBeginAlertSheet(NSLocalizedString(@"Error retrieving table information", @"error retrieving table information message"), NSLocalizedString(@"OK", @"OK button"), + nil, nil, [NSApp mainWindow], self, nil, nil, nil, + [NSString stringWithFormat:NSLocalizedString(@"An error occurred while retrieving the information for table '%@'. Please try again.\n\nMySQL said: %@", @"error retrieving table information informative message"), + tableName, [mySQLConnection getLastErrorMessage]]); + } + + return nil; + } + + [triggers removeAllObjects]; + if( [theResult numOfRows] ) { + for(int i=0; i<[theResult numOfRows]; i++){ + [triggers addObject:[theResult fetchRowAsDictionary]]; + } + } + tableData = [NSMutableDictionary dictionary]; // this will be 'Table' or 'View' @@ -565,6 +596,7 @@ [tableData setObject:[NSString stringWithString:encodingString] forKey:@"encoding"]; [tableData setObject:[NSArray arrayWithArray:tableColumns] forKey:@"columns"]; [tableData setObject:[NSArray arrayWithArray:constraints] forKey:@"constraints"]; + [tableData setObject:[NSArray arrayWithArray:triggers] forKey:@"triggers"]; [encodingString release]; [tableColumns release]; @@ -1030,6 +1062,7 @@ [columns release]; [columnNames release]; [constraints release]; + [triggers release]; [status release]; if (tableEncoding) [tableEncoding release]; diff --git a/Source/SPTableTriggers.h b/Source/SPTableTriggers.h new file mode 100644 index 00000000..f0c1c7e1 --- /dev/null +++ b/Source/SPTableTriggers.h @@ -0,0 +1,69 @@ +// +// SPTableTriggers.h +// sequel-pro +// +// This program is free software; you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation; either version 2 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program; if not, write to the Free Software +// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +// +// More info at <http://code.google.com/p/sequel-pro/> + + +#import <Cocoa/Cocoa.h> +#import <MCPKit/MCPKit.h> + + +@interface SPTableTriggers : NSObject { + IBOutlet id tableDocumentInstance; + IBOutlet id tablesListInstance; + IBOutlet id tableDataInstance; + + IBOutlet id tableList; + IBOutlet id tableWindow; + + IBOutlet NSButton *addTriggerButton; + IBOutlet NSButton *removeTriggerButton; + IBOutlet NSButton *refreshTriggersButton; + IBOutlet NSTextField *labelTextField; + IBOutlet NSTableView *triggersTableView; + IBOutlet NSPanel *addTriggerPanel; + + IBOutlet NSBox *addTriggerTableBox; + IBOutlet NSPopUpButton *columnPopUpButton; + IBOutlet NSPopUpButton *refTablePopUpButton; + IBOutlet NSPopUpButton *refColumnPopUpButton; + IBOutlet NSPopUpButton *onUpdatePopUpButton; + IBOutlet NSPopUpButton *onDeletePopUpButton; + IBOutlet NSButton *confirmAddTriggerButton; + + MCPConnection *connection; + + NSMutableArray *triggerData; +} + +@property (readwrite, assign) MCPConnection *connection; + +// IB action methods +- (IBAction)addTrigger:(id)sender; +- (IBAction)removeTrigger:(id)sender; +- (IBAction)closeRelationSheet:(id)sender; +- (IBAction)confirmAddRelation:(id)sender; +- (IBAction)selectTableColumn:(id)sender; +- (IBAction)selectReferenceTable:(id)sender; +- (IBAction)refreshTriggers:(id)sender; + +// Task interaction +- (void)startDocumentTaskForTab:(NSNotification *)aNotification; +- (void)endDocumentTaskForTab:(NSNotification *)aNotification; + +@end diff --git a/Source/SPTableTriggers.m b/Source/SPTableTriggers.m new file mode 100644 index 00000000..6825f504 --- /dev/null +++ b/Source/SPTableTriggers.m @@ -0,0 +1,515 @@ +// +// SPTableTriggers.m +// sequel-pro +// +// This program is free software; you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation; either version 2 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program; if not, write to the Free Software +// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +// +// More info at <http://code.google.com/p/sequel-pro/> + +#import "SPTableTriggers.h" +#import "TableDocument.h" +#import "TablesList.h" +#import "SPTableData.h" +#import "SPStringAdditions.h" +#import "SPConstants.h" +#import "SPAlertSheets.h" + +@interface SPTableTriggers (PrivateAPI) + +- (void)_refreshRelationDataForcingCacheRefresh:(BOOL)clearAllCaches; +- (void)_updateAvailableTableColumns; + +@end + +@implementation SPTableTriggers + +@synthesize connection; + +/** + * init + */ +- (id)init +{ + if ((self = [super init])) { + triggerData = [[NSMutableArray alloc] init]; + } + + return self; +} + +/** + * Register to listen for table selection changes upon nib awakening. + */ +- (void)awakeFromNib +{ + // Set the table relation view's vertical gridlines if required + [triggersTableView setGridStyleMask:([[NSUserDefaults standardUserDefaults] boolForKey:SPDisplayTableViewVerticalGridlines]) ? NSTableViewSolidVerticalGridLineMask : NSTableViewGridNone]; + + // Set the strutcture and index view's font + BOOL useMonospacedFont = [[NSUserDefaults standardUserDefaults] boolForKey:SPUseMonospacedFonts]; + + for (NSTableColumn *column in [triggersTableView tableColumns]) + { + [[column dataCell] setFont:(useMonospacedFont) ? [NSFont fontWithName:SPDefaultMonospacedFontName size:[NSFont smallSystemFontSize]] : [NSFont systemFontOfSize:[NSFont smallSystemFontSize]]]; + } + + // Register as an observer for the when the UseMonospacedFonts preference changes + [[NSUserDefaults standardUserDefaults] addObserver:self forKeyPath:SPUseMonospacedFonts options:NSKeyValueObservingOptionNew context:NULL]; + + [[NSNotificationCenter defaultCenter] addObserver:self + selector:@selector(tableSelectionChanged:) + name:SPTableChangedNotification + object:tableDocumentInstance]; + + // Add observers for document task activity + [[NSNotificationCenter defaultCenter] addObserver:self + selector:@selector(startDocumentTaskForTab:) + name:SPDocumentTaskStartNotification + object:tableDocumentInstance]; + [[NSNotificationCenter defaultCenter] addObserver:self + selector:@selector(endDocumentTaskForTab:) + name:SPDocumentTaskEndNotification + object:tableDocumentInstance]; +} + +#pragma mark - +#pragma mark IB action methods + +/** + * Closes the relation sheet. + */ +- (IBAction)closeRelationSheet:(id)sender +{ + [NSApp endSheet:addTriggerPanel returnCode:0]; + [addTriggerPanel orderOut:self]; +} + +/** + * Add a new relation using the selected values. + */ +- (IBAction)confirmAddRelation:(id)sender +{ + [self closeRelationSheet:self]; + + NSString *thisTable = [tablesListInstance tableName]; + NSString *thisColumn = [columnPopUpButton titleOfSelectedItem]; + NSString *thatTable = [refTablePopUpButton titleOfSelectedItem]; + NSString *thatColumn = [refColumnPopUpButton titleOfSelectedItem]; + + NSString *query = [NSString stringWithFormat:@"ALTER TABLE %@ ADD FOREIGN KEY (%@) REFERENCES %@ (%@)", + [thisTable backtickQuotedString], + [thisColumn backtickQuotedString], + [thatTable backtickQuotedString], + [thatColumn backtickQuotedString]]; + + // If required add ON DELETE + if ([onDeletePopUpButton indexOfSelectedItem] > 0) { + query = [query stringByAppendingString:[NSString stringWithFormat:@" ON DELETE %@", [[onDeletePopUpButton titleOfSelectedItem] uppercaseString]]]; + } + + // If required add ON UPDATE + if ([onUpdatePopUpButton indexOfSelectedItem] > 0) { + query = [query stringByAppendingString:[NSString stringWithFormat:@" ON UPDATE %@", [[onUpdatePopUpButton titleOfSelectedItem] uppercaseString]]]; + } + + // Execute query + [connection queryString:query]; + + NSInteger retCode = (![[connection getLastErrorMessage] isEqualToString:@""]); + + // 0 indicates success + if (retCode) { + SPBeginAlertSheet(NSLocalizedString(@"Error creating relation", @"error creating relation message"), + NSLocalizedString(@"OK", @"OK button"), + nil, nil, [NSApp mainWindow], nil, nil, nil, nil, + [NSString stringWithFormat:NSLocalizedString(@"The specified relation was unable to be created.\n\nMySQL said: %@", @"error creating relation informative message"), [connection getLastErrorMessage]]); + } + else { + [self _refreshRelationDataForcingCacheRefresh:YES]; + } +} + +/** + * Updates the available columns when the user selects a table. + */ +- (IBAction)selectTableColumn:(id)sender +{ + [self _updateAvailableTableColumns]; +} + +/** + * Updates the available columns when the user selects a table. + */ +- (IBAction)selectReferenceTable:(id)sender +{ + [self _updateAvailableTableColumns]; +} + +/** + * Called whenever the user selected to add a new trigger. + */ +- (IBAction)addTrigger:(id)sender +{ + // Set up the controls + [addTriggerTableBox setTitle:[NSString stringWithFormat:@"Table: %@", [tablesListInstance tableName]]]; + + [columnPopUpButton removeAllItems]; + [columnPopUpButton addItemsWithTitles:[tableDataInstance columnNames]]; + + [refTablePopUpButton removeAllItems]; + + // Get all InnoDB tables in the current database + MCPResult *result = [connection queryString:[NSString stringWithFormat:@"SELECT table_name FROM information_schema.tables WHERE table_type = 'BASE TABLE' AND engine = 'InnoDB' AND table_schema = %@", [[tableDocumentInstance database] tickQuotedString]]]; + + [result dataSeek:0]; + + for (NSInteger i = 0; i < [result numOfRows]; i++) + { + [refTablePopUpButton addItemWithTitle:[[result fetchRowAsArray] objectAtIndex:0]]; + } + + [self selectReferenceTable:nil]; + + [NSApp beginSheet:addTriggerPanel + modalForWindow:tableWindow + modalDelegate:self + didEndSelector:nil + contextInfo:nil]; +} + +/** + * Removes the selected trigger. + */ +- (IBAction)removeTrigger:(id)sender +{ + if ([triggersTableView numberOfSelectedRows] > 0) { + + NSAlert *alert = [NSAlert alertWithMessageText:NSLocalizedString(@"Delete relation", @"delete relation message") + defaultButton:NSLocalizedString(@"Delete", @"delete button") + alternateButton:NSLocalizedString(@"Cancel", @"cancel button") + otherButton:nil + informativeTextWithFormat:NSLocalizedString(@"Are you sure you want to delete the selected relations? This action cannot be undone.", @"delete selected relation informative message")]; + + [alert setAlertStyle:NSCriticalAlertStyle]; + + NSArray *buttons = [alert buttons]; + + // Change the alert's cancel button to have the key equivalent of return + [[buttons objectAtIndex:0] setKeyEquivalent:@"d"]; + [[buttons objectAtIndex:0] setKeyEquivalentModifierMask:NSCommandKeyMask]; + [[buttons objectAtIndex:1] setKeyEquivalent:@"\r"]; + + [alert beginSheetModalForWindow:tableWindow modalDelegate:self didEndSelector:@selector(alertDidEnd:returnCode:contextInfo:) contextInfo:@"removeRelation"]; + } +} + +/** + * Trigger a refresh of the displayed relations via the interface. + */ +- (IBAction)refreshTriggers:(id)sender +{ + [self _refreshRelationDataForcingCacheRefresh:YES]; +} + +/** + * Called whenever the user selects a different table. + */ +- (void)tableSelectionChanged:(NSNotification *)notification +{ + BOOL enableInteraction = ![[tableDocumentInstance selectedToolbarItemIdentifier] isEqualToString:SPMainToolbarTableRelations] || ![tableDocumentInstance isWorking]; + + // To begin enable all interface elements + [addTriggerButton setEnabled:enableInteraction]; + [refreshTriggersButton setEnabled:enableInteraction]; + [triggersTableView setEnabled:YES]; + + // Get the current table's storage engine + NSString *engine = [tableDataInstance statusValueForKey:@"Engine"]; + + if (([tablesListInstance tableType] == SP_TABLETYPE_TABLE) && ([[engine lowercaseString] isEqualToString:@"innodb"])) { + + // Update the text label + [labelTextField setStringValue:[NSString stringWithFormat:@"Relations for table: %@", [tablesListInstance tableName]]]; + + [addTriggerButton setEnabled:enableInteraction]; + [refreshTriggersButton setEnabled:enableInteraction]; + [triggersTableView setEnabled:YES]; + } + else { + [addTriggerButton setEnabled:NO]; + [refreshTriggersButton setEnabled:NO]; + [triggersTableView setEnabled:NO]; + + [labelTextField setStringValue:([tablesListInstance tableType] == SP_TABLETYPE_TABLE) ? @"This table currently does not support relations. Only tables that use the InnoDB storage engine support them." : @""]; + } + + [self _refreshRelationDataForcingCacheRefresh:NO]; +} + +#pragma mark - +#pragma mark Tableview datasource methods + +- (NSInteger)numberOfRowsInTableView:(NSTableView *)tableView +{ + return [triggerData count]; +} + +- (id)tableView:(NSTableView *)tableView objectValueForTableColumn:(NSTableColumn *)tableColumn row:(NSInteger)rowIndex +{ + return [[triggerData objectAtIndex:rowIndex] objectForKey:[tableColumn identifier]]; +} + +#pragma mark - +#pragma mark Tableview delegate methods + +/** + * Called whenever the relations table view selection changes. + */ +- (void)tableViewSelectionDidChange:(NSNotification *)notification +{ + [removeTriggerButton setEnabled:([triggersTableView numberOfSelectedRows] > 0)]; +} + +/* + * Double-click action on table cells - for the time being, return + * NO to disable editing. + */ +- (BOOL)tableView:(NSTableView *)aTableView shouldEditTableColumn:(NSTableColumn *)aTableColumn row:(NSInteger)rowIndex +{ + if ([tableDocumentInstance isWorking]) return NO; + + return NO; +} + +/** + * Disable row selection while the document is working. + */ +- (BOOL)tableView:(NSTableView *)aTableView shouldSelectRow:(NSInteger)rowIndex +{ + return ![tableDocumentInstance isWorking]; +} + +#pragma mark - +#pragma mark Task interaction + +/** + * Disable all content interactive elements during an ongoing task. + */ +- (void)startDocumentTaskForTab:(NSNotification *)aNotification +{ + + // Only proceed if this view is selected. + if (![[tableDocumentInstance selectedToolbarItemIdentifier] isEqualToString:SPMainToolbarTableRelations]) + return; + + [addTriggerButton setEnabled:NO]; + [refreshTriggersButton setEnabled:NO]; + [removeTriggerButton setEnabled:NO]; +} + +/** + * Enable all content interactive elements after an ongoing task. + */ +- (void)endDocumentTaskForTab:(NSNotification *)aNotification +{ + + // Only proceed if this view is selected. + if (![[tableDocumentInstance selectedToolbarItemIdentifier] isEqualToString:SPMainToolbarTableRelations]) + return; + + if ([triggersTableView isEnabled]) { + [addTriggerButton setEnabled:YES]; + [refreshTriggersButton setEnabled:YES]; + } + [removeTriggerButton setEnabled:([triggersTableView numberOfSelectedRows] > 0)]; +} + +#pragma mark - +#pragma mark Other + +/** + * NSAlert didEnd method. + */ +- (void)alertDidEnd:(NSAlert *)alert returnCode:(NSInteger)returnCode contextInfo:(NSString *)contextInfo +{ + if ([contextInfo isEqualToString:@"removeRelation"]) { + + if (returnCode == NSAlertDefaultReturn) { + + NSString *thisTable = [tablesListInstance tableName]; + NSIndexSet *selectedSet = [triggersTableView selectedRowIndexes]; + + NSUInteger row = [selectedSet lastIndex]; + + while (row != NSNotFound) + { + NSString *relationName = [[triggerData objectAtIndex:row] objectForKey:@"name"]; + NSString *query = [NSString stringWithFormat:@"ALTER TABLE %@ DROP FOREIGN KEY %@", [thisTable backtickQuotedString], [relationName backtickQuotedString]]; + + [connection queryString:query]; + + if (![[connection getLastErrorMessage] isEqualToString:@""] ) { + + SPBeginAlertSheet(NSLocalizedString(@"Unable to remove relation", @"error removing relation message"), + NSLocalizedString(@"OK", @"OK button"), + nil, nil, [NSApp mainWindow], nil, nil, nil, nil, + [NSString stringWithFormat:NSLocalizedString(@"The selected relation couldn't be removed.\n\nMySQL said: %@", @"error removing relation informative message"), [connection getLastErrorMessage]]); + + // Abort loop + break; + } + + row = [selectedSet indexLessThanIndex:row]; + } + + [self _refreshRelationDataForcingCacheRefresh:YES]; + } + } +} + +/** + * This method is called as part of Key Value Observing which is used to watch for prefernce changes which effect the interface. + */ +- (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context +{ + // Display table veiew vertical gridlines preference changed + if ([keyPath isEqualToString:SPDisplayTableViewVerticalGridlines]) { + [triggersTableView setGridStyleMask:([[change objectForKey:NSKeyValueChangeNewKey] boolValue]) ? NSTableViewSolidVerticalGridLineMask : NSTableViewGridNone]; + } + // Use monospaced fonts preference changed + else if ([keyPath isEqualToString:SPUseMonospacedFonts]) { + + BOOL useMonospacedFont = [[change objectForKey:NSKeyValueChangeNewKey] boolValue]; + + for (NSTableColumn *column in [triggersTableView tableColumns]) + { + [[column dataCell] setFont:(useMonospacedFont) ? [NSFont fontWithName:SPDefaultMonospacedFontName size:[NSFont smallSystemFontSize]] : [NSFont systemFontOfSize:[NSFont smallSystemFontSize]]]; + } + + [triggersTableView reloadData]; + } +} + +/** + * Menu validation + */ +- (BOOL)validateMenuItem:(NSMenuItem *)menuItem +{ + // Remove row + if ([menuItem action] == @selector(removeRelation:)) { + [menuItem setTitle:([triggersTableView numberOfSelectedRows] > 1) ? @"Delete Relations" : @"Delete Relation"]; + + return ([triggersTableView numberOfSelectedRows] > 0); + } + + return YES; +} + +#pragma mark - + +/* + * Dealloc. + */ +- (void)dealloc +{ + [triggerData release], triggerData = nil; + [[NSNotificationCenter defaultCenter] removeObserver:self]; + + [super dealloc]; +} + +@end + +@implementation SPTableTriggers (PrivateAPI) + +/** + * Refresh the displayed relations, optionally forcing a refresh of the underlying cache. + */ +- (void)_refreshRelationDataForcingCacheRefresh:(BOOL)clearAllCaches +{ + [triggerData removeAllObjects]; + + if ([tablesListInstance tableType] == SP_TABLETYPE_TABLE) { + + if (clearAllCaches) [tableDataInstance updateInformationForCurrentTable]; + + NSArray *triggers = [tableDataInstance triggers]; + + for (NSDictionary *trigger in triggers) + { + [triggerData addObject:[NSDictionary dictionaryWithObjectsAndKeys: + [trigger objectForKey:@"Table"], @"table", + [trigger objectForKey:@"Trigger"], @"trigger", + [trigger objectForKey:@"Event"], @"event", + [trigger objectForKey:@"Timing"], @"timing", + [trigger objectForKey:@"Statement"], @"statement", + [trigger objectForKey:@"Definer"], @"definer", + [trigger objectForKey:@"Created"], @"created", + [trigger objectForKey:@"sql_mode"], @"sql_mode", + nil]]; + + } + // NSLog(@"Triggers: %@", triggers); + } + + [triggersTableView reloadData]; +} + +/** + * Updates the available table columns that the reference is pointing to. Available columns are those that are + * within the selected table and are of the same data type as the column the reference is from. + */ +- (void)_updateAvailableTableColumns +{ + NSString *column = [columnPopUpButton titleOfSelectedItem]; + NSString *table = [refTablePopUpButton titleOfSelectedItem]; + + [tableDataInstance resetAllData]; + [tableDataInstance updateInformationForCurrentTable]; + + NSDictionary *columnInfo = [[tableDataInstance columnWithName:column] copy]; + + [refColumnPopUpButton setEnabled:NO]; + [confirmAddTriggerButton setEnabled:NO]; + + [refColumnPopUpButton removeAllItems]; + + [tableDataInstance resetAllData]; + NSDictionary *tableInfo = [tableDataInstance informationForTable:table]; + + NSArray *columns = [tableInfo objectForKey:@"columns"]; + + NSMutableArray *validColumns = [NSMutableArray array]; + + // Only add columns of the same data type + for (NSDictionary *column in columns) + { + if ([[columnInfo objectForKey:@"type"] isEqualToString:[column objectForKey:@"type"]]) { + [validColumns addObject:[column objectForKey:@"name"]]; + } + } + + // Add the valid columns + if ([validColumns count] > 0) { + [refColumnPopUpButton addItemsWithTitles:validColumns]; + + [refColumnPopUpButton setEnabled:YES]; + [confirmAddTriggerButton setEnabled:YES]; + } + + [columnInfo release]; +} + +@end diff --git a/Source/TableDocument.h b/Source/TableDocument.h index bfc6ef39..d8122d4a 100644 --- a/Source/TableDocument.h +++ b/Source/TableDocument.h @@ -266,6 +266,7 @@ - (IBAction)viewQuery:(id)sender; - (IBAction)viewStatus:(id)sender; - (IBAction)viewRelations:(id)sender; +- (IBAction)viewTriggers:(id)sender; - (IBAction)addConnectionToFavorites:(id)sender; // Titlebar methods diff --git a/Source/TableDocument.m b/Source/TableDocument.m index 368d9f94..c8834af3 100644 --- a/Source/TableDocument.m +++ b/Source/TableDocument.m @@ -3077,6 +3077,30 @@ [prefs setInteger:SPRelationsViewMode forKey:SPLastViewMode]; } +- (IBAction)viewTriggers:(id)sender +{ + // Cancel the selection if currently editing structure/a field and unable to save + if ([tableTabView indexOfTabViewItem:[tableTabView selectedTabViewItem]] == 0 + && ![tableSourceInstance saveRowOnDeselect]) { + [mainToolbar setSelectedItemIdentifier:SPMainToolbarTableStructure]; + return; + } + + // Cancel the selection if currently editing a content row and unable to save + if ([tableTabView indexOfTabViewItem:[tableTabView selectedTabViewItem]] == 1 + && ![tableContentInstance saveRowOnDeselect]) { + [mainToolbar setSelectedItemIdentifier:SPMainToolbarTableContent]; + return; + } + + + [tableTabView selectTabViewItemAtIndex:5]; + [mainToolbar setSelectedItemIdentifier:SPMainToolbarTableTriggers]; + [spHistoryControllerInstance updateHistoryEntries]; + + //[prefs setInteger:SPRelationsViewMode forKey:SPLastViewMode]; +} + /** * Adds the current database connection details to the user's favorites if it doesn't already exist. |