From 7fee03c4163cdd1724d1f9ff76398ac4431c18e6 Mon Sep 17 00:00:00 2001 From: James Tombleson Date: Sun, 28 Apr 2024 12:32:51 -0700 Subject: [PATCH] Minor adjustments and getting discord webhooks handler updated --- .gitignore | 3 - docs/docs.go | 539 ++++++++++++++++--------- docs/swagger.json | 539 ++++++++++++++++--------- docs/swagger.yaml | 385 +++++++++++------- internal/domain/dto.go | 6 +- internal/domain/entity.go | 2 - internal/domain/responses.go | 2 +- internal/handler/v1/articles.go | 10 +- internal/handler/v1/discordwebhooks.go | 283 +++++++------ internal/handler/v1/handler.go | 16 +- internal/handler/v1/root_test.go | 1 - internal/services/dtoconv.go | 18 + 12 files changed, 1160 insertions(+), 644 deletions(-) delete mode 100644 internal/handler/v1/root_test.go diff --git a/.gitignore b/.gitignore index 75d8d2c..efcc85d 100644 --- a/.gitignore +++ b/.gitignore @@ -4,9 +4,6 @@ __debug_bin server .vscode -# hide the swagger files in the repo -docs/ - # Binaries for programs and plugins *.exe *.exe~ diff --git a/docs/docs.go b/docs/docs.go index 7cc13e7..2ee6122 100644 --- a/docs/docs.go +++ b/docs/docs.go @@ -37,7 +37,19 @@ const docTemplate = `{ "200": { "description": "OK", "schema": { - "$ref": "#/definitions/routes.ArticlesListResults" + "$ref": "#/definitions/domain.ArticleResponse" + } + }, + "400": { + "description": "Bad Request", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + }, + "500": { + "description": "Internal Server Error", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" } } } @@ -55,7 +67,7 @@ const docTemplate = `{ "parameters": [ { "type": "string", - "description": "Source ID UUID", + "description": "source id", "name": "id", "in": "query", "required": true @@ -71,7 +83,19 @@ const docTemplate = `{ "200": { "description": "OK", "schema": { - "$ref": "#/definitions/routes.ArticlesListResults" + "$ref": "#/definitions/domain.ArticleResponse" + } + }, + "400": { + "description": "Bad Request", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + }, + "500": { + "description": "Internal Server Error", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" } } } @@ -89,7 +113,7 @@ const docTemplate = `{ "parameters": [ { "type": "string", - "description": "uuid", + "description": "int", "name": "ID", "in": "path", "required": true @@ -99,7 +123,19 @@ const docTemplate = `{ "200": { "description": "OK", "schema": { - "$ref": "#/definitions/routes.ArticleGetResults" + "$ref": "#/definitions/domain.ArticleResponse" + } + }, + "400": { + "description": "Bad Request", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + }, + "500": { + "description": "Internal Server Error", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" } } } @@ -117,7 +153,7 @@ const docTemplate = `{ "parameters": [ { "type": "string", - "description": "uuid", + "description": "int", "name": "ID", "in": "path", "required": true @@ -127,7 +163,19 @@ const docTemplate = `{ "200": { "description": "OK", "schema": { - "$ref": "#/definitions/routes.ArticleDetailsResult" + "$ref": "#/definitions/domain.ArticleDetailedResponse" + } + }, + "400": { + "description": "Bad Request", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + }, + "500": { + "description": "Internal Server Error", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" } } } @@ -142,8 +190,27 @@ const docTemplate = `{ "Discord", "Webhook" ], - "summary": "Returns the top 100 entries from the queue to be processed.", - "responses": {} + "summary": "Returns the top 100", + "responses": { + "200": { + "description": "OK", + "schema": { + "$ref": "#/definitions/domain.DiscordWebhookResponse" + } + }, + "400": { + "description": "Bad Request", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + }, + "500": { + "description": "Internal Server Error", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + } + } } }, "/discord/webhooks/by/serverAndChannel": { @@ -176,7 +243,19 @@ const docTemplate = `{ "200": { "description": "OK", "schema": { - "$ref": "#/definitions/routes.ListDiscordWebhooks" + "$ref": "#/definitions/domain.DiscordWebhookResponse" + } + }, + "400": { + "description": "Bad Request", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + }, + "500": { + "description": "Internal Server Error", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" } } } @@ -212,7 +291,26 @@ const docTemplate = `{ "required": true } ], - "responses": {} + "responses": { + "200": { + "description": "OK", + "schema": { + "$ref": "#/definitions/domain.DiscordWebhookResponse" + } + }, + "400": { + "description": "Bad Request", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + }, + "500": { + "description": "Internal Server Error", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + } + } } }, "/discord/webhooks/{ID}": { @@ -231,7 +329,26 @@ const docTemplate = `{ "required": true } ], - "responses": {} + "responses": { + "200": { + "description": "OK", + "schema": { + "$ref": "#/definitions/domain.DiscordWebhookResponse" + } + }, + "400": { + "description": "Bad Request", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + }, + "500": { + "description": "Internal Server Error", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + } + } } }, "/discord/webhooks/{ID}/disable": { @@ -243,14 +360,33 @@ const docTemplate = `{ "summary": "Disables a Webhook from being used.", "parameters": [ { - "type": "string", + "type": "integer", "description": "id", "name": "id", "in": "path", "required": true } ], - "responses": {} + "responses": { + "200": { + "description": "OK", + "schema": { + "$ref": "#/definitions/domain.DiscordWebhookResponse" + } + }, + "400": { + "description": "Bad Request", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + }, + "500": { + "description": "Internal Server Error", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + } + } } }, "/discord/webhooks/{ID}/enable": { @@ -262,7 +398,7 @@ const docTemplate = `{ "summary": "Enables a source to continue processing.", "parameters": [ { - "type": "string", + "type": "integer", "description": "id", "name": "id", "in": "path", @@ -284,7 +420,7 @@ const docTemplate = `{ "summary": "Returns the top 100 entries from the queue to be processed.", "parameters": [ { - "type": "string", + "type": "integer", "description": "id", "name": "id", "in": "path", @@ -295,27 +431,22 @@ const docTemplate = `{ "200": { "description": "OK", "schema": { - "$ref": "#/definitions/routes.GetDiscordWebhook" + "$ref": "#/definitions/domain.DiscordWebhookResponse" + } + }, + "400": { + "description": "Bad Request", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + }, + "500": { + "description": "Internal Server Error", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" } } } - }, - "patch": { - "tags": [ - "Discord", - "Webhook" - ], - "summary": "Updates a valid discord webhook ID based on the body given.", - "parameters": [ - { - "type": "string", - "description": "id", - "name": "id", - "in": "path", - "required": true - } - ], - "responses": {} } }, "/queue/discord/webhooks": { @@ -331,12 +462,33 @@ const docTemplate = `{ "200": { "description": "ok", "schema": { - "$ref": "#/definitions/routes.ListDiscordWebHooksQueueResults" + "$ref": "#/definitions/v1.ListDiscordWebHooksQueueResults" } } } } }, + "/settings/{key}": { + "get": { + "produces": [ + "application/json" + ], + "tags": [ + "Settings" + ], + "summary": "Returns a object based on the Key that was given.", + "parameters": [ + { + "type": "string", + "description": "Settings Key value", + "name": "key", + "in": "path", + "required": true + } + ], + "responses": {} + } + }, "/sources": { "get": { "produces": [ @@ -350,13 +502,13 @@ const docTemplate = `{ "200": { "description": "ok", "schema": { - "$ref": "#/definitions/routes.ListSources" + "$ref": "#/definitions/v1.ListSources" } }, "400": { "description": "Unable to reach SQL or Data problems", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/domain.BaseResponse" } } } @@ -384,19 +536,19 @@ const docTemplate = `{ "200": { "description": "ok", "schema": { - "$ref": "#/definitions/routes.ListSources" + "$ref": "#/definitions/v1.ListSources" } }, "400": { "description": "Unable to query SQL.", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } }, "500": { "description": "Problems with data.", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } } } @@ -431,25 +583,25 @@ const docTemplate = `{ "200": { "description": "ok", "schema": { - "$ref": "#/definitions/routes.GetSource" + "$ref": "#/definitions/v1.GetSource" } }, "204": { "description": "No record found.", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } }, "400": { "description": "Unable to query SQL.", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } }, "500": { "description": "Failed to process data from SQL.", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } } } @@ -545,25 +697,25 @@ const docTemplate = `{ "200": { "description": "ok", "schema": { - "$ref": "#/definitions/routes.GetSource" + "$ref": "#/definitions/v1.GetSource" } }, "204": { "description": "No record found.", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } }, "400": { "description": "Unable to query SQL.", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } }, "500": { "description": "Failed to process data from SQL.", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } } } @@ -634,19 +786,19 @@ const docTemplate = `{ "200": { "description": "ok", "schema": { - "$ref": "#/definitions/routes.ListSubscriptions" + "$ref": "#/definitions/v1.ListSubscriptions" } }, "400": { "description": "Unable to reach SQL.", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } }, "500": { "description": "Failed to process data from SQL.", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } } } @@ -674,7 +826,7 @@ const docTemplate = `{ "200": { "description": "ok", "schema": { - "$ref": "#/definitions/routes.ListSubscriptions" + "$ref": "#/definitions/v1.ListSubscriptions" } } } @@ -702,19 +854,19 @@ const docTemplate = `{ "200": { "description": "ok", "schema": { - "$ref": "#/definitions/routes.ListSubscriptions" + "$ref": "#/definitions/v1.ListSubscriptions" } }, "400": { "description": "Unable to reach SQL or Data problems", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } }, "500": { "description": "Data problems", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } } } @@ -733,7 +885,7 @@ const docTemplate = `{ "200": { "description": "ok", "schema": { - "$ref": "#/definitions/routes.ListSubscriptionDetails" + "$ref": "#/definitions/v1.ListSubscriptionDetails" } } } @@ -784,6 +936,146 @@ const docTemplate = `{ } }, "definitions": { + "domain.ArticleAndSourceModel": { + "type": "object", + "properties": { + "article": { + "$ref": "#/definitions/domain.ArticleDto" + }, + "source": { + "$ref": "#/definitions/domain.SourceDto" + } + } + }, + "domain.ArticleDetailedResponse": { + "type": "object", + "properties": { + "message": { + "type": "string" + }, + "payload": { + "$ref": "#/definitions/domain.ArticleAndSourceModel" + } + } + }, + "domain.ArticleDto": { + "type": "object", + "properties": { + "authorImage": { + "type": "string" + }, + "authorName": { + "type": "string" + }, + "description": { + "type": "string" + }, + "id": { + "type": "integer" + }, + "isVideo": { + "type": "boolean" + }, + "pubDate": { + "type": "string" + }, + "sourceId": { + "type": "integer" + }, + "tags": { + "type": "string" + }, + "thumbnail": { + "type": "string" + }, + "title": { + "type": "string" + }, + "url": { + "type": "string" + } + } + }, + "domain.ArticleResponse": { + "type": "object", + "properties": { + "message": { + "type": "string" + }, + "payload": { + "type": "array", + "items": { + "$ref": "#/definitions/domain.ArticleDto" + } + } + } + }, + "domain.BaseResponse": { + "type": "object", + "properties": { + "message": { + "type": "string" + } + } + }, + "domain.DiscordWebHookDto": { + "type": "object", + "properties": { + "channel": { + "type": "string" + }, + "enabled": { + "type": "boolean" + }, + "id": { + "type": "integer" + }, + "server": { + "type": "string" + }, + "url": { + "description": "Name string ` + "`" + `json:\"name\"` + "`" + `\nKey string ` + "`" + `json:\"key\"` + "`" + `", + "type": "string" + } + } + }, + "domain.DiscordWebhookResponse": { + "type": "object", + "properties": { + "message": { + "type": "string" + }, + "payload": { + "type": "array", + "items": { + "$ref": "#/definitions/domain.DiscordWebHookDto" + } + } + } + }, + "domain.SourceDto": { + "type": "object", + "properties": { + "enabled": { + "type": "boolean" + }, + "id": { + "type": "integer" + }, + "name": { + "type": "string" + }, + "source": { + "type": "string" + }, + "tags": { + "type": "string" + }, + "url": { + "type": "string" + } + } + }, "models.ArticleDetailsDto": { "type": "object", "properties": { @@ -831,53 +1123,6 @@ const docTemplate = `{ } } }, - "models.ArticleDto": { - "type": "object", - "properties": { - "authorImage": { - "type": "string" - }, - "authorName": { - "type": "string" - }, - "description": { - "type": "string" - }, - "id": { - "type": "string" - }, - "pubdate": { - "type": "string" - }, - "sourceid": { - "type": "string" - }, - "tags": { - "type": "array", - "items": { - "type": "string" - } - }, - "thumbnail": { - "type": "string" - }, - "title": { - "type": "string" - }, - "url": { - "type": "string" - }, - "video": { - "type": "string" - }, - "videoHeight": { - "type": "integer" - }, - "videoWidth": { - "type": "integer" - } - } - }, "models.DiscordQueueDetailsDto": { "type": "object", "properties": { @@ -975,7 +1220,7 @@ const docTemplate = `{ } } }, - "routes.ApiError": { + "v1.ApiError": { "type": "object", "properties": { "message": { @@ -986,66 +1231,7 @@ const docTemplate = `{ } } }, - "routes.ArticleDetailsResult": { - "type": "object", - "properties": { - "message": { - "type": "string" - }, - "payload": { - "$ref": "#/definitions/models.ArticleDetailsDto" - }, - "status": { - "type": "integer" - } - } - }, - "routes.ArticleGetResults": { - "type": "object", - "properties": { - "message": { - "type": "string" - }, - "payload": { - "$ref": "#/definitions/models.ArticleDto" - }, - "status": { - "type": "integer" - } - } - }, - "routes.ArticlesListResults": { - "type": "object", - "properties": { - "message": { - "type": "string" - }, - "payload": { - "type": "array", - "items": { - "$ref": "#/definitions/models.ArticleDto" - } - }, - "status": { - "type": "integer" - } - } - }, - "routes.GetDiscordWebhook": { - "type": "object", - "properties": { - "message": { - "type": "string" - }, - "payload": { - "$ref": "#/definitions/models.DiscordWebHooksDto" - }, - "status": { - "type": "integer" - } - } - }, - "routes.GetSource": { + "v1.GetSource": { "type": "object", "properties": { "message": { @@ -1059,7 +1245,7 @@ const docTemplate = `{ } } }, - "routes.ListDiscordWebHooksQueueResults": { + "v1.ListDiscordWebHooksQueueResults": { "type": "object", "properties": { "message": { @@ -1076,24 +1262,7 @@ const docTemplate = `{ } } }, - "routes.ListDiscordWebhooks": { - "type": "object", - "properties": { - "message": { - "type": "string" - }, - "payload": { - "type": "array", - "items": { - "$ref": "#/definitions/models.DiscordWebHooksDto" - } - }, - "status": { - "type": "integer" - } - } - }, - "routes.ListSources": { + "v1.ListSources": { "type": "object", "properties": { "message": { @@ -1110,7 +1279,7 @@ const docTemplate = `{ } } }, - "routes.ListSubscriptionDetails": { + "v1.ListSubscriptionDetails": { "type": "object", "properties": { "message": { @@ -1127,7 +1296,7 @@ const docTemplate = `{ } } }, - "routes.ListSubscriptions": { + "v1.ListSubscriptions": { "type": "object", "properties": { "message": { diff --git a/docs/swagger.json b/docs/swagger.json index b6d4557..141111c 100644 --- a/docs/swagger.json +++ b/docs/swagger.json @@ -28,7 +28,19 @@ "200": { "description": "OK", "schema": { - "$ref": "#/definitions/routes.ArticlesListResults" + "$ref": "#/definitions/domain.ArticleResponse" + } + }, + "400": { + "description": "Bad Request", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + }, + "500": { + "description": "Internal Server Error", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" } } } @@ -46,7 +58,7 @@ "parameters": [ { "type": "string", - "description": "Source ID UUID", + "description": "source id", "name": "id", "in": "query", "required": true @@ -62,7 +74,19 @@ "200": { "description": "OK", "schema": { - "$ref": "#/definitions/routes.ArticlesListResults" + "$ref": "#/definitions/domain.ArticleResponse" + } + }, + "400": { + "description": "Bad Request", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + }, + "500": { + "description": "Internal Server Error", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" } } } @@ -80,7 +104,7 @@ "parameters": [ { "type": "string", - "description": "uuid", + "description": "int", "name": "ID", "in": "path", "required": true @@ -90,7 +114,19 @@ "200": { "description": "OK", "schema": { - "$ref": "#/definitions/routes.ArticleGetResults" + "$ref": "#/definitions/domain.ArticleResponse" + } + }, + "400": { + "description": "Bad Request", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + }, + "500": { + "description": "Internal Server Error", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" } } } @@ -108,7 +144,7 @@ "parameters": [ { "type": "string", - "description": "uuid", + "description": "int", "name": "ID", "in": "path", "required": true @@ -118,7 +154,19 @@ "200": { "description": "OK", "schema": { - "$ref": "#/definitions/routes.ArticleDetailsResult" + "$ref": "#/definitions/domain.ArticleDetailedResponse" + } + }, + "400": { + "description": "Bad Request", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + }, + "500": { + "description": "Internal Server Error", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" } } } @@ -133,8 +181,27 @@ "Discord", "Webhook" ], - "summary": "Returns the top 100 entries from the queue to be processed.", - "responses": {} + "summary": "Returns the top 100", + "responses": { + "200": { + "description": "OK", + "schema": { + "$ref": "#/definitions/domain.DiscordWebhookResponse" + } + }, + "400": { + "description": "Bad Request", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + }, + "500": { + "description": "Internal Server Error", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + } + } } }, "/discord/webhooks/by/serverAndChannel": { @@ -167,7 +234,19 @@ "200": { "description": "OK", "schema": { - "$ref": "#/definitions/routes.ListDiscordWebhooks" + "$ref": "#/definitions/domain.DiscordWebhookResponse" + } + }, + "400": { + "description": "Bad Request", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + }, + "500": { + "description": "Internal Server Error", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" } } } @@ -203,7 +282,26 @@ "required": true } ], - "responses": {} + "responses": { + "200": { + "description": "OK", + "schema": { + "$ref": "#/definitions/domain.DiscordWebhookResponse" + } + }, + "400": { + "description": "Bad Request", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + }, + "500": { + "description": "Internal Server Error", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + } + } } }, "/discord/webhooks/{ID}": { @@ -222,7 +320,26 @@ "required": true } ], - "responses": {} + "responses": { + "200": { + "description": "OK", + "schema": { + "$ref": "#/definitions/domain.DiscordWebhookResponse" + } + }, + "400": { + "description": "Bad Request", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + }, + "500": { + "description": "Internal Server Error", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + } + } } }, "/discord/webhooks/{ID}/disable": { @@ -234,14 +351,33 @@ "summary": "Disables a Webhook from being used.", "parameters": [ { - "type": "string", + "type": "integer", "description": "id", "name": "id", "in": "path", "required": true } ], - "responses": {} + "responses": { + "200": { + "description": "OK", + "schema": { + "$ref": "#/definitions/domain.DiscordWebhookResponse" + } + }, + "400": { + "description": "Bad Request", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + }, + "500": { + "description": "Internal Server Error", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + } + } } }, "/discord/webhooks/{ID}/enable": { @@ -253,7 +389,7 @@ "summary": "Enables a source to continue processing.", "parameters": [ { - "type": "string", + "type": "integer", "description": "id", "name": "id", "in": "path", @@ -275,7 +411,7 @@ "summary": "Returns the top 100 entries from the queue to be processed.", "parameters": [ { - "type": "string", + "type": "integer", "description": "id", "name": "id", "in": "path", @@ -286,27 +422,22 @@ "200": { "description": "OK", "schema": { - "$ref": "#/definitions/routes.GetDiscordWebhook" + "$ref": "#/definitions/domain.DiscordWebhookResponse" + } + }, + "400": { + "description": "Bad Request", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" + } + }, + "500": { + "description": "Internal Server Error", + "schema": { + "$ref": "#/definitions/domain.BaseResponse" } } } - }, - "patch": { - "tags": [ - "Discord", - "Webhook" - ], - "summary": "Updates a valid discord webhook ID based on the body given.", - "parameters": [ - { - "type": "string", - "description": "id", - "name": "id", - "in": "path", - "required": true - } - ], - "responses": {} } }, "/queue/discord/webhooks": { @@ -322,12 +453,33 @@ "200": { "description": "ok", "schema": { - "$ref": "#/definitions/routes.ListDiscordWebHooksQueueResults" + "$ref": "#/definitions/v1.ListDiscordWebHooksQueueResults" } } } } }, + "/settings/{key}": { + "get": { + "produces": [ + "application/json" + ], + "tags": [ + "Settings" + ], + "summary": "Returns a object based on the Key that was given.", + "parameters": [ + { + "type": "string", + "description": "Settings Key value", + "name": "key", + "in": "path", + "required": true + } + ], + "responses": {} + } + }, "/sources": { "get": { "produces": [ @@ -341,13 +493,13 @@ "200": { "description": "ok", "schema": { - "$ref": "#/definitions/routes.ListSources" + "$ref": "#/definitions/v1.ListSources" } }, "400": { "description": "Unable to reach SQL or Data problems", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/domain.BaseResponse" } } } @@ -375,19 +527,19 @@ "200": { "description": "ok", "schema": { - "$ref": "#/definitions/routes.ListSources" + "$ref": "#/definitions/v1.ListSources" } }, "400": { "description": "Unable to query SQL.", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } }, "500": { "description": "Problems with data.", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } } } @@ -422,25 +574,25 @@ "200": { "description": "ok", "schema": { - "$ref": "#/definitions/routes.GetSource" + "$ref": "#/definitions/v1.GetSource" } }, "204": { "description": "No record found.", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } }, "400": { "description": "Unable to query SQL.", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } }, "500": { "description": "Failed to process data from SQL.", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } } } @@ -536,25 +688,25 @@ "200": { "description": "ok", "schema": { - "$ref": "#/definitions/routes.GetSource" + "$ref": "#/definitions/v1.GetSource" } }, "204": { "description": "No record found.", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } }, "400": { "description": "Unable to query SQL.", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } }, "500": { "description": "Failed to process data from SQL.", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } } } @@ -625,19 +777,19 @@ "200": { "description": "ok", "schema": { - "$ref": "#/definitions/routes.ListSubscriptions" + "$ref": "#/definitions/v1.ListSubscriptions" } }, "400": { "description": "Unable to reach SQL.", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } }, "500": { "description": "Failed to process data from SQL.", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } } } @@ -665,7 +817,7 @@ "200": { "description": "ok", "schema": { - "$ref": "#/definitions/routes.ListSubscriptions" + "$ref": "#/definitions/v1.ListSubscriptions" } } } @@ -693,19 +845,19 @@ "200": { "description": "ok", "schema": { - "$ref": "#/definitions/routes.ListSubscriptions" + "$ref": "#/definitions/v1.ListSubscriptions" } }, "400": { "description": "Unable to reach SQL or Data problems", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } }, "500": { "description": "Data problems", "schema": { - "$ref": "#/definitions/routes.ApiError" + "$ref": "#/definitions/v1.ApiError" } } } @@ -724,7 +876,7 @@ "200": { "description": "ok", "schema": { - "$ref": "#/definitions/routes.ListSubscriptionDetails" + "$ref": "#/definitions/v1.ListSubscriptionDetails" } } } @@ -775,6 +927,146 @@ } }, "definitions": { + "domain.ArticleAndSourceModel": { + "type": "object", + "properties": { + "article": { + "$ref": "#/definitions/domain.ArticleDto" + }, + "source": { + "$ref": "#/definitions/domain.SourceDto" + } + } + }, + "domain.ArticleDetailedResponse": { + "type": "object", + "properties": { + "message": { + "type": "string" + }, + "payload": { + "$ref": "#/definitions/domain.ArticleAndSourceModel" + } + } + }, + "domain.ArticleDto": { + "type": "object", + "properties": { + "authorImage": { + "type": "string" + }, + "authorName": { + "type": "string" + }, + "description": { + "type": "string" + }, + "id": { + "type": "integer" + }, + "isVideo": { + "type": "boolean" + }, + "pubDate": { + "type": "string" + }, + "sourceId": { + "type": "integer" + }, + "tags": { + "type": "string" + }, + "thumbnail": { + "type": "string" + }, + "title": { + "type": "string" + }, + "url": { + "type": "string" + } + } + }, + "domain.ArticleResponse": { + "type": "object", + "properties": { + "message": { + "type": "string" + }, + "payload": { + "type": "array", + "items": { + "$ref": "#/definitions/domain.ArticleDto" + } + } + } + }, + "domain.BaseResponse": { + "type": "object", + "properties": { + "message": { + "type": "string" + } + } + }, + "domain.DiscordWebHookDto": { + "type": "object", + "properties": { + "channel": { + "type": "string" + }, + "enabled": { + "type": "boolean" + }, + "id": { + "type": "integer" + }, + "server": { + "type": "string" + }, + "url": { + "description": "Name string `json:\"name\"`\nKey string `json:\"key\"`", + "type": "string" + } + } + }, + "domain.DiscordWebhookResponse": { + "type": "object", + "properties": { + "message": { + "type": "string" + }, + "payload": { + "type": "array", + "items": { + "$ref": "#/definitions/domain.DiscordWebHookDto" + } + } + } + }, + "domain.SourceDto": { + "type": "object", + "properties": { + "enabled": { + "type": "boolean" + }, + "id": { + "type": "integer" + }, + "name": { + "type": "string" + }, + "source": { + "type": "string" + }, + "tags": { + "type": "string" + }, + "url": { + "type": "string" + } + } + }, "models.ArticleDetailsDto": { "type": "object", "properties": { @@ -822,53 +1114,6 @@ } } }, - "models.ArticleDto": { - "type": "object", - "properties": { - "authorImage": { - "type": "string" - }, - "authorName": { - "type": "string" - }, - "description": { - "type": "string" - }, - "id": { - "type": "string" - }, - "pubdate": { - "type": "string" - }, - "sourceid": { - "type": "string" - }, - "tags": { - "type": "array", - "items": { - "type": "string" - } - }, - "thumbnail": { - "type": "string" - }, - "title": { - "type": "string" - }, - "url": { - "type": "string" - }, - "video": { - "type": "string" - }, - "videoHeight": { - "type": "integer" - }, - "videoWidth": { - "type": "integer" - } - } - }, "models.DiscordQueueDetailsDto": { "type": "object", "properties": { @@ -966,7 +1211,7 @@ } } }, - "routes.ApiError": { + "v1.ApiError": { "type": "object", "properties": { "message": { @@ -977,66 +1222,7 @@ } } }, - "routes.ArticleDetailsResult": { - "type": "object", - "properties": { - "message": { - "type": "string" - }, - "payload": { - "$ref": "#/definitions/models.ArticleDetailsDto" - }, - "status": { - "type": "integer" - } - } - }, - "routes.ArticleGetResults": { - "type": "object", - "properties": { - "message": { - "type": "string" - }, - "payload": { - "$ref": "#/definitions/models.ArticleDto" - }, - "status": { - "type": "integer" - } - } - }, - "routes.ArticlesListResults": { - "type": "object", - "properties": { - "message": { - "type": "string" - }, - "payload": { - "type": "array", - "items": { - "$ref": "#/definitions/models.ArticleDto" - } - }, - "status": { - "type": "integer" - } - } - }, - "routes.GetDiscordWebhook": { - "type": "object", - "properties": { - "message": { - "type": "string" - }, - "payload": { - "$ref": "#/definitions/models.DiscordWebHooksDto" - }, - "status": { - "type": "integer" - } - } - }, - "routes.GetSource": { + "v1.GetSource": { "type": "object", "properties": { "message": { @@ -1050,7 +1236,7 @@ } } }, - "routes.ListDiscordWebHooksQueueResults": { + "v1.ListDiscordWebHooksQueueResults": { "type": "object", "properties": { "message": { @@ -1067,24 +1253,7 @@ } } }, - "routes.ListDiscordWebhooks": { - "type": "object", - "properties": { - "message": { - "type": "string" - }, - "payload": { - "type": "array", - "items": { - "$ref": "#/definitions/models.DiscordWebHooksDto" - } - }, - "status": { - "type": "integer" - } - } - }, - "routes.ListSources": { + "v1.ListSources": { "type": "object", "properties": { "message": { @@ -1101,7 +1270,7 @@ } } }, - "routes.ListSubscriptionDetails": { + "v1.ListSubscriptionDetails": { "type": "object", "properties": { "message": { @@ -1118,7 +1287,7 @@ } } }, - "routes.ListSubscriptions": { + "v1.ListSubscriptions": { "type": "object", "properties": { "message": { diff --git a/docs/swagger.yaml b/docs/swagger.yaml index cb9d714..c0a9f74 100644 --- a/docs/swagger.yaml +++ b/docs/swagger.yaml @@ -1,5 +1,98 @@ basePath: /api definitions: + domain.ArticleAndSourceModel: + properties: + article: + $ref: '#/definitions/domain.ArticleDto' + source: + $ref: '#/definitions/domain.SourceDto' + type: object + domain.ArticleDetailedResponse: + properties: + message: + type: string + payload: + $ref: '#/definitions/domain.ArticleAndSourceModel' + type: object + domain.ArticleDto: + properties: + authorImage: + type: string + authorName: + type: string + description: + type: string + id: + type: integer + isVideo: + type: boolean + pubDate: + type: string + sourceId: + type: integer + tags: + type: string + thumbnail: + type: string + title: + type: string + url: + type: string + type: object + domain.ArticleResponse: + properties: + message: + type: string + payload: + items: + $ref: '#/definitions/domain.ArticleDto' + type: array + type: object + domain.BaseResponse: + properties: + message: + type: string + type: object + domain.DiscordWebHookDto: + properties: + channel: + type: string + enabled: + type: boolean + id: + type: integer + server: + type: string + url: + description: |- + Name string `json:"name"` + Key string `json:"key"` + type: string + type: object + domain.DiscordWebhookResponse: + properties: + message: + type: string + payload: + items: + $ref: '#/definitions/domain.DiscordWebHookDto' + type: array + type: object + domain.SourceDto: + properties: + enabled: + type: boolean + id: + type: integer + name: + type: string + source: + type: string + tags: + type: string + url: + type: string + type: object models.ArticleDetailsDto: properties: authorImage: @@ -31,37 +124,6 @@ definitions: videoWidth: type: integer type: object - models.ArticleDto: - properties: - authorImage: - type: string - authorName: - type: string - description: - type: string - id: - type: string - pubdate: - type: string - sourceid: - type: string - tags: - items: - type: string - type: array - thumbnail: - type: string - title: - type: string - url: - type: string - video: - type: string - videoHeight: - type: integer - videoWidth: - type: integer - type: object models.DiscordQueueDetailsDto: properties: article: @@ -125,52 +187,14 @@ definitions: sourceid: type: string type: object - routes.ApiError: + v1.ApiError: properties: message: type: string status: type: integer type: object - routes.ArticleDetailsResult: - properties: - message: - type: string - payload: - $ref: '#/definitions/models.ArticleDetailsDto' - status: - type: integer - type: object - routes.ArticleGetResults: - properties: - message: - type: string - payload: - $ref: '#/definitions/models.ArticleDto' - status: - type: integer - type: object - routes.ArticlesListResults: - properties: - message: - type: string - payload: - items: - $ref: '#/definitions/models.ArticleDto' - type: array - status: - type: integer - type: object - routes.GetDiscordWebhook: - properties: - message: - type: string - payload: - $ref: '#/definitions/models.DiscordWebHooksDto' - status: - type: integer - type: object - routes.GetSource: + v1.GetSource: properties: message: type: string @@ -179,7 +203,7 @@ definitions: status: type: integer type: object - routes.ListDiscordWebHooksQueueResults: + v1.ListDiscordWebHooksQueueResults: properties: message: type: string @@ -190,18 +214,7 @@ definitions: status: type: integer type: object - routes.ListDiscordWebhooks: - properties: - message: - type: string - payload: - items: - $ref: '#/definitions/models.DiscordWebHooksDto' - type: array - status: - type: integer - type: object - routes.ListSources: + v1.ListSources: properties: message: type: string @@ -212,7 +225,7 @@ definitions: status: type: integer type: object - routes.ListSubscriptionDetails: + v1.ListSubscriptionDetails: properties: message: type: string @@ -223,7 +236,7 @@ definitions: status: type: integer type: object - routes.ListSubscriptions: + v1.ListSubscriptions: properties: message: type: string @@ -252,14 +265,22 @@ paths: "200": description: OK schema: - $ref: '#/definitions/routes.ArticlesListResults' + $ref: '#/definitions/domain.ArticleResponse' + "400": + description: Bad Request + schema: + $ref: '#/definitions/domain.BaseResponse' + "500": + description: Internal Server Error + schema: + $ref: '#/definitions/domain.BaseResponse' summary: Lists the top 25 records ordering from newest to oldest. tags: - Articles /articles/{ID}: get: parameters: - - description: uuid + - description: int in: path name: ID required: true @@ -270,14 +291,22 @@ paths: "200": description: OK schema: - $ref: '#/definitions/routes.ArticleGetResults' + $ref: '#/definitions/domain.ArticleResponse' + "400": + description: Bad Request + schema: + $ref: '#/definitions/domain.BaseResponse' + "500": + description: Internal Server Error + schema: + $ref: '#/definitions/domain.BaseResponse' summary: Returns an article based on defined ID. tags: - Articles /articles/{ID}/details: get: parameters: - - description: uuid + - description: int in: path name: ID required: true @@ -288,14 +317,22 @@ paths: "200": description: OK schema: - $ref: '#/definitions/routes.ArticleDetailsResult' + $ref: '#/definitions/domain.ArticleDetailedResponse' + "400": + description: Bad Request + schema: + $ref: '#/definitions/domain.BaseResponse' + "500": + description: Internal Server Error + schema: + $ref: '#/definitions/domain.BaseResponse' summary: Returns an article and source based on defined ID. tags: - Articles /articles/by/sourceid: get: parameters: - - description: Source ID UUID + - description: source id in: query name: id required: true @@ -310,7 +347,15 @@ paths: "200": description: OK schema: - $ref: '#/definitions/routes.ArticlesListResults' + $ref: '#/definitions/domain.ArticleResponse' + "400": + description: Bad Request + schema: + $ref: '#/definitions/domain.BaseResponse' + "500": + description: Internal Server Error + schema: + $ref: '#/definitions/domain.BaseResponse' summary: Finds the articles based on the SourceID provided. Returns the top 25. tags: @@ -319,8 +364,20 @@ paths: get: produces: - application/json - responses: {} - summary: Returns the top 100 entries from the queue to be processed. + responses: + "200": + description: OK + schema: + $ref: '#/definitions/domain.DiscordWebhookResponse' + "400": + description: Bad Request + schema: + $ref: '#/definitions/domain.BaseResponse' + "500": + description: Internal Server Error + schema: + $ref: '#/definitions/domain.BaseResponse' + summary: Returns the top 100 tags: - Discord - Webhook @@ -332,7 +389,19 @@ paths: name: id required: true type: string - responses: {} + responses: + "200": + description: OK + schema: + $ref: '#/definitions/domain.DiscordWebhookResponse' + "400": + description: Bad Request + schema: + $ref: '#/definitions/domain.BaseResponse' + "500": + description: Internal Server Error + schema: + $ref: '#/definitions/domain.BaseResponse' summary: Deletes a record by ID. tags: - Discord @@ -344,8 +413,20 @@ paths: in: path name: id required: true - type: string - responses: {} + type: integer + responses: + "200": + description: OK + schema: + $ref: '#/definitions/domain.DiscordWebhookResponse' + "400": + description: Bad Request + schema: + $ref: '#/definitions/domain.BaseResponse' + "500": + description: Internal Server Error + schema: + $ref: '#/definitions/domain.BaseResponse' summary: Disables a Webhook from being used. tags: - Discord @@ -357,7 +438,7 @@ paths: in: path name: id required: true - type: string + type: integer responses: {} summary: Enables a source to continue processing. tags: @@ -370,30 +451,26 @@ paths: in: path name: id required: true - type: string + type: integer produces: - application/json responses: "200": description: OK schema: - $ref: '#/definitions/routes.GetDiscordWebhook' + $ref: '#/definitions/domain.DiscordWebhookResponse' + "400": + description: Bad Request + schema: + $ref: '#/definitions/domain.BaseResponse' + "500": + description: Internal Server Error + schema: + $ref: '#/definitions/domain.BaseResponse' summary: Returns the top 100 entries from the queue to be processed. tags: - Discord - Webhook - patch: - parameters: - - description: id - in: path - name: id - required: true - type: string - responses: {} - summary: Updates a valid discord webhook ID based on the body given. - tags: - - Discord - - Webhook /discord/webhooks/by/serverAndChannel: get: parameters: @@ -413,7 +490,15 @@ paths: "200": description: OK schema: - $ref: '#/definitions/routes.ListDiscordWebhooks' + $ref: '#/definitions/domain.DiscordWebhookResponse' + "400": + description: Bad Request + schema: + $ref: '#/definitions/domain.BaseResponse' + "500": + description: Internal Server Error + schema: + $ref: '#/definitions/domain.BaseResponse' summary: Returns all the known web hooks based on the Server and Channel given. tags: - Discord @@ -436,7 +521,19 @@ paths: name: channel required: true type: string - responses: {} + responses: + "200": + description: OK + schema: + $ref: '#/definitions/domain.DiscordWebhookResponse' + "400": + description: Bad Request + schema: + $ref: '#/definitions/domain.BaseResponse' + "500": + description: Internal Server Error + schema: + $ref: '#/definitions/domain.BaseResponse' summary: Creates a new record for a discord web hook to post data to. tags: - Discord @@ -449,10 +546,24 @@ paths: "200": description: ok schema: - $ref: '#/definitions/routes.ListDiscordWebHooksQueueResults' + $ref: '#/definitions/v1.ListDiscordWebHooksQueueResults' summary: Returns the top 100 entries from the queue to be processed. tags: - Queue + /settings/{key}: + get: + parameters: + - description: Settings Key value + in: path + name: key + required: true + type: string + produces: + - application/json + responses: {} + summary: Returns a object based on the Key that was given. + tags: + - Settings /sources: get: produces: @@ -461,11 +572,11 @@ paths: "200": description: ok schema: - $ref: '#/definitions/routes.ListSources' + $ref: '#/definitions/v1.ListSources' "400": description: Unable to reach SQL or Data problems schema: - $ref: '#/definitions/routes.ApiError' + $ref: '#/definitions/domain.BaseResponse' summary: Lists the top 50 records tags: - Source @@ -483,19 +594,19 @@ paths: "200": description: ok schema: - $ref: '#/definitions/routes.GetSource' + $ref: '#/definitions/v1.GetSource' "204": description: No record found. schema: - $ref: '#/definitions/routes.ApiError' + $ref: '#/definitions/v1.ApiError' "400": description: Unable to query SQL. schema: - $ref: '#/definitions/routes.ApiError' + $ref: '#/definitions/v1.ApiError' "500": description: Failed to process data from SQL. schema: - $ref: '#/definitions/routes.ApiError' + $ref: '#/definitions/v1.ApiError' summary: Returns a single entity by ID tags: - Source @@ -548,15 +659,15 @@ paths: "200": description: ok schema: - $ref: '#/definitions/routes.ListSources' + $ref: '#/definitions/v1.ListSources' "400": description: Unable to query SQL. schema: - $ref: '#/definitions/routes.ApiError' + $ref: '#/definitions/v1.ApiError' "500": description: Problems with data. schema: - $ref: '#/definitions/routes.ApiError' + $ref: '#/definitions/v1.ApiError' summary: 'Lists the top 50 records based on the name given. Example: reddit' tags: - Source @@ -579,19 +690,19 @@ paths: "200": description: ok schema: - $ref: '#/definitions/routes.GetSource' + $ref: '#/definitions/v1.GetSource' "204": description: No record found. schema: - $ref: '#/definitions/routes.ApiError' + $ref: '#/definitions/v1.ApiError' "400": description: Unable to query SQL. schema: - $ref: '#/definitions/routes.ApiError' + $ref: '#/definitions/v1.ApiError' "500": description: Failed to process data from SQL. schema: - $ref: '#/definitions/routes.ApiError' + $ref: '#/definitions/v1.ApiError' summary: Returns a single entity by ID tags: - Source @@ -649,15 +760,15 @@ paths: "200": description: ok schema: - $ref: '#/definitions/routes.ListSubscriptions' + $ref: '#/definitions/v1.ListSubscriptions' "400": description: Unable to reach SQL. schema: - $ref: '#/definitions/routes.ApiError' + $ref: '#/definitions/v1.ApiError' "500": description: Failed to process data from SQL. schema: - $ref: '#/definitions/routes.ApiError' + $ref: '#/definitions/v1.ApiError' summary: Returns the top 100 entries from the queue to be processed. tags: - Subscription @@ -675,7 +786,7 @@ paths: "200": description: ok schema: - $ref: '#/definitions/routes.ListSubscriptions' + $ref: '#/definitions/v1.ListSubscriptions' summary: Returns the top 100 entries from the queue to be processed. tags: - Subscription @@ -693,15 +804,15 @@ paths: "200": description: ok schema: - $ref: '#/definitions/routes.ListSubscriptions' + $ref: '#/definitions/v1.ListSubscriptions' "400": description: Unable to reach SQL or Data problems schema: - $ref: '#/definitions/routes.ApiError' + $ref: '#/definitions/v1.ApiError' "500": description: Data problems schema: - $ref: '#/definitions/routes.ApiError' + $ref: '#/definitions/v1.ApiError' summary: Returns the top 100 entries from the queue to be processed. tags: - Subscription @@ -713,7 +824,7 @@ paths: "200": description: ok schema: - $ref: '#/definitions/routes.ListSubscriptionDetails' + $ref: '#/definitions/v1.ListSubscriptionDetails' summary: Returns the top 50 entries with full deatils on the source and output. tags: - Subscription diff --git a/internal/domain/dto.go b/internal/domain/dto.go index 0a59cd6..751724f 100644 --- a/internal/domain/dto.go +++ b/internal/domain/dto.go @@ -23,9 +23,9 @@ type DiscordQueueDto struct { } type DiscordWebHookDto struct { - ID uint `json:"id"` - Name string `json:"name"` - Key string `json:"key"` + ID int64 `json:"id"` + //Name string `json:"name"` + //Key string `json:"key"` Url string `json:"url"` Server string `json:"server"` Channel string `json:"channel"` diff --git a/internal/domain/entity.go b/internal/domain/entity.go index c892476..bc56a9b 100644 --- a/internal/domain/entity.go +++ b/internal/domain/entity.go @@ -35,8 +35,6 @@ type DiscordWebHookEntity struct { CreatedAt time.Time UpdatedAt time.Time DeletedAt time.Time - //Name string - //Key string Url string Server string Channel string diff --git a/internal/domain/responses.go b/internal/domain/responses.go index 5175940..7c8693a 100644 --- a/internal/domain/responses.go +++ b/internal/domain/responses.go @@ -15,7 +15,7 @@ type ArticleAndSourceModel struct { Source SourceDto `json:"source"` } -type ArticleDetailResponse struct { +type ArticleDetailedResponse struct { BaseResponse Payload ArticleAndSourceModel `json:"payload"` } diff --git a/internal/handler/v1/articles.go b/internal/handler/v1/articles.go index 8bae404..02ca2ef 100644 --- a/internal/handler/v1/articles.go +++ b/internal/handler/v1/articles.go @@ -45,7 +45,7 @@ func (s *Handler) listArticles(c echo.Context) error { // @Produce application/json // @Tags Articles // @Router /articles/{ID} [get] -// @Success 200 {object} ArticleGetResults "OK" +// @Success 200 {object} domain.ArticleResponse "OK" // @Failure 400 {object} domain.BaseResponse // @Failure 500 {object} domain.BaseResponse func (s *Handler) getArticle(c echo.Context) error { @@ -79,11 +79,11 @@ func (s *Handler) getArticle(c echo.Context) error { // @Produce application/json // @Tags Articles // @Router /articles/{ID}/details [get] -// @Success 200 {object} ArticleDetailsResult "OK" +// @Success 200 {object} domain.ArticleDetailedResponse "OK" // @Failure 400 {object} domain.BaseResponse // @Failure 500 {object} domain.BaseResponse func (s *Handler) getArticleDetails(c echo.Context) error { - p := domain.ArticleDetailResponse{ + p := domain.ArticleDetailedResponse{ BaseResponse: domain.BaseResponse{ Message: ResponseMessageSuccess, }, @@ -115,12 +115,12 @@ func (s *Handler) getArticleDetails(c echo.Context) error { // ListArticlesBySourceID // @Summary Finds the articles based on the SourceID provided. Returns the top 25. -// @Param id query string true +// @Param id query string true "source id" // @Param page query int false "Page to query" // @Produce application/json // @Tags Articles // @Router /articles/by/sourceid [get] -// @Success 200 {object} ArticlesListResults "OK" +// @Success 200 {object} domain.ArticleResponse "OK" // @Failure 400 {object} domain.BaseResponse // @Failure 500 {object} domain.BaseResponse func (s *Handler) ListArticlesBySourceId(c echo.Context) error { diff --git a/internal/handler/v1/discordwebhooks.go b/internal/handler/v1/discordwebhooks.go index 93ed20a..3e2cb11 100644 --- a/internal/handler/v1/discordwebhooks.go +++ b/internal/handler/v1/discordwebhooks.go @@ -1,84 +1,66 @@ package v1 import ( - "fmt" "net/http" + "strconv" "strings" - "git.jamestombleson.com/jtom38/newsbot-api/internal/database" "git.jamestombleson.com/jtom38/newsbot-api/internal/domain" - "git.jamestombleson.com/jtom38/newsbot-api/internal/domain/models" - "github.com/google/uuid" + "git.jamestombleson.com/jtom38/newsbot-api/internal/services" "github.com/labstack/echo/v4" ) -type ListDiscordWebhooks struct { - ApiStatusModel - Payload []models.DiscordWebHooksDto `json:"payload"` -} - -type GetDiscordWebhook struct { - ApiStatusModel - Payload models.DiscordWebHooksDto `json:"payload"` -} - // ListDiscordWebhooks -// @Summary Returns the top 100 entries from the queue to be processed. +// @Summary Returns the top 100 // @Produce application/json // @Tags Discord, Webhook // @Router /discord/webhooks [get] +// @Success 200 {object} domain.DiscordWebhookResponse +// @Failure 400 {object} domain.BaseResponse +// @Failure 500 {object} domain.BaseResponse func (s *Handler) ListDiscordWebHooks(c echo.Context) error { - p := ListDiscordWebhooks{ - ApiStatusModel: ApiStatusModel{ - Message: "OK", - StatusCode: http.StatusOK, + p := domain.DiscordWebhookResponse{ + BaseResponse: domain.BaseResponse{ + Message: ResponseMessageSuccess, }, } - res, err := s.dto.ListDiscordWebHooks(c.Request().Context(), 50) + res, err := s.repo.DiscordWebHooks.ListByServerName(c.Request().Context(), "") if err != nil { return c.JSON(http.StatusInternalServerError, err) } - p.Payload = res + p.Payload = services.DiscordWebhooksToDto(res) return c.JSON(http.StatusOK, p) } // GetDiscordWebHook // @Summary Returns the top 100 entries from the queue to be processed. // @Produce application/json -// @Param id path string true "id" +// @Param id path int true "id" // @Tags Discord, Webhook // @Router /discord/webhooks/{id} [get] -// @Success 200 {object} GetDiscordWebhook "OK" +// @Success 200 {object} domain.DiscordWebhookResponse "OK" +// @Failure 400 {object} domain.BaseResponse +// @Failure 500 {object} domain.BaseResponse func (s *Handler) GetDiscordWebHooksById(c echo.Context) error { - p := GetDiscordWebhook{ - ApiStatusModel: ApiStatusModel{ - Message: "OK", - StatusCode: http.StatusOK, + p := domain.DiscordWebhookResponse{ + BaseResponse: domain.BaseResponse{ + Message: ResponseMessageSuccess, }, } - _id := c.Param("ID") - if _id == "" { - return c.JSON(http.StatusBadRequest, domain.BaseResponse{ - Message: ErrIdValueMissing, - }) + id, err := strconv.Atoi(c.Param("ID")) + if err != nil { + s.WriteError(c, err, http.StatusBadRequest) } - uuid, err := uuid.Parse(_id) + res, err := s.repo.DiscordWebHooks.GetById(c.Request().Context(), int64(id)) if err != nil { - return c.JSON(http.StatusBadRequest, domain.BaseResponse{ - Message: ErrUnableToParseId, - }) + s.WriteError(c, err, http.StatusInternalServerError) } - - res, err := s.dto.GetDiscordWebhook(c.Request().Context(), uuid) - if err != nil { - return c.JSON(http.StatusBadRequest, domain.BaseResponse{ - Message: ErrNoRecordFound, - }) - } - p.Payload = res + var dtos []domain.DiscordWebHookDto + dtos = append(dtos, services.DiscordWebhookToDto(res)) + p.Payload = dtos return c.JSON(http.StatusOK, p) } @@ -89,37 +71,32 @@ func (s *Handler) GetDiscordWebHooksById(c echo.Context) error { // @Param channel query string true "memes" // @Tags Discord, Webhook // @Router /discord/webhooks/by/serverAndChannel [get] -// @Success 200 {object} ListDiscordWebhooks "OK" +// @Success 200 {object} domain.DiscordWebhookResponse "OK" +// @Failure 400 {object} domain.BaseResponse +// @Failure 500 {object} domain.BaseResponse func (s *Handler) GetDiscordWebHooksByServerAndChannel(c echo.Context) error { - p := ListDiscordWebhooks{ - ApiStatusModel: ApiStatusModel{ - Message: "OK", - StatusCode: http.StatusOK, + p := domain.DiscordWebhookResponse{ + BaseResponse: domain.BaseResponse{ + Message: ResponseMessageSuccess, }, } _server := c.QueryParam("server") if _server == "" { - return c.JSON(http.StatusBadRequest, domain.BaseResponse{ - Message: ErrIdValueMissing, - }) + s.WriteMessage(c, "server was not defined", http.StatusBadRequest) } _channel := c.QueryParam("channel") if _channel == "" { - return c.JSON(http.StatusBadRequest, domain.BaseResponse{ - Message: fmt.Sprintf("%s channel", ErrParameterMissing), - }) + s.WriteMessage(c, "channel was not defined", http.StatusBadRequest) } - res, err := s.dto.GetDiscordWebHookByServerAndChannel(c.Request().Context(), _server, _channel) + res, err := s.repo.DiscordWebHooks.ListByServerAndChannel(c.Request().Context(), _server, _channel) if err != nil { - return c.JSON(http.StatusInternalServerError, domain.BaseResponse{ - Message: err.Error(), - }) + s.WriteError(c, err, http.StatusInternalServerError) } - p.Payload = res + p.Payload = services.DiscordWebhooksToDto(res) return c.JSON(http.StatusOK, p) } @@ -130,6 +107,9 @@ func (s *Handler) GetDiscordWebHooksByServerAndChannel(c echo.Context) error { // @Param channel query string true "Channel name" // @Tags Discord, Webhook // @Router /discord/webhooks/new [post] +// @Success 200 {object} domain.DiscordWebhookResponse "OK" +// @Failure 400 {object} domain.BaseResponse +// @Failure 500 {object} domain.BaseResponse func (s *Handler) NewDiscordWebHook(c echo.Context) error { _url := c.QueryParam("url") _server := c.QueryParam("server") @@ -155,26 +135,42 @@ func (s *Handler) NewDiscordWebHook(c echo.Context) error { Message: "channel is missing", }) } - params := database.CreateDiscordWebHookParams{ - ID: uuid.New(), - Url: _url, - Server: _server, - Channel: _channel, - Enabled: true, - } - s.Db.CreateDiscordWebHook(c.Request().Context(), params) - return c.JSON(http.StatusOK, params) + rows, err := s.repo.DiscordWebHooks.Create(c.Request().Context(), _url, _server, _channel, true) + if err != nil { + s.WriteError(c, err, http.StatusInternalServerError) + } + + if rows != 1 { + s.WriteMessage(c, "data was not written to database", http.StatusInternalServerError) + } + + item, err := s.repo.DiscordWebHooks.GetByUrl(c.Request().Context(), _url) + if err != nil { + s.WriteError(c, err, http.StatusInternalServerError) + } + + var dtos []domain.DiscordWebHookDto + dtos = append(dtos, services.DiscordWebhookToDto(item)) + + return c.JSON(http.StatusOK, domain.DiscordWebhookResponse{ + BaseResponse: domain.BaseResponse{ + Message: ResponseMessageSuccess, + }, + Payload: dtos, + }) } // DisableDiscordWebHooks // @Summary Disables a Webhook from being used. -// @Param id path string true "id" +// @Param id path int true "id" // @Tags Discord, Webhook // @Router /discord/webhooks/{ID}/disable [post] +// @Success 200 {object} domain.DiscordWebhookResponse "OK" +// @Failure 400 {object} domain.BaseResponse +// @Failure 500 {object} domain.BaseResponse func (s *Handler) disableDiscordWebHook(c echo.Context) error { - id := c.Param("ID") - uuid, err := uuid.Parse(id) + id, err := strconv.Atoi(c.Param("ID")) if err != nil { return c.JSON(http.StatusBadRequest, domain.BaseResponse{ Message: err.Error(), @@ -182,45 +178,76 @@ func (s *Handler) disableDiscordWebHook(c echo.Context) error { } // Check to make sure we can find the record - _, err = s.Db.GetDiscordWebHooksByID(c.Request().Context(), uuid) + _, err = s.repo.DiscordWebHooks.GetById(c.Request().Context(), int64(id)) if err != nil { - return c.JSON(http.StatusInternalServerError, err.Error()) + s.WriteError(c, err, http.StatusInternalServerError) } - err = s.Db.DisableDiscordWebHook(c.Request().Context(), uuid) + // flip the it + updated, err := s.repo.DiscordWebHooks.Disable(c.Request().Context(), int64(id)) if err != nil { - return c.JSON(http.StatusInternalServerError, domain.BaseResponse{ - Message: err.Error(), - }) + s.WriteError(c, err, http.StatusInternalServerError) } - return nil + + // make sure we got a row updated + if updated != 1 { + s.WriteMessage(c, "unexpected number of updates found", http.StatusInternalServerError) + } + + item, err := s.repo.DiscordWebHooks.GetById(c.Request().Context(), int64(id)) + if err != nil { + s.WriteError(c, err, http.StatusInternalServerError) + } + + var dtos []domain.DiscordWebHookDto + dtos = append(dtos, services.DiscordWebhookToDto(item)) + return c.JSON(http.StatusOK, domain.DiscordWebhookResponse{ + BaseResponse: domain.BaseResponse{ + Message: ResponseMessageSuccess, + }, + Payload: dtos, + }) } // EnableDiscordWebHook // @Summary Enables a source to continue processing. -// @Param id path string true "id" +// @Param id path int true "id" // @Tags Discord, Webhook // @Router /discord/webhooks/{ID}/enable [post] func (s *Handler) enableDiscordWebHook(c echo.Context) error { - id := c.Param("ID") - uuid, err := uuid.Parse(id) + id, err := strconv.Atoi(c.Param("ID")) if err != nil { - return c.JSON(http.StatusBadRequest, domain.BaseResponse{ - Message: err.Error(), - }) + s.WriteError(c, err, http.StatusBadRequest) } // Check to make sure we can find the record - _, err = s.Db.GetDiscordWebHooksByID(c.Request().Context(), uuid) + _, err = s.repo.DiscordWebHooks.GetById(c.Request().Context(), int64(id)) if err != nil { - return c.JSON(http.StatusInternalServerError, err.Error()) + s.WriteError(c, err, http.StatusBadRequest) } - err = s.Db.EnableDiscordWebHook(c.Request().Context(), uuid) + updated, err := s.repo.DiscordWebHooks.Enable(c.Request().Context(), int64(id)) if err != nil { - return c.JSON(http.StatusInternalServerError, err.Error()) + s.WriteError(c, err, http.StatusInternalServerError) } - return nil + + if updated != 1 { + s.WriteMessage(c, "unexpected number of updates found", http.StatusInternalServerError) + } + + item, err := s.repo.DiscordWebHooks.GetById(c.Request().Context(), int64(id)) + if err != nil { + s.WriteError(c, err, http.StatusInternalServerError) + } + + var dtos []domain.DiscordWebHookDto + dtos = append(dtos, services.DiscordWebhookToDto(item)) + return c.JSON(http.StatusOK, domain.DiscordWebhookResponse{ + BaseResponse: domain.BaseResponse{ + Message: ResponseMessageSuccess, + }, + Payload: dtos, + }) } // DeleteDiscordWebHook @@ -228,28 +255,44 @@ func (s *Handler) enableDiscordWebHook(c echo.Context) error { // @Param id path string true "id" // @Tags Discord, Webhook // @Router /discord/webhooks/{ID} [delete] +// @Success 200 {object} domain.DiscordWebhookResponse "OK" +// @Failure 400 {object} domain.BaseResponse +// @Failure 500 {object} domain.BaseResponse func (s *Handler) deleteDiscordWebHook(c echo.Context) error { - //var item model.Sources = model.Sources{} - - id := c.Param("ID") - uuid, err := uuid.Parse(id) + id, err := strconv.Atoi(c.Param("ID")) if err != nil { return c.JSON(http.StatusBadRequest, err.Error()) } // Check to make sure we can find the record - _, err = s.Db.GetDiscordQueueByID(c.Request().Context(), uuid) + _, err = s.repo.DiscordWebHooks.GetById(c.Request().Context(), int64(id)) if err != nil { return c.JSON(http.StatusInternalServerError, err.Error()) } - // Delete the record - err = s.Db.DeleteDiscordWebHooks(c.Request().Context(), uuid) + // Soft delete the record + updated, err := s.repo.DiscordWebHooks.SoftDelete(c.Request().Context(), int64(id)) if err != nil { return c.JSON(http.StatusInternalServerError, err.Error()) } - return nil + if updated != 1 { + s.WriteMessage(c, "unexpected number of updates found", http.StatusInternalServerError) + } + + item, err := s.repo.DiscordWebHooks.GetById(c.Request().Context(), int64(id)) + if err != nil { + s.WriteError(c, err, http.StatusInternalServerError) + } + + var dtos []domain.DiscordWebHookDto + dtos = append(dtos, services.DiscordWebhookToDto(item)) + return c.JSON(http.StatusOK, domain.DiscordWebhookResponse{ + BaseResponse: domain.BaseResponse{ + Message: ResponseMessageSuccess, + }, + Payload: dtos, + }) } // UpdateDiscordWebHook @@ -257,19 +300,31 @@ func (s *Handler) deleteDiscordWebHook(c echo.Context) error { // @Param id path string true "id" // @Tags Discord, Webhook // @Router /discord/webhooks/{id} [patch] -func (s *Handler) UpdateDiscordWebHook(c echo.Context) error { - id := c.Param("ID") - - uuid, err := uuid.Parse(id) - if err != nil { - return c.JSON(http.StatusInternalServerError, err.Error()) - } - - // Check to make sure we can find the record - _, err = s.Db.GetDiscordQueueByID(c.Request().Context(), uuid) - if err != nil { - return c.JSON(http.StatusInternalServerError, err.Error()) - } - - return nil -} +// @Success 200 {object} domain.DiscordWebhookResponse "OK" +// @Failure 400 {object} domain.BaseResponse +// @Failure 500 {object} domain.BaseResponse +//func (s *Handler) UpdateDiscordWebHook(c echo.Context) error { +// id, err := strconv.Atoi(c.Param("ID")) +// if err != nil { +// return c.JSON(http.StatusInternalServerError, err.Error()) +// } +// +// // Check to make sure we can find the record +// _, err = s.repo.DiscordWebHooks.GetById(c.Request().Context(), int64(id)) +// if err != nil { +// return c.JSON(http.StatusInternalServerError, err.Error()) +// } +// +// // Soft delete the record +// updated, err := s.repo.DiscordWebHooks(c.Request().Context(), int64(id)) +// if err != nil { +// return c.JSON(http.StatusInternalServerError, err.Error()) +// } +// +// _, err = s.Db.GetDiscordQueueByID(c.Request().Context(), uuid) +// if err != nil { +// return c.JSON(http.StatusInternalServerError, err.Error()) +// } +// +// return nil +//} diff --git a/internal/handler/v1/handler.go b/internal/handler/v1/handler.go index 655f72a..41bddcb 100644 --- a/internal/handler/v1/handler.go +++ b/internal/handler/v1/handler.go @@ -60,14 +60,14 @@ func NewServer(ctx context.Context, db *database.Queries, configs services.Confi articles.GET("/:id/details", s.getArticleDetails) articles.GET("/by/source/:id", s.ListArticlesBySourceId) - dwh := v1.Group("/discord/webhooks") - dwh.GET("/", s.ListDiscordWebHooks) - dwh.POST("/new", s.NewDiscordWebHook) - dwh.GET("/by/serverAndChannel", s.GetDiscordWebHooksByServerAndChannel) - dwh.GET("/:ID", s.GetDiscordWebHooksById) - dwh.DELETE("/:ID", s.deleteDiscordWebHook) - dwh.POST("/:ID/disable", s.disableDiscordWebHook) - dwh.POST("/:ID/enable", s.enableDiscordWebHook) + //dwh := v1.Group("/discord/webhooks") + //dwh.GET("/", s.ListDiscordWebHooks) + //dwh.POST("/new", s.NewDiscordWebHook) + //dwh.GET("/by/serverAndChannel", s.GetDiscordWebHooksByServerAndChannel) + //dwh.GET("/:ID", s.GetDiscordWebHooksById) + //dwh.DELETE("/:ID", s.deleteDiscordWebHook) + //dwh.POST("/:ID/disable", s.disableDiscordWebHook) + //dwh.POST("/:ID/enable", s.enableDiscordWebHook) //queue := v1.Group("/queue") //queue.GET("/discord/webhooks", s.ListDiscordWebhookQueue) // TODO this needs to be reworked diff --git a/internal/handler/v1/root_test.go b/internal/handler/v1/root_test.go deleted file mode 100644 index ba42722..0000000 --- a/internal/handler/v1/root_test.go +++ /dev/null @@ -1 +0,0 @@ -package v1_test diff --git a/internal/services/dtoconv.go b/internal/services/dtoconv.go index 1cddec3..6505dc5 100644 --- a/internal/services/dtoconv.go +++ b/internal/services/dtoconv.go @@ -26,6 +26,24 @@ func ArticleToDto(item domain.ArticleEntity) domain.ArticleDto { } } +func DiscordWebhooksToDto(items []domain.DiscordWebHookEntity) []domain.DiscordWebHookDto{ + var dtos []domain.DiscordWebHookDto + for _, item := range items { + dtos = append(dtos, DiscordWebhookToDto(item)) + } + return dtos +} + +func DiscordWebhookToDto(item domain.DiscordWebHookEntity) domain.DiscordWebHookDto { + return domain.DiscordWebHookDto{ + ID: item.ID, + Server: item.Server, + Channel: item.Channel, + Url: item.Url, + Enabled: item.Enabled, + } +} + func SourcesToDto(items []domain.SourceEntity) []domain.SourceDto { var dtos []domain.SourceDto for _, item := range items {