Skip to content

Commit

Permalink
Merge pull request #2867 from GoogleCloudPlatform/nodejs-security-cen…
Browse files Browse the repository at this point in the history
…ter-migration

migrate code from googleapis/nodejs-security-center
  • Loading branch information
NimJay authored Nov 18, 2022
2 parents 7f1b382 + 1a035ee commit 00867cf
Show file tree
Hide file tree
Showing 43 changed files with 2,298 additions and 1 deletion.
70 changes: 70 additions & 0 deletions .github/workflows/security-center-snippets.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
name: security-center-snippets
on:
push:
branches:
- main
paths:
- 'security-center/snippets/**'
pull_request:
paths:
- 'security-center/snippets/**'
pull_request_target:
types: [labeled]
paths:
- 'security-center/snippets/**'
schedule:
- cron: '0 0 * * 0'
env:
GCLOUD_ORGANIZATION: 1081635000895
jobs:
test:
if: ${{ github.event.action != 'labeled' || github.event.label.name == 'actions:force-run' }}
runs-on: ubuntu-latest
timeout-minutes: 60
permissions:
contents: 'write'
pull-requests: 'write'
id-token: 'write'
steps:
- uses: actions/checkout@v3.1.0
with:
ref: ${{github.event.pull_request.head.sha}}
- uses: 'google-github-actions/auth@v1.0.0'
with:
workload_identity_provider: 'projects/1046198160504/locations/global/workloadIdentityPools/github-actions-pool/providers/github-actions-provider'
service_account: 'kokoro-system-test@long-door-651.iam.gserviceaccount.com'
create_credentials_file: 'true'
access_token_lifetime: 600s
- uses: actions/setup-node@v3.5.1
with:
node-version: 16
- run: npm install
working-directory: security-center/snippets
- run: npm test
working-directory: security-center/snippets
env:
MOCHA_REPORTER_SUITENAME: security_center_snippets
MOCHA_REPORTER_OUTPUT: security_center_snippets_sponge_log.xml
MOCHA_REPORTER: xunit
- if: ${{ github.event.action == 'labeled' && github.event.label.name == 'actions:force-run' }}
uses: actions/github-script@v6
with:
github-token: ${{ secrets.GITHUB_TOKEN }}
script: |
try {
await github.rest.issues.removeLabel({
name: 'actions:force-run',
owner: 'GoogleCloudPlatform',
repo: 'nodejs-docs-samples',
issue_number: context.payload.pull_request.number
});
} catch (e) {
if (!e.message.includes('Label does not exist')) {
throw e;
}
}
- if: ${{ github.event_name == 'schedule'}}
run: |
curl https://github.com/googleapis/repo-automation-bots/releases/download/flakybot-1.1.0/flakybot -o flakybot -s -L
chmod +x ./flakybot
./flakybot --repo GoogleCloudPlatform/nodejs-docs-samples --commit_hash ${{github.sha}} --build_url https://github.com/${{github.repository}}/actions/runs/${{github.run_id}}
3 changes: 2 additions & 1 deletion .github/workflows/workflows.json
Original file line number Diff line number Diff line change
Expand Up @@ -57,8 +57,9 @@
"datacatalog/cloud-client",
"datacatalog/quickstart",
"datastore/functions",
"service-directory/snippets",
"scheduler",
"security-center/snippets",
"service-directory/snippets",
"secret-manager",
"speech",
"talent",
Expand Down
24 changes: 24 additions & 0 deletions security-center/snippets/package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
{
"name": "nodejs-security-center-samples",
"private": true,
"files": [
"**/*.js",
"!system-test/"
],
"engines": {
"node": ">=12.0.0"
},
"scripts": {
"test": "mocha system-test/ --recursive --timeout 6000000"
},
"license": "Apache-2.0",
"dependencies": {
"@google-cloud/pubsub": "^3.0.0",
"@google-cloud/security-center": "^6.3.1"
},
"devDependencies": {
"chai": "^4.2.0",
"mocha": "^8.0.0",
"uuid": "^9.0.0"
}
}
86 changes: 86 additions & 0 deletions security-center/snippets/system-test/v1/assetSecurityMarks.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,86 @@
// Copyright 2019 Google LLC
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// https://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

'use strict';

