;参考了许多脚本例子,这个脚本包含了大部分可能用到设置。我的这个安装程序中用到了安装数据库、写INI、定制安装等 ; 脚本用 Inno Setup 脚本向导生成。 ; 查阅文档获取创建 INNO SETUP 脚本文件详细资料! [Setup] AppName= 天翔纤维检验管理系统 AppVerName=天翔纤维检验管理系统 V2008 AppPublisher=青岛天翔软件有限公司 AppPublisherURL=http://www.tinsoft.cn AppSupportURL=http://www.tinsoft.cn AppUpdatesURL=http://www.tinsoft.cn DefaultDirName= {pf}/天翔纤维检验管理系统 DefaultGroupName=天翔纤维检验管理系统 LicenseFile=D:/安装程序 /FiberTest/Lisence.txt OutputDir=D:/安装程序/FiberTest/Out OutputBaseFilename=Setup Compression=lzma SolidCompression=yes [Languages] Name: chi; MessagesFile: compiler:Default.isl [Tasks] Name: desktopicon; Description: {cm:CreateDesktopIcon}; GroupDescription: {cm:AdditionalIcons}; Flags: unchecked Name: quicklaunchicon; Description: {cm:CreateQuickLaunchIcon}; GroupDescription: {cm:AdditionalIcons}; Flags: unchecked [Types] Name: full; Description: 完全安装 Name: Client; Description: 客户端安装 Name: Server; Description: 服务器端安装 Name: Custom; Description: 定制安装; Flags: iscustom [Components] Name: main; Description: 必须组件; Types: full Client Server Custom; Flags: fixed Name: Server; Description: 服务器组件; Types: full Server Name: Client; Description: 客户端组件; Types: full Client Name: Custom; Description: 定制组件; Types: Custom [Files] Source: 安装文件/FiberTest.exe; DestDir: {app}; Flags: ignoreversion; Components: Client Source: 安装文件/Data/*; DestDir: {app}/Data; Flags: ignoreversion recursesubdirs createallsubdirs; Components: Server Source: 安装文件/Report/*; DestDir: {app}/Report; Flags: ignoreversion recursesubdirs createallsubdirs; Components: Client; Tasks: Source: 安装文件/UPower.ini; DestDir: {app}; Components: Client Source: D:/安装程序/FiberTest/安装文件/background.bmp; DestDir: {app}; Flags: ignoreversion; Components: Client Source: D:/安装程序/FiberTest/安装文件/FiberTest.chm; DestDir: {app}; Flags: ignoreversion; Components: Client Source: 安装文件/FiberTest.ini; DestDir: {app}; Components: Client Source: D:/安装程序/FiberTest/安装文件/PY.dll; DestDir: {app}; Flags: ignoreversion; Components: Client Source: D:/安装程序/FiberTest/安装文件/PY.exe; DestDir: {app}; Flags: ignoreversion; Components: Client Source: D:/安装程序/FiberTest/安装文件/TinsZip.dll; DestDir: {app}; Flags: ignoreversion; Components: Client Source: 安装文件/UPower.exe; DestDir: {app}; Flags: ignoreversion; Components: Client ; 注意: 不要在任何共享系统文件中使用“Flags: ignoreversion” [Icons] Name: {group}/天翔纤维检验管理系统; Filename: {app}/FiberTest.exe Name: {group}/使用手册; Filename: {app}/FiberTest.chm; IconFilename: {app}/FiberTest.chm; Tasks: ; Languages: Name: {group}/{cm:UninstallProgram,天翔纤维检验管理系统}; Filename: {uninstallexe} Name: {userdesktop}/天翔纤维检验管理系统; Filename: {app}/FiberTest.exe; Tasks: desktopicon Name: {userappdata}/Microsoft/Internet Explorer/Quick Launch/天翔纤维检验管理系统; Filename: {app}/FiberTest.exe; Tasks: quicklaunchicon [Run] Filename: {app}/FiberTest.exe; Description: {cm:LaunchProgram,天翔纤维检验管理系统}; Flags: nowait postinstall skipifsilent unchecked; Components: ; Tasks: ; Languages: Filename: {app}/UPower.exe; Flags: nowait postinstall unchecked skipifsilent [INI] Filename: D:/安装程序/FiberTest/安装文件/UPower.ini; Section: UPower; Key: ConnectString; String: "Provider=SQLOLEDB.1;Persist Security Info=False;User ID=sa;Initial Catalog=FiberTest;Data Source={code:GetServer}" Filename: D:/安装程序/FiberTest/安装文件/FiberTest.ini; Section: FiberTest; Key: ApplicationTitle; String: 天翔管理系统 Filename: D:/安装程序/FiberTest/安装文件/FiberTest.ini; Section: FiberTest; Key: ConnString; String: "Provider=SQLOLEDB.1;Persist Security Info=False;User ID=sa;Initial Catalog=FiberTest;Data Source={code:GetServer}"; Components: ; Tasks: ; Languages: Filename: D:/安装程序/FiberTest/安装文件/FiberTest.ini; Section: FiberTest; Key: SocketServer; String: localhost Filename: D:/安装程序/FiberTest/安装文件/FiberTest.ini; Section: FiberTest; Key: SocketPort; String: 211 Filename: D:/安装程序/FiberTest/安装文件/FiberTest.ini; Section: FiberTest; Key: ServerName; String: UPower.UserPower Filename: D:/安装程序/FiberTest/安装文件/FiberTest.ini; Section: FiberTest; Key: BillNOLen; String: 10 Filename: D:/安装程序/FiberTest/安装文件/FiberTest.ini; Section: FiberTest; Key: BillPrintPreview; String: 1 Filename: D:/安装程序/FiberTest/安装文件/FiberTest.ini; Section: FiberTest; Key: BillPrint; String: 0 Filename: D:/安装程序/FiberTest/安装文件/FiberTest.ini; Section: FiberTest; Key: COMConnection; String: 1 Filename: D:/安装程序/FiberTest/安装文件/FiberTest.ini; Section: FiberTest; Key: DatabaseType; String: MSSQL Filename: D:/安装程序/FiberTest/安装文件/FiberTest.ini; Section: FiberTest; Key: DepartmentID; String: Tins Filename: D:/安装程序/FiberTest/安装文件/FiberTest.ini; Section: FiberTest; Key: Department; String: Tins Filename: D:/安装程序/FiberTest/安装文件/FiberTest.ini; Section: FiberTest; Key: WebNav; String: Filename: D:/安装程序/FiberTest/安装文件/FiberTest.ini; Section: FiberTest; Key: 单位名称; String: TINS Filename: D:/安装程序/FiberTest/安装文件/FiberTest.ini; Section: FiberTest; Key: 输入法; String: 中文 (简体) - 微软拼音 Filename: D:/安装程序/FiberTest/安装文件/FiberTest.ini; Section: FiberTest; Key: 任务单号自动生成; String: 1 Filename: D:/安装程序/FiberTest/安装文件/FiberTest.ini; Section: FiberTest; Key: 打印预览; String: 1 Filename: D:/安装程序/FiberTest/安装文件/FiberTest.ini; Section: FiberTest; Key: 条码打印机; String: Microsoft Office Document Image Writer Filename: D:/安装程序/FiberTest/安装文件/FiberTest.ini; Section: FiberTest; Key: 普通打印机; String: EPSON ME 1 Filename: D:/安装程序/FiberTest/安装文件/FiberTest.ini; Section: FiberTest; Key: 打印机选择; String: 0 [Code] { 关于数据库操作 } //http://hi.baidu.com/can2786/blog/item/e8c296cefeacdf0692457ef0.html // 说明一下:这块程序的前半部分在INNO SETUP的实例里面就有,而后面如果对数据库进行备份和还原在实例里面没有,在网上也不好找,是本人费了好大劲一句一句试出来的,请大家转摘时注明,以表示对个人劳动的尊重。谢谢! {--- SQLDMO ---} //关于SQLDMO的相关知识大家可以去网上搜 const //SQL 服务器名称,这个名称在安装SQL时会要求有个服务器名称的输入,所有每台机器上打开SQL服务器时看到的名称都不一样,如我如下图,但这里我们可以用一个通用的名称,就是(local),表示这个服务器是本地的。这样就可以了。 //SQLServerName = '(LOCAL)'; SQLDMOGrowth_MB = 0; var UserPage: TInputQueryWizardPage; UsagePage: TInputOptionWizardPage; LightMsgPage: TOutputMsgWizardPage; KeyPage: TInputQueryWizardPage; ProgressPage: TOutputProgressWizardPage; DataDirPage: TInputDirWizardPage; SQLServerName:String; //数据库的创建与还原事件写完了,但是它不会智能的知道什么时候去执行,所以我们要告诉它什么时候执行。下面是在程序安装完,在结束页面上建立了一个BUTTON按钮,当按下这个按钮时,会执行数据库的事件响应。 {---} //创建一个button procedure CreateButton(ALeft, ATop: Integer; ACaption: String; ANotifyEvent: TNotifyEvent); begin with TButton.Create(WizardForm) do //button对象的创建 begin Left := ALeft; //button的位置与宽高 Top := ATop; Width := WizardForm.CancelButton.Width; Height := WizardForm.CancelButton.Height; Caption := ACaption; //button的名称 OnClick := ANotifyEvent; //这个是给创建的button指定一个父窗口,也就是说让它在哪个页面上边显示出来 Parent := WizardForm.FinishedPage; //这里指定的是窗体的结束页 end; end; //这是创建一个按钮按下的事件,这个按钮就是在安装向导中页面中建立的一个“配置数据库”的按钮 procedure SQLDMOButtonOnClick(Sender: TObject); var //用到的一些变量 SQLServer, Database, DBFile, LogFile: Variant; IDColumn, NameColumn, Table,oBackup,oRestore: Variant; db_path:string; //这个变量用来保存读取注册表的键值 ResultStr: String; begin { Create the main SQLDMO COM Automation object } //检查是否已安装SQL try SQLServer := CreateOleObject('SQLDMO.SQLServer'); except RaiseException('您还没有安装SQL数据库.'#13#13'(Error ''' + GetExceptionMessage + ''' occurred)'); end; { Connect to the Microsoft SQL Server } //连接SQL SQLServer.LoginSecure := True; SQLServer.Connect(SQLServerName); //SQLServer.Connect(SQLServerName,'sa',''); //MsgBox('连接到SQL服务器 ''' + SQLServerName + '''.', mbInformation, mb_Ok); { Setup a database } try MsgBox(ExpandConstant('{app}')+'/data/FiberTest_Data.MDF;'+ExpandConstant('{app}')+'/data/FiberTest_Log.LDF', mbInformation, mb_Ok); //SQLServer.AttachDB('FiberTest',ExpandConstant('{app}')+'/data/FiberTest_Data.MDF;'+ExpandConstant('{app}')+'/data/FiberTest_Log.LDF'); SQLServer.AttachDBWithSingleFile('FiberTest',ExpandConstant('{app}')+'/data/FiberTest_Data.MDF'); MsgBox('数据库安装成功!', mbInformation, mb_Ok); except MsgBox('数据库安装失败!', mbInformation, mb_Ok); end; { //创建SQL数据库文件 Database := CreateOleObject('SQLDMO.Database'); Database.Name := 'FiberTest'; //要创建的数据库名称 DBFile := CreateOleObject('SQLDMO.DBFile'); DBFile.Name := 'FiberTestData1'; // 数据库记录 DBFile.PhysicalName := 'c:/program files/microsoft sql server/mssql/data/FiberTest_Data.MDF'; DBFile.PrimaryFile := True; DBFile.FileGrowthType := SQLDMOGrowth_MB; DBFile.FileGrowth := 1; Database.FileGroups.Item('PRIMARY').DBFiles.Add(DBFile); LogFile := CreateOleObject('SQLDMO.LogFile'); LogFile.Name := 'FiberTestLog1'; //数据库日记 LogFile.PhysicalName := 'c:/program files/microsoft sql server/mssql/data/FiberTest_Log.LDF'; Database.TransactionLog.LogFiles.Add(LogFile); // Add the database //添加数据库 SQLServer.Databases.Add(Database); } //MsgBox('Added database ''' + Database.Name + '''.', mbInformation, mb_Ok); { // 数据备份 oBackup := CreateOleObject('SQLDMO.Backup'); //创建一个备份对象 oBackup.Database := 'louyu'; //要备份的数据库名称 oBackup.Files := 'f:/louyu3.bak'; //备份到什么地方 oBackup.BackupSetName := 'louyu3.bak'; //备份的名称 oBackup.BackupSetDescription := 'bakDescription'; oBackup.Initialize := true; oBackup.SQLBackup(sqlServer); //执行SQL备份操作 //数据还原 //重点说明: //数据库的备份文件在打好的包中的某个位置,要还原数据库首先要找到备份的文件,找备份的文件的话在这之前还要知道软件安装到了什么地方,也就是安装路径。在程序安装时我们在注册表中建立了相关信息,其中有软件安装路径的记录,关于注册表请查阅前面写的“INNO SETUP注册表的添加与读取”。 //为什么还原数据库时用这种方法呢,好像是绕了个圈子一样,其实我也认为这可能不是一种好方法,但是在这我不知道还有什么别的方法来获得安装包中的数据(文件)或软件要安装的路径。app、pf等在这都无法直接使用,所以才用了这种笨方法。 //如果哪位朋友有好方法,请告知我。 //从注册表中获得程序安装的路径,根据路径找到还原数据库的备份文件。 if RegQueryStringValue(HKLM, 'SOFTWARE/*******', 'Server', ResultStr) then begin ResultStr := RemoveQuotes(ResultStr); msgbox(resultstr,mbinformation,mb_ok); try oRestore := CreateOleObject('SQLDMO.Restore'); //创建还原对象 oRestore.Database := 'dbase'; //还原的数据库名称 db_path:=resultstr + '/数据库文件/dbase.bak'; //备份文件的路径 MsgBox(db_path,mbinformation,mb_ok); //测试一下看路径对不对 oRestore.files :=db_path; //指定备份文件 oRestore.replacedatabase := true; oRestore.sqlrestore(sqlserver); //执行还原操作 MsgBox('数据库还原成功!',mbinformation,mb_ok); except MsgBox('数据库还原失败!,请重试或查阅帮助文档进行手动配置!',mbinformation,mb_ok); end; end; } end; procedure InitializeWizard; var Left, Top, TopInc: Integer; begin //Left := WizardForm.WelcomeLabel2.Left; //TopInc := WizardForm.CancelButton.Height + 8; //Top := WizardForm.WelcomeLabel2.Top + WizardForm.WelcomeLabel2.Height - 4*TopInc; //CreateButton(Left, Top, '安装数据库(&S)', @SQLDMOButtonOnClick); { 创建页面 } UserPage := CreateInputQueryPage(wpWelcome, '服务器信息', '请填写服务器的名称,该服务器为安装了SQL Server的计算机。', '请指定你的名字和公司,然后单击“下一步”。'); UserPage.Add('服务器名称:', False); UsagePage := CreateInputOptionPage(UserPage.ID,'安装选择', '进行客户端还是服务器端安装?','请指定你想安装的方式,然后单击“下一步”。', True, False); UsagePage.Add('安装数据库'); UsagePage.Add('不安装数据'); {设置默认值,如果可能,使用这些设置最后一次贮存} UserPage.Values[0] := GetPreviousData('Name', ExpandConstant('{computername}')); case GetPreviousData('UsageMode', '') of 'Server': UsagePage.SelectedValueIndex := 0; 'Client': UsagePage.SelectedValueIndex := 1; else UsagePage.SelectedValueIndex := 1; end; end; procedure RegisterPreviousData(PreviousDataKey: Integer); var UsageMode: String; begin { 贮存你可以下次进行恢复的设置 } SetPreviousData(PreviousDataKey, 'Name', UserPage.Values[0]); case UsagePage.SelectedValueIndex of 0: UsageMode := 'Server'; 1: UsageMode := 'Client'; end; end; function ShouldSkipPage(PageID: Integer): Boolean; begin { 跳过不显示的页面 } end; function NextButtonClick(CurPageID: Integer): Boolean; var I: Integer; begin { 在用户继续前进行验证 } if CurPageID = UserPage.ID then begin if UserPage.Values[0] = '' then begin MsgBox('你必须输入服务器的名字。', mbError, MB_OK); Result := False; end else begin SQLServerName:=UserPage.Values[0]; Result := True; end; end else Result :=True; end; function UpdateReadyMemo(Space, NewLine, MemoUserInfoInfo, MemoDirInfo, MemoTypeInfo, MemoComponentsInfo, MemoGroupInfo, MemoTasksInfo: String): String; var S: String; Left, Top, TopInc: Integer; begin { 填写带普通设置和自定义设置的“准备演示” } S := ''; S := S + '服务器名称:' + NewLine; S := S + Space + UserPage.Values[0] + NewLine; S := S + NewLine; S := S + '使用模式:' + NewLine + Space; case UsagePage.SelectedValueIndex of 0: S := S + '服务器端'; 1: S := S + '客户端'; end; S := S + NewLine + NewLine; S := S + MemoDirInfo + NewLine; Result := S; Left := WizardForm.WelcomeLabel2.Left; TopInc := WizardForm.CancelButton.Height + 8; Top := WizardForm.WelcomeLabel2.Top + WizardForm.WelcomeLabel2.Height - 4*TopInc; if UsagePage.SelectedValueIndex = 0 then CreateButton(Left, Top, '安装数据库(&S)', @SQLDMOButtonOnClick); end; function GetServer(Param: String): String; begin Result := UserPage.Values[0]; end; function GetUser(Param: String): String; begin { Return a user value } { Could also be split into separate GetUserName and GetUserCompany functions } if Param = 'Name' then Result := UserPage.Values[0]; end;