Skip to content
This repository has been archived by the owner on Sep 3, 2024. It is now read-only.

Commit

Permalink
add relationships; use generic types
Browse files Browse the repository at this point in the history
  • Loading branch information
erkangz committed May 21, 2020
1 parent 87a2fca commit 241c828
Show file tree
Hide file tree
Showing 5 changed files with 99 additions and 25 deletions.
12 changes: 10 additions & 2 deletions docs/jupiterone.md
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,16 @@ The following entity resources are ingested when the integration runs.
| Snipe-IT Resources | \_type of the Entity | \_class of the Entity |
| ------------------ | -------------------- | --------------------- |
| Account | `snipeit_account` | `Account` |
| Hardware | `snipeit_hardware` | `Device` |
| Location | `snipeit_location` | `Site` |
| Hardware | `hardware` | `Device` |
| Location | `location` | `Site` |

The following relationships are created:

| From | Relationship | To |
| ----------------- | ------------ | ---------- |
| `snipeit_account` | **MANAGES** | `location` |
| `snipeit_account` | **MANAGES** | `hardware` |
| `location` | **HAS** | `hardware` |

The following relationships are mapped:

Expand Down
35 changes: 29 additions & 6 deletions src/converter/entities.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,29 @@ import {
createIntegrationEntity,
getTime,
convertProperties,
Entity,
} from '@jupiterone/integration-sdk';

export const getAccountEntity = (instance: any): Entity => ({
_key: `snipe-it:account:${instance.id}`,
_type: 'snipeit_account',
_class: ['Account'],
name: instance.name,
displayName: instance.name,
description: instance.description,
});

export const getServiceEntity = (instance: any): Entity => ({
_key: `snipe-it:service:${instance.id}:itam`,
_type: 'snipe_service',
_class: ['Service'],
name: 'Snipe-IT ITAM',
displayName: 'Snipe-IT ITAM',
description: 'IT Asset Management (ITAM)',
category: 'infrastructure',
function: 'ITAM',
});

export const convertHardware = (
data: any,
): ReturnType<typeof createIntegrationEntity> =>
Expand All @@ -13,10 +34,10 @@ export const convertHardware = (
source: data,
assign: {
...convertProperties(data),
_key: `snipe-it:hardware:${data.id}`,
_type: 'snipeit_hardware',
_key: `hardware:${data.id}`,
_type: 'hardware',
_class: ['Device'],
id: `snipe-it:hardware:${data.id}`,
id: `hardware:${data.id}`,
assetId: data.id,
displayName: data.name,
activatedOn: getTime(data.activated_on),
Expand All @@ -32,6 +53,8 @@ export const convertHardware = (
status:
data.status_label?.status_meta === 'deployable'
? 'ready'
: data.status_label?.name?.match(/broken/i)
? 'defective'
: data.status_label?.status_meta,
notes: data.notes ? [data.notes] : undefined,
location: data.location?.name,
Expand All @@ -50,10 +73,10 @@ export const convertLocation = (
source: data,
assign: {
...convertProperties(data),
_key: `snipe-it:location:${data.id}`,
_type: 'snipeit_location',
_key: `location:${data.id}`,
_type: 'location',
_class: ['Site'],
id: `snipe-it:location:${data.id}`,
id: `location:${data.id}`,
locationId: data.id,
displayName: data.name,
createdOn: getTime(data.created_at?.datetime),
Expand Down
41 changes: 29 additions & 12 deletions src/steps/fetch-account/index.ts
Original file line number Diff line number Diff line change
@@ -1,34 +1,51 @@
import {
IntegrationStep,
IntegrationStepExecutionContext,
createIntegrationRelationship,
} from '@jupiterone/integration-sdk';

import { createServicesClient } from '../../collector';
import { convertLocation } from '../../converter';
import {
convertLocation,
getAccountEntity,
getServiceEntity,
} from '../../converter';

const step: IntegrationStep = {
id: 'fetch-account',
name: 'Fetch Account related data',
types: ['snipeit_account', 'snipeit_location'],
types: ['snipeit_account', 'location'],
async executionHandler({
instance,
jobState,
}: IntegrationStepExecutionContext) {
const client = createServicesClient(instance);

const accountEntity = {
_key: `snipe-it:account:${instance.id}`,
_type: 'snipeit_account',
_class: ['Account'],
name: instance.name,
displayName: instance.name,
description: instance.description,
};
const accountEntity = getAccountEntity(instance);
await jobState.addEntity(accountEntity);

const serviceEntity = getServiceEntity(instance);
await jobState.addEntity(serviceEntity);

const accountServiceRelationship = createIntegrationRelationship({
from: accountEntity,
to: serviceEntity,
_class: 'PROVIDES',
});
await jobState.addRelationship(accountServiceRelationship);

const locations = await client.listLocations();
const entities = locations.map(convertLocation);
await jobState.addEntities(entities);
const locationEntities = locations.map(convertLocation);
await jobState.addEntities(locationEntities);

const relationships = locationEntities.map((locationEntity) =>
createIntegrationRelationship({
from: accountEntity,
to: locationEntity,
_class: 'MANAGES',
}),
);
await jobState.addRelationships(relationships);
},
};

Expand Down
2 changes: 1 addition & 1 deletion src/steps/fetch-hardware/__tests__/index.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ test('should process hardware entities', async () => {
expect(context.jobState.collectedEntities).toEqual(
expect.arrayContaining([
expect.objectContaining({
_type: 'snipeit_hardware',
_type: 'hardware',
_class: ['Device'],
id: expect.any(String),
displayName: expect.any(String),
Expand Down
34 changes: 30 additions & 4 deletions src/steps/fetch-hardware/index.ts
Original file line number Diff line number Diff line change
@@ -1,24 +1,50 @@
import {
IntegrationStep,
IntegrationStepExecutionContext,
createIntegrationRelationship,
} from '@jupiterone/integration-sdk';

import { createServicesClient } from '../../collector';
import { convertHardware } from '../../converter';
import { convertHardware, getAccountEntity } from '../../converter';

const step: IntegrationStep = {
id: 'fetch-hardware',
name: 'Fetch Snipe-IT listing of hardware assets',
types: ['snipeit_hardware'],
types: ['hardware'],
async executionHandler({
instance,
jobState,
}: IntegrationStepExecutionContext) {
const client = createServicesClient(instance);
const accountEntity = getAccountEntity(instance);

const hardware = await client.listHardware();
const entities = hardware.map(convertHardware);
await jobState.addEntities(entities);

const hardwareEntities = hardware.map(convertHardware);
await jobState.addEntities(hardwareEntities);

const relationships = [];
hardwareEntities.forEach((hardwareEntity) => {
relationships.push(
createIntegrationRelationship({
from: accountEntity,
to: hardwareEntity,
_class: 'MANAGES',
}),
);
if (hardwareEntity.locationId) {
relationships.push(
createIntegrationRelationship({
fromType: 'location',
fromKey: `location:${hardwareEntity.locationId}`,
toType: hardwareEntity._type,
toKey: hardwareEntity._key,
_class: 'HAS',
}),
);
}
});
await jobState.addRelationships(relationships);
},
};

Expand Down

0 comments on commit 241c828

Please sign in to comment.