const {SecurityCenterClient} = require('@google-cloud/security-center');
const {assert} = require('chai');
const {describe, it, before} = require('mocha');
const {execSync} = require('child_process');
const exec = cmd => execSync(cmd, {encoding: 'utf8'});

const organizationId = process.env['GCLOUD_ORGANIZATION'];

describe('client with security marks for assets', async () => {
let data;
before(async () => {
// Creates a new client.
const client = new SecurityCenterClient();

const [assetResults] = await client.listAssets({
parent: client.organizationPath(organizationId),
});
const randomAsset =
assetResults[Math.floor(Math.random() * assetResults.length)].asset;
console.log('random %j', randomAsset);
data = {
orgId: organizationId,
assetName: randomAsset.name,
};
console.log('data %j', data);
});
it('client can add security marks to asset.', () => {
const output = exec(`node v1/addSecurityMarks.js ${data.assetName}`);
assert.include(output, data.assetName);
assert.match(output, /key_a/);
assert.match(output, /value_a/);
assert.match(output, /key_b/);
assert.match(output, /value_b/);
assert.notMatch(output, /undefined/);
});

it('client can add and delete security marks', () => {
// Ensure marks are set.
exec(`node v1/addSecurityMarks.js ${data.assetName}`);

const output = exec(`node v1/addDeleteSecurityMarks.js ${data.assetName}`);
assert.match(output, /key_a/);
assert.match(output, /new_value_a/);
assert.notMatch(output, /key_b/);
assert.notMatch(output, /undefined/);
});

it('client can delete security marks', () => {
// Ensure marks are set.
exec(`node v1/addSecurityMarks.js ${data.assetName}`);

const output = exec(`node v1/deleteSecurityMarks.js ${data.assetName}`);
assert.notMatch(output, /key_a/);
assert.notMatch(output, /value_a/);
assert.notMatch(output, /key_b/);
assert.notMatch(output, /value_b/);
assert.include(output, data.assetName);
assert.include(output, data.assetName);
assert.notMatch(output, /undefined/);
});

it('client can list assets with security marks', () => {
// Ensure marks are set.
exec(`node v1/addSecurityMarks.js ${data.assetName}`);

const output = exec(`node v1/listAssetsWithSecurityMarks.js ${data.orgId}`);
assert.include(output, data.assetName);
assert.notMatch(output, /undefined/);
});
});
204 changes: 204 additions & 0 deletions security-center/snippets/system-test/v1/findings.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,204 @@
// Copyright 2019 Google LLC
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// https://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

'use strict';

const {SecurityCenterClient} = require('@google-cloud/security-center');
const {assert} = require('chai');
const {describe, it, before} = require('mocha');
const {execSync} = require('child_process');
const exec = cmd => execSync(cmd, {encoding: 'utf8'});

const organizationId = process.env['GCLOUD_ORGANIZATION'];

