MySQL : multiple column values as 1 comma-separated string? - mysql

Suppose I have a select query like :
SELECT * FROM tablename
and in the table are columns : field1, field2 and field3
Does anyone know if it's possible to get a resultset with only 1 row with 1 field, with comma separated values of the columns, like this :
"fieldvalue1, fieldvalue2, fieldvalue3"
Problem is that I don't know the column names of the table in advance...
Another problem is that a prepared statement is not the way to go, since all this should be done from within a trigger, and MySQL doesn't allow dynamic cursors/selects inside a trigger.

I have done some research and only came as far as GROUP_CONCATenating the column names correctly. But the problem is, that
SELECT (SELECT GROUP_CONCAT( cols.column_name) FROM (SELECT column_name FROM information_schema.columns WHERE table_name='test_table') as cols) FROM test_table
will return one and the same concatenated string containing the column names, once for each table row, instead of evaluating it as the column names for the outer select statement and returning the actual values.
From what I have read in all of the forums discussing this kind of question (and there were many), there is really no way of getting this to work without prepared statements.
I can only think of one other way to do this, and that would be having a dedicated column on each table, where you concatenate the individual column values on INSERT or UPDATE, so you can simply select this one field instead of the full set of fields.

Seems like you have 3 questions here:
Getting a resultset with 1 row, 1 field: MYSQL has a CONCAT_WS function that works like this:
SELECT CONCAT_WS(',',Field1,Field2,Field3)
That will return "Field1Value, Field2Value, Field3Value"
I'm not sure how you are going to get these column names. Do you need to get them from a sql statement, a string, etc. ? You can get the table names `SHOW COLUMNS FROM tablename'. The Field column will have the column names.
Triggers are available in mysql (added in 5.0.2 I think): http://dev.mysql.com/doc/refman/5.0/en/triggers.html

First, to find out the columns' names in advance, assuming that you have the table's name, you can get them as any other query:
SHOW COLUMNS FROM your_table
Once you have the names you can do:
SELECT CONCAT(field1,',',field2,',',field3) AS newField FROM your_table

Related

use AS in mysql to select a name from another column on the table

I need to select a value from a column in the table as a name of the another column in mysql
for ex ::
select column AS (select column from table where id = 1) from table;
it give me a syntax error .. How can I use select statement inside AS Function
Actually I need to set a value from a column as a name to another column using AS Function in mysql
The answer is simple: It is not possible in SQL. Column aliases are constants.
You can't do this in a single query. All identifiers must be fixed in the query at the time it is parsed, which is before the query begins reading data. This includes column names and column aliases. The names or aliases of columns cannot be set at runtime based on data read during the query.
But you can do what you want in two queries.
Query to get the column alias name you want to use. This returns a string.
Use that string as you format the second query. Then the column alias will be fixed in that second query by the time you prepare it.

Eliminate underscores and convert to lowercase MySQLselect query column names

I am stuck at what seemed to be a very simple task in MySQL.
I have a table A with fields A_Id and A_Name.
MySQL query - SELECT * FROM A;
Obviously, in the output, the column names are A_Id and A_Name. But I want them to be aid and aname, that is, eliminating all underscores and converting to lowercase only the column names.
I think this should be possible. Any help/suggestion is appreciated.
EDIT:
Why do I need to do this?
I have indexed all these fields in ElasticSearch, and then querying using Spring Data Elastic, using named queries becomes difficult when there are underscores in the field names
I did look around for some answers, but all of them are either ALTER statements or manipulating the field values using REPLACE, none of which suit my usecase.
Thanks :)
You need to use the AS keyword to change the column names in the output:
SELECT A_Id as aid, A_Name as aname
FROM A;
There's no simple way to do this automatically for all columns, you need to list each column specifically. The only way to automate it would be to write a stored procedure that created the query dynamically by querying INFORMATION_SCHEMA.COLUMNS.
The query to get the columns would include something like:
SELECT GROUP_CONCAT(CONCAT(column_name), ' AS ', REPLACE(LOWER(column_name), '_', '')) AS select_list
FROM INFORMATION_SCHEMA.COLUMNS
WHERE table_name = 'A';

MySQL - Copying partial data from one table to another

This may be a silly question, and I understand why I'm getting the result that I am, however, I thought mySQL acted differently and I can't finish the documentation to tell me otherwise.
I have 2 basic tables as follows:
CREATE TABLE test ( num INT, time TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP );
CREATE TABLE test_to_copy ( num INT );
I then create a single entry into the test_to_copy table:
INSERT INTO test_to_copy VALUES ( 12 );
Now I try and copy the table test_to_copy to test like so:
INSERT INTO test SELECT * FROM test_to_copy;
The error that keeps getting thrown is
"Column count doesn't match value count at row 1".
I know that it is complaining that the number of columns in both tables does not match meaning it does not know what variable we are assigning our copy to, however, should it not be a case where the time is created automatically i.e. defaulted if nothing is inserted when we do the copy rather than throw the error?
Due to constraints, I can no longer have the time in both tables, and I must do a SELECT * on the test_to_copy table as there are over 50 columns, and i'm wondering is there an easy way around this?
This is another variation of a frequent question: "can I query *-except-for-one-column?"
No, there is no wildcard-with-exceptions syntax in SQL. The * wildcard means all columns. If you don't want all columns, you must name the columns explicitly.
If you have a variety of columns because this method may be used for more than one table, you can get the list of columns for any given table from INFORMATION_SCHEMA.COLUMNS and use that information to build a dynamic SQL query.
Here's a way you can produce the list of columns:
SELECT
GROUP_CONCAT(
CONCAT('`', column_name, '`')
) AS _cols
FROM INFORMATION_SCHEMA.COLUMNS
WHERE TABLE_SCHEMA='mydatabase' AND TABLE_NAME='mytable'
AND COLUMN_NAME NOT IN ('time'); -- or other columns to exclude
See also:
Select all columns except one in MySQL?
SQL exclude a column using SELECT * [except columnA] FROM tableA?
INSERT INTO test (num)
SELECT num
FROM test_to_copy

MySQL - Get Column Names & SELECT At Same Time?

I know of the following two ways to show column names of a table:
SHOW COLUMNS FROM tablename
and
DESCRIBE tablename
How can I do a SELECT FROM tablename and also return the columns (If possible)?
The reason I want to do this is because in Nim, the MySQL module doesn't provide any proc for returning an associative array of results that you can reference by column name. You have to get results like x[0]. I'd like to create my own module for this and I don't want to execute two different queries for it.

SQL - Select tables where row number is XX

Been searching on Google for a while now without finding the answer to my problem. I have like 10 tables where 5 of them contains 150 rows. I want to add 15 rows to these 5 tables, is there any simple solution for this? I know it's easy to add the rows manually but I want to know anyway. What I'm looking for is something like this:
INSERT INTO all_tables VALUES (col1, col2, col3) WHERE row_number() = '150'
Is it possible? Thanks in advance!
You can only target updates to one table at a time, which must always be specified by name. Also, you cannot specify a WHERE clause on an INSERT. Your best bet is probably to write one INSERT and copy and paste for the rest.
You could:
Loop through a list of the relevant table names.
Run a dynamic query like select count(*) into #c1 from SpecifiedTable against the relevant table, returning the count into a declared variable.
If the returned value is 150, run another dynamic query to insert the relevant values into the specified table.
You can find out more about dynamic queries and returning values from them in MySQL here. If this is a once-off, you will probably find it easier to do it manually.