środa, 7 kwietnia 2010

Karmimy bazę danych - dbMonster

Przez ostatni czas szukałem narzędzia do generowania dużej ilości danych dla baz danych.
Natrafiłem na dość sporo ich w sieci ale niestety znaczna większość była komercyjna a ich wersje trialowe umożliwiały generowanie np. tylko 40 rekordów. Ale na szczęście udało mi się także napotkać na miły program autorstwa Polaka Piotra Maja - dbMonster. Narzędzie to obsługuje się z poziomu (niestety) konsoli i wymaga stworzenia mapowania w pliku XML oraz prostej konfiguracji.
Zacznijmy od stworzenia tabeli w bazie danych którą później zapchamy danymi:
CONNECT TO DBMNTEST;
CREATE TABLE WOOKASZ.PRODUKTY ( 
ID_PRODUKTU BIGINT  NOT NULL  GENERATED ALWAYS AS IDENTITY (START WITH 0, INCREMENT BY 1, NO CACHE ), 
NAZWA VARCHAR (80)  NOT NULL, 
CENA DECIMAL (9, 2)  NOT NULL, 
CONSTRAINT CC1270576608403 PRIMARY KEY (ID_PRODUKTU)
);
CONNECT RESET;
W konfiguracji podajemy podstawowe dane do połączenia i kilka parametrów potrzebnych do pracy dbMonster.
test.properties:
# podstawowe dane do połączenia
dbmonster.jdbc.driver=com.ibm.db2.jcc.DB2Driver
dbmonster.jdbc.url=jdbc:db2://127.0.0.1:50000/dbmntest
dbmonster.jdbc.username=WOOKASZ
dbmonster.jdbc.password=password
# po ilu insertach wykonywać commit
dbmonster.jdbc.transaction.size=1000

# nazwa schematu dla takich baz jak Oracle lub DB2
dbmonster.jdbc.schema=WOOKASZ

# ile razy próbować wygenerować unikalny klucz
dbmonster.max-tries=1000

# domyślna liczba wierszy dla SchemaGrabber (o tym innym razem;)
dbmonster.rows=1000

# klasa wizualizująca progress bar
dbmonster.progress.monitor=pl.kernelpanic.dbmonster.ProgressMonitorAdapter
Myślę, że tak konfiguracja jest dość prosta i nie trzeba jej głębiej omawiać.
Teraz czas dla schematu w którym opisana jest struktura tabel dla których generowane będą dane. W naszym przypadku jest to tylko jedna tabela PRODUKTY.
testSchema.xml:
<?xml version="1.0" encoding="iso-8859-1"?>
<!DOCTYPE dbmonster-schema PUBLIC
    "-//kernelpanic.pl//DBMonster Database Schema DTD 1.1//EN"
    "http://dbmonster.kernelpanic.pl/dtd/dbmonster-schema-1.1.dtd">
<dbmonster-schema>
   <name>DB Monster Test Schema ! ^^</name>
    <table name="PRODUKTY" rows="15000">
        <key databaseDefault="true">
           <generator type="pl.kernelpanic.dbmonster.generator.MaxKeyGenerator">
               <property name="columnName" value="ID_PRODUKTU"/>
           </generator>
        </key>
        <column name="nazwa">
            <generator type="pl.kernelpanic.dbmonster.generator.StringGenerator">
                <property name="nulls" value="0"/>
                <property name="minLength" value="4"/>
                <property name="maxLength" value="80"/>
                <property name="allowSpaces" value="true"/>
            </generator>
        </column>
        <column name="cena">
            <generator type="pl.kernelpanic.dbmonster.generator.NumberGenerator">
                <property name="nulls" value="0"/>
                <property name="minValue" value="10"/>
                <property name="maxValue" value="30000"/>
                <property name="returnedType" value="numeric"/>
    <property name="scale" value="2"/>
            </generator>
        </column>
    </table>
</dbmonster-schema>
Opis struktury tabeli zawiera się w znaczniku table którego pierwszy atrubuty name musi zawierać poprawną nazwę tabeli, a drugi rows liczbę wierszy ile ma być wygenerowanych dla tej tabeli. dbMonster obsługuje klucze główne tabel, informacje o nich zawiera się w znaczniku key. W tym przypadku nie używamy generatora udostępnianego przez dbMonster do generowania wartości dla kluczy (używane są identity columns) dlatego atrybut databaseDefault ma wartość true. Dalej umieszczone zostały definicje kolumn. Każda kolumna zawiera parametry do generowania, zależne są one od tego jakiego typu generatora używamy. Listą dostępnych generatorów wraz z opisem parametrów dostępna jest tutaj. Co jest bardzo miłe dostępne jest pełne API który pozwala na tworzenie własnych generatorów.
Co mi się bardzo spodobało StringGenerator nie generuje dziwnego zlepku losowych liter tylko normalne słowa z dostępnego dla niego słownika:) Dlatego nazwą produktu nie będzie np. "AhT8ddnoJuuTQpp" ale np. "keypad's tingle". Wiem, że to i tak bez sensu (a może to coś znaczy ?) ale lepiej to wygląda gdy prezentujemy nasz system.
Zanim będzie można uruchomić generację należy przekopiować do katalogu /lib/ sterownik JDBC dla używanej bazy danych.
Teraz możemy użyć gotowego skryptu bat z katalogu /bin/ aby uruchomić generację:
dbmonster -c test.properties -s testSchema.xml

rem Batch file to run dbmonster under Windows

rem Contributed by Peter De Bruycker
2010-04-07 12:21:55,776 INFO  DBMonster - Let's feed this hungry database.
2010-04-07 12:21:56,257 INFO  DBCPConnectionProvider - Today we are feeding: DB2/NT SQL09070
2010-04-07 12:21:56,465 INFO  Schema - Generating schema .
2010-04-07 12:21:56,473 INFO  Table - Generating table <PRODUKTY>.
2010-04-07 12:22:28,570 INFO  Table - Generation of table <PRODUKTY> finished.
2010-04-07 12:22:28,574 INFO  Schema - Generation of schema <DB Monster Test Schema ! ^^> finished.
2010-04-07 12:22:28,579 INFO  DBMonster - Finished in 32 sec. 804 ms.
I mamy tabelę pełną danych:)
Dodam jeszcze, że tworzenie schematu nie jest konieczne, gdy w tabelach znajdują się jakieś dane. Można użyć tzw. SchemaGrabber aby wygenerować schemat xml. Jednak jeszcze nie udało mi się tego dokonać, ciągle otrzymuję pustą definicję tabeli. Jak mi się to uda to postaram się opisać.

Narzędzie jest bardzo dobre gdy nie mamy jakiś skomplikowanych warunków do tego jakie dane mają być składowane w bazie danych, do prostych zastosować idealne. Szkoda tylko, że projekt ten już od 2006 roku nie jest rozwijany, według mnie ma solidne podstawy do tego by konkurować z komercyjnymi rozwiązaniami. Może ktoś przejmie pałeczkę i zajmie się rozbudową dbMonster ?

Brak komentarzy:

Prześlij komentarz