View Full Version : بهترین روش برای آپدیت بانک sql server 2008 ؟
  
programers0
جمعه 27 بهمن 1391, 01:12 صبح
با سلام
من یه برنامه نوشتم که مرتبا در حال تغییره و ممکنه مثلا امروز برم تغییراتو برای مشتری A انجام بدم و باز فردا برای مشتری B
حالا مشکل اینجاست که من نمیدونم این مشتری تا کجای کار بانکش درسته
مجبورم برم همرو به صورت دستی چک کنم و تغییرات رو اعمال کنم
این تغییرات ممکنه view ، stored procedure و ... باشه
بهترین روش برای حل این مشکل چیه که بتونم یه برنامه جدا واسه خودم بنویسم و همه تغییرات خودکار انجام بشه.
با تشکر
یوسف زالی
شنبه 28 بهمن 1391, 03:54 صبح
سلام
SQLDelta
programers0
شنبه 28 بهمن 1391, 20:35 عصر
میشه ببیشتر توضیح بدید؟
یوسف زالی
شنبه 28 بهمن 1391, 23:35 عصر
توضیح نداره. برنامه ای هست که می خوای.
گوگل کن همه چیزش می ریزه بیرون
benyaminrahimi
یک شنبه 29 بهمن 1391, 08:57 صبح
معمولا شرکت های نرم افزاری خودشون این قضیه رو مینویسن  دو تا روش معمول و جود داره  
1 یه دیتا بیس برای آخرین ورژن تهیه کنید و دیتا مشتری رو تیبل به تیبل به این دیتا بیس انتقال بدین (که تو دیتای زیاد مسایلی داره )
2 (روشی که من استفاده میکنم ) یه ماژول generate sqript بنویسید تو این روش در سیستم نرم افزاری تمام اجزا script میشن مثل table field view stored procedure function primary key ralation index و بعد با یک اسکریپ پاکسازی تمام object های مجازی رو پاک میکنید و sqript های generate sشده رو اجرا میکنید ui و script های این روشو برای فروش دارم اگه خواستین
samani
یک شنبه 29 بهمن 1391, 09:15 صبح
برنامه هايي مثل SQLDelta ، ApexSQLDiff و ... براي پيدا كردن تفاوت ساختار يا اطلاعات جداول خوبه به شكل دستي خوبه ، اما براي كنترل تغييرات برنامه در طي زمان بايد از روش ورژن بندي برنامه استفاده كنيد
يعني اينكه در هر تغيير بانك اطلاعاتي(ساختاري يا اطلاعاتي) ، تغييرات را به شكل اسكريپت براي هر ورژن در يك  Query نگه داريد و هنگام اجراي برنامه اگر ورژن برنامه بزرگتر از ورژن بانك اطلاعاتي بود query مربوطه را اجرا ميكنيد و بعد از انجام عمليات و نداشتن خطا فيلد ورژني كه در بانك اطلاعاتي هست رو با عدد ورژن برنامه آپديت ميكنيد
اگر اسكريپت يك ورژن زياد بود داخل يك Query مثلا به نام qv2_12_1 ، اسكريپتها رو با دستور GO از هم جدا كنيد و از نمونه كد زير براي اسكريپت استفاده كنيد
unit Unit2;
interface
uses
  SysUtils, Classes, Windows, strUtils, DB, ADODB;
type
  TDMMain = class(TDataModule)
    ADOConnection1: TADOConnection;
    TVersion: TADOTable;
    qv2_12_1: TADOQuery;
    qv2_12_2: TADOQuery;
    procedure DataModuleCreate(Sender: TObject);
  private
    function Run(ver: Integer): Boolean;
  public
    { Public declarations }
  end;
var
  DMMain: TDMMain;
implementation
uses ADOInt;
{$R *.dfm}
function GetFileVer(var Major, Minor, Release, Build: word): boolean;
var
  size, len: longword;
  handle: THandle;
  buffer: pchar;
  pinfo: ^VS_FIXEDFILEINFO;
  FileName: String;
