Merge branch 'v3-ui' of github.com:Budibase/budibase into default-view-permissions
This commit is contained in:
commit
496538ac01
|
@ -11,6 +11,7 @@ export interface DeletedApp {
|
||||||
}
|
}
|
||||||
|
|
||||||
const EXPIRY_SECONDS = 3600
|
const EXPIRY_SECONDS = 3600
|
||||||
|
const INVALID_EXPIRY_SECONDS = 60
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The default populate app metadata function
|
* The default populate app metadata function
|
||||||
|
@ -48,9 +49,8 @@ export async function getAppMetadata(appId: string): Promise<App | DeletedApp> {
|
||||||
// app DB left around, but no metadata, it is invalid
|
// app DB left around, but no metadata, it is invalid
|
||||||
if (err && err.status === 404) {
|
if (err && err.status === 404) {
|
||||||
metadata = { state: AppState.INVALID }
|
metadata = { state: AppState.INVALID }
|
||||||
// don't expire the reference to an invalid app, it'll only be
|
// expire invalid apps regularly, in-case it was only briefly invalid
|
||||||
// updated if a metadata doc actually gets stored (app is remade/reverted)
|
expiry = INVALID_EXPIRY_SECONDS
|
||||||
expiry = undefined
|
|
||||||
} else {
|
} else {
|
||||||
throw err
|
throw err
|
||||||
}
|
}
|
||||||
|
|
|
@ -43,6 +43,9 @@ function buildNano(couchInfo: { url: string; cookie: string }) {
|
||||||
}
|
}
|
||||||
|
|
||||||
type DBCall<T> = () => Promise<T>
|
type DBCall<T> = () => Promise<T>
|
||||||
|
type DBCallback<T> = (
|
||||||
|
db: Nano.DocumentScope<any>
|
||||||
|
) => Promise<DBCall<T>> | DBCall<T>
|
||||||
|
|
||||||
class CouchDBError extends Error implements DBError {
|
class CouchDBError extends Error implements DBError {
|
||||||
status: number
|
status: number
|
||||||
|
@ -171,8 +174,8 @@ export class DatabaseImpl implements Database {
|
||||||
}
|
}
|
||||||
|
|
||||||
// this function fetches the DB and handles if DB creation is needed
|
// this function fetches the DB and handles if DB creation is needed
|
||||||
private async performCall<T>(
|
private async performCallWithDBCreation<T>(
|
||||||
call: (db: Nano.DocumentScope<any>) => Promise<DBCall<T>> | DBCall<T>
|
call: DBCallback<T>
|
||||||
): Promise<any> {
|
): Promise<any> {
|
||||||
const db = this.getDb()
|
const db = this.getDb()
|
||||||
const fnc = await call(db)
|
const fnc = await call(db)
|
||||||
|
@ -181,13 +184,24 @@ export class DatabaseImpl implements Database {
|
||||||
} catch (err: any) {
|
} catch (err: any) {
|
||||||
if (err.statusCode === 404 && err.reason === DATABASE_NOT_FOUND) {
|
if (err.statusCode === 404 && err.reason === DATABASE_NOT_FOUND) {
|
||||||
await this.checkAndCreateDb()
|
await this.checkAndCreateDb()
|
||||||
return await this.performCall(call)
|
return await this.performCallWithDBCreation(call)
|
||||||
}
|
}
|
||||||
// stripping the error down the props which are safe/useful, drop everything else
|
// stripping the error down the props which are safe/useful, drop everything else
|
||||||
throw new CouchDBError(`CouchDB error: ${err.message}`, err)
|
throw new CouchDBError(`CouchDB error: ${err.message}`, err)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private async performCall<T>(call: DBCallback<T>): Promise<any> {
|
||||||
|
const db = this.getDb()
|
||||||
|
const fnc = await call(db)
|
||||||
|
try {
|
||||||
|
return await fnc()
|
||||||
|
} catch (err: any) {
|
||||||
|
// stripping the error down the props which are safe/useful, drop everything else
|
||||||
|
throw new CouchDBError(`CouchDB error: ${err.message}`, err)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
async get<T extends Document>(id?: string): Promise<T> {
|
async get<T extends Document>(id?: string): Promise<T> {
|
||||||
return this.performCall(db => {
|
return this.performCall(db => {
|
||||||
if (!id) {
|
if (!id) {
|
||||||
|
@ -227,6 +241,7 @@ export class DatabaseImpl implements Database {
|
||||||
}
|
}
|
||||||
|
|
||||||
async remove(idOrDoc: string | Document, rev?: string) {
|
async remove(idOrDoc: string | Document, rev?: string) {
|
||||||
|
// not a read call - but don't create a DB to delete a document
|
||||||
return this.performCall(db => {
|
return this.performCall(db => {
|
||||||
let _id: string
|
let _id: string
|
||||||
let _rev: string
|
let _rev: string
|
||||||
|
@ -286,7 +301,7 @@ export class DatabaseImpl implements Database {
|
||||||
if (!document._id) {
|
if (!document._id) {
|
||||||
throw new Error("Cannot store document without _id field.")
|
throw new Error("Cannot store document without _id field.")
|
||||||
}
|
}
|
||||||
return this.performCall(async db => {
|
return this.performCallWithDBCreation(async db => {
|
||||||
if (!document.createdAt) {
|
if (!document.createdAt) {
|
||||||
document.createdAt = new Date().toISOString()
|
document.createdAt = new Date().toISOString()
|
||||||
}
|
}
|
||||||
|
@ -309,7 +324,7 @@ export class DatabaseImpl implements Database {
|
||||||
|
|
||||||
async bulkDocs(documents: AnyDocument[]) {
|
async bulkDocs(documents: AnyDocument[]) {
|
||||||
const now = new Date().toISOString()
|
const now = new Date().toISOString()
|
||||||
return this.performCall(db => {
|
return this.performCallWithDBCreation(db => {
|
||||||
return () =>
|
return () =>
|
||||||
db.bulk({
|
db.bulk({
|
||||||
docs: documents.map(d => ({ createdAt: now, ...d, updatedAt: now })),
|
docs: documents.map(d => ({ createdAt: now, ...d, updatedAt: now })),
|
||||||
|
@ -321,7 +336,21 @@ export class DatabaseImpl implements Database {
|
||||||
params: DatabaseQueryOpts
|
params: DatabaseQueryOpts
|
||||||
): Promise<AllDocsResponse<T>> {
|
): Promise<AllDocsResponse<T>> {
|
||||||
return this.performCall(db => {
|
return this.performCall(db => {
|
||||||
return () => db.list(params)
|
return async () => {
|
||||||
|
try {
|
||||||
|
return (await db.list(params)) as AllDocsResponse<T>
|
||||||
|
} catch (err: any) {
|
||||||
|
if (err.reason === DATABASE_NOT_FOUND) {
|
||||||
|
return {
|
||||||
|
offset: 0,
|
||||||
|
total_rows: 0,
|
||||||
|
rows: [],
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
throw err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue