Foros Club Delphi

Foros Club Delphi (https://www.clubdelphi.com/foros/index.php)
-   Firebird e Interbase (https://www.clubdelphi.com/foros/forumdisplay.php?f=19)
-   -   crear un scrip desde codigo con campo blob (https://www.clubdelphi.com/foros/showthread.php?t=45825)

Lupita 14-07-2007 19:52:25

crear un scrip desde codigo con campo blob
 
Hola estube viendo los archivos sobre el tema de campos blob y no encontre uno que me ayudara este es mi problema

Quiero hacer un script de un catalogo dentro de un sistema que al momento de apretarle a el boton de genear script me genere un archivo del registro actual para guardarlo y luego en el mismo sistema pero en otra base de datos ejecutarlo y que me agrege ese registro en este catalogo uso campos, varchar, integer y blob, estoy usando ibQuerys. en Delphi 6 con Interbase

Que me sugieren

egostar 14-07-2007 19:58:02

Puedes usar un DDL utilizando el componente IBScript que tienes en la carpeta IBX o Interbase.

En la propiedad Script escribes lo que deseas hacer y lo ejecutas con esto.

Código Delphi [-]
IBScript1.ExecuteScript;

Salud OS.

Lupita 14-07-2007 20:09:08

ok dejame probarlo
 
gracias si

Lupita 14-07-2007 20:20:12

a que te refieres con poner lo que quiero hacer
 
en la propiedad scrip si quiero que el script inserte los datos que estoy viendo en el catalogo como le debo deponer?

egostar 16-07-2007 18:59:35

Lo que yo hice en su momento fue:

Para crear una base de datos, genero un script mas o menos así:

Código SQL [-]
 
SET SQL DIALECT 3;
CREATE DATABASE 'Base.fdb'
USER 'SYSDBA' PASSWORD 'masterkey'
PAGE_SIZE 1024
DEFAULT CHARACTER SET NONE;
 
CREATE TABLE NombreTabla
(
 Campo_Entero INTEGER,
 Campo_VarChar VARCHAR(15),
 Campo_Blob BLOB SUB_TYPE 1 
);

Esto lo pego en un IBScript para ejecutarlo como ya te había mencionado, (aunque creo que se puede hacer directamente en el Script, no estoy seguro).

Posteriormente genero un IBSQL para insertar el registro que quiera en la tabla, sin embargo aqui necesitaremos ayuda de alguno de nuestros compañeros para insertar un registro Blob a través de un query ya que yo no lo se hacer aún.:o

Salud OS.

rastafarey 19-07-2007 17:32:51

Resp
 
Si es un blod tipo texto simplemente ejecutalo como si furar un acadena(char o varchar) pero si son archivos bianrios y vas almacenar alchivos binarios la cosa cambia pero si vas almacenar texto es igual que lo anterior.

ariefez 20-07-2007 21:33:04

Si la base de datos tienen alguna forma de comunicarse (Estan en la misma red o via Internet) solo se tendrias q copiar los registros de una a otra base de forma directa. Osea conectandote a una, leer el registro en cuestion y hacer un insert con los valores q son necesarios en la otra BD.

si no hay comunicacion posible entre ambas BD siempre hay otra salida, usar archivos (almacenar el registro en un archivo e insertar el contenido en la otra base).

este es el codigo q usaba en esa situacion, faltan pulir algunas cosas, pero almenos no daba problemas


Para generar el registro de insercion

Código Delphi [-]
var
  Tabla, Fields, ValueScript, Condicion: string;
  SelectSQL: string;
  PK: Integer;
  I: Integer;

  MSFields: TMemoryStream;
  BufferSize: Int64;
  InsertSQL : string[255]; // Sentencia Insert limitada
  FieldCount: Integer; // Numero de campos
  FieldValue: string[255]; // -> Falta mejorar, Esta limitado (Deberia ser Variant)
  FieldBlob: TMemoryStream;
begin
  Fields := 'CAR_ID, CAR_NOM, CAR_RDE'; // Campos a guardar
  Tabla := 'CARGOS'; // Nombre de la tabla
  Condicion := 'CAR_ID = :PK'; //Condicion para seleccionar un registro
  PK := 7; // Valor del parametro de "Condicion"
  ValueScript := ':CAR_ID, :CAR_NOM, :CAR_RDE'; // parametros de la sentencia Insert

  fptrDB.Active := True; // activo la transaccion
  MSFields := TMemoryStream.Create; // Contenedor de los valores de los campos
  try

    { Sentencia SQL de insercion - Falta mejorar (Tiene un limite de 255 caracteres)}
    InsertSQL := 'INSERT INTO ' + Tabla + ' (' + Fields + ')'
      + '  VALUES (' + ValueScript + ')';
    //Tamaño
    BufferSize := Length(InsertSQL) + 1;
    MSFields.Write(BufferSize, SizeOf(Int64));
    //Valor
    MSFields.Write(InsertSQL, BufferSize);

    {Sentencia SQL}
    SelectSQL := 'SELECT ' + Fields + ' FROM ' + Tabla + ' WHERE ' + Condicion;
    { Obtengo los campos de la tabla }
    fpdsTabla.SelectSQL.Clear;
    fpdsTabla.SelectSQL.Add(SelectSQL);
    fpdsTabla.ParamByName('PK').Value := PK; // Varia segun el contenido de "Condicion"
    fpdsTabla.Open;

    { Numero de registros }
    FieldCount := fpdsTabla.FieldCount;
    MSFields.Write(FieldCount, SizeOf(Integer));

    { Valores de los campos }
    for I := 0 to fpdsTabla.FieldCount - 1 do
      if fpdsTabla.Fields[i].IsNull then
      begin
        {Tamaño}
        BufferSize := 0;
        MSFields.Write(BufferSize, SizeOf(Int64));
      end else
        if fpdsTabla.Fields[i].IsBlob then
        begin
          FieldBlob := BlobToStream(fpdsTabla.Fields[i]);
          BufferSize := IfThen(Assigned(FieldBlob), FieldBlob.Size);
          if Assigned(FieldBlob) then
          begin
            {Tamaño}
            MSFields.Write(BufferSize, SizeOf(Int64));
            {Valor}
            if 0 < BufferSize then
              FieldBlob.SaveToStream(MSFields);
            FieldBlob.Free;
          end else
            MSFields.Write(BufferSize, SizeOf(Int64));
        end else
        begin
          FieldValue := fpdsTabla.Fields[i].AsString;
          {Tamaño}
          BufferSize := Length(FieldValue) + 1;
          MSFields.Write(BufferSize, SizeOf(Int64));
          {Valor}
          MSFields.Write(FieldValue, BufferSize);
        end;

    fpdsTabla.Close;
    { Guardo el registro }
    MSFields.SaveToFile(ExtractFilePath(Application.ExeName) + 'Registro.msr');
  finally
    fptrDB.Active := False;
    MSFields.Free;
  end;
end;

para leer el registro e ingresarlo en otra BD

Código Delphi [-]
var
  MSFields: TMemoryStream;
  BufferSize: Int64;
  InsertSQL : string[255];
  FieldCount: Integer; // Numero de campos
  FieldValue: string[255];
  FieldBlob: TMemoryStream;
  InpBuf: Pointer;
  I: Integer;
begin
  fptrDB.StartTransaction;
  MSFields := TMemoryStream.Create;
  try
    { Obtengo el registro }
    MSFields.LoadFromFile(ExtractFilePath(Application.ExeName) + 'Registro.msr');
    { Sentencia SQL de insercion }
    MSFields.Read(BufferSize, SizeOf(Int64));
    MSFields.Read(InsertSQL, BufferSize);
    { Numero de registros }
    MSFields.Read(FieldCount, SizeOf(Integer));
    { Valores de los campos }
    fpqyTabla.SQL.Clear;
    fpqyTabla.SQL.Add(InsertSQL);
    fpqyTabla.Prepare; // Preparo la consulta (reconocimiento de tipos...)
    for I := 0 to FieldCount - 1 do
    begin
      fpqyTabla.Params[i].Clear;
      if fpqyTabla.Params[i].IsBlob then
      begin
        InpBuf := nil;
        FieldBlob := TMemoryStream.Create;
        try
          {Tamaño}
          MSFields.Read(BufferSize, SizeOf(Int64));
          if 0 < BufferSize then
          begin
            GetMem(InpBuf, BufferSize);
            {Valor}
            MSFields.Read(InpBuf^, BufferSize);
            FieldBlob.Write(InpBuf^, BufferSize);
            fpqyTabla.Params[i].LoadFromStream(FieldBlob);
          end;
        finally
          FieldBlob.Free;
          if Assigned(InpBuf) then
            FreeMem(InpBuf);
        end;
      end else
      begin
        {Tamaño}
        MSFields.Read(BufferSize, SizeOf(Int64));
        if 0 < BufferSize then
        begin
          MSFields.Read(FieldValue, BufferSize);
          fpqyTabla.Params[i].Value := FieldValue;
        end;
      end;
    end;
    fpqyTabla.ExecQuery;
  finally
    fptrDB.Commit;
    MSFields.Free;
  end;
end;

e usado los componentes FibPLus pero no creo q haya problemas con otros ya que uso propiedades generales.

ariefez 20-07-2007 21:41:55

Me olvide de algo: la funcion BlobToStream

Código Delphi [-]
function BlobToStream(Field: TField): TMemoryStream;
begin
  Result := nil;
  if Field.IsBlob then
  begin
    Result := TMemoryStream.Create;
    try
      TFIBBlobField(Field).SaveToStream(Result);
    except
      FreeAndNil(Result);
    end;
  end;
end;

TFIBBlobField pertenece a FibPlus debe cambiarlo al tipo q usa interbase o prueba con el tipo TBlobField


La franja horaria es GMT +2. Ahora son las 17:54:28.

Powered by vBulletin® Version 3.6.8
Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
Traducción al castellano por el equipo de moderadores del Club Delphi