Автоматическая сборка проектов

Обсуждаются как существующие проекты (перевод документации, информационная система и т.п.), так и создание новых.

Модератор: Модераторы

Автоматическая сборка проектов

Сообщение mr.denton » 10.09.2006 01:16:34

Вот решил поделится плодом двухдневных мучений.
Был у меня батничек, примерно такого содержания
Код: Выделить всё
dcc32 project1.dpr
copy project1.exe bin

Использовался он тестером при сборке нового дистрибутива из только что загруженных исходников. И вот решил я его немного облогородить, добавить пару фич...
Преследовал я две цели:
1) Автоинкрементация номера сборки, просто очень хотелось.
2) Чтобы было поуниверсальней ( проектов у нас много ).
Ну и в качестве фич еще сборка справки и документации...
В итоге я пришел к такой схеме: в папку с проектом кидается файл примерно следующего содержания:
Код: Выделить всё
#[version]
vmajor=1
vminor=0
vrelease=0
vbuild=55
#[project]
name=FSC: Shop Complectation
copyright=2005-2006 asu.gdm
dpr=fsc.dpr
help=help\fsc.hhp
#[options]
gen_doc=no
bin_dir=bin
other_files=fsc.conf

Здесь строки, начинающиеся на # - просто комментарии. Назначение параметров в разделах version и project должно быть понятно, а о разделе options поподробнее:
gen_doc - генерация документации( используется pasdoc )
bindir - папка, в которую поместится готовый дистрибутив
other_files - файлы, необходимые для работы программы, кроме экзешника и справки.
Если какой-то параметр не указан или не имеет смысла, операция, в которой он используется не выполняется.
А далее из командной строки запускается make.bat, который на основе параметров из этого файла делает все что нужно.
Исходники состоят из двух файлов. Их текст:
gdoc.bat
Код: Выделить всё
@ECHO OFF
REM константы:
SET ADD_DIR="%~dp0\gdoc_files"
SET STYLE_FILE="%ADD_DIR%\pasdoc.css"
SET SOURCES_FILE="underdoc.tmp"
SET DEFINES_FILE="defines.tmp"
SET FOOTER_FILE="footer.html"
SET DOC_DIR="doc"
REM создание списка исходников
DIR *.pas /B > %SOURCES_FILE%
REM создание списка definов
ECHO MSWINDOWS>>%DEFINES_FILE%
ECHO WIN32>>%DEFINES_FILE%
REM создание footer'a
ECHO ^<hr noshade="noshade" size="1"^> >> %FOOTER_FILE%
ECHO copyright(c) 2005-2006 ^<a href="http://kid" target="main"^>asu.gdm^</a^> ^| generated %DATE% >> %FOOTER_FILE%
REM создание папки с будущей документацией
IF EXIST %DOC_DIR% (
   REM Если папка уже есть, из нее все удаляется!
   DEL %DOC_DIR%\* /Q /S
) ELSE (
   MD %DOC_DIR% )
REM Определяем имя проекта
IF {%1}=={} (
   SET PROJECT_TITLE=""
) ELSE (
   SET PROJECT_TITLE="--title="%1""
)
REM Cоздаем доки
pasdoc --source=%SOURCES_FILE% --output=%DOC_DIR% --staronly ^
   --visible-members=private,protected,public,published --use-tipue-search ^
   --auto-abstract --language=ru.1251 %PROJECT_TITLE% ^
   --conditionals=%DEFINES_FILE% --exclude-generator --auto-link ^
   --footer=%FOOTER_FILE% --css=%STYLE_FILE%
REM Чистим мусор
DEL %SOURCES_FILE% %DEFINES_FILE% %FOOTER_FILE% /Q /S

make.bat
Код: Выделить всё
@ECHO off
REM константы
SET RC_FILE=version.rc
SET HHC_COMP="c:\Program Files\HTML Help Workshop\hhc.exe"
REM имя makefile'лa
IF {%1}=={} (
   SET MAKEFILE=makefile.gdm
) ELSE (
   SET MAKEFILE=%1
)
REM Если макфайла нет, создаем новый и выходим
IF NOT EXIST %MAKEFILE% (
   CALL :CONF_WRITE >%MAKEFILE%
   GOTO :EOF
)

REM Процесс компиляции
CALL :CONF_READ && ^
CALL :RC_BUILD > %RC_FILE% && ^
CALL :RES_COMP && ^
CALL :EXE_COMP && ^
CALL :HELP_COMP && ^
CALL :GEN_DOC && ^
CALL :TMP_CLEAN && ^
CALL :BIN_COPY && ^
CALL :CONF_WRITE > %MAKEFILE% && CALL :OK
GOTO :END

REM ::::::::::::::::::::::::::::::::::::::::::::::   Functions   ::::::::::::::

