Class: NServer::Server

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

Instance Method Summary collapse

Constructor Details

#initialize(opts = {}) ⇒ Server

Create a NServer::Server instance

Options:

port

Port for the server to listen on. Default is 10001

host

Host (IP) for the server to listen on. Default is 127.0.0.1 Note that if you specify a non-localhost IP here you must specifiy an allow list. Also accepts 0.0.0.0 to listen on all available interfaces.

allow

Comma seperated list of IPs to accept connections from. Default is only 127.0.0.1 IP ranges are allowed, in a x.x.x.x/y format.

check_interval

Interval to check for messages. Default is 10s.

tray_icon

GTK Icon name to use for the systray icon. Default is ‘gnome-gmush’.

msg_timeout

Message display timeout. Default is 5000ms (5s).



36
37
38
39
40
41
42
43
44
45
46
47
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
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
# File 'lib/nserver.rb', line 36

def initialize( opts = {} )
  unless RNOTIFY_FOUND
    raise StandardError.new("RNotify library not found.")
  end
  opts[:port] ||= 10001
  opts[:host] ||= "127.0.0.1"
  
  super(opts[:port], opts[:host])

  opts[:check_interval] ||= 10
  opts[:tray_icon] ||= "gnome-gmush"
  opts[:msg_timeout] ||= 5000
  opts[:allow] = ( opts[:allow] or "127.0.0.1" ).split(',').collect {|i| IPAddr.new( i ) }

  @check_interval = opts[:check_interval]

  @msg_list = [ Message.new("NServer Ready.") ]
  @msg_history = []
  @allowed_clients = opts[:allow]

  Notify.init("Notification Server")
  @tray_icon = Gtk::StatusIcon.new
  @tray_icon.icon_name = opts[:tray_icon]
  #tray_icon.file = File.join( File.dirname(__FILE__), 'icons', 'default.png')
  @tray_icon.tooltip = "NServer"

  @notification = Notify::Notification::new("X", nil, nil, @tray_icon)
  @notification.timeout = opts[:msg_timeout]
  #@notification.signal_connect('closed') do |s|
  #  puts "Closed!"
  #end

  Thread.new { Gtk.main }
  sleep 5
  @tray_icon.embedded? || raise("Failed to setup tray icon.")

  @tray_icon.signal_connect('activate') do |ti|
    dialog = Gtk::Dialog.new(
      "Message History",
      nil,
      Gtk::Dialog::DESTROY_WITH_PARENT,
      [ Gtk::Stock::OK, Gtk::Dialog::RESPONSE_NONE ]
    )
    dialog.signal_connect('response') {|d,r| d.destroy }
    dialog.vbox.add(Gtk::Label.new("Message history (most recent on top)"))
    @msg_history.reverse.each do |m| 
      label = Gtk::Label.new(m.text)
      label.set_alignment(0,0.5)

      dialog.vbox.add(Gtk::HSeparator.new)
      dialog.vbox.add(label)
    end
    dialog.default_response = -1
    dialog.set_default_size(300, 0)
    dialog.show_all
  end
  

  ## Setup msg thread
  @msg_thread = Thread.new(self, @check_interval) do |server, intv|
    loop do
      server.process
      sleep(intv)
    end
  end
end

Instance Method Details

#add_message(msg, priority = :normal) ⇒ Object

Add a message to the message queue



115
116
117
# File 'lib/nserver.rb', line 115

def add_message(msg, priority = :normal)
  @msg_list << Message.new(msg, priority)
end

#add_message_obj(msg) ⇒ Object

Add an actual message object



120
121
122
# File 'lib/nserver.rb', line 120

def add_message_obj(msg)
  @msg_list << msg
end

#notify(msg) ⇒ Object

Display the message



104
105
106
107
108
109
110
111
112
# File 'lib/nserver.rb', line 104

def notify(msg)
  @msg_history << msg
  @msg_history.shift if @msg_history.size > 5

  @notification.update((msg.title or "Message Received"), msg.text, nil)
  @notification.urgency = msg.priority
  #@tray_icon.tooltip = msg.title
  @notification.show
end

#processObject

Display the next message, if any.



125
126
127
128
129
# File 'lib/nserver.rb', line 125

def process
  if @msg_list.size > 0
    notify(@msg_list.shift)
  end
end

#serve(io) ⇒ Object

Get and add a message to the list. GServer method.



132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
# File 'lib/nserver.rb', line 132

def serve(io)
  unless @allowed_clients.any? {|allowed| allowed.include?(IPAddr.new(io.peeraddr.last)) }
    io.puts "#{io.peeraddr.last} is not allowed."
    return
  end
  io.puts("Enter message, terminate with . on it's own line (like SMTP)")
  ## Get message loop
  msg = []
  loop do
    line = io.gets.strip
    break if line == '.' or ! line

    msg << line
  end

  msg = msg.join("\n")

  if msg == "EXITNOW"
    notify("Shutting down.")
    self.shutdown
  elsif msg =~ /^--- !ruby\/object:NServer::Message/
    ## Yaml message?
    m = YAML.load( msg )
    add_message_obj(m)
    io.puts "OK"
  else
    priority = :normal
    if msg =~ /^(.*?):/
      if Message::PRIORITIES.include?( $1.downcase.to_sym )
        priority = $1.downcase.to_sym
        msg.gsub!( /^#{$1}:/, '' )
      end
    end
    add_message(msg, priority)
    io.puts "OK"
  end
end

#shutdownObject

On server shutdown, also do GUI shutdown stuff.



171
172
173
174
175
# File 'lib/nserver.rb', line 171

def shutdown
  Notify.uninit
  Gtk.main_quit
  self.stop
end