К основному контенту

Testing Oracle 12.1.0.2 "in-memory" feature

As some may know Oracle resently realised RDBMS 12.1.0.2 version, which features, among others, IN-MEMORY option. So I disided to test how it works, and what benefits would it give if deployed to production.


TestLab configuration

On host with VMWare ESXi 5.0 I created virtual machine of 4 cpu cores and 8Gb RAM. Operating system used was Oracle Linux 6.5.
Database server - ofcourse Oracle EE 12.1.0.2

Instance was configured with following parameters:


sga_max_size                         big integer 6G
sga_target                           big integer 6G
pga_aggregate_limit                  big integer 1057M
pga_aggregate_target                 big integer 800M
inmemory_size                        big integer 512M

HugePages was enabled for this installation.

Configure in-memory


ALTER SYSTEM SET INMEMORY_SIZE=512M SCOPE=SPFILE;
SHUTDOWN IMMEDIATE;
STARTUP;

Total System Global Area 6442450944 bytes
Fixed Size                  2938792 bytes
Variable Size            1157630040 bytes
Database Buffers         4731174912 bytes
Redo Buffers               13836288 bytes
In-Memory Area            536870912 bytes
Database mounted.

Database opened.

Createing test user and tables

First of all I need to create some tables to do full scans on.

GRANT DBA TO DBAX IDENTIFIED BY DBAX;

Granting DBA to my test user, and no worries about futher permissions.

CONNECT DBAX/DBAX

Now I'll create two tables one with inmemory enabled and another - traditional table.

CREATE TABLE IMMEM AS SELECT * FROM DBA_TABLES;

BEGIN
FOR I IN 1..1000
LOOP
INSERT INTO INMEM (SELECT * FROM DBA_TABLES);
END LOOP;
COMMIT;
END;

ALTER TABLE INMEM INMEMORY;

CREATE TABLE NOMEM AS SELECT * FROM INMEM;

SET TIMI ON
SET AUTOTRACE ON

Now I'm going to run analitycal query as this is what Oracle declares in-memory feature's main purpose.

Test Traditional table

SELECT COUNT (*) 
            FROM (
SELECT OWNER,SUM(NUM_ROWS) OVER(PARTITION BY OWNER) 
            FROM DBAX.NOMEM 
            WHERE OWNER = 'DBAX');

  COUNT(*)
----------
      2006
 
Elapsed: 00:00:04.79

Explain plan:
-----------------------------------------------------------------
| Id  | Operation          | Name  | Rows  | Bytes | Cost (%CPU)| Time  |
-----------------------------------------------------------------
|   0 | SELECT STATEMENT   |       |     1 |     8 | 29742   (1)| 00:00:02 |
|   1 |  SORT AGGREGATE    |       |     1 |     8 |            |          |
|*  2 |   TABLE ACCESS FULL| NOMEM |  2006 | 16840 | 29742   (1)| 00:00:02 |
-----------------------------------------------------------------

Test In-memory table

SELECT COUNT (*) 
            FROM (
            SELECT OWNER,SUM(NUM_ROWS) OVER(PARTITION BY OWNER)               FOM DBAX.INMEM
            WHERE OWNER = 'DBAX');

  COUNT(*)
----------
      2006

Elapsed: 00:00:00.04

Explain plan:
-----------------------------------------------------------------
| Id  | Operation                   | Name  | Rows  | Bytes | Cost (%CPU)| Time     |
-----------------------------------------------------------------
|   0 | SELECT STATEMENT            |       |     1 |     8 |  1150   (5)| 00:00:01 |
|   1 |  SORT AGGREGATE             |       |     1 |     8 |            |          |
|*  2 |   TABLE ACCESS INMEMORY FULL| INMEM |  2006 | 16840 |  1150   (5)| 00:00:01 |

-----------------------------------------------------------------

As we may see results are speacking for themselfes.


Test In-memory compression

Inmemory table is created by default with "MEMCOMPRESS FOR QUERY LOW" In-memory data compression. Lets test more radical option whish is going to save us a lot fo RAM space, but would lower performance.

CREATE TABLE INMEM2 AS SELECT * FROM INMEM;

ALTER TABLE DBAX.INMEM2 INMEMORY MEMCOMPRESS FOR CAPACITY HIGH;

SELECT COUNT (*) 
             FROM (
             SELECT OWNER,SUM(NUM_ROWS) OVER(PARTITION BY OWNER)              FROM DBAX.INMEM 
             WHERE OWNER = 'DBAX');

  COUNT(*)