REM Чтение макфайла
:CONF_READ
FOR /f "eol=# delims== TOKENS=1,2" %%i IN (%MAKEFILE%) DO (
   SET %%i=%%j
)
EXIT /b 0

REM Сборка ресурсов
:RC_BUILD
REM Выходим, если не надо
IF "%DPR%"=="" (
   EXIT /b 0
)
REM Выводим файл ресурсов
ECHO VS_VERSION_INFO VERSIONINFO
ECHO FILEVERSION %VMAJOR%,%VMINOR%,%VRELEASE%,%VBUILD%
ECHO PRODUCTVERSION %VMAJOR%,%VMINOR%,%VRELEASE%,%VBUILD%
ECHO FILEOS VOS__WINDOWS32
ECHO FILETYPE VFT_APP
ECHO BEGIN
ECHO     BLOCK "StringFileInfo"
ECHO     BEGIN
ECHO         BLOCK "041904b0"
ECHO         BEGIN
ECHO             VALUE "FileVersion", "%VMAJOR%.%VMINOR%.%VRELEASE%\0"
ECHO             VALUE "LegalCopyright", "%COPYRIGHT%\0"
ECHO             VALUE "FileDescription", "%NAME%\0"
ECHO             VALUE "ProductVersion", "%VMAJOR%.%VMINOR%\0"
ECHO         END
ECHO     END
ECHO     BLOCK "VarFileInfo"
ECHO     BEGIN
ECHO         VALUE "Translation", 0x419, 1200
ECHO     END
ECHO END
EXIT /b 0

REM Компилим ресурс
:RES_COMP
REM Выходим, если не надо
IF "%DPR%"=="" (
   DEL %RC_FILE%
   EXIT /b 0
) ELSE (
   brcc32 %RC_FILE% && DEL %RC_FILE%
   EXIT /b 0
)

REM Сборка екзешника
:EXE_COMP
REM Выходим, если не надо
IF "%DPR%"=="" (
   EXIT /b 0
)
REM компилим
DCC32 %DPR%
EXIT /b 0

REM Компилирование справки
:HELP_COMP
IF NOT "%HELP%"=="" (
   %HHC_COMP% %HELP%
)
EXIT /b 0

REM Создание документации
:GEN_DOC
IF /i "%GEN_DOC%"=="yes" (
   gdoc "%NAME% build:%VBUILD%"
   IF NOT "%DOC_FILES%"=="" (
   FOR %%i in (%DOC_FILES%) DO COPY %%i doc
)
)
EXIT /b 0

REM Очистка
:TMP_CLEAN
REM Удаляем мусор
IF EXIST *.~* DEL /S *.~*
IF EXIST *.ddp DEL /S *.ddp
EXIT /b 0

REM Сборка дистрибутива
:BIN_COPY
IF "%BIN_DIR%"=="" EXIT /b 0
REM создаем папку
IF NOT EXIST %BIN_DIR% MD %BIN_DIR%
REM Копируем откомпиленный файл
IF EXIST *.exe COPY *.exe %BIN_DIR%
REM Копирование справки
IF EXIST *.chm COPY *.chm %BIN_DIR%
IF NOT "%OTHER_FILES%"=="" (
   FOR %%i in (%OTHER_FILES%) DO COPY %%i %BIN_DIR%
)
EXIT /b 0

REM Запись настроек
:CONF_WRITE
REM Увеличиваем номер сборки :)
SET /A VBUILD=%VBUILD%+1
REM Пишем
ECHO #[version]
ECHO vmajor=%VMAJOR%
ECHO vminor=%VMINOR%
ECHO vrelease=%VRELEASE%
ECHO vbuild=%VBUILD%
ECHO #[project]
ECHO name=%NAME%
ECHO copyright=%COPYRIGHT%
ECHO dpr=%DPR%
ECHO help=%HELP%
ECHO #[options]
ECHO gen_doc=%GEN_DOC%
ECHO bin_dir=%BIN_DIR%
ECHO other_files=%OTHER_FILES%
ECHO doc_files=%DOC_FILES%
EXIT /b 0

REM Установка в случае если нет ошибок
:OK
   SET ISOK=yes
EXIT /b 0

REM Выход, вызывать тока чере goto
:END
IF "%ISOK%"=="yes" (
   ECHO Make complete.
) ELSE (
   ECHO Make failed.
)
GOTO :EOF

Как видно здесь используется компилятор Delphi, но при желании его можно переделать под fpc, али еще какой.
PS: Оказывается и на bat можно писать более-менее сложные программы. Хотя на чем нибудь более привычном я бы писал побыстрее, но... Большое спасибо статье http://www.rsdn.ru/article/winshell/batanyca.xml. Она меня поддержала в самый трудный момент, когда казалось все было потеряно.
Всем спасибо.
Аватара пользователя
mr.denton
новенький
 
