web-dev-qa-db-ja.com

列およびテーブルごとの照合と文字セットの削除

最近、データベースのCHARSET=utf8 COLLATE=latin1からCHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ciへの移行を完了しました。プロセス中に、それぞれの文字セットと照合プロパティを変更することにより、テーブルが一度に1つずつ移行されました。

移行が完了し、すべてのサーバーとデータベース自体がutf8mb4とutf8mb4_unicode_ciを使用するように設定されたので、これらのプロパティを列とテーブルから削除して、サーバーに設定されているデフォルト値を継承するにはどうすればよいですか?

たとえば、現在、ほとんどの列のSHOW FULL COLUMNS FROM table;照合順序を実行すると、NULLではなくutf8mb4_unicode_ciに設定されます。

2
anthonyryan1

列の変換:

ALTER TABLE table_name MODIFY col_name VARCHAR(100) CHARACTER SET utf8;

テーブルの変換:

ALTER TABLE table_name CONVERT TO CHARACTER SET utf8;
1

プログラマーとして、データベースに「継承」があると想定するのは簡単です。値がnullの場合は、親を調べます。

継承はありません

テキストタイプの列にnull文字セットまたは照合順序を含めることはできません。各フィールドは、作成時に固定の文字セットと照合順序を持ちます。テーブルレベルまたはデータベースレベルで完全に異なる文字セットに変更し、既存の列の既存のデータが新しい文字セットを自動的に継承するとします。おそらく壊れているように見えます。

ここにいくつかのドキュメントがあります: https://dev.mysql.com/doc/refman/8.0/en/charset-table.html

MySQLは次の方法でテーブルの文字セットと照合を選択します。

CHARACTER SET charset_nameとCOLLATE collat​​ion_nameの両方が指定されている場合、文字セットcharset_nameと照合collat​​ion_nameが使用されます。

COLLATEなしでCHARACTER SET charset_nameを指定すると、文字セットcharset_nameとそのデフォルトの照合が使用されます。各文字セットのデフォルトの照合を表示するには、SHOW CHARACTER SETステートメントを使用するか、INFORMATION_SCHEMA CHARACTER_SETSテーブルをクエリします。

COLACT collat​​ion_nameがCHARACTER SETなしで指定されている場合、collat​​ion_nameおよびcollat​​ion collat​​ion_nameに関連付けられている文字セットが使用されます。

それ以外の場合(CHARACTER SETもCOLLATEも指定されていない場合)、データベースの文字セットと照合順序が使用されます。

明確にするために、文字セットと照合は列の作成時に選択されます。それらを変更する場合は、同時にデータも変換する必要があります。

0
Frank Forte

私のテストでは、列に設定されていない場合、SHOW FULL COLUMNSは常にテーブルの照合を結果に含めるように見えます。テキストタイプの列のみ。数値、日付などは照合順序がありません。

例の表には、照合がある1つの列があります。

CREATE TABLE `testCollationChanging` (
  `apiUserID` int(11) NOT NULL AUTO_INCREMENT,
  `name` varchar(128) NOT NULL,
  `email` varchar(128) COLLATE latin1_general_ci NULL,
  `apiKey` char(32) NOT NULL,
  `companyID` int(11) NOT NULL,
  `userID` int(11) NOT NULL,
  PRIMARY KEY (`apiUserID`),
  UNIQUE KEY `Duplicate name/company combo check` (`name`,`companyID`) USING BTREE,
  UNIQUE KEY `apiKey` (`apiKey`) USING BTREE
) ENGINE=InnoDB DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci;

SHOW FULL COLUMNS FROM `testCollationChanging`;

ALTER TABLE `testCollationChanging` CONVERT TO CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_520_ci;

SHOW FULL COLUMNS FROM `testCollationChanging`;

DROP TABLE `testCollationChanging`;

これは、次の2つの結果セットを示しています...

apiUserID   int(11)     NO  PRI     auto_increment  select,insert,update,references 
name    varchar(128)    latin1_swedish_ci   NO  MUL         select,insert,update,references 
email   varchar(128)    latin1_general_ci   YES             select,insert,update,references 
apiKey  char(32)    latin1_swedish_ci   NO  UNI         select,insert,update,references 
companyID   int(11)     NO              select,insert,update,references 
userID  int(11)     NO              select,insert,update,references 

そして

apiUserID   int(11)     NO  PRI     auto_increment  select,insert,update,references 
name    varchar(128)    utf8mb4_unicode_520_ci  NO  MUL         select,insert,update,references 
email   varchar(128)    utf8mb4_unicode_520_ci  YES             select,insert,update,references 
apiKey  char(32)    utf8mb4_unicode_520_ci  NO  UNI         select,insert,update,references 
companyID   int(11)     NO              select,insert,update,references 
userID  int(11)     NO              select,insert,update,references 

列の照合順序に一貫性がない場合は、それらも変換する必要があると思います。上記の例では、適切に変換されているようです。

組み込む...

SELECT * FROM information_schema.TABLES WHERE TABLE_NAME = 'testCollationChanging';
SELECT * FROM information_schema.COLUMNS WHERE TABLE_NAME = 'testCollationChanging';

結果には、情報スキーマが各列に対して照合を保持していることが示されています。

0