Skip to content

Commit

Permalink
Change volume file
Browse files Browse the repository at this point in the history
  • Loading branch information
Saverio976 committed Apr 8, 2024
1 parent 0051e48 commit 2b6df5f
Show file tree
Hide file tree
Showing 3 changed files with 265 additions and 6 deletions.
199 changes: 199 additions & 0 deletions src/Instance.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,199 @@
import * as pulumi from '@pulumi/pulumi';
import type { ItemType, MachineVolume } from '@aleph-sdk/message';
import { AuthenticatedAlephHttpClient } from '@aleph-sdk/client';
import { getAccount, getAlephExplorerUrl } from './utils';
import type { Volume } from './volumes';

export interface InstanceInputs {
channel: pulumi.Input<string>;
authorizedKeys: pulumi.Input<string[]>;
memory: pulumi.Input<number>;
image: pulumi.Input<string>;
volumes: pulumi.Input<Array<Volume>>;
storageEngine: pulumi.Input<ItemType.storage | ItemType.ipfs>;
accountEnvName: pulumi.Input<string>;
}

interface InstanceProviderInputs {
channel: string;
authorizedKeys: string[];
memory: number;
image: string;
volumes: Array<Volume>;
storageEngine: ItemType.storage | ItemType.ipfs;
accountEnvName: string;
}

const propChannel = 'channel';
const propAuthorizedKeys = 'authorizedKeys';
const propMemory = 'memory';
const propImage = 'image';
const propVolumes = 'volumes';
const propStorageEngine = 'storageEngine';
const propAccountEnvName = 'accountEnvName';

export interface InstanceOutputs {
// inputs
channel: string;
authorizedKeys: string[];
memory: number;
image: string;
volumes: Array<Volume>;
storageEngine: ItemType.storage | ItemType.ipfs;
accountEnvName: string;
// outputs
chain: string;
sender: string;
type: string;
item_hash: string;
// Created
aleph_explorer_url: string;
}

export const getDefaultImage = () => {
return '549ec451d9b099cad112d4aaa2c00ac40fb6729a92ff252ff22eef0b5c3cb613';
};

const InstanceProvider: pulumi.dynamic.ResourceProvider = {
async diff(id: string, olds: InstanceOutputs, news: InstanceProviderInputs) {
const replaces = [];

if (olds[propChannel] !== news[propChannel]) {
replaces.push(propChannel);
}
if (olds[propAuthorizedKeys] !== news[propAuthorizedKeys]) {
replaces.push(propAuthorizedKeys);
}
if (olds[propMemory] !== news[propMemory]) {
replaces.push(propMemory);
}
if (olds[propImage] !== news[propImage]) {
replaces.push(propImage);
}
if (
JSON.stringify(olds[propVolumes]) !== JSON.stringify(news[propVolumes])
) {
replaces.push(propVolumes);
}
if (olds[propStorageEngine] !== news[propStorageEngine]) {
replaces.push(propStorageEngine);
}
if (replaces.length === 0) {
return { changes: false };
}
return { replaces: replaces };
},

async update(id: string, olds: InstanceOutputs, news: InstanceInputs) {
throw new Error('Update not implemented; Only Delete and Create');
},

async delete(id: string, props: InstanceOutputs) {
const account = await getAccount(props[propAccountEnvName]);
const client = new AuthenticatedAlephHttpClient(account);
await client.forget({
channel: props[propChannel],
hashes: [props.item_hash],
sync: true,
});
},

async create(
inputs: InstanceProviderInputs
): Promise<pulumi.dynamic.CreateResult<InstanceOutputs>> {
const account = await getAccount(inputs[propAccountEnvName]);
const client = new AuthenticatedAlephHttpClient(account);
const res = await client.createInstance({
channel: inputs[propChannel],
authorized_keys: inputs[propAuthorizedKeys],
resources: {
memory: inputs[propMemory],
},
image: inputs[propImage],
volumes: inputs[propVolumes].map((volume): MachineVolume => {
if (volume._type === 'immutable') {
return {
...volume,
is_read_only: () => true,
};
} else if (volume._type === 'ephemeral') {
return {
...volume,
is_read_only: () => false,
};
} else {
throw new Error('Invalid volume type: This should never happen.');
}
}),
storageEngine: inputs[propStorageEngine],
});
const out: InstanceOutputs = {
// inputs
channel: inputs[propChannel],
authorizedKeys: inputs[propAuthorizedKeys],
memory: inputs[propMemory],
image: inputs[propImage],
volumes: inputs[propVolumes],
storageEngine: inputs[propStorageEngine],
accountEnvName: inputs[propAccountEnvName],
// outputs
chain: res.chain,
sender: res.sender,
type: `${res.type}`,
item_hash: res.item_hash,
// Created
aleph_explorer_url: getAlephExplorerUrl(
res.chain,
res.sender,
'INSTANCE',
res.item_hash
),
};
return {
id: `${account.address}-${res.item_hash}`,
outs: out,
};
},
};

