Вопрос по postgresql, java – безопасность потока postgresql для временных таблиц

5

Этот синтаксис я использую для создания временной таблицы:

create temp table tmpTable (id bigint not null, primary key (id)) on commit drop;

Я знаю, что это означает, что в конце каждой транзакции эта таблица будет удалена. У меня вопрос: если два или более потоков в одном сеансе создадут и вставят значения во временную таблицу, получат ли они каждый свой собственный экземпляр, или этот общий экземпляр будет общим для всего сеанса? Если он используется совместно, есть ли способ сделать его локальным для каждого потока?

Спасибо Netta

Они используют одно соединение с БД или каждый поток имеет свое собственное? NPE

Ваш Ответ

1   ответ
8

cannot создать временную таблицу с тем же именемin the same session перед тем, как вы отбросите ту, которая существует (зафиксируйте транзакцию в вашем случае).

Вы можете использовать:

CREATE TEMP TABLE tmptbl IF NOT EXISTS ...

Больше оCREATE TABLE in the manual.

Unique temp tables

Чтобы сделать временную таблицу локальной для "потока" (в том же сеансе) вам нужно использоватьunique table names, Одним из способов будет использование несвязанныхSEQUENCE и динамический SQL - в процедурном языке, таком как plpgsql или в операторе DO (который в основном одинаков без сохранения функции).

Запустите один:

CREATE SEQUENCE myseq;

Использование:

DO $
BEGIN
EXECUTE 'CREATE TABLE tmp' || nextval('myseq')  ||'(id int)';
END;
$

Чтобы узнать последнее имя таблицы:

SELECT 'tmp' || currval('myseq');

Или поместите все это в функцию plpgsql и верните таблицу или повторно используйте имя таблицы.

Все дальнейшие команды SQL должны выполняться динамически, поскольку простые операторы SQL работают с жестко закодированными идентификаторами. Так что, вероятно, лучше всего поместить все это в функцию plpgsql.

Unique ID to use same temp table

Другим возможным решением может быть использованиеsame temp table для всех потоков в одном сеансе и добавить столбецthread_id к столу. Обязательно индексируйте столбец, если вы интенсивно используете эту функцию. Тогда используйте уникальныйthread_id на поток (в том же сеансе).

Только однажды:

CREATE SEQUENCE myseq;

Один раз в теме:

CREATE TEMP TABLE tmptbl(thread_id int, col1 int) IF NOT EXISTS;
my_id :=  nextval('myseq'); -- in plpgsql
-- else find another way to assign unique id per thread

SQL:

INSERT INTO tmptbl(thread_id, col1) VALUES
(my_id, 2), (my_id, 3), (my_id, 4);

SELECT * FROM tmptbl WHERE thread_id = my_id;
Все дело в том, что мне нужны разные временные таблицы для каждого потока. Нет ли способа создать локальную временную таблицу? netta
Это настолько элегантно, насколько это возможно в PostgreSQL. Отлично сделано, сэр.
@IamIC: в течение одного сеанса может выполняться только одна транзакция за раз. Так что такая ситуация невозможна. Теоретически это может быть изменено (AFAIC), но это так, как оно реализовано.
@netta: временные таблицыlocal на сессию. Используйте отдельные сеансы, если вы хотите работать с одинаковыми именами. Иначе вы должны прибегнуть к динамическому SQL, как я добавил в своем ответе. Или используйте уникальный идентификатор для каждой темы - я добавил еще одну идею в свой ответ.
Если временная таблица помечена WITH ON COMMIT DROP, как PG будет обрабатывать несколько потоков, обращающихся к этой таблице? Любой поток может фиксироваться, но таблицу нельзя удалить, поскольку она используется.

Похожие вопросы