Сообщения: 23
Зарегистрирован: 30.04.2006 03:23:07

Сообщение mr.denton » 10.09.2006 01:22:41

Забыл добавить. для работы скрипта gdoc.bat нужно создать папку gdoc_files прям рядом с ним и кинуть в нее pasdoc.css. Ну или поправить gdoc.bat :oops:
Аватара пользователя
mr.denton
новенький
 
Сообщения: 23
Зарегистрирован: 30.04.2006 03:23:07

Сообщение Cheb » 11.09.2006 19:49:21

О. Я так проникся, что свою накатал:

Код: Выделить всё
program incbuild;
uses sysutils;
var
  f: text;
  b: integer;
begin
  Assign(f, GetCurrentDir + '\' + paramstr(1));
  Reset(f);
  Readln(f, b);
  Writeln('Build number: ',b);
  CloseFile(f);
  inc(b);
  Rewrite(f);
  Writeln(f, b);
  CloseFile(f);
end.


В программе:
Код: Выделить всё
const BuildNumber = {$include build.h};


Батник:
Код: Выделить всё
echo off
mkdir ..\..\temp
del /Q ..\..\temp\*.*
del ..\cge.exe
fpc cge.pp -dcge -O2 -Op3 -Or -Sd -Sh -Sc -Rintel -FE..\..\ -FU..\..\temp
if errorlevel 1 goto err
..\..\bin\incbuild build.h
upx ..\..\cge.exe -9 --force
:err
Аватара пользователя
Cheb
энтузиаст
 
Сообщения: 994
Зарегистрирован: 06.06.2005 15:54:34

Сообщение mr.denton » 12.09.2006 15:53:18

Изначально хотел сделать все в одном батнике, так чтобы он хранил номер сборки в своем тексте, а при выполнении сам себя изменял, чтобы версия стала другой. Своеобразная самомодификация кода. В принципе, задумка почти удалась, но никак не могу перезаписать тот-же файл, что и запускал. Есть идея с созданием буффера в виде другого батника, который перезаписывал бы требуемый, а за тем убивал бы себя, но этот способ ловит дикие глюки.

Привожу два варианта:
Первый создает файл с другим именем, куда кидает свое новое содержимое.
Код: Выделить всё
@ECHO off
SET /A VBUILD=0
SET /A VBUILD2=%VBUILD%+1
ECHO %VBUILD2%
FOR /F "delims=  " %%i IN ( %0 ) DO (
   IF "%%i"=="SET /A VBUILD=%VBUILD%" (
      ECHO SET /A VBUILD=%VBUILD2% >> %~pn0_buff.bat
   ) ELSE (
      ECHO %%i >> %~pn0_buff.bat
   )
)


Второй вариант: в конце вызывается этот новый батник, который должен перезаписать старый и убить себя. Но это в теории, в реальности такой глюк...
Код: Выделить всё
@ECHO off

IF {%1}=={} GOTO :NEXT
TYPE %0>%1
DEL %0

:NEXT
SET /A VBUILD=0
SET /A VBUILD2=%VBUILD%+1
ECHO %VBUILD2%

FOR /F "delims=  " %%i IN ( %0 ) DO (
   IF "%%i"=="SET /A VBUILD=%VBUILD%" (
      ECHO SET /A VBUILD=%VBUILD2% >> %~pn0_buff.bat
   ) ELSE (
      ECHO %%i >> %~pn0_buff.bat
   )
)
CALL %~pn0_buff.bat


Так возможна самомодификация bat-кода? Интересно...
Аватара пользователя
mr.denton
новенький
 
Сообщения: 23
Зарегистрирован: 30.04.2006 03:23:07

Сообщение ev » 12.09.2006 21:08:54

Так возможна самомодификация bat-кода? Интересно...

насколько я помню - нет
вроде все вирусы на батниках делают временный батник, который модифицирует основной ;)
ev
долгожитель
 
Сообщения: 1772
Зарегистрирован: 27.04.2005 23:19:06
Откуда: Москва

Сообщение mr.denton » 13.09.2006 17:05:36

насколько я помню - нет

И все таки почти возможна. Операция echo text>>%0 записывает text в конец bat-файла. И когда до него дойдет очередь, он выполнится. А это уже что-то...
Пример:
Код: Выделить всё
@ECHO off
CALl :EXEC %0
ECHO %NUM%
GOTO :EOF
:EXEC
SET NUM=0
ECHO SET /A NUM=%%NUM%%+1>>%1


В конце обязательно должен быть перевод строки!

Эта программа каждый раз когда ее запускают выводит каждый раз новое значение.

Всех с днем программиста!!! :D
Аватара пользователя
mr.denton
новенький
 
Сообщения: 23
Зарегистрирован: 30.04.2006 03:23:07


Вернуться в Разное

Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 10

Рейтинг@Mail.ru