From 5eafb192292a106195dc26289676cb1eee99d9e8 Mon Sep 17 00:00:00 2001 From: HYH0804 Date: Thu, 9 Apr 2026 23:49:44 +0900 Subject: [PATCH] =?UTF-8?q?#145=20[Feat]=20=EB=94=A5=EB=A7=81=ED=81=AC=20?= =?UTF-8?q?=EA=B3=B5=EC=9C=A0=20API=20=EA=B5=AC=ED=98=84=20(=EB=A6=AC?= =?UTF-8?q?=ED=8F=AC=ED=8A=B8/=EB=B0=B0=ED=8B=80)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-Authored-By: Claude Sonnet 4.6 --- .../share/controller/ShareApiController.java | 32 +++++++ .../share/controller/ShareController.java | 37 +++++++- .../picke/global/config/SecurityConfig.java | 3 + .../static/.well-known/assetlinks.json | 13 +++ .../resources/templates/share/battle.html | 33 +++++++ .../resources/templates/share/report.html | 33 +++++++ .../resources/templates/share/result.html | 92 ------------------- 7 files changed, 147 insertions(+), 96 deletions(-) create mode 100644 src/main/java/com/swyp/picke/domain/share/controller/ShareApiController.java create mode 100644 src/main/resources/static/.well-known/assetlinks.json create mode 100644 src/main/resources/templates/share/battle.html create mode 100644 src/main/resources/templates/share/report.html delete mode 100644 src/main/resources/templates/share/result.html diff --git a/src/main/java/com/swyp/picke/domain/share/controller/ShareApiController.java b/src/main/java/com/swyp/picke/domain/share/controller/ShareApiController.java new file mode 100644 index 00000000..6bdcd53e --- /dev/null +++ b/src/main/java/com/swyp/picke/domain/share/controller/ShareApiController.java @@ -0,0 +1,32 @@ +package com.swyp.picke.domain.share.controller; + +import com.swyp.picke.global.common.response.ApiResponse; +import lombok.RequiredArgsConstructor; +import org.springframework.beans.factory.annotation.Value; +import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestParam; +import org.springframework.web.bind.annotation.RestController; + +import java.util.Map; + +@RestController +@RequestMapping("/api/v1/share") +@RequiredArgsConstructor +public class ShareApiController { + + @Value("${picke.baseUrl}") + private String baseUrl; + + @GetMapping("/report") + public ApiResponse> getReportShareUrl(@RequestParam Long reportId) { + String shareUrl = baseUrl + "/report/" + reportId; + return ApiResponse.onSuccess(Map.of("shareUrl", shareUrl)); + } + + @GetMapping("/battle") + public ApiResponse> getBattleShareUrl(@RequestParam Long battleId) { + String shareUrl = baseUrl + "/battle/" + battleId; + return ApiResponse.onSuccess(Map.of("shareUrl", shareUrl)); + } +} diff --git a/src/main/java/com/swyp/picke/domain/share/controller/ShareController.java b/src/main/java/com/swyp/picke/domain/share/controller/ShareController.java index 8ab75402..3ef17c37 100644 --- a/src/main/java/com/swyp/picke/domain/share/controller/ShareController.java +++ b/src/main/java/com/swyp/picke/domain/share/controller/ShareController.java @@ -1,16 +1,45 @@ package com.swyp.picke.domain.share.controller; +import jakarta.servlet.http.HttpServletRequest; +import org.springframework.beans.factory.annotation.Value; import org.springframework.stereotype.Controller; import org.springframework.ui.Model; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.PathVariable; +import org.springframework.web.servlet.view.RedirectView; @Controller public class ShareController { - @GetMapping("/result/{userId}") - public String result(@PathVariable Long userId, Model model) { - model.addAttribute("userId", userId); - return "share/result"; + //출시 이후 URL 필요 + @Value("${picke.store.android:https://play.google.com/store/apps/details?id=com.swyp.picke}") + private String androidStoreUrl; + + @GetMapping("/report/{reportId}") + public Object report(@PathVariable Long reportId, HttpServletRequest request, Model model) { + String ua = request.getHeader("User-Agent"); + if (ua == null) ua = ""; + ua = ua.toLowerCase(); + + if (ua.contains("android")) { + return new RedirectView(androidStoreUrl); + } else { + model.addAttribute("reportId", reportId); + return "share/report"; + } + } + + @GetMapping("/battle/{battleId}") + public Object battle(@PathVariable Long battleId, HttpServletRequest request, Model model) { + String ua = request.getHeader("User-Agent"); + if (ua == null) ua = ""; + ua = ua.toLowerCase(); + + if (ua.contains("android")) { + return new RedirectView(androidStoreUrl); + } else { + model.addAttribute("battleId", battleId); + return "share/battle"; + } } } diff --git a/src/main/java/com/swyp/picke/global/config/SecurityConfig.java b/src/main/java/com/swyp/picke/global/config/SecurityConfig.java index 3e29ab22..379c1266 100644 --- a/src/main/java/com/swyp/picke/global/config/SecurityConfig.java +++ b/src/main/java/com/swyp/picke/global/config/SecurityConfig.java @@ -43,6 +43,9 @@ public SecurityFilterChain filterChain(HttpSecurity http) throws Exception { "/js/**", "/css/**", "/favicon.ico", "/api/v1/admin/login", "/api/v1/admin", "/result/**", + "/report/**", + "/battle/**", + "/.well-known/**", "/api/v1/resources/images/**", "/api/v1/resources/audio/**", "/api/v1/admob/reward/**" diff --git a/src/main/resources/static/.well-known/assetlinks.json b/src/main/resources/static/.well-known/assetlinks.json new file mode 100644 index 00000000..4e5d52a6 --- /dev/null +++ b/src/main/resources/static/.well-known/assetlinks.json @@ -0,0 +1,13 @@ +[ + { + "relation": ["delegate_permission/common.handle_all_urls"], + "target": { + "namespace": "android_app", + "package_name": "com.picke.app", + "sha256_cert_fingerprints": [ + "8C:DA:C0:E5:4A:F3:24:AE:C4:AA:37:01:76:8E:CE:DA:D4:EE:0A:CB:09:29:45:45:A8:B4:BA:A6:F8:16:E8:BF", + "17:D6:B0:C3:F7:94:09:B3:62:78:C8:9B:1B:21:D0:C7:D9:AC:E0:0E:C8:8A:B3:5A:31:78:4D:50:A9:58:FB:45" + ] + } + } +] diff --git a/src/main/resources/templates/share/battle.html b/src/main/resources/templates/share/battle.html new file mode 100644 index 00000000..c9f872ff --- /dev/null +++ b/src/main/resources/templates/share/battle.html @@ -0,0 +1,33 @@ + + + + + + Pické - 배틀 + + + + + + + +
+
🦉
+

Pické

+

+ 배틀에 참여하려면
모바일 앱에서 확인하세요. +

+
+

앱을 설치하고 배틀에 참여해보세요

+ +
+
+ + + diff --git a/src/main/resources/templates/share/report.html b/src/main/resources/templates/share/report.html new file mode 100644 index 00000000..b7e692a6 --- /dev/null +++ b/src/main/resources/templates/share/report.html @@ -0,0 +1,33 @@ + + + + + + Pické - 철학자 리포트 + + + + + + + +
+
🦉
+

Pické

+

+ 친구의 철학자 리포트를 보려면
모바일 앱에서 확인하세요. +

+
+

앱을 설치하고 리포트를 확인해보세요

+ +
+
+ + + diff --git a/src/main/resources/templates/share/result.html b/src/main/resources/templates/share/result.html deleted file mode 100644 index b75c451f..00000000 --- a/src/main/resources/templates/share/result.html +++ /dev/null @@ -1,92 +0,0 @@ - - - - - - Pické - 철학자 유형 결과 - - - - - - - -
- - - - - - - -
- - - - -