From 615db4760633369d0fac376979ba05402f86323b Mon Sep 17 00:00:00 2001 From: Meninjar Mulyono Date: Tue, 19 Aug 2025 10:48:40 +0700 Subject: [PATCH] Perbaikan Tools, Perbaikan --- README.md | 14 +++- docs/docs.go | 61 +++++++++++++- docs/swagger.json | 56 +++++++++++++ docs/swagger.yaml | 38 +++++++++ example.env | 14 ++-- internal/handlers/bpjs/reference/diagnosa.go | 85 ++++++++++++++++++++ internal/models/bpjs/reference/diagnosa.go | 47 +++++++++++ internal/routes/v1/routes.go | 5 ++ tools/generate-bpjs-handler.go | 12 +-- 9 files changed, 314 insertions(+), 18 deletions(-) create mode 100644 internal/handlers/bpjs/reference/diagnosa.go create mode 100644 internal/models/bpjs/reference/diagnosa.go diff --git a/README.md b/README.md index 04855e0b..1980a725 100644 --- a/README.md +++ b/README.md @@ -1,5 +1,15 @@ # 🚀 API Service Guide +## 📖 Introduction +This API service is designed to provide a robust backend for managing products, orders, and user authentication. It integrates with BPJS for health insurance services and offers a comprehensive set of features for developers. + +## 🌟 Features +- User authentication with JWT +- CRUD operations for products and orders +- Integration with BPJS services +- Swagger documentation for easy API testing +- Docker support for easy deployment + ## 📋 Quick Start (5 Menit) ### 1. Setup Environment @@ -73,6 +83,8 @@ tools/generate.bat product get post put delete go run tools/generate-handler.go product get post go run tools/generate-handler.go order get post put delete stats + +go run tools/generate-bpjs-handler.go reference/peserta get ``` ### Method Tersedia @@ -209,5 +221,3 @@ const products = await axios.get('/api/v1/products'); --- **Total waktu setup: 5 menit** | **Generate CRUD: 30 detik** | **Testing: Langsung di Swagger** - - diff --git a/docs/docs.go b/docs/docs.go index a2629128..e2f54f4a 100644 --- a/docs/docs.go +++ b/docs/docs.go @@ -1,4 +1,5 @@ -// Package docs Code generated by swaggo/swag. DO NOT EDIT +// Code generated by swaggo/swag. DO NOT EDIT. + package docs import "github.com/swaggo/swag" @@ -275,6 +276,50 @@ const docTemplate = `{ } } }, + "/api/v1/bpjs/reference/referensi/diagnosa": { + "get": { + "description": "Get all diagnosa reference data", + "consumes": [ + "application/json" + ], + "produces": [ + "application/json" + ], + "tags": [ + "bpjs/reference" + ], + "summary": "Get all diagnosa reference data", + "responses": { + "200": { + "description": "Success response", + "schema": { + "$ref": "#/definitions/models.DiagnosaResponse" + } + }, + "400": { + "description": "Bad request", + "schema": { + "type": "object", + "additionalProperties": true + } + }, + "404": { + "description": "Data not found", + "schema": { + "type": "object", + "additionalProperties": true + } + }, + "500": { + "description": "Internal server error", + "schema": { + "type": "object", + "additionalProperties": true + } + } + } + } + }, "/api/v1/retribusi/{id}": { "get": { "description": "Returns a single retribusi by ID", @@ -1118,6 +1163,18 @@ const docTemplate = `{ } } }, + "models.DiagnosaResponse": { + "type": "object", + "properties": { + "data": { + "type": "object", + "additionalProperties": true + }, + "message": { + "type": "string" + } + } + }, "sql.NullString": { "type": "object", "properties": { @@ -1155,8 +1212,6 @@ var SwaggerInfo = &swag.Spec{ Description: "A comprehensive Go API service with Swagger documentation", InfoInstanceName: "swagger", SwaggerTemplate: docTemplate, - LeftDelim: "{{", - RightDelim: "}}", } func init() { diff --git a/docs/swagger.json b/docs/swagger.json index 87770997..4f277a52 100644 --- a/docs/swagger.json +++ b/docs/swagger.json @@ -273,6 +273,50 @@ } } }, + "/api/v1/bpjs/reference/referensi/diagnosa": { + "get": { + "description": "Get all diagnosa reference data", + "consumes": [ + "application/json" + ], + "produces": [ + "application/json" + ], + "tags": [ + "bpjs/reference" + ], + "summary": "Get all diagnosa reference data", + "responses": { + "200": { + "description": "Success response", + "schema": { + "$ref": "#/definitions/models.DiagnosaResponse" + } + }, + "400": { + "description": "Bad request", + "schema": { + "type": "object", + "additionalProperties": true + } + }, + "404": { + "description": "Data not found", + "schema": { + "type": "object", + "additionalProperties": true + } + }, + "500": { + "description": "Internal server error", + "schema": { + "type": "object", + "additionalProperties": true + } + } + } + } + }, "/api/v1/retribusi/{id}": { "get": { "description": "Returns a single retribusi by ID", @@ -1116,6 +1160,18 @@ } } }, + "models.DiagnosaResponse": { + "type": "object", + "properties": { + "data": { + "type": "object", + "additionalProperties": true + }, + "message": { + "type": "string" + } + } + }, "sql.NullString": { "type": "object", "properties": { diff --git a/docs/swagger.yaml b/docs/swagger.yaml index 75742f33..8bc9b8df 100644 --- a/docs/swagger.yaml +++ b/docs/swagger.yaml @@ -292,6 +292,14 @@ definitions: message: type: string type: object + models.DiagnosaResponse: + properties: + data: + additionalProperties: true + type: object + message: + type: string + type: object sql.NullString: properties: string: @@ -487,6 +495,36 @@ paths: summary: Get participant data by NIK tags: - bpjs + /api/v1/bpjs/reference/referensi/diagnosa: + get: + consumes: + - application/json + description: Get all diagnosa reference data + produces: + - application/json + responses: + "200": + description: Success response + schema: + $ref: '#/definitions/models.DiagnosaResponse' + "400": + description: Bad request + schema: + additionalProperties: true + type: object + "404": + description: Data not found + schema: + additionalProperties: true + type: object + "500": + description: Internal server error + schema: + additionalProperties: true + type: object + summary: Get all diagnosa reference data + tags: + - bpjs/reference /api/v1/retribusi/{id}: delete: consumes: diff --git a/example.env b/example.env index ed71be4d..30881e71 100644 --- a/example.env +++ b/example.env @@ -41,13 +41,13 @@ MONGODB_MONGOHL7_LOCAL=local MONGODB_MONGOHL7_SSLMODE=disable # MYSQL Antrian Database -# MYSQL_ANTRIAN_CONNECTION=mysql -# MYSQL_ANTRIAN_HOST=10.10.123.163 -# MYSQL_ANTRIAN_USERNAME=www-data -# MYSQL_ANTRIAN_PASSWORD=www-data -# MYSQL_ANTRIAN_DATABASE=antrian_rssa -# MYSQL_ANTRIAN_PORT=5432 -# MYSQL_ANTRIAN_SSLMODE=disable +MYSQL_ANTRIAN_CONNECTION=mysql +MYSQL_ANTRIAN_HOST=10.10.123.163 +MYSQL_ANTRIAN_USERNAME=www-data +MYSQL_ANTRIAN_PASSWORD=www-data +MYSQL_ANTRIAN_DATABASE=antrian_rssa +MYSQL_ANTRIAN_PORT=3306 +MYSQL_ANTRIAN_SSLMODE=disable MYSQL_MEDICAL_CONNECTION=mysql diff --git a/internal/handlers/bpjs/reference/diagnosa.go b/internal/handlers/bpjs/reference/diagnosa.go new file mode 100644 index 00000000..a23ab4e0 --- /dev/null +++ b/internal/handlers/bpjs/reference/diagnosa.go @@ -0,0 +1,85 @@ +package handlers + +import ( + "context" + "fmt" + "net/http" + "time" + "api-service/internal/config" + services "api-service/internal/services/bpjs" + "github.com/gin-gonic/gin" +) + +// DiagnosaHandler handles BPJS diagnosa operations +type DiagnosaHandler struct { + bpjsService services.VClaimService +} + +// NewDiagnosaHandler creates a new DiagnosaHandler instance +func NewDiagnosaHandler(cfg config.BpjsConfig) *DiagnosaHandler { + return &DiagnosaHandler{ + bpjsService: services.NewService(cfg), + } +} + +// GetAll godoc +// @Summary Get all diagnosa reference data +// @Description Get all diagnosa reference data +// @Tags bpjs/reference +// @Accept json +// @Produce json +// @Success 200 {object} models.DiagnosaResponse "Success response" +// @Failure 400 {object} map[string]interface{} "Bad request" +// @Failure 404 {object} map[string]interface{} "Data not found" +// @Failure 500 {object} map[string]interface{} "Internal server error" +// @Router /api/v1/bpjs/reference/referensi/diagnosa [get] +func (h *DiagnosaHandler) GetAll(c *gin.Context) { + + // Create context with timeout + ctx, cancel := context.WithTimeout(c.Request.Context(), 30*time.Second) + defer cancel() + + // Build endpoint URL + endpoint := "/referensi/diagnosa" + + // Call BPJS service + var result map[string]interface{} + if err := h.bpjsService.Get(ctx, endpoint, &result); err != nil { + c.JSON(http.StatusInternalServerError, gin.H{ + "error": "Failed to fetch diagnosa data", + "message": err.Error(), + }) + return + } + + // Return successful response + c.JSON(http.StatusOK, gin.H{ + "message": "Data diagnosa berhasil diambil", + "data": result, + }) +} + + +// Helper methods for error handling and response formatting + +// handleBPJSError handles BPJS service errors and returns appropriate HTTP responses +func (h *DiagnosaHandler) handleBPJSError(c *gin.Context, err error, operation string) { + c.JSON(http.StatusInternalServerError, gin.H{ + "error": fmt.Sprintf("Failed to %s", operation), + "message": err.Error(), + }) +} + +// validateDateFormat validates if the date string is in yyyy-MM-dd format +func (h *DiagnosaHandler) validateDateFormat(dateStr string) error { + _, err := time.Parse("2006-01-02", dateStr) + return err +} + +// buildSuccessResponse builds a standardized success response +func (h *DiagnosaHandler) buildSuccessResponse(message string, data interface{}) gin.H { + return gin.H{ + "message": message, + "data": data, + } +} diff --git a/internal/models/bpjs/reference/diagnosa.go b/internal/models/bpjs/reference/diagnosa.go new file mode 100644 index 00000000..98cf4572 --- /dev/null +++ b/internal/models/bpjs/reference/diagnosa.go @@ -0,0 +1,47 @@ +package models + +// DiagnosaResponse represents the response structure for BPJS diagnosa data +type DiagnosaResponse struct { + Message string `json:"message"` + Data map[string]interface{} `json:"data"` +} + +// DiagnosaRawResponse represents the raw response structure from BPJS API +type DiagnosaRawResponse struct { + MetaData struct { + Code string `json:"code"` + Message string `json:"message"` + } `json:"metaData"` + Response interface{} `json:"response"` +} + + +// DiagnosaData represents the diagnosa reference data structure +type DiagnosaData struct { + KdDiag string `json:"kdDiag"` + NmDiag string `json:"nmDiag"` +} + +// DiagnosaListResponse represents the response structure for diagnosa list +type DiagnosaListResponse struct { + Diagnosa []DiagnosaData `json:"diagnosa"` +} + +// ErrorResponse represents error response structure +type ErrorResponse struct { + Error string `json:"error"` + Message string `json:"message"` + Code int `json:"code,omitempty"` +} + +// BPJSMetaData represents BPJS API metadata structure +type BPJSMetaData struct { + Code string `json:"code"` + Message string `json:"message"` +} + +// DiagnosaFilter represents filter parameters for diagnosa queries +type DiagnosaFilter struct { + NIK *string `form:"nik" json:"nik,omitempty"` + TglSEP *string `form:"tglSEP" json:"tglSEP,omitempty"` +} diff --git a/internal/routes/v1/routes.go b/internal/routes/v1/routes.go index cc4f5ad3..81f063a9 100644 --- a/internal/routes/v1/routes.go +++ b/internal/routes/v1/routes.go @@ -1,6 +1,7 @@ package v1 import ( + bpjsDiagnosaHandlers "api-service/internal/handlers/bpjs/reference" bpjsPesertaHandlers "api-service/internal/handlers/bpjs/reference" retribusiHandlers "api-service/internal/handlers/retribusi" @@ -61,6 +62,10 @@ func RegisterRoutes(cfg *config.Config) *gin.Engine { bpjsPesertaHandler := bpjsPesertaHandlers.NewPesertaHandler(cfg.Bpjs) v1.GET("/bpjs/Peserta/nik/:nik/tglSEP/:tglSEP", bpjsPesertaHandler.GetPesertaByNIK) + // BPJS Diagnosa endpoints + bpjsDiagnosaHandler := bpjsDiagnosaHandlers.NewDiagnosaHandler(cfg.Bpjs) + v1.GET("/bpjs/reference/referensi/diagnosa", bpjsDiagnosaHandler.GetAll) + protected := v1.Group("/") protected.Use(middleware.JWTAuthMiddleware(authService)) { diff --git a/tools/generate-bpjs-handler.go b/tools/generate-bpjs-handler.go index 1134de0b..8ff8d92b 100644 --- a/tools/generate-bpjs-handler.go +++ b/tools/generate-bpjs-handler.go @@ -203,12 +203,12 @@ func generateDefaultEndpoints(data BpjsHandlerData) []BpjsEndpoint { func generateBpjsHandlerFile(data BpjsHandlerData, handlerDir string) { // Determine import path based on category - var modelsImportPath string - if data.Category != "" { - modelsImportPath = `models "` + data.ModuleName + `/internal/models/bpjs/` + data.Category + `"` - } else { - modelsImportPath = `models "` + data.ModuleName + `/internal/models/bpjs/` + data.NameLower + `"` - } + // var modelsImportPath string + // if data.Category != "" { + // modelsImportPath = `models "` + data.ModuleName + `/internal/models/bpjs/` + data.Category + `"` + // } else { + // modelsImportPath = `models "` + data.ModuleName + `/internal/models/bpjs/` + data.NameLower + `"` + // } handlerContent := `package handlers