rxdb
Version:
A local-first realtime NoSQL Database for JavaScript applications - https://rxdb.info/
109 lines (93 loc) • 3.31 kB
text/typescript
import type { GoogleDriveOptionsWithDefaults } from './google-drive-types.ts';
import {
ensureFolderExists,
readFolder,
createEmptyFile,
fillFileIfEtagMatches,
readJsonFileContent
} from './google-drive-helper.ts';
import { newRxError } from '../../rx-error.ts';
import { randomToken } from '../utils/utils-string.ts';
import { TRANSACTION_FILE_NAME } from './transaction.ts';
import { ensureNotFalsy } from '../utils/index.ts';
import { WAL_FILE_NAME } from './upstream.ts';
const NON_ALLOWED_ROOT_FOLDERS = [
'/',
'',
null,
false,
undefined,
'root'
];
export async function initDriveStructure(
googleDriveOptions: GoogleDriveOptionsWithDefaults
) {
NON_ALLOWED_ROOT_FOLDERS.forEach(nonAllowed => {
if (googleDriveOptions.folderPath === nonAllowed) {
throw newRxError('GDR1', {
folderPath: googleDriveOptions.folderPath
});
}
});
// root folder
const rootFolderId = await ensureFolderExists(googleDriveOptions, googleDriveOptions.folderPath);
const rootFolderContent = await readFolder(googleDriveOptions, googleDriveOptions.folderPath);
/**
* Folder but either be empty
* or already used as a RxDB google-drive sync target.
*/
const hasRxDBJson = rootFolderContent.find((file: any) => file.name === 'rxdb.json');
const hasOther = rootFolderContent.find((file: any) => file.name !== 'rxdb.json');
if (hasOther && !hasRxDBJson) {
throw newRxError('GDR9', {
folderPath: googleDriveOptions.folderPath
});
}
/**
* Create rxdb.json file.
* This must always be the first step.
*/
const rxdbJson = await createEmptyFile(googleDriveOptions, rootFolderId, 'rxdb.json');
let replicationIdentifier: string;
if (rxdbJson.size === 0) {
const rxdbJsonData = await fillFileIfEtagMatches<{ replicationIdentifier: string }>(
googleDriveOptions,
rxdbJson.fileId,
rxdbJson.etag,
{ replicationIdentifier: randomToken(10) }
);
replicationIdentifier = ensureNotFalsy(rxdbJsonData.content).replicationIdentifier;
} else {
const rxdbJsonData = await readJsonFileContent<{ replicationIdentifier: string }>(
googleDriveOptions,
rxdbJson.fileId
);
replicationIdentifier = ensureNotFalsy(rxdbJsonData.content).replicationIdentifier;
}
// docs folder
const docsFolderId = await ensureFolderExists(googleDriveOptions, googleDriveOptions.folderPath + '/docs');
// signaling folder
const signalingFolderId = await ensureFolderExists(googleDriveOptions, googleDriveOptions.folderPath + '/signaling');
// transaction file
const transactionFile = await createEmptyFile(
googleDriveOptions,
rootFolderId,
TRANSACTION_FILE_NAME
);
// WAL file
const walFile = await createEmptyFile(
googleDriveOptions,
rootFolderId,
WAL_FILE_NAME
);
return {
rootFolderId,
docsFolderId,
signalingFolderId,
replicationIdentifier,
rxdbJson,
transactionFile,
walFile
};
}
export type DriveStructure = Awaited<ReturnType<typeof initDriveStructure>>;