fix: snippet private data leak

This commit is contained in:
Innei
2022-05-08 21:01:06 +08:00
parent f076c1da91
commit 513d9e0a16
2 changed files with 38 additions and 7 deletions

View File

@@ -107,9 +107,28 @@ export class SnippetController {
if (typeof reference !== 'string') {
throw new ForbiddenException('reference should be string')
}
const cached = await this.snippetService.getCachedSnippet(reference, name)
let cached: string | null = null
if (isMaster) {
cached =
(
await Promise.all(
(['public', 'private'] as const).map((type) => {
return this.snippetService.getCachedSnippet(reference, name, type)
}),
)
).find(Boolean) || null
} else {
cached = await this.snippetService.getCachedSnippet(
reference,
name,
'public',
)
}
if (cached) {
return cached
const json = JSON.safeParse(cached)
return json ? json : cached
}
const snippet = await this.snippetService.getSnippetByName(name, reference)

View File

@@ -154,7 +154,7 @@ export class SnippetService {
async cacheSnippet(model: SnippetModel, value: any) {
const { reference, name } = model
const key = `${reference}:${name}`
const key = `${reference}:${name}:${model.private ? 'private' : ''}`
const client = this.cacheService.getClient()
await client.hset(
getRedisKey(RedisKeys.SnippetCache),
@@ -162,16 +162,28 @@ export class SnippetService {
typeof value !== 'string' ? JSON.stringify(value) : value,
)
}
async getCachedSnippet(reference: string, name: string) {
const key = `${reference}:${name}`
async getCachedSnippet(
reference: string,
name: string,
accessType: 'public' | 'private',
) {
const key = `${reference}:${name}:${
accessType === 'private' ? 'private' : ''
}`
const client = this.cacheService.getClient()
const value = await client.hget(getRedisKey(RedisKeys.SnippetCache), key)
return value
}
async deleteCachedSnippet(reference: string, name: string) {
const key = `${reference}:${name}`
const keyBase = `${reference}:${name}`
const key1 = `${keyBase}:`
const key2 = `${keyBase}:private`
const client = this.cacheService.getClient()
await client.hdel(getRedisKey(RedisKeys.SnippetCache), key)
await Promise.all(
[key1, key2].map((key) => {
return client.hdel(getRedisKey(RedisKeys.SnippetCache), key)
}),
)
}
}