PostgreSQL
 sql >> Baza danych >  >> RDS >> PostgreSQL

Jak zapisać dane z przecinkiem zmieniającym się, które przechodzi przez wyzwalacz?

Możesz użyć format() aby znacznie ułatwić tworzenie dynamicznego zapytania SQL, ponieważ automatycznie zajmie się ono poprawnie identyfikatorami i literałami. Jedną z rzeczy, które ludzie zwykle przeoczają, jest to, że możesz rozwinąć pojedyncze wyrażenie rekordu do wszystkich jego kolumn za pomocą (...).* - działa to również w przypadku NEW i OLD rejestrować zmienne w wyzwalaczu, np. select (new).*

Możesz także przekazać zmienne do dynamicznego SQL za pomocą using słowo kluczowe execute oświadczenie. Nie ma potrzeby konwertowania rekordu tam iz powrotem między rekordem a reprezentacją tekstową.

Korzystając z tej możliwości, można uprościć funkcję wyzwalania do:

DECLARE 
  l_sql text;
BEGIN
    IF TG_TABLE_SCHEMA = 'public' THEN
      newtable := TG_TABLE_NAME || '_actividad';
    ELSE
      newtable := TG_TABLE_SCHEMA || '_' || TG_TABLE_NAME || '_actividad';
    END IF;

    PERFORM creartablaactividad(TG_TABLE_SCHEMA, TG_TABLE_NAME);
    l_sql := 'INSERT INTO actividad.%I  SELECT current_user, current_timestamp, %L, ($1).*';

    IF TG_OP = 'DELETE' THEN
      execute format(l_sql, newtable, 'D') using OLD;
      RETURN OLD;
    ELSE
      -- covers UPDATE and INSERT
      execute format(l_sql, newtable, 'U') using NEW;
      RETURN NEW;
    END IF;

    RETURN NULL; -- result is ignored since this is an AFTER trigger
END;

Używanie symboli zastępczych, takich jak %I i %L umożliwia również jednokrotne zdefiniowanie rzeczywistego kodu SQL i ponowne jego wykorzystanie. Te "parametry" są zastępowane przez format() funkcja (która zachowuje $1 )

Zwróć uwagę na użycie ($1).* wewnątrz ciągu SQL. To sprawi, że execute instrukcja rozwiń parametr rekordu $1 do wszystkich jego kolumn. Sam rekord jest przekazywany „natywnie” za pomocą USING słowo kluczowe.

Użycie INSERT bez docelowej listy kolumn (insert into some_table ... zamiast insert into some_table (col1, col2, ...) ... ) jest dość delikatną rzeczą do zrobienia. Jeśli źródło i cel nie pasują do siebie, wstawienie może dość łatwo zawieść. .

Jeśli nie uruchamiasz masowego raportowania w tabelach audytu (gdzie posiadanie wyraźnych nazw kolumn byłoby znacznie bardziej wydajne), możesz pomyśleć o bardziej ogólnym wyzwalaczu audytu używającym JSON lub HSTORE kolumna do przechowywania całego rekordu. Dostępnych jest kilka gotowych wyzwalaczy audytu:




  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Funkcja JPA lower() na parametrze

  2. Django jak ponownie połączyć się po DatabaseError:limit czasu zapytania

  3. Jak używać Railsów z nazwami kolumn pisanymi wielkimi literami?

  4. Napraw „BŁĄD:kolumna „colname” nie istnieje” w PostgreSQL podczas korzystania z UNION, EXCEPT lub INTERSECT

  5. Jak mogę uzyskać dostęp do bazy danych postgresql z matlab bez przybornika bazy danych matlabs?