Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
27 changes: 25 additions & 2 deletions index.js
Original file line number Diff line number Diff line change
Expand Up @@ -12,8 +12,11 @@ const YAML_SCHEMA = YamlParser.CORE_SCHEMA.withTags(
);

/* eslint-disable max-len */
const RESERVED_JOB_ANNOTATIONS = require('screwdriver-data-schema').config.annotations.reservedJobAnnotations;
const RESERVED_PIPELINE_ANNOTATIONS = require('screwdriver-data-schema').config.annotations.reservedPipelineAnnotations;
const {
reservedJobAnnotations: RESERVED_JOB_ANNOTATIONS,
reservedPipelineAnnotations: RESERVED_PIPELINE_ANNOTATIONS,
reservedStageAnnotations: RESERVED_STAGE_ANNOTATIONS
} = require('screwdriver-data-schema').config.annotations;
const SCHEMA_PIPELINE_TEMPLATE = require('screwdriver-data-schema').config.pipelineTemplate.template;
/* eslint-enable max-len */

Expand Down Expand Up @@ -101,6 +104,26 @@ function validateReservedAnnotation(doc) {
);
}

if (RESERVED_STAGE_ANNOTATIONS) {
const stages = Hoek.reach(doc, 'stages', { default: {} });

Object.keys(stages).forEach(stageName => {
const stageAnnotations = Hoek.reach(stages[stageName], 'annotations', { default: {} });

warnings = warnings.concat(
Object.keys(stageAnnotations)
.filter(key => {
if (key.startsWith('screwdriver.cd/')) {
return RESERVED_STAGE_ANNOTATIONS.indexOf(key) === -1;
}

return false;
})
.map(value => `${value} is not an annotation that is reserved for Stage-Level`)
);
});
}

if (RESERVED_JOB_ANNOTATIONS) {
Object.keys(doc.jobs).forEach(jobName => {
const jobAnnotations = Hoek.reach(doc.jobs[jobName], 'annotations', {
Expand Down
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -56,7 +56,7 @@
"joi": "^17.13.3",
"js-yaml": "^5.2.3",
"keymbinatorial": "^3.0.0",
"screwdriver-data-schema": "^25.0.0",
"screwdriver-data-schema": "^26.0.0",
"screwdriver-notifications-email": "^5.0.0",
"screwdriver-notifications-slack": "^7.0.0",
"screwdriver-workflow-parser": "^6.0.0",
Expand Down
133 changes: 133 additions & 0 deletions test/data/pipeline-with-stages-and-annotations.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,133 @@
{
"annotations": {},
"parameters": {},
"subscribe": {},
"jobs": {
"foo": [
{
"annotations": {},
"commands": [
{
"command": "echo foo",
"name": "echo"
}
],
"environment": {},
"image": "node:18",
"secrets": [],
"settings": {},
"requires": [
"~stage@foobar:setup"
],
"stage": {
"name": "foobar"
}
}
],
"bar": [
{
"annotations": {},
"commands": [
{
"command": "echo foo",
"name": "echo"
}
],
"environment": {},
"image": "node:18",
"secrets": [],
"settings": {},
"requires": [
"foo"
],
"stage": {
"name": "foobar"
}
}
],
"stage@foobar:setup": [
{
"annotations": {
"screwdriver.cd/virtualJob": true
},
"commands": [
{
"command": "echo noop",
"name": "noop"
}
],
"environment": {},
"image": "node:18",
"secrets": [],
"settings": {},
"requires": [
"~commit"
],
"stage": {
"name": "foobar"
}
}
],
"stage@foobar:teardown": [
{
"annotations": {
"screwdriver.cd/virtualJob": true
},
"commands": [
{
"command": "echo noop",
"name": "noop"
}
],
"environment": {},
"image": "node:18",
"secrets": [],
"settings": {},
"requires": [
"bar"
],
"stage": {
"name": "foobar"
}
}
]
},
"workflowGraph": {
"nodes": [
{ "name": "~pr" },
{ "name": "~commit" },
{ "name": "foo", "stageName": "foobar" },
{
"name": "stage@foobar:setup",
"virtual": true,
"stageName": "foobar"
},
{ "name": "bar", "stageName": "foobar" },
{
"name": "stage@foobar:teardown",
"virtual": true,
"stageName": "foobar"
}
],
"edges": [
{ "src": "stage@foobar:setup", "dest": "foo" },
{ "src": "foo", "dest": "bar", "join": true },
{ "src": "~commit", "dest": "stage@foobar:setup" },
{ "src": "bar", "dest": "stage@foobar:teardown", "join": true }
]
},
"stages": {
"foobar": {
"jobs": [
"foo",
"bar"
],
"requires": [
"~commit"
],
"annotations": {
"screwdriver.cd/manualStartEnabled": true
}
}
}
}
17 changes: 17 additions & 0 deletions test/data/pipeline-with-stages-and-annotations.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
stages:
foobar:
requires: [ ~commit ]
jobs: [ foo, bar ]
annotations:
screwdriver.cd/manualStartEnabled: true

shared:
image: node:18
steps:
- echo: echo foo

jobs:
foo:
requires: []
bar:
requires: [ foo ]
12 changes: 12 additions & 0 deletions test/data/warn-stage-level-annotation.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
jobs:
main:
image: test
steps:
- foo: bar
stages:
test:
jobs: [main]
annotations:
screwdriver.cd/manualStartEnabled: false
screwdriver.cd/foo: bar
baz: qux
21 changes: 21 additions & 0 deletions test/index.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -332,6 +332,16 @@ jobs:
assert.deepEqual(data, JSON.parse(loadData('pipeline-with-stages-and-sourcePaths.json')));
}));

it('returns a yaml with annotations in stages', () =>
parser({
yaml: loadData('pipeline-with-stages-and-annotations.yaml'),
templateFactory: templateFactoryMock,
triggerFactory,
pipelineId
}).then(data => {
assert.deepEqual(data, JSON.parse(loadData('pipeline-with-stages-and-annotations.json')));
}));

it('returns an error if bad stages', () =>
parser({ yaml: loadData('bad-stages.yaml'), triggerFactory, pipelineId }).then(data => {
assert.match(
Expand Down Expand Up @@ -1366,6 +1376,17 @@ jobs:
);
/* eslint-enable max-len */
}));
it('warning it is not stage-level annotation', () =>
parser({ yaml: loadData('warn-stage-level-annotation.yaml'), triggerFactory }).then(data => {
console.log(data);
/* eslint-disable max-len */
assert.match(
data.warnMessages[0],
/screwdriver.cd\/foo is not an annotation that is reserved for Stage-Level/
);
assert.equal(data.warnMessages.length, 1);
/* eslint-enable max-len */
}));
it('warning it is not job-level annotation', () =>
parser({ yaml: loadData('warn-job-level-annotation.yaml'), triggerFactory }).then(data => {
/* eslint-disable max-len */
Expand Down