Kims12 commited on
Commit
49065f7
Β·
verified Β·
1 Parent(s): a024e59

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +86 -47
app.py CHANGED
@@ -75,13 +75,13 @@ def get_blog_count(keyword):
75
  # ν΄λΌμ΄μ–ΈνŠΈ ID와 μ‹œν¬λ¦Ώμ„ ν™˜κ²½ λ³€μˆ˜μ—μ„œ λΆˆλŸ¬μ˜΅λ‹ˆλ‹€.
76
  client_id = CLIENT_ID
77
  client_secret = CLIENT_SECRET
78
-
79
  # keywordκ°€ λ°”μ΄νŠΈ νƒ€μž…μΌ 경우 λ””μ½”λ”©
80
  if isinstance(keyword, bytes):
81
  keyword = keyword.decode('utf-8')
82
  elif not isinstance(keyword, str):
83
  keyword = str(keyword)
84
-
85
  encText = urllib.parse.quote(keyword)
86
  url = "https://openapi.naver.com/v1/search/blog?query=" + encText
87
  request = urllib.request.Request(url)
@@ -107,40 +107,15 @@ def get_keywords_data_chunk(chunk):
107
  def get_blog_count_parallel(keyword):
108
  return (keyword, get_blog_count(keyword))
109
 
110
- def get_monthly_search_volumes(keywords, include_related_keywords=True):
111
- all_data = []
112
- chunk_size = 10 # ν‚€μ›Œλ“œλ₯Ό 10κ°œμ”© λ‚˜λˆ„μ–΄ μš”μ²­
113
-
114
- if include_related_keywords:
115
- # API 병렬 μš”μ²­
116
- with ThreadPoolExecutor(max_workers=5) as executor:
117
- futures = [executor.submit(get_keywords_data_chunk, keywords[i:i+chunk_size]) for i in range(0, len(keywords), chunk_size)]
118
- for future in futures:
119
- try:
120
- data = future.result()
121
- if 'keywordList' in data:
122
- all_data.extend(data['keywordList'])
123
- except Exception as e:
124
- print(f"Error fetching keywords data chunk: {e}")
125
- else:
126
- # 연관검색어λ₯Ό ν¬ν•¨ν•˜μ§€ μ•ŠμœΌλ―€λ‘œ μž…λ ₯ ν‚€μ›Œλ“œλ§Œ 처리
127
- for keyword in keywords:
128
- # κ°€μƒμ˜ 데이터 ꡬ쑰을 λ§žμΆ”κΈ° μœ„ν•΄
129
- all_data.append({
130
- 'relKeyword': keyword,
131
- 'monthlyPcQcCnt': '0', # μ‹€μ œ APIμ—μ„œ 값을 κ°€μ Έμ˜€λ €λ©΄ 별도 μš”μ²­ ν•„μš”
132
- 'monthlyMobileQcCnt': '0'
133
- })
134
-
135
- if not all_data:
136
- return [("Error", "데이터가 λ°˜ν™˜λ˜μ§€ μ•Šμ•˜κ±°λ‚˜ API 응닡이 μœ νš¨ν•˜μ§€ μ•ŠμŠ΅λ‹ˆλ‹€.", "", "", "")] # λΈ”λ‘œκ·Έ λ¬Έμ„œ 수 칼럼 μΆ”κ°€
137
-
138
- results = []
139
- unique_keywords = set()
140
- for item in all_data:
141
- keyword = item['relKeyword']
142
- if keyword not in unique_keywords:
143
- unique_keywords.add(keyword)
144
  monthly_pc = item.get('monthlyPcQcCnt', 0)
145
  monthly_mobile = item.get('monthlyMobileQcCnt', 0)
146
 
@@ -158,14 +133,78 @@ def get_monthly_search_volumes(keywords, include_related_keywords=True):
158
  monthly_mobile = 0
159
 
160
  total_searches = monthly_pc + monthly_mobile
161
- results.append((keyword, monthly_pc, monthly_mobile, total_searches))
162
-
163
- if len(results) >= 100 and include_related_keywords:
164
- break
 
 
 
 
 
 
165
 
166
  if include_related_keywords:
167
- # λΈ”λ‘œκ·Έ λ¬Έμ„œ 수 병렬 μš”μ²­
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
168
  with ThreadPoolExecutor(max_workers=5) as executor:
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
169
  blog_futures = [executor.submit(get_blog_count_parallel, result[0]) for result in results]
170
  for i, future in enumerate(blog_futures):
171
  try:
