Skip to content

Commit 63cd62d

Browse files
authored
Add GitHub as a dependency source to CI (#13)
1 parent 95686ba commit 63cd62d

File tree

1 file changed

+99
-19
lines changed

1 file changed

+99
-19
lines changed

.github/workflows/make.pas

Lines changed: 99 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
program Make;
22
{$mode objfpc}{$H+}
3+
{$SCOPEDENUMS ON}
34

45
uses
56
Classes,
@@ -14,7 +15,6 @@
1415

1516
const
1617
Target: string = '.';
17-
Dependencies: array of string = ();
1818

1919
// ANSI color codes
2020
CSI_Reset = #27'[0m';
@@ -35,6 +35,45 @@
3535
;
3636

3737
OPMBaseUrl = 'https://packages.lazarus-ide.org/';
38+
GitHubArchiveBaseUrl = 'https://github.com/';
39+
40+
// ---------------------------------------------------------------------------
41+
// Dependency configuration
42+
// ---------------------------------------------------------------------------
43+
44+
type
45+
TDependencyKind = (OPM, GitHub);
46+
47+
TDependency = record
48+
Kind: TDependencyKind;
49+
Name: string; // OPM: package name | GitHub: 'owner/repo'
50+
Ref: string; // GitHub: branch, tag or commit (ignored for OPM)
51+
end;
52+
53+
const
54+
Dependencies: array of TDependency = (
55+
// Examples:
56+
// (Kind: TDependencyKind.OPM; Name: 'HashLib'; Ref: ''),
57+
// (Kind: TDependencyKind.GitHub; Name: 'Xor-el/SimpleBaseLib4Pascal'; Ref: 'master'),
58+
);
59+
60+
// ---------------------------------------------------------------------------
61+
// Helpers for building TDependency records (optional convenience)
62+
// ---------------------------------------------------------------------------
63+
64+
function OPM(const AName: string): TDependency;
65+
begin
66+
Result.Kind := TDependencyKind.OPM;
67+
Result.Name := AName;
68+
Result.Ref := '';
69+
end;
70+
71+
function GitHub(const AOwnerRepo, ARef: string): TDependency;
72+
begin
73+
Result.Kind := TDependencyKind.GitHub;
74+
Result.Name := AOwnerRepo;
75+
Result.Ref := ARef;
76+
end;
3877

3978
var
4079
ErrorCount: Integer = 0;
@@ -266,20 +305,9 @@ procedure RunTestProject(const APath: string);
266305
end;
267306

268307
// ---------------------------------------------------------------------------
269-
// OPM dependency installation
308+
// Shared download + extract
270309
// ---------------------------------------------------------------------------
271310

272-
function GetOPMPackagesDir: string;
273-
begin
274-
Result :=
275-
{$IFDEF MSWINDOWS}
276-
GetEnvironmentVariable('APPDATA') + '\.lazarus\onlinepackagemanager\packages\'
277-
{$ELSE}
278-
GetEnvironmentVariable('HOME') + '/.lazarus/onlinepackagemanager/packages/'
279-
{$ENDIF}
280-
;
281-
end;
282-
283311
procedure DownloadAndExtract(const AUrl, ADestDir: string);
284312
var
285313
TempFile: string;
@@ -317,14 +345,63 @@ procedure DownloadAndExtract(const AUrl, ADestDir: string);
317345
end;
318346
end;
319347

348+
// ---------------------------------------------------------------------------
349+
// Dependency providers
350+
// ---------------------------------------------------------------------------
351+
352+
function GetDepsBaseDir(const ASubDir: string): string;
353+
var
354+
BaseDir: string;
355+
begin
356+
{$IFDEF MSWINDOWS}
357+
BaseDir := GetEnvironmentVariable('APPDATA');
358+
{$ELSE}
359+
BaseDir := GetEnvironmentVariable('HOME');
360+
{$ENDIF}
361+
Result := IncludeTrailingPathDelimiter(
362+
ConcatPaths([BaseDir, '.lazarus', ASubDir]));
363+
end;
364+
320365
function InstallOPMPackage(const APackageName: string): string;
321366
begin
322-
Result := GetOPMPackagesDir + APackageName;
367+
Result := GetDepsBaseDir(ConcatPaths(['onlinepackagemanager', 'packages']))
368+
+ APackageName;
323369
if DirectoryExists(Result) then
324370
Exit;
325371
DownloadAndExtract(OPMBaseUrl + APackageName + '.zip', Result);
326372
end;
327373

374+
function InstallGitHubPackage(const AOwnerRepo, ARef: string): string;
375+
var
376+
SafeName, EffectiveRef: string;
377+
begin
378+
// Flatten 'owner/repo' to 'owner--repo' for a safe directory name
379+
SafeName := StringReplace(AOwnerRepo, '/', '--', [rfReplaceAll]);
380+
EffectiveRef := ARef;
381+
if EffectiveRef = '' then
382+
EffectiveRef := 'main';
383+
384+
Result := GetDepsBaseDir('github-packages') + SafeName;
385+
if DirectoryExists(Result) then
386+
Exit;
387+
388+
// https://github.com/{owner}/{repo}/archive/refs/heads/{branch}.zip
389+
// also works for tags: refs/tags/{tag}.zip and commits: {sha}.zip
390+
DownloadAndExtract(
391+
GitHubArchiveBaseUrl + AOwnerRepo + '/archive/' + EffectiveRef + '.zip',
392+
Result);
393+
end;
394+
395+
function ResolveDependency(const ADep: TDependency): string;
396+
begin
397+
case ADep.Kind of
398+
TDependencyKind.OPM: Result := InstallOPMPackage(ADep.Name);
399+
TDependencyKind.GitHub: Result := InstallGitHubPackage(ADep.Name, ADep.Ref);
400+
else
401+
raise Exception.CreateFmt('Unknown dependency kind for "%s"', [ADep.Name]);
402+
end;
403+
end;
404+
328405
// ---------------------------------------------------------------------------
329406
// Determine whether an .lpi project is a test runner
330407
// ---------------------------------------------------------------------------
@@ -386,14 +463,17 @@ procedure BuildAllProjects;
386463

387464
procedure Main;
388465
var
389-
Each: string;
466+
I: Integer;
390467
begin
391468
UpdateSubmodules;
392-
InitSSLInterface;
393469

394-
// Install and register OPM dependencies
395-
for Each in Dependencies do
396-
RegisterAllPackages(InstallOPMPackage(Each));
470+
// Install and register dependencies (safe when array is empty)
471+
if Length(Dependencies) > 0 then
472+
begin
473+
InitSSLInterface;
474+
for I := 0 to High(Dependencies) do
475+
RegisterAllPackages(ResolveDependency(Dependencies[I]));
476+
end;
397477

398478
// Register all local packages
399479
RegisterAllPackages(GetCurrentDir);

0 commit comments

Comments
 (0)