Class: KayaBot

Inherits:
Object
  • Object
show all
Defined in:
lib/kayabot.rb

Constant Summary collapse

PLAY_URL =
"/bot/play"
OPEN_GAME_URL =
"/bot/open_game"
RESIGN_URL =
"/bot/resign"
SCORE_URL =
"/bot/score"
CLOSE_GAME_URL =
"/bot/close_game"
ERROR_REPORT_URL =
"/bot/error"
VERSION =
Gem::Specification.find_by_name("kayabot").version.to_s
TIME_LAPSE =
4

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(config) ⇒ KayaBot

Returns a new instance of KayaBot.



22
23
24
25
26
27
28
29
30
31
32
33
34
# File 'lib/kayabot.rb', line 22

def initialize(config)
  p config
  @server_url = config["url"]
  @user = config["user"]
  @pass = config["pass"]
  @size = config["size"]
  @title = config["title"]
  @bot = config["bot"]
  @agent = Mechanize.new
  @agent.max_history = 2
  @error_limit = 3
  @loop_reading = 50
end

Instance Attribute Details

#challengerObject

Returns the value of attribute challenger.



20
21
22
# File 'lib/kayabot.rb', line 20

def challenger
  @challenger
end

#moveObject

Returns the value of attribute move.



20
21
22
# File 'lib/kayabot.rb', line 20

def move
  @move
end

#statusObject

Returns the value of attribute status.



20
21
22
# File 'lib/kayabot.rb', line 20

def status
  @status
end

Instance Method Details

#close_gameObject



107
108
109
110
# File 'lib/kayabot.rb', line 107

def close_game
  res = @agent.post(@server_url + CLOSE_GAME_URL)
  $stdout.puts res.body
end

#connectObject



40
41
42
43
44
# File 'lib/kayabot.rb', line 40

def connect
  return if @agent.cookies.last && @agent.cookies.last.name == "rack.session"
  page = @agent.post(@server_url+ "/session/create", {:id => @user, :password => @pass})
  page.body
end

#fetch_and_parse_dataObject



74
75
76
77
78
79
80
81
82
83
84
# File 'lib/kayabot.rb', line 74

def fetch_and_parse_data
   page = @agent.get(@server_url + "/bot/status", {:version => VERSION })
   json = JSON.parse(page.body)
   $stdout.puts json
   @status = json["status"]
   @move = json["moves"]
   @bots_turn = json["bot_play?"]
   @color = json["next"]
   @master_node = json["sgf_master_node"]
   page.body
end

#game_configurationObject



36
37
38
# File 'lib/kayabot.rb', line 36

def game_configuration
   {:title => @title || "Come at me bro", :size => @size || 19}
end

#listener_loopObject



48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
# File 'lib/kayabot.rb', line 48

def listener_loop
  begin
    while (true) do
      $stdout.puts GC::Profiler.report
      connect
      fetch_and_parse_data
      open_game if @status=="connected" || @status=="finished"
      post_score if @status=="scoring"
      post_move if @bots_turn && @status=="playing"
      sleep TIME_LAPSE #lets not explode in requests
    end
  rescue SystemExit, Interrupt
    close_game
    raise
  rescue Exception => e
    $stderr.puts "There was an error. Will try to run again. If problems persist, contact Kaya at [email protected]"
    $stderr.puts e
    $stderr.puts e.backtrace[0]
    btrace = "" 
    e.backtrace.each {|line| btrace < "\n#{line}"}
    post_error(e.to_s,btrace)
    sleep 5
    listener_loop
  end
end

#open_gameObject



86
87
88
89
# File 'lib/kayabot.rb', line 86

def open_game
  res = @agent.post(@server_url+ OPEN_GAME_URL, game_configuration)
  p res.body
end

#parse_result_from_bot(result) ⇒ Object

Black wins by 61.5 points



131
132
133
134
135
# File 'lib/kayabot.rb', line 131

def parse_result_from_bot(result)
  color = result[0].chr
  points = result.match(/\d{0,3}\.\d/)[0]
  return "#{color}+#{points}"
end

#post_error(title, exception_message = "Unavailable") ⇒ Object



119
120
121
122
123
124
125
126
127
128
# File 'lib/kayabot.rb', line 119

def post_error(title,exception_message="Unavailable")
  if @error_limit > 0
    exception_message = "Unavailable" if exception_message.empty?
    res = @agent.post(@server_url + ERROR_REPORT_URL, {:title=> title, :content => exception_message})
    $stdout.puts res.body
    @error_limit -= 1
  else
    $stdout.puts "Error report limit passed."
  end
end

#post_moveObject



90
91
92
93
94
95
96
97
98
99
100
101
102
103
# File 'lib/kayabot.rb', line 90

def post_move
  #TODO should insert master node . Need handi/komi
  bot_move = ai_move("temp",sgf_content, @color)
  if (bot_move == "resign")
    resign
  else
    color_short = (@color=="black" ? "B" : "W")
    bot_move = "" if bot_move == "pass"
    bot_move = ";#{color_short}[#{bot_move}]#{color_short}L[#{(25*60) - ((@move && !@move.empty?) ? @move.count(";") : 1)}.000]"
    @agent.post(@server_url+ PLAY_URL,
                :move => bot_move)
    @move = nil
  end
end

#post_scoreObject



112
113
114
115
116
117
# File 'lib/kayabot.rb', line 112

def post_score
  result = score_game("temp", sgf_content)
  $stdout.puts result
  res = @agent.post(@server_url+ SCORE_URL, {:score => parse_result_from_bot(result[:score]), :dead_stones => result[:dead_stones]})
  res.body
end

#resignObject



104
105
106
# File 'lib/kayabot.rb', line 104

def resign
  $stdout.puts (@agent.post(@server_url+ RESIGN_URL, {:result => "resign"}).body)
end

#sgf_contentObject



137
138
139
140
141
# File 'lib/kayabot.rb', line 137

def sgf_content
  sgf = SGF.new
  sgf.add_move(@move) if @move && !@move.empty? 
  return "(#{@master_node}#{sgf.move_list})"
end