@@ -174,10 +213,8 @@ def get_monthly_search_volumes(keywords, include_related_keywords=True):
174
  except Exception as e:
175
  print(f"Error fetching blog count for keyword '{results[i][0]}': {e}")
176
  results[i] = (results[i][0], results[i][1], results[i][2], results[i][3], "Error")
177
- else:
178
- # λΈ”λ‘œκ·Έ λ¬Έμ„œ 수 병렬 μš”μ²­ (연관검색어가 아닐 경우 각 ν‚€μ›Œλ“œμ— λŒ€ν•΄)
179
- with ThreadPoolExecutor(max_workers=5) as executor:
180
- blog_futures = [executor.submit(get_blog_count_parallel, keyword) for keyword in results]
181
  temp_results = []
182
  for future in blog_futures:
183
  try:
@@ -200,7 +237,9 @@ def save_to_excel(results, keyword):
200
  return file_path
201
 
202
  def display_search_volumes(keywords, include_related):
203
- keyword_list = [keyword.strip() for keyword in keywords.split(',')]
 
 
204
  results = get_monthly_search_volumes(keyword_list, include_related_keywords=include_related)
205
  file_path = save_to_excel(results, keywords)
206
  return results, file_path
@@ -208,7 +247,7 @@ def display_search_volumes(keywords, include_related):
208
  iface = gr.Interface(
209
  fn=display_search_volumes,
210
  inputs=[
211
- gr.Textbox(placeholder="ν‚€μ›Œλ“œλ₯Ό μž…λ ₯ν•˜μ„Έμš”"),
212
  gr.Checkbox(label="연관검색어 포함", value=True) # 연관검색어 ν† κΈ€ μΆ”κ°€
213
  ],
214
  outputs=[
 
75
  # ν΄λΌμ΄μ–ΈνŠΈ ID와 μ‹œν¬λ¦Ώμ„ ν™˜κ²½ λ³€μˆ˜μ—μ„œ λΆˆλŸ¬μ˜΅λ‹ˆλ‹€.
76
  client_id = CLIENT_ID
77
  client_secret = CLIENT_SECRET
78
+
79
  # keywordκ°€ λ°”μ΄νŠΈ νƒ€μž…μΌ 경우 λ””μ½”λ”©
80
  if isinstance(keyword, bytes):
81
  keyword = keyword.decode('utf-8')
82
  elif not isinstance(keyword, str):
83
  keyword = str(keyword)
84
+
85
  encText = urllib.parse.quote(keyword)
86
  url = "https://openapi.naver.com/v1/search/blog?query=" + encText
87
  request = urllib.request.Request(url)
 
107
  def get_blog_count_parallel(keyword):
108
  return (keyword, get_blog_count(keyword))
109
 
110
+ def get_search_volumes(keyword):
111
+ """
112
+ 단일 ν‚€μ›Œλ“œμ˜ μ›” κ²€μƒ‰λŸ‰μ„ κ°€μ Έμ˜€λŠ” ν•¨μˆ˜.
113
+ """
114
+ api = NaverAPI(BASE_URL, API_KEY, SECRET_KEY, CUSTOMER_ID)
115
+ try:
116
+ data = api.get_keywords_data([keyword])
117
+ if 'keywordList' in data and len(data['keywordList']) > 0:
118
+ item = data['keywordList'][0]
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
119
  monthly_pc = item.get('monthlyPcQcCnt', 0)
120
  monthly_mobile = item.get('monthlyMobileQcCnt', 0)
121
 
 
133
  monthly_mobile = 0
134
 
135
  total_searches = monthly_pc + monthly_mobile
136
+ return (keyword, monthly_pc, monthly_mobile, total_searches)
137
+ else:
138
+ return (keyword, 0, 0, 0)
139
+ except Exception as e:
140
+ print(f"Error fetching search volumes for keyword '{keyword}': {e}")
141
+ return (keyword, 0, 0, 0)
142
+
143
+ def get_monthly_search_volumes(keywords, include_related_keywords=True):
144
+ all_data = []
145
+ results = []
146
 
147
  if include_related_keywords:
148
+ chunk_size = 10 # ν‚€μ›Œλ“œλ₯Ό 10κ°œμ”© λ‚˜λˆ„μ–΄ μš”μ²­
149
+ # API 병렬 μš”μ²­
150
+ with ThreadPoolExecutor(max_workers=5) as executor:
151
+ futures = [executor.submit(get_keywords_data_chunk, keywords[i:i+chunk_size]) for i in range(0, len(keywords), chunk_size)]
152
+ for future in futures:
153
+ try:
154
+ data = future.result()
155
+ if 'keywordList' in data:
156
+ all_data.extend(data['keywordList'])
157
+ except Exception as e:
158
+ print(f"Error fetching keywords data chunk: {e}")
159
+
160
+ if not all_data:
161
+ return [("Error", "데이터가 λ°˜ν™˜λ˜μ§€ μ•Šμ•˜κ±°λ‚˜ API 응닡이 μœ νš¨ν•˜μ§€ μ•ŠμŠ΅λ‹ˆλ‹€.", "", "", "")]
162
+
163
+ unique_keywords = set()
164
+ for item in all_data:
165
+ keyword = item['relKeyword']
166
+ if keyword not in unique_keywords:
167
+ unique_keywords.add(keyword)
168
+ monthly_pc = item.get('monthlyPcQcCnt', 0)
169
+ monthly_mobile = item.get('monthlyMobileQcCnt', 0)
170
+
171
+ if isinstance(monthly_pc, str):
172
+ monthly_pc = monthly_pc.replace(',', '').replace('< 10', '0')
173
+ try:
174
+ monthly_pc = int(monthly_pc)
175
+ except ValueError:
176
+ monthly_pc = 0
177
+ if isinstance(monthly_mobile, str):
178
+ monthly_mobile = monthly_mobile.replace(',', '').replace('< 10', '0')
179
+ try:
180
+ monthly_mobile = int(monthly_mobile)
181
+ except ValueError:
182
+ monthly_mobile = 0
183
+
184
+ total_searches = monthly_pc + monthly_mobile
185
+ results.append((keyword, monthly_pc, monthly_mobile, total_searches))
186
+
187
+ if len(results) >= 100:
188
+ break
189
+
190
+ else:
191
+ # 연관검색어λ₯Ό ν¬ν•¨ν•˜μ§€ μ•ŠμœΌλ―€λ‘œ μž…λ ₯ ν‚€μ›Œλ“œλ§Œ 처리
192
  with ThreadPoolExecutor(max_workers=5) as executor:
193
+ futures = [executor.submit(get_search_volumes, keyword) for keyword in keywords]
194
+ for future in futures:
195
+ try:
196
+ result = future.result()
197
+ results.append(result)
198
+ except Exception as e:
199
+ print(f"Error fetching search volumes for keyword '{keyword}': {e}")
200
+ results.append((keyword, 0, 0, 0))
201
+
202
+ if not results:
203
+ return [("Error", "데이터가 λ°˜ν™˜λ˜μ§€ μ•Šμ•˜κ±°λ‚˜ API 응닡이 μœ νš¨ν•˜μ§€ μ•ŠμŠ΅λ‹ˆλ‹€.", "", "", "")]
204
+
205
+ # λΈ”λ‘œκ·Έ λ¬Έμ„œ 수 병렬 μš”μ²­
206
+ with ThreadPoolExecutor(max_workers=5) as executor:
207
+ if include_related_keywords:
208
  blog_futures = [executor.submit(get_blog_count_parallel, result[0]) for result in results]
209
  for i, future in enumerate(blog_futures):
210
  try:
 
213
  except Exception as e:
214
  print(f"Error fetching blog count for keyword '{results[i][0]}': {e}")
215
  results[i] = (results[i][0], results[i][1], results[i][2], results[i][3], "Error")
216
+ else:
217
+ blog_futures = [executor.submit(get_blog_count_parallel, result[0]) for result in results]
 
 
218
  temp_results = []
219
  for future in blog_futures:
220
  try:
 
237
  return file_path
238
 
239
  def display_search_volumes(keywords, include_related):
240
+ keyword_list = [keyword.strip() for keyword in keywords.split(',') if keyword.strip()]
241
+ if not keyword_list:
242
+ return [("Error", "μž…λ ₯된 ν‚€μ›Œλ“œκ°€ μ—†μŠ΅λ‹ˆλ‹€.", "", "", "")], None
243
  results = get_monthly_search_volumes(keyword_list, include_related_keywords=include_related)
244
  file_path = save_to_excel(results, keywords)
245
  return results, file_path
 
247
  iface = gr.Interface(
248
  fn=display_search_volumes,
249
  inputs=[
250
+ gr.Textbox(placeholder="ν‚€μ›Œλ“œλ₯Ό μž…λ ₯ν•˜μ„Έμš” (μ‰Όν‘œλ‘œ ꡬ뢄)", lines=2),
251
  gr.Checkbox(label="연관검색어 포함", value=True) # 연관검색어 ν† κΈ€ μΆ”κ°€
252
  ],
253
  outputs=[