1269 lines
36 KiB
Markdown
1269 lines
36 KiB
Markdown
# Fitness Core Backend Reference
|
|
|
|
## Purpose
|
|
|
|
This file is a code-first reference for the current backend implementation in `Fitness_Core_BE`.
|
|
It covers:
|
|
|
|
- project structure
|
|
- runtime configuration
|
|
- authentication
|
|
- response envelopes
|
|
- REST endpoints
|
|
- legacy RPC-style endpoints
|
|
- request and response DTOs
|
|
- helpers
|
|
- services, repositories, and models
|
|
- existing support files such as Postman collections and Markdown files
|
|
|
|
This document reflects the codebase as currently implemented on July 6, 2026.
|
|
|
|
## Project Overview
|
|
|
|
The backend is an ASP.NET Core Web API project with:
|
|
|
|
- Entity Framework Core + MySQL
|
|
- controller-based HTTP APIs
|
|
- a mixed API style:
|
|
- newer resource-oriented REST endpoints in `Controllers/ClientController.cs`, `Controllers/AdminController.cs`, and `Controllers/AgentController.cs`
|
|
- older function-dispatch endpoints in `Controllers/APIController.cs`
|
|
- SignalR chat hub at `/hubs/chat`
|
|
- helper-based JWT validation for normal user flows
|
|
- custom API-key authentication for on-prem agent flows
|
|
- AI orchestration services for meal/workout planning
|
|
|
|
## Top-Level Structure
|
|
|
|
- `Controllers/`
|
|
- HTTP API entrypoints
|
|
- `Services/`
|
|
- business logic
|
|
- `Services/FunctionHandler/`
|
|
- legacy function router layer for `ApiRequest`
|
|
- `Repos/`
|
|
- repository implementations
|
|
- `Interfaces/`
|
|
- repository and service contracts
|
|
- `Models/`
|
|
- EF entities, enums, IO contracts
|
|
- `DTOs/`
|
|
- request/response DTOs
|
|
- `Helpers/`
|
|
- auth, payload, response, crypto, parsing, and utility helpers
|
|
- `AI/`
|
|
- AI client and meal/workout plan orchestration
|
|
- `Infra/UoW/`
|
|
- unit-of-work abstraction
|
|
- `Hubs/`
|
|
- SignalR hub(s)
|
|
- `Migrations/`
|
|
- EF Core migrations
|
|
- `postman/` and `.postman/`
|
|
- API collections
|
|
- `README.md`
|
|
- current content is only a short placeholder
|
|
|
|
## Runtime and DI Setup
|
|
|
|
`Program.cs` configures:
|
|
|
|
- controllers with `ReferenceHandler.IgnoreCycles`
|
|
- Swagger in development
|
|
- MySQL `AppDBContext`
|
|
- permissive CORS policy named `AllowAll`
|
|
- SignalR
|
|
- dependency injection for repositories, services, helpers, function handlers, agent auth, and AI services
|
|
- `app.MapControllers()`
|
|
- `app.MapHub<ChatHub>("/hubs/chat")`
|
|
|
|
## Authentication and Authorization
|
|
|
|
### 1. Standard user/client/admin flows
|
|
|
|
The custom action filter `JwtMiddleware.CustomMiddlewareAttribute` is used on protected endpoints.
|
|
|
|
It accepts the token from:
|
|
|
|
- `MobileAuthToken: Bearer <token>` request header, or
|
|
- `access_token` cookie
|
|
|
|
It validates against:
|
|
|
|
- `Jwt:PublicKey`
|
|
- `Jwt:Issuer`
|
|
- `Jwt:Audience`
|
|
|
|
It populates:
|
|
|
|
- `HttpContext.Items["UserId"]`
|
|
- `HttpContext.Items["Email"]`
|
|
- `HttpContext.Items["UserType"]`
|
|
- `HttpContext.Items["RoleId"]`
|
|
|
|
### 2. Request-access token for onboarding
|
|
|
|
`RequestAccessTokenHelper` creates a short-lived JWT used between OTP verification and onboarding request creation.
|
|
|
|
Claims:
|
|
|
|
- `MobileNumber`
|
|
- `Purpose = RequestAccess`
|
|
|
|
Configuration:
|
|
|
|
- `RequestAccessToken:SigningKey`
|
|
- `RequestAccessToken:ExpiresInMinutes`
|
|
|
|
### 3. On-prem agent authentication
|
|
|
|
The agent flow uses `X-Api-Key`.
|
|
|
|
Implementation:
|
|
|
|
- `Auth/AgentApiKeyAuthenticationHandler.cs`
|
|
- policy name: `AgentApiKey`
|
|
|
|
Resolved server-side claims:
|
|
|
|
- `AgentId`
|
|
- `FKClientId`
|
|
|
|
Important behavior:
|
|
|
|
- the backend never trusts `clientId` or `agentId` from the request body for authenticated agent endpoints
|
|
- the API key is stored hashed with SHA-256 via `ApiKeyHelper`
|
|
|
|
## Standard Response Envelopes
|
|
|
|
### Generic API envelope
|
|
|
|
Most endpoints return:
|
|
|
|
```json
|
|
{
|
|
"statusCode": 200,
|
|
"message": "success",
|
|
"data": {}
|
|
}
|
|
```
|
|
|
|
Code types:
|
|
|
|
- `Models/IOs/ApiResponse.cs`
|
|
- `Helpers/ApiResponseHelper.cs`
|
|
|
|
### Legacy RPC request envelope
|
|
|
|
Used by the old `POST /api/...` dispatcher endpoints:
|
|
|
|
```json
|
|
{
|
|
"functionName": "SomeFunction",
|
|
"payload": {},
|
|
"reference": "optional caller reference"
|
|
}
|
|
```
|
|
|
|
Type:
|
|
|
|
- `Models/IOs/ApiRequest.cs`
|
|
|
|
## HTTP Surface
|
|
|
|
## A. `APIController` legacy dispatcher (`/api`)
|
|
|
|
This controller mixes one health endpoint, one document download endpoint, and many RPC-style POST endpoints.
|
|
|
|
### A1. Direct endpoints
|
|
|
|
| Method | Path | Auth | Request | Response |
|
|
|---|---|---|---|---|
|
|
| `GET` | `/api/status` | `CustomMiddleware` | none | `200 OK` with `{ status, timestamp }` |
|
|
| `GET` | `/api/docService/{docId}` | anonymous | route param `docId` | file download or error string |
|
|
|
|
### A2. RPC dispatch endpoints
|
|
|
|
All of these accept `ApiRequest` unless otherwise noted.
|
|
|
|
| Method | Path | Auth |
|
|
|---|---|---|
|
|
| `POST` | `/api/ticket` | `CustomMiddleware` |
|
|
| `POST` | `/api/activitylog` | none |
|
|
| `POST` | `/api/client` | `CustomMiddleware` |
|
|
| `POST` | `/api/auth` | none |
|
|
| `POST` | `/api/VerifyOTP` | `CustomMiddleware` |
|
|
| `POST` | `/api/refreshToken` | anonymous |
|
|
| `POST` | `/api/logout` | anonymous |
|
|
| `POST` | `/api/staff` | `CustomMiddleware` |
|
|
| `POST` | `/api/clientinvoice` | `CustomMiddleware` |
|
|
| `POST` | `/api/customer` | `CustomMiddleware` |
|
|
| `POST` | `/api/customerinvoice` | `CustomMiddleware` |
|
|
| `POST` | `/api/customerplan` | `CustomMiddleware` |
|
|
| `POST` | `/api/customersubscription` | `CustomMiddleware` |
|
|
| `POST` | `/api/meal` | `CustomMiddleware` |
|
|
| `POST` | `/api/workout` | `CustomMiddleware` |
|
|
| `POST` | `/api/document` | `CustomMiddleware` |
|
|
| `POST` | `/api/feed` | `CustomMiddleware` |
|
|
| `POST` | `/api/accessdevice` | none |
|
|
| `POST` | `/api/attendance` | `CustomMiddleware` |
|
|
| `POST` | `/api/chat` | `CustomMiddleware` |
|
|
| `POST` | `/api/initChat` | `CustomMiddleware` |
|
|
| `POST` | `/api/payment` | `CustomMiddleware` |
|
|
| `POST` | `/api/clientstat` | `CustomMiddleware` |
|
|
| `POST` | `/api/register` | none |
|
|
|
|
### A3. Function names supported by each legacy dispatcher
|
|
|
|
#### `/api/activitylog`
|
|
|
|
- `LogActivity`
|
|
- `GetActivityLogs`
|
|
|
|
#### `/api/auth`
|
|
|
|
- `SendOtp`
|
|
- `VerifyOTP`
|
|
- `IsAvailable`
|
|
- `RegisterUser`
|
|
- `UpdateUser`
|
|
- `GetUserDetails`
|
|
- `LoginUser`
|
|
- `RefreshToken`
|
|
- `VerifyOtpForLogin`
|
|
- `LogOut`
|
|
|
|
`POST /api/VerifyOTP` forces `FunctionName = "VerifyOTP"`.
|
|
|
|
`POST /api/refreshToken` forces `FunctionName = "RefreshToken"`.
|
|
|
|
`POST /api/logout` forces `FunctionName = "LogOut"`.
|
|
|
|
#### `/api/client`
|
|
|
|
- `GetClientList`
|
|
- `GetClientById`
|
|
- `GetCustomerDetailsById`
|
|
- `CreateCustomerWithPlans`
|
|
- `UpdateCustomerByClient`
|
|
- `GetCustomersByClientId`
|
|
- `GetCustomerPlansByClientId`
|
|
- `RegisterClient`
|
|
- `GetPackageList`
|
|
- `GetAllCustomers`
|
|
- `DeleteCustomerByClient`
|
|
- `ClientLogOut`
|
|
- `GetAllCustomerPlans`
|
|
- `GetMealPlansByClientId`
|
|
- `GetWorkoutPlansByClientId`
|
|
- `GetMealPlanById`
|
|
- `GetWorkoutPlanById`
|
|
- `GetCustomerPlanById`
|
|
- `GetOwnCards`
|
|
|
|
#### `/api/staff`
|
|
|
|
- `GetAllStaff`
|
|
- `GetStaffById`
|
|
- `GetStaffByClientId`
|
|
- `CreateStaff`
|
|
- `UpdateStaff`
|
|
- `DeleteStaff`
|
|
|
|
#### `/api/clientinvoice`
|
|
|
|
- `CreateClientInvoiceFromSubscription`
|
|
- `GetClientInvoiceById`
|
|
- `GetClientInvoicesByClientId`
|
|
- `GetClientInvoicesByUserId`
|
|
- `UpdateClientInvoiceStatus`
|
|
- `CalculateClientInvoiceTotal`
|
|
|
|
#### `/api/customer`
|
|
|
|
- `CreateCustomer`
|
|
- `DeleteCustomer`
|
|
- `UpdateCustomer`
|
|
- `GetCustomerMealPlan`
|
|
- `GetCustomerMealPlanById`
|
|
- `GetCustomerWorkOutPlan`
|
|
- `GetCustomerWorkoutPlanById`
|
|
- `FollowMealPlan`
|
|
- `GetFollowedMealPlans`
|
|
- `GetFollowedWorkoutPlans`
|
|
- `FollowWorkOutPlan`
|
|
- `GetClientDataById`
|
|
- `CreateCusHealthRec`
|
|
- `CreateCusProgressRec`
|
|
- `UpdateCusHealthRec`
|
|
- `UpdateCusProgressRec`
|
|
- `UpdateCustomerTargetNutritions`
|
|
- `GetClientGyms`
|
|
- `GetCustomerProgress`
|
|
- `UpdateWeeklyProgress`
|
|
- `GetWeeklyProgressForCustomer`
|
|
- `GetCusBasicDetails`
|
|
- `GetCusHealthDetails`
|
|
- `GetCusProgressDetails`
|
|
- `CreateFeed`
|
|
- `GetOwnCards`
|
|
|
|
#### `/api/customerinvoice`
|
|
|
|
- `CreateCustomerInvoiceFromSubscription`
|
|
- `GetCustomerInvoiceById`
|
|
- `GetCustomerInvoicesByCustomerId`
|
|
- `GetCustomerInvoicesByClientId`
|
|
- `UpdateCustomerInvoiceStatus`
|
|
- `CalculateCustomerInvoiceTotal`
|
|
|
|
#### `/api/customerplan`
|
|
|
|
- `GetAllCustomerPlans`
|
|
- `GetCustomerPlanById`
|
|
- `CreateCustomerPlan`
|
|
- `UpdateCustomerPlan`
|
|
- `DeleteCustomerPlan`
|
|
|
|
#### `/api/customersubscription`
|
|
|
|
- `CreateCustomerSubscription`
|
|
- `GetCustomerSubscriptionById`
|
|
- `GetCustomerSubscriptionsByCustomerId`
|
|
- `GetActiveSubscriptionByCustomerId`
|
|
|
|
#### `/api/meal`
|
|
|
|
- `GetMealCategoryList`
|
|
- `CreateMealCategory`
|
|
- `GetMealPlanList`
|
|
- `GetMealPlanById`
|
|
- `GetMealPlanByCustomerId`
|
|
- `CreateMealPlan`
|
|
- `CreateCustomerMealPlan`
|
|
- `UpdateMealPlan`
|
|
- `GetMealItemsByMealPlanId`
|
|
- `CreateMealItem`
|
|
- `DeleteMealPlan`
|
|
|
|
#### `/api/workout`
|
|
|
|
- `GetWorkoutCategoryList`
|
|
- `CreateWorkoutCategory`
|
|
- `GetWorkoutPlanList`
|
|
- `GetWorkoutPlanById`
|
|
- `GetWorkoutPlanByCustomerId`
|
|
- `CreateWorkoutPlan`
|
|
- `CreateCustomerWorkout`
|
|
- `UpdateWorkoutPlan`
|
|
- `DeleteWorkoutPlan`
|
|
- `GetWorkoutItemsByWorkoutPlanId`
|
|
- `CreateWorkoutItem`
|
|
|
|
#### `/api/document`
|
|
|
|
- `UploadDocument`
|
|
- `GetDocumentsByUserId`
|
|
- `GetDocumentById`
|
|
- `RemoveDocument`
|
|
|
|
#### `/api/feed`
|
|
|
|
- `GetFeedPostById`
|
|
- `GetFeedList`
|
|
- `Like`
|
|
- `Unlike`
|
|
- `IsLiked`
|
|
- `CreateFeed`
|
|
- `ShowFeedByClientId`
|
|
- `DeleteFeedByPostId`
|
|
|
|
#### `/api/accessdevice`
|
|
|
|
- `AddDevice`
|
|
- `RemoveDevice`
|
|
- `GeneratePairingCode`
|
|
- `AddUser`
|
|
- `WhiteListMember`
|
|
- `BlackListMember`
|
|
|
|
#### `/api/attendance`
|
|
|
|
- `GetAllAttendanceRecords`
|
|
- `GetAttendanceCounts`
|
|
- `GetTodayAttendance`
|
|
|
|
#### `/api/chat`
|
|
|
|
Current function map in code:
|
|
|
|
- `GetOrCreateChatAsync`
|
|
- `GetClientById` -> calls `SendMessageAsync`
|
|
- `RegisterClient` -> calls `GetMessagesAsync`
|
|
|
|
These function names look legacy/inconsistent, but this is the current implementation.
|
|
|
|
#### `/api/payment`
|
|
|
|
- `CreateCustomerPayment`
|
|
- `CreateClientPayment`
|
|
- `GetPaymentById`
|
|
- `GetPaymentsByCustomerInvoice`
|
|
- `GetPaymentsByClientInvoice`
|
|
- `ApprovePayment`
|
|
|
|
#### `/api/clientstat`
|
|
|
|
- `GetTotalCustomerCount`
|
|
- `GetMonthlyCustomerCount`
|
|
- `GetTotalWorkoutPlanCount`
|
|
- `GetTotalMealPlanCount`
|
|
- `GetLastMonthCustomerCount`
|
|
- `GetLastFiveAttendances`
|
|
- `GetLastFivePayments`
|
|
- `GetLastMonthRevenue`
|
|
- `GetMonthlyRevenueVariation`
|
|
- `GetTotalRevenue`
|
|
- `GetClientStatSummary`
|
|
|
|
#### `/api/register`
|
|
|
|
- `CreateCustomer`
|
|
- `RegisterClient`
|
|
|
|
## B. `AdminController` (`/api/admin`)
|
|
|
|
All endpoints are protected by `CustomMiddleware`.
|
|
|
|
| Method | Path | Request | Response |
|
|
|---|---|---|---|
|
|
| `GET` | `/api/admin/onboarding-requests` | query: `OnboardingRequestQuery` | `ApiResponse<PagedResult<OnboardingRequestSummary>>` |
|
|
| `GET` | `/api/admin/onboarding-requests/{id}` | route `id` | `ApiResponse<OnboardingRequestDetail>` |
|
|
| `PATCH` | `/api/admin/onboarding-requests/{id}/status` | body: `UpdateOnboardingStatusRequest` | `ApiResponse<OnboardingRequestDetail>` |
|
|
| `POST` | `/api/admin/onboarding-requests/{id}/resend-activation-link` | route `id` | `ApiResponse<object>` with `{ sent = true }` |
|
|
| `GET` | `/api/admin/payout-kyc` | query: `status` | `ApiResponse<List<ClientPayoutKycDto>>` |
|
|
| `GET` | `/api/admin/payout-kyc/{clientId}` | route `clientId` | `ApiResponse<ClientPayoutKycDto>` |
|
|
| `PATCH` | `/api/admin/payout-kyc/{clientId}/status` | body: `ReviewPayoutKycRequest` | `ApiResponse<ClientPayoutKycDto>` |
|
|
| `GET` | `/api/admin/clients` | query: `ClientDirectoryQuery` | `ApiResponse<PagedResult<ClientSummary>>` |
|
|
| `GET` | `/api/admin/clients/{id}` | route `id` | `ApiResponse<object>` |
|
|
|
|
## C. `ClientController` (`/api/client`)
|
|
|
|
### C1. Onboarding request access
|
|
|
|
| Method | Path | Auth | Request | Response |
|
|
|---|---|---|---|---|
|
|
| `POST` | `/api/client/onboarding/requests/mobile-check` | none | `MobileNumberCheckRequest` | `ApiResponse<MobileNumberCheckResult>` |
|
|
| `POST` | `/api/client/onboarding/requests/otp` | none | `SendMobileOtpRequest` | `ApiResponse<SendOtpResult>` |
|
|
| `POST` | `/api/client/onboarding/requests/otp/verify` | none | `VerifyMobileOtpRequest` | `ApiResponse<VerifyOtpResult>` |
|
|
| `POST` | `/api/client/onboarding/requests` | bearer request-access token | `CreateOnboardingRequest` | `ApiResponse<OnboardingRequestCreated>` |
|
|
| `GET` | `/api/client/onboarding/sandbox/{sandboxToken}/status` | none | route `sandboxToken` | `ApiResponse<SandboxStatus>` |
|
|
| `PATCH` | `/api/client/onboarding/sandbox/{sandboxToken}/progress` | none | `SandboxProgressUpdate` | `ApiResponse<SandboxStatus>` |
|
|
|
|
### C2. Activation
|
|
|
|
| Method | Path | Auth | Request | Response |
|
|
|---|---|---|---|---|
|
|
| `POST` | `/api/client/activation/{activationToken}/email/otp` | none | `SendEmailOtpRequest` | `ApiResponse<SendOtpResult>` |
|
|
| `POST` | `/api/client/activation/{activationToken}/email/otp/verify` | none | `VerifyOtpCodeRequest` | `ApiResponse<object>` with `{ emailVerified = true }` |
|
|
| `POST` | `/api/client/activation/{activationToken}/nic` | none | multipart form: `nicNumber`, `frontImage`, `backImage` | `ApiResponse<NicUploadResult>` |
|
|
| `PUT` | `/api/client/activation/{activationToken}/gym-profile` | none | `GymProfileRequest` | `ApiResponse<object>` |
|
|
| `POST` | `/api/client/activation/{activationToken}/payment-method` | none | `SetPaymentMethodRequest` | `ApiResponse<PaymentMethodResult>` |
|
|
| `POST` | `/api/client/activation/{activationToken}/charge` | none | none | `ApiResponse<ActivationCompleteResult>` |
|
|
| `GET` | `/api/client/activation/{activationToken}/checklist` | none | route `activationToken` | `ApiResponse<List<SetupChecklistItem>>` |
|
|
| `GET` | `/api/client/activation/{activationToken}/status` | none | route `activationToken` | `ApiResponse<ActivationStatusResult>` |
|
|
|
|
### C3. Own profile and business
|
|
|
|
| Method | Path | Auth | Request | Response |
|
|
|---|---|---|---|---|
|
|
| `GET` | `/api/client/me` | `CustomMiddleware` | none | `ApiResponse<object>` |
|
|
| `GET` | `/api/client/packages` | `CustomMiddleware` | none | `ApiResponse<object>` |
|
|
|
|
### C4. Customer management
|
|
|
|
| Method | Path | Auth | Request | Response |
|
|
|---|---|---|---|---|
|
|
| `GET` | `/api/client/customers` | `CustomMiddleware` | none | `ApiResponse<object>` |
|
|
| `GET` | `/api/client/customers/{customerId}` | `CustomMiddleware` | route `customerId` | `ApiResponse<object>` |
|
|
| `POST` | `/api/client/customers` | `CustomMiddleware` | `CreateCustomerWithPlansRequest` | `ApiResponse<object>` |
|
|
| `PUT` | `/api/client/customers/{customerId}` | `CustomMiddleware` | `UpdateCustomerByClientRequest` | `ApiResponse<object>` |
|
|
| `DELETE` | `/api/client/customers/{customerId}` | `CustomMiddleware` | query `softDelete=true` optional | `ApiResponse<object>` |
|
|
|
|
### C5. Staff management
|
|
|
|
| Method | Path | Auth | Request | Response |
|
|
|---|---|---|---|---|
|
|
| `GET` | `/api/client/staff` | `CustomMiddleware` | none | `ApiResponse<object>` |
|
|
| `GET` | `/api/client/staff/{staffId}` | `CustomMiddleware` | route `staffId` | `ApiResponse<object>` |
|
|
| `POST` | `/api/client/staff` | `CustomMiddleware` | `CreateStaffRequest` | `ApiResponse<object>` |
|
|
| `PUT` | `/api/client/staff/{staffId}` | `CustomMiddleware` | `UpdateStaffRequest` | `ApiResponse<object>` |
|
|
| `DELETE` | `/api/client/staff/{staffId}` | `CustomMiddleware` | query `softDelete=true` optional | `ApiResponse<object>` |
|
|
|
|
### C6. Invoices
|
|
|
|
`customer-invoices` here means platform invoices billed to the gym.
|
|
|
|
`member-invoices` means invoices billed to gym members.
|
|
|
|
| Method | Path | Auth | Request | Response |
|
|
|---|---|---|---|---|
|
|
| `GET` | `/api/client/customer-invoices` | `CustomMiddleware` | none | `ApiResponse<object>` |
|
|
| `GET` | `/api/client/customer-invoices/{id}` | `CustomMiddleware` | route `id` | `ApiResponse<object>` |
|
|
| `GET` | `/api/client/member-invoices` | `CustomMiddleware` | none | `ApiResponse<object>` |
|
|
| `GET` | `/api/client/member-invoices/{id}` | `CustomMiddleware` | route `id` | `ApiResponse<object>` |
|
|
|
|
### C7. Dashboard stats
|
|
|
|
| Method | Path | Auth | Request | Response |
|
|
|---|---|---|---|---|
|
|
| `GET` | `/api/client/stats/summary` | `CustomMiddleware` | none | `ApiResponse<object>` |
|
|
| `GET` | `/api/client/stats/monthly-revenue` | `CustomMiddleware` | none | `ApiResponse<object>` |
|
|
| `GET` | `/api/client/stats/recent-payments` | `CustomMiddleware` | none | `ApiResponse<object>` |
|
|
| `GET` | `/api/client/stats/recent-attendance` | `CustomMiddleware` | none | `ApiResponse<object>` |
|
|
|
|
### C8. Payments enablement
|
|
|
|
| Method | Path | Auth | Request | Response |
|
|
|---|---|---|---|---|
|
|
| `GET` | `/api/client/payments/tracks` | `CustomMiddleware` | none | `ApiResponse<List<PaymentTrackOption>>` |
|
|
| `POST` | `/api/client/payments/track-selection` | `CustomMiddleware` | `SelectPaymentTrackRequest` | `ApiResponse<PaymentTrackSelectionResult>` |
|
|
| `POST` | `/api/client/payments/kyc` | `CustomMiddleware` | multipart form: `brCertificate`, `bankProof` | `ApiResponse<ClientPayoutKycDto>` |
|
|
| `GET` | `/api/client/payments/kyc/status` | `CustomMiddleware` | none | `ApiResponse<object>` with `{ kycStatus }` |
|
|
| `GET` | `/api/client/payments/wallet` | `CustomMiddleware` | none | `ApiResponse<WalletDto>` |
|
|
| `GET` | `/api/client/payments/payout-schedule` | `CustomMiddleware` | none | `ApiResponse<PayoutScheduleDto>` |
|
|
|
|
### C9. Attendance
|
|
|
|
| Method | Path | Auth | Request | Response |
|
|
|---|---|---|---|---|
|
|
| `GET` | `/api/client/attendance` | `CustomMiddleware` | none | `ApiResponse<object>` |
|
|
| `GET` | `/api/client/attendance/today` | `CustomMiddleware` | none | `ApiResponse<object>` |
|
|
| `GET` | `/api/client/attendance/counts` | `CustomMiddleware` | query `fromDate`, `toDate` | `ApiResponse<object>` |
|
|
|
|
### C10. Membership plans
|
|
|
|
| Method | Path | Auth | Request | Response |
|
|
|---|---|---|---|---|
|
|
| `GET` | `/api/client/plans` | `CustomMiddleware` | query `includeInactive=false` | `ApiResponse<object>` |
|
|
| `GET` | `/api/client/plans/{id}` | `CustomMiddleware` | route `id` | `ApiResponse<object>` |
|
|
| `POST` | `/api/client/plans` | `CustomMiddleware` | `CreateCustomerPlanRequest` | `ApiResponse<object>` |
|
|
| `PUT` | `/api/client/plans/{id}` | `CustomMiddleware` | `UpdateCustomerPlanRequest` | `ApiResponse<object>` |
|
|
| `DELETE` | `/api/client/plans/{id}` | `CustomMiddleware` | route `id` | `ApiResponse<object>` |
|
|
|
|
### C11. Workout plans
|
|
|
|
| Method | Path | Auth | Request | Response |
|
|
|---|---|---|---|---|
|
|
| `GET` | `/api/client/workout-plans` | `CustomMiddleware` | none | `ApiResponse<object>` |
|
|
| `GET` | `/api/client/workout-plans/{id}` | `CustomMiddleware` | route `id` | `ApiResponse<object>` |
|
|
| `POST` | `/api/client/workout-plans` | `CustomMiddleware` | `WorkoutPlanRequest` | `ApiResponse<object>` |
|
|
| `PUT` | `/api/client/workout-plans/{id}` | `CustomMiddleware` | `WorkoutPlanRequest` | `ApiResponse<object>` |
|
|
| `DELETE` | `/api/client/workout-plans/{id}` | `CustomMiddleware` | route `id` | `ApiResponse<object>` |
|
|
| `GET` | `/api/client/workout-plans/{id}/items` | `CustomMiddleware` | route `id` | `ApiResponse<object>` |
|
|
| `POST` | `/api/client/workout-plans/{id}/items` | `CustomMiddleware` | `WorkoutItemRequest` | `ApiResponse<object>` |
|
|
| `GET` | `/api/client/workout-plans/categories` | `CustomMiddleware` | none | `ApiResponse<object>` |
|
|
| `POST` | `/api/client/workout-plans/categories` | `CustomMiddleware` | `PlanCategoryRequest` | `ApiResponse<object>` |
|
|
| `POST` | `/api/client/workout-plans/{id}/assignments` | `CustomMiddleware` | `PlanAssignRequest` | `ApiResponse<object>` |
|
|
| `DELETE` | `/api/client/workout-plans/assignments/{customerWorkoutId}` | `CustomMiddleware` | route `customerWorkoutId` | `ApiResponse<object>` |
|
|
|
|
### C12. Meal plans
|
|
|
|
| Method | Path | Auth | Request | Response |
|
|
|---|---|---|---|---|
|
|
| `GET` | `/api/client/meal-plans` | `CustomMiddleware` | none | `ApiResponse<object>` |
|
|
| `GET` | `/api/client/meal-plans/{id}` | `CustomMiddleware` | route `id` | `ApiResponse<object>` |
|
|
| `POST` | `/api/client/meal-plans` | `CustomMiddleware` | `MealPlanRequest` | `ApiResponse<object>` |
|
|
| `PUT` | `/api/client/meal-plans/{id}` | `CustomMiddleware` | `MealPlanRequest` | `ApiResponse<object>` |
|
|
| `DELETE` | `/api/client/meal-plans/{id}` | `CustomMiddleware` | route `id` | `ApiResponse<object>` |
|
|
| `GET` | `/api/client/meal-plans/{id}/items` | `CustomMiddleware` | route `id` | `ApiResponse<object>` |
|
|
| `POST` | `/api/client/meal-plans/{id}/items` | `CustomMiddleware` | `MealItemRequest` | `ApiResponse<object>` |
|
|
| `GET` | `/api/client/meal-plans/categories` | `CustomMiddleware` | none | `ApiResponse<object>` |
|
|
| `POST` | `/api/client/meal-plans/categories` | `CustomMiddleware` | `PlanCategoryRequest` | `ApiResponse<object>` |
|
|
| `POST` | `/api/client/meal-plans/{id}/assignments` | `CustomMiddleware` | `PlanAssignRequest` | `ApiResponse<object>` |
|
|
| `DELETE` | `/api/client/meal-plans/assignments/{customerMealId}` | `CustomMiddleware` | route `customerMealId` | `ApiResponse<object>` |
|
|
|
|
### C13. Feed
|
|
|
|
| Method | Path | Auth | Request | Response |
|
|
|---|---|---|---|---|
|
|
| `GET` | `/api/client/feed` | `CustomMiddleware` | none | `ApiResponse<object>` |
|
|
| `POST` | `/api/client/feed` | `CustomMiddleware` | `CreateFeedRequest` | `ApiResponse<object>` |
|
|
| `DELETE` | `/api/client/feed/{postId}` | `CustomMiddleware` | route `postId` | `ApiResponse<object>` |
|
|
| `POST` | `/api/client/feed/{postId}/like` | `CustomMiddleware` | route `postId` | `ApiResponse<object>` |
|
|
| `DELETE` | `/api/client/feed/{postId}/like` | `CustomMiddleware` | route `postId` | `ApiResponse<object>` |
|
|
| `GET` | `/api/client/feed/{postId}/like` | `CustomMiddleware` | route `postId` | `ApiResponse<object>` |
|
|
|
|
### C14. Tickets
|
|
|
|
| Method | Path | Auth | Request | Response |
|
|
|---|---|---|---|---|
|
|
| `GET` | `/api/client/tickets` | `CustomMiddleware` | none | `ApiResponse<object>` |
|
|
| `GET` | `/api/client/tickets/{id}` | `CustomMiddleware` | route `id` | `ApiResponse<object>` |
|
|
| `GET` | `/api/client/tickets/categories` | `CustomMiddleware` | none | `ApiResponse<object>` |
|
|
| `POST` | `/api/client/tickets` | `CustomMiddleware` | `CreateTicketRequest` | `ApiResponse<object>` |
|
|
| `PUT` | `/api/client/tickets/{id}` | `CustomMiddleware` | `UpdateTicketRequest` | `ApiResponse<object>` |
|
|
| `POST` | `/api/client/tickets/{id}/messages` | `CustomMiddleware` | `SendTicketMessageRequest` | `ApiResponse<object>` |
|
|
| `POST` | `/api/client/tickets/{id}/feedback` | `CustomMiddleware` | `TicketFeedbackRequest` | `ApiResponse<object>` |
|
|
| `POST` | `/api/client/tickets/{id}/close` | `CustomMiddleware` | none | `ApiResponse<object>` |
|
|
| `DELETE` | `/api/client/tickets/{id}` | `CustomMiddleware` | route `id` | `ApiResponse<object>` |
|
|
|
|
### C15. Subscriptions and group members
|
|
|
|
| Method | Path | Auth | Request | Response |
|
|
|---|---|---|---|---|
|
|
| `GET` | `/api/client/subscriptions/{id}` | `CustomMiddleware` | route `id` | `ApiResponse<object>` |
|
|
| `POST` | `/api/client/subscriptions/{id}/members` | `CustomMiddleware` | `AddSubscriptionMemberRequest` | `ApiResponse<object>` |
|
|
| `DELETE` | `/api/client/subscriptions/{id}/members/{memberId}` | `CustomMiddleware` | route `id`, route `memberId` | `ApiResponse<object>` |
|
|
| `GET` | `/api/client/subscriptions/{id}/payments` | `CustomMiddleware` | route `id` | `ApiResponse<object>` |
|
|
| `POST` | `/api/client/subscriptions/{id}/payments` | `CustomMiddleware` | `RecordSubscriptionPaymentRequest` | `ApiResponse<object>` |
|
|
|
|
## D. `AgentController` (`/api/agent`)
|
|
|
|
| Method | Path | Auth | Request | Response |
|
|
|---|---|---|---|---|
|
|
| `POST` | `/api/agent/enroll` | anonymous | `EnrollRequest` | `ApiResponse<object>` |
|
|
| `POST` | `/api/agent/devices` | `X-Api-Key` | `RegisterDeviceRequest` | `ApiResponse<object>` |
|
|
| `POST` | `/api/agent/attendance` | `X-Api-Key` | `AgentAttendanceRequest` | `ApiResponse<object>` |
|
|
| `GET` | `/api/agent/commands` | `X-Api-Key` | none | `ApiResponse<object>` |
|
|
| `POST` | `/api/agent/commands/{id}/result` | `X-Api-Key` | `CommandResultRequest` | `ApiResponse<object>` |
|
|
| `POST` | `/api/agent/heartbeat` | `X-Api-Key` | none | `ApiResponse<object>` |
|
|
|
|
## Request and Response DTOs
|
|
|
|
## Onboarding and activation DTOs
|
|
|
|
Defined in `Models/IOs/OnboardingDtos.cs`.
|
|
|
|
### Request contracts
|
|
|
|
- `SendMobileOtpRequest`
|
|
- `mobileNumber`
|
|
- `VerifyMobileOtpRequest`
|
|
- `mobileNumber`
|
|
- `referenceNumber`
|
|
- `otpCode`
|
|
- `VerifyOtpCodeRequest`
|
|
- `referenceNumber`
|
|
- `otpCode`
|
|
- `CreateOnboardingRequest`
|
|
- `ownerName`
|
|
- `gymName`
|
|
- `city`
|
|
- `MobileNumberCheckRequest`
|
|
- `mobileNumber`
|
|
- `SandboxProgressUpdate`
|
|
- `tourStepCompleted`
|
|
- `minutesElapsedDelta`
|
|
- `SendEmailOtpRequest`
|
|
- `email`
|
|
- `GymProfileRequest`
|
|
- `gymName`
|
|
- `address`
|
|
- `city`
|
|
- `SetPaymentMethodRequest`
|
|
- `payHereToken`
|
|
- `UpdateOnboardingStatusRequest`
|
|
- `status`
|
|
- `reason`
|
|
- `ReviewPayoutKycRequest`
|
|
- `status`
|
|
- `reason`
|
|
- `SelectPaymentTrackRequest`
|
|
- `track`
|
|
- `OnboardingRequestQuery`
|
|
- `status`
|
|
- `search`
|
|
- `page`
|
|
- `pageSize`
|
|
- `ClientDirectoryQuery`
|
|
- `search`
|
|
- `page`
|
|
- `pageSize`
|
|
|
|
### Response contracts
|
|
|
|
- `SendOtpResult`
|
|
- `referenceNumber`
|
|
- `expiresInSeconds`
|
|
- `resendAllowedInSeconds`
|
|
- `VerifyOtpResult`
|
|
- `requestAccessToken`
|
|
- `expiresIn`
|
|
- `OnboardingRequestCreated`
|
|
- `onboardingRequestId`
|
|
- `sandboxToken`
|
|
- `status`
|
|
- `SandboxStatus`
|
|
- `id`
|
|
- `status`
|
|
- `bannerMessage`
|
|
- `tourProgress`
|
|
- `minutesInSandbox`
|
|
- `ActivationStatusResult`
|
|
- `status`
|
|
- `canActivate`
|
|
- `rejectionReason`
|
|
- `MobileNumberCheckResult`
|
|
- `exists`
|
|
- `message`
|
|
- `status`
|
|
- `sandboxToken`
|
|
- `OnboardingRequestSummary`
|
|
- `OnboardingRequestDetail`
|
|
- `PagedResult<T>`
|
|
- `NicUploadResult`
|
|
- `nicFrontDocId`
|
|
- `nicBackDocId`
|
|
- `OwnerActivationSummary`
|
|
- `PaymentMethodResult`
|
|
- `cardLast4`
|
|
- `cardType`
|
|
- `ActivationCompleteResult`
|
|
- `accessToken`
|
|
- `refreshToken`
|
|
- `clientId`
|
|
- `checklist`
|
|
- `SetupChecklistItem`
|
|
- `key`
|
|
- `label`
|
|
- `isComplete`
|
|
- `PaymentTrackOption`
|
|
- `track`
|
|
- `feeSummary`
|
|
- `PaymentTrackSelectionResult`
|
|
- `track`
|
|
- `kycRequired`
|
|
- `ClientPayoutKycDto`
|
|
- `id`
|
|
- `clientId`
|
|
- `kycStatus`
|
|
- `submittedAt`
|
|
- `WalletDto`
|
|
- `WalletLedgerEntryDto`
|
|
- `PayoutScheduleDto`
|
|
- `ClientSummary`
|
|
|
|
## ClientController inline request DTOs
|
|
|
|
These are declared at the bottom of `Controllers/ClientController.cs`.
|
|
|
|
- `WorkoutPlanRequest`
|
|
- `name`
|
|
- `description`
|
|
- `isTemplate`
|
|
- `workoutCategoryId`
|
|
- `customerIds`
|
|
- `workoutItems`
|
|
- `WorkoutItemRequest`
|
|
- `exerciseDay`
|
|
- `description`
|
|
- `exercises`
|
|
- `howToDo`
|
|
- `doURL`
|
|
- `MealPlanRequest`
|
|
- `name`
|
|
- `description`
|
|
- `isTemplate`
|
|
- `mealCategoryId`
|
|
- `customerIds`
|
|
- `mealItems`
|
|
- `MealItemRequest`
|
|
- `name`
|
|
- `description`
|
|
- `calories`
|
|
- `servingSize`
|
|
- `preparationNotes`
|
|
- `PlanCategoryRequest`
|
|
- `name`
|
|
- `description`
|
|
- `PlanAssignRequest`
|
|
- `customerId`
|
|
- `notes`
|
|
- `CreateFeedRequest`
|
|
- `caption`
|
|
- `description`
|
|
- `document`
|
|
- `CreateTicketRequest`
|
|
- `mainReason`
|
|
- `ticketCategoryId`
|
|
- `UpdateTicketRequest`
|
|
- `mainReason`
|
|
- `ticketCategoryId`
|
|
- `SendTicketMessageRequest`
|
|
- `message`
|
|
- `attachmentURL`
|
|
- `TicketFeedbackRequest`
|
|
- `rating`
|
|
- `feedback`
|
|
- `AddSubscriptionMemberRequest`
|
|
- `customerId`
|
|
- `RecordSubscriptionPaymentRequest`
|
|
- `amount`
|
|
- `note`
|
|
|
|
## DTO inventory under `DTOs/`
|
|
|
|
### Auth
|
|
|
|
- `DTOs/Auth/AuthResponse.cs`
|
|
- `AuthResponse`
|
|
|
|
### Agent
|
|
|
|
- `DTOs/Agent/AgentRequests.cs`
|
|
- `EnrollRequest`
|
|
- `RegisterDeviceRequest`
|
|
- `AgentAttendanceRequest`
|
|
- `AgentAttendanceEvent`
|
|
- `CommandResultRequest`
|
|
|
|
### Attendance
|
|
|
|
- `AttendanceCountDTO`
|
|
- `AttendanceDTO`
|
|
- `TodayAttendanceDTO`
|
|
|
|
### Client invoice
|
|
|
|
- `ClientInvoiceDto`
|
|
- `ClientInvoiceItemDto`
|
|
- `CreateClientInvoiceRequest`
|
|
- `UpdateClientInvoiceStatusRequest`
|
|
|
|
### Customer
|
|
|
|
- `CreateCustomerRequest`
|
|
- `CustomerDto`
|
|
- `MemberListRowDto`
|
|
- `UpdateCustomerRequest`
|
|
|
|
### Customer invoice
|
|
|
|
- `CreateCustomerInvoiceRequest`
|
|
- `CustomerInvoiceDto`
|
|
- `CustomerInvoiceItemDto`
|
|
- `UpdateCustomerInvoiceStatusRequest`
|
|
|
|
### Customer plan
|
|
|
|
- `CreateCustomerPlanRequest`
|
|
- `CustomerPlanDto`
|
|
- `UpdateCustomerPlanRequest`
|
|
|
|
### Customer subscription
|
|
|
|
- `CreateCustomerSubscriptionRequest`
|
|
- `CustomerSubscriptionDto`
|
|
- `CustomerSubItemDto`
|
|
- `SubscriptionSummaryDto`
|
|
- `SubscriptionMemberDto`
|
|
- `SubscriptionInstallmentDto`
|
|
|
|
### Meal
|
|
|
|
- `CustomerMealDto`
|
|
- `MealCategoryDto`
|
|
- `MealDto`
|
|
- `MealPlanDetailDto`
|
|
- `MealPlanDto`
|
|
|
|
### Staff
|
|
|
|
- `CreateStaffRequest`
|
|
- `StaffDto`
|
|
- `UpdateStaffRequest`
|
|
|
|
### Stats
|
|
|
|
- `ClientStatSummaryDto`
|
|
- `MonthlyRevenueStat`
|
|
|
|
### Ticket
|
|
|
|
- `TicketDto`
|
|
- `TicketDetailDto`
|
|
- `TicketMessageDto`
|
|
|
|
### Workout
|
|
|
|
- `CustomerWorkoutDto`
|
|
- `WorkoutCategoryDto`
|
|
- `WorkoutItemDto`
|
|
- `WorkoutPlanDetailDto`
|
|
- `WorkoutPlanDto`
|
|
|
|
### Miscellaneous
|
|
|
|
- `DocumentDownloadModel`
|
|
- `UpdateTuteItemRequest`
|
|
|
|
## Notable request DTO field detail
|
|
|
|
### `CreateCustomerPlanRequest`
|
|
|
|
Fields:
|
|
|
|
- `planName` required
|
|
- `planDescription` optional
|
|
- `planPrice` required decimal
|
|
- `durationInDays` optional, validated by service
|
|
- `planScope` optional, `"Individual"` or `"Group"`
|
|
- `memberLimit` optional, used for group plans
|
|
- `durationMode` optional, `"Rolling"` or `"FixedRange"`
|
|
- `validFrom` optional
|
|
- `validTo` optional
|
|
- `allowSplitPayments` optional
|
|
- `installmentCount` optional
|
|
|
|
### `AuthResponse`
|
|
|
|
Fields:
|
|
|
|
- `statusCode`
|
|
- `success`
|
|
- `message`
|
|
- `data`
|
|
|
|
## Helpers
|
|
|
|
### `Helpers/ApiKeyHelper.cs`
|
|
|
|
- generates 256-bit agent API keys
|
|
- hashes API keys using SHA-256 for storage and lookup
|
|
|
|
### `Helpers/ApiResponseHelper.cs`
|
|
|
|
- wraps data into `ApiResponse<T>`
|
|
|
|
### `Helpers/AuthOtpResponseParser.cs`
|
|
|
|
- parses OTP-related auth responses
|
|
|
|
### `Helpers/CustomerProgressHelper.cs`
|
|
|
|
- customer fitness/progress calculations and predictions
|
|
- related to progress formulas in `CustomerProgressFormulas.txt`
|
|
|
|
### `Helpers/DataExtractor.cs`
|
|
|
|
- extracts typed values from JSON payload dictionaries
|
|
- helpers for string, int, decimal, bool, guid, datetime, date, and auth response parsing
|
|
- provides `GetUserIdFromContext`
|
|
|
|
### `Helpers/DeserializePayload.cs`
|
|
|
|
- payload deserialization helper
|
|
|
|
### `Helpers/EncryptionHelper.cs`
|
|
|
|
- encryption-related utility methods
|
|
|
|
### `Helpers/JwtMiddleware.cs`
|
|
|
|
- custom auth filter named `CustomMiddlewareAttribute`
|
|
- validates standard JWT access tokens
|
|
|
|
### `Helpers/RequestAccessTokenHelper.cs`
|
|
|
|
- issues and validates onboarding request-access tokens
|
|
|
|
### `Helpers/UserRoleHelper.cs`
|
|
|
|
- resolves role/client relationships from users
|
|
|
|
## Services
|
|
|
|
### Core services
|
|
|
|
- `AccessDeviceService`
|
|
- `ActivationService`
|
|
- `ActivityLogService`
|
|
- `AdminClientDirectoryService`
|
|
- `AgentService`
|
|
- `AttendanceService`
|
|
- `AuthService`
|
|
- `ChatService`
|
|
- `ClientInvoiceService`
|
|
- `ClientService`
|
|
- `ClientStatService`
|
|
- `CustomerInvoiceService`
|
|
- `CustomerPlanService`
|
|
- `CustomerService`
|
|
- `CustomerSubscriptionService`
|
|
- `DocumentService`
|
|
- `FeedService`
|
|
- `MealService`
|
|
- `OnboardingAdminService`
|
|
- `OnboardingService`
|
|
- `PaymentService`
|
|
- `PaymentsEnablementService`
|
|
- `PayoutKycReviewService`
|
|
- `SmsService`
|
|
- `StaffService`
|
|
- `TicketService`
|
|
- `WorkoutService`
|
|
|
|
### Function handler services
|
|
|
|
- `AccessDeviceFunctionHandler`
|
|
- `ActivityLogFuncHandler`
|
|
- `AttendanceFunctionHandler`
|
|
- `AuthFuncHandler`
|
|
- `ChatFunctionHandler`
|
|
- `ClientFuncHandler`
|
|
- `ClientInvoiceFunctionHandler`
|
|
- `ClientStatFuncHandler`
|
|
- `CustomerFunctionHandler`
|
|
- `CustomerInvoiceFunctionHandler`
|
|
- `CustomerPlanFunctionHandler`
|
|
- `CustomerSubscriptionFunctionHandler`
|
|
- `DocumentFunctionHandler`
|
|
- `FeedFuncHandler`
|
|
- `MealFunctionHandler`
|
|
- `PaymentFunctionHandler`
|
|
- `StaffFunctionHandler`
|
|
- `TicketFunctionhandler`
|
|
- `UserRegisterHandler`
|
|
- `WorkoutFunctionHandler`
|
|
|
|
### AI services
|
|
|
|
- `GeminiClient`
|
|
- `IAiClient`
|
|
- `MealPlanOrchestrator`
|
|
- `WorkoutPlanOrchestrator`
|
|
- `ModificationGuard`
|
|
|
|
## Repositories
|
|
|
|
- `AccessDeviceRepo`
|
|
- `ActivityLogRepository`
|
|
- `AdminClientDirectoryRepository`
|
|
- `AgentRepo`
|
|
- `AttendanceRepository`
|
|
- `ChatRepository`
|
|
- `ClientInvoiceRepository`
|
|
- `ClientRepository`
|
|
- `ClientStatRepository`
|
|
- `CustomerInvoiceRepository`
|
|
- `CustomerPlanRepository`
|
|
- `CustomerRepository`
|
|
- `CustomerSubscriptionRepository`
|
|
- `DeviceCommandRepo`
|
|
- `DocumentRepository`
|
|
- `FeedRepository`
|
|
- `MealRepository`
|
|
- `OnboardingRepository`
|
|
- `PairingCodeRepo`
|
|
- `PaymentRepository`
|
|
- `PaymentsEnablementRepository`
|
|
- `StaffRepository`
|
|
- `TicketRepository`
|
|
- `WorkoutRepository`
|
|
|
|
## Data Model Inventory
|
|
|
|
### Main entities
|
|
|
|
- `User`
|
|
- `Admin`
|
|
- `Client`
|
|
- `ClientBusiness`
|
|
- `ClientCard`
|
|
- `ClientPackage`
|
|
- `ClientSubscription`
|
|
- `ClientSubItems`
|
|
- `ClientInvoice`
|
|
- `ClientInvoiceItem`
|
|
- `ClientPayoutKyc`
|
|
- `ClientWallet`
|
|
- `WalletLedgerEntry`
|
|
- `PayoutBatch`
|
|
|
|
- `Customer`
|
|
- `CustomerAccess`
|
|
- `CustomerCards`
|
|
- `CustomerHealth`
|
|
- `CustomerTarget`
|
|
- `CusWeightLossProgress`
|
|
- `CustomerPlan`
|
|
- `CustomerSubscription`
|
|
- `CustomerSubItem`
|
|
- `SubscriptionMember`
|
|
- `SubscriptionInstallment`
|
|
- `CustomerInvoice`
|
|
- `CustomerInvoiceItem`
|
|
- `CustomerWorkout`
|
|
- `CustomerMeal`
|
|
|
|
- `WorkoutCategory`
|
|
- `WorkoutPlan`
|
|
- `WorkoutItem`
|
|
|
|
- `MealCategory`
|
|
- `MealPlan`
|
|
- `Meal`
|
|
|
|
- `FeedPost`
|
|
- `FeedLike`
|
|
|
|
- `Ticket`
|
|
- `TicketCategory`
|
|
- `TicketMessage`
|
|
- `TicketStatus`
|
|
|
|
- `Attendance`
|
|
- `ActivityLog`
|
|
|
|
- `Chat`
|
|
- `ChatMessages`
|
|
|
|
- `UserDocument`
|
|
- `DocumentTypes`
|
|
|
|
- `AccessDevice`
|
|
- `Agent`
|
|
- `PairingCode`
|
|
- `DeviceCommand`
|
|
|
|
- `OnboardingRequest`
|
|
- `OwnerActivation`
|
|
|
|
### Enum inventory
|
|
|
|
- `BeneficiaryType`
|
|
- `BusinessType`
|
|
- `FirstChargeStatus`
|
|
- `KycStatus`
|
|
- `OnboardingStatus`
|
|
- `PaymentTrack`
|
|
- `PayoutBatchStatus`
|
|
- `PriorityLevel`
|
|
- `ProgressGoalType`
|
|
- `Sex`
|
|
- `TicketStatusEnum`
|
|
- `WalletEntryType`
|
|
|
|
### EF Core DbSets in `AppDBContext`
|
|
|
|
The context currently exposes DbSets for all major entities above, including:
|
|
|
|
- users, clients, customers, staff
|
|
- plans and subscriptions
|
|
- invoices and payments
|
|
- meals and workouts
|
|
- feed, chat, tickets, attendance
|
|
- access devices and agents
|
|
- onboarding and payout flows
|
|
|
|
## Interfaces
|
|
|
|
### Repository interfaces
|
|
|
|
- `IActivityLogRepository`
|
|
- `IAccessDeviceRepo`
|
|
- `IAdminClientDirectoryRepository`
|
|
- `IAgentRepo`
|
|
- `IAttendanceRepository`
|
|
- `IChatRepo`
|
|
- `IClientInvoiceRepository`
|
|
- `IClientRepository`
|
|
- `IClientStatRepository`
|
|
- `ICustomerInvoiceRepository`
|
|
- `ICustomerPlanRepository`
|
|
- `ICustomerRepository`
|
|
- `ICustomerSubscriptionRepository`
|
|
- `IDeviceCommandRepo`
|
|
- `IDocumentRepository`
|
|
- `IFeedRepository`
|
|
- `IMealRepository`
|
|
- `IOnboardingRepository`
|
|
- `IPairingCodeRepo`
|
|
- `IPaymentRepository`
|
|
- `IPaymentsEnablementRepository`
|
|
- `IStaffRepository`
|
|
- `ITicketRepository`
|
|
- `IWorkoutRepository`
|
|
|
|
### Service interfaces
|
|
|
|
- `IAccessDeviceService`
|
|
- `IActivationService`
|
|
- `IActivityLogService`
|
|
- `IAdminClientDirectoryService`
|
|
- `IAgentService`
|
|
- `IAttendanceService`
|
|
- `IAuthService`
|
|
- `IChatService`
|
|
- `IClientInvoiceService`
|
|
- `IClientService`
|
|
- `IClientStatService`
|
|
- `ICustomerInvoiceService`
|
|
- `ICustomerPlanService`
|
|
- `ICustomerService`
|
|
- `ICustomerSubscriptionService`
|
|
- `IDocumentService`
|
|
- `IFeedService`
|
|
- `IMealService`
|
|
- `IOnboardingAdminService`
|
|
- `IOnboardingService`
|
|
- `IPaymentService`
|
|
- `IPaymentsEnablementService`
|
|
- `IPayoutKycReviewService`
|
|
- `ISmsService`
|
|
- `IStaffService`
|
|
- `ITicketService`
|
|
- `IWorkoutService`
|
|
|
|
## Other Important Files
|
|
|
|
### Markdown
|
|
|
|
- `README.md`
|
|
- current placeholder text only
|
|
- `PROJECT_REFERENCE.md`
|
|
- this generated project reference
|
|
|
|
### Postman
|
|
|
|
- `Fitness_Core_API.postman_collection.json`
|
|
- `postman/Client-Admin-API.postman_collection.json`
|
|
|
|
### Miscellaneous
|
|
|
|
- `CustomerProgressFormulas.txt`
|
|
- formulas used by customer progress logic
|
|
- `tools/Update-Md5Reference.ps1`
|
|
- PowerShell utility script
|
|
|
|
## Practical Notes and Caveats
|
|
|
|
1. Many newer endpoints in `ClientController` and `AdminController` still return `ApiResponse<object>`.
|
|
The actual data shape comes from service-layer return objects and may not always have a dedicated DTO class.
|
|
|
|
2. Some REST endpoints intentionally omit null properties before passing payloads to services.
|
|
This matters because several services use direct `GetString()`, `GetDecimal()`, or similar access patterns.
|
|
|
|
3. The legacy RPC layer is still a major part of the system.
|
|
If you are building a frontend or integration, do not assume every domain has a clean REST endpoint yet.
|
|
|
|
4. Chat function names in `ChatFunctionHandler` appear mismatched with the actual service methods.
|
|
This document lists them exactly as implemented.
|
|
|
|
5. Protected endpoints mostly rely on the custom middleware rather than standard `[Authorize]` attributes.
|
|
|
|
## Suggested Reading Order
|
|
|
|
If you need to understand the project quickly, read in this order:
|
|
|
|
1. `Program.cs`
|
|
2. `Controllers/ClientController.cs`
|
|
3. `Controllers/AdminController.cs`
|
|
4. `Controllers/AgentController.cs`
|
|
5. `Controllers/APIController.cs`
|
|
6. `Models/IOs/OnboardingDtos.cs`
|
|
7. `Helpers/JwtMiddleware.cs`
|
|
8. `Services/FunctionHandler/*`
|
|
9. target service file for the domain you are changing
|
|
|