import {z} from 'zod' export type GetApiRestApiV1InvestorProgramTradersOptions = {baseUrl?: string | undefined, ApiKeyAuth?: string | undefined, fetch?: typeof fetch | undefined}; export const channelHealthDTO = z.object({autoDisabled: z.boolean().optional(), consecutiveFailures: z.number().int().optional(), lastError: z.string().optional(), lastFailureAt: z.string().optional(), lastSuccessAt: z.string().optional(), throttled: z.boolean().optional()}); export const telegramRecipientDTO = z.object({enabled: z.boolean().optional(), health: channelHealthDTO.optional(), name: z.string().optional(), useAlias: z.boolean().optional(), username: z.string(), verified: z.boolean().optional()}); export const notificationCooldownDTO = z.object({enabled: z.boolean().optional(), minutes: z.number().int().optional()}); export const notificationDigestDTO = z.object({enabled: z.boolean().optional(), errorsImmediate: z.boolean().optional(), windowSeconds: z.number().int().optional()}); export const logTypeDTO = z.object({id: z.number().int(), name: z.string().optional()}); export const notificationQuietHoursDTO = z.object({activeDays: z.array(z.number().int()).optional(), after: z.string().optional(), allowErrors: z.boolean().optional(), enabled: z.boolean().optional(), from: z.string().optional(), timeZone: z.string().optional(), to: z.string().optional()}); export const notificationTargetDTO = z.object({featureId: z.string().optional(), recipient: z.string().optional()}); export const proxyRegionDTO = z.object({id: z.number().int(), name: z.string().optional()}); export const proxyDTO = z.object({id: z.number().int().optional(), ipAddress: z.string().optional(), region: proxyRegionDTO.optional(), usedByAccounts: z.array(z.string()).optional()}); export const featureTpSlManagementDTO: z.ZodType = z.object({additionalSlPoints: z.number().int().optional(), additionalTpPoints: z.number().int().optional(), adjustWithMasterDistance: z.boolean().optional(), attachTpSlAfterOpen: z.boolean().optional(), blockTradeWithoutTpSl: z.boolean().optional(), fixedSlInPoints: z.number().int().optional(), fixedTpInPoints: z.number().int().optional(), lockTpSl: z.boolean().optional(), masterTpSlPriority: z.boolean().optional(), removeSl: z.boolean().optional(), removeTp: z.boolean().optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureTpSlManagementDTO)).optional()}); export const contactDTO = z.object({discord: z.string().max(100).optional(), email: z.string().max(255).optional(), telegram: z.string().max(100).optional(), website: z.string().max(500).optional(), whatsapp: z.string().max(50).optional()}); export const scaleTypeDTO = z.object({id: z.number().int(), name: z.string().optional()}); export const copierDTO = z.object({active: z.boolean().optional(), copyMagicNumber: z.boolean().optional(), copyOpenPositions: z.boolean().optional(), copyOriginalComment: z.boolean().optional(), copyStopLoss: z.boolean().optional(), copyTakeProfit: z.boolean().optional(), created: z.string().optional(), customComment: z.string().max(20).optional(), customMagicNumber: z.number().int().optional(), fixMasterBalanceAndEquity: z.number().int().optional(), fixSlaveBalanceAndEquity: z.number().int().optional(), fixedLotSize: z.number().optional(), forceMinTrade: z.boolean().optional(), forcePositionLotSize: z.boolean().optional(), fromAccountAlias: z.string().optional(), fromAccountId: z.string().optional(), fromStrategyId: z.string().optional(), fromStrategyName: z.string().optional(), hideComment: z.boolean().optional(), id: z.string().optional(), ignoreContractSize: z.boolean().optional(), ignoreCurrency: z.boolean().optional(), martingaleStrategy: z.boolean().optional(), maxLotSize: z.number().optional(), maxOpenPositions: z.number().int().optional(), maxSlippage: z.number().int().optional(), maximumLot: z.number().optional(), minVolumeSafetySkipThresholdMultiplier: z.number().gte(0).lte(999.99).optional(), monitorOnly: z.boolean().optional(), multiplier: z.number().gte(0.001).lte(999.999).optional(), openRetry: z.boolean().optional(), openRetryTimeoutInMinutes: z.number().int().optional(), reverse: z.boolean().optional(), scaleType: scaleTypeDTO.optional(), skipPendingOrders: z.boolean().optional(), toAccountId: z.string().optional(), toStrategyId: z.string().optional()}); export const regionDTO = z.object({id: z.number().int(), name: z.string().optional()}); export const featureMaxOpenPositionsDTO: z.ZodType = z.object({maxOpenPositions: z.number().int().optional(), maxPositionsInTimeWindow: z.number().int().optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureMaxOpenPositionsDTO)).optional(), timeWindowSeconds: z.number().int().optional()}); export const featureMaxLotSizeDTO: z.ZodType = z.object({checkMasterLotSize: z.boolean().optional(), maxLotSize: z.number().optional(), skipIfExceedsMax: z.boolean().optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureMaxLotSizeDTO)).optional()}); export const multiplierRuleDTO = z.object({belowMinimumLot: z.enum(["ROUND_UP", "SKIP"]).optional(), comment: z.array(z.string()).optional(), fixedLotSize: z.number().optional(), magicNumber: z.array(z.string()).optional(), maxLotSize: z.number().optional(), multiplier: z.number().gte(0.001).lte(999.999), name: z.string().max(20).optional(), scaleType: scaleTypeDTO.optional(), skip: z.boolean().optional()}); export const featureMultiplierDTO: z.ZodType = z.object({fixMasterBalanceAndEquity: z.number().int().optional(), fixSlaveBalanceAndEquity: z.number().int().optional(), fixedLotSize: z.number().optional(), multiplier: z.number().gte(0.001).lte(999.999).optional(), rules: z.array(multiplierRuleDTO).optional(), scaleType: scaleTypeDTO.optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureMultiplierDTO)).optional()}); export const featureMaximumLotDTO: z.ZodType = z.object({maximumLot: z.number().optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureMaximumLotDTO)).optional()}); export const featureBreakEvenDTO: z.ZodType = z.object({reverse: z.boolean().optional(), reverseStopLossInPoints: z.number().int().optional(), reverseTriggerInPoints: z.number().int().optional(), stopLossInPoints: z.number().int().optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureBreakEvenDTO)).optional(), triggerInPoints: z.number().int().optional()}); export const featureTrailingStopDTO: z.ZodType = z.object({activationThresholdPercentage: z.number().optional(), activationThresholdPoints: z.number().int().optional(), initialStopLossPoints: z.number().int().optional(), minimumDistancePoints: z.number().int().optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureTrailingStopDTO)).optional(), trailingStepPercentage: z.number().optional(), trailingStepPoints: z.number().int().optional()}); export const tradingWindowDTO = z.object({activeDays: z.array(z.number().int()).optional(), endTime: z.string(), startTime: z.string()}); export const featureTradingWindowsDTO: z.ZodType = z.object({closePositionsAtWindowEnd: z.boolean().optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureTradingWindowsDTO)).optional(), temporarilySkipUntilNextWindow: z.boolean().optional(), tradingWindows: z.array(tradingWindowDTO)}); export const featureDelayedExecutionDTO: z.ZodType = z.object({maxDelayClose: z.number().gte(0).lte(3600).optional(), maxDelayOpen: z.number().gte(0).lte(3600).optional(), minDelayClose: z.number().gte(0).lte(3600).optional(), minDelayOpen: z.number().gte(0).lte(3600).optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureDelayedExecutionDTO)).optional()}); export const accountTypeDTO = z.object({id: z.number().int(), name: z.string().optional()}); export const copierStateDTO = z.object({active: z.boolean().optional(), monitorOnly: z.boolean().optional()}); export const cryptoWalletConfigDTO = z.object({btcXpub: z.string().optional(), custodyMode: z.string().optional(), enabledCoins: z.array(z.string()).optional(), encryptedSeed: z.string().optional(), ethXpub: z.string().optional(), sweepDestinationByNetwork: z.record(z.string(), z.string()).optional(), tronXpub: z.string().optional()}); export const featureMinimumHoldingTimeDTO: z.ZodType = z.object({minimumHoldSeconds: z.number().int().gte(0).optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureMinimumHoldingTimeDTO)).optional()}); export const featureSkipPositionDTO: z.ZodType = z.object({ifSlNotDefined: z.boolean().optional(), ifTpNotDefined: z.boolean().optional(), logicOperatorTpSl: z.enum(["AND", "OR", "AND", "OR"]).optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureSkipPositionDTO)).optional()}); export const featureRiskPerTradeDTO: z.ZodType = z.object({absoluteRisk: z.number().optional(), aggregateRiskPerSymbol: z.boolean().optional(), autoCloseOnRiskThresholdReached: z.boolean().optional(), correctLotSizeBasedOnTheStopLoss: z.boolean().optional(), missingStopLossBehavior: z.enum(["OPEN_UNADJUSTED", "OPEN_MINIMUM_VOLUME", "SKIP_TRADE"]).optional(), relativeRisk: z.number().optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureRiskPerTradeDTO)).optional(), tickValue: z.number().optional(), tickValueAutomaticAdjustement: z.boolean().optional(), waitForStopLossSeconds: z.number().int().optional()}); export const featureLiveDelayDTO: z.ZodType = z.object({resetIntervalMinutes: z.number().int().lte(1440).optional(), resetOnPositionClose: z.boolean().optional(), skipOrdersCount: z.number().int().optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureLiveDelayDTO)).optional(), trackByDirection: z.boolean().optional()}); export const featureMasanielloDTO: z.ZodType = z.object({assumedPointRisk: z.number().gte(1).lte(10000).optional(), autoResetOnSeriesComplete: z.boolean().optional(), autoTuneBoundsValid: z.boolean().optional(), bankrollBase: z.enum(["BALANCE", "EQUITY", "FREE_MARGIN"]), bankrollPercentage: z.number().gte(0.1).lte(100).optional(), cooldownAfterResetMinutes: z.number().int().gte(0).lte(1440).optional(), excludeBreakEvenTrades: z.boolean().optional(), expectedLossRMultiple: z.number().gte(-1).lte(0).optional(), expectedPayoutFactor: z.number().gte(0.01).lte(5).optional(), expectedRMultiple: z.number().gte(0.05).lte(10).optional(), expectedWins: z.number().int().gte(1).lte(100).optional(), expectedWinsValid: z.boolean().optional(), lotRoundingMode: z.enum(["DOWN", "UP", "NEAREST"]), lotStep: z.number().gte(0.0001).lte(100).optional(), maxConsecutiveLosses: z.number().int().gte(0).lte(50).optional(), maxExpectedWins: z.number().int().gte(1).lte(100).optional(), maximumLotSize: z.number().gte(0.01).lte(1000).optional(), minExpectedWins: z.number().int().gte(1).lte(100).optional(), minimumLotSize: z.number().gte(0).lte(100).optional(), minimumTradesForHistoricalWinRate: z.number().int().gte(1).lte(500).optional(), outcomePolicy: z.enum(["THRESHOLD", "SIGN", "R_BASED"]), partialWinPolicy: z.enum(["IGNORE", "COUNT_AS_WIN", "COUNT_AS_LOSS", "PROPORTIONAL"]), payoutModel: z.enum(["R_MULTIPLE", "PAYOUT_FACTOR", "REALIZED_R"]), resetOnBankrollDepleted: z.boolean().optional(), resetOnTargetReached: z.boolean().optional(), statisticsLookBackDays: z.number().int().gte(0).lte(365).optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureMasanielloDTO)).optional(), targetProfitPercentage: z.number().gte(1).lte(1000).optional(), totalEvents: z.number().int().gte(2).lte(100).optional(), useHistoricalWinRate: z.boolean().optional(), winRateSmoothingFactor: z.number().gte(0).lte(1).optional(), winThresholdBase: z.enum(["RISK", "NOTIONAL", "ABSOLUTE"]), winThresholdPercentage: z.number().gte(0).lte(100).optional()}); export const featureTradeGuardrailsDTO: z.ZodType = z.object({aggregatePerSymbol: z.boolean().optional(), enabled: z.boolean().optional(), maxLotSizeThreshold: z.number().optional(), maxOpenTimeSeconds: z.number().int().optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureTradeGuardrailsDTO)).optional()}); export const featureMartingaleStrategyDTO: z.ZodType = z.object({enableMartingaleStrategy: z.boolean().optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureMartingaleStrategyDTO)).optional()}); export const telegramChatDTO = z.object({chatId: z.number().int().optional(), chatType: z.string().optional(), forumTopicId: z.number().int().optional(), memberCount: z.number().int().optional(), title: z.string().optional(), username: z.string().optional()}); export const featureTradeCooldownDTO: z.ZodType = z.object({cooldownAnchor: z.enum(["CLOSE", "OPEN"]).optional(), cooldownMinutes: z.number().int().lte(1440).optional(), correlationGroups: z.array(z.array(z.string())).optional(), correlationMode: z.enum(["NONE", "CUSTOM_GROUPS"]).optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureTradeCooldownDTO)).optional(), trackByDirection: z.boolean().optional()}); export const symbolCurrencyMappingDTO = z.object({currencies: z.array(z.string()).optional(), pattern: z.string().optional()}); export const newsEventSelectionDTO = z.object({categoryBlacklist: z.array(z.string()).optional(), currencyWhitelist: z.array(z.string()).optional(), eventTitleBlacklist: z.array(z.string()).optional(), eventTitleWhitelist: z.array(z.string()).optional(), includeGlobalEvents: z.boolean().optional(), includeHolidays: z.boolean().optional(), minImpact: z.enum(["HOLIDAY", "LOW", "MEDIUM", "HIGH"]).optional(), symbolMappings: z.array(symbolCurrencyMappingDTO).optional()}); export const featureNewsFilterDTO: z.ZodType = z.object({blackoutAfterMinutes: z.number().int().lte(240).optional(), blackoutBeforeMinutes: z.number().int().lte(240).optional(), blockModifications: z.boolean().optional(), dailyAgendaAtUtc: z.string().optional(), enableHolidayMode: z.boolean().optional(), enableNewsFilter: z.boolean().optional(), events: newsEventSelectionDTO.optional(), holidayAction: z.enum(["NONE", "REDUCE_SIZE", "SKIP_NEW_OPENS"]).optional(), holidayCountries: z.array(z.string()).optional(), holidaySizeFactorPercent: z.number().int().lte(100).optional(), logSkippedTrades: z.boolean().optional(), notificationTargets: z.array(notificationTargetDTO).optional(), notifyOnEvents: z.array(z.enum(["POSITION_OPENED", "POSITION_CLOSED", "POSITION_MODIFIED", "HISTORY_UPDATED", "TRADE_APPROVAL_REQUIRED", "TRADE_APPROVED", "UNMANAGED_POSITION_DETECTED", "COPY_SKIPPED", "ORDER_REJECTED", "INSUFFICIENT_MARGIN", "TRADE_FAILED_DISCONNECTED", "COPY_FAILED", "DUPLICATE_POSITION_DETECTED", "ACCOUNT_STARTED", "ACCOUNT_STOPPED", "ACCOUNT_CONNECTED", "ACCOUNT_DISCONNECTED", "ACCOUNT_LOGIN_FAILED", "ACCOUNT_TOKEN_EXPIRING", "ACCOUNT_RESTRICTED", "ACCOUNT_FALLBACK_MODE", "RISK_LIMIT_REACHED", "PROFIT_TARGET_REACHED", "LOSS_PROTECTED_EXIT", "GUARDRAIL_TRIGGERED", "COPIER_STOPPED_BY_RISK", "LIMIT_RESET", "BALANCE_ADJUSTMENT_DETECTED", "NEWS_EVENT_UPCOMING", "NEWS_EVENT_RELEASED", "NEWS_FILTER_ACTION_SCHEDULED", "NEWS_FILTER_ACTION_IMMINENT", "NEWS_FILTER_DAILY_AGENDA", "NEWS_FILTER_SKIPPED_COPY", "NEWS_FILTER_CLOSED_POSITION", "NEWS_FILTER_REOPENED", "NEWS_FILTER_REOPEN_SKIPPED", "NEWS_FILTER_HOLIDAY_MODE", "MARKET_NEWS_HIGH_IMPACT", "SIGNAL_RECEIVED", "SIGNAL_EXECUTED", "SIGNAL_REJECTED", "SIGNAL_AI_LIMIT_REACHED", "SIGNAL_SUBSCRIPTION_ENDED", "CONFIGURATION_ERROR", "CONFIGURATION_CHANGED", "MAINTENANCE_WINDOW", "PROXY_ISSUE", "EXPERT_ADVISOR_STARTED", "EXPERT_ADVISOR_STOPPED", "EXPERT_ADVISOR_WARNING", "LOG_RATE_LIMITED", "NOTIFICATION_CHANNEL_DISABLED", "GENERAL"])).optional(), sendDailyAgenda: z.boolean().optional(), skipMarketOrders: z.boolean().optional(), skipPendingOrders: z.boolean().optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureNewsFilterDTO)).optional(), warnBeforeMinutes: z.array(z.number().int()).optional(), warnOnlyIfExposed: z.boolean().optional()}); export const featureNewsProtectionDTO: z.ZodType = z.object({cancelPendingOrders: z.boolean().optional(), closeBeforeMinutes: z.number().int().gte(1).lte(120).optional(), closeOnlyLosingPositions: z.boolean().optional(), dailyAgendaAtUtc: z.string().optional(), enableNewsProtection: z.boolean().optional(), events: newsEventSelectionDTO.optional(), minProfitToClose: z.number().optional(), notificationTargets: z.array(notificationTargetDTO).optional(), notifyOnEvents: z.array(z.enum(["POSITION_OPENED", "POSITION_CLOSED", "POSITION_MODIFIED", "HISTORY_UPDATED", "TRADE_APPROVAL_REQUIRED", "TRADE_APPROVED", "UNMANAGED_POSITION_DETECTED", "COPY_SKIPPED", "ORDER_REJECTED", "INSUFFICIENT_MARGIN", "TRADE_FAILED_DISCONNECTED", "COPY_FAILED", "DUPLICATE_POSITION_DETECTED", "ACCOUNT_STARTED", "ACCOUNT_STOPPED", "ACCOUNT_CONNECTED", "ACCOUNT_DISCONNECTED", "ACCOUNT_LOGIN_FAILED", "ACCOUNT_TOKEN_EXPIRING", "ACCOUNT_RESTRICTED", "ACCOUNT_FALLBACK_MODE", "RISK_LIMIT_REACHED", "PROFIT_TARGET_REACHED", "LOSS_PROTECTED_EXIT", "GUARDRAIL_TRIGGERED", "COPIER_STOPPED_BY_RISK", "LIMIT_RESET", "BALANCE_ADJUSTMENT_DETECTED", "NEWS_EVENT_UPCOMING", "NEWS_EVENT_RELEASED", "NEWS_FILTER_ACTION_SCHEDULED", "NEWS_FILTER_ACTION_IMMINENT", "NEWS_FILTER_DAILY_AGENDA", "NEWS_FILTER_SKIPPED_COPY", "NEWS_FILTER_CLOSED_POSITION", "NEWS_FILTER_REOPENED", "NEWS_FILTER_REOPEN_SKIPPED", "NEWS_FILTER_HOLIDAY_MODE", "MARKET_NEWS_HIGH_IMPACT", "SIGNAL_RECEIVED", "SIGNAL_EXECUTED", "SIGNAL_REJECTED", "SIGNAL_AI_LIMIT_REACHED", "SIGNAL_SUBSCRIPTION_ENDED", "CONFIGURATION_ERROR", "CONFIGURATION_CHANGED", "MAINTENANCE_WINDOW", "PROXY_ISSUE", "EXPERT_ADVISOR_STARTED", "EXPERT_ADVISOR_STOPPED", "EXPERT_ADVISOR_WARNING", "LOG_RATE_LIMITED", "NOTIFICATION_CHANNEL_DISABLED", "GENERAL"])).optional(), reopenAfterMinutes: z.number().int().gte(1).lte(240).optional(), reopenExpiryMinutes: z.number().int().gte(1).lte(1440).optional(), reopenMaxAdverseMovePips: z.number().int().optional(), reopenMaxSpreadPoints: z.number().int().optional(), reopenMode: z.enum(["NONE", "SAME_VOLUME", "RESYNC_WITH_MASTER"]).optional(), reopenOnlyIfMasterStillOpen: z.boolean().optional(), sendDailyAgenda: z.boolean().optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureNewsProtectionDTO)).optional(), warnBeforeMinutes: z.array(z.number().int()).optional(), warnImminent: z.boolean().optional(), warnOnlyIfExposed: z.boolean().optional()}); export const featureMarginCapDTO: z.ZodType = z.object({behavior: z.enum(["REDUCE_LOT_SIZE", "SKIP_TRADE"]).optional(), leverageOverride: z.number().int().optional(), marginCapPercentage: z.number().optional(), scope: z.enum(["CUMULATIVE", "PER_TRADE"]).optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureMarginCapDTO)).optional()}); export const featureSpreadFilterDTO: z.ZodType = z.object({mode: z.enum(["POINTS", "PERCENTAGE_OF_PRICE"]).optional(), onMissingPrice: z.enum(["ALLOW", "BLOCK"]).optional(), retryOnBlock: z.boolean().optional(), source: z.enum(["MASTER", "SLAVE"]).optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureSpreadFilterDTO)).optional(), threshold: z.number().optional()}); export const featureOverallTargetDTO: z.ZodType = z.object({adjustReferenceOnBalanceChange: z.boolean().optional(), overallLossLimit: z.number().gte(0).lte(100).optional(), overallLossLimitAmount: z.number().gte(0).optional(), overallProfitTarget: z.number().gte(0).lte(1000).optional(), overallProfitTargetAmount: z.number().gte(0).optional(), pauseInsteadOfClose: z.boolean().optional(), referenceBalance: z.number().gte(0).optional(), referenceMode: z.enum(["EQUITY", "BALANCE", "EQUITY", "BALANCE"]).optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureOverallTargetDTO)).optional()}); export const closeReopenScheduleDTO = z.object({activeDays: z.array(z.number().int()).optional(), closeTime: z.string(), enabled: z.boolean().optional(), label: z.string().max(50).optional(), reopenDayOffset: z.number().int().lte(7).optional(), reopenTime: z.string().optional(), skipNewTradesUntilReopen: z.boolean().optional()}); export const featureScheduledCloseReopenDTO: z.ZodType = z.object({enabled: z.boolean().optional(), includePendingOrders: z.boolean().optional(), maxLossToClosePoints: z.number().int().optional(), maxReopenSlippagePoints: z.number().int().optional(), onlyCloseInProfit: z.boolean().optional(), onlyCloseNegativeSwapPositions: z.boolean().optional(), restoreStopLossTakeProfit: z.boolean().optional(), schedules: z.array(closeReopenScheduleDTO), skipReopenIfMasterClosed: z.boolean().optional(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureScheduledCloseReopenDTO)).optional()}); export const featureLossProtectedExitDTO: z.ZodType = z.object({breakevenOffsetPoints: z.number().int().optional(), closeAllDetectionWindowSeconds: z.number().int().gte(1).lte(10).optional(), enabled: z.boolean(), forceTpToBreakeven: z.boolean().optional(), lossToleranceAbsolute: z.number().gte(0).optional(), lossTolerancePercent: z.number().gte(0).lte(100), protectionMode: z.enum(["CLOSE_ALL_ONLY", "EVERY_CLOSE"]).optional(), setBreakevenTakeProfit: z.boolean(), symbolsConfiguration: z.record(z.string(), z.lazy(() => featureLossProtectedExitDTO)).optional()}); export const featureSettingDTO = z.union([z.object({recipients: z.array(telegramRecipientDTO).optional(), schemaVersion: z.number().int().optional()}), z.object({configurationUrl: z.string().optional(), enabled: z.boolean().optional(), health: channelHealthDTO.optional(), kind: z.string().optional(), name: z.string(), slackChannelId: z.string().optional(), slackChannelName: z.string().optional(), slackTeamId: z.string().optional(), slackTeamName: z.string().optional(), webhookUrl: z.string().optional()}), z.object({enabled: z.boolean().optional(), health: channelHealthDTO.optional(), kind: z.string().optional(), name: z.string(), webhookUrl: z.string()}), z.object({avatarUrl: z.string().optional(), discordChannelId: z.string().optional(), discordGuildId: z.string().optional(), discordWebhookName: z.string().optional(), displayUsername: z.string().optional(), enabled: z.boolean().optional(), health: channelHealthDTO.optional(), kind: z.string().optional(), mentionRoleIdOnError: z.string().optional(), name: z.string(), threadId: z.string().optional(), webhookUrl: z.string().optional()}), z.object({accountIds: z.array(z.string()).optional(), categories: z.array(z.enum(["TRADING", "COPY_SKIPPED", "EXECUTION_ERROR", "ACCOUNT_CONNECTION", "RISK", "NEWS", "SIGNALS", "SYSTEM", "OTHER"])).optional(), cooldown: notificationCooldownDTO.optional(), digest: notificationDigestDTO.optional(), enabled: z.boolean().optional(), events: z.array(z.enum(["POSITION_OPENED", "POSITION_CLOSED", "POSITION_MODIFIED", "HISTORY_UPDATED", "TRADE_APPROVAL_REQUIRED", "TRADE_APPROVED", "UNMANAGED_POSITION_DETECTED", "COPY_SKIPPED", "ORDER_REJECTED", "INSUFFICIENT_MARGIN", "TRADE_FAILED_DISCONNECTED", "COPY_FAILED", "DUPLICATE_POSITION_DETECTED", "ACCOUNT_STARTED", "ACCOUNT_STOPPED", "ACCOUNT_CONNECTED", "ACCOUNT_DISCONNECTED", "ACCOUNT_LOGIN_FAILED", "ACCOUNT_TOKEN_EXPIRING", "ACCOUNT_RESTRICTED", "ACCOUNT_FALLBACK_MODE", "RISK_LIMIT_REACHED", "PROFIT_TARGET_REACHED", "LOSS_PROTECTED_EXIT", "GUARDRAIL_TRIGGERED", "COPIER_STOPPED_BY_RISK", "LIMIT_RESET", "BALANCE_ADJUSTMENT_DETECTED", "NEWS_EVENT_UPCOMING", "NEWS_EVENT_RELEASED", "NEWS_FILTER_ACTION_SCHEDULED", "NEWS_FILTER_ACTION_IMMINENT", "NEWS_FILTER_DAILY_AGENDA", "NEWS_FILTER_SKIPPED_COPY", "NEWS_FILTER_CLOSED_POSITION", "NEWS_FILTER_REOPENED", "NEWS_FILTER_REOPEN_SKIPPED", "NEWS_FILTER_HOLIDAY_MODE", "MARKET_NEWS_HIGH_IMPACT", "SIGNAL_RECEIVED", "SIGNAL_EXECUTED", "SIGNAL_REJECTED", "SIGNAL_AI_LIMIT_REACHED", "SIGNAL_SUBSCRIPTION_ENDED", "CONFIGURATION_ERROR", "CONFIGURATION_CHANGED", "MAINTENANCE_WINDOW", "PROXY_ISSUE", "EXPERT_ADVISOR_STARTED", "EXPERT_ADVISOR_STOPPED", "EXPERT_ADVISOR_WARNING", "LOG_RATE_LIMITED", "NOTIFICATION_CHANNEL_DISABLED", "GENERAL"])).optional(), excludeAccountIds: z.array(z.string()).optional(), includeProjectEvents: z.boolean().optional(), kind: z.string().optional(), migratedFromFeatureId: z.string().optional(), minLogLevel: logTypeDTO, name: z.string(), quietHours: notificationQuietHoursDTO.optional(), sourceFeatureIds: z.array(z.string()).optional(), sourceFeatureTypeIds: z.array(z.number().int()).optional(), targets: z.array(notificationTargetDTO).optional(), useAlias: z.boolean().optional()}), z.object({comment: z.array(z.string()).optional(), magicNumber: z.array(z.string()).optional(), maxLotSize: z.number().optional(), minLotSize: z.number().optional()}), z.object({closeAfterInSeconds: z.number().int().gte(0).lte(3600).optional(), cronExpressions: z.array(z.string()), symbol: z.string()}), z.object({blacklist: z.array(z.string()).optional(), whitelist: z.array(z.string()).optional()}), z.object({dedicatedProxyServerId: z.number().int()}), z.object({dedicatedProxyServerIds: z.record(z.string(), z.array(proxyDTO)).optional(), poolSize: z.record(z.string(), z.number().int())}), z.object({cycles: z.number().int().gte(1).lte(10).optional(), lastLossGreaterThanInPercentage: z.number().gte(0).lte(100).optional(), limitLevels: z.number().int().gte(1).lte(100).optional(), lookBackInDays: z.number().int().gte(1).lte(7).optional(), multiplier: z.number().gte(0.001).lte(999.999).optional()}), z.object({additionalSlPoints: z.number().int().optional(), additionalTpPoints: z.number().int().optional(), adjustWithMasterDistance: z.boolean().optional(), attachTpSlAfterOpen: z.boolean().optional(), blockTradeWithoutTpSl: z.boolean().optional(), fixedSlInPoints: z.number().int().optional(), fixedTpInPoints: z.number().int().optional(), lockTpSl: z.boolean().optional(), masterTpSlPriority: z.boolean().optional(), removeSl: z.boolean().optional(), removeTp: z.boolean().optional(), symbolsConfiguration: z.record(z.string(), featureTpSlManagementDTO).optional()}), z.object({ignoreForSeconds: z.number().int().gte(0).optional(), onlyIfTpSlAreSet: z.boolean()}), z.object({autoResetIfBalanceIsBelow: z.boolean().optional(), dailyAbsoluteProfitTarget: z.number().gte(0).optional(), dailyProfitTarget: z.number().gte(0).lte(100).optional(), dailyRelativeProfitTarget: z.number().gte(0).optional(), pauseInsteadOfClose: z.boolean().optional(), resetOnBalanceChange: z.boolean().optional(), resetTime: z.string().optional(), trackByOpenDate: z.boolean().optional()}), z.object({autoResetIfBalanceIsBelow: z.boolean().optional(), pauseInsteadOfClose: z.boolean().optional(), resetOnBalanceChange: z.boolean().optional(), weeklyAbsoluteProfitTarget: z.number().gte(0).optional(), weeklyProfitTarget: z.number().gte(0).lte(100).optional(), weeklyRelativeProfitTarget: z.number().gte(0).optional()}), z.object({autoResetIfBalanceIsBelow: z.boolean().optional(), monthlyAbsoluteProfitTarget: z.number().gte(0).optional(), monthlyProfitTarget: z.number().gte(0).lte(100).optional(), monthlyRelativeProfitTarget: z.number().gte(0).optional(), pauseInsteadOfClose: z.boolean().optional(), resetOnBalanceChange: z.boolean().optional()}), z.object({accessAllowed: z.boolean().optional(), allowCustomers: z.array(z.string()).optional(), allowOverrideCopierSetting: z.boolean().optional(), allowReselling: z.boolean().optional(), allowedBrokers: z.array(z.string()).optional(), allowedOverrideFields: z.array(z.string()).optional(), billingModel: z.enum(["MONTHLY_PROFIT", "HIGH_WATERMARK"]).optional(), contact: contactDTO.optional(), copier: copierDTO, coverFollowerCosts: z.boolean().optional(), customerId: z.number().int().optional(), description: z.string().max(400).optional(), detailedDescription: z.string().max(10000).optional(), isPublic: z.boolean().optional(), logo: z.string().optional(), makeHistoryPublic: z.boolean().optional(), makeVisibleInMarketplace: z.boolean().optional(), maxCoveredAccountsPerProject: z.number().int().gte(0).lte(100).optional(), minimumBalance: z.number().int().gte(0).optional(), monthlySubscriptionFee: z.number().gte(0).lte(300).optional(), name: z.string().max(255), profileLink: z.string().max(500).optional(), profitSharingFee: z.number().gte(0).lte(100).optional(), subscribers: z.array(z.string()).optional(), useMetaCopierAsPaymentProvider: z.boolean().optional(), verified: z.boolean().optional()}), z.object({active: z.boolean().optional(), copier: copierDTO.optional(), disableMinVolumeSafetySkip: z.boolean().optional(), monitorOnly: z.boolean().optional(), signalProviderAvailable: z.boolean().optional(), signalProviderId: z.string(), signalProviderName: z.string().optional(), suspended: z.boolean().optional()}), z.object({allowedRegions: z.array(regionDTO).optional(), noFallback: z.boolean().optional()}), z.object({host: z.string(), httpPort: z.number().int().optional(), password: z.string(), socksPort: z.number().int().optional(), username: z.string()}), z.object({maxOpenPositions: z.number().int().optional(), maxPositionsInTimeWindow: z.number().int().optional(), symbolsConfiguration: z.record(z.string(), featureMaxOpenPositionsDTO).optional(), timeWindowSeconds: z.number().int().optional()}), z.object({checkMasterLotSize: z.boolean().optional(), maxLotSize: z.number().optional(), skipIfExceedsMax: z.boolean().optional(), symbolsConfiguration: z.record(z.string(), featureMaxLotSizeDTO).optional()}), z.object({fixMasterBalanceAndEquity: z.number().int().optional(), fixSlaveBalanceAndEquity: z.number().int().optional(), fixedLotSize: z.number().optional(), multiplier: z.number().gte(0.001).lte(999.999).optional(), rules: z.array(multiplierRuleDTO).optional(), scaleType: scaleTypeDTO.optional(), symbolsConfiguration: z.record(z.string(), featureMultiplierDTO).optional()}), z.object({maximumLot: z.number().optional(), symbolsConfiguration: z.record(z.string(), featureMaximumLotDTO).optional()}), z.object({reverse: z.boolean().optional(), reverseStopLossInPoints: z.number().int().optional(), reverseTriggerInPoints: z.number().int().optional(), stopLossInPoints: z.number().int().optional(), symbolsConfiguration: z.record(z.string(), featureBreakEvenDTO).optional(), triggerInPoints: z.number().int().optional()}), z.object({activationThresholdPercentage: z.number().optional(), activationThresholdPoints: z.number().int().optional(), initialStopLossPoints: z.number().int().optional(), minimumDistancePoints: z.number().int().optional(), symbolsConfiguration: z.record(z.string(), featureTrailingStopDTO).optional(), trailingStepPercentage: z.number().optional(), trailingStepPoints: z.number().int().optional()}), z.object({closePositionsAtWindowEnd: z.boolean().optional(), symbolsConfiguration: z.record(z.string(), featureTradingWindowsDTO).optional(), temporarilySkipUntilNextWindow: z.boolean().optional(), tradingWindows: z.array(tradingWindowDTO)}), z.object({activateHftMode: z.boolean().optional()}), z.object({activateSocket: z.boolean().optional()}), z.object({activateApproval: z.boolean().optional()}), z.object({maxDelayClose: z.number().gte(0).lte(3600).optional(), maxDelayOpen: z.number().gte(0).lte(3600).optional(), minDelayClose: z.number().gte(0).lte(3600).optional(), minDelayOpen: z.number().gte(0).lte(3600).optional(), symbolsConfiguration: z.record(z.string(), featureDelayedExecutionDTO).optional()}), z.object({accountType: accountTypeDTO.optional(), affectedAccountIds: z.array(z.string()).optional(), affectedCopierStates: z.record(z.string(), copierStateDTO).optional(), broker: z.string().max(255).optional(), closePositionStrategy: z.enum(["DO_NOT_CLOSE", "CLOSE_ALL", "CLOSE_ALL_IF_PROFIT"]).optional(), enabled: z.boolean().optional(), endTime: z.string(), entryActionsExecuted: z.boolean().optional(), maintenanceAction: z.enum(["STOP_ACCOUNTS", "PAUSE_COPIERS"]).optional(), positionsClosedForAccounts: z.array(z.string()).optional(), startTime: z.string()}), z.object({accountPriceDedicated: z.number().gte(0).lte(5).optional(), accountPriceDedicatedMin: z.number().gte(0).lte(5).optional(), accountPriceShared: z.number().gte(0).lte(5).optional(), accountTypes: z.array(accountTypeDTO).optional(), allowedEmailDomains: z.array(z.string()).optional(), allowedRegions: z.array(regionDTO).optional(), allowedRegistrationEmails: z.array(z.string()).optional(), authPageBackground: z.string().max(7).optional(), cTraderClientId: z.string().optional(), cTraderClientSecret: z.string().optional(), cryptoEnabledCoins: z.array(z.string()).optional(), cryptoNativeEnabled: z.boolean().optional(), cryptoNativeReady: z.boolean().optional(), cryptoWallet: cryptoWalletConfigDTO.optional(), customCss: z.string().max(50000).optional(), customJavascript: z.string().max(50000).optional(), disableAddingCopiers: z.boolean().optional(), disableDedicatedIpPurchase: z.boolean().optional(), disableDedicatedProjects: z.boolean().optional(), disableInvoicing: z.boolean().optional(), disableMarketplaceSubscription: z.boolean().optional(), enableTelegramSignals: z.boolean().optional(), enableTradingViewWebhook: z.boolean().optional(), featurePrice: z.number().gte(0).lte(1).optional(), hideBrokerInSignalProvider: z.boolean().optional(), hideCurrentBalanceInSignalProvider: z.boolean().optional(), homeLink: z.string().max(255).optional(), layout: z.string().optional(), logo: z.string(), manualCollection: z.boolean().optional(), manualCollectionPaymentInstructions: z.string().max(2000).optional(), maxAccountsPerProject: z.number().int().gte(0).lte(100).optional(), maxProjectsPerUser: z.number().int().gte(0).lte(30).optional(), name: z.string().max(20), pro: z.boolean().optional(), publicMarketplace: z.boolean().optional(), registrationLink: z.string().max(255).optional(), restrictRegistration: z.boolean().optional(), sendManualCollectionEmail: z.boolean().optional(), showScoreOnMarketplace: z.boolean().optional(), signalProviderAlias: z.string().max(30).optional(), stripeApiKey: z.string(), subdomain: z.string().max(30), supportEmail: z.string().max(255), supportLink: z.string().max(255).optional(), theme: z.string().optional(), tradeStationClientId: z.string().optional(), tradeStationClientSecret: z.string().optional(), tradovateClientId: z.string().optional(), tradovateClientSecret: z.string().optional()}), z.object({minimumHoldSeconds: z.number().int().gte(0).optional(), symbolsConfiguration: z.record(z.string(), featureMinimumHoldingTimeDTO).optional()}), z.object({ifSlNotDefined: z.boolean().optional(), ifTpNotDefined: z.boolean().optional(), logicOperatorTpSl: z.enum(["AND", "OR", "AND", "OR"]).optional(), symbolsConfiguration: z.record(z.string(), featureSkipPositionDTO).optional()}), z.object({absoluteRisk: z.number().optional(), aggregateRiskPerSymbol: z.boolean().optional(), autoCloseOnRiskThresholdReached: z.boolean().optional(), correctLotSizeBasedOnTheStopLoss: z.boolean().optional(), missingStopLossBehavior: z.enum(["OPEN_UNADJUSTED", "OPEN_MINIMUM_VOLUME", "SKIP_TRADE"]).optional(), relativeRisk: z.number().optional(), symbolsConfiguration: z.record(z.string(), featureRiskPerTradeDTO).optional(), tickValue: z.number().optional(), tickValueAutomaticAdjustement: z.boolean().optional(), waitForStopLossSeconds: z.number().int().optional()}), z.object({resetIntervalMinutes: z.number().int().lte(1440).optional(), resetOnPositionClose: z.boolean().optional(), skipOrdersCount: z.number().int().optional(), symbolsConfiguration: z.record(z.string(), featureLiveDelayDTO).optional(), trackByDirection: z.boolean().optional()}), z.object({allowedOrderTypes: z.array(z.enum(["Buy", "Sell", "BuyLimit", "SellLimit", "BuyStop", "SellStop"])).optional()}), z.object({activateDataCollector: z.boolean(), collectionIntervalSeconds: z.number().int().gte(30), normalizeValues: z.boolean(), recordBalance: z.boolean(), recordEquity: z.boolean(), recordFloatingPnL: z.boolean(), retentionDays: z.number().int().optional()}), z.object({assumedPointRisk: z.number().gte(1).lte(10000).optional(), autoResetOnSeriesComplete: z.boolean().optional(), autoTuneBoundsValid: z.boolean().optional(), bankrollBase: z.enum(["BALANCE", "EQUITY", "FREE_MARGIN"]), bankrollPercentage: z.number().gte(0.1).lte(100).optional(), cooldownAfterResetMinutes: z.number().int().gte(0).lte(1440).optional(), excludeBreakEvenTrades: z.boolean().optional(), expectedLossRMultiple: z.number().gte(-1).lte(0).optional(), expectedPayoutFactor: z.number().gte(0.01).lte(5).optional(), expectedRMultiple: z.number().gte(0.05).lte(10).optional(), expectedWins: z.number().int().gte(1).lte(100).optional(), expectedWinsValid: z.boolean().optional(), lotRoundingMode: z.enum(["DOWN", "UP", "NEAREST"]), lotStep: z.number().gte(0.0001).lte(100).optional(), maxConsecutiveLosses: z.number().int().gte(0).lte(50).optional(), maxExpectedWins: z.number().int().gte(1).lte(100).optional(), maximumLotSize: z.number().gte(0.01).lte(1000).optional(), minExpectedWins: z.number().int().gte(1).lte(100).optional(), minimumLotSize: z.number().gte(0).lte(100).optional(), minimumTradesForHistoricalWinRate: z.number().int().gte(1).lte(500).optional(), outcomePolicy: z.enum(["THRESHOLD", "SIGN", "R_BASED"]), partialWinPolicy: z.enum(["IGNORE", "COUNT_AS_WIN", "COUNT_AS_LOSS", "PROPORTIONAL"]), payoutModel: z.enum(["R_MULTIPLE", "PAYOUT_FACTOR", "REALIZED_R"]), resetOnBankrollDepleted: z.boolean().optional(), resetOnTargetReached: z.boolean().optional(), statisticsLookBackDays: z.number().int().gte(0).lte(365).optional(), symbolsConfiguration: z.record(z.string(), featureMasanielloDTO).optional(), targetProfitPercentage: z.number().gte(1).lte(1000).optional(), totalEvents: z.number().int().gte(2).lte(100).optional(), useHistoricalWinRate: z.boolean().optional(), winRateSmoothingFactor: z.number().gte(0).lte(1).optional(), winThresholdBase: z.enum(["RISK", "NOTIONAL", "ABSOLUTE"]), winThresholdPercentage: z.number().gte(0).lte(100).optional()}), z.object({aggregatePerSymbol: z.boolean().optional(), enabled: z.boolean().optional(), maxLotSizeThreshold: z.number().optional(), maxOpenTimeSeconds: z.number().int().optional(), symbolsConfiguration: z.record(z.string(), featureTradeGuardrailsDTO).optional()}), z.object({enableMartingaleStrategy: z.boolean().optional(), symbolsConfiguration: z.record(z.string(), featureMartingaleStrategyDTO).optional()}), z.object({analyticsUrl: z.string().optional(), description: z.string().max(1000), displayName: z.string().max(255), maxDrawdownPercentage: z.number(), status: z.enum(["PENDING", "ACTIVE", "SUSPENDED"]).optional()}), z.object({profitSharePercentage: z.number().optional(), status: z.enum(["PENDING", "ACTIVE", "SUSPENDED"]).optional(), traderFeatures: z.array(z.lazy(() => featureDTO)).optional()}), z.object({allowCloseAll: z.boolean().optional(), allowSymbolOnlyClose: z.boolean().optional(), allowedActions: z.array(z.string()).optional(), authMethod: z.enum(["SECRET", "HMAC"]), dataRetentionDays: z.number().int().gte(1).lte(90).optional(), enableWebhook: z.boolean(), enabled: z.boolean().optional(), hmacSecret: z.string().optional(), ipAllowlist: z.array(z.string()).optional(), maxAllowedVolume: z.number().gte(0).optional(), maxMatchCount: z.number().int().gte(1).lte(100).optional(), maxMatchCountOrDefault: z.number().int().optional(), openRetry: z.boolean().optional(), openRetryTimeoutInMinutes: z.number().int().gte(1).lte(60).optional(), openRetryTimeoutInMinutesOrDefault: z.number().int().optional(), requireTimestampForSecret: z.boolean().optional(), timestampToleranceSeconds: z.number().int().gte(10).lte(300).optional(), timestampToleranceSecondsOrDefault: z.number().int().optional(), webhookSecret: z.string().min(16).max(64).optional()}), z.object({authMethod: z.enum(["HMAC_SHA256", "BEARER_TOKEN", "NONE"]), bearerToken: z.string().min(16).max(512).optional(), customHeaders: z.record(z.string(), z.string()).optional(), description: z.string().max(255).optional(), enableOutboundWebhook: z.boolean(), enabled: z.boolean().optional(), endpointUrl: z.string().min(10).max(2048), hmacSecret: z.string().min(32).max(512).optional(), includeAccountMetadata: z.boolean().optional(), includePositionDetails: z.boolean().optional(), includeTimestampInSignature: z.boolean().optional(), initialRetryDelayMs: z.number().int().gte(500).lte(30000).optional(), initialRetryDelayMsOrDefault: z.number().int().optional(), maxRetries: z.number().int().gte(0).lte(5).optional(), maxRetriesOrDefault: z.number().int().optional(), rateLimitPerMinute: z.number().int().gte(0).lte(1000).optional(), rateLimitPerMinuteOrDefault: z.number().int().optional(), requestTimeoutSeconds: z.number().int().gte(5).lte(60).optional(), requestTimeoutSecondsOrDefault: z.number().int().optional(), subscribedEvents: z.array(z.enum(["POSITION_OPENED", "POSITION_CLOSED", "HISTORY_UPDATED"])).optional()}), z.object({apiHash: z.string().optional(), apiId: z.number().int(), authErrorMessage: z.string().optional(), authStatus: z.enum(["PENDING", "CODE_REQUIRED", "PASSWORD_REQUIRED", "AUTHORIZED", "FAILED", "SESSION_EXPIRED", "DISCONNECTED"]).optional(), availableChats: z.array(telegramChatDTO).optional(), connected: z.boolean().optional(), disconnectedSince: z.string().optional(), includePrivateChats: z.boolean().optional(), lastSyncAt: z.string().optional(), phoneNumber: z.string(), regionId: z.number().int(), restartAuth: z.boolean().optional(), twoFactorPassword: z.string().optional(), verificationCode: z.string().optional()}), z.object({aiInstructions: z.string().max(2000).optional(), aiTier: z.enum(["BASIC", "STANDARD", "PRO"]).optional(), allowedActions: z.array(z.string()).optional(), chatId: z.number().int(), chatTitle: z.string().optional(), confidenceThreshold: z.number().int().gte(0).lte(100).optional(), connectorIndex: z.number().int().optional(), contextMessageCount: z.number().int().gte(1).lte(10).optional(), defaultStopLossPoints: z.number().int().gte(0).optional(), defaultTakeProfitPoints: z.number().int().gte(0).optional(), defaultVolume: z.number().gte(0.001).optional(), enabled: z.boolean(), errorMessage: z.string().optional(), excludePatterns: z.array(z.string()).optional(), forceMinTrade: z.boolean().optional(), forceVolumeMode: z.boolean().optional(), forumTopicId: z.number().int().optional(), includePatterns: z.array(z.string()).optional(), lastMessageAt: z.string().optional(), lotsPerThousandBalance: z.number().gte(0.001).optional(), magicNumber: z.number().int().optional(), marginPercent: z.number().gte(0.01).optional(), maxAllowedVolume: z.number().gte(0.001).optional(), messageExpiryMinutes: z.number().int().gte(1).lte(10080).optional(), riskAmount: z.number().gte(0.01).optional(), riskPercent: z.number().gte(0.01).optional(), signalRiskMultiplierEnabled: z.boolean().optional(), status: z.enum(["PENDING", "ACTIVE", "PAUSED", "ERROR", "DISCONNECTED"]).optional(), telegramAccountFeatureId: z.string(), volumeMode: z.enum(["FIXED", "BALANCE_SCALED", "RISK_PERCENT", "RISK_AMOUNT", "MARGIN_PERCENT", "AI"]).optional()}), z.object({blockHedging: z.boolean().optional()}), z.object({cooldownAnchor: z.enum(["CLOSE", "OPEN"]).optional(), cooldownMinutes: z.number().int().lte(1440).optional(), correlationGroups: z.array(z.array(z.string())).optional(), correlationMode: z.enum(["NONE", "CUSTOM_GROUPS"]).optional(), symbolsConfiguration: z.record(z.string(), featureTradeCooldownDTO).optional(), trackByDirection: z.boolean().optional()}), z.object({blackoutAfterMinutes: z.number().int().lte(240).optional(), blackoutBeforeMinutes: z.number().int().lte(240).optional(), blockModifications: z.boolean().optional(), dailyAgendaAtUtc: z.string().optional(), enableHolidayMode: z.boolean().optional(), enableNewsFilter: z.boolean().optional(), events: newsEventSelectionDTO.optional(), holidayAction: z.enum(["NONE", "REDUCE_SIZE", "SKIP_NEW_OPENS"]).optional(), holidayCountries: z.array(z.string()).optional(), holidaySizeFactorPercent: z.number().int().lte(100).optional(), logSkippedTrades: z.boolean().optional(), notificationTargets: z.array(notificationTargetDTO).optional(), notifyOnEvents: z.array(z.enum(["POSITION_OPENED", "POSITION_CLOSED", "POSITION_MODIFIED", "HISTORY_UPDATED", "TRADE_APPROVAL_REQUIRED", "TRADE_APPROVED", "UNMANAGED_POSITION_DETECTED", "COPY_SKIPPED", "ORDER_REJECTED", "INSUFFICIENT_MARGIN", "TRADE_FAILED_DISCONNECTED", "COPY_FAILED", "DUPLICATE_POSITION_DETECTED", "ACCOUNT_STARTED", "ACCOUNT_STOPPED", "ACCOUNT_CONNECTED", "ACCOUNT_DISCONNECTED", "ACCOUNT_LOGIN_FAILED", "ACCOUNT_TOKEN_EXPIRING", "ACCOUNT_RESTRICTED", "ACCOUNT_FALLBACK_MODE", "RISK_LIMIT_REACHED", "PROFIT_TARGET_REACHED", "LOSS_PROTECTED_EXIT", "GUARDRAIL_TRIGGERED", "COPIER_STOPPED_BY_RISK", "LIMIT_RESET", "BALANCE_ADJUSTMENT_DETECTED", "NEWS_EVENT_UPCOMING", "NEWS_EVENT_RELEASED", "NEWS_FILTER_ACTION_SCHEDULED", "NEWS_FILTER_ACTION_IMMINENT", "NEWS_FILTER_DAILY_AGENDA", "NEWS_FILTER_SKIPPED_COPY", "NEWS_FILTER_CLOSED_POSITION", "NEWS_FILTER_REOPENED", "NEWS_FILTER_REOPEN_SKIPPED", "NEWS_FILTER_HOLIDAY_MODE", "MARKET_NEWS_HIGH_IMPACT", "SIGNAL_RECEIVED", "SIGNAL_EXECUTED", "SIGNAL_REJECTED", "SIGNAL_AI_LIMIT_REACHED", "SIGNAL_SUBSCRIPTION_ENDED", "CONFIGURATION_ERROR", "CONFIGURATION_CHANGED", "MAINTENANCE_WINDOW", "PROXY_ISSUE", "EXPERT_ADVISOR_STARTED", "EXPERT_ADVISOR_STOPPED", "EXPERT_ADVISOR_WARNING", "LOG_RATE_LIMITED", "NOTIFICATION_CHANNEL_DISABLED", "GENERAL"])).optional(), sendDailyAgenda: z.boolean().optional(), skipMarketOrders: z.boolean().optional(), skipPendingOrders: z.boolean().optional(), symbolsConfiguration: z.record(z.string(), featureNewsFilterDTO).optional(), warnBeforeMinutes: z.array(z.number().int()).optional(), warnOnlyIfExposed: z.boolean().optional()}), z.object({cancelPendingOrders: z.boolean().optional(), closeBeforeMinutes: z.number().int().gte(1).lte(120).optional(), closeOnlyLosingPositions: z.boolean().optional(), dailyAgendaAtUtc: z.string().optional(), enableNewsProtection: z.boolean().optional(), events: newsEventSelectionDTO.optional(), minProfitToClose: z.number().optional(), notificationTargets: z.array(notificationTargetDTO).optional(), notifyOnEvents: z.array(z.enum(["POSITION_OPENED", "POSITION_CLOSED", "POSITION_MODIFIED", "HISTORY_UPDATED", "TRADE_APPROVAL_REQUIRED", "TRADE_APPROVED", "UNMANAGED_POSITION_DETECTED", "COPY_SKIPPED", "ORDER_REJECTED", "INSUFFICIENT_MARGIN", "TRADE_FAILED_DISCONNECTED", "COPY_FAILED", "DUPLICATE_POSITION_DETECTED", "ACCOUNT_STARTED", "ACCOUNT_STOPPED", "ACCOUNT_CONNECTED", "ACCOUNT_DISCONNECTED", "ACCOUNT_LOGIN_FAILED", "ACCOUNT_TOKEN_EXPIRING", "ACCOUNT_RESTRICTED", "ACCOUNT_FALLBACK_MODE", "RISK_LIMIT_REACHED", "PROFIT_TARGET_REACHED", "LOSS_PROTECTED_EXIT", "GUARDRAIL_TRIGGERED", "COPIER_STOPPED_BY_RISK", "LIMIT_RESET", "BALANCE_ADJUSTMENT_DETECTED", "NEWS_EVENT_UPCOMING", "NEWS_EVENT_RELEASED", "NEWS_FILTER_ACTION_SCHEDULED", "NEWS_FILTER_ACTION_IMMINENT", "NEWS_FILTER_DAILY_AGENDA", "NEWS_FILTER_SKIPPED_COPY", "NEWS_FILTER_CLOSED_POSITION", "NEWS_FILTER_REOPENED", "NEWS_FILTER_REOPEN_SKIPPED", "NEWS_FILTER_HOLIDAY_MODE", "MARKET_NEWS_HIGH_IMPACT", "SIGNAL_RECEIVED", "SIGNAL_EXECUTED", "SIGNAL_REJECTED", "SIGNAL_AI_LIMIT_REACHED", "SIGNAL_SUBSCRIPTION_ENDED", "CONFIGURATION_ERROR", "CONFIGURATION_CHANGED", "MAINTENANCE_WINDOW", "PROXY_ISSUE", "EXPERT_ADVISOR_STARTED", "EXPERT_ADVISOR_STOPPED", "EXPERT_ADVISOR_WARNING", "LOG_RATE_LIMITED", "NOTIFICATION_CHANNEL_DISABLED", "GENERAL"])).optional(), reopenAfterMinutes: z.number().int().gte(1).lte(240).optional(), reopenExpiryMinutes: z.number().int().gte(1).lte(1440).optional(), reopenMaxAdverseMovePips: z.number().int().optional(), reopenMaxSpreadPoints: z.number().int().optional(), reopenMode: z.enum(["NONE", "SAME_VOLUME", "RESYNC_WITH_MASTER"]).optional(), reopenOnlyIfMasterStillOpen: z.boolean().optional(), sendDailyAgenda: z.boolean().optional(), symbolsConfiguration: z.record(z.string(), featureNewsProtectionDTO).optional(), warnBeforeMinutes: z.array(z.number().int()).optional(), warnImminent: z.boolean().optional(), warnOnlyIfExposed: z.boolean().optional()}), z.object({behavior: z.enum(["REDUCE_LOT_SIZE", "SKIP_TRADE"]).optional(), leverageOverride: z.number().int().optional(), marginCapPercentage: z.number().optional(), scope: z.enum(["CUMULATIVE", "PER_TRADE"]).optional(), symbolsConfiguration: z.record(z.string(), featureMarginCapDTO).optional()}), z.object({mode: z.enum(["POINTS", "PERCENTAGE_OF_PRICE"]).optional(), onMissingPrice: z.enum(["ALLOW", "BLOCK"]).optional(), retryOnBlock: z.boolean().optional(), source: z.enum(["MASTER", "SLAVE"]).optional(), symbolsConfiguration: z.record(z.string(), featureSpreadFilterDTO).optional(), threshold: z.number().optional()}), z.object({adjustReferenceOnBalanceChange: z.boolean().optional(), overallLossLimit: z.number().gte(0).lte(100).optional(), overallLossLimitAmount: z.number().gte(0).optional(), overallProfitTarget: z.number().gte(0).lte(1000).optional(), overallProfitTargetAmount: z.number().gte(0).optional(), pauseInsteadOfClose: z.boolean().optional(), referenceBalance: z.number().gte(0).optional(), referenceMode: z.enum(["EQUITY", "BALANCE", "EQUITY", "BALANCE"]).optional(), symbolsConfiguration: z.record(z.string(), featureOverallTargetDTO).optional()}), z.object({enabled: z.boolean().optional(), includePendingOrders: z.boolean().optional(), maxLossToClosePoints: z.number().int().optional(), maxReopenSlippagePoints: z.number().int().optional(), onlyCloseInProfit: z.boolean().optional(), onlyCloseNegativeSwapPositions: z.boolean().optional(), restoreStopLossTakeProfit: z.boolean().optional(), schedules: z.array(closeReopenScheduleDTO), skipReopenIfMasterClosed: z.boolean().optional(), symbolsConfiguration: z.record(z.string(), featureScheduledCloseReopenDTO).optional()}), z.object({breakevenOffsetPoints: z.number().int().optional(), closeAllDetectionWindowSeconds: z.number().int().gte(1).lte(10).optional(), enabled: z.boolean(), forceTpToBreakeven: z.boolean().optional(), lossToleranceAbsolute: z.number().gte(0).optional(), lossTolerancePercent: z.number().gte(0).lte(100), protectionMode: z.enum(["CLOSE_ALL_ONLY", "EVERY_CLOSE"]).optional(), setBreakevenTakeProfit: z.boolean(), symbolsConfiguration: z.record(z.string(), featureLossProtectedExitDTO).optional()})]); export const featureTypeDTO = z.object({id: z.number().int(), name: z.string().optional(), planName: z.string().optional()}); export const featureDTO: z.ZodType = z.object({accountId: z.string().optional(), copierId: z.string().optional(), created: z.string().optional(), featureId: z.string().optional(), id: z.string().optional(), projectId: z.string().optional(), setting: featureSettingDTO, type: featureTypeDTO}); export const getApiRestApiV1InvestorProgramTradersResponse = z.array(featureDTO); export const validateResponse = async ( schema: { readonly '~standard': { readonly validate: (value: unknown) => ({ readonly value: Output; readonly issues?: undefined } | { readonly issues: ReadonlyArray<{ readonly message: string; readonly path?: ReadonlyArray | undefined }> }) | Promise<{ readonly value: Output; readonly issues?: undefined } | { readonly issues: ReadonlyArray<{ readonly message: string; readonly path?: ReadonlyArray | undefined }> }> } }, value: unknown ): Promise => { const result = await schema['~standard'].validate(value) if (result.issues !== undefined) { const detail = result.issues .map(({ message, path }) => path?.length ? `${path.map((segment) => String(typeof segment === 'object' ? segment.key : segment)).join('.')}: ${message}` : message ) .join('; ') throw new Error(`Response does not match the schema: ${detail}`, { cause: { issues: result.issues } }) } return result.value }; /** * Get all approved traders in the investor program * * GET /rest/api/v1/investorProgram/traders */ export const getApiRestApiV1InvestorProgramTraders = async (options?: GetApiRestApiV1InvestorProgramTradersOptions) => { const {baseUrl = "https://api.metacopier.io", fetch: fetchFn = fetch, ApiKeyAuth} = options ?? {} const query = new URLSearchParams() const headers = new Headers() headers.set('accept', "application/json") if (ApiKeyAuth !== undefined) headers.set("X-API-KEY", ApiKeyAuth) const url = `${baseUrl.replace(/\/+$/, '')}/rest/api/v1/investorProgram/traders${query.size > 0 ? `?${query}` : ''}` const res = await fetchFn(url, {method: "GET", headers}) if (!res.ok) throw new Error(`Request failed with status ${res.status}`, {cause: {status: res.status, body: await res.text()}}) return validateResponse(getApiRestApiV1InvestorProgramTradersResponse, await res.json()) };