@synergenius/flowweaver-pack-github-actions 0.1.2 → 0.1.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/target.d.ts CHANGED
@@ -44,6 +44,14 @@ export declare class GitHubActionsTarget extends BaseCICDTarget {
44
44
  private renderWorkflowYAML;
45
45
  private renderTriggers;
46
46
  private renderJob;
47
+ /**
48
+ * Parse a timeout string like "30m", "1h", "1h30m" into minutes.
49
+ */
50
+ private parseTimeoutMinutes;
51
+ /**
52
+ * Translate GitLab-style CI variable conditions to GitHub Actions expressions.
53
+ */
54
+ private translateCondition;
47
55
  private renderStep;
48
56
  private renderCacheStep;
49
57
  /**
package/dist/target.js CHANGED
@@ -182,12 +182,37 @@ export class GitHubActionsTarget extends BaseCICDTarget {
182
182
  }
183
183
  renderJob(job, ast) {
184
184
  const jobObj = {};
185
- // runs-on
186
- jobObj['runs-on'] = job.runner || 'ubuntu-latest';
185
+ // runs-on (tags override: self-hosted + tag labels)
186
+ if (job.tags && job.tags.length > 0) {
187
+ jobObj['runs-on'] = ['self-hosted', ...job.tags];
188
+ }
189
+ else {
190
+ jobObj['runs-on'] = job.runner || 'ubuntu-latest';
191
+ }
187
192
  // needs
188
193
  if (job.needs.length > 0) {
189
194
  jobObj.needs = job.needs;
190
195
  }
196
+ // continue-on-error (from @job allow_failure)
197
+ if (job.allowFailure) {
198
+ jobObj['continue-on-error'] = true;
199
+ }
200
+ // timeout-minutes (from @job timeout, parse "30m" → 30, "1h" → 60)
201
+ if (job.timeout) {
202
+ jobObj['timeout-minutes'] = this.parseTimeoutMinutes(job.timeout);
203
+ }
204
+ // if: conditional (from @job rules)
205
+ if (job.rules && job.rules.length > 0) {
206
+ // Use the first rule's `if` condition, translate GitLab-style vars to GitHub context
207
+ const condition = job.rules[0].if;
208
+ if (condition) {
209
+ jobObj.if = this.translateCondition(condition);
210
+ }
211
+ }
212
+ // env (from @job variables or @variables)
213
+ if (job.variables && Object.keys(job.variables).length > 0) {
214
+ jobObj.env = { ...job.variables };
215
+ }
191
216
  // environment
192
217
  if (job.environment) {
193
218
  const envConfig = ast.options?.cicd?.environments?.find((e) => e.name === job.environment);
@@ -246,6 +271,13 @@ export class GitHubActionsTarget extends BaseCICDTarget {
246
271
  if (job.cache) {
247
272
  steps.push(this.renderCacheStep(job.cache));
248
273
  }
274
+ // before_script as a setup step
275
+ if (job.beforeScript && job.beforeScript.length > 0) {
276
+ steps.push({
277
+ name: 'Setup',
278
+ run: job.beforeScript.join('\n'),
279
+ });
280
+ }
249
281
  // Node steps
250
282
  for (const step of job.steps) {
251
283
  steps.push(this.renderStep(step));
@@ -266,9 +298,66 @@ export class GitHubActionsTarget extends BaseCICDTarget {
266
298
  steps.push(uploadStep);
267
299
  }
268
300
  }
301
+ // reports: junit → test-reporter, coverage → codecov
302
+ if (job.reports && job.reports.length > 0) {
303
+ for (const report of job.reports) {
304
+ if (report.type === 'junit') {
305
+ steps.push({
306
+ name: 'Test Report',
307
+ uses: 'dorny/test-reporter@v1',
308
+ if: 'always()',
309
+ with: {
310
+ name: 'Test Results',
311
+ path: report.path,
312
+ reporter: 'java-junit',
313
+ },
314
+ });
315
+ }
316
+ else if (report.type === 'cobertura' || report.type === 'coverage') {
317
+ steps.push({
318
+ name: 'Upload Coverage',
319
+ uses: 'codecov/codecov-action@v4',
320
+ with: { files: report.path },
321
+ });
322
+ }
323
+ else {
324
+ steps.push({
325
+ name: `Upload ${report.type} report`,
326
+ uses: 'actions/upload-artifact@v4',
327
+ with: {
328
+ name: `${report.type}-report`,
329
+ path: report.path,
330
+ },
331
+ });
332
+ }
333
+ }
334
+ }
269
335
  jobObj.steps = steps;
270
336
  return jobObj;
271
337
  }
338
+ /**
339
+ * Parse a timeout string like "30m", "1h", "1h30m" into minutes.
340
+ */
341
+ parseTimeoutMinutes(timeout) {
342
+ let minutes = 0;
343
+ const hourMatch = timeout.match(/(\d+)h/);
344
+ const minMatch = timeout.match(/(\d+)m/);
345
+ if (hourMatch)
346
+ minutes += parseInt(hourMatch[1], 10) * 60;
347
+ if (minMatch)
348
+ minutes += parseInt(minMatch[1], 10);
349
+ return minutes || 60; // default 60 if unparseable
350
+ }
351
+ /**
352
+ * Translate GitLab-style CI variable conditions to GitHub Actions expressions.
353
+ */
354
+ translateCondition(condition) {
355
+ return condition
356
+ .replace(/\$CI_COMMIT_BRANCH/g, "github.ref_name")
357
+ .replace(/\$CI_COMMIT_TAG/g, "startsWith(github.ref, 'refs/tags/')")
358
+ .replace(/\$CI_PIPELINE_SOURCE/g, "github.event_name")
359
+ .replace(/==/g, '==');
360
+ }
272
361
  renderStep(step) {
273
362
  const mapping = this.resolveActionMapping(step, 'github-actions');
274
363
  if (mapping?.githubAction) {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@synergenius/flowweaver-pack-github-actions",
3
- "version": "0.1.2",
3
+ "version": "0.1.3",
4
4
  "description": "GitHub Actions CI/CD export target for Flow Weaver",
5
5
  "keywords": [
6
6
  "flowweaver-marketplace-pack",
@@ -36,7 +36,7 @@
36
36
  },
37
37
  "devDependencies": {
38
38
  "typescript": "^5.0.0",
39
- "@synergenius/flow-weaver": "^0.17.1",
39
+ "@synergenius/flow-weaver": "^0.17.3",
40
40
  "@types/node": "^20.0.0"
41
41
  },
42
42
  "license": "SEE LICENSE IN LICENSE",