stability-ai
Version:
Node SDK for Stability AI REST API
154 lines • 5.24 kB
JavaScript
;
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.processContentResponse = exports.processArrayBufferResponse = exports.downloadImage = exports.ImagePath = exports.isValidFile = exports.isValidHttpUrl = exports.makeUrl = exports.DEFAULT_OUTPUT_FORMAT = exports.APIVersion = void 0;
const axios_1 = __importDefault(require("axios"));
const path_1 = __importDefault(require("path"));
const os_1 = __importDefault(require("os"));
const fs_extra_1 = __importDefault(require("fs-extra"));
const uuid_1 = require("uuid");
const STABILITY_AI_BASE_URL = 'https://api.stability.ai';
var APIVersion;
(function (APIVersion) {
APIVersion["V1"] = "v1";
APIVersion["V2_BETA"] = "v2beta";
})(APIVersion || (exports.APIVersion = APIVersion = {}));
exports.DEFAULT_OUTPUT_FORMAT = 'png';
// HELPER FUNCTIONS
function makeUrl(verison, resource, endpoint) {
return `${STABILITY_AI_BASE_URL}/${verison}/${resource}${endpoint.length > 0 ? `/${endpoint}` : ''}`;
}
exports.makeUrl = makeUrl;
function isValidHttpUrl(value) {
try {
const url = new URL(value);
return url.protocol === 'http:' || url.protocol === 'https:';
}
catch {
return false;
}
}
exports.isValidHttpUrl = isValidHttpUrl;
function isValidFile(value) {
try {
return fs_extra_1.default.statSync(value).isFile();
}
catch {
return false;
}
}
exports.isValidFile = isValidFile;
class ImagePath {
constructor(resource) {
this.resource = resource;
if (isValidHttpUrl(resource)) {
this.type = 'download';
}
else if (isValidFile(resource)) {
this.type = 'local';
}
else {
throw new Error('Invalid image resource. Must be local filepath or public image URL.');
}
}
async filepath() {
switch (this.type) {
case 'local': {
return this.resource;
}
case 'download': {
if (this.downloadFilepath)
return this.downloadFilepath;
this.downloadFilepath = await downloadImage(this.resource);
return this.downloadFilepath;
}
}
}
cleanup() {
switch (this.type) {
case 'download': {
if (this.downloadFilepath) {
fs_extra_1.default.unlinkSync(this.downloadFilepath);
this.downloadFilepath = undefined;
}
break;
}
default: {
break;
}
}
}
}
exports.ImagePath = ImagePath;
/**
* Download an image from a URL and return the local file path
*
* @param url
* @returns filepath string
*
* TODO - image type validation and use corresponding image filetype in filename
*/
async function downloadImage(url) {
const filename = `image-${(0, uuid_1.v4)()}.png`;
const filepath = path_1.default.join(os_1.default.tmpdir(), filename);
const response = await (0, axios_1.default)({
url,
method: 'GET',
responseType: 'stream',
});
await fs_extra_1.default.ensureDir(path_1.default.dirname(filepath));
await new Promise((resolve, reject) => {
try {
response.data
.pipe(fs_extra_1.default.createWriteStream(filepath))
.on('error', reject)
.once('close', () => resolve(filepath));
}
catch (err) {
reject(err);
}
});
return filepath;
}
exports.downloadImage = downloadImage;
async function processArrayBufferResponse(data, outputFormat, resource) {
const filename = `${resource}_${(0, uuid_1.v4)()}.${outputFormat}`;
const filepath = path_1.default.join(os_1.default.tmpdir(), filename);
await fs_extra_1.default.writeFile(filepath, Buffer.from(data));
return {
filepath,
filename,
contentType: '3d',
outputFormat,
contentFiltered: false,
errored: false,
seed: data.seed,
};
}
exports.processArrayBufferResponse = processArrayBufferResponse;
async function processContentResponse(data, outputFormat, resource) {
let fileData = outputFormat === 'mp4' ? data.video : data.image;
if (!fileData)
fileData = data.base64;
if (!fileData && data.result)
fileData = data.result;
if (!fileData)
throw new Error('No file data found in response');
const finishReason = data.finish_reason;
const filename = `${resource}_${(0, uuid_1.v4)()}.${outputFormat}`;
const filepath = path_1.default.join(os_1.default.tmpdir(), filename);
await fs_extra_1.default.writeFile(filepath, fileData, 'base64');
return {
filepath,
filename,
contentType: outputFormat === 'mp4' ? 'video' : 'image',
outputFormat,
contentFiltered: finishReason === 'CONTENT_FILTERED',
errored: finishReason === 'ERROR',
seed: data.seed,
};
}
exports.processContentResponse = processContentResponse;
//# sourceMappingURL=util.js.map