appwrite-utils-cli
Version:
Appwrite Utility Functions to help with database management, data conversion, data import, migrations, and much more. Meant to be used as a CLI tool, I do not recommend installing this in frontend environments.
723 lines (722 loc) • 29.8 kB
TypeScript
import { z } from "zod";
import { type AppwriteConfig, type AppwriteFunction } from "appwrite-utils";
declare const YamlConfigSchema: z.ZodObject<{
appwrite: z.ZodObject<{
endpoint: z.ZodDefault<z.ZodString>;
project: z.ZodString;
key: z.ZodString;
sessionCookie: z.ZodOptional<z.ZodString>;
authMethod: z.ZodDefault<z.ZodOptional<z.ZodEnum<{
session: "session";
apikey: "apikey";
auto: "auto";
}>>>;
sessionMetadata: z.ZodOptional<z.ZodObject<{
email: z.ZodOptional<z.ZodString>;
expiresAt: z.ZodOptional<z.ZodString>;
}, z.core.$strip>>;
}, z.core.$strip>;
logging: z.ZodDefault<z.ZodOptional<z.ZodObject<{
enabled: z.ZodDefault<z.ZodBoolean>;
level: z.ZodDefault<z.ZodEnum<{
error: "error";
info: "info";
debug: "debug";
warn: "warn";
}>>;
directory: z.ZodOptional<z.ZodString>;
console: z.ZodDefault<z.ZodBoolean>;
}, z.core.$strip>>>;
backups: z.ZodDefault<z.ZodOptional<z.ZodObject<{
enabled: z.ZodDefault<z.ZodBoolean>;
interval: z.ZodDefault<z.ZodNumber>;
retention: z.ZodDefault<z.ZodNumber>;
cleanup: z.ZodDefault<z.ZodBoolean>;
}, z.core.$strip>>>;
data: z.ZodDefault<z.ZodOptional<z.ZodObject<{
enableMockData: z.ZodDefault<z.ZodBoolean>;
documentBucketId: z.ZodDefault<z.ZodString>;
usersCollectionName: z.ZodDefault<z.ZodString>;
importDirectory: z.ZodDefault<z.ZodString>;
}, z.core.$strip>>>;
schemas: z.ZodDefault<z.ZodOptional<z.ZodObject<{
outputDirectory: z.ZodDefault<z.ZodString>;
yamlSchemaDirectory: z.ZodDefault<z.ZodString>;
collectionsDirectory: z.ZodDefault<z.ZodString>;
tablesDirectory: z.ZodDefault<z.ZodString>;
}, z.core.$strip>>>;
migrations: z.ZodDefault<z.ZodOptional<z.ZodObject<{
enabled: z.ZodDefault<z.ZodBoolean>;
}, z.core.$strip>>>;
databases: z.ZodDefault<z.ZodOptional<z.ZodArray<z.ZodObject<{
id: z.ZodString;
name: z.ZodString;
bucket: z.ZodOptional<z.ZodObject<{
id: z.ZodString;
name: z.ZodString;
permissions: z.ZodOptional<z.ZodArray<z.ZodUnion<[z.ZodObject<{
permission: z.ZodString;
target: z.ZodString;
}, z.core.$strip>, z.ZodPipe<z.ZodString, z.ZodTransform<{
permission: string;
target: string;
}, string>>]>>>;
fileSecurity: z.ZodOptional<z.ZodBoolean>;
enabled: z.ZodOptional<z.ZodBoolean>;
maximumFileSize: z.ZodOptional<z.ZodNumber>;
allowedFileExtensions: z.ZodOptional<z.ZodArray<z.ZodString>>;
compression: z.ZodOptional<z.ZodEnum<{
none: "none";
gzip: "gzip";
zstd: "zstd";
}>>;
encryption: z.ZodOptional<z.ZodBoolean>;
antivirus: z.ZodOptional<z.ZodBoolean>;
}, z.core.$strip>>;
}, z.core.$strip>>>>;
buckets: z.ZodDefault<z.ZodOptional<z.ZodArray<z.ZodObject<{
id: z.ZodString;
name: z.ZodString;
permissions: z.ZodOptional<z.ZodArray<z.ZodUnion<[z.ZodObject<{
permission: z.ZodString;
target: z.ZodString;
}, z.core.$strip>, z.ZodPipe<z.ZodString, z.ZodTransform<{
permission: string;
target: string;
}, string>>]>>>;
fileSecurity: z.ZodOptional<z.ZodBoolean>;
enabled: z.ZodOptional<z.ZodBoolean>;
maximumFileSize: z.ZodOptional<z.ZodNumber>;
allowedFileExtensions: z.ZodOptional<z.ZodArray<z.ZodString>>;
compression: z.ZodOptional<z.ZodEnum<{
none: "none";
gzip: "gzip";
zstd: "zstd";
}>>;
encryption: z.ZodOptional<z.ZodBoolean>;
antivirus: z.ZodOptional<z.ZodBoolean>;
}, z.core.$strip>>>>;
functions: z.ZodDefault<z.ZodOptional<z.ZodArray<z.ZodObject<{
id: z.ZodString;
name: z.ZodString;
runtime: any;
execute: z.ZodOptional<z.ZodArray<z.ZodString>>;
events: z.ZodOptional<z.ZodArray<z.ZodString>>;
schedule: z.ZodOptional<z.ZodString>;
timeout: z.ZodOptional<z.ZodNumber>;
enabled: z.ZodOptional<z.ZodBoolean>;
logging: z.ZodOptional<z.ZodBoolean>;
entrypoint: z.ZodOptional<z.ZodString>;
commands: z.ZodOptional<z.ZodString>;
scopes: z.ZodOptional<z.ZodArray<z.ZodString>>;
installationId: z.ZodOptional<z.ZodString>;
providerRepositoryId: z.ZodOptional<z.ZodString>;
providerBranch: z.ZodOptional<z.ZodString>;
providerSilentMode: z.ZodOptional<z.ZodBoolean>;
providerRootDirectory: z.ZodOptional<z.ZodString>;
templateRepository: z.ZodOptional<z.ZodString>;
templateOwner: z.ZodOptional<z.ZodString>;
templateRootDirectory: z.ZodOptional<z.ZodString>;
templateBranch: z.ZodOptional<z.ZodString>;
specification: z.ZodOptional<z.ZodString>;
dirPath: z.ZodOptional<z.ZodString>;
predeployCommands: z.ZodOptional<z.ZodArray<z.ZodString>>;
deployDir: z.ZodOptional<z.ZodString>;
ignore: z.ZodOptional<z.ZodArray<z.ZodString>>;
templateVersion: z.ZodOptional<z.ZodString>;
}, z.core.$strip>>>>;
}, z.core.$strip>;
export type YamlConfig = z.infer<typeof YamlConfigSchema>;
export declare const convertYamlToAppwriteConfig: (yamlConfig: YamlConfig) => AppwriteConfig;
/**
* Enhanced config loading with session authentication support
* Supports session override options for preserving session state
*/
export interface YamlSessionOptions {
sessionCookie?: string;
authMethod?: "session" | "apikey" | "auto";
sessionMetadata?: {
email?: string;
expiresAt?: string;
};
}
/**
* Load YAML config with optional session preservation
* Maintains authentication priority: explicit session > YAML file > system prefs
*/
export declare const loadYamlConfigWithSession: (configPath: string, sessionOptions?: YamlSessionOptions) => Promise<AppwriteConfig | null>;
export declare const loadYamlConfig: (configPath: string) => Promise<AppwriteConfig | null>;
export declare const findYamlConfig: (startDir: string) => string | null;
export declare const generateYamlConfigTemplate: (outputPath: string) => void;
/**
* Converts AppwriteConfig back to YAML format and writes to file
* @param configPath Path to the YAML config file
* @param config The AppwriteConfig to convert and save
*/
export declare const writeYamlConfig: (configPath: string, config: AppwriteConfig) => Promise<void>;
/**
* Adds a new function to the YAML config file
* @param configPath Path to the YAML config file
* @param newFunction The function configuration to add
*/
export declare const addFunctionToYamlConfig: (configPath: string, newFunction: AppwriteFunction) => Promise<void>;
/**
* Extract session options from AppwriteConfig for YAML operations
* Useful for preserving session state during config reloads
*/
export declare const extractSessionOptionsFromConfig: (config: AppwriteConfig) => YamlSessionOptions;
/**
* Create session-preserved YAML config operations
* Maintains authentication state during config file updates
*/
export declare const createSessionPreservingYamlConfig: (configPath: string, sessionOptions: YamlSessionOptions) => {
load: () => Promise<{
appwriteEndpoint: string;
appwriteProject: string;
appwriteKey: string;
appwriteClient: any;
authMethod: "session" | "apikey" | "auto";
logging: {
enabled: boolean;
level: "error" | "warn" | "info" | "debug";
console: boolean;
logDirectory?: string | undefined;
};
enableBackups: boolean;
backupInterval: number;
backupRetention: number;
enableBackupCleanup: boolean;
enableMockData: boolean;
documentBucketId: string;
usersCollectionName: string;
databases: {
$id: string;
name: string;
bucket?: {
$id: string;
name: string;
permissions?: ({
permission: string;
target: string;
} | {
permission: string;
target: string;
})[] | undefined;
fileSecurity?: boolean | undefined;
enabled?: boolean | undefined;
maximumFileSize?: number | undefined;
allowedFileExtensions?: string[] | undefined;
compression?: "none" | "gzip" | "zstd" | undefined;
encryption?: boolean | undefined;
antivirus?: boolean | undefined;
} | undefined;
}[];
buckets: {
$id: string;
name: string;
permissions?: ({
permission: string;
target: string;
} | {
permission: string;
target: string;
})[] | undefined;
fileSecurity?: boolean | undefined;
enabled?: boolean | undefined;
maximumFileSize?: number | undefined;
allowedFileExtensions?: string[] | undefined;
compression?: "none" | "gzip" | "zstd" | undefined;
encryption?: boolean | undefined;
antivirus?: boolean | undefined;
}[];
apiMode: "auto" | "legacy" | "tablesdb";
sessionCookie?: string | undefined;
sessionMetadata?: {
email?: string | undefined;
expiresAt?: string | undefined;
} | undefined;
collections?: {
name: string;
attributes: ({
key: string;
required: boolean;
type: "integer";
array?: boolean | undefined;
format?: string | undefined;
status?: string | undefined;
attributes?: string[] | undefined;
orders?: string[] | undefined;
$createdAt?: string | undefined;
$updatedAt?: string | undefined;
error?: string | undefined;
min?: number | undefined;
max?: number | undefined;
xdefault?: number | null | undefined;
} | {
key: string;
required: boolean;
type: "relationship";
relatedCollection: string;
relationType: "oneToMany" | "manyToOne" | "oneToOne" | "manyToMany";
twoWay: boolean;
onDelete: "setNull" | "cascade" | "restrict";
array?: boolean | undefined;
format?: string | undefined;
status?: string | undefined;
attributes?: string[] | undefined;
orders?: string[] | undefined;
$createdAt?: string | undefined;
$updatedAt?: string | undefined;
error?: string | undefined;
twoWayKey?: string | undefined;
side?: "parent" | "child" | undefined;
importMapping?: {
originalIdField: string;
targetField?: string | undefined;
} | undefined;
} | {
key: string;
required: boolean;
type: "string";
size: number;
array?: boolean | undefined;
format?: string | undefined;
status?: string | undefined;
attributes?: string[] | undefined;
orders?: string[] | undefined;
$createdAt?: string | undefined;
$updatedAt?: string | undefined;
error?: string | undefined;
xdefault?: string | null | undefined;
encrypt?: boolean | undefined;
} | {
key: string;
required: boolean;
type: "double";
array?: boolean | undefined;
format?: string | undefined;
status?: string | undefined;
attributes?: string[] | undefined;
orders?: string[] | undefined;
$createdAt?: string | undefined;
$updatedAt?: string | undefined;
error?: string | undefined;
min?: number | undefined;
max?: number | undefined;
xdefault?: number | null | undefined;
} | {
key: string;
required: boolean;
type: "float";
array?: boolean | undefined;
format?: string | undefined;
status?: string | undefined;
attributes?: string[] | undefined;
orders?: string[] | undefined;
$createdAt?: string | undefined;
$updatedAt?: string | undefined;
error?: string | undefined;
min?: number | undefined;
max?: number | undefined;
xdefault?: number | null | undefined;
} | {
key: string;
required: boolean;
type: "boolean";
array?: boolean | undefined;
format?: string | undefined;
status?: string | undefined;
attributes?: string[] | undefined;
orders?: string[] | undefined;
$createdAt?: string | undefined;
$updatedAt?: string | undefined;
error?: string | undefined;
xdefault?: boolean | null | undefined;
} | {
key: string;
required: boolean;
type: "datetime";
array?: boolean | undefined;
format?: string | undefined;
status?: string | undefined;
attributes?: string[] | undefined;
orders?: string[] | undefined;
$createdAt?: string | undefined;
$updatedAt?: string | undefined;
error?: string | undefined;
xdefault?: string | null | undefined;
} | {
key: string;
required: boolean;
type: "email";
array?: boolean | undefined;
format?: string | undefined;
status?: string | undefined;
attributes?: string[] | undefined;
orders?: string[] | undefined;
$createdAt?: string | undefined;
$updatedAt?: string | undefined;
error?: string | undefined;
xdefault?: string | null | undefined;
} | {
key: string;
required: boolean;
type: "ip";
array?: boolean | undefined;
format?: string | undefined;
status?: string | undefined;
attributes?: string[] | undefined;
orders?: string[] | undefined;
$createdAt?: string | undefined;
$updatedAt?: string | undefined;
error?: string | undefined;
xdefault?: string | null | undefined;
} | {
key: string;
required: boolean;
type: "url";
array?: boolean | undefined;
format?: string | undefined;
status?: string | undefined;
attributes?: string[] | undefined;
orders?: string[] | undefined;
$createdAt?: string | undefined;
$updatedAt?: string | undefined;
error?: string | undefined;
xdefault?: string | null | undefined;
} | {
key: string;
required: boolean;
type: "enum";
elements: string[];
array?: boolean | undefined;
format?: string | undefined;
status?: string | undefined;
attributes?: string[] | undefined;
orders?: string[] | undefined;
$createdAt?: string | undefined;
$updatedAt?: string | undefined;
error?: string | undefined;
xdefault?: string | null | undefined;
})[];
$permissions: {
permission: string;
target: string;
}[];
indexes: {
key: string;
type: "key" | "unique" | "fulltext";
attributes: string[];
status?: string | undefined;
error?: string | undefined;
orders?: string[] | undefined;
}[];
importDefs: {
filePath: string;
primaryKeyField: string;
attributeMappings: {
targetKey: string;
oldKey?: string | undefined;
oldKeys?: string[] | undefined;
valueToSet?: any;
fileData?: {
name: string;
path: string;
} | undefined;
converters?: string[] | undefined;
validationActions?: {
action: string;
params: string[];
}[] | undefined;
postImportActions?: {
action: string;
params: (string | Record<string, any>)[];
}[] | undefined;
}[];
type?: "create" | "update" | undefined;
basePath?: string | undefined;
idMappings?: {
sourceField: string;
targetField: string;
targetCollection: string;
fieldToSet?: string | undefined;
targetFieldToMatch?: string | undefined;
}[] | undefined;
createUsers?: boolean | null | undefined;
updateMapping?: {
originalIdField: string;
targetField: string;
} | undefined;
}[];
$id?: string | undefined;
enabled?: boolean | undefined;
documentSecurity?: boolean | undefined;
databaseId?: string | undefined;
databaseIds?: string[] | undefined;
}[] | undefined;
tables?: {
attributes: ({
key: string;
required: boolean;
type: "integer";
array?: boolean | undefined;
format?: string | undefined;
status?: string | undefined;
attributes?: string[] | undefined;
orders?: string[] | undefined;
$createdAt?: string | undefined;
$updatedAt?: string | undefined;
error?: string | undefined;
min?: number | undefined;
max?: number | undefined;
xdefault?: number | null | undefined;
} | {
key: string;
required: boolean;
type: "relationship";
relatedCollection: string;
relationType: "oneToMany" | "manyToOne" | "oneToOne" | "manyToMany";
twoWay: boolean;
onDelete: "setNull" | "cascade" | "restrict";
array?: boolean | undefined;
format?: string | undefined;
status?: string | undefined;
attributes?: string[] | undefined;
orders?: string[] | undefined;
$createdAt?: string | undefined;
$updatedAt?: string | undefined;
error?: string | undefined;
twoWayKey?: string | undefined;
side?: "parent" | "child" | undefined;
importMapping?: {
originalIdField: string;
targetField?: string | undefined;
} | undefined;
} | {
key: string;
required: boolean;
type: "string";
size: number;
array?: boolean | undefined;
format?: string | undefined;
status?: string | undefined;
attributes?: string[] | undefined;
orders?: string[] | undefined;
$createdAt?: string | undefined;
$updatedAt?: string | undefined;
error?: string | undefined;
xdefault?: string | null | undefined;
encrypt?: boolean | undefined;
} | {
key: string;
required: boolean;
type: "double";
array?: boolean | undefined;
format?: string | undefined;
status?: string | undefined;
attributes?: string[] | undefined;
orders?: string[] | undefined;
$createdAt?: string | undefined;
$updatedAt?: string | undefined;
error?: string | undefined;
min?: number | undefined;
max?: number | undefined;
xdefault?: number | null | undefined;
} | {
key: string;
required: boolean;
type: "float";
array?: boolean | undefined;
format?: string | undefined;
status?: string | undefined;
attributes?: string[] | undefined;
orders?: string[] | undefined;
$createdAt?: string | undefined;
$updatedAt?: string | undefined;
error?: string | undefined;
min?: number | undefined;
max?: number | undefined;
xdefault?: number | null | undefined;
} | {
key: string;
required: boolean;
type: "boolean";
array?: boolean | undefined;
format?: string | undefined;
status?: string | undefined;
attributes?: string[] | undefined;
orders?: string[] | undefined;
$createdAt?: string | undefined;
$updatedAt?: string | undefined;
error?: string | undefined;
xdefault?: boolean | null | undefined;
} | {
key: string;
required: boolean;
type: "datetime";
array?: boolean | undefined;
format?: string | undefined;
status?: string | undefined;
attributes?: string[] | undefined;
orders?: string[] | undefined;
$createdAt?: string | undefined;
$updatedAt?: string | undefined;
error?: string | undefined;
xdefault?: string | null | undefined;
} | {
key: string;
required: boolean;
type: "email";
array?: boolean | undefined;
format?: string | undefined;
status?: string | undefined;
attributes?: string[] | undefined;
orders?: string[] | undefined;
$createdAt?: string | undefined;
$updatedAt?: string | undefined;
error?: string | undefined;
xdefault?: string | null | undefined;
} | {
key: string;
required: boolean;
type: "ip";
array?: boolean | undefined;
format?: string | undefined;
status?: string | undefined;
attributes?: string[] | undefined;
orders?: string[] | undefined;
$createdAt?: string | undefined;
$updatedAt?: string | undefined;
error?: string | undefined;
xdefault?: string | null | undefined;
} | {
key: string;
required: boolean;
type: "url";
array?: boolean | undefined;
format?: string | undefined;
status?: string | undefined;
attributes?: string[] | undefined;
orders?: string[] | undefined;
$createdAt?: string | undefined;
$updatedAt?: string | undefined;
error?: string | undefined;
xdefault?: string | null | undefined;
} | {
key: string;
required: boolean;
type: "enum";
elements: string[];
array?: boolean | undefined;
format?: string | undefined;
status?: string | undefined;
attributes?: string[] | undefined;
orders?: string[] | undefined;
$createdAt?: string | undefined;
$updatedAt?: string | undefined;
error?: string | undefined;
xdefault?: string | null | undefined;
})[];
columns: undefined;
indexes: {
key: string;
type: "key" | "unique" | "fulltext";
attributes: string[];
status?: string | undefined;
error?: string | undefined;
orders?: string[] | undefined;
}[];
name: string;
$permissions: {
permission: string;
target: string;
}[];
importDefs: {
filePath: string;
primaryKeyField: string;
attributeMappings: {
targetKey: string;
oldKey?: string | undefined;
oldKeys?: string[] | undefined;
valueToSet?: any;
fileData?: {
name: string;
path: string;
} | undefined;
converters?: string[] | undefined;
validationActions?: {
action: string;
params: string[];
}[] | undefined;
postImportActions?: {
action: string;
params: (string | Record<string, any>)[];
}[] | undefined;
}[];
type?: "create" | "update" | undefined;
basePath?: string | undefined;
idMappings?: {
sourceField: string;
targetField: string;
targetCollection: string;
fieldToSet?: string | undefined;
targetFieldToMatch?: string | undefined;
}[] | undefined;
createUsers?: boolean | null | undefined;
updateMapping?: {
originalIdField: string;
targetField: string;
} | undefined;
}[];
$id?: string | undefined;
enabled?: boolean | undefined;
documentSecurity?: boolean | undefined;
databaseId?: string | undefined;
databaseIds?: string[] | undefined;
tableId?: string | undefined;
rowSecurity?: boolean | undefined;
}[] | undefined;
functions?: {
$id: string;
name: string;
runtime: any;
execute: string[];
dirPath?: string | undefined;
events?: string[] | undefined;
schedule?: string | undefined;
timeout?: number | undefined;
enabled?: boolean | undefined;
logging?: boolean | undefined;
ignore?: string[] | undefined;
entrypoint?: string | undefined;
predeployCommands?: string[] | undefined;
deployDir?: string | undefined;
commands?: string | undefined;
scopes?: string[] | undefined;
installationId?: string | undefined;
providerRepositoryId?: string | undefined;
providerBranch?: string | undefined;
providerSilentMode?: boolean | undefined;
providerRootDirectory?: string | undefined;
templateRepository?: string | undefined;
templateOwner?: string | undefined;
templateRootDirectory?: string | undefined;
templateVersion?: string | undefined;
specification?: string | undefined;
}[] | undefined;
schemaConfig?: {
outputDirectory: string;
yamlSchemaDirectory: string;
importDirectory: string;
collectionsDirectory: string;
tablesDirectory: string;
} | undefined;
} | null>;
write: (config: AppwriteConfig) => Promise<void>;
addFunction: (func: AppwriteFunction) => Promise<void>;
};
/**
* Determine if YAML config has session authentication configured
*/
export declare const hasYamlSessionAuth: (configPath: string) => boolean;
export {};