diff --git a/.gitignore b/.gitignore index f1aec7a..404778a 100644 --- a/.gitignore +++ b/.gitignore @@ -1,4 +1,5 @@ node_modules dist coverage -.vscode \ No newline at end of file +.vscode +globalConfig.json \ No newline at end of file diff --git a/package.json b/package.json index f8211a8..3a5f988 100644 --- a/package.json +++ b/package.json @@ -8,9 +8,9 @@ "build": "rimraf dist && tsc -p tsconfig-build.json", "dev": "sucrase-node src/main/server.ts", "check": "npm-check -s -u", - "test": "jest --passWithNoTests --silent --noStackTrace --runInBand", - "test:verbose": "jest --passWithNoTests --runInBand", + "test": "jest --passWithNoTests --runInBand --no-cache", "test:unit": "npm test -- --watch -c jest-unit-config.js", + "test:verbose": "jest --passWithNoTests --runInBand", "test:integration": "npm test -- --watch -c jest-integration-config.js", "test:staged": "npm test -- --findRelatedTests", "test:ci": "npm test -- --coverage", @@ -18,7 +18,7 @@ }, "keywords": [], "author": "Gilberto Mossmann", - "license": "ISC", + "license": "GPL-3.0-or-later", "devDependencies": { "@shelf/jest-mongodb": "^4.1.7", "@types/bcrypt": "^5.0.0", @@ -60,6 +60,9 @@ "swagger-ui-express": "^4.6.2", "validator": "^13.9.0" }, + "engines": { + "node": "16.x" + }, "_moduleAliases": { "@": "dist" } diff --git a/src/main/docs/components.ts b/src/main/docs/components.ts new file mode 100644 index 0000000..01d760d --- /dev/null +++ b/src/main/docs/components.ts @@ -0,0 +1,19 @@ +import { apiKeyAuthSchema } from './schemas/' +import { + badRequest, + serverError, + unauthorized, + notFound, + forbidden +} from './components/' + +export default { + securitySchemes: { + apiKeyAuth: apiKeyAuthSchema + }, + badRequest, + serverError, + unauthorized, + notFound, + forbidden +} diff --git a/src/main/docs/components/bad-request.ts b/src/main/docs/components/bad-request.ts new file mode 100644 index 0000000..2df8e40 --- /dev/null +++ b/src/main/docs/components/bad-request.ts @@ -0,0 +1,10 @@ +export const badRequest = { + description: 'Requisição inválida', + content: { + 'application/json': { + schema: { + $ref: '#/schemas/error' + } + } + } +} diff --git a/src/main/docs/components/forbidden.ts b/src/main/docs/components/forbidden.ts new file mode 100644 index 0000000..a18c287 --- /dev/null +++ b/src/main/docs/components/forbidden.ts @@ -0,0 +1,10 @@ +export const forbidden = { + description: 'Acesso negado', + content: { + 'application/json': { + schema: { + $ref: '#/schemas/error' + } + } + } +} diff --git a/src/main/docs/components/index.ts b/src/main/docs/components/index.ts new file mode 100644 index 0000000..b1b4c83 --- /dev/null +++ b/src/main/docs/components/index.ts @@ -0,0 +1,5 @@ +export * from './bad-request' +export * from './server-error' +export * from './unauthorized' +export * from './not-found' +export * from './forbidden' diff --git a/src/main/docs/components/not-found.ts b/src/main/docs/components/not-found.ts new file mode 100644 index 0000000..a9318b9 --- /dev/null +++ b/src/main/docs/components/not-found.ts @@ -0,0 +1,3 @@ +export const notFound = { + description: 'API não encontrada' +} diff --git a/src/main/docs/components/server-error.ts b/src/main/docs/components/server-error.ts new file mode 100644 index 0000000..cdc9209 --- /dev/null +++ b/src/main/docs/components/server-error.ts @@ -0,0 +1,10 @@ +export const serverError = { + description: 'Erro interno no servidor', + content: { + 'application/json': { + schema: { + $ref: '#/schemas/error' + } + } + } +} diff --git a/src/main/docs/components/unauthorized.ts b/src/main/docs/components/unauthorized.ts new file mode 100644 index 0000000..f88e9ff --- /dev/null +++ b/src/main/docs/components/unauthorized.ts @@ -0,0 +1,10 @@ +export const unauthorized = { + description: 'Credenciais inválidas', + content: { + 'application/json': { + schema: { + $ref: '#/schemas/error' + } + } + } +} diff --git a/src/main/docs/index.ts b/src/main/docs/index.ts index 6079f6d..717695f 100644 --- a/src/main/docs/index.ts +++ b/src/main/docs/index.ts @@ -1,6 +1,6 @@ -import { loginPath } from './paths/login-path' -import { accountSchema } from './schemas/account-schema' -import { loginParamsSchema } from './schemas/login-params-schema' +import paths from './paths' +import components from './components' +import schemas from './schemas' export default { openapi: '3.0.0', @@ -14,16 +14,17 @@ export default { } }, servers: [{ - url: '/api' + url: '/api', + description: 'Servidor Principal' }], tags: [{ - name: 'Login' + name: 'Login', + description: 'APIs relacionadas a Login' + }, { + name: 'Enquete', + description: 'APIs relacionadas a Enquete' }], - paths: { - '/login': loginPath - }, - schemas: { - account: accountSchema, - loginParams: loginParamsSchema - } + paths, + schemas, + components } diff --git a/src/main/docs/paths.ts b/src/main/docs/paths.ts new file mode 100644 index 0000000..00eae63 --- /dev/null +++ b/src/main/docs/paths.ts @@ -0,0 +1,13 @@ +import { + loginPath, + surveyPath, + signUpPath, + surveyResultPath +} from './paths/' + +export default { + '/login': loginPath, + '/signup': signUpPath, + '/surveys': surveyPath, + '/surveys/{surveyId}/results': surveyResultPath +} diff --git a/src/main/docs/paths/index.ts b/src/main/docs/paths/index.ts new file mode 100644 index 0000000..4614b3f --- /dev/null +++ b/src/main/docs/paths/index.ts @@ -0,0 +1,4 @@ +export * from './login-path' +export * from './survey-path' +export * from './signup-path' +export * from './survey-result-path' diff --git a/src/main/docs/paths/login-path.ts b/src/main/docs/paths/login-path.ts index 868bf8b..d66c8d3 100644 --- a/src/main/docs/paths/login-path.ts +++ b/src/main/docs/paths/login-path.ts @@ -2,7 +2,9 @@ export const loginPath = { post: { tags: ['Login'], summary: 'API para autenticar usuário', + description: 'Essa rota pode ser executada por **qualquer usuário**', requestBody: { + required: true, content: { 'application/json': { schema: { @@ -21,6 +23,18 @@ export const loginPath = { } } } + }, + 400: { + $ref: '#/components/badRequest' + }, + 401: { + $ref: '#/components/unauthorized' + }, + 404: { + $ref: '#/components/notFound' + }, + 500: { + $ref: '#/components/serverError' } } } diff --git a/src/main/docs/paths/signup-path.ts b/src/main/docs/paths/signup-path.ts new file mode 100644 index 0000000..d2741b5 --- /dev/null +++ b/src/main/docs/paths/signup-path.ts @@ -0,0 +1,41 @@ +export const signUpPath = { + post: { + tags: ['Login'], + summary: 'API para criar conta de um usuário', + description: 'Essa rota pode ser executada por **qualquer usuário**', + requestBody: { + required: true, + content: { + 'application/json': { + schema: { + $ref: '#/schemas/signUpParams' + } + } + } + }, + responses: { + 200: { + description: 'Sucesso', + content: { + 'application/json': { + schema: { + $ref: '#/schemas/account' + } + } + } + }, + 400: { + $ref: '#/components/badRequest' + }, + 403: { + $ref: '#/components/forbidden' + }, + 404: { + $ref: '#/components/notFound' + }, + 500: { + $ref: '#/components/serverError' + } + } + } +} diff --git a/src/main/docs/paths/survey-path.ts b/src/main/docs/paths/survey-path.ts new file mode 100644 index 0000000..4e85893 --- /dev/null +++ b/src/main/docs/paths/survey-path.ts @@ -0,0 +1,66 @@ +export const surveyPath = { + get: { + security: [{ + apiKeyAuth: [] + }], + tags: ['Enquete'], + summary: 'API para listar todas as enquetes', + description: 'Essa rota só pode ser executada por **usuários autenticados**', + responses: { + 200: { + description: 'Sucesso', + content: { + 'application/json': { + schema: { + $ref: '#/schemas/surveys' + } + } + } + }, + 204: { + description: 'Sucesso, mas sem dados para exibir' + }, + 403: { + $ref: '#/components/forbidden' + }, + 404: { + $ref: '#/components/notFound' + }, + 500: { + $ref: '#/components/serverError' + } + } + }, + post: { + security: [{ + apiKeyAuth: [] + }], + tags: ['Enquete'], + summary: 'API para criar uma enquete', + description: 'Essa rota só pode ser executada por **administradores**', + requestBody: { + required: true, + content: { + 'application/json': { + schema: { + $ref: '#/schemas/addSurveyParams' + } + } + } + }, + responses: { + 204: { + description: 'Sucesso, mas sem dados para exibir' + }, + 403: { + $ref: '#/components/forbidden' + }, + 404: { + $ref: '#/components/notFound' + }, + 500: { + $ref: '#/components/serverError' + } + } + } +} diff --git a/src/main/docs/paths/survey-result-path.ts b/src/main/docs/paths/survey-result-path.ts new file mode 100644 index 0000000..7b14c9e --- /dev/null +++ b/src/main/docs/paths/survey-result-path.ts @@ -0,0 +1,88 @@ +export const surveyResultPath = { + put: { + security: [{ + apiKeyAuth: [] + }], + tags: ['Enquete'], + summary: 'API para criar a resposta de uma enquete', + description: 'Essa rota só pode ser executada por **usuários autenticados**', + parameters: [{ + in: 'path', + name: 'surveyId', + description: 'ID da enquete a ser respondida', + required: true, + schema: { + type: 'string' + } + }], + requestBody: { + required: true, + content: { + 'application/json': { + schema: { + $ref: '#/schemas/saveSurveyParams' + } + } + } + }, + responses: { + 200: { + description: 'Sucesso', + content: { + 'application/json': { + schema: { + $ref: '#/schemas/surveyResult' + } + } + } + }, + 403: { + $ref: '#/components/forbidden' + }, + 404: { + $ref: '#/components/notFound' + }, + 500: { + $ref: '#/components/serverError' + } + } + }, + get: { + security: [{ + apiKeyAuth: [] + }], + tags: ['Enquete'], + summary: 'API para consultar o resultado de uma enquete', + description: 'Essa rota só pode ser executada por **usuários autenticados**', + parameters: [{ + in: 'path', + name: 'surveyId', + description: 'ID da enquete a ser respondida', + required: true, + schema: { + type: 'string' + } + }], + responses: { + 200: { + description: 'Sucesso', + content: { + 'application/json': { + schema: { + $ref: '#/schemas/surveyResult' + } + } + } + }, + 403: { + $ref: '#/components/forbidden' + }, + 404: { + $ref: '#/components/notFound' + }, + 500: { + $ref: '#/components/serverError' + } + } + } +} diff --git a/src/main/docs/schemas.ts b/src/main/docs/schemas.ts new file mode 100644 index 0000000..d5029e8 --- /dev/null +++ b/src/main/docs/schemas.ts @@ -0,0 +1,27 @@ +import { + accountSchema, + loginParamsSchema, + errorSchema, + surveyAnswerSchema, + surveysSchema, + surveySchema, + signUpParamsSchema, + addSurveyParamsSchema, + saveSurveyParamsSchema, + surveyResultSchema, + surveyResultAnswerSchema +} from './schemas/' + +export default { + account: accountSchema, + loginParams: loginParamsSchema, + signUpParams: signUpParamsSchema, + addSurveyParams: addSurveyParamsSchema, + error: errorSchema, + surveys: surveysSchema, + survey: surveySchema, + surveyAnswer: surveyAnswerSchema, + saveSurveyParams: saveSurveyParamsSchema, + surveyResult: surveyResultSchema, + surveyResultAnswer: surveyResultAnswerSchema +} diff --git a/src/main/docs/schemas/account-schema.ts b/src/main/docs/schemas/account-schema.ts index 5c3c26e..874ff13 100644 --- a/src/main/docs/schemas/account-schema.ts +++ b/src/main/docs/schemas/account-schema.ts @@ -3,6 +3,10 @@ export const accountSchema = { properties: { accessToken: { type: 'string' + }, + name: { + type: 'string' } - } + }, + required: ['accessToken', 'name'] } diff --git a/src/main/docs/schemas/add-survey-params-schema.ts b/src/main/docs/schemas/add-survey-params-schema.ts new file mode 100644 index 0000000..36c9326 --- /dev/null +++ b/src/main/docs/schemas/add-survey-params-schema.ts @@ -0,0 +1,15 @@ +export const addSurveyParamsSchema = { + type: 'object', + properties: { + question: { + type: 'string' + }, + answers: { + type: 'array', + items: { + $ref: '#/schemas/surveyAnswer' + } + } + }, + required: ['question', 'answers'] +} diff --git a/src/main/docs/schemas/api-key-auth-schema.ts b/src/main/docs/schemas/api-key-auth-schema.ts new file mode 100644 index 0000000..171de7e --- /dev/null +++ b/src/main/docs/schemas/api-key-auth-schema.ts @@ -0,0 +1,5 @@ +export const apiKeyAuthSchema = { + type: 'apiKey', + in: 'header', + name: 'x-access-token' +} diff --git a/src/main/docs/schemas/error-schema.ts b/src/main/docs/schemas/error-schema.ts new file mode 100644 index 0000000..17394c1 --- /dev/null +++ b/src/main/docs/schemas/error-schema.ts @@ -0,0 +1,9 @@ +export const errorSchema = { + type: 'object', + properties: { + error: { + type: 'string' + } + }, + required: ['error'] +} diff --git a/src/main/docs/schemas/index.ts b/src/main/docs/schemas/index.ts new file mode 100644 index 0000000..01f402d --- /dev/null +++ b/src/main/docs/schemas/index.ts @@ -0,0 +1,12 @@ +export * from './account-schema' +export * from './error-schema' +export * from './login-params-schema' +export * from './signup-params-schema' +export * from './add-survey-params-schema' +export * from './survey-schema' +export * from './surveys-schema' +export * from './survey-answer-schema' +export * from './api-key-auth-schema' +export * from './save-survey-params-schema' +export * from './survey-result-schema' +export * from './survey-result-answer-schema' diff --git a/src/main/docs/schemas/save-survey-params-schema.ts b/src/main/docs/schemas/save-survey-params-schema.ts new file mode 100644 index 0000000..136a834 --- /dev/null +++ b/src/main/docs/schemas/save-survey-params-schema.ts @@ -0,0 +1,9 @@ +export const saveSurveyParamsSchema = { + type: 'object', + properties: { + answer: { + type: 'string' + } + }, + required: ['answer'] +} diff --git a/src/main/docs/schemas/signup-params-schema.ts b/src/main/docs/schemas/signup-params-schema.ts new file mode 100644 index 0000000..0d88c8c --- /dev/null +++ b/src/main/docs/schemas/signup-params-schema.ts @@ -0,0 +1,18 @@ +export const signUpParamsSchema = { + type: 'object', + properties: { + name: { + type: 'string' + }, + email: { + type: 'string' + }, + password: { + type: 'string' + }, + passwordConfirmation: { + type: 'string' + } + }, + required: ['name', 'email', 'password', 'passwordConfirmation'] +} diff --git a/src/main/docs/schemas/survey-answer-schema.ts b/src/main/docs/schemas/survey-answer-schema.ts new file mode 100644 index 0000000..54cf4ba --- /dev/null +++ b/src/main/docs/schemas/survey-answer-schema.ts @@ -0,0 +1,12 @@ +export const surveyAnswerSchema = { + type: 'object', + properties: { + image: { + type: 'string' + }, + answer: { + type: 'string' + } + }, + required: ['answer'] +} diff --git a/src/main/docs/schemas/survey-result-answer-schema.ts b/src/main/docs/schemas/survey-result-answer-schema.ts new file mode 100644 index 0000000..c386603 --- /dev/null +++ b/src/main/docs/schemas/survey-result-answer-schema.ts @@ -0,0 +1,21 @@ +export const surveyResultAnswerSchema = { + type: 'object', + properties: { + image: { + type: 'string' + }, + answer: { + type: 'string' + }, + count: { + type: 'number' + }, + percent: { + type: 'number' + }, + isCurrentAccountAnswer: { + type: 'boolean' + } + }, + required: ['answer', 'count', 'percent', 'isCurrentAccountAnswer'] +} diff --git a/src/main/docs/schemas/survey-result-schema.ts b/src/main/docs/schemas/survey-result-schema.ts new file mode 100644 index 0000000..d4243d2 --- /dev/null +++ b/src/main/docs/schemas/survey-result-schema.ts @@ -0,0 +1,21 @@ +export const surveyResultSchema = { + type: 'object', + properties: { + surveyId: { + type: 'string' + }, + question: { + type: 'string' + }, + answers: { + type: 'array', + items: { + $ref: '#/schemas/surveyResultAnswer' + } + }, + date: { + type: 'string' + } + }, + required: ['surveyId', 'question', 'answers', 'date'] +} diff --git a/src/main/docs/schemas/survey-schema.ts b/src/main/docs/schemas/survey-schema.ts new file mode 100644 index 0000000..17d8ae7 --- /dev/null +++ b/src/main/docs/schemas/survey-schema.ts @@ -0,0 +1,24 @@ +export const surveySchema = { + type: 'object', + properties: { + id: { + type: 'string' + }, + question: { + type: 'string' + }, + answers: { + type: 'array', + items: { + $ref: '#/schemas/surveyAnswer' + } + }, + date: { + type: 'string' + }, + didAnswer: { + type: 'boolean' + } + }, + required: ['id', 'question', 'answers', 'date', 'didAnswer'] +} diff --git a/src/main/docs/schemas/surveys-schema.ts b/src/main/docs/schemas/surveys-schema.ts new file mode 100644 index 0000000..29e7ccf --- /dev/null +++ b/src/main/docs/schemas/surveys-schema.ts @@ -0,0 +1,6 @@ +export const surveysSchema = { + type: 'array', + items: { + $ref: '#/schemas/survey' + } +}