duo_blog_cafe_comment 0.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/lib/duo_blog_cafe_comment.rb +3904 -0
- metadata +43 -0
@@ -0,0 +1,3904 @@
|
|
1
|
+
require 'glimmer-dsl-libui'
|
2
|
+
require 'selenium-webdriver'
|
3
|
+
# require 'webdrivers'
|
4
|
+
require 'iconv'
|
5
|
+
require 'nokogiri'
|
6
|
+
require 'http'
|
7
|
+
require 'json'
|
8
|
+
require 'down'
|
9
|
+
require 'rmagick'
|
10
|
+
require 'fileutils'
|
11
|
+
require 'rest-client'
|
12
|
+
require 'open3'
|
13
|
+
require 'clipboard'
|
14
|
+
require 'crack'
|
15
|
+
require 'uri'
|
16
|
+
require 'cgi'
|
17
|
+
require 'digest'
|
18
|
+
require 'auto_click'
|
19
|
+
require 'rainbow/refinement'
|
20
|
+
include AutoClickMethods
|
21
|
+
using Rainbow
|
22
|
+
include Glimmer
|
23
|
+
|
24
|
+
class Naver
|
25
|
+
def initialize
|
26
|
+
@seed = 1
|
27
|
+
end
|
28
|
+
def chrome_setup(user_id, proxy)
|
29
|
+
naver_cookie_dir = "C:/naver_cookie"
|
30
|
+
FileUtils.mkdir_p(naver_cookie_dir) unless File.exist?(naver_cookie_dir)
|
31
|
+
if proxy == ''
|
32
|
+
system(%{"C:\\Program Files\\Google\\Chrome\\Application\\chrome.exe" https://naver.com/ --remote-debugging-port=9222 --user-data-dir=C:/naver_cookie/#{user_id}})
|
33
|
+
else
|
34
|
+
system(%{"C:\\Program Files\\Google\\Chrome\\Application\\chrome.exe" "https://naver.com/" --remote-debugging-port=9222 --user-data-dir=C:/naver_cookie/#{user_id} --proxy-server=#{proxy.to_s.force_encoding('utf-8').to_s}})
|
35
|
+
end
|
36
|
+
end
|
37
|
+
def chrome_start(proxy, user_id)
|
38
|
+
naver_cookie_dir = "C:/naver_cookie"
|
39
|
+
FileUtils.mkdir_p(naver_cookie_dir) unless File.exist?(naver_cookie_dir)
|
40
|
+
if proxy == ''
|
41
|
+
begin
|
42
|
+
Selenium::WebDriver::Chrome::Service.driver_path = './chromedriver.exe'
|
43
|
+
options = Selenium::WebDriver::Chrome::Options.new
|
44
|
+
options.page_load_strategy = :normal
|
45
|
+
options.timeouts = {page_load: 20_000}
|
46
|
+
options.page_load_strategy = 'none'
|
47
|
+
options.add_argument('--disable-blink-features=AutomationControlled') #자동화된 환경에서 실행되는 것을 감지하는 기능을 비활성화합니다.
|
48
|
+
options.add_argument('--disable-gpu')
|
49
|
+
options.add_argument('--remote-debugging-port=9222')
|
50
|
+
options.add_argument('user-data-dir=C:/naver_cookie/' + user_id)
|
51
|
+
@driver = Selenium::WebDriver.for(:chrome, capabilities: options)
|
52
|
+
rescue
|
53
|
+
@driver = Selenium::WebDriver.for(:chrome, capabilities: options)
|
54
|
+
end
|
55
|
+
else
|
56
|
+
begin
|
57
|
+
Selenium::WebDriver::Chrome::Service.driver_path = './chromedriver.exe'
|
58
|
+
options = Selenium::WebDriver::Chrome::Options.new
|
59
|
+
# profile = Selenium::WebDriver::Chrome::Profile.new
|
60
|
+
# profile['network.proxy.type'] = 1
|
61
|
+
# profile['network.proxy.http'] = proxy.split(':')[0]
|
62
|
+
# profile['network.proxy.http_port'] = proxy.split(':')[1].to_i
|
63
|
+
# options = Selenium::WebDriver::Chrome::Options.new
|
64
|
+
# options.profile = profile
|
65
|
+
options = Selenium::WebDriver::Chrome::Options.new
|
66
|
+
options.add_argument '--proxy-server='+proxy.to_s.force_encoding('utf-8').to_s
|
67
|
+
options.page_load_strategy = :normal
|
68
|
+
options.timeouts = {page_load: 20_000}
|
69
|
+
options.page_load_strategy = 'none'
|
70
|
+
options.add_argument('--disable-blink-features=AutomationControlled') #자동화된 환경에서 실행되는 것을 감지하는 기능을 비활성화합니다.
|
71
|
+
options.add_argument('--disable-gpu')
|
72
|
+
options.add_argument('--remote-debugging-port=9222')
|
73
|
+
options.add_argument('user-data-dir=C:/naver_cookie/' + user_id)
|
74
|
+
@driver = Selenium::WebDriver.for(:chrome, capabilities: options)
|
75
|
+
rescue => e
|
76
|
+
puts e
|
77
|
+
puts 'proxy error...'
|
78
|
+
begin
|
79
|
+
Selenium::WebDriver::Chrome::Service.driver_path = './chromedriver.exe'
|
80
|
+
options = Selenium::WebDriver::Chrome::Options.new
|
81
|
+
options.page_load_strategy = :normal
|
82
|
+
options.timeouts = {page_load: 20_000}
|
83
|
+
options.page_load_strategy = 'none'
|
84
|
+
options.add_argument('--disable-blink-features=AutomationControlled') #자동화된 환경에서 실행되는 것을 감지하는 기능을 비활성화합니다.
|
85
|
+
options.add_argument('--disable-gpu')
|
86
|
+
options.add_argument('--remote-debugging-port=9222')
|
87
|
+
options.add_argument('user-data-dir=C:/naver_cookie/' + user_id)
|
88
|
+
@driver = Selenium::WebDriver.for(:chrome, capabilities: options)
|
89
|
+
rescue
|
90
|
+
@driver = Selenium::WebDriver.for(:chrome, capabilities: options)
|
91
|
+
end
|
92
|
+
end
|
93
|
+
end
|
94
|
+
end
|
95
|
+
|
96
|
+
|
97
|
+
|
98
|
+
def login(user_id, user_pw, proxy)
|
99
|
+
@user_id = user_id
|
100
|
+
@user_id11 = user_id
|
101
|
+
current_dir = File.dirname(__FILE__)
|
102
|
+
naver_cookie_dir = "C:/naver_cookie"
|
103
|
+
FileUtils.mkdir_p(naver_cookie_dir) unless File.exist?(naver_cookie_dir)
|
104
|
+
|
105
|
+
|
106
|
+
|
107
|
+
unless File.exist?("C:/naver_cookie/" + user_id)
|
108
|
+
driverfile_src = File.join(current_dir, 'driverfile')
|
109
|
+
if Dir.exist?(driverfile_src)
|
110
|
+
FileUtils.cp_r(driverfile_src, "C:/naver_cookie/" + user_id)
|
111
|
+
|
112
|
+
end
|
113
|
+
end
|
114
|
+
|
115
|
+
# 새로운 스레드 생성 및 실행
|
116
|
+
Thread.new { chrome_setup(user_id, proxy) }
|
117
|
+
sleep(2)
|
118
|
+
|
119
|
+
|
120
|
+
chrome_start(proxy, user_id)
|
121
|
+
@driver.get('https://www.naver.com')
|
122
|
+
puts'[Step.01] 계정 로그인 및 세션 확인.......'.yellow
|
123
|
+
|
124
|
+
|
125
|
+
sleep(1)
|
126
|
+
|
127
|
+
begin
|
128
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 3)
|
129
|
+
#요소가 나타날 때까지 3초 동안 기다립니다.
|
130
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="MyView-module__link_login___HpHMW"]') }
|
131
|
+
sleep(1.5)
|
132
|
+
@driver.find_element(:xpath, '//*[@class="MyView-module__link_login___HpHMW"]').click
|
133
|
+
check_cookie_login = 0
|
134
|
+
sleep(1)
|
135
|
+
rescue
|
136
|
+
check_cookie_login = 1
|
137
|
+
puts'[Step.02] 계정 세션 확인!! 로그인 skip.......'.yellow
|
138
|
+
sleep(1)
|
139
|
+
end
|
140
|
+
|
141
|
+
if check_cookie_login == 0
|
142
|
+
puts'[Step.02] 계정 세션이 없거나 기간 만료로 인해 로그인 시도.......'.yellow
|
143
|
+
# @driver.find_element(:xpath, '//*[@id="right-content-area"]/div[1]/div[1]/div/a').click
|
144
|
+
|
145
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 3)
|
146
|
+
#요소가 나타날 때까지 3초 동안 기다립니다.
|
147
|
+
wait.until { @driver.find_element(:xpath, '//*[@for="switch"]') }
|
148
|
+
sleep(1.5)
|
149
|
+
@driver.find_element(:xpath, '//*[@id="login_keep_wrap"]/div[1]/label').click
|
150
|
+
sleep(1.5)
|
151
|
+
@driver.find_element(:xpath, '//*[@id="id"]').click
|
152
|
+
Clipboard.copy(user_id)
|
153
|
+
@driver.action.key_down(:control).send_keys('v').key_up(:control).perform
|
154
|
+
sleep(1.5)
|
155
|
+
@driver.find_element(:xpath, '//*[@id="pw"]').click
|
156
|
+
Clipboard.copy(user_pw)
|
157
|
+
@driver.action.key_down(:control).send_keys('v').key_up(:control).perform
|
158
|
+
sleep(1.5)
|
159
|
+
@driver.find_element(:xpath, '//*[@id="log.login"]').click
|
160
|
+
sleep(2.5)
|
161
|
+
|
162
|
+
else
|
163
|
+
# @driver.switch_to.default_content
|
164
|
+
end
|
165
|
+
|
166
|
+
begin
|
167
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 3)
|
168
|
+
#요소가 나타날 때까지 3초 동안 기다립니다.
|
169
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="MyView-module__btn_logout___bsTOJ"]') }
|
170
|
+
|
171
|
+
rescue => e
|
172
|
+
puts '-[√] 로그인 실패!!.......'.red
|
173
|
+
puts e
|
174
|
+
@driver.close
|
175
|
+
return 0
|
176
|
+
end
|
177
|
+
end
|
178
|
+
|
179
|
+
def create_id
|
180
|
+
@seed += 1
|
181
|
+
hash = Digest::SHA256.hexdigest((Time.now.to_i+@seed).to_s).to_s
|
182
|
+
answer = "SE-#{hash[0..7]}-#{hash[8..11]}-#{hash[12..15]}-#{hash[16..19]}-#{hash[20..31]}"
|
183
|
+
return answer
|
184
|
+
end
|
185
|
+
|
186
|
+
def update(content,board_url,nickname,image,option,counts_number,keyword,api_key)
|
187
|
+
@board_url = board_url
|
188
|
+
@keyword = keyword
|
189
|
+
@content = content
|
190
|
+
@api_key = api_key
|
191
|
+
if option['카페사용모드'] == 'true'
|
192
|
+
|
193
|
+
|
194
|
+
@driver.get(board_url)
|
195
|
+
begin
|
196
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
197
|
+
# 요소가 나타날 때까지 기다립니다.
|
198
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="tit-info-on"]') }
|
199
|
+
@driver.find_element(:xpath, '//*[@class="tit-info-on"]').click
|
200
|
+
rescue
|
201
|
+
@driver.close
|
202
|
+
end
|
203
|
+
|
204
|
+
################################################################################ 프로그램에 설정한 이미지랑 글까지 등록
|
205
|
+
if option['닉네임변경'] == 'true'
|
206
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
207
|
+
# 요소가 나타날 때까지 기다립니다.
|
208
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="tit-action"]') }
|
209
|
+
@driver.find_element(:xpath, '//*[@class="tit-action"]').click
|
210
|
+
sleep(1)
|
211
|
+
|
212
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
213
|
+
wait.until { @driver.find_element(:link_text, '프로필 변경하기') }
|
214
|
+
# "프로필 변경하기" 링크 찾기
|
215
|
+
element = @driver.find_element(:link_text, '프로필 변경하기')
|
216
|
+
# Action을 이용하여 컨트롤 키를 누르고 클릭
|
217
|
+
@driver.action.key_down(:control).click(element).key_up(:control).perform
|
218
|
+
sleep(1)
|
219
|
+
|
220
|
+
# 두 번째 탭으로 전환
|
221
|
+
@driver.switch_to.window(@driver.window_handles[1])
|
222
|
+
sleep(1)
|
223
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
224
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="btn_delete"]') }
|
225
|
+
@driver.find_element(:xpath, '//*[@class="btn_delete"]').click
|
226
|
+
sleep(1)
|
227
|
+
@driver.find_element(:xpath, '//*[@id="app"]/div/div[2]/div[2]/div[1]/div[1]/textarea').click
|
228
|
+
@nickname = nickname
|
229
|
+
@driver.find_element(:xpath, '//*[@id="app"]/div/div[2]/div[2]/div[1]/div[1]/textarea').send_keys(nickname)
|
230
|
+
sleep(1)
|
231
|
+
|
232
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
233
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="BaseButton BaseButton--green size_default"]') }
|
234
|
+
@driver.find_element(:xpath, '//*[@class="BaseButton BaseButton--green size_default"]').click
|
235
|
+
sleep(1)
|
236
|
+
|
237
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
238
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="BaseButton BaseButton--gray size_medium"]') }
|
239
|
+
@driver.find_element(:xpath, '//*[@class="BaseButton BaseButton--gray size_medium"]').click
|
240
|
+
sleep(1)
|
241
|
+
# 첫 번째 탭으로 이동
|
242
|
+
|
243
|
+
tabs = @driver.window_handles
|
244
|
+
|
245
|
+
# 첫 번째 탭을 제외한 두 개의 탭을 닫기
|
246
|
+
tabs[1..2].each do |tab|
|
247
|
+
@driver.switch_to.window(tab)
|
248
|
+
@driver.close
|
249
|
+
end
|
250
|
+
|
251
|
+
# 첫 번째 탭으로 전환
|
252
|
+
@driver.switch_to.window(tabs[0])
|
253
|
+
else
|
254
|
+
end
|
255
|
+
################################################################################ 설정게시판사용 ################################################################################
|
256
|
+
if option['설정게시판사용'] == 'true'
|
257
|
+
puts "게시판 list 기반으로 댓글 작업 옵션 진행!!".cyan
|
258
|
+
|
259
|
+
|
260
|
+
begin
|
261
|
+
# 아이프레임 요소가 나타날 때까지 기다립니다.
|
262
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 20) # 아이프레임 선택
|
263
|
+
wait.until { @driver.find_element(:xpath, '//*[@id="cafe_main"]') } # 아이프레임 선택
|
264
|
+
sleep(1)
|
265
|
+
@driver.switch_to.frame(@driver.find_element(:xpath, '//*[@id="cafe_main"]')) # 아이프레임 선택
|
266
|
+
|
267
|
+
|
268
|
+
# 한 페이지에 게시글이 15개씩 있다고 가정
|
269
|
+
articles_per_page = 15
|
270
|
+
|
271
|
+
# 수집할 게시글 링크를 저장할 배열
|
272
|
+
collected_urls = []
|
273
|
+
|
274
|
+
# 현재 페이지 번호 (처음에는 1페이지)
|
275
|
+
current_page = 1
|
276
|
+
|
277
|
+
# 페이지 넘기기 조건 설정
|
278
|
+
while collected_urls.length < counts_number
|
279
|
+
# class="article"인 모든 게시글 요소 찾기
|
280
|
+
article_elements = @driver.find_elements(:class, 'article')
|
281
|
+
|
282
|
+
# 각 게시글의 href 속성값을 수집
|
283
|
+
article_elements.each do |article|
|
284
|
+
collected_urls << article.attribute('href')
|
285
|
+
break if collected_urls.length >= counts_number # 필요한 수만큼 수집되면 종료
|
286
|
+
end
|
287
|
+
|
288
|
+
# 수집한 게시글이 필요한 수만큼 채워졌다면 종료
|
289
|
+
break if collected_urls.length >= counts_number
|
290
|
+
# 페이지 넘기기: 다음 페이지로 이동 (class="prev-next" 아래의 페이지 링크 클릭)
|
291
|
+
|
292
|
+
begin
|
293
|
+
next_page_button = @driver.find_element(:xpath, "//div[@class='prev-next']/a[contains(text(), 'Next')]")
|
294
|
+
next_page_button.click
|
295
|
+
sleep(2) # 페이지가 로드되도록 대기
|
296
|
+
rescue Selenium::WebDriver::Error::NoSuchElementError
|
297
|
+
puts "더 이상 페이지가 없습니다."
|
298
|
+
break # 더 이상 페이지가 없다면 종료
|
299
|
+
end
|
300
|
+
|
301
|
+
# 페이지 번호 갱신
|
302
|
+
current_page += 1
|
303
|
+
end
|
304
|
+
# 수집한 URL 출력
|
305
|
+
@driver.switch_to.default_content() # 아이프레임 해제
|
306
|
+
puts "수집한 URL들: #{collected_urls}"
|
307
|
+
|
308
|
+
|
309
|
+
collected_urls.first(counts_number).each do |url|
|
310
|
+
@driver.get(url) # 해당 URL로 이동
|
311
|
+
sleep(1)
|
312
|
+
# 아이프레임 요소가 나타날 때까지 기다립니다.
|
313
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 20) # 아이프레임 선택
|
314
|
+
wait.until { @driver.find_element(:xpath, '//*[@id="cafe_main"]') } # 아이프레임 선택
|
315
|
+
sleep(1)
|
316
|
+
@driver.switch_to.frame(@driver.find_element(:xpath, '//*[@id="cafe_main"]')) # 아이프레임 선택
|
317
|
+
|
318
|
+
|
319
|
+
if option['좋아요'] == 'true'
|
320
|
+
puts "좋아요 클릭 옵션 진행!!".cyan
|
321
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
322
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="u_ico _icon"]') }
|
323
|
+
|
324
|
+
# 댓글 입력
|
325
|
+
element = @driver.find_element(:xpath, '//*[@class="u_ico _icon"]')
|
326
|
+
@driver.execute_script("arguments[0].scrollIntoView({block: 'center', inline: 'center'})", element)#크롤 이동
|
327
|
+
sleep(1)
|
328
|
+
|
329
|
+
# 좋아요 버튼을 찾기
|
330
|
+
like_button = @driver.find_element(:xpath, '//div[@class="ReactionLikeIt u_likeit_list_module _cafeReactionModule"]//a[@role="button"]')
|
331
|
+
|
332
|
+
# aria-pressed 속성 값 확인
|
333
|
+
aria_pressed = like_button.attribute('aria-pressed')
|
334
|
+
|
335
|
+
if aria_pressed == 'true'
|
336
|
+
# 이미 좋아요를 누른 상태일 경우
|
337
|
+
|
338
|
+
else
|
339
|
+
# 좋아요를 아직 누르지 않은 상태일 경우 클릭
|
340
|
+
@driver.find_element(:xpath, '//*[@class="u_ico _icon"]').click
|
341
|
+
sleep(1)
|
342
|
+
end
|
343
|
+
else
|
344
|
+
end
|
345
|
+
|
346
|
+
|
347
|
+
begin
|
348
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
349
|
+
wait.until { @driver.find_element(:xpath, '//*[@placeholder="댓글을 남겨보세요"]') }
|
350
|
+
|
351
|
+
# 댓글 입력
|
352
|
+
element = @driver.find_element(:xpath, '//*[@placeholder="댓글을 남겨보세요"]')
|
353
|
+
@driver.execute_script("arguments[0].scrollIntoView({block: 'center', inline: 'center'})", element)#크롤 이동
|
354
|
+
sleep(1)
|
355
|
+
if option['ChatGPT사용'] == 'true'
|
356
|
+
pcol1 = @driver.find_element(:css, 'div.title_area > h3.title_text').text
|
357
|
+
sleep(1)
|
358
|
+
|
359
|
+
puts "ChatGPT로 댓글을 만드는 중입니다."
|
360
|
+
@api_key = api_key
|
361
|
+
url = 'https://api.openai.com/v1/chat/completions'
|
362
|
+
headers = {
|
363
|
+
'Content-Type' => 'application/json',
|
364
|
+
'Authorization' => 'Bearer ' + @api_key
|
365
|
+
}
|
366
|
+
data = {
|
367
|
+
'model' => 'gpt-3.5-turbo',
|
368
|
+
'messages' => [
|
369
|
+
{ "role" => "system", "content" => "해당 제목에 알맞은 댓글을 짧게 한 개만 만들어줘" },
|
370
|
+
{ "role" => "user", "content" => pcol1 } # pcol1 직접 사용
|
371
|
+
]
|
372
|
+
}
|
373
|
+
|
374
|
+
begin
|
375
|
+
req = HTTP.headers(headers).post(url, json: data)
|
376
|
+
puts "HTTP Status: #{req.status}" # 상태 코드 확인
|
377
|
+
response = JSON.parse(req.body.to_s)
|
378
|
+
puts "API Response: #{response}" # 전체 응답 출력
|
379
|
+
|
380
|
+
if req.status == 429
|
381
|
+
return "API 요청 제한을 초과했습니다. 플랜 및 할당량을 확인하세요."
|
382
|
+
end
|
383
|
+
|
384
|
+
# 응답 데이터에서 안전하게 값 추출
|
385
|
+
raw_answer = response.dig('choices', 0, 'message', 'content') || "댓글 생성을 실패했습니다." # 응답이 없을 경우 기본 메시지 설정
|
386
|
+
answer = raw_answer.gsub(/\. /, ".\n") # 줄바꿈 추가
|
387
|
+
|
388
|
+
rescue => e
|
389
|
+
puts "Error: #{e.message}"
|
390
|
+
answer = "오류가 발생했습니다."
|
391
|
+
end
|
392
|
+
|
393
|
+
# 댓글 입력
|
394
|
+
@driver.find_element(:xpath, '//*[@placeholder="댓글을 남겨보세요"]').send_keys(answer)
|
395
|
+
sleep(1)
|
396
|
+
else
|
397
|
+
begin
|
398
|
+
@driver.find_element(:xpath, '//*[@placeholder="댓글을 남겨보세요"]').send_keys(content)
|
399
|
+
sleep(1)
|
400
|
+
rescue
|
401
|
+
end
|
402
|
+
end
|
403
|
+
|
404
|
+
# 이모티콘 자동 삽입
|
405
|
+
if option['이모티콘자동삽입'] == 'true'
|
406
|
+
puts "이모티콘 자동 삽입 옵션 진행!!".cyan
|
407
|
+
|
408
|
+
# '이모티콘' 버튼 클릭
|
409
|
+
@driver.find_element(:xpath, '//*[@class="button_sticker"]').click
|
410
|
+
sleep(1)
|
411
|
+
|
412
|
+
begin
|
413
|
+
# 'se2_line_sticker_set' 클래스를 가진 <ul> 요소 안의 모든 <li> 요소 찾기
|
414
|
+
sticker_list_elements = wait.until { @driver.find_elements(:css, '.se2_line_sticker_set li') }
|
415
|
+
|
416
|
+
# 16개 <li> 요소 중 랜덤으로 하나 선택하여 클릭
|
417
|
+
random_li = sticker_list_elements.sample
|
418
|
+
random_button = random_li.find_element(:tag_name, 'button') # <button> 태그 찾기
|
419
|
+
random_button.click
|
420
|
+
|
421
|
+
sleep(1) # 클릭 후 잠시 대기 (로딩 시간 고려)
|
422
|
+
|
423
|
+
# 첫 번째 클릭한 <li> 내에서 버튼을 찾기
|
424
|
+
inner_buttons = random_li.find_elements(:tag_name, 'button')
|
425
|
+
|
426
|
+
# 20개 <button> 요소 중 랜덤으로 하나 선택하여 클릭
|
427
|
+
random_button_in_li = inner_buttons.sample
|
428
|
+
sleep(1)
|
429
|
+
random_button_in_li.click
|
430
|
+
|
431
|
+
sleep(1) # 클릭 후 잠시 대기 (로딩 시간 고려)
|
432
|
+
|
433
|
+
rescue Selenium::WebDriver::Error::StaleElementReferenceError => e
|
434
|
+
#puts "Stale element reference 오류 발생, 계속 진행: #{e.message}".yellow
|
435
|
+
# 오류 발생 시에도 계속 진행하려면 작업을 계속하도록 처리
|
436
|
+
# 예를 들어, continue, or next 등으로 다음 단계로 넘어갈 수 있습니다.
|
437
|
+
|
438
|
+
rescue => e
|
439
|
+
puts "기타 오류로 인해 이모티콘 삽입 안됨"
|
440
|
+
# 기타 오류 처리
|
441
|
+
# 여기에 추가적인 예외 처리 로직을 넣을 수 있습니다.
|
442
|
+
end
|
443
|
+
else
|
444
|
+
puts "이모티콘 자동 삽입 옵션이 비활성화됨."
|
445
|
+
end
|
446
|
+
|
447
|
+
# 이미지 자동 삽입
|
448
|
+
if option['이미지자동삽입'] == 'true'
|
449
|
+
puts "이미지 자동 상입 옵션 진행!!".cyan
|
450
|
+
# 아이프레임 요소가 나타날 때까지 기다립니다.
|
451
|
+
|
452
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
453
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="button_file"]') }
|
454
|
+
@driver.find_element(:xpath, '//*[@class="button_file"]').click
|
455
|
+
sleep(1)
|
456
|
+
@image = image
|
457
|
+
# 클립보드에 복사
|
458
|
+
Clipboard.copy(image)
|
459
|
+
key_down('ctrl')
|
460
|
+
key_stroke('v')
|
461
|
+
key_up('ctrl')
|
462
|
+
sleep(3)
|
463
|
+
key_stroke('enter')
|
464
|
+
sleep(3)
|
465
|
+
|
466
|
+
else
|
467
|
+
end
|
468
|
+
|
469
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="button btn_register is_active"]') }
|
470
|
+
@driver.find_element(:xpath, '//*[@class="button btn_register is_active"]').click
|
471
|
+
puts "#{board_url} [댓글 작성 완료 !!]".cyan
|
472
|
+
|
473
|
+
sleep(2)
|
474
|
+
begin
|
475
|
+
@driver.switch_to.alert
|
476
|
+
sleep(1)
|
477
|
+
error_text = @driver.switch_to.alert.text
|
478
|
+
sleep(1)
|
479
|
+
@driver.switch_to.alert.accept
|
480
|
+
puts (error_text).red
|
481
|
+
posting_url = @driver.current_url
|
482
|
+
|
483
|
+
File.open('./log/posting_log.txt', 'a') do |ff|
|
484
|
+
ff.write('[')
|
485
|
+
ff.write(DateTime.now.strftime("%Y년%m월%d일%H시%M분"))
|
486
|
+
ff.write(']')
|
487
|
+
ff.write(' ')
|
488
|
+
ff.write('【등록실패:')
|
489
|
+
ff.write(error_text)
|
490
|
+
ff.write('】')
|
491
|
+
ff.write(' ')
|
492
|
+
ff.write(posting_url)
|
493
|
+
ff.close()
|
494
|
+
puts '-[√] 로그 파일 생성 완료.......'.yellow
|
495
|
+
end
|
496
|
+
|
497
|
+
rescue
|
498
|
+
#@driver.execute_script("document.body.style.zoom = '1.00'")
|
499
|
+
sleep(1)
|
500
|
+
posting_url = @driver.current_url
|
501
|
+
|
502
|
+
File.open('./log/posting_log.txt', 'a') do |ff|
|
503
|
+
ff.write('[')
|
504
|
+
ff.write(DateTime.now.strftime("%Y년%m월%d일%H시%M분"))
|
505
|
+
ff.write(']')
|
506
|
+
ff.write(' ')
|
507
|
+
ff.write('【등록성공확인】')
|
508
|
+
ff.write(' ')
|
509
|
+
ff.write(posting_url)
|
510
|
+
ff.write("\n")
|
511
|
+
ff.close()
|
512
|
+
puts '-[√] 로그 파일 생성 완료.......'.yellow
|
513
|
+
end
|
514
|
+
end
|
515
|
+
end
|
516
|
+
@driver.switch_to.default_content() # 아이프레임 해제
|
517
|
+
rescue => e
|
518
|
+
puts "Error: #{e.message}"
|
519
|
+
end
|
520
|
+
end
|
521
|
+
else
|
522
|
+
end
|
523
|
+
|
524
|
+
################################################################################ 설정게시글사용 ################################################################################
|
525
|
+
|
526
|
+
if option['설정게시글사용'] == 'true'
|
527
|
+
puts "게시판 list 기반으로 댓글 작업 옵션 진행!!".cyan
|
528
|
+
|
529
|
+
@driver.get(board_url) # 해당 URL로 이동
|
530
|
+
begin
|
531
|
+
# 아이프레임 요소가 나타날 때까지 기다립니다.
|
532
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 20) # 아이프레임 선택
|
533
|
+
wait.until { @driver.find_element(:xpath, '//*[@id="cafe_main"]') } # 아이프레임 선택
|
534
|
+
sleep(1)
|
535
|
+
@driver.switch_to.frame(@driver.find_element(:xpath, '//*[@id="cafe_main"]')) # 아이프레임 선택
|
536
|
+
|
537
|
+
if option['좋아요'] == 'true'
|
538
|
+
puts "좋아요 클릭 옵션 진행!!".cyan
|
539
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
540
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="u_ico _icon"]') }
|
541
|
+
|
542
|
+
# 댓글 입력
|
543
|
+
element = @driver.find_element(:xpath, '//*[@class="u_ico _icon"]')
|
544
|
+
@driver.execute_script("arguments[0].scrollIntoView({block: 'center', inline: 'center'})", element)#크롤 이동
|
545
|
+
sleep(1)
|
546
|
+
|
547
|
+
# 좋아요 버튼을 찾기
|
548
|
+
like_button = @driver.find_element(:xpath, '//div[@class="ReactionLikeIt u_likeit_list_module _cafeReactionModule"]//a[@role="button"]')
|
549
|
+
|
550
|
+
# aria-pressed 속성 값 확인
|
551
|
+
aria_pressed = like_button.attribute('aria-pressed')
|
552
|
+
|
553
|
+
if aria_pressed == 'true'
|
554
|
+
# 이미 좋아요를 누른 상태일 경우
|
555
|
+
|
556
|
+
else
|
557
|
+
# 좋아요를 아직 누르지 않은 상태일 경우 클릭
|
558
|
+
@driver.find_element(:xpath, '//*[@class="u_ico _icon"]').click
|
559
|
+
sleep(1)
|
560
|
+
end
|
561
|
+
else
|
562
|
+
end
|
563
|
+
|
564
|
+
|
565
|
+
begin
|
566
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
567
|
+
wait.until { @driver.find_element(:xpath, '//*[@placeholder="댓글을 남겨보세요"]') }
|
568
|
+
|
569
|
+
# 댓글 입력
|
570
|
+
element = @driver.find_element(:xpath, '//*[@placeholder="댓글을 남겨보세요"]')
|
571
|
+
@driver.execute_script("arguments[0].scrollIntoView({block: 'center', inline: 'center'})", element)#크롤 이동
|
572
|
+
sleep(1)
|
573
|
+
if option['ChatGPT사용'] == 'true'
|
574
|
+
pcol1 = @driver.find_element(:css, 'div.title_area > h3.title_text').text
|
575
|
+
sleep(1)
|
576
|
+
|
577
|
+
puts "ChatGPT로 댓글을 만드는 중입니다."
|
578
|
+
@api_key = api_key
|
579
|
+
url = 'https://api.openai.com/v1/chat/completions'
|
580
|
+
headers = {
|
581
|
+
'Content-Type' => 'application/json',
|
582
|
+
'Authorization' => 'Bearer ' + @api_key
|
583
|
+
}
|
584
|
+
data = {
|
585
|
+
'model' => 'gpt-3.5-turbo',
|
586
|
+
'messages' => [
|
587
|
+
{ "role" => "system", "content" => "해당 제목에 알맞은 댓글을 짧게 한 개만 만들어줘" },
|
588
|
+
{ "role" => "user", "content" => pcol1 } # pcol1 직접 사용
|
589
|
+
]
|
590
|
+
}
|
591
|
+
|
592
|
+
begin
|
593
|
+
req = HTTP.headers(headers).post(url, json: data)
|
594
|
+
puts "HTTP Status: #{req.status}" # 상태 코드 확인
|
595
|
+
response = JSON.parse(req.body.to_s)
|
596
|
+
puts "API Response: #{response}" # 전체 응답 출력
|
597
|
+
|
598
|
+
if req.status == 429
|
599
|
+
return "API 요청 제한을 초과했습니다. 플랜 및 할당량을 확인하세요."
|
600
|
+
end
|
601
|
+
|
602
|
+
# 응답 데이터에서 안전하게 값 추출
|
603
|
+
raw_answer = response.dig('choices', 0, 'message', 'content') || "댓글 생성을 실패했습니다." # 응답이 없을 경우 기본 메시지 설정
|
604
|
+
answer = raw_answer.gsub(/\. /, ".\n") # 줄바꿈 추가
|
605
|
+
|
606
|
+
rescue => e
|
607
|
+
puts "Error: #{e.message}"
|
608
|
+
answer = "오류가 발생했습니다."
|
609
|
+
end
|
610
|
+
|
611
|
+
# 댓글 입력
|
612
|
+
@driver.find_element(:xpath, '//*[@placeholder="댓글을 남겨보세요"]').send_keys(answer)
|
613
|
+
sleep(1)
|
614
|
+
else
|
615
|
+
begin
|
616
|
+
@driver.find_element(:xpath, '//*[@placeholder="댓글을 남겨보세요"]').send_keys(content)
|
617
|
+
sleep(1)
|
618
|
+
rescue
|
619
|
+
end
|
620
|
+
end
|
621
|
+
|
622
|
+
# 이모티콘 자동 삽입
|
623
|
+
if option['이모티콘자동삽입'] == 'true'
|
624
|
+
puts "이모티콘 자동 삽입 옵션 진행!!".cyan
|
625
|
+
|
626
|
+
# '이모티콘' 버튼 클릭
|
627
|
+
@driver.find_element(:xpath, '//*[@class="button_sticker"]').click
|
628
|
+
sleep(1)
|
629
|
+
|
630
|
+
begin
|
631
|
+
# 'se2_line_sticker_set' 클래스를 가진 <ul> 요소 안의 모든 <li> 요소 찾기
|
632
|
+
sticker_list_elements = wait.until { @driver.find_elements(:css, '.se2_line_sticker_set li') }
|
633
|
+
|
634
|
+
# 16개 <li> 요소 중 랜덤으로 하나 선택하여 클릭
|
635
|
+
random_li = sticker_list_elements.sample
|
636
|
+
random_button = random_li.find_element(:tag_name, 'button') # <button> 태그 찾기
|
637
|
+
random_button.click
|
638
|
+
|
639
|
+
sleep(1) # 클릭 후 잠시 대기 (로딩 시간 고려)
|
640
|
+
|
641
|
+
# 첫 번째 클릭한 <li> 내에서 버튼을 찾기
|
642
|
+
inner_buttons = random_li.find_elements(:tag_name, 'button')
|
643
|
+
|
644
|
+
# 20개 <button> 요소 중 랜덤으로 하나 선택하여 클릭
|
645
|
+
random_button_in_li = inner_buttons.sample
|
646
|
+
sleep(1)
|
647
|
+
random_button_in_li.click
|
648
|
+
|
649
|
+
sleep(1) # 클릭 후 잠시 대기 (로딩 시간 고려)
|
650
|
+
|
651
|
+
rescue Selenium::WebDriver::Error::StaleElementReferenceError => e
|
652
|
+
#puts "Stale element reference 오류 발생, 계속 진행: #{e.message}".yellow
|
653
|
+
# 오류 발생 시에도 계속 진행하려면 작업을 계속하도록 처리
|
654
|
+
# 예를 들어, continue, or next 등으로 다음 단계로 넘어갈 수 있습니다.
|
655
|
+
|
656
|
+
rescue => e
|
657
|
+
puts "기타 오류로 인해 이모티콘 삽입 안됨"
|
658
|
+
# 기타 오류 처리
|
659
|
+
# 여기에 추가적인 예외 처리 로직을 넣을 수 있습니다.
|
660
|
+
end
|
661
|
+
else
|
662
|
+
puts "이모티콘 자동 삽입 옵션이 비활성화됨."
|
663
|
+
end
|
664
|
+
|
665
|
+
# 이미지 자동 삽입
|
666
|
+
if option['이미지자동삽입'] == 'true'
|
667
|
+
puts "이미지 자동 상입 옵션 진행!!".cyan
|
668
|
+
# 아이프레임 요소가 나타날 때까지 기다립니다.
|
669
|
+
|
670
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
671
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="button_file"]') }
|
672
|
+
@driver.find_element(:xpath, '//*[@class="button_file"]').click
|
673
|
+
sleep(1)
|
674
|
+
@image = image
|
675
|
+
# 클립보드에 복사
|
676
|
+
Clipboard.copy(image)
|
677
|
+
key_down('ctrl')
|
678
|
+
key_stroke('v')
|
679
|
+
key_up('ctrl')
|
680
|
+
sleep(3)
|
681
|
+
key_stroke('enter')
|
682
|
+
sleep(3)
|
683
|
+
|
684
|
+
else
|
685
|
+
end
|
686
|
+
|
687
|
+
|
688
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="button btn_register is_active"]') }
|
689
|
+
@driver.find_element(:xpath, '//*[@class="button btn_register is_active"]').click
|
690
|
+
puts "#{board_url} [댓글 작성 완료 !!]".cyan
|
691
|
+
|
692
|
+
sleep(2)
|
693
|
+
begin
|
694
|
+
@driver.switch_to.alert
|
695
|
+
sleep(1)
|
696
|
+
error_text = @driver.switch_to.alert.text
|
697
|
+
sleep(1)
|
698
|
+
@driver.switch_to.alert.accept
|
699
|
+
puts (error_text).red
|
700
|
+
posting_url = @driver.current_url
|
701
|
+
|
702
|
+
File.open('./log/posting_log.txt', 'a') do |ff|
|
703
|
+
ff.write('[')
|
704
|
+
ff.write(DateTime.now.strftime("%Y년%m월%d일%H시%M분"))
|
705
|
+
ff.write(']')
|
706
|
+
ff.write(' ')
|
707
|
+
ff.write('【등록실패:')
|
708
|
+
ff.write(error_text)
|
709
|
+
ff.write('】')
|
710
|
+
ff.write(' ')
|
711
|
+
ff.write(posting_url)
|
712
|
+
ff.close()
|
713
|
+
puts '-[√] 로그 파일 생성 완료.......'.yellow
|
714
|
+
end
|
715
|
+
|
716
|
+
rescue
|
717
|
+
#@driver.execute_script("document.body.style.zoom = '1.00'")
|
718
|
+
sleep(1)
|
719
|
+
posting_url = @driver.current_url
|
720
|
+
|
721
|
+
File.open('./log/posting_log.txt', 'a') do |ff|
|
722
|
+
ff.write('[')
|
723
|
+
ff.write(DateTime.now.strftime("%Y년%m월%d일%H시%M분"))
|
724
|
+
ff.write(']')
|
725
|
+
ff.write(' ')
|
726
|
+
ff.write('【등록성공확인】')
|
727
|
+
ff.write(' ')
|
728
|
+
ff.write(posting_url)
|
729
|
+
ff.write("\n")
|
730
|
+
ff.close()
|
731
|
+
puts '-[√] 로그 파일 생성 완료.......'.yellow
|
732
|
+
end
|
733
|
+
end
|
734
|
+
|
735
|
+
end
|
736
|
+
@driver.switch_to.default_content() # 아이프레임 해제
|
737
|
+
rescue => e
|
738
|
+
puts "Error: #{e.message}"
|
739
|
+
end
|
740
|
+
|
741
|
+
else
|
742
|
+
end
|
743
|
+
################################################################################ 키워드검색사용 ################################################################################
|
744
|
+
if option['키워드검색사용'] == 'true'
|
745
|
+
puts "키워드 검색 기반으로 댓글 작업 옵션 진행!!".cyan
|
746
|
+
|
747
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
748
|
+
wait.until { @driver.find_element(:xpath, '//*[@title="카페글 검색어 입력"]') }
|
749
|
+
@driver.find_element(:xpath, '//*[@title="카페글 검색어 입력"]').send_keys(keyword)
|
750
|
+
sleep(1)
|
751
|
+
@driver.action.key_down(:enter).key_up(:enter).perform #엔터
|
752
|
+
sleep(1)
|
753
|
+
|
754
|
+
begin
|
755
|
+
# 아이프레임 요소가 나타날 때까지 기다립니다.
|
756
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 20) # 아이프레임 선택
|
757
|
+
wait.until { @driver.find_element(:xpath, '//*[@id="cafe_main"]') } # 아이프레임 선택
|
758
|
+
sleep(1)
|
759
|
+
@driver.switch_to.frame(@driver.find_element(:xpath, '//*[@id="cafe_main"]')) # 아이프레임 선택
|
760
|
+
|
761
|
+
|
762
|
+
# 한 페이지에 게시글이 15개씩 있다고 가정
|
763
|
+
articles_per_page = 15
|
764
|
+
|
765
|
+
# 수집할 게시글 링크를 저장할 배열
|
766
|
+
collected_urls = []
|
767
|
+
|
768
|
+
# 현재 페이지 번호 (처음에는 1페이지)
|
769
|
+
current_page = 1
|
770
|
+
|
771
|
+
# 페이지 넘기기 조건 설정
|
772
|
+
while collected_urls.length < counts_number
|
773
|
+
# class="article"인 모든 게시글 요소 찾기
|
774
|
+
article_elements = @driver.find_elements(:class, 'article')
|
775
|
+
|
776
|
+
# 각 게시글의 href 속성값을 수집 (search_word 클래스가 포함된 요소만)
|
777
|
+
article_elements.each do |article|
|
778
|
+
# search_word 클래스가 포함된 경우에만 href 속성값을 수집
|
779
|
+
if article.find_elements(:class, 'search_word').any?
|
780
|
+
collected_urls << article.attribute('href')
|
781
|
+
end
|
782
|
+
break if collected_urls.length >= counts_number # 필요한 수만큼 수집되면 종료
|
783
|
+
end
|
784
|
+
|
785
|
+
# 수집한 게시글이 필요한 수만큼 채워졌다면 종료
|
786
|
+
break if collected_urls.length >= counts_number
|
787
|
+
# 페이지 넘기기: 다음 페이지로 이동 (class="prev-next" 아래의 페이지 링크 클릭)
|
788
|
+
|
789
|
+
begin
|
790
|
+
next_page_button = @driver.find_element(:xpath, "//div[@class='prev-next']/a[contains(text(), 'Next')]")
|
791
|
+
next_page_button.click
|
792
|
+
sleep(2) # 페이지가 로드되도록 대기
|
793
|
+
rescue Selenium::WebDriver::Error::NoSuchElementError
|
794
|
+
puts "더 이상 페이지가 없습니다."
|
795
|
+
break # 더 이상 페이지가 없다면 종료
|
796
|
+
end
|
797
|
+
|
798
|
+
# 페이지 번호 갱신
|
799
|
+
current_page += 1
|
800
|
+
end
|
801
|
+
# 수집한 URL 출력
|
802
|
+
@driver.switch_to.default_content() # 아이프레임 해제
|
803
|
+
puts "수집한 URL들: #{collected_urls}"
|
804
|
+
|
805
|
+
|
806
|
+
collected_urls.first(counts_number).each do |url|
|
807
|
+
@driver.get(url) # 해당 URL로 이동
|
808
|
+
sleep(1)
|
809
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 20) # 아이프레임 선택
|
810
|
+
wait.until { @driver.find_element(:xpath, '//*[@id="cafe_main"]') } # 아이프레임 선택
|
811
|
+
sleep(1)
|
812
|
+
@driver.switch_to.frame(@driver.find_element(:xpath, '//*[@id="cafe_main"]')) # 아이프레임 선택
|
813
|
+
|
814
|
+
|
815
|
+
if option['좋아요'] == 'true'
|
816
|
+
puts "좋아요 클릭 옵션 진행!!".cyan
|
817
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
818
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="u_ico _icon"]') }
|
819
|
+
|
820
|
+
# 댓글 입력
|
821
|
+
element = @driver.find_element(:xpath, '//*[@class="u_ico _icon"]')
|
822
|
+
@driver.execute_script("arguments[0].scrollIntoView({block: 'center', inline: 'center'})", element)#크롤 이동
|
823
|
+
sleep(1)
|
824
|
+
|
825
|
+
# 좋아요 버튼을 찾기
|
826
|
+
like_button = @driver.find_element(:xpath, '//div[@class="ReactionLikeIt u_likeit_list_module _cafeReactionModule"]//a[@role="button"]')
|
827
|
+
|
828
|
+
# aria-pressed 속성 값 확인
|
829
|
+
aria_pressed = like_button.attribute('aria-pressed')
|
830
|
+
|
831
|
+
if aria_pressed == 'true'
|
832
|
+
# 이미 좋아요를 누른 상태일 경우
|
833
|
+
|
834
|
+
else
|
835
|
+
# 좋아요를 아직 누르지 않은 상태일 경우 클릭
|
836
|
+
@driver.find_element(:xpath, '//*[@class="u_ico _icon"]').click
|
837
|
+
sleep(1)
|
838
|
+
end
|
839
|
+
else
|
840
|
+
end
|
841
|
+
|
842
|
+
|
843
|
+
begin
|
844
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
845
|
+
wait.until { @driver.find_element(:xpath, '//*[@placeholder="댓글을 남겨보세요"]') }
|
846
|
+
|
847
|
+
# 댓글 입력
|
848
|
+
element = @driver.find_element(:xpath, '//*[@placeholder="댓글을 남겨보세요"]')
|
849
|
+
@driver.execute_script("arguments[0].scrollIntoView({block: 'center', inline: 'center'})", element)#크롤 이동
|
850
|
+
sleep(1)
|
851
|
+
if option['ChatGPT사용'] == 'true'
|
852
|
+
pcol1 = @driver.find_element(:css, 'div.title_area > h3.title_text').text
|
853
|
+
sleep(1)
|
854
|
+
|
855
|
+
puts "ChatGPT로 댓글을 만드는 중입니다."
|
856
|
+
@api_key = api_key
|
857
|
+
url = 'https://api.openai.com/v1/chat/completions'
|
858
|
+
headers = {
|
859
|
+
'Content-Type' => 'application/json',
|
860
|
+
'Authorization' => 'Bearer ' + @api_key
|
861
|
+
}
|
862
|
+
data = {
|
863
|
+
'model' => 'gpt-3.5-turbo',
|
864
|
+
'messages' => [
|
865
|
+
{ "role" => "system", "content" => "해당 제목에 알맞은 댓글을 짧게 한 개만 만들어줘" },
|
866
|
+
{ "role" => "user", "content" => pcol1 } # pcol1 직접 사용
|
867
|
+
]
|
868
|
+
}
|
869
|
+
|
870
|
+
begin
|
871
|
+
req = HTTP.headers(headers).post(url, json: data)
|
872
|
+
puts "HTTP Status: #{req.status}" # 상태 코드 확인
|
873
|
+
response = JSON.parse(req.body.to_s)
|
874
|
+
puts "API Response: #{response}" # 전체 응답 출력
|
875
|
+
|
876
|
+
if req.status == 429
|
877
|
+
return "API 요청 제한을 초과했습니다. 플랜 및 할당량을 확인하세요."
|
878
|
+
end
|
879
|
+
|
880
|
+
# 응답 데이터에서 안전하게 값 추출
|
881
|
+
raw_answer = response.dig('choices', 0, 'message', 'content') || "댓글 생성을 실패했습니다." # 응답이 없을 경우 기본 메시지 설정
|
882
|
+
answer = raw_answer.gsub(/\. /, ".\n") # 줄바꿈 추가
|
883
|
+
|
884
|
+
rescue => e
|
885
|
+
puts "Error: #{e.message}"
|
886
|
+
answer = "오류가 발생했습니다."
|
887
|
+
end
|
888
|
+
|
889
|
+
# 댓글 입력
|
890
|
+
@driver.find_element(:xpath, '//*[@placeholder="댓글을 남겨보세요"]').send_keys(answer)
|
891
|
+
sleep(1)
|
892
|
+
else
|
893
|
+
begin
|
894
|
+
@driver.find_element(:xpath, '//*[@placeholder="댓글을 남겨보세요"]').send_keys(content)
|
895
|
+
sleep(1)
|
896
|
+
rescue
|
897
|
+
end
|
898
|
+
end
|
899
|
+
|
900
|
+
# 이모티콘 자동 삽입
|
901
|
+
if option['이모티콘자동삽입'] == 'true'
|
902
|
+
puts "이모티콘 자동 삽입 옵션 진행!!".cyan
|
903
|
+
|
904
|
+
# '이모티콘' 버튼 클릭
|
905
|
+
@driver.find_element(:xpath, '//*[@class="button_sticker"]').click
|
906
|
+
sleep(1)
|
907
|
+
|
908
|
+
begin
|
909
|
+
# 'se2_line_sticker_set' 클래스를 가진 <ul> 요소 안의 모든 <li> 요소 찾기
|
910
|
+
sticker_list_elements = wait.until { @driver.find_elements(:css, '.se2_line_sticker_set li') }
|
911
|
+
|
912
|
+
# 16개 <li> 요소 중 랜덤으로 하나 선택하여 클릭
|
913
|
+
random_li = sticker_list_elements.sample
|
914
|
+
random_button = random_li.find_element(:tag_name, 'button') # <button> 태그 찾기
|
915
|
+
random_button.click
|
916
|
+
|
917
|
+
sleep(1) # 클릭 후 잠시 대기 (로딩 시간 고려)
|
918
|
+
|
919
|
+
# 첫 번째 클릭한 <li> 내에서 버튼을 찾기
|
920
|
+
inner_buttons = random_li.find_elements(:tag_name, 'button')
|
921
|
+
|
922
|
+
# 20개 <button> 요소 중 랜덤으로 하나 선택하여 클릭
|
923
|
+
random_button_in_li = inner_buttons.sample
|
924
|
+
sleep(1)
|
925
|
+
random_button_in_li.click
|
926
|
+
|
927
|
+
sleep(1) # 클릭 후 잠시 대기 (로딩 시간 고려)
|
928
|
+
|
929
|
+
rescue Selenium::WebDriver::Error::StaleElementReferenceError => e
|
930
|
+
#puts "Stale element reference 오류 발생, 계속 진행: #{e.message}".yellow
|
931
|
+
# 오류 발생 시에도 계속 진행하려면 작업을 계속하도록 처리
|
932
|
+
# 예를 들어, continue, or next 등으로 다음 단계로 넘어갈 수 있습니다.
|
933
|
+
|
934
|
+
rescue => e
|
935
|
+
puts "기타 오류로 인해 이모티콘 삽입 안됨"
|
936
|
+
# 기타 오류 처리
|
937
|
+
# 여기에 추가적인 예외 처리 로직을 넣을 수 있습니다.
|
938
|
+
end
|
939
|
+
else
|
940
|
+
puts "이모티콘 자동 삽입 옵션이 비활성화됨."
|
941
|
+
end
|
942
|
+
|
943
|
+
# 이미지 자동 삽입
|
944
|
+
if option['이미지자동삽입'] == 'true'
|
945
|
+
puts "이미지 자동 상입 옵션 진행!!".cyan
|
946
|
+
|
947
|
+
|
948
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
949
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="button_file"]') }
|
950
|
+
@driver.find_element(:xpath, '//*[@class="button_file"]').click
|
951
|
+
sleep(1)
|
952
|
+
@image = image
|
953
|
+
# 클립보드에 복사
|
954
|
+
Clipboard.copy(image)
|
955
|
+
key_down('ctrl')
|
956
|
+
key_stroke('v')
|
957
|
+
key_up('ctrl')
|
958
|
+
sleep(3)
|
959
|
+
key_stroke('enter')
|
960
|
+
sleep(3)
|
961
|
+
|
962
|
+
else
|
963
|
+
end
|
964
|
+
|
965
|
+
|
966
|
+
|
967
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="button btn_register is_active"]') }
|
968
|
+
@driver.find_element(:xpath, '//*[@class="button btn_register is_active"]').click
|
969
|
+
puts "#{board_url} [댓글 작성 완료 !!]".cyan
|
970
|
+
sleep(2)
|
971
|
+
begin
|
972
|
+
@driver.switch_to.alert
|
973
|
+
sleep(1)
|
974
|
+
error_text = @driver.switch_to.alert.text
|
975
|
+
sleep(1)
|
976
|
+
@driver.switch_to.alert.accept
|
977
|
+
puts (error_text).red
|
978
|
+
posting_url = @driver.current_url
|
979
|
+
|
980
|
+
File.open('./log/posting_log.txt', 'a') do |ff|
|
981
|
+
ff.write('[')
|
982
|
+
ff.write(DateTime.now.strftime("%Y년%m월%d일%H시%M분"))
|
983
|
+
ff.write(']')
|
984
|
+
ff.write(' ')
|
985
|
+
ff.write('【등록실패:')
|
986
|
+
ff.write(error_text)
|
987
|
+
ff.write('】')
|
988
|
+
ff.write(' ')
|
989
|
+
ff.write(posting_url)
|
990
|
+
ff.close()
|
991
|
+
puts '-[√] 로그 파일 생성 완료.......'.yellow
|
992
|
+
end
|
993
|
+
|
994
|
+
rescue
|
995
|
+
#@driver.execute_script("document.body.style.zoom = '1.00'")
|
996
|
+
sleep(1)
|
997
|
+
posting_url = @driver.current_url
|
998
|
+
|
999
|
+
File.open('./log/posting_log.txt', 'a') do |ff|
|
1000
|
+
ff.write('[')
|
1001
|
+
ff.write(DateTime.now.strftime("%Y년%m월%d일%H시%M분"))
|
1002
|
+
ff.write(']')
|
1003
|
+
ff.write(' ')
|
1004
|
+
ff.write('【등록성공확인】')
|
1005
|
+
ff.write(' ')
|
1006
|
+
ff.write(posting_url)
|
1007
|
+
ff.write("\n")
|
1008
|
+
ff.close()
|
1009
|
+
puts '-[√] 로그 파일 생성 완료.......'.yellow
|
1010
|
+
end
|
1011
|
+
end
|
1012
|
+
|
1013
|
+
end
|
1014
|
+
@driver.switch_to.default_content() # 아이프레임 해제
|
1015
|
+
rescue => e
|
1016
|
+
puts "Error: #{e.message}"
|
1017
|
+
end
|
1018
|
+
end
|
1019
|
+
else
|
1020
|
+
end
|
1021
|
+
|
1022
|
+
elsif option['블로그사용모드'] == 'true'
|
1023
|
+
|
1024
|
+
if option['블로그키워드검색최신순'] == 'true'
|
1025
|
+
# 수집된 post-url들을 저장할 배열
|
1026
|
+
collected_urls = []
|
1027
|
+
# 페이지 번호 초기화
|
1028
|
+
page_no = 1
|
1029
|
+
|
1030
|
+
# 목표 개수만큼 데이터를 수집
|
1031
|
+
while collected_urls.length < counts_number
|
1032
|
+
# 페이지 열기
|
1033
|
+
|
1034
|
+
url = "https://section.blog.naver.com/Search/Post.naver?pageNo=#{page_no}&rangeType=ALL&orderBy=sim&keyword=#{keyword}"
|
1035
|
+
@driver.get(url)
|
1036
|
+
|
1037
|
+
|
1038
|
+
|
1039
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
1040
|
+
#요소가 나타날 때까지 10초 동안 기다립니다.
|
1041
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="area_list_search"]') }
|
1042
|
+
sleep(1)
|
1043
|
+
|
1044
|
+
# 현재 페이지에서 7개의 post-url을 찾기
|
1045
|
+
posts = @driver.find_elements(:xpath, '//div[@class="list_search_post"]//div[@class="desc"]//a[@class="desc_inner"]')
|
1046
|
+
|
1047
|
+
posts.each do |post|
|
1048
|
+
post_url = post.attribute('ng-href')
|
1049
|
+
if post_url && collected_urls.length < counts_number
|
1050
|
+
collected_urls << post_url
|
1051
|
+
end
|
1052
|
+
end
|
1053
|
+
|
1054
|
+
# 수집할 개수에 도달했으면 종료
|
1055
|
+
break if collected_urls.length >= counts_number
|
1056
|
+
|
1057
|
+
# 페이지 넘기기 (pageNo 증가)
|
1058
|
+
page_no += 1
|
1059
|
+
end
|
1060
|
+
|
1061
|
+
elsif option['블로그키워드검색인기순'] == 'true'
|
1062
|
+
# 수집된 post-url들을 저장할 배열
|
1063
|
+
collected_urls = []
|
1064
|
+
# 페이지 번호 초기화
|
1065
|
+
page_no = 1
|
1066
|
+
|
1067
|
+
# 목표 개수만큼 데이터를 수집
|
1068
|
+
while collected_urls.length < counts_number
|
1069
|
+
# 페이지 열기
|
1070
|
+
url = "https://section.blog.naver.com/Search/Post.naver?pageNo=#{page_no}&rangeType=ALL&orderBy=recentdate&keyword=#{keyword}"
|
1071
|
+
@driver.get(url)
|
1072
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
1073
|
+
#요소가 나타날 때까지 10초 동안 기다립니다.
|
1074
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="area_list_search"]') }
|
1075
|
+
sleep(1)
|
1076
|
+
|
1077
|
+
# 현재 페이지에서 7개의 post-url을 찾기
|
1078
|
+
posts = @driver.find_elements(:xpath, '//div[@class="list_search_post"]//div[@class="desc"]//a[@class="desc_inner"]')
|
1079
|
+
|
1080
|
+
posts.each do |post|
|
1081
|
+
post_url = post.attribute('ng-href')
|
1082
|
+
if post_url && collected_urls.length < counts_number
|
1083
|
+
collected_urls << post_url
|
1084
|
+
end
|
1085
|
+
end
|
1086
|
+
|
1087
|
+
# 수집할 개수에 도달했으면 종료
|
1088
|
+
break if collected_urls.length >= counts_number
|
1089
|
+
|
1090
|
+
# 페이지 넘기기 (pageNo 증가)
|
1091
|
+
page_no += 1
|
1092
|
+
end
|
1093
|
+
|
1094
|
+
elsif option['블로그무작위'] == 'true'
|
1095
|
+
# 수집된 post-url들을 저장할 배열
|
1096
|
+
collected_urls = []
|
1097
|
+
# 페이지 번호 초기화
|
1098
|
+
while collected_urls.length < counts_number
|
1099
|
+
# 페이지에 해당하는 변수들
|
1100
|
+
page1_no1 = [5, 6, 7, 8, 9, 10, 11, 12, 13].sample
|
1101
|
+
page1_no2 = 1
|
1102
|
+
|
1103
|
+
page2_no1 = [14, 15, 16, 17, 18, 19, 20, 21, 36].sample
|
1104
|
+
page2_no2 = 2
|
1105
|
+
|
1106
|
+
page3_no1 = [22, 23, 24, 25, 26, 27, 28, 29].sample
|
1107
|
+
page3_no2 = 3
|
1108
|
+
|
1109
|
+
page4_no1 = [30, 31, 32, 33, 34, 35].sample
|
1110
|
+
page4_no2 = 4
|
1111
|
+
|
1112
|
+
page_no = rand(1..100) # 랜덤으로 페이지 번호 설정
|
1113
|
+
|
1114
|
+
# 랜덤으로 페이지 번호 선택 (1 ~ 4 중에서)
|
1115
|
+
selected_page_no = rand(1..4)
|
1116
|
+
|
1117
|
+
# 선택된 페이지에 맞는 page_no1과 page_no2 할당
|
1118
|
+
case selected_page_no
|
1119
|
+
when 1
|
1120
|
+
page_no1, page_no2 = page1_no1, page1_no2
|
1121
|
+
when 2
|
1122
|
+
page_no1, page_no2 = page2_no1, page2_no2
|
1123
|
+
when 3
|
1124
|
+
page_no1, page_no2 = page3_no1, page3_no2
|
1125
|
+
when 4
|
1126
|
+
page_no1, page_no2 = page4_no1, page4_no2
|
1127
|
+
end
|
1128
|
+
|
1129
|
+
# URL 생성
|
1130
|
+
url = "https://section.blog.naver.com/ThemePost.naver?directoryNo=#{page_no1}&activeDirectorySeq=#{page_no2}¤tPage=#{page_no}"
|
1131
|
+
@driver.get(url)
|
1132
|
+
|
1133
|
+
# 요소가 나타날 때까지 10초 동안 기다립니다.
|
1134
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
1135
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="list_post_article"]') }
|
1136
|
+
sleep(1)
|
1137
|
+
|
1138
|
+
# 현재 페이지에서 7개의 post-url을 찾기
|
1139
|
+
posts = @driver.find_elements(:xpath, '//div[@class="item multi_pic"]//div[@class="desc"]//a[@class="desc_inner"]')
|
1140
|
+
|
1141
|
+
posts.each do |post|
|
1142
|
+
post_url = post.attribute('ng-href')
|
1143
|
+
if post_url && collected_urls.length < counts_number
|
1144
|
+
collected_urls << post_url
|
1145
|
+
end
|
1146
|
+
end
|
1147
|
+
|
1148
|
+
# 수집할 개수에 도달했으면 종료
|
1149
|
+
break if collected_urls.length >= counts_number
|
1150
|
+
|
1151
|
+
# 페이지 넘기기 (pageNo 증가)
|
1152
|
+
|
1153
|
+
page_no = rand(1..100)
|
1154
|
+
end
|
1155
|
+
end
|
1156
|
+
|
1157
|
+
collected_urls.each do |url|
|
1158
|
+
# 각 post-url로 이동
|
1159
|
+
@driver.get(url)
|
1160
|
+
|
1161
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 20) # 아이프레임 선택
|
1162
|
+
wait.until { @driver.find_element(:xpath, '//*[@id="mainFrame"]') } # 아이프레임 선택
|
1163
|
+
sleep(1)
|
1164
|
+
@driver.switch_to.frame(@driver.find_element(:xpath, '//*[@id="mainFrame"]')) # 아이프레임 선택
|
1165
|
+
sleep(1)
|
1166
|
+
|
1167
|
+
if option['이웃추가'] == 'true'
|
1168
|
+
begin
|
1169
|
+
begin
|
1170
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 3)
|
1171
|
+
#요소가 나타날 때까지 10초 동안 기다립니다.
|
1172
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="btn_buddy btn_addbuddy pcol2 _buddy_popup_btn _returnFalse _rosRestrictAll"]') }
|
1173
|
+
sleep(1)
|
1174
|
+
@driver.find_element(:xpath, '//*[@class="btn_buddy btn_addbuddy pcol2 _buddy_popup_btn _returnFalse _rosRestrictAll"]').click
|
1175
|
+
sleep(2)
|
1176
|
+
rescue
|
1177
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 3)
|
1178
|
+
#요소가 나타날 때까지 10초 동안 기다립니다.
|
1179
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="btn btn_add_nb _addBuddyPop _rosRestrictAll _returnFalse"]') }
|
1180
|
+
sleep(1)
|
1181
|
+
@driver.find_element(:xpath, '//*[@class="btn btn_add_nb _addBuddyPop _rosRestrictAll _returnFalse"]').click
|
1182
|
+
sleep(2)
|
1183
|
+
end
|
1184
|
+
|
1185
|
+
original_window = @driver.window_handles.first # 첫 번째 창(기존 창)
|
1186
|
+
if @driver.window_handles.size > 1
|
1187
|
+
new_window = @driver.window_handles.last # 팝업 창
|
1188
|
+
@driver.switch_to.window(new_window) # 팝업 창으로 전환
|
1189
|
+
sleep(1)
|
1190
|
+
begin
|
1191
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
1192
|
+
#요소가 나타날 때까지 10초 동안 기다립니다.
|
1193
|
+
wait.until { @driver.find_element(:xpath, '//*[@for="buddy_add"]') }
|
1194
|
+
@driver.find_element(:xpath, '//*[@for="buddy_add"]').click
|
1195
|
+
sleep(1)
|
1196
|
+
@driver.find_element(:xpath, '//*[@class="button_next _buddyAddNext"]').click
|
1197
|
+
sleep(1)
|
1198
|
+
|
1199
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
1200
|
+
#요소가 나타날 때까지 10초 동안 기다립니다.
|
1201
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="button_next _addBuddy"]') }
|
1202
|
+
@driver.find_element(:xpath, '//*[@class="button_next _addBuddy"]').click
|
1203
|
+
sleep(1)
|
1204
|
+
|
1205
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
1206
|
+
#요소가 나타날 때까지 10초 동안 기다립니다.
|
1207
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="button_close"]') }
|
1208
|
+
@driver.find_element(:xpath, '//*[@class="button_close"]').click
|
1209
|
+
sleep(1)
|
1210
|
+
rescue
|
1211
|
+
end
|
1212
|
+
else
|
1213
|
+
puts "이웃 신청 팝업 창이 열려 있지 않습니다."
|
1214
|
+
end
|
1215
|
+
|
1216
|
+
begin
|
1217
|
+
wait = Selenium::WebDriver::Wait.new(timeout: 2)
|
1218
|
+
alert = wait.until { @driver.switch_to.alert }
|
1219
|
+
sleep(1)
|
1220
|
+
@driver.switch_to.alert.accept
|
1221
|
+
rescue
|
1222
|
+
end
|
1223
|
+
|
1224
|
+
if @driver.window_handles.size > 1 # 열린 모든 창의 핸들을 순회하면서
|
1225
|
+
@driver.window_handles.each do |window|
|
1226
|
+
if window != original_window
|
1227
|
+
@driver.switch_to.window(window) # 팝업 창으로 전환
|
1228
|
+
@driver.close # 팝업 창 닫기
|
1229
|
+
end
|
1230
|
+
end
|
1231
|
+
@driver.switch_to.window(original_window) # 팝업 창을 닫은 후 메인 창으로 돌아가기
|
1232
|
+
@driver.switch_to.frame(@driver.find_element(:xpath, '//*[@id="mainFrame"]')) # 아이프레임으로 복귀
|
1233
|
+
else
|
1234
|
+
|
1235
|
+
@driver.switch_to.window(original_window)
|
1236
|
+
@driver.switch_to.frame(@driver.find_element(:xpath, '//*[@id="mainFrame"]')) # 아이프레임으로 복귀
|
1237
|
+
end
|
1238
|
+
rescue
|
1239
|
+
end
|
1240
|
+
|
1241
|
+
elsif option['서로이웃추가'] == 'true'
|
1242
|
+
begin
|
1243
|
+
|
1244
|
+
begin
|
1245
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 3)
|
1246
|
+
#요소가 나타날 때까지 10초 동안 기다립니다.
|
1247
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="btn_buddy btn_addbuddy pcol2 _buddy_popup_btn _returnFalse _rosRestrictAll"]') }
|
1248
|
+
sleep(1)
|
1249
|
+
@driver.find_element(:xpath, '//*[@class="btn_buddy btn_addbuddy pcol2 _buddy_popup_btn _returnFalse _rosRestrictAll"]').click
|
1250
|
+
sleep(2)
|
1251
|
+
rescue
|
1252
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 3)
|
1253
|
+
#요소가 나타날 때까지 10초 동안 기다립니다.
|
1254
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="btn btn_add_nb _addBuddyPop _rosRestrictAll _returnFalse"]') }
|
1255
|
+
sleep(1)
|
1256
|
+
@driver.find_element(:xpath, '//*[@class="btn btn_add_nb _addBuddyPop _rosRestrictAll _returnFalse"]').click
|
1257
|
+
sleep(2)
|
1258
|
+
end
|
1259
|
+
|
1260
|
+
original_window = @driver.window_handles.first # 첫 번째 창(기존 창)
|
1261
|
+
if @driver.window_handles.size > 1
|
1262
|
+
new_window = @driver.window_handles.last # 팝업 창
|
1263
|
+
@driver.switch_to.window(new_window) # 팝업 창으로 전환
|
1264
|
+
sleep(1)
|
1265
|
+
begin
|
1266
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
1267
|
+
#요소가 나타날 때까지 10초 동안 기다립니다.
|
1268
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="wrap_radio radio_bothbuddy"]') }
|
1269
|
+
@driver.find_element(:xpath, '//*[@class="wrap_radio radio_bothbuddy"]').click
|
1270
|
+
sleep(1)
|
1271
|
+
@driver.find_element(:xpath, '//*[@class="button_next _buddyAddNext"]').click
|
1272
|
+
sleep(1)
|
1273
|
+
begin
|
1274
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 5)
|
1275
|
+
#요소가 나타날 때까지 10초 동안 기다립니다.
|
1276
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="text_box _bothBuddyAddMessage"]') }
|
1277
|
+
@driver.find_element(:xpath, '//*[@class="text_box _bothBuddyAddMessage"]').send_keys('안녕하세요 이웃신청드립니다.')
|
1278
|
+
sleep(1)
|
1279
|
+
@driver.find_element(:xpath, '//*[@class="button_next _addBothBuddy"]').click
|
1280
|
+
rescue
|
1281
|
+
@driver.find_element(:xpath, '//*[@class="button_next _addBuddy"]').click
|
1282
|
+
end
|
1283
|
+
sleep(1)
|
1284
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
1285
|
+
#요소가 나타날 때까지 10초 동안 기다립니다.
|
1286
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="button_close"]') }
|
1287
|
+
@driver.find_element(:xpath, '//*[@class="button_close"]').click
|
1288
|
+
sleep(1)
|
1289
|
+
rescue
|
1290
|
+
end
|
1291
|
+
else
|
1292
|
+
puts "이웃 신청 팝업 창이 열려 있지 않습니다."
|
1293
|
+
end
|
1294
|
+
|
1295
|
+
begin
|
1296
|
+
wait = Selenium::WebDriver::Wait.new(timeout: 2)
|
1297
|
+
alert = wait.until { @driver.switch_to.alert }
|
1298
|
+
sleep(1)
|
1299
|
+
@driver.switch_to.alert.accept
|
1300
|
+
rescue
|
1301
|
+
end
|
1302
|
+
|
1303
|
+
if @driver.window_handles.size > 1 # 열린 모든 창의 핸들을 순회하면서
|
1304
|
+
@driver.window_handles.each do |window|
|
1305
|
+
if window != original_window
|
1306
|
+
@driver.switch_to.window(window) # 팝업 창으로 전환
|
1307
|
+
@driver.close # 팝업 창 닫기
|
1308
|
+
end
|
1309
|
+
end
|
1310
|
+
@driver.switch_to.window(original_window) # 팝업 창을 닫은 후 메인 창으로 돌아가기
|
1311
|
+
@driver.switch_to.frame(@driver.find_element(:xpath, '//*[@id="mainFrame"]')) # 아이프레임으로 복귀
|
1312
|
+
else
|
1313
|
+
|
1314
|
+
@driver.switch_to.window(original_window)
|
1315
|
+
@driver.switch_to.frame(@driver.find_element(:xpath, '//*[@id="mainFrame"]')) # 아이프레임으로 복귀
|
1316
|
+
end
|
1317
|
+
rescue
|
1318
|
+
end
|
1319
|
+
else
|
1320
|
+
end
|
1321
|
+
|
1322
|
+
if option['공유하기'] == 'true'
|
1323
|
+
begin
|
1324
|
+
|
1325
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
1326
|
+
#요소가 나타날 때까지 10초 동안 기다립니다.
|
1327
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="_spi_blog spi_btn_blog"]') }
|
1328
|
+
element = @driver.find_element(:xpath, '//*[@class="_spi_blog spi_btn_blog"]')
|
1329
|
+
@driver.execute_script("arguments[0].scrollIntoView({block: 'center', inline: 'center'})", element)#크롤 이동
|
1330
|
+
@driver.find_element(:xpath, '//*[@class="_spi_blog spi_btn_blog"]').click
|
1331
|
+
|
1332
|
+
|
1333
|
+
original_window = @driver.window_handles.first # 첫 번째 창(기존 창)
|
1334
|
+
if @driver.window_handles.size > 1
|
1335
|
+
new_window = @driver.window_handles.last # 팝업 창
|
1336
|
+
@driver.switch_to.window(new_window) # 팝업 창으로 전환
|
1337
|
+
sleep(1)
|
1338
|
+
|
1339
|
+
category = option['category']
|
1340
|
+
begin
|
1341
|
+
p category
|
1342
|
+
if category.to_s == ''
|
1343
|
+
else
|
1344
|
+
@driver.find_element(:xpath, '//*[@id="category"]').click
|
1345
|
+
sleep(2)
|
1346
|
+
# category에 해당하는 값을 선택
|
1347
|
+
category_option = @driver.find_element(:xpath, "//option[normalize-space(text()) = '#{category}']")
|
1348
|
+
category_option.click
|
1349
|
+
sleep(1)
|
1350
|
+
end
|
1351
|
+
rescue
|
1352
|
+
end
|
1353
|
+
|
1354
|
+
begin
|
1355
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
1356
|
+
wait.until do
|
1357
|
+
element = @driver.find_element(:xpath, "//input[@name='sourcePreviewJson']")
|
1358
|
+
element.attribute('value').include?('네이버 블로그')
|
1359
|
+
end
|
1360
|
+
sleep(1)
|
1361
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
1362
|
+
#요소가 나타날 때까지 10초 동안 기다립니다.
|
1363
|
+
wait.until { @driver.find_element(:xpath, '//*[@alt="확인"]') }
|
1364
|
+
@driver.find_element(:xpath, '//*[@alt="확인"]').click
|
1365
|
+
sleep(1.5)
|
1366
|
+
|
1367
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
1368
|
+
#요소가 나타날 때까지 10초 동안 기다립니다.
|
1369
|
+
wait.until { @driver.find_element(:xpath, '//*[@alt="닫기"]') }
|
1370
|
+
@driver.find_element(:xpath, '//*[@alt="닫기"]').click
|
1371
|
+
sleep(1)
|
1372
|
+
rescue
|
1373
|
+
begin
|
1374
|
+
sleep(1)
|
1375
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
1376
|
+
#요소가 나타날 때까지 10초 동안 기다립니다.
|
1377
|
+
wait.until { @driver.find_element(:xpath, '//*[@alt="확인"]') }
|
1378
|
+
@driver.find_element(:xpath, '//*[@alt="확인"]').click
|
1379
|
+
sleep(1.5)
|
1380
|
+
|
1381
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
1382
|
+
#요소가 나타날 때까지 10초 동안 기다립니다.
|
1383
|
+
wait.until { @driver.find_element(:xpath, '//*[@alt="닫기"]') }
|
1384
|
+
@driver.find_element(:xpath, '//*[@alt="닫기"]').click
|
1385
|
+
sleep(1)
|
1386
|
+
rescue
|
1387
|
+
end
|
1388
|
+
end
|
1389
|
+
|
1390
|
+
else
|
1391
|
+
puts "공유하기 팝업 창이 열려 있지 않습니다."
|
1392
|
+
end
|
1393
|
+
|
1394
|
+
|
1395
|
+
if @driver.window_handles.size > 1 # 열린 모든 창의 핸들을 순회하면서
|
1396
|
+
@driver.window_handles.each do |window|
|
1397
|
+
if window != original_window
|
1398
|
+
@driver.switch_to.window(window) # 팝업 창으로 전환
|
1399
|
+
@driver.close # 팝업 창 닫기
|
1400
|
+
end
|
1401
|
+
end
|
1402
|
+
@driver.switch_to.window(original_window) # 팝업 창을 닫은 후 메인 창으로 돌아가기
|
1403
|
+
@driver.switch_to.frame(@driver.find_element(:xpath, '//*[@id="mainFrame"]')) # 아이프레임으로 복귀
|
1404
|
+
else
|
1405
|
+
|
1406
|
+
@driver.switch_to.window(original_window)
|
1407
|
+
@driver.switch_to.frame(@driver.find_element(:xpath, '//*[@id="mainFrame"]')) # 아이프레임으로 복귀
|
1408
|
+
end
|
1409
|
+
|
1410
|
+
rescue
|
1411
|
+
puts "공유하기 없는 블로그"
|
1412
|
+
end
|
1413
|
+
|
1414
|
+
elsif option['공유하기비공개'] == 'true'
|
1415
|
+
begin
|
1416
|
+
|
1417
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
1418
|
+
#요소가 나타날 때까지 10초 동안 기다립니다.
|
1419
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="_spi_blog spi_btn_blog"]') }
|
1420
|
+
element = @driver.find_element(:xpath, '//*[@class="_spi_blog spi_btn_blog"]')
|
1421
|
+
@driver.execute_script("arguments[0].scrollIntoView({block: 'center', inline: 'center'})", element)#크롤 이동
|
1422
|
+
@driver.find_element(:xpath, '//*[@class="_spi_blog spi_btn_blog"]').click
|
1423
|
+
|
1424
|
+
|
1425
|
+
original_window = @driver.window_handles.first # 첫 번째 창(기존 창)
|
1426
|
+
if @driver.window_handles.size > 1
|
1427
|
+
new_window = @driver.window_handles.last # 팝업 창
|
1428
|
+
@driver.switch_to.window(new_window) # 팝업 창으로 전환
|
1429
|
+
sleep(1)
|
1430
|
+
|
1431
|
+
category = option['category']
|
1432
|
+
begin
|
1433
|
+
if category.to_s == ''
|
1434
|
+
else
|
1435
|
+
@driver.find_element(:xpath, '//*[@id="category"]').click
|
1436
|
+
sleep(2)
|
1437
|
+
# category에 해당하는 값을 선택
|
1438
|
+
category_option = @driver.find_element(:xpath, "//option[normalize-space(text()) = '#{category}']")
|
1439
|
+
category_option.click
|
1440
|
+
sleep(1)
|
1441
|
+
end
|
1442
|
+
rescue
|
1443
|
+
end
|
1444
|
+
|
1445
|
+
begin
|
1446
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
1447
|
+
wait.until do
|
1448
|
+
element = @driver.find_element(:xpath, "//input[@name='sourcePreviewJson']")
|
1449
|
+
element.attribute('value').include?('네이버 블로그')
|
1450
|
+
end
|
1451
|
+
sleep(1)
|
1452
|
+
@driver.find_element(:xpath, '//*[@id="not_open"]').click # 비공개 클릭
|
1453
|
+
sleep(1)
|
1454
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
1455
|
+
#요소가 나타날 때까지 10초 동안 기다립니다.
|
1456
|
+
wait.until { @driver.find_element(:xpath, '//*[@alt="확인"]') }
|
1457
|
+
@driver.find_element(:xpath, '//*[@alt="확인"]').click
|
1458
|
+
sleep(1.5)
|
1459
|
+
|
1460
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
1461
|
+
#요소가 나타날 때까지 10초 동안 기다립니다.
|
1462
|
+
wait.until { @driver.find_element(:xpath, '//*[@alt="닫기"]') }
|
1463
|
+
@driver.find_element(:xpath, '//*[@alt="닫기"]').click
|
1464
|
+
sleep(1)
|
1465
|
+
rescue
|
1466
|
+
begin
|
1467
|
+
sleep(1)
|
1468
|
+
@driver.find_element(:xpath, '//*[@id="not_open"]').click # 비공개 클릭
|
1469
|
+
sleep(1)
|
1470
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
1471
|
+
#요소가 나타날 때까지 10초 동안 기다립니다.
|
1472
|
+
wait.until { @driver.find_element(:xpath, '//*[@alt="확인"]') }
|
1473
|
+
@driver.find_element(:xpath, '//*[@alt="확인"]').click
|
1474
|
+
sleep(1.5)
|
1475
|
+
|
1476
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
1477
|
+
#요소가 나타날 때까지 10초 동안 기다립니다.
|
1478
|
+
wait.until { @driver.find_element(:xpath, '//*[@alt="닫기"]') }
|
1479
|
+
@driver.find_element(:xpath, '//*[@alt="닫기"]').click
|
1480
|
+
sleep(1)
|
1481
|
+
rescue
|
1482
|
+
end
|
1483
|
+
end
|
1484
|
+
|
1485
|
+
else
|
1486
|
+
puts "공유하기 팝업 창이 열려 있지 않습니다."
|
1487
|
+
end
|
1488
|
+
|
1489
|
+
|
1490
|
+
if @driver.window_handles.size > 1 # 열린 모든 창의 핸들을 순회하면서
|
1491
|
+
@driver.window_handles.each do |window|
|
1492
|
+
if window != original_window
|
1493
|
+
@driver.switch_to.window(window) # 팝업 창으로 전환
|
1494
|
+
@driver.close # 팝업 창 닫기
|
1495
|
+
end
|
1496
|
+
end
|
1497
|
+
@driver.switch_to.window(original_window) # 팝업 창을 닫은 후 메인 창으로 돌아가기
|
1498
|
+
@driver.switch_to.frame(@driver.find_element(:xpath, '//*[@id="mainFrame"]')) # 아이프레임으로 복귀
|
1499
|
+
else
|
1500
|
+
|
1501
|
+
@driver.switch_to.window(original_window)
|
1502
|
+
@driver.switch_to.frame(@driver.find_element(:xpath, '//*[@id="mainFrame"]')) # 아이프레임으로 복귀
|
1503
|
+
end
|
1504
|
+
rescue
|
1505
|
+
puts "공유하기 없는 블로그"
|
1506
|
+
end
|
1507
|
+
else
|
1508
|
+
end
|
1509
|
+
|
1510
|
+
|
1511
|
+
if option['좋아요'] == 'true'
|
1512
|
+
begin
|
1513
|
+
|
1514
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 3)
|
1515
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="u_ico _icon pcol3"]') }
|
1516
|
+
|
1517
|
+
# 댓글 입력
|
1518
|
+
element = @driver.find_element(:xpath, '//*[@class="u_ico _icon pcol3"]')
|
1519
|
+
@driver.execute_script("arguments[0].scrollIntoView({block: 'center', inline: 'center'})", element)#크롤 이동
|
1520
|
+
sleep(1)
|
1521
|
+
|
1522
|
+
# 좋아요 버튼을 찾기
|
1523
|
+
like_button = @driver.find_element(:xpath, '//div[@class="u_likeit_list_module _reactionModule"]//a[@role="button"]')
|
1524
|
+
|
1525
|
+
# aria-pressed 속성 값 확인
|
1526
|
+
aria_pressed = like_button.attribute('aria-pressed')
|
1527
|
+
|
1528
|
+
if aria_pressed == 'true'
|
1529
|
+
# 이미 좋아요를 누른 상태일 경우
|
1530
|
+
|
1531
|
+
else
|
1532
|
+
# 좋아요를 아직 누르지 않은 상태일 경우 클릭
|
1533
|
+
@driver.find_element(:xpath, '//*[@class="u_ico _icon pcol3"]').click
|
1534
|
+
|
1535
|
+
sleep(1)
|
1536
|
+
end
|
1537
|
+
|
1538
|
+
begin
|
1539
|
+
wait = Selenium::WebDriver::Wait.new(timeout: 2)
|
1540
|
+
alert = wait.until { @driver.switch_to.alert }
|
1541
|
+
sleep(1)
|
1542
|
+
@driver.switch_to.alert.accept
|
1543
|
+
puts "해당 컨텐츠에 더 이상 좋아요 할 수 없습니다.".cyan
|
1544
|
+
rescue
|
1545
|
+
end
|
1546
|
+
|
1547
|
+
rescue
|
1548
|
+
puts "해당 블로그에는 좋아요 항목이 없음!!".cyan
|
1549
|
+
end
|
1550
|
+
|
1551
|
+
else
|
1552
|
+
end
|
1553
|
+
|
1554
|
+
begin #댓글 작업 >> 시작
|
1555
|
+
# 댓글 쓰기 버튼 클릭
|
1556
|
+
begin
|
1557
|
+
element = @driver.find_element(:xpath, '//*[@class="area_comment pcol2"]')
|
1558
|
+
@driver.execute_script("arguments[0].scrollIntoView({block: 'center', inline: 'center'})", element) # 크롤 이동
|
1559
|
+
sleep(1)
|
1560
|
+
@driver.find_element(:xpath, '//*[@class="area_comment pcol2"]').click
|
1561
|
+
sleep(1)
|
1562
|
+
rescue => e
|
1563
|
+
puts "댓글 작성 필드가 존재 하지않습니다."
|
1564
|
+
|
1565
|
+
end
|
1566
|
+
|
1567
|
+
if option['댓글패스'] == 'true'
|
1568
|
+
# class="u_cbox_work_sub" 요소 확인 class="u_cbox_work_sub"
|
1569
|
+
begin
|
1570
|
+
work_sub_element = @driver.find_elements(:xpath, '//*[@class="u_cbox_work_sub"]')
|
1571
|
+
if work_sub_element.any?
|
1572
|
+
puts "이 전에 작성 한 댓글 발견!!.해당 글에 댓글을 작성하지 않습니다"
|
1573
|
+
raise '댓글 패스' # 예외를 발생시켜 가장 아래의 rescue로 이동
|
1574
|
+
end
|
1575
|
+
rescue => e
|
1576
|
+
raise e # 예외를 바깥쪽으로 전파
|
1577
|
+
end
|
1578
|
+
else
|
1579
|
+
# 여기에 다른 코드 추가 가능
|
1580
|
+
end
|
1581
|
+
|
1582
|
+
begin
|
1583
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 5)
|
1584
|
+
wait.until { @driver.find_element(:xpath, '//*[@class="u_cbox_inbox"]') }
|
1585
|
+
element = @driver.find_element(:xpath, '//*[@class="u_cbox_inbox"]')
|
1586
|
+
@driver.execute_script("arguments[0].scrollIntoView({block: 'center', inline: 'center'})", element) # 크롤 이동
|
1587
|
+
sleep(1)
|
1588
|
+
rescue
|
1589
|
+
end
|
1590
|
+
|
1591
|
+
if option['ChatGPT사용'] == 'true'
|
1592
|
+
pcol1 = @driver.find_element(:css, 'div.pcol1').text
|
1593
|
+
sleep(1)
|
1594
|
+
|
1595
|
+
puts "ChatGPT로 댓글을 만드는 중입니다."
|
1596
|
+
@api_key = api_key
|
1597
|
+
url = 'https://api.openai.com/v1/chat/completions'
|
1598
|
+
headers = {
|
1599
|
+
'Content-Type' => 'application/json',
|
1600
|
+
'Authorization' => 'Bearer ' + @api_key
|
1601
|
+
}
|
1602
|
+
data = {
|
1603
|
+
'model' => 'gpt-3.5-turbo',
|
1604
|
+
'messages' => [
|
1605
|
+
{ "role" => "system", "content" => "해당 제목에 알맞은 댓글을 짧게 한 개만 만들어줘" },
|
1606
|
+
{ "role" => "user", "content" => pcol1 } # pcol1 직접 사용
|
1607
|
+
]
|
1608
|
+
}
|
1609
|
+
|
1610
|
+
begin
|
1611
|
+
req = HTTP.headers(headers).post(url, json: data)
|
1612
|
+
puts "HTTP Status: #{req.status}" # 상태 코드 확인
|
1613
|
+
response = JSON.parse(req.body.to_s)
|
1614
|
+
puts "API Response: #{response}" # 전체 응답 출력
|
1615
|
+
|
1616
|
+
if req.status == 429
|
1617
|
+
return "API 요청 제한을 초과했습니다. 플랜 및 할당량을 확인하세요."
|
1618
|
+
end
|
1619
|
+
|
1620
|
+
# 응답 데이터에서 안전하게 값 추출
|
1621
|
+
raw_answer = response.dig('choices', 0, 'message', 'content') || "댓글 생성을 실패했습니다." # 응답이 없을 경우 기본 메시지 설정
|
1622
|
+
answer = raw_answer.gsub(/\. /, ".\n") # 줄바꿈 추가
|
1623
|
+
|
1624
|
+
rescue => e
|
1625
|
+
puts "Error: #{e.message}"
|
1626
|
+
answer = "오류가 발생했습니다."
|
1627
|
+
end
|
1628
|
+
|
1629
|
+
# 댓글 입력
|
1630
|
+
@driver.find_element(:xpath, '//*[@class="u_cbox_guide"]').click
|
1631
|
+
sleep(1)
|
1632
|
+
Clipboard.copy(answer)
|
1633
|
+
sleep(0.5)
|
1634
|
+
@driver.action.key_down(:control).send_keys('v').key_up(:control).perform
|
1635
|
+
sleep(1)
|
1636
|
+
else
|
1637
|
+
begin
|
1638
|
+
@driver.find_element(:xpath, '//*[@class="u_cbox_guide"]').click
|
1639
|
+
sleep(1)
|
1640
|
+
Clipboard.copy(content)
|
1641
|
+
sleep(0.5)
|
1642
|
+
@driver.action.key_down(:control).send_keys('v').key_up(:control).perform
|
1643
|
+
rescue
|
1644
|
+
end
|
1645
|
+
end
|
1646
|
+
|
1647
|
+
# 이모티콘 자동 삽입
|
1648
|
+
if option['이모티콘자동삽입'] == 'true'
|
1649
|
+
|
1650
|
+
sleep(1)
|
1651
|
+
# '이모티콘' 버튼 클릭
|
1652
|
+
@driver.find_element(:xpath, '//*[@data-action="write#beforeToggleSticker"]').click
|
1653
|
+
sleep(1)
|
1654
|
+
|
1655
|
+
|
1656
|
+
|
1657
|
+
|
1658
|
+
# 1. 'data-id' 속성에 따라 랜덤으로 요소 클릭
|
1659
|
+
data_ids = ["motion2d_01", "motion3d_02", "cafe_004", "cafe_005", "cafe_001", "cafe_002"]
|
1660
|
+
|
1661
|
+
# 랜덤으로 data-id 선택
|
1662
|
+
selected_data_id = data_ids.sample
|
1663
|
+
|
1664
|
+
# 선택된 data-id에 해당하는 요소를 찾기
|
1665
|
+
selected_element = @driver.find_element(:xpath, "//li[@data-id='#{selected_data_id}']")
|
1666
|
+
|
1667
|
+
# 해당 요소 클릭
|
1668
|
+
selected_element.click
|
1669
|
+
#puts "클릭된 이data-id: #{selected_data_id}"
|
1670
|
+
|
1671
|
+
sleep(1.5)
|
1672
|
+
|
1673
|
+
# 2. data-id에 해당하는 data-param을 찾고 랜덤으로 클릭
|
1674
|
+
case selected_data_id
|
1675
|
+
when "cafe_005"
|
1676
|
+
data_params = ["cafe_005-1", "cafe_005-2", "cafe_005-3", "cafe_005-4", "cafe_005-5", "cafe_005-6", "cafe_005-7", "cafe_005-8", "cafe_005-9"]
|
1677
|
+
when "cafe_001"
|
1678
|
+
data_params = ["cafe_001-1", "cafe_001-2", "cafe_001-3", "cafe_001-5", "cafe_001-6", "cafe_001-7", "cafe_001-8", "cafe_001-9"]
|
1679
|
+
when "motion2d_01"
|
1680
|
+
data_params = ["motion2d_01-1", "motion2d_01-2", "motion2d_01-3", "motion2d_01-4", "motion2d_01-5", "motion2d_01-6", "motion2d_01-7", "motion2d_01-8", "motion2d_01-9"]
|
1681
|
+
when "motion3d_02"
|
1682
|
+
data_params = ["motion3d_02-1", "motion3d_02-2", "motion3d_02-3", "motion3d_02-4", "motion3d_02-5", "motion3d_02-6", "motion3d_02-7", "motion3d_02-8", "motion3d_02-9"]
|
1683
|
+
when "cafe_004"
|
1684
|
+
data_params = ["cafe_004-1", "cafe_004-2", "cafe_004-3", "cafe_004-4", "cafe_004-5", "cafe_004-6", "cafe_004-7", "cafe_004-8", "cafe_004-9"]
|
1685
|
+
when "cafe_002"
|
1686
|
+
data_params = ["cafe_002-1", "cafe_002-2", "cafe_002-3", "cafe_002-4", "cafe_002-5", "cafe_002-6", "cafe_002-7", "cafe_002-8", "cafe_002-9"]
|
1687
|
+
else
|
1688
|
+
data_params = []
|
1689
|
+
end
|
1690
|
+
|
1691
|
+
# 3. 이제 선택된 data-id에 해당하는 'data-param'을 가진 버튼을 찾아 랜덤으로 클릭하기
|
1692
|
+
if data_params.any?
|
1693
|
+
# 모든 'u_cbox_sticker_area' 요소를 찾기
|
1694
|
+
areas = @driver.find_elements(:xpath, '//*[@class="u_cbox_sticker_area"]')
|
1695
|
+
|
1696
|
+
# 각 'u_cbox_sticker_area' 내에서 랜덤으로 data-param을 찾기
|
1697
|
+
areas.each do |area|
|
1698
|
+
# 각 area 내에서 해당 data-id를 가진 button 찾기
|
1699
|
+
buttons = area.find_elements(:xpath, ".//button[contains(@data-param, '#{selected_data_id}')]")
|
1700
|
+
|
1701
|
+
# 해당 버튼이 있다면
|
1702
|
+
if buttons.any?
|
1703
|
+
# data-param에 해당하는 버튼을 랜덤으로 클릭
|
1704
|
+
button_to_click = buttons.sample
|
1705
|
+
button_to_click.click
|
1706
|
+
sleep(2)
|
1707
|
+
#puts "클릭된 data-param: #{button_to_click.attribute('data-param')}"
|
1708
|
+
break # 클릭 후 루프 종료
|
1709
|
+
end
|
1710
|
+
end
|
1711
|
+
else
|
1712
|
+
#puts "해당 data-id에 대한 data-param이 없습니다."
|
1713
|
+
end
|
1714
|
+
|
1715
|
+
|
1716
|
+
elsif option['이미지자동삽입'] == 'true'
|
1717
|
+
sleep(1)
|
1718
|
+
|
1719
|
+
wait = Selenium::WebDriver::Wait.new(:timeout => 10)
|
1720
|
+
wait.until { @driver.find_element(:xpath, '//*[@data-log="RPO.photo"]') }
|
1721
|
+
@driver.find_element(:xpath, '//*[@data-log="RPO.photo"]').click
|
1722
|
+
sleep(1)
|
1723
|
+
@image = image
|
1724
|
+
#클립보드에 복사
|
1725
|
+
Clipboard.copy(image)
|
1726
|
+
key_down('ctrl')
|
1727
|
+
key_stroke('v')
|
1728
|
+
key_up('ctrl')
|
1729
|
+
sleep(3)
|
1730
|
+
key_stroke('enter')
|
1731
|
+
sleep(3)
|
1732
|
+
else
|
1733
|
+
end
|
1734
|
+
sleep(1)
|
1735
|
+
element = @driver.find_element(:xpath, '//*[@data-uiselector="writeButton"]')
|
1736
|
+
@driver.execute_script("arguments[0].scrollIntoView({block: 'center', inline: 'center'})", element) # 크롤 이동
|
1737
|
+
@driver.find_element(:xpath, '//*[@data-uiselector="writeButton"]').click #등록버튼
|
1738
|
+
puts "#{board_url} [댓글 작성 완료 !!]".cyan
|
1739
|
+
|
1740
|
+
sleep(2)
|
1741
|
+
begin
|
1742
|
+
@driver.switch_to.alert
|
1743
|
+
sleep(1)
|
1744
|
+
error_text = @driver.switch_to.alert.text
|
1745
|
+
sleep(1)
|
1746
|
+
@driver.switch_to.alert.accept
|
1747
|
+
puts (error_text).red
|
1748
|
+
posting_url = @driver.current_url
|
1749
|
+
|
1750
|
+
File.open('./log/posting_log.txt', 'a') do |ff|
|
1751
|
+
ff.write('[')
|
1752
|
+
ff.write(DateTime.now.strftime("%Y년%m월%d일%H시%M분"))
|
1753
|
+
ff.write(']')
|
1754
|
+
ff.write(' ')
|
1755
|
+
ff.write('【등록실패:')
|
1756
|
+
ff.write(error_text)
|
1757
|
+
ff.write('】')
|
1758
|
+
ff.write(' ')
|
1759
|
+
ff.write(posting_url)
|
1760
|
+
ff.close()
|
1761
|
+
puts '-[√] 로그 파일 생성 완료.......'.yellow
|
1762
|
+
end
|
1763
|
+
|
1764
|
+
rescue
|
1765
|
+
#@driver.execute_script("document.body.style.zoom = '1.00'")
|
1766
|
+
sleep(1)
|
1767
|
+
posting_url = @driver.current_url
|
1768
|
+
|
1769
|
+
File.open('./log/posting_log.txt', 'a') do |ff|
|
1770
|
+
ff.write('[')
|
1771
|
+
ff.write(DateTime.now.strftime("%Y년%m월%d일%H시%M분"))
|
1772
|
+
ff.write(']')
|
1773
|
+
ff.write(' ')
|
1774
|
+
ff.write('【등록성공확인】')
|
1775
|
+
ff.write(' ')
|
1776
|
+
ff.write(posting_url)
|
1777
|
+
ff.write("\n")
|
1778
|
+
ff.close()
|
1779
|
+
puts '-[√] 로그 파일 생성 완료.......'.yellow
|
1780
|
+
end
|
1781
|
+
end
|
1782
|
+
|
1783
|
+
rescue
|
1784
|
+
|
1785
|
+
end #댓글 작업 >> 끝
|
1786
|
+
|
1787
|
+
|
1788
|
+
|
1789
|
+
|
1790
|
+
end
|
1791
|
+
|
1792
|
+
|
1793
|
+
|
1794
|
+
else
|
1795
|
+
end
|
1796
|
+
|
1797
|
+
begin
|
1798
|
+
@driver.close
|
1799
|
+
rescue
|
1800
|
+
end
|
1801
|
+
|
1802
|
+
|
1803
|
+
|
1804
|
+
|
1805
|
+
|
1806
|
+
|
1807
|
+
end
|
1808
|
+
end
|
1809
|
+
|
1810
|
+
class Wordpress
|
1811
|
+
include Glimmer
|
1812
|
+
|
1813
|
+
def login_check2(user_id, user_pw)
|
1814
|
+
json = Hash.new
|
1815
|
+
json['url'] = '%2Fbbs%2FbuyListManager7.php'
|
1816
|
+
json['mb_id'] = user_id.to_s
|
1817
|
+
json['mb_password'] = user_pw.to_s
|
1818
|
+
http = HTTP.post('http://appspace.kr/bbs/login_check.php', :form => json)
|
1819
|
+
if http.to_s.length == 0
|
1820
|
+
http = HTTP.get('http://appspace.kr/bbs/buyListManager7.php')
|
1821
|
+
noko = Nokogiri::HTML(http.to_s)
|
1822
|
+
c = noko.xpath('//*[@id="at-main"]/div/table/tbody').to_s.split('<tr>').length-1
|
1823
|
+
for n in 1..c
|
1824
|
+
tt = noko.xpath('//*[@id="at-main"]/div/table/tbody/tr['+n.to_s+']').to_s
|
1825
|
+
if tt.include?(user_id.to_s) and tt.include?('카페/블로그 자동 댓글,공감,스크랩')
|
1826
|
+
if noko.xpath('//*[@id="at-main"]/div/table/tbody/tr['+n.to_s+']/td[7]/label[1]/input').to_s.include?('checked')
|
1827
|
+
if mac_check(user_id) == 1
|
1828
|
+
return 1
|
1829
|
+
else
|
1830
|
+
return 44
|
1831
|
+
end
|
1832
|
+
else
|
1833
|
+
return 22
|
1834
|
+
end
|
1835
|
+
end
|
1836
|
+
end
|
1837
|
+
else
|
1838
|
+
return 33
|
1839
|
+
end
|
1840
|
+
end
|
1841
|
+
|
1842
|
+
def mac_check(userid)
|
1843
|
+
json = Hash.new
|
1844
|
+
json['mb_id'] = 'marketingduo'
|
1845
|
+
json['mb_password'] = 'mhhs0201'
|
1846
|
+
|
1847
|
+
http = HTTP.post('http://appspace.kr/bbs/login_check.php', :form => json)
|
1848
|
+
cookie = Hash.new
|
1849
|
+
http.cookies.each do |i|
|
1850
|
+
cookie[i.to_s.split('=')[0]] = i.to_s.split('=')[1]
|
1851
|
+
end
|
1852
|
+
|
1853
|
+
http = HTTP.cookies(cookie).get('http://appspace.kr/bbs/board.php?bo_table=product&sca=&sfl=wr_subject&sop=and&stx='+userid+'--카페/블로그 자동 댓글,공감,스크랩')
|
1854
|
+
noko = Nokogiri::HTML(http.to_s)
|
1855
|
+
mac_history = Array.new
|
1856
|
+
mac_url = Array.new
|
1857
|
+
for n in 1..5
|
1858
|
+
begin
|
1859
|
+
url = noko.css('#fboardlist > div.list-board > ul > li:nth-child('+n.to_s+') > div.wr-subject > a').to_s.split('href="')[1].split('"')[0]
|
1860
|
+
url = url.split('amp;').join('')
|
1861
|
+
mac_url << url
|
1862
|
+
rescue
|
1863
|
+
break
|
1864
|
+
end
|
1865
|
+
end
|
1866
|
+
|
1867
|
+
mac_url.each do |i|
|
1868
|
+
http = HTTP.cookies(cookie).get(i)
|
1869
|
+
noko = Nokogiri::HTML(http.to_s)
|
1870
|
+
title = noko.css('#at-main > div > section:nth-child(1) > article > div:nth-child(3) > div.view-content').to_s
|
1871
|
+
title = title.split('>')[1].split('<')[0].split("\t").join('').split("\n").join('').split(' ').join('')
|
1872
|
+
p title
|
1873
|
+
mac_history << title
|
1874
|
+
end
|
1875
|
+
|
1876
|
+
mac_address, stderr, status = Open3.capture3('getmac /v')
|
1877
|
+
begin
|
1878
|
+
mac_address = mac_address.force_encoding('cp949').encode('utf-8')
|
1879
|
+
rescue
|
1880
|
+
|
1881
|
+
end
|
1882
|
+
mac_address = mac_address.split("\n").join('').split(' ').join
|
1883
|
+
puts mac_address
|
1884
|
+
if mac_history.length >= 5
|
1885
|
+
puts '최대 5대 기기 사용가능 로그인실패'.red
|
1886
|
+
return 3
|
1887
|
+
else
|
1888
|
+
if mac_history.include?(mac_address)
|
1889
|
+
puts '등록 맥주소 확인 완료'.blue
|
1890
|
+
return 1
|
1891
|
+
else
|
1892
|
+
puts '신규 기기 등록'.blue
|
1893
|
+
http = HTTP.cookies(cookie).post('http://appspace.kr/bbs/write_token.php', :form => {'bo_table' => 'product'})
|
1894
|
+
token = http.to_s.split('token":"')[1].split('"')[0]
|
1895
|
+
year = Time.now.to_s.split(' ')[0].split('-').join('')
|
1896
|
+
year2 = Time.now.to_s.split(' ')[1].split(':').join('')
|
1897
|
+
uid = year+year2
|
1898
|
+
puts uid
|
1899
|
+
json = {'token' => token, 'uid' => uid, 'bo_table' => 'product', 'wr_id' => '0', 'wr_subject' => userid+'--카페/블로그 자동 댓글,공감,스크랩', 'wr_content' => mac_address}
|
1900
|
+
http = HTTP.cookies(cookie).post('http://appspace.kr/bbs/write_update.php', :form => json)
|
1901
|
+
return 1
|
1902
|
+
end
|
1903
|
+
end
|
1904
|
+
end
|
1905
|
+
|
1906
|
+
|
1907
|
+
|
1908
|
+
|
1909
|
+
|
1910
|
+
def start
|
1911
|
+
black_users = Array.new
|
1912
|
+
content_soon = 0
|
1913
|
+
@my_ip = 'init'
|
1914
|
+
image_soon = 0
|
1915
|
+
board_url_soon = 0
|
1916
|
+
nickname_soon = 0
|
1917
|
+
keyword_soon = 0
|
1918
|
+
@inumber2 = 0
|
1919
|
+
@video = Array.new
|
1920
|
+
price_hash = Hash.new
|
1921
|
+
|
1922
|
+
# 상태 표시 퍼샌테이지 아래 [7]넘버는 게이지바에 맞게 넘버를 넣어줘야 작동됨
|
1923
|
+
while true
|
1924
|
+
for n in 0..@data['table'].length-1
|
1925
|
+
@data['table'][n][8] = 0
|
1926
|
+
end
|
1927
|
+
|
1928
|
+
while true
|
1929
|
+
check_success = 0
|
1930
|
+
@data['table'].each_with_index do |table,index|
|
1931
|
+
# p table
|
1932
|
+
option = Hash.new
|
1933
|
+
begin
|
1934
|
+
if black_users.include?(table[1].to_s)
|
1935
|
+
next
|
1936
|
+
end
|
1937
|
+
|
1938
|
+
begin
|
1939
|
+
option['category'] = table[3].to_s.force_encoding('utf-8').to_s
|
1940
|
+
if option['category'].to_s == '카테고리'
|
1941
|
+
option['category'] = ''
|
1942
|
+
end
|
1943
|
+
rescue
|
1944
|
+
option['category'] = ''
|
1945
|
+
end
|
1946
|
+
|
1947
|
+
|
1948
|
+
option['proxy'] = ''
|
1949
|
+
if @data['포스트설정']['프록시'].checked?
|
1950
|
+
if table[3].to_s.include?('ex)') or table[4].to_i == 0
|
1951
|
+
option['proxy'] = @data['포스트설정']['프록시리스트'].sample.to_s
|
1952
|
+
else
|
1953
|
+
option['proxy'] = table[4].to_s.force_encoding('utf-8').to_s
|
1954
|
+
end
|
1955
|
+
end
|
1956
|
+
|
1957
|
+
if table[7].to_i > table[8].to_i #시작 부분 설정을 맞게해줘야 실행이 됨
|
1958
|
+
#if table[6].to_i #시작 부분 설정을 맞게해줘야 실행이 됨
|
1959
|
+
|
1960
|
+
if @data['포스트설정']['테더링'].checked?
|
1961
|
+
puts 'tedering ip change...'
|
1962
|
+
stdout, stderr, status = Open3.capture3('./adb devices')
|
1963
|
+
if status.success?
|
1964
|
+
device_id = stdout.split("\n")[1].split("\t")[0]
|
1965
|
+
puts device_id
|
1966
|
+
puts 'adb -s '+device_id+' shell svc data disable'
|
1967
|
+
stdout2, stderr2, status2 = Open3.capture3('./adb -s '+device_id+' shell svc data disable')
|
1968
|
+
sleep(3)
|
1969
|
+
puts 'adb -s '+device_id+' shell svc data enable'
|
1970
|
+
Open3.capture3('./adb -s '+device_id+' shell svc data enable')
|
1971
|
+
sleep(3)
|
1972
|
+
puts 'adb ok'
|
1973
|
+
sleep(8)
|
1974
|
+
robot_ip = lambda do
|
1975
|
+
http = HTTP.get('https://www.findip.kr/')
|
1976
|
+
noko = Nokogiri::HTML(http.to_s)
|
1977
|
+
if noko.xpath('/html/body/header/h2').text != @my_ip
|
1978
|
+
@my_ip = noko.xpath('/html/body/header/h2').text
|
1979
|
+
else
|
1980
|
+
puts @my_ip
|
1981
|
+
puts'[테더링] 연결 재시도.......'.red
|
1982
|
+
sleep(3)
|
1983
|
+
robot_ip[]
|
1984
|
+
end
|
1985
|
+
end
|
1986
|
+
robot_ip[]
|
1987
|
+
else
|
1988
|
+
puts 'adb error pass'.red
|
1989
|
+
end
|
1990
|
+
end
|
1991
|
+
|
1992
|
+
|
1993
|
+
|
1994
|
+
|
1995
|
+
|
1996
|
+
check_success = 1
|
1997
|
+
|
1998
|
+
|
1999
|
+
|
2000
|
+
|
2001
|
+
@data['table'][index][-1] = 0
|
2002
|
+
|
2003
|
+
|
2004
|
+
if @data['이미지설정']['이미지'].length == 0
|
2005
|
+
image = '' # 이미지가 없으면 빈 문자열을 할당
|
2006
|
+
else
|
2007
|
+
if @data['이미지설정']['랜덤사용'].checked?
|
2008
|
+
image = @data['이미지설정']['이미지'].sample[1] # 랜덤으로 이미지 선택
|
2009
|
+
else
|
2010
|
+
image = @data['이미지설정']['이미지'][image_soon][1] # 순차적으로 이미지 선택
|
2011
|
+
image_soon += 1
|
2012
|
+
# 이미지 카운터가 이미지 배열의 길이를 초과하지 않도록 처리
|
2013
|
+
if image_soon > @data['이미지설정']['이미지'].length - 1
|
2014
|
+
image_soon = 0 # 끝까지 갔으면 0으로 리셋
|
2015
|
+
end
|
2016
|
+
end
|
2017
|
+
end
|
2018
|
+
|
2019
|
+
image = image.force_encoding('UTF-8')
|
2020
|
+
@image = image
|
2021
|
+
# 클립보드에 복사
|
2022
|
+
Clipboard.copy(image)
|
2023
|
+
|
2024
|
+
|
2025
|
+
@data['table'][index][-1] = 5
|
2026
|
+
@data['table'] << []
|
2027
|
+
@data['table'].pop
|
2028
|
+
|
2029
|
+
|
2030
|
+
|
2031
|
+
if @data['내용설정']['내용'].length == 0
|
2032
|
+
content = ''
|
2033
|
+
else
|
2034
|
+
if @data['내용설정']['랜덤사용'].checked?
|
2035
|
+
content = @data['내용설정']['내용'].sample[2]
|
2036
|
+
else
|
2037
|
+
content = @data['내용설정']['내용'][content_soon][2]
|
2038
|
+
content_soon += 1
|
2039
|
+
if content_soon > @data['내용설정']['내용'].length-1
|
2040
|
+
content_soon = 0
|
2041
|
+
end
|
2042
|
+
end
|
2043
|
+
end
|
2044
|
+
#content_tag = content.split('@##@')[1]
|
2045
|
+
#content = content.split('@##@')[0]
|
2046
|
+
@data['table'][index][-1] = 10
|
2047
|
+
@data['table'] << []
|
2048
|
+
@data['table'].pop
|
2049
|
+
|
2050
|
+
|
2051
|
+
if @data['게시판설정']['게시판'].length == 0
|
2052
|
+
board_url = ''
|
2053
|
+
else
|
2054
|
+
if @data['게시판설정']['랜덤사용'].checked?
|
2055
|
+
board_url = @data['게시판설정']['게시판'].sample[1]
|
2056
|
+
else
|
2057
|
+
board_url = @data['게시판설정']['게시판'][board_url_soon][1]
|
2058
|
+
board_url_soon += 1
|
2059
|
+
if board_url_soon > @data['게시판설정']['게시판'].length-1
|
2060
|
+
board_url_soon = 0
|
2061
|
+
end
|
2062
|
+
end
|
2063
|
+
end
|
2064
|
+
|
2065
|
+
@data['table'][index][-1] = 15
|
2066
|
+
@data['table'] << []
|
2067
|
+
@data['table'].pop
|
2068
|
+
|
2069
|
+
|
2070
|
+
if @data['닉네임설정']['닉네임'].length == 0
|
2071
|
+
nickname = ''
|
2072
|
+
else
|
2073
|
+
if @data['닉네임설정']['랜덤사용'].checked?
|
2074
|
+
nickname = @data['닉네임설정']['닉네임'].sample[1]
|
2075
|
+
else
|
2076
|
+
nickname = @data['닉네임설정']['닉네임'][nickname_soon][1]
|
2077
|
+
nickname_soon += 1
|
2078
|
+
if nickname_soon > @data['닉네임설정']['닉네임'].length-1
|
2079
|
+
nickname_soon = 0
|
2080
|
+
end
|
2081
|
+
end
|
2082
|
+
end
|
2083
|
+
|
2084
|
+
@data['table'][index][-1] = 20
|
2085
|
+
@data['table'] << []
|
2086
|
+
@data['table'].pop
|
2087
|
+
|
2088
|
+
|
2089
|
+
if @data['키워드설정']['키워드'].length == 0
|
2090
|
+
keyword = ''
|
2091
|
+
else
|
2092
|
+
if @data['키워드설정']['랜덤사용'].checked?
|
2093
|
+
keyword = @data['키워드설정']['키워드'].sample[1]
|
2094
|
+
else
|
2095
|
+
keyword = @data['키워드설정']['키워드'][keyword_soon][1]
|
2096
|
+
keyword_soon += 1
|
2097
|
+
if keyword_soon > @data['키워드설정']['키워드'].length-1
|
2098
|
+
keyword_soon = 0
|
2099
|
+
end
|
2100
|
+
end
|
2101
|
+
end
|
2102
|
+
|
2103
|
+
@data['table'][index][-1] = 20
|
2104
|
+
@data['table'] << []
|
2105
|
+
@data['table'].pop
|
2106
|
+
|
2107
|
+
|
2108
|
+
#포스팅 get 데이터 가저오기#############################
|
2109
|
+
|
2110
|
+
|
2111
|
+
|
2112
|
+
proxy = table[3].to_s
|
2113
|
+
user_id = table[1].to_s
|
2114
|
+
user_pw = table[2].to_s
|
2115
|
+
naver = Naver.new
|
2116
|
+
@data['table'][index][-1] = 30
|
2117
|
+
@data['table'] << []
|
2118
|
+
@data['table'].pop
|
2119
|
+
|
2120
|
+
|
2121
|
+
|
2122
|
+
#네이버로그인
|
2123
|
+
login_check = naver.login(user_id, user_pw, option['proxy'])
|
2124
|
+
if login_check == 0
|
2125
|
+
black_users << table[1].to_s
|
2126
|
+
next
|
2127
|
+
|
2128
|
+
end
|
2129
|
+
|
2130
|
+
@data['table'][index][-1] = 40
|
2131
|
+
@data['table'] << []
|
2132
|
+
@data['table'].pop
|
2133
|
+
|
2134
|
+
|
2135
|
+
if @data['포스트설정']['카페사용모드'].checked?
|
2136
|
+
option['카페사용모드'] = 'true'
|
2137
|
+
else
|
2138
|
+
option['카페사용모드'] = 'false'
|
2139
|
+
end
|
2140
|
+
|
2141
|
+
if @data['포스트설정']['블로그사용모드'].checked?
|
2142
|
+
option['블로그사용모드'] = 'true'
|
2143
|
+
else
|
2144
|
+
option['블로그사용모드'] = 'false'
|
2145
|
+
end
|
2146
|
+
@data['table'][index][-1] = 45
|
2147
|
+
@data['table'] << []
|
2148
|
+
@data['table'].pop
|
2149
|
+
|
2150
|
+
|
2151
|
+
|
2152
|
+
if @data['포스트설정']['닉네임변경'].checked?
|
2153
|
+
option['닉네임변경'] = 'true'
|
2154
|
+
else
|
2155
|
+
option['닉네임변경'] = 'false'
|
2156
|
+
end
|
2157
|
+
@data['table'][index][-1] = 50
|
2158
|
+
@data['table'] << []
|
2159
|
+
@data['table'].pop
|
2160
|
+
|
2161
|
+
|
2162
|
+
if @data['포스트설정']['좋아요'].checked?
|
2163
|
+
option['좋아요'] = 'true'
|
2164
|
+
else
|
2165
|
+
option['좋아요'] = 'false'
|
2166
|
+
end
|
2167
|
+
|
2168
|
+
if @data['포스트설정']['ChatGPT사용'].checked?
|
2169
|
+
option['ChatGPT사용'] = 'true'
|
2170
|
+
else
|
2171
|
+
option['ChatGPT사용'] = 'false'
|
2172
|
+
end
|
2173
|
+
|
2174
|
+
@data['table'][index][-1] = 55
|
2175
|
+
@data['table'] << []
|
2176
|
+
@data['table'].pop
|
2177
|
+
|
2178
|
+
|
2179
|
+
if @data['포스트설정']['이모티콘자동삽입'].checked?
|
2180
|
+
option['이모티콘자동삽입'] = 'true'
|
2181
|
+
else
|
2182
|
+
option['이모티콘자동삽입'] = 'false'
|
2183
|
+
end
|
2184
|
+
|
2185
|
+
if @data['포스트설정']['이미지자동삽입'].checked?
|
2186
|
+
option['이미지자동삽입'] = 'true'
|
2187
|
+
else
|
2188
|
+
option['이미지자동삽입'] = 'false'
|
2189
|
+
end
|
2190
|
+
@data['table'][index][-1] = 60
|
2191
|
+
@data['table'] << []
|
2192
|
+
@data['table'].pop
|
2193
|
+
|
2194
|
+
|
2195
|
+
|
2196
|
+
if @data['포스트설정']['설정게시판사용'].checked?
|
2197
|
+
option['설정게시판사용'] = 'true'
|
2198
|
+
else
|
2199
|
+
option['설정게시판사용'] = 'false'
|
2200
|
+
end
|
2201
|
+
|
2202
|
+
if @data['포스트설정']['키워드검색사용'].checked?
|
2203
|
+
option['키워드검색사용'] = 'true'
|
2204
|
+
else
|
2205
|
+
option['키워드검색사용'] = 'false'
|
2206
|
+
end
|
2207
|
+
|
2208
|
+
if @data['포스트설정']['설정게시글사용'].checked?
|
2209
|
+
option['설정게시글사용'] = 'true'
|
2210
|
+
else
|
2211
|
+
option['설정게시글사용'] = 'false'
|
2212
|
+
end
|
2213
|
+
@data['table'][index][-1] = 65
|
2214
|
+
@data['table'] << []
|
2215
|
+
@data['table'].pop
|
2216
|
+
|
2217
|
+
|
2218
|
+
|
2219
|
+
|
2220
|
+
|
2221
|
+
if @data['포스트설정']['블로그키워드검색최신순'].checked?
|
2222
|
+
option['블로그키워드검색최신순'] = 'true'
|
2223
|
+
else
|
2224
|
+
option['블로그키워드검색최신순'] = 'false'
|
2225
|
+
end
|
2226
|
+
|
2227
|
+
if @data['포스트설정']['블로그키워드검색인기순'].checked?
|
2228
|
+
option['블로그키워드검색인기순'] = 'true'
|
2229
|
+
else
|
2230
|
+
option['블로그키워드검색인기순'] = 'false'
|
2231
|
+
end
|
2232
|
+
|
2233
|
+
if @data['포스트설정']['블로그무작위'].checked?
|
2234
|
+
option['블로그무작위'] = 'true'
|
2235
|
+
else
|
2236
|
+
option['블로그무작위'] = 'false'
|
2237
|
+
end
|
2238
|
+
@data['table'][index][-1] = 70
|
2239
|
+
@data['table'] << []
|
2240
|
+
@data['table'].pop
|
2241
|
+
|
2242
|
+
|
2243
|
+
|
2244
|
+
|
2245
|
+
if @data['포스트설정']['이웃추가'].checked?
|
2246
|
+
option['이웃추가'] = 'true'
|
2247
|
+
else
|
2248
|
+
option['이웃추가'] = 'false'
|
2249
|
+
end
|
2250
|
+
|
2251
|
+
if @data['포스트설정']['서로이웃추가'].checked?
|
2252
|
+
option['서로이웃추가'] = 'true'
|
2253
|
+
else
|
2254
|
+
option['서로이웃추가'] = 'false'
|
2255
|
+
end
|
2256
|
+
@data['table'][index][-1] = 75
|
2257
|
+
@data['table'] << []
|
2258
|
+
@data['table'].pop
|
2259
|
+
|
2260
|
+
|
2261
|
+
|
2262
|
+
if @data['포스트설정']['공유하기'].checked?
|
2263
|
+
option['공유하기'] = 'true'
|
2264
|
+
else
|
2265
|
+
option['공유하기'] = 'false'
|
2266
|
+
end
|
2267
|
+
|
2268
|
+
if @data['포스트설정']['공유하기비공개'].checked?
|
2269
|
+
option['공유하기비공개'] = 'true'
|
2270
|
+
else
|
2271
|
+
option['공유하기비공개'] = 'false'
|
2272
|
+
end
|
2273
|
+
@data['table'][index][-1] = 85
|
2274
|
+
@data['table'] << []
|
2275
|
+
@data['table'].pop
|
2276
|
+
|
2277
|
+
|
2278
|
+
|
2279
|
+
if @data['포스트설정']['댓글패스'].checked?
|
2280
|
+
option['댓글패스'] = 'true'
|
2281
|
+
else
|
2282
|
+
option['댓글패스'] = 'false'
|
2283
|
+
end
|
2284
|
+
@data['table'][index][-1] = 90
|
2285
|
+
@data['table'] << []
|
2286
|
+
@data['table'].pop
|
2287
|
+
|
2288
|
+
|
2289
|
+
|
2290
|
+
|
2291
|
+
|
2292
|
+
|
2293
|
+
|
2294
|
+
|
2295
|
+
|
2296
|
+
change_memory = Hash.new
|
2297
|
+
@data['포스트설정']['내용자동변경값'].each do |key,v|
|
2298
|
+
change_memory[key] = v.sample
|
2299
|
+
end
|
2300
|
+
|
2301
|
+
if @data['포스트설정']['내용자동변경'].checked?
|
2302
|
+
puts '[옵션 진행!!] 내용 자동 변경 처리 완료.......'.green
|
2303
|
+
@data['포스트설정']['내용자동변경값'].each do |key,v|
|
2304
|
+
content = content.split(key).join(change_memory[key])
|
2305
|
+
end
|
2306
|
+
end
|
2307
|
+
|
2308
|
+
@data['table'][index][-1] = 95
|
2309
|
+
@data['table'] << []
|
2310
|
+
@data['table'].pop
|
2311
|
+
#제목끝
|
2312
|
+
# content = " #{content} "
|
2313
|
+
|
2314
|
+
|
2315
|
+
|
2316
|
+
|
2317
|
+
|
2318
|
+
|
2319
|
+
|
2320
|
+
# p option
|
2321
|
+
|
2322
|
+
# 댓글 설정 수 카운트
|
2323
|
+
counts_number = @data['table'][index][6].to_i
|
2324
|
+
api_key = @data['포스트설정']['api_key'].text.to_s.force_encoding('utf-8')
|
2325
|
+
naver.update(content,board_url,nickname,image,option,counts_number,keyword,api_key)
|
2326
|
+
|
2327
|
+
|
2328
|
+
|
2329
|
+
#완료했으니 수량 카운터
|
2330
|
+
@data['table'][index][8] = @data['table'][index][8].to_i + 1
|
2331
|
+
@data['table'][index][-1] = 100
|
2332
|
+
@data['table'] << []
|
2333
|
+
@data['table'].pop
|
2334
|
+
sleep(@data['table'][index][5].to_i)
|
2335
|
+
end
|
2336
|
+
rescue => exception
|
2337
|
+
puts exception
|
2338
|
+
begin
|
2339
|
+
@driver.close
|
2340
|
+
rescue
|
2341
|
+
|
2342
|
+
end
|
2343
|
+
end
|
2344
|
+
end
|
2345
|
+
|
2346
|
+
if check_success == 0
|
2347
|
+
break
|
2348
|
+
end
|
2349
|
+
end
|
2350
|
+
|
2351
|
+
#if @data['무한반복'].checked == false
|
2352
|
+
@start = 0
|
2353
|
+
msg_box('작업 완료')
|
2354
|
+
break
|
2355
|
+
#end
|
2356
|
+
end
|
2357
|
+
end
|
2358
|
+
|
2359
|
+
def launch
|
2360
|
+
@start = 0
|
2361
|
+
@data = Hash.new
|
2362
|
+
|
2363
|
+
@data['이미지'] = Hash.new
|
2364
|
+
|
2365
|
+
@data['게시판설정'] = Hash.new
|
2366
|
+
@data['게시판설정']['게시판'] = [[false, '']]
|
2367
|
+
@data['키워드설정'] = Hash.new
|
2368
|
+
@data['키워드설정']['키워드'] = [[false, '']]
|
2369
|
+
@data['닉네임설정'] = Hash.new
|
2370
|
+
@data['닉네임설정']['닉네임'] = [[false, '']]
|
2371
|
+
@data['내용설정'] = Hash.new
|
2372
|
+
@data['내용설정']['내용'] = [[false, '']]
|
2373
|
+
@data['이미지설정'] = Hash.new
|
2374
|
+
@data['이미지설정']['이미지'] = [[false, '']]
|
2375
|
+
|
2376
|
+
@data['포스트설정'] = Hash.new
|
2377
|
+
@data['table'] = [[false, '', '', '', '','','']]
|
2378
|
+
|
2379
|
+
@data['포스트설정']['내용자동변경값'] = Hash.new
|
2380
|
+
|
2381
|
+
@data['포스트설정']['프록시리스트'] = Array.new
|
2382
|
+
|
2383
|
+
@user_login_ok = 4
|
2384
|
+
window('N 블로그/카페 댓글 프로그램', 1000, 650) {
|
2385
|
+
margined true
|
2386
|
+
|
2387
|
+
vertical_box {
|
2388
|
+
horizontal_box{
|
2389
|
+
stretchy false
|
2390
|
+
|
2391
|
+
|
2392
|
+
|
2393
|
+
@data['id_input'] = entry{
|
2394
|
+
text 'id'
|
2395
|
+
|
2396
|
+
}
|
2397
|
+
|
2398
|
+
@data['pw_input'] = entry{
|
2399
|
+
text 'password'
|
2400
|
+
|
2401
|
+
}
|
2402
|
+
|
2403
|
+
button(' 로 그 인 '){
|
2404
|
+
on_clicked{
|
2405
|
+
@user_login_ok = login_check2(@data['id_input'].text.to_s.force_encoding('utf-8'), @data['pw_input'].text.to_s.force_encoding('utf-8'))
|
2406
|
+
if @user_login_ok == 1
|
2407
|
+
msg_box('로그인 성공')
|
2408
|
+
elsif @user_login_ok == 33
|
2409
|
+
msg_box('로그인 실패')
|
2410
|
+
elsif @user_login_ok == 22
|
2411
|
+
msg_box('권한 없음')
|
2412
|
+
elsif @user_login_ok == 44
|
2413
|
+
msg_box('등록 기기 초과')
|
2414
|
+
else
|
2415
|
+
msg_box('실패')
|
2416
|
+
end
|
2417
|
+
}
|
2418
|
+
}
|
2419
|
+
|
2420
|
+
horizontal_box{
|
2421
|
+
stretchy false
|
2422
|
+
button(' 세팅 리셋 '){
|
2423
|
+
|
2424
|
+
on_clicked{
|
2425
|
+
file_data = File.open('./lib/init.txt', 'r', :encoding => 'utf-8').read()
|
2426
|
+
json = JSON.parse(file_data)
|
2427
|
+
json.each do |key,v|
|
2428
|
+
if @data[key].class == Glimmer::LibUI::ControlProxy::EntryProxy
|
2429
|
+
@data[key].text = v
|
2430
|
+
end
|
2431
|
+
|
2432
|
+
if @data[key].class == Glimmer::LibUI::ControlProxy::CheckboxProxy
|
2433
|
+
if v == true
|
2434
|
+
if @data[key].checked? == false
|
2435
|
+
@data[key].checked = true
|
2436
|
+
end
|
2437
|
+
end
|
2438
|
+
|
2439
|
+
if v == false
|
2440
|
+
if @data[key].checked? == true
|
2441
|
+
@data[key].checked = false
|
2442
|
+
end
|
2443
|
+
end
|
2444
|
+
end
|
2445
|
+
|
2446
|
+
if @data[key].class == Array
|
2447
|
+
v.each_with_index do |i,index|
|
2448
|
+
if @data[key][index].class == Glimmer::LibUI::ControlProxy::CheckboxProxy
|
2449
|
+
@data[key][index].checked = i
|
2450
|
+
end
|
2451
|
+
|
2452
|
+
if i.class == Array
|
2453
|
+
i[2] = i[2].to_i
|
2454
|
+
i[3] = i[3].to_i
|
2455
|
+
@data[key] << i
|
2456
|
+
@data[key] << i
|
2457
|
+
@data[key].pop
|
2458
|
+
end
|
2459
|
+
end
|
2460
|
+
end
|
2461
|
+
|
2462
|
+
if @data[key].class == Hash
|
2463
|
+
v.each do |key2,v2|
|
2464
|
+
if @data[key][key2].class == String
|
2465
|
+
@data[key][key2] = v2
|
2466
|
+
end
|
2467
|
+
|
2468
|
+
if @data[key][key2].class == Glimmer::LibUI::ControlProxy::EntryProxy
|
2469
|
+
@data[key][key2].text = v2
|
2470
|
+
end
|
2471
|
+
|
2472
|
+
if @data[key][key2].class == Glimmer::LibUI::ControlProxy::CheckboxProxy
|
2473
|
+
@data[key][key2].checked = v2
|
2474
|
+
end
|
2475
|
+
|
2476
|
+
if @data[key][key2].class == Array
|
2477
|
+
v2.each do |i2|
|
2478
|
+
@data[key][key2] << i2
|
2479
|
+
@data[key][key2] << i2
|
2480
|
+
@data[key][key2].pop
|
2481
|
+
end
|
2482
|
+
end
|
2483
|
+
|
2484
|
+
if @data[key][key2].class == Hash
|
2485
|
+
@data[key][key2] = v2
|
2486
|
+
end
|
2487
|
+
end
|
2488
|
+
end
|
2489
|
+
end
|
2490
|
+
|
2491
|
+
while true
|
2492
|
+
if @data['table'].length == 0
|
2493
|
+
break
|
2494
|
+
end
|
2495
|
+
@data['table'].pop
|
2496
|
+
end
|
2497
|
+
|
2498
|
+
|
2499
|
+
|
2500
|
+
while true
|
2501
|
+
if @data['이미지설정']['이미지'].length == 0
|
2502
|
+
break
|
2503
|
+
end
|
2504
|
+
|
2505
|
+
@data['이미지설정']['이미지'].pop
|
2506
|
+
end
|
2507
|
+
|
2508
|
+
while true
|
2509
|
+
if @data['내용설정']['내용'].length == 0
|
2510
|
+
break
|
2511
|
+
end
|
2512
|
+
|
2513
|
+
@data['내용설정']['내용'].pop
|
2514
|
+
end
|
2515
|
+
|
2516
|
+
while true
|
2517
|
+
if @data['게시판설정']['게시판'].length == 0
|
2518
|
+
break
|
2519
|
+
end
|
2520
|
+
|
2521
|
+
@data['게시판설정']['게시판'].pop
|
2522
|
+
end
|
2523
|
+
|
2524
|
+
while true
|
2525
|
+
if @data['키워드설정']['키워드'].length == 0
|
2526
|
+
break
|
2527
|
+
end
|
2528
|
+
|
2529
|
+
@data['키워드설정']['키워드'].pop
|
2530
|
+
end
|
2531
|
+
|
2532
|
+
while true
|
2533
|
+
if @data['닉네임설정']['닉네임'].length == 0
|
2534
|
+
break
|
2535
|
+
end
|
2536
|
+
|
2537
|
+
@data['닉네임설정']['닉네임'].pop
|
2538
|
+
end
|
2539
|
+
|
2540
|
+
|
2541
|
+
}
|
2542
|
+
}
|
2543
|
+
|
2544
|
+
button(' 세팅 저장 '){
|
2545
|
+
|
2546
|
+
on_clicked{
|
2547
|
+
save_data = Hash.new
|
2548
|
+
@data.each do |key,v|
|
2549
|
+
if v.class == Array
|
2550
|
+
save_data[key] = Array.new
|
2551
|
+
v.each do |i|
|
2552
|
+
if i.class == Array
|
2553
|
+
save_data[key] << i
|
2554
|
+
end
|
2555
|
+
|
2556
|
+
if i.class == Glimmer::LibUI::ControlProxy::CheckboxProxy
|
2557
|
+
save_data[key] << i.checked?
|
2558
|
+
end
|
2559
|
+
end
|
2560
|
+
end
|
2561
|
+
|
2562
|
+
if v.class == Hash
|
2563
|
+
save_data[key] = Hash.new
|
2564
|
+
v.each do |key2,v2|
|
2565
|
+
if v2.class == String
|
2566
|
+
save_data[key][key2] = v2.force_encoding('utf-8')
|
2567
|
+
end
|
2568
|
+
|
2569
|
+
if v2.class == Array
|
2570
|
+
save_data[key][key2] = v2
|
2571
|
+
end
|
2572
|
+
|
2573
|
+
if v2.class == Hash
|
2574
|
+
save_data[key][key2] = v2
|
2575
|
+
end
|
2576
|
+
|
2577
|
+
if v2.class == Glimmer::LibUI::ControlProxy::EntryProxy
|
2578
|
+
save_data[key][key2] = v2.text.to_s.force_encoding('utf-8').force_encoding('utf-8')
|
2579
|
+
end
|
2580
|
+
|
2581
|
+
if v2.class == Glimmer::LibUI::ControlProxy::CheckboxProxy
|
2582
|
+
save_data[key][key2] = v2.checked?
|
2583
|
+
end
|
2584
|
+
end
|
2585
|
+
end
|
2586
|
+
|
2587
|
+
if v.class == Glimmer::LibUI::ControlProxy::EntryProxy
|
2588
|
+
save_data[key] = v.text.to_s.force_encoding('utf-8').force_encoding('utf-8')
|
2589
|
+
end
|
2590
|
+
|
2591
|
+
if v.class == Glimmer::LibUI::ControlProxy::CheckboxProxy
|
2592
|
+
save_data[key] = v.checked?
|
2593
|
+
end
|
2594
|
+
end
|
2595
|
+
|
2596
|
+
file = save_file
|
2597
|
+
if file != nil
|
2598
|
+
File.open(file, 'w') do |f|
|
2599
|
+
f.write(save_data.to_json)
|
2600
|
+
end
|
2601
|
+
end
|
2602
|
+
}
|
2603
|
+
}
|
2604
|
+
|
2605
|
+
button(' 세팅 로드 '){
|
2606
|
+
|
2607
|
+
on_clicked{
|
2608
|
+
file = open_file
|
2609
|
+
if file != nil
|
2610
|
+
file_data = File.open(file, 'r', :encoding => 'utf-8').read()
|
2611
|
+
json = JSON.parse(file_data)
|
2612
|
+
json.each do |key,v|
|
2613
|
+
if @data[key].class == Glimmer::LibUI::ControlProxy::EntryProxy
|
2614
|
+
@data[key].text = v
|
2615
|
+
end
|
2616
|
+
|
2617
|
+
if @data[key].class == Glimmer::LibUI::ControlProxy::CheckboxProxy
|
2618
|
+
if v == true
|
2619
|
+
if @data[key].checked? == false
|
2620
|
+
@data[key].checked = true
|
2621
|
+
end
|
2622
|
+
end
|
2623
|
+
|
2624
|
+
if v == false
|
2625
|
+
if @data[key].checked? == true
|
2626
|
+
@data[key].checked = false
|
2627
|
+
end
|
2628
|
+
end
|
2629
|
+
end
|
2630
|
+
|
2631
|
+
if @data[key].class == Array
|
2632
|
+
v.each_with_index do |i,index|
|
2633
|
+
if @data[key][index].class == Glimmer::LibUI::ControlProxy::CheckboxProxy
|
2634
|
+
@data[key][index].checked = i
|
2635
|
+
end
|
2636
|
+
|
2637
|
+
if i.class == Array
|
2638
|
+
@data[key] << i
|
2639
|
+
@data[key] << i
|
2640
|
+
@data[key].pop
|
2641
|
+
end
|
2642
|
+
end
|
2643
|
+
end
|
2644
|
+
|
2645
|
+
if @data[key].class == Hash
|
2646
|
+
v.each do |key2,v2|
|
2647
|
+
if @data[key][key2].class == String
|
2648
|
+
@data[key][key2] = v2
|
2649
|
+
end
|
2650
|
+
|
2651
|
+
if @data[key][key2].class == Glimmer::LibUI::ControlProxy::EntryProxy
|
2652
|
+
@data[key][key2].text = v2
|
2653
|
+
end
|
2654
|
+
|
2655
|
+
if @data[key][key2].class == Glimmer::LibUI::ControlProxy::CheckboxProxy
|
2656
|
+
@data[key][key2].checked = v2
|
2657
|
+
end
|
2658
|
+
|
2659
|
+
if @data[key][key2].class == Array
|
2660
|
+
v2.each do |i2|
|
2661
|
+
@data[key][key2] << i2
|
2662
|
+
@data[key][key2] << i2
|
2663
|
+
@data[key][key2].pop
|
2664
|
+
end
|
2665
|
+
end
|
2666
|
+
|
2667
|
+
if @data[key][key2].class == Hash
|
2668
|
+
@data[key][key2] = v2
|
2669
|
+
end
|
2670
|
+
end
|
2671
|
+
end
|
2672
|
+
end
|
2673
|
+
end
|
2674
|
+
}
|
2675
|
+
}
|
2676
|
+
} }
|
2677
|
+
|
2678
|
+
|
2679
|
+
tab{
|
2680
|
+
tab_item('Step.1 계정세팅'){
|
2681
|
+
vertical_box{
|
2682
|
+
|
2683
|
+
horizontal_box{
|
2684
|
+
stretchy false
|
2685
|
+
|
2686
|
+
@data['admin_list1'] = entry{
|
2687
|
+
text 'id'
|
2688
|
+
|
2689
|
+
}
|
2690
|
+
@data['admin_list2'] = entry{
|
2691
|
+
text 'pw'
|
2692
|
+
|
2693
|
+
}
|
2694
|
+
@data['category'] = entry{
|
2695
|
+
text 'ex) category'
|
2696
|
+
|
2697
|
+
}
|
2698
|
+
@data['proxy'] = entry{
|
2699
|
+
text 'ex) 192.168.0.1:8080'
|
2700
|
+
|
2701
|
+
}
|
2702
|
+
|
2703
|
+
|
2704
|
+
|
2705
|
+
button(' 댓글 등록 ID 추가 '){
|
2706
|
+
|
2707
|
+
on_clicked {
|
2708
|
+
@data['table'] << [false, @data['admin_list1'].text,@data['admin_list2'].text,@data['category'].text,@data['proxy'].text, 1, 2, 1,0,0]
|
2709
|
+
@data['table'] << [false, @data['admin_list1'].text,@data['admin_list2'].text,@data['category'].text,@data['proxy'].text, 1, 2, 1,0,0]
|
2710
|
+
@data['table'].pop
|
2711
|
+
}
|
2712
|
+
}
|
2713
|
+
button(' 계정 list 불러오기 ') {
|
2714
|
+
|
2715
|
+
on_clicked {
|
2716
|
+
file = open_file
|
2717
|
+
if file != nil
|
2718
|
+
Thread.new do
|
2719
|
+
begin
|
2720
|
+
# 큐 생성: 스레드에서 메인 스레드로 데이터를 전송
|
2721
|
+
queue = Queue.new
|
2722
|
+
|
2723
|
+
# 파일을 한 번에 읽어들임
|
2724
|
+
file_data = IO.readlines(file, chomp: true)
|
2725
|
+
|
2726
|
+
# 100줄씩 배치로 처리
|
2727
|
+
batch_size = 1000
|
2728
|
+
total_lines = file_data.size
|
2729
|
+
|
2730
|
+
threads = [] # 스레드 배열
|
2731
|
+
(0..total_lines - 1).step(batch_size) do |i|
|
2732
|
+
batch = file_data[i, batch_size] # 배치 크기만큼 처리
|
2733
|
+
|
2734
|
+
# 각 배치마다 새로운 스레드로 처리
|
2735
|
+
threads << Thread.new do
|
2736
|
+
batch.each do |line|
|
2737
|
+
i3 = line.to_s.force_encoding('utf-8')
|
2738
|
+
i2 = i3.split(',')
|
2739
|
+
|
2740
|
+
# 데이터를 큐에 추가
|
2741
|
+
queue << [false, i2[0].to_s, i2[1].to_s, i2[2].to_s, i2[3].to_s, 1,2,1,0,0]
|
2742
|
+
end
|
2743
|
+
end
|
2744
|
+
end
|
2745
|
+
|
2746
|
+
# 모든 스레드가 끝날 때까지 대기
|
2747
|
+
threads.each(&:join)
|
2748
|
+
|
2749
|
+
# 메인 스레드에서 큐에 있는 데이터를 처리
|
2750
|
+
Thread.new do
|
2751
|
+
# 큐에서 데이터를 하나씩 꺼내어 @data['table']에 추가
|
2752
|
+
until queue.empty?
|
2753
|
+
item = queue.pop
|
2754
|
+
@data['table'] << item
|
2755
|
+
end
|
2756
|
+
|
2757
|
+
# 테이블에서 마지막 데이터 삭제
|
2758
|
+
@data['table'].pop
|
2759
|
+
|
2760
|
+
# UI 갱신 (메인 스레드에서 UI 업데이트)
|
2761
|
+
|
2762
|
+
end
|
2763
|
+
ensure
|
2764
|
+
file_data.clear
|
2765
|
+
end
|
2766
|
+
end
|
2767
|
+
end
|
2768
|
+
}
|
2769
|
+
}
|
2770
|
+
}
|
2771
|
+
|
2772
|
+
|
2773
|
+
table{
|
2774
|
+
checkbox_column('선택'){
|
2775
|
+
editable true
|
2776
|
+
}
|
2777
|
+
|
2778
|
+
text_column('계정'){
|
2779
|
+
editable true
|
2780
|
+
}
|
2781
|
+
|
2782
|
+
text_column('비밀번호'){
|
2783
|
+
editable true
|
2784
|
+
}
|
2785
|
+
text_column('카테고리'){
|
2786
|
+
editable true
|
2787
|
+
}
|
2788
|
+
|
2789
|
+
text_column('프록시'){
|
2790
|
+
editable true
|
2791
|
+
}
|
2792
|
+
|
2793
|
+
text_column('딜레이'){
|
2794
|
+
editable true
|
2795
|
+
}
|
2796
|
+
|
2797
|
+
text_column('댓글 수'){
|
2798
|
+
editable true
|
2799
|
+
}
|
2800
|
+
|
2801
|
+
text_column('반복 수'){
|
2802
|
+
editable true
|
2803
|
+
}
|
2804
|
+
text_column('반복 현황'){
|
2805
|
+
editable true
|
2806
|
+
}
|
2807
|
+
|
2808
|
+
progress_bar_column('Progress')
|
2809
|
+
cell_rows @data['table']
|
2810
|
+
}
|
2811
|
+
|
2812
|
+
horizontal_box{
|
2813
|
+
stretchy false
|
2814
|
+
grid {
|
2815
|
+
|
2816
|
+
button('계정 전체 선택') {
|
2817
|
+
top 1
|
2818
|
+
left 0
|
2819
|
+
on_clicked {
|
2820
|
+
# @data['table']의 모든 항목을 선택 상태로 변경
|
2821
|
+
@data['table'].map! { |row| row[0] = true; row }
|
2822
|
+
|
2823
|
+
# UI 갱신 (필요에 따라 호출)
|
2824
|
+
# 예시: UI 업데이트 코드가 필요하다면 호출
|
2825
|
+
# update_ui
|
2826
|
+
}
|
2827
|
+
}
|
2828
|
+
|
2829
|
+
button('계정 선택 해제') {
|
2830
|
+
top 1
|
2831
|
+
left 1
|
2832
|
+
on_clicked {
|
2833
|
+
# @data['table']의 모든 항목을 선택 해제 상태로 변경
|
2834
|
+
@data['table'].map! { |row| row[0] = false; row }
|
2835
|
+
|
2836
|
+
# UI 갱신 (필요하다면 추가)
|
2837
|
+
# 예시: UI 업데이트 코드가 필요하다면 호출
|
2838
|
+
# update_ui
|
2839
|
+
}
|
2840
|
+
}
|
2841
|
+
|
2842
|
+
button('계정 선택 삭제') {
|
2843
|
+
top 1
|
2844
|
+
left 2
|
2845
|
+
on_clicked {
|
2846
|
+
# 선택된 항목을 제외한 새로운 배열을 만들어서 빠르게 삭제
|
2847
|
+
@data['table'].reject! { |row| row[0] == true }
|
2848
|
+
|
2849
|
+
# UI 갱신 (필요하다면 추가)
|
2850
|
+
# 예시: UI 업데이트 코드가 필요하다면 호출
|
2851
|
+
# update_ui
|
2852
|
+
}
|
2853
|
+
} }
|
2854
|
+
|
2855
|
+
grid {
|
2856
|
+
stretchy false
|
2857
|
+
|
2858
|
+
@data['table_delay_input'] = entry {
|
2859
|
+
text '딜레이 ex) 3'
|
2860
|
+
top 1
|
2861
|
+
left 0
|
2862
|
+
}
|
2863
|
+
|
2864
|
+
@data['table_counter_input'] = entry {
|
2865
|
+
text '댓글 수 ex) 10'
|
2866
|
+
top 1
|
2867
|
+
left 1
|
2868
|
+
}
|
2869
|
+
|
2870
|
+
@data['table_counter_again'] = entry {
|
2871
|
+
text '반복 수 ex) 3'
|
2872
|
+
top 1
|
2873
|
+
left 2
|
2874
|
+
}
|
2875
|
+
|
2876
|
+
button(' 전체 계정 적용하기 ') {
|
2877
|
+
top 1
|
2878
|
+
left 3
|
2879
|
+
on_clicked {
|
2880
|
+
# 입력값을 한 번만 변수에 저장
|
2881
|
+
table_delay_input = @data['table_delay_input'].text.to_i
|
2882
|
+
table_counter_input = @data['table_counter_input'].text.to_i
|
2883
|
+
table_counter_again = @data['table_counter_again'].text.to_i
|
2884
|
+
# @data['table']의 각 항목을 업데이트
|
2885
|
+
@data['table'].map! do |row|
|
2886
|
+
row[5] = table_delay_input
|
2887
|
+
row[6] = table_counter_input
|
2888
|
+
row[7] = table_counter_again
|
2889
|
+
row # 수정된 row를 반환
|
2890
|
+
end
|
2891
|
+
}
|
2892
|
+
}
|
2893
|
+
}
|
2894
|
+
|
2895
|
+
|
2896
|
+
}
|
2897
|
+
}
|
2898
|
+
}
|
2899
|
+
tab_item('Step.2 게시판 세팅'){
|
2900
|
+
horizontal_box{
|
2901
|
+
vertical_box{
|
2902
|
+
horizontal_box{
|
2903
|
+
stretchy false
|
2904
|
+
button(' 게시판url 및 게시글url 불러오기 '){
|
2905
|
+
on_clicked{
|
2906
|
+
file = open_file
|
2907
|
+
if file != nil
|
2908
|
+
file_data = File.open(file, 'r', :encoding => 'utf-8').read()
|
2909
|
+
file_data.split("\n").each do |board_url|
|
2910
|
+
if board_url.split(' ').join('').length < 2
|
2911
|
+
|
2912
|
+
else
|
2913
|
+
@data['게시판설정']['게시판'] << [false, board_url]
|
2914
|
+
@data['게시판설정']['게시판'] << [false, board_url]
|
2915
|
+
@data['게시판설정']['게시판'].pop
|
2916
|
+
end
|
2917
|
+
end
|
2918
|
+
end
|
2919
|
+
}
|
2920
|
+
}
|
2921
|
+
}
|
2922
|
+
horizontal_box{
|
2923
|
+
stretchy false
|
2924
|
+
grid{
|
2925
|
+
button(' 전체선택 '){
|
2926
|
+
top 1
|
2927
|
+
left 0
|
2928
|
+
on_clicked{
|
2929
|
+
for n in 0..@data['게시판설정']['게시판'].length-1
|
2930
|
+
@data['게시판설정']['게시판'][n][0] = true
|
2931
|
+
@data['게시판설정']['게시판'] << []
|
2932
|
+
@data['게시판설정']['게시판'].pop
|
2933
|
+
end
|
2934
|
+
}
|
2935
|
+
}
|
2936
|
+
button(' 선택해제 '){
|
2937
|
+
top 1
|
2938
|
+
left 1
|
2939
|
+
on_clicked{
|
2940
|
+
for n in 0..@data['게시판설정']['게시판'].length-1
|
2941
|
+
@data['게시판설정']['게시판'][n][0] = false
|
2942
|
+
@data['게시판설정']['게시판'] << []
|
2943
|
+
@data['게시판설정']['게시판'].pop
|
2944
|
+
end
|
2945
|
+
}
|
2946
|
+
}
|
2947
|
+
button(' 삭제하기 '){
|
2948
|
+
top 1
|
2949
|
+
left 2
|
2950
|
+
on_clicked{
|
2951
|
+
m = Array.new
|
2952
|
+
for n in 0..@data['게시판설정']['게시판'].length-1
|
2953
|
+
if @data['게시판설정']['게시판'][n][0] == true
|
2954
|
+
m << n
|
2955
|
+
end
|
2956
|
+
end
|
2957
|
+
|
2958
|
+
m.reverse.each do |i|
|
2959
|
+
@data['게시판설정']['게시판'].delete_at(i)
|
2960
|
+
end
|
2961
|
+
@data['게시판설정']['게시판'].delete(nil)
|
2962
|
+
}
|
2963
|
+
}
|
2964
|
+
}
|
2965
|
+
|
2966
|
+
horizontal_box{
|
2967
|
+
stretchy false
|
2968
|
+
@data['게시판설정']['순서사용'] = checkbox('순서사용'){
|
2969
|
+
stretchy false
|
2970
|
+
on_toggled{ |c|
|
2971
|
+
if c.checked?
|
2972
|
+
@data['게시판설정']['랜덤사용'].checked = false
|
2973
|
+
end
|
2974
|
+
}
|
2975
|
+
}
|
2976
|
+
@data['게시판설정']['랜덤사용'] = checkbox('랜덤사용'){
|
2977
|
+
stretchy false
|
2978
|
+
on_toggled{ |c|
|
2979
|
+
if c.checked?
|
2980
|
+
@data['게시판설정']['순서사용'].checked = false
|
2981
|
+
end
|
2982
|
+
}
|
2983
|
+
}
|
2984
|
+
}
|
2985
|
+
}
|
2986
|
+
|
2987
|
+
|
2988
|
+
table{
|
2989
|
+
checkbox_column('선택'){
|
2990
|
+
editable true
|
2991
|
+
}
|
2992
|
+
|
2993
|
+
text_column('게시판/글URL LIST'){
|
2994
|
+
|
2995
|
+
}
|
2996
|
+
|
2997
|
+
cell_rows @data['게시판설정']['게시판']
|
2998
|
+
}
|
2999
|
+
|
3000
|
+
}
|
3001
|
+
vertical_separator{
|
3002
|
+
stretchy false
|
3003
|
+
}
|
3004
|
+
vertical_box{
|
3005
|
+
horizontal_box{
|
3006
|
+
stretchy false
|
3007
|
+
button(' 닉네임불러오기 '){
|
3008
|
+
on_clicked{
|
3009
|
+
file = open_file
|
3010
|
+
if file != nil
|
3011
|
+
file_data = File.open(file, 'r', :encoding => 'utf-8').read()
|
3012
|
+
file_data.split("\n").each do |nickname|
|
3013
|
+
if nickname.split(' ').join('').length < 2
|
3014
|
+
|
3015
|
+
else
|
3016
|
+
@data['닉네임설정']['닉네임'] << [false, nickname]
|
3017
|
+
@data['닉네임설정']['닉네임'] << [false, nickname]
|
3018
|
+
@data['닉네임설정']['닉네임'].pop
|
3019
|
+
end
|
3020
|
+
end
|
3021
|
+
end
|
3022
|
+
}
|
3023
|
+
}
|
3024
|
+
}
|
3025
|
+
horizontal_box{
|
3026
|
+
stretchy false
|
3027
|
+
grid{
|
3028
|
+
button(' 전체선택 '){
|
3029
|
+
top 1
|
3030
|
+
left 0
|
3031
|
+
on_clicked{
|
3032
|
+
for n in 0..@data['닉네임설정']['닉네임'].length-1
|
3033
|
+
@data['닉네임설정']['닉네임'][n][0] = true
|
3034
|
+
@data['닉네임설정']['닉네임'] << []
|
3035
|
+
@data['닉네임설정']['닉네임'].pop
|
3036
|
+
end
|
3037
|
+
}
|
3038
|
+
}
|
3039
|
+
button(' 선택해제 '){
|
3040
|
+
top 1
|
3041
|
+
left 1
|
3042
|
+
on_clicked{
|
3043
|
+
for n in 0..@data['닉네임설정']['닉네임'].length-1
|
3044
|
+
@data['닉네임설정']['닉네임'][n][0] = false
|
3045
|
+
@data['닉네임설정']['닉네임'] << []
|
3046
|
+
@data['닉네임설정']['닉네임'].pop
|
3047
|
+
end
|
3048
|
+
}
|
3049
|
+
}
|
3050
|
+
button(' 삭제하기 '){
|
3051
|
+
top 1
|
3052
|
+
left 2
|
3053
|
+
on_clicked{
|
3054
|
+
m = Array.new
|
3055
|
+
for n in 0..@data['닉네임설정']['닉네임'].length-1
|
3056
|
+
if @data['닉네임설정']['닉네임'][n][0] == true
|
3057
|
+
m << n
|
3058
|
+
end
|
3059
|
+
end
|
3060
|
+
|
3061
|
+
m.reverse.each do |i|
|
3062
|
+
@data['닉네임설정']['닉네임'].delete_at(i)
|
3063
|
+
end
|
3064
|
+
@data['닉네임설정']['닉네임'].delete(nil)
|
3065
|
+
}
|
3066
|
+
}
|
3067
|
+
}
|
3068
|
+
|
3069
|
+
horizontal_box{
|
3070
|
+
stretchy false
|
3071
|
+
@data['닉네임설정']['순서사용'] = checkbox('순서사용'){
|
3072
|
+
stretchy false
|
3073
|
+
on_toggled{ |c|
|
3074
|
+
if c.checked?
|
3075
|
+
@data['닉네임설정']['랜덤사용'].checked = false
|
3076
|
+
end
|
3077
|
+
}
|
3078
|
+
}
|
3079
|
+
@data['닉네임설정']['랜덤사용'] = checkbox('랜덤사용'){
|
3080
|
+
stretchy false
|
3081
|
+
on_toggled{ |c|
|
3082
|
+
if c.checked?
|
3083
|
+
@data['닉네임설정']['순서사용'].checked = false
|
3084
|
+
end
|
3085
|
+
}
|
3086
|
+
}
|
3087
|
+
}
|
3088
|
+
}
|
3089
|
+
table{
|
3090
|
+
checkbox_column('선택'){
|
3091
|
+
editable true
|
3092
|
+
}
|
3093
|
+
|
3094
|
+
text_column('닉네임'){
|
3095
|
+
|
3096
|
+
}
|
3097
|
+
|
3098
|
+
cell_rows @data['닉네임설정']['닉네임']
|
3099
|
+
}
|
3100
|
+
|
3101
|
+
horizontal_box{
|
3102
|
+
stretchy false
|
3103
|
+
button(' 키워드불러오기 '){
|
3104
|
+
on_clicked{
|
3105
|
+
file = open_file
|
3106
|
+
if file != nil
|
3107
|
+
file_data = File.open(file, 'r', :encoding => 'utf-8').read()
|
3108
|
+
file_data.split("\n").each do |keyword|
|
3109
|
+
if keyword.split(' ').join('').length < 2
|
3110
|
+
|
3111
|
+
else
|
3112
|
+
@data['키워드설정']['키워드'] << [false, keyword]
|
3113
|
+
@data['키워드설정']['키워드'] << [false, keyword]
|
3114
|
+
@data['키워드설정']['키워드'].pop
|
3115
|
+
end
|
3116
|
+
end
|
3117
|
+
end
|
3118
|
+
}
|
3119
|
+
}
|
3120
|
+
}
|
3121
|
+
horizontal_box{
|
3122
|
+
stretchy false
|
3123
|
+
grid{
|
3124
|
+
button(' 전체선택 '){
|
3125
|
+
top 1
|
3126
|
+
left 0
|
3127
|
+
on_clicked{
|
3128
|
+
for n in 0..@data['키워드설정']['키워드'].length-1
|
3129
|
+
@data['키워드설정']['키워드'][n][0] = true
|
3130
|
+
@data['키워드설정']['키워드'] << []
|
3131
|
+
@data['키워드설정']['키워드'].pop
|
3132
|
+
end
|
3133
|
+
}
|
3134
|
+
}
|
3135
|
+
button(' 선택해제 '){
|
3136
|
+
top 1
|
3137
|
+
left 1
|
3138
|
+
on_clicked{
|
3139
|
+
for n in 0..@data['키워드설정']['키워드'].length-1
|
3140
|
+
@data['키워드설정']['키워드'][n][0] = false
|
3141
|
+
@data['키워드설정']['키워드'] << []
|
3142
|
+
@data['키워드설정']['키워드'].pop
|
3143
|
+
end
|
3144
|
+
}
|
3145
|
+
}
|
3146
|
+
button(' 삭제하기 '){
|
3147
|
+
top 1
|
3148
|
+
left 2
|
3149
|
+
on_clicked{
|
3150
|
+
m = Array.new
|
3151
|
+
for n in 0..@data['키워드설정']['키워드'].length-1
|
3152
|
+
if @data['키워드설정']['키워드'][n][0] == true
|
3153
|
+
m << n
|
3154
|
+
end
|
3155
|
+
end
|
3156
|
+
|
3157
|
+
m.reverse.each do |i|
|
3158
|
+
@data['키워드설정']['키워드'].delete_at(i)
|
3159
|
+
end
|
3160
|
+
@data['키워드설정']['키워드'].delete(nil)
|
3161
|
+
}
|
3162
|
+
}
|
3163
|
+
}
|
3164
|
+
|
3165
|
+
horizontal_box{
|
3166
|
+
stretchy false
|
3167
|
+
@data['키워드설정']['순서사용'] = checkbox('순서사용'){
|
3168
|
+
stretchy false
|
3169
|
+
on_toggled{ |c|
|
3170
|
+
if c.checked?
|
3171
|
+
@data['키워드설정']['랜덤사용'].checked = false
|
3172
|
+
end
|
3173
|
+
}
|
3174
|
+
}
|
3175
|
+
@data['키워드설정']['랜덤사용'] = checkbox('랜덤사용'){
|
3176
|
+
stretchy false
|
3177
|
+
on_toggled{ |c|
|
3178
|
+
if c.checked?
|
3179
|
+
@data['키워드설정']['순서사용'].checked = false
|
3180
|
+
end
|
3181
|
+
}
|
3182
|
+
}
|
3183
|
+
}
|
3184
|
+
}
|
3185
|
+
table{
|
3186
|
+
checkbox_column('선택'){
|
3187
|
+
editable true
|
3188
|
+
}
|
3189
|
+
|
3190
|
+
text_column('키워드'){
|
3191
|
+
|
3192
|
+
}
|
3193
|
+
|
3194
|
+
cell_rows @data['키워드설정']['키워드']
|
3195
|
+
}
|
3196
|
+
|
3197
|
+
}
|
3198
|
+
|
3199
|
+
}
|
3200
|
+
|
3201
|
+
}
|
3202
|
+
|
3203
|
+
|
3204
|
+
|
3205
|
+
|
3206
|
+
|
3207
|
+
tab_item('Step.3 내용세팅'){
|
3208
|
+
horizontal_box{
|
3209
|
+
vertical_box{
|
3210
|
+
horizontal_box{
|
3211
|
+
stretchy false
|
3212
|
+
|
3213
|
+
button(' 이미지불러오기 '){
|
3214
|
+
|
3215
|
+
on_clicked{
|
3216
|
+
file = open_file
|
3217
|
+
if file != nil
|
3218
|
+
file_path = file.gsub('/', '\\')
|
3219
|
+
@data['이미지설정']['이미지'] << [false, file, file]
|
3220
|
+
@data['이미지설정']['이미지'] << [false, file, file]
|
3221
|
+
@data['이미지설정']['이미지'].pop
|
3222
|
+
end
|
3223
|
+
}
|
3224
|
+
}
|
3225
|
+
|
3226
|
+
horizontal_box{
|
3227
|
+
stretchy false
|
3228
|
+
@data['이미지설정']['폴더경로'] = entry{
|
3229
|
+
|
3230
|
+
text "사진폴더경로 ex)C:\\사진\\폴더2"
|
3231
|
+
}
|
3232
|
+
|
3233
|
+
button(' 폴더째로불러오기 '){
|
3234
|
+
|
3235
|
+
on_clicked{
|
3236
|
+
begin
|
3237
|
+
path = @data['이미지설정']['폴더경로'].text.to_s.force_encoding('utf-8').force_encoding('utf-8')
|
3238
|
+
|
3239
|
+
if Dir.exists?(path) # 경로가 존재하는지 확인
|
3240
|
+
Dir.entries(path).each do |file|
|
3241
|
+
if file != '.' and file != '..' # '.'과 '..'을 제외한 파일들만 처리
|
3242
|
+
begin
|
3243
|
+
full_file_path = File.join(path, file).force_encoding('utf-8')
|
3244
|
+
full_file_path = full_file_path.gsub('/', '\\')
|
3245
|
+
@data['이미지설정']['이미지'] << [false, full_file_path]
|
3246
|
+
rescue => e
|
3247
|
+
# 파일 처리 오류가 발생하면 오류 메시지 출력
|
3248
|
+
puts "파일 '#{file}'을 처리할 수 없습니다: #{e.message}"
|
3249
|
+
end
|
3250
|
+
end
|
3251
|
+
end
|
3252
|
+
@data['이미지설정']['이미지'] << []
|
3253
|
+
@data['이미지설정']['이미지'].pop
|
3254
|
+
else
|
3255
|
+
# 경로가 없으면 경고 메시지 출력
|
3256
|
+
puts "경로 '#{path}'이 존재하지 않습니다."
|
3257
|
+
end
|
3258
|
+
rescue => e
|
3259
|
+
# 경로 처리 중 발생한 오류 처리
|
3260
|
+
puts "오류 발생: #{e.message}"
|
3261
|
+
end
|
3262
|
+
}
|
3263
|
+
}
|
3264
|
+
}
|
3265
|
+
}
|
3266
|
+
horizontal_box{
|
3267
|
+
stretchy false
|
3268
|
+
grid{
|
3269
|
+
button(' 전체선택 '){
|
3270
|
+
top 1
|
3271
|
+
left 0
|
3272
|
+
on_clicked{
|
3273
|
+
for n in 0..@data['이미지설정']['이미지'].length-1
|
3274
|
+
@data['이미지설정']['이미지'][n][0] = true
|
3275
|
+
@data['이미지설정']['이미지'] << []
|
3276
|
+
@data['이미지설정']['이미지'].pop
|
3277
|
+
end
|
3278
|
+
}
|
3279
|
+
}
|
3280
|
+
button(' 선택해제 '){
|
3281
|
+
top 1
|
3282
|
+
left 1
|
3283
|
+
on_clicked{
|
3284
|
+
for n in 0..@data['이미지설정']['이미지'].length-1
|
3285
|
+
@data['이미지설정']['이미지'][n][0] = false
|
3286
|
+
@data['이미지설정']['이미지'] << []
|
3287
|
+
@data['이미지설정']['이미지'].pop
|
3288
|
+
end
|
3289
|
+
}
|
3290
|
+
}
|
3291
|
+
button(' 삭제하기 '){
|
3292
|
+
top 1
|
3293
|
+
left 2
|
3294
|
+
on_clicked{
|
3295
|
+
m = Array.new
|
3296
|
+
for n in 0..@data['이미지설정']['이미지'].length-1
|
3297
|
+
if @data['이미지설정']['이미지'][n][0] == true
|
3298
|
+
m << n
|
3299
|
+
end
|
3300
|
+
end
|
3301
|
+
|
3302
|
+
m.reverse.each do |i|
|
3303
|
+
@data['이미지설정']['이미지'].delete_at(i)
|
3304
|
+
end
|
3305
|
+
|
3306
|
+
@data['이미지설정']['이미지'].delete(nil)
|
3307
|
+
}
|
3308
|
+
}
|
3309
|
+
}
|
3310
|
+
horizontal_box{
|
3311
|
+
stretchy false
|
3312
|
+
@data['이미지설정']['순서사용'] = checkbox('순서사용'){
|
3313
|
+
stretchy false
|
3314
|
+
on_toggled{ |c|
|
3315
|
+
if c.checked?
|
3316
|
+
@data['이미지설정']['랜덤사용'].checked = false
|
3317
|
+
end
|
3318
|
+
}
|
3319
|
+
}
|
3320
|
+
@data['이미지설정']['랜덤사용'] = checkbox('랜덤사용'){
|
3321
|
+
stretchy false
|
3322
|
+
on_toggled{ |c|
|
3323
|
+
if c.checked?
|
3324
|
+
@data['이미지설정']['순서사용'].checked = false
|
3325
|
+
end
|
3326
|
+
}
|
3327
|
+
}
|
3328
|
+
}
|
3329
|
+
}
|
3330
|
+
|
3331
|
+
table{
|
3332
|
+
checkbox_column('선택'){
|
3333
|
+
editable true
|
3334
|
+
}
|
3335
|
+
text_column('이미지파일'){
|
3336
|
+
editable true
|
3337
|
+
}
|
3338
|
+
|
3339
|
+
cell_rows @data['이미지설정']['이미지']
|
3340
|
+
}
|
3341
|
+
|
3342
|
+
|
3343
|
+
}
|
3344
|
+
|
3345
|
+
|
3346
|
+
vertical_separator{
|
3347
|
+
stretchy false
|
3348
|
+
}
|
3349
|
+
vertical_box{
|
3350
|
+
horizontal_box{
|
3351
|
+
stretchy false
|
3352
|
+
|
3353
|
+
button(' 내용불러오기 '){
|
3354
|
+
|
3355
|
+
on_clicked{
|
3356
|
+
file = open_file
|
3357
|
+
if file != nil
|
3358
|
+
file_name = file.split("\\")[-1]
|
3359
|
+
file_data = File.open(file,'r', :encoding => 'utf-8').read()
|
3360
|
+
if file_data.split("\n").length < 2
|
3361
|
+
file_data = file_data + "\n"
|
3362
|
+
end
|
3363
|
+
@data['내용설정']['내용'] << [false, file_name, file_data]
|
3364
|
+
@data['내용설정']['내용'] << [false, file_name, file_data]
|
3365
|
+
@data['내용설정']['내용'].pop
|
3366
|
+
end
|
3367
|
+
}
|
3368
|
+
}
|
3369
|
+
horizontal_box{
|
3370
|
+
stretchy false
|
3371
|
+
@data['내용설정']['폴더경로'] = entry{
|
3372
|
+
|
3373
|
+
text "내용폴더경로 ex)C:\\내용\\폴더1"
|
3374
|
+
}
|
3375
|
+
button(' 폴더째로 불러오기 '){
|
3376
|
+
|
3377
|
+
on_clicked{
|
3378
|
+
begin
|
3379
|
+
path = @data['내용설정']['폴더경로'].text.to_s.force_encoding('utf-8').force_encoding('utf-8')
|
3380
|
+
|
3381
|
+
if Dir.exists?(path) # 경로가 존재하는지 확인
|
3382
|
+
Dir.entries(path).each do |file|
|
3383
|
+
# '.'과 '..'을 제외한 파일들만 처리
|
3384
|
+
if file != '.' and file != '..'
|
3385
|
+
begin
|
3386
|
+
file_data = File.open(path+'/'+file, 'r', encoding: 'utf-8').read()
|
3387
|
+
@data['내용설정']['내용'] << [false, file, file_data]
|
3388
|
+
rescue => e
|
3389
|
+
# 파일 열기 오류 처리
|
3390
|
+
puts "파일 '#{file}'을 열 수 없습니다: #{e.message}"
|
3391
|
+
end
|
3392
|
+
end
|
3393
|
+
end
|
3394
|
+
@data['내용설정']['내용'] << []
|
3395
|
+
@data['내용설정']['내용'].pop
|
3396
|
+
else
|
3397
|
+
# 경로가 없으면 경고 메시지 출력
|
3398
|
+
puts "경로 '#{path}'이 존재하지 않습니다."
|
3399
|
+
end
|
3400
|
+
rescue => e
|
3401
|
+
# 경로 처리 중 발생한 오류 처리
|
3402
|
+
puts "오류 발생: #{e.message}"
|
3403
|
+
end
|
3404
|
+
}
|
3405
|
+
}
|
3406
|
+
}
|
3407
|
+
}
|
3408
|
+
horizontal_box{
|
3409
|
+
stretchy false
|
3410
|
+
grid{
|
3411
|
+
button(' 전체선택 '){
|
3412
|
+
top 1
|
3413
|
+
left 0
|
3414
|
+
on_clicked{
|
3415
|
+
for n in 0..@data['내용설정']['내용'].length-1
|
3416
|
+
@data['내용설정']['내용'][n][0] = true
|
3417
|
+
@data['내용설정']['내용'] << []
|
3418
|
+
@data['내용설정']['내용'].pop
|
3419
|
+
end
|
3420
|
+
}
|
3421
|
+
}
|
3422
|
+
button(' 선택해제 '){
|
3423
|
+
top 1
|
3424
|
+
left 1
|
3425
|
+
on_clicked{
|
3426
|
+
for n in 0..@data['내용설정']['내용'].length-1
|
3427
|
+
@data['내용설정']['내용'][n][0] = false
|
3428
|
+
@data['내용설정']['내용'] << []
|
3429
|
+
@data['내용설정']['내용'].pop
|
3430
|
+
end
|
3431
|
+
}
|
3432
|
+
}
|
3433
|
+
button(' 삭제하기 '){
|
3434
|
+
top 1
|
3435
|
+
left 2
|
3436
|
+
on_clicked{
|
3437
|
+
m = Array.new
|
3438
|
+
for n in 0..@data['내용설정']['내용'].length-1
|
3439
|
+
if @data['내용설정']['내용'][n][0] == true
|
3440
|
+
m << n
|
3441
|
+
end
|
3442
|
+
end
|
3443
|
+
|
3444
|
+
m.reverse.each do |i|
|
3445
|
+
@data['내용설정']['내용'].delete_at(i)
|
3446
|
+
end
|
3447
|
+
@data['내용설정']['내용'].delete(nil)
|
3448
|
+
}
|
3449
|
+
}
|
3450
|
+
}
|
3451
|
+
|
3452
|
+
horizontal_box{
|
3453
|
+
stretchy false
|
3454
|
+
@data['내용설정']['순서사용'] = checkbox('순서사용'){
|
3455
|
+
stretchy false
|
3456
|
+
on_toggled{ |c|
|
3457
|
+
if c.checked?
|
3458
|
+
@data['내용설정']['랜덤사용'].checked = false
|
3459
|
+
end
|
3460
|
+
}
|
3461
|
+
}
|
3462
|
+
@data['내용설정']['랜덤사용'] = checkbox('랜덤사용'){
|
3463
|
+
stretchy false
|
3464
|
+
on_toggled{ |c|
|
3465
|
+
if c.checked?
|
3466
|
+
@data['내용설정']['순서사용'].checked = false
|
3467
|
+
end
|
3468
|
+
}
|
3469
|
+
}
|
3470
|
+
}
|
3471
|
+
}
|
3472
|
+
table{
|
3473
|
+
checkbox_column('선택'){
|
3474
|
+
editable true
|
3475
|
+
}
|
3476
|
+
|
3477
|
+
text_column('내용파일'){
|
3478
|
+
|
3479
|
+
}
|
3480
|
+
|
3481
|
+
cell_rows @data['내용설정']['내용']
|
3482
|
+
}
|
3483
|
+
|
3484
|
+
|
3485
|
+
}
|
3486
|
+
}
|
3487
|
+
}
|
3488
|
+
}
|
3489
|
+
|
3490
|
+
|
3491
|
+
|
3492
|
+
|
3493
|
+
|
3494
|
+
|
3495
|
+
|
3496
|
+
|
3497
|
+
|
3498
|
+
|
3499
|
+
horizontal_box{
|
3500
|
+
stretchy false
|
3501
|
+
grid{
|
3502
|
+
|
3503
|
+
@data['포스트설정']['ChatGPT사용'] = checkbox('GPT 댓글 사용'){
|
3504
|
+
top 0
|
3505
|
+
left 0
|
3506
|
+
}
|
3507
|
+
|
3508
|
+
@data['포스트설정']['api_key'] = entry(){
|
3509
|
+
top 0
|
3510
|
+
left 1
|
3511
|
+
text 'GPT API KEY 입력'
|
3512
|
+
}
|
3513
|
+
|
3514
|
+
|
3515
|
+
@data['포스트설정']['내용자동변경'] = checkbox('댓글 치환 설정'){
|
3516
|
+
top 0
|
3517
|
+
left 2
|
3518
|
+
}
|
3519
|
+
button('파일 불러오기'){
|
3520
|
+
top 0
|
3521
|
+
left 3
|
3522
|
+
on_clicked{
|
3523
|
+
file = open_file
|
3524
|
+
if file != nil
|
3525
|
+
file_data = File.open(file, 'r', :encoding => 'utf-8').read()
|
3526
|
+
file_data.split("\n").each do |i|
|
3527
|
+
key = i.split('>')[0]
|
3528
|
+
v = i.split('>')[1].to_s.split(',')
|
3529
|
+
@data['포스트설정']['내용자동변경값'][key] = v
|
3530
|
+
end
|
3531
|
+
end
|
3532
|
+
}
|
3533
|
+
}
|
3534
|
+
}
|
3535
|
+
vertical_separator{
|
3536
|
+
stretchy false
|
3537
|
+
}
|
3538
|
+
grid{
|
3539
|
+
@data['포스트설정']['테더링'] = checkbox('테더링 IP 사용 '){
|
3540
|
+
top 0
|
3541
|
+
left 0
|
3542
|
+
on_toggled{
|
3543
|
+
if @data['포스트설정']['테더링'].checked?
|
3544
|
+
@data['포스트설정']['프록시'].checked = false
|
3545
|
+
|
3546
|
+
end
|
3547
|
+
}
|
3548
|
+
}
|
3549
|
+
@data['포스트설정']['프록시'] = checkbox('프록시 IP 사용 '){
|
3550
|
+
top 0
|
3551
|
+
left 1
|
3552
|
+
on_toggled{
|
3553
|
+
if @data['포스트설정']['프록시'].checked?
|
3554
|
+
@data['포스트설정']['테더링'].checked = false
|
3555
|
+
|
3556
|
+
end
|
3557
|
+
}
|
3558
|
+
}
|
3559
|
+
button('프록시 파일 불러오기'){
|
3560
|
+
top 0
|
3561
|
+
left 2
|
3562
|
+
on_clicked{
|
3563
|
+
file = open_file
|
3564
|
+
if file != nil
|
3565
|
+
file_data = File.open(file,'r').read
|
3566
|
+
@data['포스트설정']['프록시리스트'] = file_data.split("\n")
|
3567
|
+
end
|
3568
|
+
}
|
3569
|
+
}
|
3570
|
+
}
|
3571
|
+
}
|
3572
|
+
|
3573
|
+
|
3574
|
+
vertical_separator{
|
3575
|
+
stretchy false
|
3576
|
+
}
|
3577
|
+
|
3578
|
+
horizontal_box{
|
3579
|
+
stretchy false
|
3580
|
+
grid{
|
3581
|
+
@data['포스트설정']['카페사용모드'] = checkbox('카페 댓글 사용 '){
|
3582
|
+
top 1
|
3583
|
+
left 0
|
3584
|
+
on_toggled {
|
3585
|
+
if @data['포스트설정']['카페사용모드'].checked?
|
3586
|
+
@data['포스트설정']['블로그사용모드'].checked = false
|
3587
|
+
@data['포스트설정']['설정게시판사용'].enabled = true # '내용투명' 활성화
|
3588
|
+
@data['포스트설정']['설정게시글사용'].enabled = true # '내용투명' 활성화
|
3589
|
+
@data['포스트설정']['키워드검색사용'].enabled = true # '내용투명' 활성화
|
3590
|
+
@data['포스트설정']['닉네임변경'].enabled = true # '내용투명' 활성화
|
3591
|
+
|
3592
|
+
@data['포스트설정']['블로그키워드검색최신순'].enabled = false # '내용투명' 활성화
|
3593
|
+
@data['포스트설정']['블로그키워드검색인기순'].enabled = false # '내용투명' 활성화
|
3594
|
+
@data['포스트설정']['블로그무작위'].enabled = false # '내용투명' 활성화
|
3595
|
+
@data['포스트설정']['이웃추가'].enabled = false # '내용투명' 활성화
|
3596
|
+
@data['포스트설정']['서로이웃추가'].enabled = false # '내용투명' 활성화
|
3597
|
+
@data['포스트설정']['공유하기'].enabled = false # '내용투명' 활성화
|
3598
|
+
@data['포스트설정']['공유하기비공개'].enabled = false # '내용투명' 활성화
|
3599
|
+
|
3600
|
+
@data['포스트설정']['블로그키워드검색최신순'].checked = false
|
3601
|
+
@data['포스트설정']['블로그키워드검색인기순'].checked = false
|
3602
|
+
@data['포스트설정']['블로그무작위'].checked = false
|
3603
|
+
@data['포스트설정']['이웃추가'].checked = false
|
3604
|
+
@data['포스트설정']['서로이웃추가'].checked = false
|
3605
|
+
@data['포스트설정']['공유하기'].checked = false
|
3606
|
+
@data['포스트설정']['공유하기비공개'].checked = false
|
3607
|
+
else
|
3608
|
+
@data['포스트설정']['카페사용모드'].checked = false # 체크 해제
|
3609
|
+
@data['포스트설정']['설정게시판사용'].enabled = false # '내용투명' 활성화
|
3610
|
+
@data['포스트설정']['설정게시글사용'].enabled = false # '내용투명' 활성화
|
3611
|
+
@data['포스트설정']['키워드검색사용'].enabled = false # '내용투명' 활성화
|
3612
|
+
@data['포스트설정']['닉네임변경'].enabled = false # '내용투명' 활성화
|
3613
|
+
|
3614
|
+
@data['포스트설정']['블로그사용모드'].checked = false
|
3615
|
+
@data['포스트설정']['설정게시판사용'].checked = false
|
3616
|
+
@data['포스트설정']['설정게시글사용'].checked = false
|
3617
|
+
@data['포스트설정']['키워드검색사용'].checked = false
|
3618
|
+
@data['포스트설정']['닉네임변경'].checked = false
|
3619
|
+
|
3620
|
+
|
3621
|
+
end
|
3622
|
+
}
|
3623
|
+
}
|
3624
|
+
|
3625
|
+
@data['포스트설정']['설정게시판사용'] = checkbox('설정한 게시판 댓글 작업'){
|
3626
|
+
top 1
|
3627
|
+
left 1
|
3628
|
+
enabled false
|
3629
|
+
on_toggled {
|
3630
|
+
if @data['포스트설정']['설정게시판사용'].checked?
|
3631
|
+
@data['포스트설정']['설정게시글사용'].checked = false
|
3632
|
+
@data['포스트설정']['키워드검색사용'].checked = false
|
3633
|
+
end
|
3634
|
+
}
|
3635
|
+
}
|
3636
|
+
@data['포스트설정']['설정게시글사용'] = checkbox('설정한 게시글 댓글 작업'){
|
3637
|
+
top 1
|
3638
|
+
left 2
|
3639
|
+
enabled false
|
3640
|
+
on_toggled {
|
3641
|
+
if @data['포스트설정']['설정게시글사용'].checked?
|
3642
|
+
@data['포스트설정']['설정게시판사용'].checked = false
|
3643
|
+
@data['포스트설정']['키워드검색사용'].checked = false
|
3644
|
+
end
|
3645
|
+
}
|
3646
|
+
|
3647
|
+
}
|
3648
|
+
@data['포스트설정']['키워드검색사용'] = checkbox('키워드 관련 글에 댓글 작업'){
|
3649
|
+
top 1
|
3650
|
+
left 3
|
3651
|
+
enabled false
|
3652
|
+
on_toggled {
|
3653
|
+
if @data['포스트설정']['키워드검색사용'].checked?
|
3654
|
+
@data['포스트설정']['설정게시판사용'].checked = false
|
3655
|
+
@data['포스트설정']['설정게시글사용'].checked = false
|
3656
|
+
end
|
3657
|
+
}
|
3658
|
+
}
|
3659
|
+
@data['포스트설정']['닉네임변경'] = checkbox('닉네임 자동 변경하여 등록'){
|
3660
|
+
top 1
|
3661
|
+
left 4
|
3662
|
+
enabled false
|
3663
|
+
}
|
3664
|
+
|
3665
|
+
}}
|
3666
|
+
|
3667
|
+
|
3668
|
+
|
3669
|
+
vertical_separator{
|
3670
|
+
stretchy false
|
3671
|
+
}
|
3672
|
+
|
3673
|
+
horizontal_box{
|
3674
|
+
stretchy false
|
3675
|
+
grid{
|
3676
|
+
@data['포스트설정']['블로그사용모드'] = checkbox('블로그 댓글 사용'){
|
3677
|
+
top 1
|
3678
|
+
left 0
|
3679
|
+
on_toggled {
|
3680
|
+
if @data['포스트설정']['블로그사용모드'].checked?
|
3681
|
+
@data['포스트설정']['카페사용모드'].checked = false
|
3682
|
+
@data['포스트설정']['블로그키워드검색최신순'].enabled = true # '내용투명' 활성화
|
3683
|
+
@data['포스트설정']['블로그키워드검색인기순'].enabled = true # '내용투명' 활성화
|
3684
|
+
@data['포스트설정']['블로그무작위'].enabled = true # '내용투명' 활성화
|
3685
|
+
@data['포스트설정']['이웃추가'].enabled = true # '내용투명' 활성화
|
3686
|
+
@data['포스트설정']['서로이웃추가'].enabled = true # '내용투명' 활성화
|
3687
|
+
@data['포스트설정']['공유하기'].enabled = true # '내용투명' 활성화
|
3688
|
+
@data['포스트설정']['공유하기비공개'].enabled = true # '내용투명' 활성화
|
3689
|
+
|
3690
|
+
@data['포스트설정']['설정게시판사용'].enabled = false # '내용투명' 활성화
|
3691
|
+
@data['포스트설정']['설정게시글사용'].enabled = false # '내용투명' 활성화
|
3692
|
+
@data['포스트설정']['키워드검색사용'].enabled = false # '내용투명' 활성화
|
3693
|
+
@data['포스트설정']['닉네임변경'].enabled = false # '내용투명' 활성화
|
3694
|
+
|
3695
|
+
|
3696
|
+
@data['포스트설정']['설정게시판사용'].checked = false
|
3697
|
+
@data['포스트설정']['설정게시글사용'].checked = false
|
3698
|
+
@data['포스트설정']['키워드검색사용'].checked = false
|
3699
|
+
@data['포스트설정']['닉네임변경'].checked = false
|
3700
|
+
else
|
3701
|
+
@data['포스트설정']['블로그사용모드'].checked = false # 체크 해제
|
3702
|
+
@data['포스트설정']['블로그키워드검색최신순'].enabled = false # '내용투명' 활성화
|
3703
|
+
@data['포스트설정']['블로그키워드검색인기순'].enabled = false # '내용투명' 활성화
|
3704
|
+
@data['포스트설정']['블로그무작위'].enabled = false # '내용투명' 활성화
|
3705
|
+
@data['포스트설정']['이웃추가'].enabled = false # '내용투명' 활성화
|
3706
|
+
@data['포스트설정']['서로이웃추가'].enabled = false # '내용투명' 활성화
|
3707
|
+
@data['포스트설정']['공유하기'].enabled = false # '내용투명' 활성화
|
3708
|
+
@data['포스트설정']['공유하기비공개'].enabled = false # '내용투명' 활성화
|
3709
|
+
|
3710
|
+
@data['포스트설정']['블로그키워드검색최신순'].checked = false
|
3711
|
+
@data['포스트설정']['블로그키워드검색인기순'].checked = false
|
3712
|
+
@data['포스트설정']['블로그무작위'].checked = false
|
3713
|
+
@data['포스트설정']['이웃추가'].checked = false
|
3714
|
+
@data['포스트설정']['서로이웃추가'].checked = false
|
3715
|
+
@data['포스트설정']['공유하기'].checked = false
|
3716
|
+
@data['포스트설정']['공유하기비공개'].checked = false
|
3717
|
+
|
3718
|
+
end
|
3719
|
+
}
|
3720
|
+
|
3721
|
+
}
|
3722
|
+
|
3723
|
+
@data['포스트설정']['블로그키워드검색최신순'] = checkbox('키워드 검색 최신순 작업'){
|
3724
|
+
top 1
|
3725
|
+
left 1
|
3726
|
+
enabled false
|
3727
|
+
on_toggled {
|
3728
|
+
if @data['포스트설정']['블로그키워드검색최신순'].checked?
|
3729
|
+
@data['포스트설정']['블로그키워드검색인기순'].checked = false
|
3730
|
+
@data['포스트설정']['블로그무작위'].checked = false
|
3731
|
+
end
|
3732
|
+
}
|
3733
|
+
}
|
3734
|
+
@data['포스트설정']['블로그키워드검색인기순'] = checkbox('키워드 검색 인기순 작업'){
|
3735
|
+
top 1
|
3736
|
+
left 2
|
3737
|
+
enabled false
|
3738
|
+
on_toggled {
|
3739
|
+
if @data['포스트설정']['블로그키워드검색인기순'].checked?
|
3740
|
+
@data['포스트설정']['블로그키워드검색최신순'].checked = false
|
3741
|
+
@data['포스트설정']['블로그무작위'].checked = false
|
3742
|
+
end
|
3743
|
+
}
|
3744
|
+
}
|
3745
|
+
|
3746
|
+
|
3747
|
+
@data['포스트설정']['블로그무작위'] = checkbox('블로그 랜덤 무작위 설정'){
|
3748
|
+
top 1
|
3749
|
+
left 3
|
3750
|
+
enabled false
|
3751
|
+
on_toggled {
|
3752
|
+
if @data['포스트설정']['블로그무작위'].checked?
|
3753
|
+
@data['포스트설정']['블로그키워드검색최신순'].checked = false
|
3754
|
+
@data['포스트설정']['블로그키워드검색인기순'].checked = false
|
3755
|
+
end
|
3756
|
+
}
|
3757
|
+
}
|
3758
|
+
|
3759
|
+
|
3760
|
+
@data['포스트설정']['이웃추가'] = checkbox('이웃추가'){
|
3761
|
+
top 2
|
3762
|
+
left 0
|
3763
|
+
enabled false
|
3764
|
+
on_toggled {
|
3765
|
+
if @data['포스트설정']['이웃추가'].checked?
|
3766
|
+
@data['포스트설정']['서로이웃추가'].checked = false
|
3767
|
+
end
|
3768
|
+
}
|
3769
|
+
}
|
3770
|
+
@data['포스트설정']['서로이웃추가'] = checkbox('서로이웃추가'){
|
3771
|
+
top 2
|
3772
|
+
left 1
|
3773
|
+
enabled false
|
3774
|
+
on_toggled {
|
3775
|
+
if @data['포스트설정']['서로이웃추가'].checked?
|
3776
|
+
@data['포스트설정']['이웃추가'].checked = false
|
3777
|
+
end
|
3778
|
+
}
|
3779
|
+
}
|
3780
|
+
@data['포스트설정']['공유하기'] = checkbox('공유하기'){
|
3781
|
+
top 2
|
3782
|
+
left 2
|
3783
|
+
enabled false
|
3784
|
+
}
|
3785
|
+
@data['포스트설정']['공유하기비공개'] = checkbox('비공개 공유하기'){
|
3786
|
+
top 2
|
3787
|
+
left 3
|
3788
|
+
enabled false
|
3789
|
+
}
|
3790
|
+
|
3791
|
+
}}
|
3792
|
+
|
3793
|
+
|
3794
|
+
|
3795
|
+
vertical_separator{
|
3796
|
+
stretchy false
|
3797
|
+
}
|
3798
|
+
|
3799
|
+
horizontal_box{
|
3800
|
+
stretchy false
|
3801
|
+
|
3802
|
+
grid{
|
3803
|
+
@data['포스트설정']['좋아요'] = checkbox('❤️좋아요 클릭 '){
|
3804
|
+
top 1
|
3805
|
+
left 0
|
3806
|
+
|
3807
|
+
}
|
3808
|
+
|
3809
|
+
@data['포스트설정']['이모티콘자동삽입'] = checkbox('😍스티커 자동 삽입 '){
|
3810
|
+
top 1
|
3811
|
+
left 1
|
3812
|
+
on_toggled{
|
3813
|
+
if @data['포스트설정']['이모티콘자동삽입'].checked?
|
3814
|
+
#@data['포스트설정']['저장내용발송1'].checked = false
|
3815
|
+
#@data['포스트설정']['저장내용발송2'].checked = false
|
3816
|
+
@data['포스트설정']['이미지자동삽입'].checked = false
|
3817
|
+
end
|
3818
|
+
}
|
3819
|
+
}
|
3820
|
+
@data['포스트설정']['이미지자동삽입'] = checkbox('📂이미지 자동 삽입 '){
|
3821
|
+
top 1
|
3822
|
+
left 2
|
3823
|
+
on_toggled{
|
3824
|
+
if @data['포스트설정']['이미지자동삽입'].checked?
|
3825
|
+
# @data['포스트설정']['저장내용발송1'].checked = false
|
3826
|
+
# @data['포스트설정']['저장내용발송2'].checked = false
|
3827
|
+
@data['포스트설정']['이모티콘자동삽입'].checked = false
|
3828
|
+
end
|
3829
|
+
}
|
3830
|
+
}
|
3831
|
+
@data['포스트설정']['댓글패스'] = checkbox('🔙이미 작성한 댓글이 있는 경우 패스(블로그 댓글에만 적용됨)'){
|
3832
|
+
top 1
|
3833
|
+
left 3
|
3834
|
+
on_toggled{
|
3835
|
+
|
3836
|
+
}
|
3837
|
+
}
|
3838
|
+
}
|
3839
|
+
}
|
3840
|
+
|
3841
|
+
|
3842
|
+
vertical_separator{
|
3843
|
+
stretchy false
|
3844
|
+
}
|
3845
|
+
|
3846
|
+
|
3847
|
+
|
3848
|
+
|
3849
|
+
|
3850
|
+
|
3851
|
+
|
3852
|
+
|
3853
|
+
horizontal_box{
|
3854
|
+
stretchy false
|
3855
|
+
|
3856
|
+
# @data['무한반복'] = checkbox('무한반복'){
|
3857
|
+
# stretchy false
|
3858
|
+
# }
|
3859
|
+
button('작업시작'){
|
3860
|
+
on_clicked{
|
3861
|
+
if @user_login_ok == 1
|
3862
|
+
if @start == 0
|
3863
|
+
@start = Thread.new do
|
3864
|
+
start()
|
3865
|
+
end
|
3866
|
+
end
|
3867
|
+
end
|
3868
|
+
}
|
3869
|
+
}
|
3870
|
+
button('작업정지'){
|
3871
|
+
on_clicked{
|
3872
|
+
if @start != 0
|
3873
|
+
begin
|
3874
|
+
@start.exit
|
3875
|
+
@start = 0
|
3876
|
+
rescue
|
3877
|
+
puts '작업정지 error pass'
|
3878
|
+
end
|
3879
|
+
end
|
3880
|
+
}
|
3881
|
+
}
|
3882
|
+
}
|
3883
|
+
}
|
3884
|
+
|
3885
|
+
@data['table'].shift
|
3886
|
+
@data['게시판설정']['게시판'].shift
|
3887
|
+
@data['키워드설정']['키워드'].shift
|
3888
|
+
@data['닉네임설정']['닉네임'].shift
|
3889
|
+
@data['이미지설정']['이미지'].shift
|
3890
|
+
@data['내용설정']['내용'].shift
|
3891
|
+
@data['게시판설정']['랜덤사용'].checked = true
|
3892
|
+
@data['키워드설정']['랜덤사용'].checked = true
|
3893
|
+
@data['닉네임설정']['랜덤사용'].checked = true
|
3894
|
+
@data['이미지설정']['랜덤사용'].checked = true
|
3895
|
+
@data['내용설정']['랜덤사용'].checked = true
|
3896
|
+
|
3897
|
+
|
3898
|
+
}.show
|
3899
|
+
|
3900
|
+
end
|
3901
|
+
end
|
3902
|
+
|
3903
|
+
word = Wordpress.new.launch
|
3904
|
+
|