MySQL on Ubuntu Case Sensitivity Issues - mysql

DB was designed for SQL Server initially. Back then all table names were mixed case. For example, UserTasks.
Hundreds of stored procedures were written on these tables and those stored procedures use mixed case table names.
DB was migrated to MySQL (on Windows) and during that process table names were automatically converted to all lower case but code inside stored procedures was converted to MySQL format without changing the table name cases.
We just migrated to Ubuntu and everything stopped working because MySQL can no longer find those tables used in SQL statements in stored procedures.
Is there a easy way around this? I know the hard way. Open each one of those 550 stored procedures and change table names to lower case one by one.

You should read https://dev.mysql.com/doc/refman/5.7/en/identifier-case-sensitivity.html
Case sensitivity of table names is a complex story on MySQL, because it works on all types of environments: Windows, which is case-insensitive, Unix and Linux, which is case-sensitive, and also MacOS which is sort of a hybrid.
You might be able to use the lower_case_table_names option. I can't be sure, because I don't use that option myself, I don't use Windows, and I seldom use MySQL stored procedures, so I'm not sure how this will interact with the procedure code.
Good luck!

Related

Any reason not to put stored procs independent of specific database in mysql's mysql database?

I've never wanted to touch the database actually named "mysql" (the one with tables proc, slow_log, user, etc) unless doing something officially supported with it. By this, I mean I wouldn't create new tables in it, etc.
But, if I'm creating a few stored procedures that operate on any database and aren't specific to a single one, is it appropriate to store those to the "mysql" database, or would it be better to create a "genericStoredProcs" database to put them in that had no tables?
I would not recommend adding any objects to the mysql database.
It might be possible to do that, and it might be supported. But I wouldn't take that risk. That's just asking for trouble. Just let the mysql database be what it's supposed to be, let it do what it's supposed to do, and don't muck with it.
If you need a database to store "shared" objects, then create a new database, and grant appropriate privileges.

mysql stored procedure does not find table due to Case

I'm currently moving my project to production and found an odd situation. The database was (unfortunately) created with object names in lowercase. Now, I'm acting on table all over my 100+ stored procedures/functions, not always keeping in mind the fact that I should use lowercase for table names.
I made a simple test:
select * from mytable ;
yields all the records in the table, whereas:
select * from Mytable ;
returns a "table does not exist" error.
Is there any solution someone could suggest besides going one by one through each and every stored procedure/function and correct the case of the table names?
Thanking in advance for any life-saving suggestion.
From the MySQL documentation on cases in identifiers:
In MySQL, databases correspond to directories within the data
directory. Each table within a database corresponds to at least one
file within the database directory (and possibly more, depending on
the storage engine). Triggers also correspond to files. Consequently,
the case sensitivity of the underlying operating system plays a part
in the case sensitivity of database, table, and trigger names.
I would probably take the time to make everything lower case because it will save you headaches further down the line. If you have a client with a decent editor like MySQL Workbench then you can do these replaces with a quick find and replace.
EDIT:
According to the documentation, you can try setting the lower_case_table_names system variable to 1, which will:
Table names are stored in lowercase on disk and name comparisons are
not case sensitive. MySQL converts all table names to lowercase on
storage and lookup. This behavior also applies to database names and
table aliases.
This might solve your problem if all of the table had been created with lowercase on disk.

How do I quote a reserved word in SQL so it works across all the common database systems?

Say I have a table call ‘users’ with a column ‘order’ and I wish my application code to work across all the database systems out there.
Assume that it is impractical to change the database schema. Even if the schema was change, one of the main database engine will come up with yet another reserved word, so stopping the app working when a database engine is updated.
I would rather not have to process the SQL strings to convert them into the correct form for each database.
'How to find if a column name is a reserved keyword across various databases' partly overlaps with this question.
('Syntax error due to using a reserved word as a table or column name in MySQL' is the reference question for MySQL.
)
You have to test on everything you are going to support, so "all the database systems out there" is not in realty an option.
To be more realistic, you can decide which DBMS you want to support, and write a subset of SQL which they are all happy with, and test them with automated tests.
For example, you might consider:
MySQL
Postgres
MS SQL Server
Oracle
I believe these all support ANSI double-quotes for quoting names, so if you quote all names all the time then you have one less thing to worry about.