export class Instance extends pulumi.dynamic.Resource {
// inputs
public readonly channel!: pulumi.Output<string>;
public readonly authorizedKeys!: pulumi.Output<string[]>;
public readonly memory!: pulumi.Output<number>;
public readonly image!: pulumi.Output<string>;
public readonly volumes!: pulumi.Output<Array<Volume>>;
public readonly storageEngine!: pulumi.Output<
ItemType.storage | ItemType.ipfs
>;
public readonly accountEnvName!: pulumi.Output<string>;
// outputs
public readonly chain!: pulumi.Output<string>;
public readonly sender!: pulumi.Output<string>;
public readonly type!: pulumi.Output<string>;
public readonly item_hash!: pulumi.Output<string>;
// Created
public readonly aleph_explorer_url!: pulumi.Output<string>;

constructor(
name: string,
args: InstanceInputs,
opts?: pulumi.CustomResourceOptions
) {
super(
InstanceProvider,
name,
{
// outputs
chain: undefined,
sender: undefined,
type: undefined,
item_hash: undefined,
// Created
aleph_explorer_url: undefined,
...args,
},
opts
);
}
}
29 changes: 23 additions & 6 deletions src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -33,9 +33,6 @@ export { hashData, getAccount, zipPath, getRawFileUrl };
import {
// TODO: Subscription (but broken for now)
// Subscription,
getImmutableVolume,
getEphemeralVolume,
Volume,
ProgramInputs,
ProgramOutputs,
getDefaultRuntime,
Expand All @@ -44,11 +41,31 @@ import {
export {
// TODO: Subscription (but broken for now)
// Subscription,
getImmutableVolume,
getEphemeralVolume,
Volume,
ProgramInputs,
ProgramOutputs,
getDefaultRuntime,
Program,
};

import {
getImmutableVolume,
getEphemeralVolume,
Volume,
EphemeralVolume,
ImmutableVolume,
} from './volumes';
export {
getImmutableVolume,
getEphemeralVolume,
Volume,
EphemeralVolume,
ImmutableVolume,
};

import {
InstanceInputs,
InstanceOutputs,
getDefaultImage,
Instance,
} from './Instance';
export { InstanceInputs, InstanceOutputs, getDefaultImage, Instance };
43 changes: 43 additions & 0 deletions src/volumes.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
type AbstractVolume = {
mount: Array<string>;
_type: 'immutable' | 'ephemeral';
};

export type ImmutableVolume = AbstractVolume & {
ref: string;
use_latest: boolean;
_type: 'immutable';
};

export const getImmutableVolume = (
ref: string,
use_latest: boolean,
mount: Array<string>
): ImmutableVolume => {
return {
mount: mount,
ref: ref,
use_latest: use_latest,
_type: 'immutable',
};
};

export type EphemeralVolume = AbstractVolume & {
ephemeral: true;
size_mib: number;
_type: 'ephemeral';
};

export const getEphemeralVolume = (
size_mib: number,
mount: Array<string>
): EphemeralVolume => {
return {
mount: mount,
ephemeral: true,
size_mib: size_mib,
_type: 'ephemeral',
};
};

export type Volume = ImmutableVolume | EphemeralVolume;

0 comments on commit 2b6df5f

Please sign in to comment.