package mail

import (
	"context"
	"io"
	"time"

	"github.com/ultisuite/ulti-backend/internal/api/query"
	"github.com/ultisuite/ulti-backend/internal/mail/credentials"
	"github.com/ultisuite/ulti-backend/internal/mail/listunsubscribe"
)

// ServiceAPI is the mail handler service boundary. *Service implements it in production.
type ServiceAPI interface {
	ResolveUserID(ctx context.Context, externalID string) (string, error)
	GetMailSettings(ctx context.Context, externalID string) (MailSettings, error)
	UpdateMailSettings(ctx context.Context, externalID string, req *patchMailSettingsRequest) (MailSettings, error)
	ListUnifiedFolders(ctx context.Context, externalID, accountID string, params query.ListParams) (UnifiedFoldersList, error)
	CreateUnifiedFolder(ctx context.Context, userID string, req *createUnifiedFolderRequest) (string, error)
	UpdateUnifiedFolder(ctx context.Context, externalID, folderID string, req *updateUnifiedFolderRequest) error
	DeleteUnifiedFolder(ctx context.Context, externalID, folderID string) error
	ListAccounts(ctx context.Context, externalID string, params query.ListParams) (AccountsList, error)
	CreateAccount(ctx context.Context, externalID string, req *createAccountRequest) (string, error)
	CreateAccountWithCredential(ctx context.Context, externalID string, req *createAccountRequest, cred credentials.Credential) (string, error)
	GetAccount(ctx context.Context, externalID, accountID string) (map[string]any, error)
	UpdateAccount(ctx context.Context, externalID, accountID string, req *updateAccountRequest) error
	CredentialForConnectionTest(ctx context.Context, externalID string, req *testAccountRequest) (credentials.Credential, error)
	DeleteAccount(ctx context.Context, externalID, accountID string) error
	ResanitizeAccountBodies(ctx context.Context, externalID, accountID string) (ResanitizeBodiesResult, error)
	ListMessages(ctx context.Context, externalID string, filter MessageListFilter, params query.ListParams) (MessagesList, error)
	MessageAccountID(ctx context.Context, externalID, messageID string) (string, error)
	AttachmentAccountID(ctx context.Context, externalID, attachmentID string) (string, error)
	ThreadAccessible(ctx context.Context, externalID, threadID string, scopedAccountIDs []string) (bool, error)
	GetMessage(ctx context.Context, externalID, messageID string) (map[string]any, error)
	SendMailtoListUnsubscribe(ctx context.Context, externalID, messageID string, sender MailSender) (*listunsubscribe.Mailto, error)
	UpdateLabels(ctx context.Context, externalID, messageID string, labels []string) error
	UpdateFlags(ctx context.Context, externalID, messageID string, flags []string) error
	DeleteMessage(ctx context.Context, externalID, messageID string) error
	GetThread(ctx context.Context, externalID, threadID string, scopedAccountIDs []string) (map[string]any, error)
	SendMessage(ctx context.Context, userID string, req *sendMessageRequest) (id, status string, err error)
	SendOutboxNow(ctx context.Context, userID, outboxID string) (status string, err error)
	RescheduleOutbox(ctx context.Context, userID, outboxID string, scheduledAt time.Time) (status string, err error)
	CancelScheduledOutbox(ctx context.Context, userID, outboxID string) (status string, err error)
	ListDrafts(ctx context.Context, externalID string, params query.ListParams) (DraftsList, error)
	GetDraft(ctx context.Context, externalID, draftID string) (map[string]any, error)
	CreateDraft(ctx context.Context, userID string, req *draftRequest) (string, error)
	UpdateDraft(ctx context.Context, externalID, draftID string, req *draftRequest) error
	DeleteDraft(ctx context.Context, externalID, draftID string) error
	ListRules(ctx context.Context, externalID string, params query.ListParams) (RulesList, error)
	CreateRule(ctx context.Context, userID string, req *createRuleRequest) (string, error)
	UpdateRule(ctx context.Context, externalID, ruleID string, req *updateRuleRequest) error
	DeleteRule(ctx context.Context, externalID, ruleID string) error
	SimulateRule(ctx context.Context, externalID string, req *simulateRuleRequest) (any, error)
	ListWebhooks(ctx context.Context, externalID string, params query.ListParams) (WebhooksList, error)
	CreateWebhook(ctx context.Context, externalID string, req *createWebhookRequest, method string, maxRetries int) (string, error)
	UpdateWebhook(ctx context.Context, externalID, webhookID string, req *updateWebhookRequest, method string, maxRetries int) error
	PreviewWebhookTemplate(ctx context.Context, externalID string, req *previewWebhookRequest) (map[string]any, error)
	DeleteWebhook(ctx context.Context, externalID, webhookID string) error
	ListIdentities(ctx context.Context, externalID, accountID string, params query.ListParams) (IdentitiesList, error)
	GetIdentity(ctx context.Context, externalID, identityID string) (map[string]any, error)
	CreateIdentity(ctx context.Context, externalID, accountID string, req *createIdentityRequest) (string, error)
	UpdateIdentity(ctx context.Context, externalID, identityID string, req *updateIdentityRequest) error
	DeleteIdentity(ctx context.Context, externalID, identityID string) error
	ListSignatures(ctx context.Context, externalID string, params query.ListParams) (SignaturesList, error)
	GetSignature(ctx context.Context, externalID, signatureID string) (map[string]any, error)
	CreateSignature(ctx context.Context, externalID string, req *createSignatureRequest) (string, error)
	UpdateSignature(ctx context.Context, externalID, signatureID string, req *updateSignatureRequest) error
	DeleteSignature(ctx context.Context, externalID, signatureID string) error
	ListFolders(ctx context.Context, externalID, accountID string, params query.ListParams) (FoldersList, error)
	GetFolder(ctx context.Context, externalID, folderID string) (map[string]any, error)
	CreateFolder(ctx context.Context, userID string, req *createFolderRequest) (string, error)
	UpdateFolder(ctx context.Context, externalID, folderID string, req *updateFolderRequest) error
	DeleteFolder(ctx context.Context, externalID, folderID string) error
	ListUserLabels(ctx context.Context, externalID string, params query.ListParams) (UserLabelsList, error)
	CreateUserLabel(ctx context.Context, externalID string, req *createUserLabelRequest) (string, error)
	UpdateUserLabel(ctx context.Context, externalID, labelID string, req *updateUserLabelRequest) error
	DeleteUserLabel(ctx context.Context, externalID, labelID string) error
	ReorderUserLabels(ctx context.Context, externalID string, req *reorderLabelsRequest) error
	ReorderUnifiedFolders(ctx context.Context, externalID string, req *reorderUnifiedFoldersRequest) error
	SearchMessages(ctx context.Context, externalID string, filter MessageSearchFilter, params query.ListParams) (MessageSearchResult, error)
	ListMessageAttachments(ctx context.Context, externalID, messageID string) ([]map[string]any, error)
	MessageAttachmentCIDMap(ctx context.Context, externalID, messageID string) (map[string]string, error)
	UploadMessageAttachment(ctx context.Context, externalID, messageID, filename, contentType, contentID string, isInline bool, reader io.Reader, size int64) (string, error)
	OpenAttachment(ctx context.Context, externalID, attachmentID string) (filename, contentType string, size int64, isInline bool, body io.ReadCloser, err error)
	UploadDraftAttachment(ctx context.Context, externalID, draftID, filename, contentType, contentID string, isInline bool, reader io.Reader, size int64) (string, error)
	OpenDraftAttachment(ctx context.Context, externalID, draftID, attachmentID string) (filename, contentType string, body io.ReadCloser, err error)
	SaveAttachmentToDrive(ctx context.Context, externalID, email, sub, displayName, messageID, attachmentID, folderPath string) (string, error)
	SaveMessageAttachmentsToDrive(ctx context.Context, externalID, email, sub, displayName, messageID, folderPath string) ([]map[string]any, error)
}

var _ ServiceAPI = (*Service)(nil)
