- Newest
- Most votes
- Most comments
Hi there.
I find the use of a temporary table in this manner as an anti-pattern. You would use a temporary table, "temporary", meaning, you create it, use it, and dispose it. What I mean by all this is that the way this temporary table is being used in the procedure is no different than using a permanent table.
I'm not sure what do you mean when you say:
Saw few blogs, which suggests using permanent table to avoid this error, but that is seems not feasible solution as we need to call the same procedure from multiple sessions so we may need to end up creating multiple tables then for each session/user which is not good.
Why is no good? You wouldn't create a table multiple times, just create it once (but not inside the the procedure), and then use it in your procedure.
Also, what is the exact error you are getting? the full message, line number, etc. I'm not clear where in the code is the error thrown.
Thanks.
Thank you @Jose Guay
Below is simple test case of how this error getting reproduced.
But the key issue is, when wanted to use this in a broader perspective i.e., populate this temporary table once and utilize the results in multiple queries subsequently, it doesn't work if referring to it twice.
And as you rightly said, we should create temporary table outside the procedure and just use it and truncate it after the work in the session. So how should we handle a requirement in which similar procedure/business logic is getting called simultaneously from multiple session/users. as because creating multiple tables each time with different name is not a good idea. And at the same time calling the same business logic using subquery or CTE in the queries multiple times in the procedure (without storing this intermediate result set in temporary/permanent table) means performance hit. Correct me if wrong.
Considering this situation what would be the optimal suggested way to handle such type of business logic in the procedure?
CREATE TABLE employees ( ID INTEGER, Name VARCHAR(100) );
insert into employees values(1, 'A'); insert into employees values(2, 'B');
CREATE temporary TABLE IF NOT EXISTS employees_backup1 as (select * from employees);
Below statement works fine without any error
select * from employees eb1, employees_backup1 eb2 where eb1.id= eb2.id;
ID Name ID Name 1 A 1 A 2 B 2 B
Below statement errors out
select * from employees_backup1 eb1, employees_backup1 eb2 where eb1.id= eb2.id;
Can't reopen table: 'eb1'
Hi there.
Is there a reason why you are joining your temporary table with itself? I know this is not an answer to your question, but I'm just wondering about what are you trying to achieve.
Thanks.
Relevant content
- Accepted Answerasked 4 months ago
- AWS OFFICIALUpdated 10 months ago
- AWS OFFICIALUpdated 2 years ago
- AWS OFFICIALUpdated 3 years ago
- AWS OFFICIALUpdated a year ago
Actually, the above procedure compiles fine. But when i call the procedure using below, its failing with "Can't reopen table: 'eb1'. So basically, its failing during runtime but not compile time.
CALL ExampleProc(@v_Proc_status,@vResult); SELECT @v_Proc_status,@vResult;
I was talking of thee below blogs - https://sebhastian.com/mysql-cant-reopen-table/ https://bugs.mysql.com/bug.php?id=10327
Also, I see below, it mentioned the temporary table can be used and populated with different data set but with exactly same name. So, I was thinking it would be good use case in our procedure as that procedure can be called from different sessions by different user at same time and serving different result sets. Correct me if my understanding is wrong here.
https://dev.mysql.com/doc/refman/8.0/en/create-temporary-table.html
13.1.20.2 CREATE TEMPORARY TABLE Statement You can use the TEMPORARY keyword when creating a table. A TEMPORARY table is visible only within the current session, and is dropped automatically when the session is closed. This means that two different sessions can use the same temporary table name without conflicting with each other or with an existing non-TEMPORARY table of the same name. (The existing table is hidden until the temporary table is dropped.)