in compiler/src/model/utils.ts [1317:1448]
export function verifyUniqueness (project: Project): void {
const types: Map<string, string[]> = new Map()
const common: string[] = []
// get global `_types`
for (const sourceFile of project.getSourceFiles()) {
const path = dirname(sourceFile.getFilePath().replace(/.*[/\\]specification[/\\]?/, ''))
if (!path.startsWith('_types')) continue
for (const declaration of sourceFile.getClasses()) {
const name = declaration.getName()
assert(declaration, name != null, 'Anonymous classes cannot exists')
assert(declaration, !name.endsWith('Request') && !name.endsWith('Response'), 'A type cannot end with "Request" or "Response"')
assert(declaration, !common.includes(name), `${name} is already defined in the global types`)
common.push(name)
}
for (const declaration of sourceFile.getInterfaces()) {
assert(declaration, !declaration.getName().endsWith('Request') && !declaration.getName().endsWith('Response'), 'A type cannot end with "Request" or "Response"')
assert(declaration, !common.includes(declaration.getName()), `${declaration.getName()} is already defined in the global types`)
common.push(declaration.getName())
}
for (const declaration of sourceFile.getEnums()) {
assert(declaration, !declaration.getName().endsWith('Request') && !declaration.getName().endsWith('Response'), 'A type cannot end with "Request" or "Response"')
assert(declaration, !common.includes(declaration.getName()), `${declaration.getName()} is already defined in the global types`)
common.push(declaration.getName())
}
for (const declaration of sourceFile.getTypeAliases()) {
assert(declaration, !declaration.getName().endsWith('Request') && !declaration.getName().endsWith('Response'), 'A type cannot end with "Request" or "Response"')
assert(declaration, !common.includes(declaration.getName()), `${declaration.getName()} is already defined in the global types`)
common.push(declaration.getName())
}
}
// nested `_types`
for (const sourceFile of project.getSourceFiles()) {
const path = dirname(sourceFile.getFilePath().replace(/.*[/\\]specification[/\\]?/, ''))
if (path.startsWith('_types')) continue
if (!path.includes('_types')) continue
const namespace = path.startsWith('_global') ? `_global${'/'}${path.split('/')[1]}` : path.split('/')[0]
const names = types.get(namespace) ?? []
for (const declaration of sourceFile.getClasses()) {
const name = declaration.getName()
assert(declaration, name != null, 'Anonymous classes cannot exists')
assert(declaration, !name.endsWith('Request') && !name.endsWith('Response'), 'A type cannot end with "Request" or "Response"')
assert(declaration, !common.includes(name), `${name} is already defined in ${namespace} is already defined in the global types`)
assert(declaration, !names.includes(name), `${name} is already defined in ${namespace} local types`)
names.push(name)
}
for (const declaration of sourceFile.getInterfaces()) {
assert(declaration, !declaration.getName().endsWith('Request') && !declaration.getName().endsWith('Response'), 'A type cannot end with "Request" or "Response"')
assert(declaration, !common.includes(declaration.getName()), `${declaration.getName()} is already defined in the global types`)
assert(declaration, !names.includes(declaration.getName()), `${declaration.getName()} is already defined in ${namespace} local types`)
names.push(declaration.getName())
}
for (const declaration of sourceFile.getEnums()) {
assert(declaration, !declaration.getName().endsWith('Request') && !declaration.getName().endsWith('Response'), 'A type cannot end with "Request" or "Response"')
assert(declaration, !common.includes(declaration.getName()), `${declaration.getName()} is already defined in the global types`)
assert(declaration, !names.includes(declaration.getName()), `${declaration.getName()} is already defined in ${namespace} local types`)
names.push(declaration.getName())
}
for (const declaration of sourceFile.getTypeAliases()) {
assert(declaration, !declaration.getName().endsWith('Request') && !declaration.getName().endsWith('Response'), 'A type cannot end with "Request" or "Response"')
assert(declaration, !common.includes(declaration.getName()), `${declaration.getName()} is already defined in the global types`)
assert(declaration, !names.includes(declaration.getName()), `${declaration.getName()} is already defined in ${namespace} local types`)
names.push(declaration.getName())
}
types.set(namespace, names)
}
// every other namespaced type
for (const sourceFile of project.getSourceFiles()) {
const path = dirname(sourceFile.getFilePath().replace(/.*[/\\]specification[/\\]?/, ''))
if (path.includes('_types')) continue
const namespace = path.startsWith('_global') ? `_global${'/'}${path.split('/')[1]}` : path.split('/')[0]
const names = types.get(path) ?? []
const localTypes = types.get(namespace) ?? []
for (const declaration of sourceFile.getClasses()) {
const name = declaration.getName()
assert(declaration, name != null, 'Anonymous classes cannot exists')
if (name !== 'Request' && name !== 'Response') {
assert(declaration, !name.endsWith('Request') && !name.endsWith('Response'), 'A type cannot end with "Request" or "Response"')
}
assert(declaration, !names.includes(name), `${name} is already defined`)
assert(declaration, !common.includes(name), `${name} is already defined in the global types`)
assert(declaration, !localTypes.includes(name), `${name} is already defined in ${namespace} local types`)
names.push(name)
}
for (const declaration of sourceFile.getInterfaces()) {
if (declaration.getName() !== 'Request' && declaration.getName() !== 'Response') {
assert(declaration, !declaration.getName().endsWith('Request') && !declaration.getName().endsWith('Response'), 'A type cannot end with "Request" or "Response"')
}
assert(declaration, !names.includes(declaration.getName()), `${declaration.getName()} is already defined`)
assert(declaration, !common.includes(declaration.getName()), `${declaration.getName()} is already defined in the global types`)
assert(declaration, !localTypes.includes(declaration.getName()), `${declaration.getName()} is already defined in ${namespace} local types`)
names.push(declaration.getName())
}
for (const declaration of sourceFile.getEnums()) {
if (declaration.getName() !== 'Request' && declaration.getName() !== 'Response') {
assert(declaration, !declaration.getName().endsWith('Request') && !declaration.getName().endsWith('Response'), 'A type cannot end with "Request" or "Response"')
}
assert(declaration, !names.includes(declaration.getName()), `${declaration.getName()} is already defined`)
assert(declaration, !common.includes(declaration.getName()), `${declaration.getName()} is already defined in the global types`)
assert(declaration, !localTypes.includes(declaration.getName()), `${declaration.getName()} is already defined in ${namespace} local types`)
names.push(declaration.getName())
}
for (const declaration of sourceFile.getTypeAliases()) {
if (declaration.getName() !== 'Request' && declaration.getName() !== 'Response') {
assert(declaration, !declaration.getName().endsWith('Request') && !declaration.getName().endsWith('Response'), 'A type cannot end with "Request" or "Response"')
}
assert(declaration, !names.includes(declaration.getName()), `${declaration.getName()} is already defined`)
assert(declaration, !common.includes(declaration.getName()), `${declaration.getName()} is already defined in the global types`)
assert(declaration, !localTypes.includes(declaration.getName()), `${declaration.getName()} is already defined in ${namespace} local types`)
names.push(declaration.getName())
}
types.set(path, names)
}
}