begin
  Result := False;
  FileName := ParamStr(0);
  size := GetFileVersionInfoSize(Pointer(FileName), handle);
  if size > 0 then begin
    GetMem(buffer, size);
    if GetFileVersionInfo(Pointer(FileName), 0, size, buffer) then
      if VerQueryValue(buffer, '\', pointer(pinfo), len) then begin
        Major   := HiWord(pinfo.dwFileVersionMS);
        Minor   := LoWord(pinfo.dwFileVersionMS);
        Release := HiWord(pinfo.dwFileVersionLS);
        Build   := LoWord(pinfo.dwFileVersionLS);
        Result  := True;
      end;
    FreeMem(buffer);
  end;
end;
function ExecuteScript(pScript: WideString): boolean;
var i, j: integer;
  s: WideString;
  sl: TStringList;
begin
  Result := False;
  if Trim(pScript) = '' then Exit;
  sl := TStringList.Create;
  try
    pScript := #13#10'GO'#13#10 + pScript + #13#10'GO'#13#10;
    i := 0;
    repeat
      j := PosEx(#13#10'GO'#13#10, UpperCase(pScript), i);
      if (j >= i) and (j > 0) then
        begin
          s := Trim(Copy(pScript, i+1, j-i));
          sl.Text := s;
          while (sl.Count > 0) and (Trim(sl[0]) = #13#10) do
            sl.Delete(0);
          while (sl.Count > 0) and (Trim(sl[sl.Count-1]) = #13#10) do
            sl.Delete(sl.Count-1);
          s := Trim(sl.Text);
          i := j + 4;
          if (s <> '') and (UpperCase(s) <> 'GO') then
            DMMain.ADOConnection1.Execute(Trim(s));
        end;
    until (j = 0) or (i = j);
    Result := True;
  finally
    sl.Free;
  end;
end;
function TDMMain.Run(ver: Integer): Boolean;
begin
  Result := True;
  try
    case ver of
      21201:
        begin
          ExecuteScript(qv2_12_1.SQL.Text);
        end;
      21202:
        begin
          ExecuteScript(qv2_12_2.SQL.Text);
        end
    else ;
    end;
  except on e: Exception do
    begin
      Result := False;
      //log or showmessage(e.Message);
    end;
  end;
end;
procedure TDMMain.DataModuleCreate(Sender: TObject);
var
  i: integer;
  FileMajor, FileMinor, FileRelease, FileBuild: word;
  dbMajor, dbMinor, dbRelease, dbBuild: word;
  FullFileVer, FullDBVer: Integer;
  f: boolean;
begin
  TVersion.Open;
  dbMajor := DMMain.TVersion.FieldByName('MajorVer').AsInteger;
  dbMinor := DMMain.TVersion.FieldByName('MinorVer').AsInteger;
  dbRelease := DMMain.TVersion.FieldByName('ReleaseVer').AsIntege r;
  dbBuild := DMMain.TVersion.FieldByName('BuildVer').AsInteger;
  FullDBVer := StrToIntDef(Format('%d%.2d%.2d', [dbMajor, dbMinor, dbRelease]), -1);
  GetFileVer(FileMajor, FileMinor, FileRelease, FileBuild);
  FullFileVer := StrToInt(Format('%d%.2d%.2d', [FileMajor, FileMinor, FileRelease]));
  f := True;  // f := BackupDB;
  i := FullDBVer + 1;
  while f and (i <= FullFileVer) do
    begin
      f := Run(i);
      inc(i);
    end;
  if f and (FullFileVer > FullDBVer) then
    DMMain.ADOConnection1.Execute('Update Version Set MajorVer = '+IntToStr(FileMajor)+', MinorVer = '+IntToStr(FileMinor)+', ReleaseVer = '+IntToStr(FileRelease)+', BuildVer = '+IntToStr(FileBuild));
end;
end.
یوسف زالی
یک شنبه 29 بهمن 1391, 11:23 صبح
مشکل اسکریبت اینه که داده های شما رو به خطر می ندازه.
فکر کنید اسکریبت یک جدول رو دوباره ران کنید...
دوستان، SQLDelta !
samani
یک شنبه 29 بهمن 1391, 11:41 صبح
تمام تغييرات هر ورژن بايد اتوماتيك انجام شود نه دستي
هر اسكريپت قبل از اجرا بايد در بانك اطلاعاتي چك شود اگر وجود نداشت اجرا ميشود براي مثال
if not exists (select * from dbo.sysobjects where id = object_id(N'dbo.Test') and OBJECTPROPERTY(id, N'IsUserTable') = 1)
CREATE TABLE dbo.Test (
	ID uniqueidentifier NOT NULL ,
	f_ForeignKey uniqueidentifier NOT NULL
) ON [PRIMARY]
GO
IF NOT EXISTS (SELECT * FROM sysobjects where id = object_id(N'PK_Test') and OBJECTPROPERTY(id, N'IsConstraint') = 1)
ALTER TABLE dbo.Test WITH NOCHECK ADD CONSTRAINT PK_Test PRIMARY KEY CLUSTERED (ID) ON [PRIMARY]
GO
if not exists (select * from sysColumns where id = object_id(N'dbo.Test') and Name = 'Title')
  ALTER TABLE Test ADD Title varchar(100) NULL
GO
UPDATE Test SET 
  Title = 'تست' 
WHERE Title IS NULL
GO
benyaminrahimi
یک شنبه 29 بهمن 1391, 12:03 عصر
اگه پارامتر ها با not exists باشه مشکلی پیش نمیاد ... معلومه که تیبل دراپ نباید بشه  منم نوشتم آبکت های مجازی که با دیتا کاری ندارند مثل view..
یوسف زالی
یک شنبه 29 بهمن 1391, 13:44 عصر
خب اون برنامه هم همین چک ها رو خودش انجام می ده.
اون برنامه این قابلیت ها رو داره:
انتخاب جدول - دیاگرام - ویو - استور - فانکشن - یوزر - رول - قانون - قید - دیفالت - کی - فیلد - سینونیم  ...
قابلیت نمایش متنی که در استور متفاوته
قابلیت انتخاب بخشی از تغییرات برای سینک شدن
قابلیت فیلتر کردن آبجکت ها
.
.
حالا اصرار برای دستی انجام دادنش ممکنه یک کم "اختراع مجدد چرخ" باشه
benyaminrahimi
یک شنبه 29 بهمن 1391, 14:43 عصر
بعضی مواقع ترییب SQRIPT مهمه یا مسایل دیگه ... که وقتی تو این مورد خاص کد میزنی دست خودته.. همون کاری که sql data کرده ولی تظمینی نیست که تو همه مسایلی که تو میخای جواب بده ..  وگرنه   این چیزایی که شوما نوشتینم با قابلیت فیلتر!!!!! خود SQL SERVER داره پس این برنامه هم چرخو مجددا اختراع کرده ؟  ............. منظور از دستی انجام دادنشو نفهمیدم
یوسف زالی
یک شنبه 29 بهمن 1391, 15:02 عصر
:)))
فیلتر تعجب نداره!
دستی Generate کردن Script منظور منه.
SQL Server میاد دو تا StoredProc رو مقایسه کنه و بگه کجاهاش متفاوته؟
واقعا؟!
عجب...
benyaminrahimi
یک شنبه 29 بهمن 1391, 15:17 عصر
نه اینایی که شوما نوشتی گفتم آخه رو فیلتر کردن خیلی مانور داده بودین (قابلیت ) که sql داره اینارو  
اون برنامه این قابلیت ها رو داره:
انتخاب جدول - دیاگرام - ویو - استور - فانکشن - یوزر - رول - قانون - قید - دیفالت - کی - فیلد - سینونیم ...
قابلیت نمایش متنی که در استور متفاوته
قابلیت انتخاب بخشی از تغییرات برای سینک شدن
قابلیت فیلتر کردن آبجکت ها
مقایسه و فهمیدن اختلاف دو پروسیجر تو ورژنیگ زیاد مهم نیست ... تو check in کردن برنامه نویسا مهمه 
من برای اینکه ساده تر بگم یه نمونه کدای تغییرات جدولمو میذارم که خیلی راحته و با برنامه خودم در عرض 2 ثانیه اسکریپت میده 
IF EXISTS (SELECT * FROM tempdb.dbo.sysobjects WHERE id = object_id(N'[tempdb].[dbo].[#tblSQL]'))
DROP TABLE [dbo].[#tblSQL]
CREATE TABLE #tblSQL
( 
sc VARCHAR(max) NOT NULL
)
INSERT INTO #tblSQL
(
	sc
)
SELECT 
       'IF NOT EXISTS (SELECT * FROM sys.objects WHERE object_id = OBJECT_ID(N'+''''+'[dbo].[' + 
   so.name ++ ']'+''''+') AND type in (' + '''U'''
       + '))   begin create table [' + so.name + '] (' + o.list + ')' + CASE 
                                                                             WHEN 
                                                                                  tc.Constraint_Name 
                                                                                  IS 
                                                                                  NULL THEN 
                                                                                  ''
                                                                             ELSE 
                                                                                  'ALTER TABLE [' 
                                                                                  + 
                                                                                  so.Name 
                                                                                  +
                                                                                  '] ADD CONSTRAINT [' 
                                                                                  + 
                                                                                  tc.Constraint_Name 
                                                                                  +
                                                                                  '] PRIMARY KEY ' 
                                                                                  + 
                                                                                  ' (' 
                                                                                  +
                                                                                  LEFT(j.List, LEN(j.List) - 1) 
                                                                                  + 
                                                                                  ')  '
                                                                                
                                                                        END+' end ' AS tbl_sc
FROM   sysobjects so
       CROSS APPLY 
(
    SELECT '  [' + column_name + '] ' +
           data_type + CASE data_type
                            WHEN 'sql_variant' THEN ''
                            
                            WHEN 'text' THEN ''
                            WHEN 'IMAGE' THEN ''
                            WHEN 'decimal' THEN '(' + CAST(numeric_precision_radix AS VARCHAR) 
                                 + ', ' + CAST(numeric_scale AS VARCHAR) + ')'
                            ELSE COALESCE(
                                     '(' + CASE 
                                                WHEN character_maximum_length =
                                                     -1 THEN 'MAX'
                                                ELSE CAST(character_maximum_length AS VARCHAR)
                                           END + ')',
                                     ''
                                 )
                       END + ' ' +
           CASE 
                WHEN EXISTS (
                         SELECT id
                         FROM   syscolumns
                         WHERE  OBJECT_NAME(id) = so.name
                                AND NAME = column_name
                                AND COLUMNPROPERTY(id, NAME, 'IsIdentity') = 1
                     ) THEN 'IDENTITY(' +
                     CAST(IDENT_SEED(so.name) AS VARCHAR) + ',' +
                     CAST(IDENT_INCR(so.name) AS VARCHAR) + ')'
                ELSE ''
           END + ' ' + (CASE WHEN IS_NULLABLE = 'No' THEN 'NOT ' ELSE '' END) +
           'NULL ' +
           CASE 
                WHEN information_schema.columns.COLUMN_DEFAULT IS NOT NULL THEN 
                     'DEFAULT ' + information_schema.columns.COLUMN_DEFAULT
                ELSE ''
           END + ', '
    FROM   information_schema.columns
    WHERE  table_name = so.name
    ORDER BY
           ordinal_position
           FOR XML PATH('')
) o(list)
LEFT JOIN information_schema.table_constraints tc
            ON  tc.Table_name = so.Name
            AND tc.Constraint_Type = 'PRIMARY KEY  '
       CROSS APPLY
(
    SELECT '[' + Column_Name + '], '
    FROM   information_schema.key_column_usage kcu
    WHERE  kcu.Constraint_Name = tc.Constraint_Name  
    ORDER BY
           ORDINAL_POSITION
           FOR XML PATH('')
)
j(list)
WHERE  xtype = 'U'
       AND NAME NOT IN ('dtproperties')
       
       
       SELECT * FROM #tblSQL
یوسف زالی
یک شنبه 29 بهمن 1391, 20:55 عصر
مانور؟!
بین اون همه پیامبر جرجیس رو مثال می زنی؟!
برای من مهمه که چرا اختلاف وجود داره.
نظر شما هم محترم. موفق باشید.
 
vBulletin® v4.2.5, Copyright ©2000-1404, Jelsoft Enterprises Ltd.