----------
      2006

Elapsed: 00:00:00.11

As I presumed it took more time to process my query, by this time is still much lower comparing whith traditional table.

Now lets what benefits did we got from high level of compression.

SELECT V.OWNER,
       V.SEGMENT_NAME, 
       V.BYTES ORIG_SIZE, 
       V.INMEMORY_SIZE IN_MEM_SIZE, 
       V.BYTES / V.INMEMORY_SIZE COMP_RATIO
FROM V$IM_SEGMENTS V;

OWNER SEGMENT_NAME ORIG_SIZE IN_MEM_SIZE COMP_RATIO
-----------------------------------------------------------------
DBAX  INMEM        905969664 45547520    19.8906475
                                                
DBAX  INMEM2       900726784 7798784     115.495798

It' almost 6 time less space against default compression.

 I ran  all tests several times and results were the same (add or remove several centiseconds)


Nota bene:

After first table access it can take up to half an hour in my environment to populate inmemory segments. During this time running query will take almost same time as traditional table query, but explain plan will still claim INMEMORY access.

Progress of inmemory segments population can be observed by queriing POPULATE_STATUS from:
SELECT * FROM V$IM_SEGMENTS;
and
SELECT * FROM V$INMEMORY_AREA;

We can force inmemory segments population on instance startup by setting INMEMORY PRIORITY for our table (default is NONE).


Комментарии

Популярные сообщения из этого блога

Установка и настройка pgAgent(планировщика заданий PostgreSQL)

Установка pgAgent Последняя версия скрипта для установки агента  тут . Перенести инструкцию по агенту в отдельную тему. 1. Создать пользователя ОС, и сделать ему домашний каталог: useradd -s /bin/false -r -M pgagent mkdir /home/pgagent 2. Установить и настроить демон: yum install pgagent_94 При наличии ошибок вида (была на Oracle Linux 6.8) Error: Package: pgagent_94-3.4.0-1.rhel6.x86_64 (pgdg94)            Requires: libwx_baseu-2.8.so.0(WXU_2.8)(64bit) Нужно установить EPEL systemctl enable pgagent_94 chown pgagent:pgagent /var/log/pgagent_94.log 3. Установить схему агента в базе: sudo -u postgres psql -f /usr/share/pgagent_94-3.4.0/pgagent.sql postgres 4. Создать файл паролей для подключения агента к базе. vi /home/pgagent/.pgpass localhost:5432:*:postgres:postgres chown pgagent.pgagent /home/pgagent -R chmod 600 /home/pagent/.pgpass 5. Запустить и проверить работу агента systemctl start pgagent_94.service systemctl status pga

Включение логирования для Haproxy

Изначально логирование в syslog в HaProxy отключено. Ниже пример настройки логирования для ОС Centos 7. Настройка: Добавить строку  log 127.0.0.1 local2 в секцию global файла /etc/haproxy/haproxy.cfg Раскомментировать $ModLoad imudp и $UDPServerRun 514 в файле  /etc/rsyslog.conf Создать файл  /etc/rsyslog.d/haproxy.conf со следующим содержимым:  local2.* /var/log/haproxy.log Перезапустить rsyslog и haproxy.

Использование oraenv для установки окружения.

Для настройки окружения в Linux можно все параметры базы указать в .bash_profile: ORACLE_HOME=/app/oracle/product/11.2.0.4/dbhome_1 export ORACLE_HOME ORACLE_BASE=/app/oracle export ORACLE_BASE ORACLE_SID=orcl export ORACLE_SID PATH=$PATH:$HOME/bin:$ORACLE_HOME/bin export PATH Но лучше использовать для этих целей утилиту oraenv. oraenv берет данные из файла /etc/oratab orcl:/app/oracle/product/12.1.0/dbhome_1:N И на ее основе задает параметры окружения: ORACLE_SID, ORACLE_BASE,ORACLE_HOME и PATH Использовать можно в интерактивном режиме: . oraenv ORACLE_SID = [orcl] ? orcl The Oracle base has been set to /app/oracle И в неинтерактивном режиме. Добавить в  .bash_profile: ORACLE_SID=orcl ORAENV_ASK=NO . oraenv Для ASM ситуация аналогичная. . oraenv ORACLE_SID = [orcl] ? +ASM1 The Oracle base has been set to /u01/app/oracle echo $ORACLE_HOME /app/11.2.0/grid