From 40908f1bef9eed4bdd43533a4bfafd326d00e655 Mon Sep 17 00:00:00 2001 From: Ansgar Becker Date: Sat, 15 Feb 2020 12:51:08 +0100 Subject: [PATCH] Issue #885: Move types of table keys from global scope constants to class constants in TTableKey definition, to make them stable against mix-ups --- source/const.inc | 7 +------ source/dbconnection.pas | 40 +++++++++++++++++++++++----------------- source/table_editor.pas | 38 +++++++++++++++++++------------------- 3 files changed, 43 insertions(+), 42 deletions(-) diff --git a/source/const.inc b/source/const.inc index d6763e3e..08dcfc49 100644 --- a/source/const.inc +++ b/source/const.inc @@ -2,6 +2,7 @@ const // Line breaks + // TODO: use sLineBreak instead CRLF = #13#10; LB_UNIX = #10; LB_MAC = #13; @@ -102,12 +103,6 @@ const MsgInvalidColumn: String = 'Column #%d not available. Query returned %d columns and %d rows.'; SPortableLockFile: String = 'portable.lock'; - PKEY = 'PRIMARY'; - KEY = 'KEY'; - UKEY = 'UNIQUE'; - FKEY = 'FULLTEXT'; - SKEY = 'SPATIAL'; - SYNCOMPLETION_PATTERN = '\image{%d}\hspace{5}\color{clGrayText}%s\column{}\color{clWindowText}%s\color{clGrayText}%s'; HELPERNODE_COLUMNS = 0; diff --git a/source/dbconnection.pas b/source/dbconnection.pas index ffd23c97..055d9c27 100644 --- a/source/dbconnection.pas +++ b/source/dbconnection.pas @@ -62,6 +62,12 @@ type end; TTableKey = class(TPersistent) + const + PRIMARY = 'PRIMARY'; + KEY = 'KEY'; + UNIQUE = 'UNIQUE'; + FULLTEXT = 'FULLTEXT'; + SPATIAL = 'SPATIAL'; private FConnection: TDBConnection; function GetImageIndex: Integer; @@ -4821,7 +4827,7 @@ begin NewKey.Name := KeyQuery.Col('CONSTRAINT_NAME'); NewKey.OldName := NewKey.Name; if KeyQuery.Col('CONSTRAINT_TYPE').ToLowerInvariant.StartsWith('primary') then - NewKey.IndexType := 'PRIMARY' + NewKey.IndexType := TTableKey.PRIMARY else NewKey.IndexType := KeyQuery.Col('CONSTRAINT_TYPE'); NewKey.OldIndexType := NewKey.IndexType; @@ -4850,13 +4856,13 @@ begin NewKey.Name := KeyQuery.Col('Key_name'); NewKey.OldName := NewKey.Name; if NewKey.Name.ToLowerInvariant = 'primary' then - NewKey.IndexType := 'PRIMARY' + NewKey.IndexType := TTableKey.PRIMARY else if KeyQuery.Col('Non_unique') = '0' then - NewKey.IndexType := 'UNIQUE' + NewKey.IndexType := TTableKey.UNIQUE else if KeyQuery.Col('Index_type').ToLowerInvariant = 'fulltext' then - NewKey.IndexType := 'FULLTEXT' + NewKey.IndexType := TTableKey.FULLTEXT else - NewKey.IndexType := 'KEY'; + NewKey.IndexType := TTableKey.KEY; // Todo: spatial keys NewKey.OldIndexType := NewKey.IndexType; if ExecRegExpr('(BTREE|HASH)', KeyQuery.Col('Index_type')) then @@ -4888,7 +4894,7 @@ begin ' ),'+ ' ndx_cols AS ('+ ' SELECT pg_class.relname, UNNEST(i.indkey) AS col_ndx,'+ - ' CASE i.indisprimary WHEN true THEN '+EscapeString('PRIMARY')+' ELSE CASE i.indisunique WHEN true THEN '+EscapeString('UNIQUE')+' ELSE '+EscapeString('KEY')+' END END AS CONSTRAINT_TYPE,'+ + ' CASE i.indisprimary WHEN true THEN '+EscapeString(TTableKey.PRIMARY)+' ELSE CASE i.indisunique WHEN true THEN '+EscapeString(TTableKey.UNIQUE)+' ELSE '+EscapeString(TTableKey.KEY)+' END END AS CONSTRAINT_TYPE,'+ ' pg_class.oid'+ ' FROM pg_class'+ ' JOIN pg_index i ON (pg_class.oid = i.indexrelid)'+ @@ -4954,7 +4960,7 @@ begin Result.Add(NewKey); NewKey.Name := 'PRIMARY'; NewKey.OldName := NewKey.Name; - NewKey.IndexType := 'PRIMARY'; + NewKey.IndexType := TTableKey.PRIMARY; NewKey.OldIndexType := NewKey.IndexType; end; NewKey.Columns.Add(ColQuery.Col('name')); @@ -4969,7 +4975,7 @@ begin Result.Add(NewKey); NewKey.Name := KeyQuery.Col('name'); NewKey.OldName := NewKey.Name; - NewKey.IndexType := IfThen(KeyQuery.Col('unique')='0', 'KEY', 'UNIQUE'); + NewKey.IndexType := IfThen(KeyQuery.Col('unique')='0', TTableKey.KEY, TTableKey.UNIQUE); NewKey.OldIndexType := NewKey.IndexType; ColQuery := GetResults('SELECT * FROM pragma_index_info('+EscapeString(NewKey.Name)+')'); while not ColQuery.Eof do begin @@ -5948,13 +5954,13 @@ begin // Find best key for updates // 1. round: find a primary key for Key in Keys do begin - if Key.IndexType = PKEY then + if Key.IndexType = TTableKey.PRIMARY then Result.Assign(Key.Columns); end; if Result.Count = 0 then begin // no primary key available -> 2. round: find a unique key for Key in Keys do begin - if Key.IndexType = UKEY then begin + if Key.IndexType = TTableKey.UNIQUE then begin // We found a UNIQUE key - better than nothing. Check if one of the key // columns allows NULLs which makes it dangerous to use in UPDATES + DELETES. AllowsNull := False; @@ -8906,11 +8912,11 @@ end; function TTableKey.GetImageIndex: Integer; begin // Detect key icon index for specified index - if IndexType = PKEY then Result := ICONINDEX_PRIMARYKEY - else if IndexType = KEY then Result := ICONINDEX_INDEXKEY - else if IndexType = UKEY then Result := ICONINDEX_UNIQUEKEY - else if IndexType = FKEY then Result := ICONINDEX_FULLTEXTKEY - else if IndexType = SKEY then Result := ICONINDEX_SPATIALKEY + if IndexType = TTableKey.PRIMARY then Result := ICONINDEX_PRIMARYKEY + else if IndexType = TTableKey.KEY then Result := ICONINDEX_INDEXKEY + else if IndexType = TTableKey.UNIQUE then Result := ICONINDEX_UNIQUEKEY + else if IndexType = TTableKey.FULLTEXT then Result := ICONINDEX_FULLTEXTKEY + else if IndexType = TTableKey.SPATIAL then Result := ICONINDEX_SPATIALKEY else Result := -1; end; @@ -8922,10 +8928,10 @@ begin // Supress SQL error trying index creation with 0 column if Columns.Count = 0 then Exit; - if IndexType = PKEY then + if IndexType = TTableKey.PRIMARY then Result := Result + 'PRIMARY KEY ' else begin - if IndexType <> KEY then + if IndexType <> TTableKey.KEY then Result := Result + IndexType + ' '; Result := Result + 'INDEX ' + FConnection.QuoteIdent(Name) + ' '; end; diff --git a/source/table_editor.pas b/source/table_editor.pas index e11b9866..14cf3c2c 100644 --- a/source/table_editor.pas +++ b/source/table_editor.pas @@ -700,7 +700,7 @@ begin // Drop indexes, also changed indexes, which will be readded below for i:=0 to DeletedKeys.Count-1 do begin Mainform.ProgressStep; - if DeletedKeys[i] = PKEY then + if DeletedKeys[i] = TTableKey.PRIMARY then IndexSQL := 'PRIMARY KEY' else IndexSQL := 'INDEX ' + Conn.QuoteIdent(DeletedKeys[i]); @@ -710,7 +710,7 @@ begin for i:=0 to FKeys.Count-1 do begin Mainform.ProgressStep; if FKeys[i].Modified and (not FKeys[i].Added) then begin - if FKeys[i].OldIndexType = PKEY then + if FKeys[i].OldIndexType = TTableKey.PRIMARY then IndexSQL := 'PRIMARY KEY' else IndexSQL := 'INDEX ' + Conn.QuoteIdent(FKeys[i].OldName); @@ -1139,7 +1139,7 @@ begin // Do not allow NULL, and force NOT NULL, on primary key columns Result := True; for i:=0 to FKeys.Count-1 do begin - if (FKeys[i].IndexType = PKEY) and (FKeys[i].Columns.IndexOf(Col.Name) > -1) then begin + if (FKeys[i].IndexType = TTableKey.PRIMARY) and (FKeys[i].Columns.IndexOf(Col.Name) > -1) then begin if Col.AllowNull then begin Col.AllowNull := False; Col.Status := esModified; @@ -1236,7 +1236,7 @@ begin Col := Sender.GetNodeData(Node); // Bold font for primary key columns for i:=0 to FKeys.Count-1 do begin - if (FKeys[i].IndexType = PKEY) and (FKeys[i].Columns.IndexOf(Col.Name) > -1) then begin + if (FKeys[i].IndexType = TTableKey.PRIMARY) and (FKeys[i].Columns.IndexOf(Col.Name) > -1) then begin TargetCanvas.Font.Style := TargetCanvas.Font.Style + [fsBold]; break; end; @@ -1535,7 +1535,7 @@ begin TblKey := TTableKey.Create(DBObject.Connection); TblKey.Name := _('Index')+' '+IntToStr(FKeys.Count+1); TblKey.OldName := TblKey.Name; - TblKey.IndexType := KEY; + TblKey.IndexType := TTableKey.KEY; TblKey.OldIndexType := TblKey.IndexType; TblKey.Added := True; FKeys.Add(TblKey); @@ -1576,7 +1576,7 @@ begin end; if not ColExists then begin NewCol := Column.Name; - if (TblKey.IndexType <> FKEY) and (Column.DataType.Index in [dtTinyText, dtText, dtMediumText, dtLongText, dtTinyBlob, dtBlob, dtMediumBlob, dtLongBlob]) then + if (TblKey.IndexType <> TTableKey.FULLTEXT) and (Column.DataType.Index in [dtTinyText, dtText, dtMediumText, dtLongText, dtTinyBlob, dtBlob, dtMediumBlob, dtLongBlob]) then PartLength := '100'; break; end; @@ -1672,7 +1672,7 @@ begin 0: begin TblKey := FKeys[Node.Index]; case Column of - 0: if TblKey.IndexType = PKEY then + 0: if TblKey.IndexType = TTableKey.PRIMARY then CellText := TblKey.IndexType + ' KEY' // Fixed name "PRIMARY KEY", cannot be changed else CellText := TblKey.Name; @@ -1766,7 +1766,7 @@ begin Allowed := False; if VT.GetNodeLevel(Node) = 0 then begin // Disallow renaming primary key - if (Column <> 0) or (VT.Text[Node, 1] <> PKEY) then + if (Column <> 0) or (VT.Text[Node, 1] <> TTableKey.PRIMARY) then Allowed := True end else case Column of 0: Allowed := True; @@ -1800,7 +1800,7 @@ begin // Index type pulldown EnumEditor := TEnumEditorLink.Create(VT, True); EnumEditor.ValueList := TStringList.Create; - EnumEditor.ValueList.CommaText := PKEY +','+ KEY +','+ UKEY +','+ FKEY +','+ SKEY; + EnumEditor.ValueList.CommaText := TTableKey.PRIMARY +','+ TTableKey.KEY +','+ TTableKey.UNIQUE +','+ TTableKey.FULLTEXT +','+ TTableKey.SPATIAL; EditLink := EnumEditor; end else if (Level = 0) and (Column = 2) then begin // Algorithm pulldown @@ -1839,8 +1839,8 @@ begin 0: TblKey.Name := NewText; 1: begin TblKey.IndexType := NewText; - if NewText = PKEY then - TblKey.Name := PKEY; + if NewText = TTableKey.PRIMARY then + TblKey.Name := TTableKey.PRIMARY; end; 2: TblKey.Algorithm := NewText; end; @@ -1968,7 +1968,7 @@ begin TblKey.Columns.Insert(ColPos, ColName); PartLength := ''; - if (TblKey.IndexType <> FKEY) and (Col.DataType.Index in [dtTinyText, dtText, dtMediumText, dtLongText, dtTinyBlob, dtBlob, dtMediumBlob, dtLongBlob]) then + if (TblKey.IndexType <> TTableKey.FULLTEXT) and (Col.DataType.Index in [dtTinyText, dtText, dtMediumText, dtLongText, dtTinyBlob, dtBlob, dtMediumBlob, dtLongBlob]) then PartLength := '100'; TblKey.Subparts.Insert(ColPos, PartLength); IndexNode.States := IndexNode.States + [vsHasChildren, vsExpanded]; @@ -2096,9 +2096,9 @@ begin // Auto create submenu items for "Add to index" ... PrimaryKeyExists := False; for i:=0 to FKeys.Count-1 do begin - if FKeys[i].IndexType = PKEY then begin + if FKeys[i].IndexType = TTableKey.PRIMARY then begin PrimaryKeyExists := True; - IndexName := PKEY; + IndexName := TTableKey.PRIMARY; end else IndexName := FKeys[i].Name + ' ('+FKeys[i].IndexType+')'; Item := AddItem(menuAddToIndex, IndexName, FKeys[i].ImageIndex); @@ -2118,12 +2118,12 @@ begin menuAddToIndex.Enabled := menuAddToIndex.Count > 0; // ... and for item "Create index" - Item := AddItem(menuCreateIndex, PKEY, ICONINDEX_PRIMARYKEY); + Item := AddItem(menuCreateIndex, TTableKey.PRIMARY, ICONINDEX_PRIMARYKEY); Item.Enabled := not PrimaryKeyExists; - AddItem(menuCreateIndex, KEY, ICONINDEX_INDEXKEY); - AddItem(menuCreateIndex, UKEY, ICONINDEX_UNIQUEKEY); - AddItem(menuCreateIndex, FKEY, ICONINDEX_FULLTEXTKEY); - AddItem(menuCreateIndex, SKEY, ICONINDEX_SPATIALKEY); + AddItem(menuCreateIndex, TTableKey.KEY, ICONINDEX_INDEXKEY); + AddItem(menuCreateIndex, TTableKey.UNIQUE, ICONINDEX_UNIQUEKEY); + AddItem(menuCreateIndex, TTableKey.FULLTEXT, ICONINDEX_FULLTEXTKEY); + AddItem(menuCreateIndex, TTableKey.SPATIAL, ICONINDEX_SPATIALKEY); end;