diff --git a/src/main/java/kz/konturai/parser/controller/TargetingCampaignController.java b/src/main/java/kz/konturai/parser/controller/TargetingCampaignController.java index b69f8a6..9f7f9a1 100644 --- a/src/main/java/kz/konturai/parser/controller/TargetingCampaignController.java +++ b/src/main/java/kz/konturai/parser/controller/TargetingCampaignController.java @@ -15,7 +15,7 @@ import java.util.List; import java.util.Map; @RestController -@RequestMapping("/api/marketing/targeting") +@RequestMapping("/api/marketing/campaigns") @RequiredArgsConstructor @Slf4j public class TargetingCampaignController { @@ -40,7 +40,7 @@ public class TargetingCampaignController { return userId; } - @PostMapping("/campaigns") + @PostMapping public ResponseEntity createCampaign( @RequestHeader(value = "X-User-Id", required = false) String userIdHeader, @RequestHeader(value = "Authorization", required = false) String authHeader, @@ -50,7 +50,7 @@ public class TargetingCampaignController { return ResponseEntity.ok(campaignService.createCampaign(request, userId)); } - @GetMapping("/campaigns") + @GetMapping public ResponseEntity> getUserCampaigns( @RequestHeader(value = "X-User-Id", required = false) String userIdHeader, @RequestHeader(value = "Authorization", required = false) String authHeader, @@ -61,7 +61,7 @@ public class TargetingCampaignController { return ResponseEntity.ok(campaignService.getUserCampaigns(userId, page, size)); } - @GetMapping("/campaigns/{id}") + @GetMapping("/{id}") public ResponseEntity getCampaign( @RequestHeader(value = "X-User-Id", required = false) String userIdHeader, @RequestHeader(value = "Authorization", required = false) String authHeader, @@ -71,7 +71,7 @@ public class TargetingCampaignController { return ResponseEntity.ok(campaignService.getCampaignById(id, userId)); } - @PostMapping("/campaigns/{id}/pause") + @PostMapping("/{id}/pause") public ResponseEntity pauseCampaign( @RequestHeader(value = "X-User-Id", required = false) String userIdHeader, @RequestHeader(value = "Authorization", required = false) String authHeader, @@ -81,7 +81,7 @@ public class TargetingCampaignController { return ResponseEntity.ok(campaignService.pauseCampaign(id, userId)); } - @PostMapping("/campaigns/{id}/resume") + @PostMapping("/{id}/resume") public ResponseEntity resumeCampaign( @RequestHeader(value = "X-User-Id", required = false) String userIdHeader, @RequestHeader(value = "Authorization", required = false) String authHeader, @@ -91,7 +91,7 @@ public class TargetingCampaignController { return ResponseEntity.ok(campaignService.resumeCampaign(id, userId)); } - @GetMapping("/campaigns/{id}/insights") + @GetMapping("/{id}/insights") public ResponseEntity getInsights( @RequestHeader(value = "X-User-Id", required = false) String userIdHeader, @RequestHeader(value = "Authorization", required = false) String authHeader, @@ -102,7 +102,7 @@ public class TargetingCampaignController { return ResponseEntity.ok(campaignService.getCampaignInsights(id, userId, datePreset)); } - @PostMapping("/campaigns/{id}/sync-insights") + @PostMapping("/{id}/sync-insights") public ResponseEntity syncInsights( @RequestHeader(value = "X-User-Id", required = false) String userIdHeader, @RequestHeader(value = "Authorization", required = false) String authHeader, @@ -114,7 +114,7 @@ public class TargetingCampaignController { return ResponseEntity.ok().build(); } - @GetMapping("/campaigns/{id}/ab-test/evaluate") + @GetMapping("/{id}/ab-test/evaluate") public ResponseEntity evaluateAbTest( @RequestHeader(value = "X-User-Id", required = false) String userIdHeader, @RequestHeader(value = "Authorization", required = false) String authHeader, @@ -124,10 +124,10 @@ public class TargetingCampaignController { TargetingCampaign campaign = campaignService.getCampaignById(id, userId); return ResponseEntity.ok(abTestingService.evaluateABTest(campaign)); } - - // --- Audience endpoints --- - @PostMapping("/audience/segment") + // --- Audience tools (under /targeting) --- + + @PostMapping("/targeting/audience/segment") public ResponseEntity> segmentAudience( @RequestHeader(value = "X-User-Id", required = false) String userIdHeader, @RequestHeader(value = "Authorization", required = false) String authHeader, @@ -138,7 +138,7 @@ public class TargetingCampaignController { return ResponseEntity.ok(audienceService.segmentAudience(doc)); } - @PostMapping("/audience/estimate") + @PostMapping("/targeting/audience/estimate") public ResponseEntity> estimateAudience( @RequestHeader(value = "X-User-Id", required = false) String userIdHeader, @RequestHeader(value = "Authorization", required = false) String authHeader, @@ -148,9 +148,9 @@ public class TargetingCampaignController { return ResponseEntity.ok(audienceService.estimateAudienceSize(profile, platform)); } - // --- Budget endpoint --- + // --- Budget tools (under /targeting) --- - @PostMapping("/budget/optimize") + @PostMapping("/targeting/budget/optimize") public ResponseEntity optimizeBudget( @RequestHeader(value = "X-User-Id", required = false) String userIdHeader, @RequestHeader(value = "Authorization", required = false) String authHeader, @@ -163,9 +163,9 @@ public class TargetingCampaignController { return ResponseEntity.ok(budgetOptimizerService.optimizeBudget(campaign, doc)); } - // --- Account Selection endpoint --- + // --- Account Selection tools (under /targeting) --- - @PostMapping("/account/select") + @PostMapping("/targeting/account/select") public ResponseEntity selectAdAccount( @RequestHeader(value = "X-User-Id", required = false) String userIdHeader, @RequestHeader(value = "Authorization", required = false) String authHeader, @@ -180,70 +180,9 @@ public class TargetingCampaignController { return ResponseEntity.ok().build(); } -// // --- Facebook OAuth --- -// -// @GetMapping("/facebook/oauth-url") -// public ResponseEntity> getFbOauthUrl(@RequestHeader("X-User-Id") String userId) { -// log.info("[Targeting] FB OAuth URL requested by {}", userId); -// return ResponseEntity.ok(Map.of("url", facebookAdsService.getOAuthUrl(userId))); -// } -// -// @GetMapping("/facebook/callback") -// public ResponseEntity fbCallback( -// @RequestParam String code, -// @RequestParam String state) { -// log.info("[Targeting] FB Callback received for state/userId: {}", state); -// try { -// facebookAdsService.exchangeCodeForToken(code, state); -// return ResponseEntity.ok("Facebook Ads account successfully linked!"); -// } catch (Exception e) { -// log.error("[Targeting] FB Callback error", e); -// return ResponseEntity.badRequest().body("Facebook integration failed: " + e.getMessage()); -// } -// } -// -// @GetMapping("/facebook/ad-accounts") -// public ResponseEntity> getFbAdAccounts( -// @RequestHeader("X-User-Id") String userId, -// @RequestHeader("Authorization") String token) { -// log.info("[Targeting] Get FB Ad Accounts"); -// // token passed via header or db; assuming passed directly here for dynamic use or fetched via service inside -// return ResponseEntity.ok(facebookAdsService.getAdAccounts(token.replace("Bearer ", ""))); -// } -// -// // --- TikTok OAuth --- -// -// @GetMapping("/tiktok/oauth-url") -// public ResponseEntity> getTtOauthUrl(@RequestHeader("X-User-Id") String userId) { -// log.info("[Targeting] TT OAuth URL requested by {}", userId); -// return ResponseEntity.ok(Map.of("url", tikTokAdsService.getOAuthUrl(userId))); -// } -// -// @GetMapping("/tiktok/callback") -// public ResponseEntity ttCallback( -// @RequestParam String auth_code, -// @RequestParam String state) { -// log.info("[Targeting] TT Callback received for state/userId: {}", state); -// try { -// tikTokAdsService.exchangeCodeForToken(auth_code, state); -// return ResponseEntity.ok("TikTok Ads account successfully linked!"); -// } catch (Exception e) { -// log.error("[Targeting] TT Callback error", e); -// return ResponseEntity.badRequest().body("TikTok integration failed: " + e.getMessage()); -// } -// } -// -// @GetMapping("/tiktok/advertisers") -// public ResponseEntity>> getTtAdvertisers( -// @RequestHeader("X-User-Id") String userId, -// @RequestHeader("Authorization") String token) { -// log.info("[Targeting] Get TT Advertisers"); -// return ResponseEntity.ok(tikTokAdsService.getAdvertisers(token.replace("Bearer ", ""))); -// } + // --- Campaign Status Polling --- - // ── Polling статуса ─────────────────────────────────────────────────────── - - @GetMapping("/campaigns/{id}/status") + @GetMapping("/{id}/status") public ResponseEntity> getCampaignStatus( @RequestHeader(value = "X-User-Id", required = false) String userIdHeader, @RequestHeader(value = "Authorization", required = false) String authHeader, @@ -258,9 +197,9 @@ public class TargetingCampaignController { )); } - // ── AI Предсказания ─────────────────────────────────────────────────────── + // --- AI Predictions (Campaign-specific) --- - @GetMapping("/campaigns/{id}/prediction") + @GetMapping("/{id}/prediction") public ResponseEntity getPrediction( @RequestHeader(value = "X-User-Id", required = false) String userIdHeader, @RequestHeader(value = "Authorization", required = false) String authHeader, @@ -272,7 +211,7 @@ public class TargetingCampaignController { .orElse(ResponseEntity.notFound().build()); } - @PostMapping("/campaigns/{id}/predict") + @PostMapping("/{id}/predict") public ResponseEntity triggerPrediction( @RequestHeader(value = "X-User-Id", required = false) String userIdHeader, @RequestHeader(value = "Authorization", required = false) String authHeader, @@ -284,9 +223,9 @@ public class TargetingCampaignController { return ResponseEntity.accepted().body(Map.of("message", "Генерация предсказания запущена")); } - // ── Инсайты ─────────────────────────────────────────────────────────────── + // --- Insights --- - @GetMapping("/campaigns/{id}/insights/raw") + @GetMapping("/{id}/insights/raw") public ResponseEntity getRawInsights( @RequestHeader(value = "X-User-Id", required = false) String userIdHeader, @RequestHeader(value = "Authorization", required = false) String authHeader, @@ -296,9 +235,9 @@ public class TargetingCampaignController { return ResponseEntity.ok(campaign.getInsights() != null ? campaign.getInsights() : List.of()); } - // ── Retry ───────────────────────────────────────────────────────────────── + // --- Retry --- - @PostMapping("/campaigns/{id}/retry") + @PostMapping("/{id}/retry") public ResponseEntity retryCampaign( @RequestHeader(value = "X-User-Id", required = false) String userIdHeader, @RequestHeader(value = "Authorization", required = false) String authHeader, @@ -308,9 +247,9 @@ public class TargetingCampaignController { return ResponseEntity.ok(campaignService.retryCampaign(id, userId)); } - // ── Обновление бюджета и аудитории ─────────────────────────────────────── + // --- Budget and Audience Updates --- - @PutMapping("/campaigns/{id}/budget") + @PutMapping("/{id}/budget") public ResponseEntity updateBudget( @RequestHeader(value = "X-User-Id", required = false) String userIdHeader, @RequestHeader(value = "Authorization", required = false) String authHeader, @@ -322,7 +261,7 @@ public class TargetingCampaignController { body.get("totalBudget"), body.get("dailyBudget"))); } - @PutMapping("/campaigns/{id}/audience") + @PutMapping("/{id}/audience") public ResponseEntity updateAudience( @RequestHeader(value = "X-User-Id", required = false) String userIdHeader, @RequestHeader(value = "Authorization", required = false) String authHeader, @@ -333,9 +272,9 @@ public class TargetingCampaignController { return ResponseEntity.ok(campaignService.updateAudience(id, userId, audience)); } - // ── AdSets ─────────────────────────────────────────────────────────────── + // --- AdSets --- - @GetMapping("/campaigns/{id}/adsets") + @GetMapping("/{id}/adsets") public ResponseEntity> getAdSets( @RequestHeader(value = "X-User-Id", required = false) String userIdHeader, @RequestHeader(value = "Authorization", required = false) String authHeader, @@ -344,7 +283,7 @@ public class TargetingCampaignController { return ResponseEntity.ok(campaignService.getAdSets(id, userId)); } - @PutMapping("/campaigns/{id}/adsets/{adSetId}") + @PutMapping("/{id}/adsets/{adSetId}") public ResponseEntity updateAdSet( @RequestHeader(value = "X-User-Id", required = false) String userIdHeader, @RequestHeader(value = "Authorization", required = false) String authHeader,