Update app.py
Browse files
app.py
CHANGED
@@ -11,34 +11,49 @@ from zoneinfo import ZoneInfo
|
|
11 |
# OpenAI API 키를 환경변수에서 가져오기
|
12 |
API_KEY = os.getenv("API_KEY")
|
13 |
|
14 |
-
|
15 |
-
|
16 |
-
|
17 |
-
|
18 |
-
|
19 |
-
|
20 |
-
|
21 |
-
|
22 |
-
|
23 |
-
|
24 |
-
|
25 |
-
|
26 |
-
|
27 |
-
|
28 |
-
|
29 |
-
|
30 |
-
|
31 |
-
|
32 |
-
|
33 |
-
|
34 |
-
|
35 |
-
|
36 |
-
|
37 |
-
|
38 |
-
|
39 |
-
|
40 |
-
|
41 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
42 |
}
|
43 |
|
44 |
def convert_to_seoul_time(year, month, day, hour, minute, timezone_offset):
|
@@ -385,42 +400,46 @@ button:hover {
|
|
385 |
box-shadow: 0 4px 15px rgba(0, 0, 0, 0.1);
|
386 |
}
|
387 |
|
388 |
-
/* 시간대
|
389 |
-
.timezone-
|
390 |
-
margin: 20px 0;
|
391 |
-
padding: 15px;
|
392 |
background: linear-gradient(135deg, #ffffff, #f8f9fa);
|
393 |
border-radius: 10px;
|
|
|
|
|
394 |
box-shadow: 0 4px 15px rgba(0, 0, 0, 0.1);
|
|
|
|
|
395 |
}
|
396 |
|
397 |
-
.timezone-
|
398 |
-
|
399 |
-
|
400 |
-
border-radius: 5px !important;
|
401 |
-
}
|
402 |
-
|
403 |
-
.timezone-slider .thumb {
|
404 |
-
width: 20px !important;
|
405 |
-
height: 20px !important;
|
406 |
-
background: white !important;
|
407 |
-
border: 2px solid #6e8efb !important;
|
408 |
-
box-shadow: 0 2px 6px rgba(0, 0, 0, 0.2) !important;
|
409 |
}
|
410 |
|
411 |
-
.timezone-
|
|
|
|
|
|
|
|
|
412 |
font-size: 14px;
|
413 |
-
font-weight: 500;
|
414 |
color: #2d3748;
|
415 |
-
|
416 |
}
|
417 |
|
418 |
-
|
419 |
-
|
|
|
|
|
|
|
420 |
font-size: 14px;
|
421 |
color: #4a5568;
|
422 |
-
|
423 |
-
|
|
|
|
|
|
|
|
|
|
|
424 |
}
|
425 |
|
426 |
/* 분석 결과 스타일 */
|
@@ -522,6 +541,69 @@ input:focus, select:focus, textarea:focus {
|
|
522 |
box-shadow: 0 0 0 2px rgba(110, 142, 251, 0.2) !important;
|
523 |
transform: translateY(-1px);
|
524 |
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
525 |
"""
|
526 |
|
527 |
# Gradio UI 부분
|
@@ -529,7 +611,7 @@ with gr.Blocks(css=css) as demo:
|
|
529 |
gr.Markdown("# 🔮 AI 사주 운세 분석 시스템 ✨", elem_id="title")
|
530 |
gr.Markdown("### 🌟 양력 생년월일시와 출생 지역을 입력하시면 AI가 당신의 운세를 분석해드립니다! 💫", elem_id="description1")
|
531 |
gr.Markdown("### 💫 커뮤니티: https://discord.gg/openfreeai 🌈", elem_id="description3")
|
532 |
-
|
533 |
with gr.Tab("📝 기본 정보 입력 및 요약"):
|
534 |
with gr.Group(elem_classes="input-container"):
|
535 |
solYear = gr.Textbox(label="🎂 생년 (예: 1990)")
|
@@ -539,19 +621,25 @@ with gr.Blocks(css=css) as demo:
|
|
539 |
label="⏰ 생시 (예: 1030)",
|
540 |
placeholder="24시간 형식으로 입력 (예: 2230)"
|
541 |
)
|
542 |
-
|
543 |
-
|
544 |
-
|
545 |
-
|
546 |
-
|
547 |
-
|
548 |
-
info="서울은 UTC+9 입니다. 출생 지역의 UTC 시간대를 선택하세요.",
|
549 |
-
elem_classes="timezone-slider"
|
550 |
)
|
551 |
gr.Markdown(
|
552 |
-
"
|
553 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
554 |
)
|
|
|
555 |
|
556 |
with gr.Group(elem_classes="output-container"):
|
557 |
output1 = gr.JSON(label="🎯 사주 분석 결과")
|
|
|
11 |
# OpenAI API 키를 환경변수에서 가져오기
|
12 |
API_KEY = os.getenv("API_KEY")
|
13 |
|
14 |
+
TIMEZONE_CITIES = {
|
15 |
+
# 아시아
|
16 |
+
"서울, 도쿄, 평양 (UTC+9)": 9,
|
17 |
+
"베이징, 홍콩, 싱가포르, 타이페이, 마닐라 (UTC+8)": 8,
|
18 |
+
"방콕, 자카르타, 하노이, 프놈펜 (UTC+7)": 7,
|
19 |
+
"양곤 (UTC+6.5)": 6.5,
|
20 |
+
"다카, 알마티 (UTC+6)": 6,
|
21 |
+
"뉴델리, 뭄바이, 콜롬보 (UTC+5.5)": 5.5,
|
22 |
+
"타슈켄트, 이슬라마바드, 카라치 (UTC+5)": 5,
|
23 |
+
"카불 (UTC+4.5)": 4.5,
|
24 |
+
"두바이, 아부다비, 무스카트 (UTC+4)": 4,
|
25 |
+
"테헤란 (UTC+3.5)": 3.5,
|
26 |
+
"모스크바, 이스탄불, 리야드, 바그다드 (UTC+3)": 3,
|
27 |
+
|
28 |
+
# 유럽
|
29 |
+
"아테네, 헬싱키, 키예프, 카이로 (UTC+2)": 2,
|
30 |
+
"파리, 로마, 베를린, 마드리드, 암스테르담 (UTC+1)": 1,
|
31 |
+
"런던, 리스본, 더블린 (UTC+0)": 0,
|
32 |
+
|
33 |
+
# 아메리카
|
34 |
+
"아조레스 제도 (UTC-1)": -1,
|
35 |
+
"페르난도 데 노로냐 (UTC-2)": -2,
|
36 |
+
"상파울루, 부에노스아이레스, 몬테비데오 (UTC-3)": -3,
|
37 |
+
"산티아고, 아순시온 (UTC-4)": -4,
|
38 |
+
"뉴욕, 마이애미, 보스턴, 토론토 (UTC-5)": -5,
|
39 |
+
"시카고, 멕시코시티, 달라스 (UTC-6)": -6,
|
40 |
+
"덴버, 피닉스, 솔트레이크시티 (UTC-7)": -7,
|
41 |
+
"로스앤젤레스, 샌프란시스코, 라스베가스, 시애틀 (UTC-8)": -8,
|
42 |
+
"앵커리지, 페어뱅크스 (UTC-9)": -9,
|
43 |
+
"하와이, 타히티 (UTC-10)": -10,
|
44 |
+
"사모아 (UTC-11)": -11,
|
45 |
+
"베이커 섬 (UTC-12)": -12,
|
46 |
+
|
47 |
+
# 오세아니아
|
48 |
+
"오클랜드, 웰링턴 (UTC+12)": 12,
|
49 |
+
"시드니, 멜버른, 캔버라 (UTC+10)": 10,
|
50 |
+
"다윈 (UTC+9.5)": 9.5,
|
51 |
+
"애들레이드 (UTC+9.5)": 9.5,
|
52 |
+
|
53 |
+
# 아프리카
|
54 |
+
"요하네스버그, 하라레 (UTC+2)": 2,
|
55 |
+
"라고스, 알제 (UTC+1)": 1,
|
56 |
+
"다카르, 카사블랑카 (UTC+0)": 0,
|
57 |
}
|
58 |
|
59 |
def convert_to_seoul_time(year, month, day, hour, minute, timezone_offset):
|
|
|
400 |
box-shadow: 0 4px 15px rgba(0, 0, 0, 0.1);
|
401 |
}
|
402 |
|
403 |
+
/* 시간대 드롭다운 스타일 */
|
404 |
+
.timezone-dropdown {
|
|
|
|
|
405 |
background: linear-gradient(135deg, #ffffff, #f8f9fa);
|
406 |
border-radius: 10px;
|
407 |
+
padding: 15px;
|
408 |
+
margin: 15px 0;
|
409 |
box-shadow: 0 4px 15px rgba(0, 0, 0, 0.1);
|
410 |
+
border: 1px solid rgba(110, 142, 251, 0.2);
|
411 |
+
transition: all 0.3s ease;
|
412 |
}
|
413 |
|
414 |
+
.timezone-dropdown:hover {
|
415 |
+
transform: translateY(-2px);
|
416 |
+
box-shadow: 0 6px 20px rgba(0, 0, 0, 0.15);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
417 |
}
|
418 |
|
419 |
+
.timezone-dropdown select {
|
420 |
+
width: 100%;
|
421 |
+
padding: 12px;
|
422 |
+
border-radius: 8px;
|
423 |
+
border: 1px solid rgba(0, 0, 0, 0.1);
|
424 |
font-size: 14px;
|
|
|
425 |
color: #2d3748;
|
426 |
+
background-color: white;
|
427 |
}
|
428 |
|
429 |
+
.timezone-info {
|
430 |
+
background: linear-gradient(135deg, rgba(110, 142, 251, 0.1), rgba(167, 119, 227, 0.1));
|
431 |
+
border-radius: 10px;
|
432 |
+
padding: 15px;
|
433 |
+
margin: 15px 0;
|
434 |
font-size: 14px;
|
435 |
color: #4a5568;
|
436 |
+
border-left: 4px solid #6e8efb;
|
437 |
+
line-height: 1.8;
|
438 |
+
box-shadow: 0 2px 10px rgba(0, 0, 0, 0.05);
|
439 |
+
}
|
440 |
+
|
441 |
+
.timezone-info b {
|
442 |
+
color: #2d3748;
|
443 |
}
|
444 |
|
445 |
/* 분석 결과 스타일 */
|
|
|
541 |
box-shadow: 0 0 0 2px rgba(110, 142, 251, 0.2) !important;
|
542 |
transform: translateY(-1px);
|
543 |
}
|
544 |
+
|
545 |
+
/* ��롭다운 옵션 스타일 */
|
546 |
+
select option {
|
547 |
+
padding: 12px;
|
548 |
+
font-size: 14px;
|
549 |
+
background-color: white;
|
550 |
+
color: #2d3748;
|
551 |
+
}
|
552 |
+
|
553 |
+
select option:hover {
|
554 |
+
background-color: #f7fafc;
|
555 |
+
}
|
556 |
+
|
557 |
+
/* 스크롤바 스타일 */
|
558 |
+
::-webkit-scrollbar {
|
559 |
+
width: 8px;
|
560 |
+
height: 8px;
|
561 |
+
}
|
562 |
+
|
563 |
+
::-webkit-scrollbar-track {
|
564 |
+
background: #f1f1f1;
|
565 |
+
border-radius: 4px;
|
566 |
+
}
|
567 |
+
|
568 |
+
::-webkit-scrollbar-thumb {
|
569 |
+
background: linear-gradient(135deg, #6e8efb, #a777e3);
|
570 |
+
border-radius: 4px;
|
571 |
+
}
|
572 |
+
|
573 |
+
::-webkit-scrollbar-thumb:hover {
|
574 |
+
background: linear-gradient(135deg, #a777e3, #6e8efb);
|
575 |
+
}
|
576 |
+
|
577 |
+
/* 드롭다운 화살표 스타일 */
|
578 |
+
select {
|
579 |
+
appearance: none;
|
580 |
+
-webkit-appearance: none;
|
581 |
+
-moz-appearance: none;
|
582 |
+
background-image: url("data:image/svg+xml;charset=UTF-8,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='currentColor' stroke-width='2' stroke-linecap='round' stroke-linejoin='round'%3e%3cpolyline points='6 9 12 15 18 9'%3e%3c/polyline%3e%3c/svg%3e");
|
583 |
+
background-repeat: no-repeat;
|
584 |
+
background-position: right 1rem center;
|
585 |
+
background-size: 1em;
|
586 |
+
}
|
587 |
+
|
588 |
+
/* 호버 효과 애니메이션 */
|
589 |
+
@keyframes float {
|
590 |
+
0% {
|
591 |
+
transform: translateY(0px);
|
592 |
+
}
|
593 |
+
50% {
|
594 |
+
transform: translateY(-5px);
|
595 |
+
}
|
596 |
+
100% {
|
597 |
+
transform: translateY(0px);
|
598 |
+
}
|
599 |
+
}
|
600 |
+
|
601 |
+
.input-container:hover,
|
602 |
+
.timezone-dropdown:hover,
|
603 |
+
.large-output-box:hover,
|
604 |
+
.newyear-container:hover {
|
605 |
+
animation: float 2s ease-in-out infinite;
|
606 |
+
}
|
607 |
"""
|
608 |
|
609 |
# Gradio UI 부분
|
|
|
611 |
gr.Markdown("# 🔮 AI 사주 운세 분석 시스템 ✨", elem_id="title")
|
612 |
gr.Markdown("### 🌟 양력 생년월일시와 출생 지역을 입력하시면 AI가 당신의 운세를 분석해드립니다! 💫", elem_id="description1")
|
613 |
gr.Markdown("### 💫 커뮤니티: https://discord.gg/openfreeai 🌈", elem_id="description3")
|
614 |
+
|
615 |
with gr.Tab("📝 기본 정보 입력 및 요약"):
|
616 |
with gr.Group(elem_classes="input-container"):
|
617 |
solYear = gr.Textbox(label="🎂 생년 (예: 1990)")
|
|
|
621 |
label="⏰ 생시 (예: 1030)",
|
622 |
placeholder="24시간 형식으로 입력 (예: 2230)"
|
623 |
)
|
624 |
+
timezone_select = gr.Dropdown(
|
625 |
+
choices=sorted(list(TIMEZONE_CITIES.keys())), # 알파벳 순으로 정렬
|
626 |
+
value="서울, 도쿄, 평양 (UTC+9)",
|
627 |
+
label="🌍 출생 지역 시간대",
|
628 |
+
info="출생 지역의 시간대를 선택하세요. 기본값은 서울(UTC+9) 입니다.",
|
629 |
+
elem_classes="timezone-dropdown"
|
|
|
|
|
630 |
)
|
631 |
gr.Markdown(
|
632 |
+
"""
|
633 |
+
<div class="timezone-info">
|
634 |
+
ℹ️ <b>시간대 정보</b>
|
635 |
+
<br>• 선택한 시간대는 자동으로 서울 시간으로 변환되어 계산됩니다.
|
636 |
+
<br>• 예시: 뉴욕 1월 1일 오후 2시 → 서울 기준 1월 2일 오전 4시
|
637 |
+
<br>• 정확한 시간대를 모르시면 가장 가까운 대도시를 선택하세요.
|
638 |
+
</div>
|
639 |
+
""",
|
640 |
+
elem_classes="timezone-info"
|
641 |
)
|
642 |
+
|
643 |
|
644 |
with gr.Group(elem_classes="output-container"):
|
645 |
output1 = gr.JSON(label="🎯 사주 분석 결과")
|