Hi there, I’m Alex, and as I was finishing Ryan’s scraping course, I saw that a friend had a hard time getting an appointment on a specific date range on a South Korean government website.
I had just learned about Watir Special Keys, and thought it was the perfect opportunity to practice what I had learned in the course!
My goal was to build a small bot that would:
So I built a bot that does all of this!
You can see it in action here:
[Sadly here, only dates in September were available so it just refreshed again and again, but it ended up working for my friend, and he was alerted by this sound!](https://s3-us-west-2.amazonaws.com/secure.notion-static.com/d885c576-bdb9-4ac6-8bb9-795a8551b1bf/CleanShot_2022-07-11_at_23.17.25.mp4)
Sadly here, only dates in September were available so it just refreshed again and again, but it ended up working for my friend, and he was alerted by this sound!
I was super happy that I could build something useful in a few hours, and I also hope it maybe gave you some ideas of stuff to build!
Here are the contents of the bot for those who are curious and/or want to try it for themselves:
require "watir"
require "nokogiri"
require "open-uri"
class Scraper
attr_accessor :browser
def initialize
Watir.default_timeout = 5 # => gem default is 30
@browser = Watir::Browser.new(:chrome) # => Open Browser
end
def call # => Do the initial process one time, which is a bit longer
browser.goto("<https://consulat.gouv.fr/ambassade-de-france-a-seoul/rendez-vous?name=Visa%20Long%20s%C3%A9jour%20%C3%A9tudiant%20%2F%20Long%20stay%20student%20visa>")
sleep(2.5)
browser.button(class: "fr-btn--primary").click
sleep(1)
browser.button(class: "fr-btn--primary").click
sleep(1)
browser.label(class: "custom-control-label").click
browser.button(class: "fr-btn--primary").click
sleep(1)
start_robot
end
def start_robot # => Starts the program, and lets me read errors while programming the bot
begin
is_date_good
rescue => e
puts "Error: #{e.message}"
end
end
def is_date_good # => When on the selection page, only chooses dates that are in
sleep(1.5)
is_a_date_available
first_date = browser.div(class: "date-active").text
if first_date.include?("Juillet")
puts "Appointment available in July!!"
choose_time
notify_me
complete_info
elsif first_date.include?("Août") and (first_date.match(/\\d/).to_s.to_i < 23) # => Here I used
choose_time
notify_me
complete_info
puts "Appointment available in August before the 23rd!"
else
restart_process
end
end
def is_a_date_available # => Checks if any time slot is available, if yes, continue script, if no, refresh page
if browser.divs(class: "schedule-time-text-container").first.exists?
puts "a date is available"
else
restart_process
end
end
def choose_time # => Select the first time slot available and validate it
browser.divs(class: "schedule-time-text-container").first.click
browser.button(class: "fr-btn--primary").click
end
def complete_info # => Completes the personal information form with Watir
browser.input(id: "lastname").send_keys ["First_Name"]
sleep(0.5)
browser.input(id: "firstname").send_keys ["Last_Name"]
sleep(0.5)
browser.input(id: "email").send_keys ["[email protected]"]
sleep(0.5)
browser.input(id: "phone").send_keys ["00000"]
sleep(0.5)
browser.input(id: "birthdate").send_keys ["01012000"]
sleep(0.5)
browser.inputs(class: "form-control")[5].send_keys ["01012000"]
sleep(0.5)
browser.inputs(class: "form-control")[6].send_keys ["Nationality"]
sleep(0.5)
browser.inputs(class: "form-control")[7].send_keys ["PasseportNB"]
sleep(600) # Wait 10 Min
end
def notify_me # => Notify with a sound, and goes back to the page with all the information completed
sleep(2)
puts "You got an appointment 🎉"
browser.execute_script('window.open("<https://assets.mixkit.co/sfx/preview/mixkit-video-game-win-2016.mp3>")')
browser.switch_window
sleep(2)
browser.switch_window
end
def restart_process # => Refreshes the page and starts the bot again
browser.goto("<https://consulat.gouv.fr/ambassade-de-france-a-seoul/rendez-vous?name=Visa%20Long%20s%C3%A9jour%20%C3%A9tudiant%20%2F%20Long%20stay%20student%20visa>")
sleep(0.5)
browser.button(class: "fr-btn--primary").click
sleep(0.5)
browser.buttons(class: "btn-md")[1].click
sleep(0.5)
browser.button(class: "fr-btn--primary").click
sleep(0.5)
start_robot
end
end
scraper = Scraper.new
scraper.call