Files
tm_back/internal/domain/entities.go
T
2025-07-27 16:20:21 +03:30

390 lines
16 KiB
Go

package domain
import (
"time"
"github.com/google/uuid"
)
// Customer represents a mobile app user (customer)
type Customer struct {
ID uuid.UUID `json:"id" bson:"_id"`
Email string `json:"email" bson:"email"`
Password string `json:"-" bson:"password"` // Never serialize password
FirstName string `json:"first_name" bson:"first_name"`
LastName string `json:"last_name" bson:"last_name"`
Phone string `json:"phone" bson:"phone"`
Role CustomerRole `json:"role" bson:"role"`
CompanyID uuid.UUID `json:"company_id" bson:"company_id"`
IsActive bool `json:"is_active" bson:"is_active"`
IsVerified bool `json:"is_verified" bson:"is_verified"`
DeviceTokens []string `json:"device_tokens" bson:"device_tokens"` // For push notifications
Preferences CustomerPreferences `json:"preferences" bson:"preferences"`
LastLoginAt *time.Time `json:"last_login_at,omitempty" bson:"last_login_at,omitempty"`
CreatedAt time.Time `json:"created_at" bson:"created_at"`
UpdatedAt time.Time `json:"updated_at" bson:"updated_at"`
}
// CustomerPreferences represents customer-specific preferences
type CustomerPreferences struct {
Language string `json:"language" bson:"language"`
NotificationSettings NotificationSettings `json:"notification_settings" bson:"notification_settings"`
TenderAlerts bool `json:"tender_alerts" bson:"tender_alerts"`
EmailNotifications bool `json:"email_notifications" bson:"email_notifications"`
PushNotifications bool `json:"push_notifications" bson:"push_notifications"`
PreferredCategories []string `json:"preferred_categories" bson:"preferred_categories"`
}
// NotificationSettings represents notification preferences
type NotificationSettings struct {
NewTenders bool `json:"new_tenders" bson:"new_tenders"`
DeadlineReminder bool `json:"deadline_reminder" bson:"deadline_reminder"`
StatusUpdates bool `json:"status_updates" bson:"status_updates"`
SystemAlerts bool `json:"system_alerts" bson:"system_alerts"`
}
// CustomerRole defines roles for mobile app users
type CustomerRole string
const (
CustomerRoleUser CustomerRole = "customer_user" // Regular customer
CustomerRoleManager CustomerRole = "customer_manager" // Company manager
)
// User represents a panel user (admin/staff)
type User struct {
ID uuid.UUID `json:"id" bson:"_id"`
Email string `json:"email" bson:"email"`
Password string `json:"-" bson:"password"` // Never serialize password
FirstName string `json:"first_name" bson:"first_name"`
LastName string `json:"last_name" bson:"last_name"`
Role UserRole `json:"role" bson:"role"`
Department string `json:"department" bson:"department"`
IsActive bool `json:"is_active" bson:"is_active"`
Permissions []string `json:"permissions" bson:"permissions"`
LastLoginAt *time.Time `json:"last_login_at,omitempty" bson:"last_login_at,omitempty"`
CreatedBy *uuid.UUID `json:"created_by,omitempty" bson:"created_by,omitempty"`
CreatedAt time.Time `json:"created_at" bson:"created_at"`
UpdatedAt time.Time `json:"updated_at" bson:"updated_at"`
}
// UserRole defines roles for panel users
type UserRole string
const (
UserRoleAdmin UserRole = "admin" // Full system administrator
UserRoleModerator UserRole = "moderator" // Moderator with limited admin access
UserRoleSupport UserRole = "support" // Support user with read-only access
UserRoleAnalyst UserRole = "analyst" // Data analyst with reporting access
)
// Customer methods
func (c *Customer) HasRole(role CustomerRole) bool {
return c.Role == role
}
func (c *Customer) IsManager() bool {
return c.Role == CustomerRoleManager
}
func (c *Customer) CanAccessCompanySettings() bool {
return c.IsActive && c.IsVerified && c.IsManager()
}
func (c *Customer) FullName() string {
return c.FirstName + " " + c.LastName
}
// User methods
func (u *User) HasRole(role UserRole) bool {
return u.Role == role
}
func (u *User) HasAnyRole(roles ...UserRole) bool {
for _, role := range roles {
if u.Role == role {
return true
}
}
return false
}
func (u *User) HasPermission(permission string) bool {
for _, perm := range u.Permissions {
if perm == permission {
return true
}
}
return false
}
func (u *User) IsAdmin() bool {
return u.Role == UserRoleAdmin
}
func (u *User) CanManageUsers() bool {
return u.IsActive && (u.Role == UserRoleAdmin || u.HasPermission("manage_users"))
}
func (u *User) CanManageTenders() bool {
return u.IsActive && (u.Role == UserRoleAdmin || u.Role == UserRoleModerator || u.HasPermission("manage_tenders"))
}
func (u *User) CanViewReports() bool {
return u.IsActive && (u.Role == UserRoleAdmin || u.Role == UserRoleAnalyst || u.HasPermission("view_reports"))
}
func (u *User) FullName() string {
return u.FirstName + " " + u.LastName
}
// Company represents a company profile
type Company struct {
ID uuid.UUID `json:"id" bson:"_id"`
Name string `json:"name" bson:"name"`
Description string `json:"description" bson:"description"`
Industry string `json:"industry" bson:"industry"`
Country string `json:"country" bson:"country"`
Website string `json:"website" bson:"website"`
Keywords []string `json:"keywords" bson:"keywords"`
Products []string `json:"products" bson:"products"`
Services []string `json:"services" bson:"services"`
Capabilities []string `json:"capabilities" bson:"capabilities"`
Documents []Document `json:"documents" bson:"documents"`
Interests InterestProfile `json:"interests" bson:"interests"`
CreatedAt time.Time `json:"created_at" bson:"created_at"`
UpdatedAt time.Time `json:"updated_at" bson:"updated_at"`
}
// InterestProfile represents company's tender interests
type InterestProfile struct {
Keywords []string `json:"keywords" bson:"keywords"`
Industries []string `json:"industries" bson:"industries"`
CPVCodes []string `json:"cpv_codes" bson:"cpv_codes"`
MinBudget *float64 `json:"min_budget,omitempty" bson:"min_budget,omitempty"`
MaxBudget *float64 `json:"max_budget,omitempty" bson:"max_budget,omitempty"`
Regions []string `json:"regions" bson:"regions"`
Embeddings []float32 `json:"-" bson:"embeddings"` // AI embeddings for matching
UpdatedAt time.Time `json:"updated_at" bson:"updated_at"`
}
// Tender represents a tender opportunity
type Tender struct {
ID uuid.UUID `json:"id" bson:"_id"`
Title string `json:"title" bson:"title"`
Description string `json:"description" bson:"description"`
Summary string `json:"summary" bson:"summary"`
Type TenderType `json:"type" bson:"type"`
Status TenderStatus `json:"status" bson:"status"`
PublicationDate time.Time `json:"publication_date" bson:"publication_date"`
Deadline time.Time `json:"deadline" bson:"deadline"`
Budget *float64 `json:"budget,omitempty" bson:"budget,omitempty"`
Currency string `json:"currency" bson:"currency"`
Region string `json:"region" bson:"region"`
Country string `json:"country" bson:"country"`
CPVCodes []string `json:"cpv_codes" bson:"cpv_codes"`
Categories []string `json:"categories" bson:"categories"`
Keywords []string `json:"keywords" bson:"keywords"`
Tags []string `json:"tags" bson:"tags"`
Language string `json:"language" bson:"language"`
SourceURL string `json:"source_url" bson:"source_url"`
SourceName string `json:"source_name" bson:"source_name"`
Documents []TenderDocument `json:"documents" bson:"documents"`
Requirements []Requirement `json:"requirements" bson:"requirements"`
Embeddings []float32 `json:"-" bson:"embeddings"` // AI embeddings for matching
ProcessedAt *time.Time `json:"processed_at,omitempty" bson:"processed_at,omitempty"`
CreatedAt time.Time `json:"created_at" bson:"created_at"`
UpdatedAt time.Time `json:"updated_at" bson:"updated_at"`
}
// TenderType defines types of tenders
type TenderType string
const (
TenderTypeRFI TenderType = "RFI" // Request for Information
TenderTypeRFP TenderType = "RFP" // Request for Proposal
TenderTypeRFQ TenderType = "RFQ" // Request for Quote
TenderTypeTender TenderType = "TENDER" // Public Tender
)
// TenderStatus defines tender statuses
type TenderStatus string
const (
TenderStatusActive TenderStatus = "active"
TenderStatusExpired TenderStatus = "expired"
TenderStatusCancelled TenderStatus = "cancelled"
TenderStatusAwarded TenderStatus = "awarded"
)
// TenderDocument represents documents associated with a tender
type TenderDocument struct {
ID uuid.UUID `json:"id" bson:"id"`
Name string `json:"name" bson:"name"`
Type DocumentType `json:"type" bson:"type"`
URL string `json:"url" bson:"url"`
LocalPath string `json:"local_path" bson:"local_path"`
Size int64 `json:"size" bson:"size"`
ContentType string `json:"content_type" bson:"content_type"`
Checksum string `json:"checksum" bson:"checksum"`
Downloaded bool `json:"downloaded" bson:"downloaded"`
DownloadedAt *time.Time `json:"downloaded_at,omitempty" bson:"downloaded_at,omitempty"`
}
// Requirement represents tender requirements
type Requirement struct {
ID uuid.UUID `json:"id" bson:"id"`
Type RequirementType `json:"type" bson:"type"`
Description string `json:"description" bson:"description"`
Mandatory bool `json:"mandatory" bson:"mandatory"`
Category string `json:"category" bson:"category"`
}
// RequirementType defines types of requirements
type RequirementType string
const (
RequirementTypeLegal RequirementType = "legal"
RequirementTypeTechnical RequirementType = "technical"
RequirementTypeFinancial RequirementType = "financial"
RequirementTypeExperience RequirementType = "experience"
)
// Document represents uploaded company documents
type Document struct {
ID uuid.UUID `json:"id" bson:"id"`
Name string `json:"name" bson:"name"`
Type DocumentType `json:"type" bson:"type"`
Category string `json:"category" bson:"category"`
Description string `json:"description" bson:"description"`
FilePath string `json:"file_path" bson:"file_path"`
Size int64 `json:"size" bson:"size"`
ContentType string `json:"content_type" bson:"content_type"`
Checksum string `json:"checksum" bson:"checksum"`
ExpiryDate *time.Time `json:"expiry_date,omitempty" bson:"expiry_date,omitempty"`
Keywords []string `json:"keywords" bson:"keywords"`
UploadedBy uuid.UUID `json:"uploaded_by" bson:"uploaded_by"`
CreatedAt time.Time `json:"created_at" bson:"created_at"`
UpdatedAt time.Time `json:"updated_at" bson:"updated_at"`
}
// DocumentType defines types of documents
type DocumentType string
const (
DocumentTypePDF DocumentType = "pdf"
DocumentTypeWord DocumentType = "word"
DocumentTypeExcel DocumentType = "excel"
DocumentTypeImage DocumentType = "image"
DocumentTypeCertificate DocumentType = "certificate"
DocumentTypeLicense DocumentType = "license"
DocumentTypeContract DocumentType = "contract"
DocumentTypeCatalog DocumentType = "catalog"
)
// TenderSource represents tender source configuration
type TenderSource struct {
ID uuid.UUID `json:"id" bson:"_id"`
Name string `json:"name" bson:"name"`
BaseURL string `json:"base_url" bson:"base_url"`
Type SourceType `json:"type" bson:"type"`
AuthRequired bool `json:"auth_required" bson:"auth_required"`
CredentialsID *uuid.UUID `json:"credentials_id,omitempty" bson:"credentials_id,omitempty"`
CheckInterval time.Duration `json:"check_interval" bson:"check_interval"`
CategoryTags []string `json:"category_tags" bson:"category_tags"`
Region string `json:"region" bson:"region"`
Language string `json:"language" bson:"language"`
Status SourceStatus `json:"status" bson:"status"`
LastCheckedAt *time.Time `json:"last_checked_at,omitempty" bson:"last_checked_at,omitempty"`
Configuration SourceConfiguration `json:"configuration" bson:"configuration"`
CreatedAt time.Time `json:"created_at" bson:"created_at"`
UpdatedAt time.Time `json:"updated_at" bson:"updated_at"`
}
// SourceType defines types of tender sources
type SourceType string
const (
SourceTypeAPI SourceType = "api"
SourceTypeHTML SourceType = "html"
SourceTypeJS SourceType = "js"
SourceTypePDF SourceType = "pdf"
SourceTypeRSS SourceType = "rss"
)
// SourceStatus defines tender source statuses
type SourceStatus string
const (
SourceStatusActive SourceStatus = "active"
SourceStatusInactive SourceStatus = "inactive"
SourceStatusError SourceStatus = "error"
)
// SourceConfiguration holds source-specific configuration
type SourceConfiguration struct {
Headers map[string]string `json:"headers,omitempty" bson:"headers,omitempty"`
QueryParams map[string]string `json:"query_params,omitempty" bson:"query_params,omitempty"`
Selectors map[string]string `json:"selectors,omitempty" bson:"selectors,omitempty"`
PaginationKey string `json:"pagination_key,omitempty" bson:"pagination_key,omitempty"`
MaxPages int `json:"max_pages,omitempty" bson:"max_pages,omitempty"`
RateLimitDelay time.Duration `json:"rate_limit_delay,omitempty" bson:"rate_limit_delay,omitempty"`
}
// TenderMatch represents AI-powered tender recommendations
type TenderMatch struct {
ID uuid.UUID `json:"id" bson:"_id"`
CompanyID uuid.UUID `json:"company_id" bson:"company_id"`
TenderID uuid.UUID `json:"tender_id" bson:"tender_id"`
Score float64 `json:"score" bson:"score"`
Explanation string `json:"explanation" bson:"explanation"`
Tags []string `json:"tags" bson:"tags"`
Status MatchStatus `json:"status" bson:"status"`
UserAction *UserAction `json:"user_action,omitempty" bson:"user_action,omitempty"`
CreatedAt time.Time `json:"created_at" bson:"created_at"`
UpdatedAt time.Time `json:"updated_at" bson:"updated_at"`
}
// MatchStatus defines tender match statuses
type MatchStatus string
const (
MatchStatusPending MatchStatus = "pending"
MatchStatusViewed MatchStatus = "viewed"
MatchStatusLiked MatchStatus = "liked"
MatchStatusDisliked MatchStatus = "disliked"
MatchStatusApplied MatchStatus = "applied"
)
// UserAction represents user interaction with tender matches
type UserAction struct {
Action MatchStatus `json:"action" bson:"action"`
Timestamp time.Time `json:"timestamp" bson:"timestamp"`
UserID uuid.UUID `json:"user_id" bson:"user_id"`
}
// Notification represents system notifications
type Notification struct {
ID uuid.UUID `json:"id" bson:"_id"`
UserID uuid.UUID `json:"user_id" bson:"user_id"`
CompanyID uuid.UUID `json:"company_id" bson:"company_id"`
Type NotificationType `json:"type" bson:"type"`
Title string `json:"title" bson:"title"`
Message string `json:"message" bson:"message"`
Data map[string]any `json:"data,omitempty" bson:"data,omitempty"`
Read bool `json:"read" bson:"read"`
Sent bool `json:"sent" bson:"sent"`
SentAt *time.Time `json:"sent_at,omitempty" bson:"sent_at,omitempty"`
CreatedAt time.Time `json:"created_at" bson:"created_at"`
}
// NotificationType defines types of notifications
type NotificationType string
const (
NotificationTypeNewTender NotificationType = "new_tender"
NotificationTypeDeadline NotificationType = "deadline_reminder"
NotificationTypeStatusUpdate NotificationType = "status_update"
NotificationTypeSystemAlert NotificationType = "system_alert"
)