MySQL REPLACE in UPDATE does not work properly - mysql

The following query:
select replace(`Abilities`, 'export_import', 'auto') from fl_account_types;
gives me 'auto,listings' correct replacement from Abilities column. However, when I execute:
update fl_account_types set `Abilities` = replace(`Abilities`, 'export_import', 'autos');
MySQL just omits 'export_import' string and replaces Abilities with 'listings' string.
What could be the reason?

The problem was that Abilities was of type SET and I was trying to replace with a value which was not listed in a definition of it. But I still do not understand why select replace works well and why MySQL do not throw an error.

Related

Inserting a point into MySQL 8.0 from workbench

I've got a column called 'coordinates' of type 'point'.
This query:
update `my-db`.`community`
set `coordinates`= POINT( 31.9931217, 35.2823115 )
where 'id' = 1;
Returns the following error:
cannot get geometry object from data you send to the GEOMETRY field
What is the proper formatting here?
To start with: 'id' is not a valid column name (that's a string litteral). As a general hint, you should avoid quoting the column names unless it is really necessary (ie when the name contains special characters or starts with a number, or clashes with a reserved word).
Apart from that, your syntax should work, as described in the documentation and tested in this DB Fiddle.
As an alernative, you can also try and use ST_GeomFromText(), as follows:
update `my-db`.`community`
SET `coordinates`= ST_GeomFromText('POINT(31.9931217 35.2823115)')
where `id` = 1;
Looks like the correct syntax is
UPDATE my-db.community SET coordinates=GeomFromText('POINT(31.9931217 35.2823115)') WHERE 'id' = 1;
Try and see

Is there an equivalent way to do MySQL's JSONOBJECTAGG() in MariaDB?

The server I was working on for a data project crashed and I am now recreating the database. I used to be working on a MySQL database, and now I'm using MariaDB. I have never used MariaDB before.
Previously, I used the following command to insert some data into one table from another:
CREATE TABLE collaborators_list
SELECT awards.id, awards.researcher_name, awards.organization_id,
JSON_OBJECTAGG(awards.fiscal_year, coapplicants.coapplicant_name,
coapplicants.organization_number)
AS 'coapplicants_list' FROM awards
INNER JOIN coapplicants
ON awards.id=coapplicants.id
GROUP BY awards.researcher_name, awards.organization_id;
Basically, I want to do the same thing in MariaDB. I tried looking here:
https://mariadb.com/kb/en/library/json-functions/
but unless I am misreading something, none of these is what I really want...
Help!
No, MariaDB still does not support JSON_ARRAYAGG and JSON_OBJECTAGG functions. A JIRA ticket has been raised for requesting this feature: https://jira.mariadb.org/browse/MDEV-16620
Now, from the docs of JSON_OBJECTAGG():
It takes only two column names or expressions as arguments, the
first of these being used as a key and the second as a value.
An error occurs if any key name is NULL or the number of arguments is
not equal to 2.
However, you are specifying three arguments in JSON_OBJECTAGG(awards.fiscal_year, coapplicants.coapplicant_name, coapplicants.organization_number); so your attempted query will not work as well.
Now, in the absence of the required functions, we can utilize Group_Concat() with Concat(). I am assuming that you need only first two arguments (as explained in previous para).
GROUP_CONCAT( DISTINCT CONCAT('"', awards.fiscal_year, '": "',
coapplicants.coapplicant_name, '"')
SEPARATOR ', ')
Note that, in case of string getting very very long, Group_Concat() may truncate it. So, you can increase the allowed length, by executing the following query, before the above query:
SET SESSION group_concat_max_len = ##max_allowed_packet;

What is the correct syntax for a Regex find-and-replace using REGEXP_REPLACE in MariaDB?

I need to run a regex find-and-replace against a column named message in a MySQL table named post.
My database is running MariaDB 10.
According to the docs, MariaDB 10 has a new REGEXP_REPLACE function designed to do exactly this, but I can't seem to figure out the actual syntax.
It will affect 280,000 rows, so ideally there's also a way to limit it to only changing one specific row at a time while I'm testing it, or simply doing a SELECT rather than an UPDATE until I'm sure it does what I want.
The regex I want to run:
\[quote\sauthor=(.+)\slink=[^\]]+]
The replacement string:
[quote="$1"]
The following was what I tried, but it just throws a SQL error:
UPDATE post SET message = REGEXP_REPLACE(message, '\[quote\sauthor=(.+)\slink=[^\]]+]', '[quote="$1"]') WHERE post_id = 12
In this case, the original message was:
[quote author=Jon_doe link=board=2;threadid=125;start=40#msg1206 date=1065088] and the end result should be [quote="Jon_doe"]
What is the proper syntax to make this REGEXP_REPLACE work?
You have to do a lot of escaping here:
REGEXP_REPLACE(message, "\\[quote\\sauthor=(.+)\\slink=[^\\]]+]", "\\[quote=\"\\1\"\\]")
Please note that you have to reference the Group by \\1

Could this simple T-SQL update fail when running on multiple processors?

Assuming that all values of MBR_DTH_DT evaluate to a Date data type other than the value '00000000', could the following UPDATE SQL fail when running on multiple processors if the CAST were performed before the filter by racing threads?
UPDATE a
SET a.[MBR_DTH_DT] = cast(a.[MBR_DTH_DT] as date)
FROM [IPDP_MEMBER_DEMOGRAPHIC_DECBR] a
WHERE a.[MBR_DTH_DT] <> '00000000'
I am trying to find the source of the following error
Error: 2014-01-30 04:42:47.67
Code: 0xC002F210
Source: Execute csp_load_ipdp_member_demographic Execute SQL Task
Description: Executing the query "exec dbo.csp_load_ipdp_member_demographic" failed with the following error: "Conversion failed when converting date and/or time from character string.". Possible failure reasons: Problems with the query, "ResultSet" property not set correctly, parameters not set correctly, or connection not established correctly.
End Error
It could be another UPDATE or INSERT query, but the otehrs in question appear to have data that is proeprly typed from what I see,, so I am left onbly with the above.
No, it simply sounds like you have bad data in the MBR_DTH_DT column, which is VARCHAR but should be a date (once you clean out the bad data).
You can identify those rows using:
SELECT MBR_DTH_DT
FROM dbo.IPDP_MEMBER_DEMOGRAPHIC_DECBR
WHERE ISDATE(MBR_DTH_DT) = 0;
Now, you may only get rows that happen to match the where clause you're using to filter (e.g. MBR_DTH_DT = '00000000').
This has nothing to do with multiple processors, race conditions, etc. It's just that SQL Server can try to perform the cast before it applies the filter.
Randy suggests adding an additional clause, but this is not enough, because the CAST can still happen before any/all filters. You usually work around this by something like this (though it makes absolutely no sense in your case, when everything is the same column):
UPDATE dbo.IPDP_MEMBER_DEMOGRAPHIC_DECBR
SET MBR_DTH_DT = CASE
WHEN ISDATE(MBR_DTH_DT) = 1 THEN CAST(MBR_DTH_DT AS DATE)
ELSE MBR_DTH_DT END
WHERE MBR_DTH_DT <> '00000000';
(I'm not sure why in the question you're using UPDATE alias FROM table AS alias syntax; with a single-table update, this only serves to make the syntax more convoluted.)
However, in this case, this does you absolutely no good; since the target column is a string, you're just trying to convert a string to a date and back to a string again.
The real solution: stop using strings to store dates, and stop using token strings like '00000000' to denote that a date isn't available. Either use a dimension table for your dates or just live with NULL already.
Not likely. Even with multiple processors, there is no guarantee the query will processed in parallel.
Why not try something like this, assuming you're using SQL Server 2012. Even if you're not, you could write a UDF to validate a date like this.
UPDATE a
SET a.[MBR_DTH_DT] = cast(a.[MBR_DTH_DT] as date)
FROM [IPDP_MEMBER_DEMOGRAPHIC_DECBR] a
WHERE a.[MBR_DTH_DT] <> '00000000' And IsDate(MBR_DTH_DT) = 1
Most likely you have bad data are are not aware of it.
Whoops, just checked. IsDate has been available since SQL 2005. So try using it.

Select query returns false result

eg:
Table : user
column : user_id (type is int)
SELECT * FROM user WHERE user_id = '10xyz'
is giving same result of
SELECT * FROM user WHERE user_id = '10'
The input value is not integer but not giving an error in this case.
The reason why you are getting the same result is because MySQL automatically removes the trailing characters from the string and implicitly converts it to integer.
SQLFiddle Demo
SQLFiddle Demo (updated)
If you don't want to change all your code, but you have your database queries all going through one or a few subs, you can change those to check for warnings after using a statement handle (e.g. if ( $sth->{mysql_warning_count} ) ...).
Or you can create a DBI subclass that does that automatically for you, promoting warnings to errors. If you do, many others have use for such a thing. There are configuration settings to give an error instead of a warning when updating or inserting something like '10xyz' into an integer field, but not anything broader than that, and dear Oracle considers it Not a Bug. Maybe MariaDB does (or could do) better?
datatype of user_id is in database is INT
that why it giving same output and not error