Default database for MySQL

Is there a way to allocate a default database to a specific user in MySQL so they don't need to specify the database name while making a query?
I think you need to revisit some concepts - as Lmwangi points out if you are connecting with mysql client then my.cnf can set it.
However, your use of the word query suggests that you are talking about connecting from some programming environment - in this case you will always need a connection object. To create connection object and in this case having default database to connect to will lead to no improvement (in terms of speed or simplicity). Efficiently managing your connection(s) might be interesting for you - but for this you should let us know exactly what is your environment.
If you use a database schema you don't need to specify the database name every time, but you need to select the database name.
The best thing to do would be to use a MySQL trigger on the connection. However, MySQL only accepts triggers for updates, deletes and inserts. A quick Google search yielded an interesting stored procedure alternative. Please
see MySQL Logon trigger.
When you assign the permissions to every user group, you can also specify, at the same file, several things for that group, for example the database that users group need to use.
You can do this with a specification file, depending on the language you are working with, as a simple variable. Later, you only have to look for that variable to know which database you need to work with. But, I repeat, it depends on the language. The specification file can be an XML, phpspecs file, or anything like this.

MySQL Lowercase Table Names in Windows Uppercase names on Unix

I have a a problem whereby my production server runs Unix and my dev server runs MS Windows.
The problem is that Windows is not case sensitive and Unix is. So my table set on the production server uses Uppercase table names ie "Customers" and on Windows the table names are in lowercase "customers".
All this is fine until you need to get data from one box to another and your SQL export says insert into "customers" in lowercase, and presto "Unkown table customers". Because the production server is currently on a shared hosting plan i cant change the settings and install the key that ignores case.
So my question, is there a way to get Windows to convert the tables back to the correct case or is there some setting I can include in the export SQL file so that i can upload data without this problem.
Thanks
UPDATE
Here is what I discovered for anybody else having this issue.
If you have already set up your tables running MySQL on Windows adding
lower_case_table_names=2 to your my.cnf or my.ini file will not change the case of your tables automatically even if they were originally created using uppercase or mixed case names.
CREATE TABLE "MyTable" will create a new table "mytable" not "MyTable" even when lower_case_table_names=2 is set in your my.cnf file.
To get around this problem use this method
Make a copy of your original table
Drop your original table
Rename your copy table using the correct case.
This is the only way it will work. Hope this helps somebody.
Taken from dev.mysql.com:
To avoid data transfer problems arising from lettercase of database or table names, you have two options:
Use lower_case_table_names=1 on all systems. The main disadvantage with this is that when you use SHOW TABLES or SHOW DATABASES, you do not see the names in their original lettercase.
Use lower_case_table_names=0 on Unix and lower_case_table_names=2 on Windows. This preserves the lettercase of database and table names. The disadvantage of this is that you must ensure that your statements always refer to your database and table names with the correct lettercase on Windows. If you transfer your statements to Unix, where lettercase is significant, they do not work if the lettercase is incorrect.
Exception: If you are using InnoDB tables and you are trying to avoid these data transfer problems, you should set lower_case_table_names to 1 on all platforms to force names to be converted to lowercase.
If you plan to set the lower_case_table_names system variable to 1 on Unix, you must first convert your old database and table names to lowercase before stopping mysqld and restarting it with the new variable setting.
There is one easy solution:
Always name your tablenames lowercase.
The universal guiding philosophy of Windows with respect to case is "case-insensitive, case stored". That means Windows never intends to discard your case, so it's a little mysterious why your tables on Windows are lower-case.
Apologies if this is a dumb question, but have you tried renaming the tables on the Windows machine so they have the correct case pattern?