shell-script-pt
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

RE: [shell-script] sed - substituir \n


From: MrBiTs
Subject: RE: [shell-script] sed - substituir \n
Date: Mon, 6 Dec 2004 18:42:00 -0200

<QUOTE>
Eu optei pelo seguinte, tive alguns problemas em chamar via shell, o LOAD
DATA, (ele não processava (desprezava) os campos onde eu tenho primary key
que possuiam dados duplicados e abortava o load) então, no meu script shell,
na filtragem do arquivo original, eu coloquei um ";" a mais no final de cada
linha do arquivo final e, quando eu dou carga no banco de dados com meu
script php, eu desprezo o último campo (uso ";" 
como separador de campos), ai ficou belezinha....

de qualquer forma valeu a dica.....também constatei que a carga de dados,
quando chamada via shell, usando o mysql, é muuuuuuuuuuuuuuuuuuuuuuuito mais
rapida, comparando com a carga de dados feita via php, onde posso ter
registros duplicados....o php dá a carga em questão de 2 minutos.....via
shell, cai para meros 18s!!!!!!! Vou estudar mais a respeito.....
</QUOTE>

Com toda certeza... Isso é um processo de BULK COPY, que carrega os dados em
blocos, nao insert por insert, como eu imagino que voce estava fazendo.

Caso voce tenha problemas caso as chaves primarias, voce tem que garantir
que o seu arquivo esta integro em relacao ao banco ANTES de rodar um Bulk
Copy OU desabilitar os indices da sua tabela, importar os dados e recriar
esses indices, onde entao as duplicidades das chaves primarias vao ser
destruidas. Digamos que seus dados estejam em um arquivo gerado por um
mysqldump -etq da vida, onde vc tem uma unica clausula INSERT para todos os
dados. Olha um scriptzinho safado pra isso:

for TBL in *.sql ; do 
        tblname=`echo $TBL | cut -d "." -f 1`
        # Desabilita os indices das tabelas
        myisamchk -rq -K0 /var/lib/mysql/BANCO/$tblname 
        mysql -u user -psenha BANCO < $TBL
        myisamchk -r/var/lib/mysql/BANCO/$tblname
done


No momento do myisamchk -r, os indices vao ser reconstruidos e as
duplicidades, excluidas. 

Entretanto, o LOAD DATA nao costuma dar erros nem abortar no caso das chaves
primarias. Ele simplesmente desencana e nao importa os registros. Veja um
teste simples, com uma tabela teste cuja estrutura contem codigo INT, nome
VARCHAR(30) e codigo como PK, e os dados um load de um arquivo assim:

1^Vitto
2^Michael
3^Santino
4^Fredo
5^Luca
6^Clemenza
7^Carlo
8^Johnny
9^Tataglia
10^Barzini
3^Santino

No primeiro momento, com a tabela vazia, fazemos:

# mysql -u root -psenha -e "LOAD DATA LOCAL INFILE 'nomes.txt' INTO TABLE
teste FIELDS TERMINATED BY '^' (codigo,nome)" test

Tenho a carga dos nomes, mas olhe que legal:

# mysql -u root -psenha -e "Select * from teste" test
+--------+----------+
| codigo | nome     |
+--------+----------+
|      1 | Vitto    |
|      2 | Michael  |
|      3 | Santino  |
|      4 | Fredo    |
|      5 | Luca     |
|      6 | Clemenza |
|      7 | Carlo    |
|      8 | Johnny   |
|      9 | Tataglia |
|     10 | Barzini  |
+--------+----------+
OPA !!!!!! Cade os registros 3 e 8 duplicados ? Foram simplesmente
ignorados. Agora, vou apagar 3 registros dessa tabela:

# mysql -u root -psenha -e "Delete  from teste where codigo >= 7" test
# mysql -u root -psenha -e "Select * from teste" test
+--------+----------+
| codigo | nome     |
+--------+----------+
|      1 | Vitto    |
|      2 | Michael  |
|      3 | Santino  |
|      4 | Fredo    |
|      5 | Luca     |
|      6 | Clemenza |
+--------+----------+

E agora, o load novamente, e apos:
# mysql -u root -psenha -e "LOAD DATA LOCAL INFILE 'nomes.txt' INTO TABLE
teste FIELDS TERMINATED BY '^' (codigo,nome)" test && mysql -u root -psenha
-e "Select * from teste" test
+--------+----------+
| codigo | nome     |
+--------+----------+
|      1 | Vitto    |
|      2 | Michael  |
|      3 | Santino  |
|      4 | Fredo    |
|      5 | Luca     |
|      6 | Clemenza |
|     10 | Barzini  |
|      9 | Tataglia |
|      8 | Johnny   |
|      7 | Carlo    |
+--------+----------+

Tai... Os dados excluidos foram re-inseridos, sem erros nem abends (
ETIMOLOGIA: ABEND vem de ABnormal ENDing, mensagens que programas COBOL em
mainframes geravam ). "AH !!!!!!!!! MAS NAO ESTAO ORDENADOS !!!!"

# mysql -u root -psenha -e "Select * from teste order by codigo" test
+--------+----------+
| codigo | nome     |
+--------+----------+
|      1 | Vitto    |
|      2 | Michael  |
|      3 | Santino  |
|      4 | Fredo    |
|      5 | Luca     |
|      6 | Clemenza |
|      7 | Carlo    |
|      8 | Johnny   |
|      9 | Tataglia |
|     10 | Barzini  |
+--------+----------+

, C.Q.D.

So para nao ter duvidas:

# mysql -u root -psenha -e "Show fields from teste" test
+--------+-------------+------+-----+---------+-------+
| Field  | Type        | Null | Key | Default | Extra |
+--------+-------------+------+-----+---------+-------+
| codigo | int(11)     |      | PRI | 0       |       |
| nome   | varchar(30) |      |     |         |       |
+--------+-------------+------+-----+---------+-------+

Veja que codigo É PK da tabela teste.

Atraves do PHP, vc tbm pode utilizar LOAD. Para evitar erros, coloque os
arquivos de importacao no /tmp e rode LOAD DATA como uma query. Em perl, eu
faço algo como

$sql = "LOAD DATA blablabla";
$sth = $dbh->prepare($sql);
$sth->execute() || die "Nao executei a query $sql \n $DBI::errstr\n";

Acredito, e peço desculpas ao grupo, que a discussao ja fugiu (faz tempo )
do escopo. Se vc quiser, batemos mais papo atraves do meu e-mail particular,
a menos que o pessoal nao se incomode com o Off-Topic. Me da uma ideia da
sua estrutura e mensagens de erro e vamos ver se eu consigo te ajudar.

[]'s



reply via email to

[Prev in Thread] Current Thread [Next in Thread]