describe('Client with SourcesAndFindings', async () => {
let data;
before(async () => {
// Creates a new client.
const client = new SecurityCenterClient();
const [source] = await client
.createSource({
source: {
displayName: 'Customized Display Name',
description: 'A new custom source that does X',
},
parent: client.organizationPath(organizationId),
})
.catch(error => console.error(error));
const eventTime = new Date();
const createFindingTemplate = {
parent: source.name,
findingId: 'somefinding',
finding: {
state: 'ACTIVE',
// Resource the finding is associated with. This is an
// example any resource identifier can be used.
resourceName:
'//cloudresourcemanager.googleapis.com/organizations/11232',
// A free-form category.
category: 'MEDIUM_RISK_ONE',
// The time associated with discovering the issue.
eventTime: {
seconds: Math.floor(eventTime.getTime() / 1000),
nanos: (eventTime.getTime() % 1000) * 1e6,
},
},
};
const [finding] = await client.createFinding(createFindingTemplate);
createFindingTemplate.findingId = 'untouchedFindingId';
createFindingTemplate.finding.category = 'XSS';
const [untouchedFinding] = await client
.createFinding(createFindingTemplate)
.catch(error => console.error(error));
data = {
orgId: organizationId,
sourceName: source.name,
findingName: finding.name,
untouchedFindingName: untouchedFinding.name,
};
console.log('my data %j', data);
});

it('client can create source', () => {
const output = exec(`node v1/createSource.js ${data.orgId}`);
assert.match(output, new RegExp(data.orgId));
assert.match(output, /New Source/);
assert.notMatch(output, /undefined/);
});

it('client can get source', () => {
const output = exec(`node v1/getSource.js ${data.sourceName}`);
assert.match(output, new RegExp(data.sourceName));
assert.match(output, /Source/);
assert.match(output, /"description":"A new custom source that does X"/);
assert.notMatch(output, /undefined/);
});

it('client can list all sources', () => {
const output = exec(`node v1/listAllSources.js ${data.orgId}`);
assert.match(output, new RegExp(data.sourceName));
assert.match(output, /Sources/);
assert.notMatch(output, /undefined/);
});

it('client can update a source', () => {
const output = exec(`node v1/updateSource.js ${data.sourceName}`);
assert.match(output, new RegExp(data.sourceName));
assert.match(output, /New Display Name/);
assert.match(output, /source that does X/);
assert.notMatch(output, /undefined/);
});

it('client can create a finding', () => {
const output = exec(`node v1/createFinding.js ${data.sourceName}`);
assert.match(output, new RegExp(data.sourceName));
assert.match(output, /New finding created/);
assert.notMatch(output, /undefined/);
});

it('client can create a finding with source properties', () => {
const output = exec(
`node v1/createFindingSourceProperties.js ${data.sourceName}`
);
assert.match(output, new RegExp(data.sourceName));
assert.match(output, /New finding created/);
assert.match(output, /n_value/);
assert.notMatch(output, /undefined/);
});

it('client can update a findings source properties', () => {
const output = exec(
`node v1/updateFindingSourceProperties.js ${data.findingName}`
);
assert.match(output, new RegExp(data.findingName));
assert.match(output, /Updated Finding/);
assert.match(output, /new_string_example/);
assert.notMatch(output, /undefined/);
});

it('client can set finding state', () => {
const output = exec(`node v1/setFindingState.js ${data.findingName}`);
assert.match(output, new RegExp(data.findingName));
assert.match(output, /INACTIVE/);
assert.notMatch(output, /undefined/);
});

it('client can test IAM privileges', () => {
const output = exec(`node v1/testIam.js ${data.sourceName}`);
assert.equal(
(output.match(/true/g) || []).length,
2,
`${output} contains true twice`
);
assert.notMatch(output, /undefined/);
});

it('client can list all findings', () => {
const output = exec(`node v1/listAllFindings.js ${data.orgId}`);
assert.match(output, new RegExp(data.findingName));
assert.match(output, new RegExp(data.untouchedFindingName));
assert.notMatch(output, /undefined/);
});

it('client can list only some findings', () => {
const output = exec(`node v1/listFilteredFindings.js ${data.sourceName}`);
assert.match(output, new RegExp(data.findingName));
assert.notMatch(output, new RegExp(data.untouchedFindingName));
assert.notMatch(output, /undefined/);
});

it('client can list findings at a time.', () => {
const output = exec(`node v1/listFindingsAtTime.js ${data.sourceName}`);
// Nothing was created for the source more then a few minutes ago, so
// days ago should return nothing.
assert.equal(output, '');
});

it('client can add security marks to finding', () => {
const output = exec(
`node v1/addFindingSecurityMarks.js ${data.findingName}`
);
assert.match(output, new RegExp(data.findingName));
assert.match(output, /key_a/);
assert.match(output, /value_a/);
assert.match(output, /key_b/);
assert.match(output, /value_b/);
assert.notMatch(output, /undefined/);
});

it('client can list findings withe security marks', () => {
// Ensure marks are set.
exec(`node v1/addFindingSecurityMarks.js ${data.findingName}`);
const output = exec(
`node v1/listFindingsWithSecurityMarks.js ${data.sourceName}`
);
assert.notMatch(output, new RegExp(data.findingName));
assert.match(output, new RegExp(data.untouchedFindingName));
assert.notMatch(output, /undefined/);
});

it('client can get a sources policy', () => {
const output = exec(`node v1/getSourceIam.js ${data.sourceName}`);
assert.match(output, /Current policy/);
assert.notMatch(output, /undefined/);
});

it('client set a sources policy', () => {
const user = 'csccclienttest@gmail.com';
const output = exec(`node v1/setSourceIam.js ${data.sourceName} ${user}`);
assert.match(output, /Updated policy/);
assert.include(output, user);
assert.notMatch(output, /undefined/);
});
});
Loading

0 comments on commit 00867cf

Please sign in to comment.