lib/session/sessionstorage.rb in rsence-2.0.0.6.pre vs lib/session/sessionstorage.rb in rsence-2.0.0.7.pre
- old
+ new
@@ -4,343 +4,336 @@
#
# You should have received a copy of the GNU General Public License along
# with this software package. If not, contact licensing@riassence.com
##
-require 'rubygems'
-require 'sequel'
-## HValue class for session restoration
-require 'values/hvalue'
-
-
module RSence
-=begin
-SessionStorage doesn't do anything by itself, it's simply
-the superclass for SessionManager that does all the boring
-housekeeping duties.
-
-Splitted of as a separate file to reduce the complexity
-of SessionManager.
-
-=end
-class SessionStorage
- attr_accessor :db
- def initialize
- ## Session data storage (by ses_id)
- @sessions = {}
+ require 'rubygems'
+ require 'sequel'
+
+ ## HValue class for session restoration
+ require 'values/hvalue'
+
+ # SessionStorage doesn't do anything by itself, it's simply
+ # the superclass for SessionManager that does all the boring
+ # housekeeping duties.
+ #
+ # Splitted of as a separate file to reduce the complexity
+ # of SessionManager.
+ class SessionStorage
+ attr_accessor :db
+ def initialize
+ ## Session data storage (by ses_id)
+ @sessions = {}
- ## Session id by key
- @session_keys = {}
+ ## Session id by key
+ @session_keys = {}
- ## Session id by cookie key
- @session_cookie_keys = {}
+ ## Session id by cookie key
+ @session_cookie_keys = {}
- @clone_origins = {
- # id => [ id, id, id ... ]
- }
- @clone_sources = {
- # id => id
- }
- @clone_targets = {
- # id => [ id, id, id ... ]
- }
+ @clone_origins = {
+ # id => [ id, id, id ... ]
+ }
+ @clone_sources = {
+ # id => id
+ }
+ @clone_targets = {
+ # id => [ id, id, id ... ]
+ }
- ## Disposable keys (new ses_key each request)
- @config = ::RSence.config[:session_conf]
+ ## Disposable keys (new ses_key each request)
+ @config = ::RSence.config[:session_conf]
- @db_uri = ::RSence.config[:database][:ses_db]
+ @db_uri = ::RSence.config[:database][:ses_db]
- if db_test
- @db_avail = true
- db_init
- else
- @db_avail = false
- puts "Warning: Session database is not available. Can't use persistent sessions."
- @id_counter = 0
- end
+ if db_test
+ @db_avail = true
+ db_init
+ else
+ @db_avail = false
+ puts "Warning: Session database is not available. Can't use persistent sessions."
+ @id_counter = 0
+ end
- @accept_requests = true
+ @accept_requests = true
- end
+ end
- attr_reader :accept_requests
+ attr_reader :accept_requests
- def db_test
- begin
- db_open
- if @db.table_exists?(:rsence_test)
+ def db_test
+ begin
+ db_open
+ if @db.table_exists?(:rsence_test)
+ @db.drop_table(:rsence_test)
+ end
+ @db.create_table(:rsence_test) { primary_key :id; String :test }
+ test_id = @db[:rsence_test].insert( :test => 'TestFoo' )
+ @db[:rsence_test].filter( :id => test_id ).update( :test => 'TestFoo2' )
+ @db[:rsence_test].filter( :id => test_id ).delete
+ @db[:rsence_test].delete
@db.drop_table(:rsence_test)
+ db_close
+ return true
+ rescue => e
+ if RSence.args[:debug]
+ err_msg = [
+ "ERROR: SessionStorage couldn't open database",
+ "#{e.class.to_s}, #{e.message}",
+ "Backtrace:",
+ "\t"+e.backtrace.join("\n\t")
+ ].join("\n")+"\n"
+ $stderr.write( err_msg )
+ elsif RSence.args[:verbose]
+ puts "Failed to open database '#{@db_uri}'."
+ puts "Run RSence in debug mode for full error output."
+ end
+ return false
end
- @db.create_table(:rsence_test) { primary_key :id; String :test }
- test_id = @db[:rsence_test].insert( :test => 'TestFoo' )
- @db[:rsence_test].filter( :id => test_id ).update( :test => 'TestFoo2' )
- @db[:rsence_test].filter( :id => test_id ).delete
- @db[:rsence_test].delete
- @db.drop_table(:rsence_test)
- db_close
- return true
- rescue => e
- if RSence.args[:debug]
- err_msg = [
- "ERROR: SessionStorage couldn't open database",
- "#{e.class.to_s}, #{e.message}",
- "Backtrace:",
- "\t"+e.backtrace.join("\n\t")
- ].join("\n")+"\n"
- $stderr.write( err_msg )
- elsif RSence.args[:verbose]
- puts "Failed to open database '#{@db_uri}'."
- puts "Run RSence in debug mode for full error output."
- end
- return false
end
- end
- def db_close
- @db.disconnect
- end
+ def db_close
+ @db.disconnect
+ end
- def db_open
- # work-around for windows (drive letters causing confusion)
- if @db_uri.start_with?('sqlite://')
- @db = Sequel.sqlite( @db_uri.split('sqlite://')[1] )
- else
- @db = Sequel.connect(@db_uri)
+ def db_open
+ # work-around for windows (drive letters causing confusion)
+ if @db_uri.start_with?('sqlite://')
+ @db = Sequel.sqlite( @db_uri.split('sqlite://')[1] )
+ else
+ @db = Sequel.connect(@db_uri)
+ end
end
- end
- ## Creates the 'rsence_session' table, if necessary
- ## This table is used to store sessions
- def create_session_table
- db_open
- unless @db.table_exists?(:rsence_session)
- puts "Creating session table..." if RSence.args[:verbose]
- @db.create_table :rsence_session do
- primary_key( :id )
- column( :cookie_key, String )
- column( :ses_key, String )
- column( :ses_timeout, Integer )
- column( :user_id, Integer )
- column( :ses_active, TrueClass )
- column( :ses_stored, Integer )
- column( :ses_data, File )
+ ## Creates the 'rsence_session' table, if necessary
+ ## This table is used to store sessions
+ def create_session_table
+ db_open
+ unless @db.table_exists?(:rsence_session)
+ puts "Creating session table..." if RSence.args[:verbose]
+ @db.create_table :rsence_session do
+ primary_key( :id )
+ column( :cookie_key, String )
+ column( :ses_key, String )
+ column( :ses_timeout, Integer )
+ column( :user_id, Integer )
+ column( :ses_active, TrueClass )
+ column( :ses_stored, Integer )
+ column( :ses_data, File )
+ end
end
+ db_close
end
- db_close
- end
- ## Creates the 'rsence_version' table, if necessary
- ## This table is used to check for the need of future database upgrades
- def create_version_table
- db_open
- unless @db.table_exists?(:rsence_version)
- puts "Creating version info table..." if RSence.args[:verbose]
- @db.create_table :rsence_version do
- Integer :version
+ ## Creates the 'rsence_version' table, if necessary
+ ## This table is used to check for the need of future database upgrades
+ def create_version_table
+ db_open
+ unless @db.table_exists?(:rsence_version)
+ puts "Creating version info table..." if RSence.args[:verbose]
+ @db.create_table :rsence_version do
+ Integer :version
+ end
+ @db[:rsence_version].insert(:version => 586)
end
- @db[:rsence_version].insert(:version => 586)
+ db_close
end
- db_close
- end
- ## Creates the 'rsence_uploads' table, if necessary
- ## This table is used for storing temporary uploads before processing
- def create_uploads_table
- db_open
- unless @db.table_exists?(:rsence_uploads)
- puts "Creating uploads table..." if RSence.args[:verbose]
- @db.create_table :rsence_uploads do
- primary_key( :id )
- foreign_key( :ses_id, :rsence_session )
- column( :upload_date, Integer )
- column( :upload_done, Integer )
- column( :ticket_id, String )
- column( :file_size, Integer )
- column( :file_name, String )
- column( :file_mime, String )
- column( :file_data, File )
+ ## Creates the 'rsence_uploads' table, if necessary
+ ## This table is used for storing temporary uploads before processing
+ def create_uploads_table
+ db_open
+ unless @db.table_exists?(:rsence_uploads)
+ puts "Creating uploads table..." if RSence.args[:verbose]
+ @db.create_table :rsence_uploads do
+ primary_key( :id )
+ foreign_key( :ses_id, :rsence_session )
+ column( :upload_date, Integer )
+ column( :upload_done, Integer )
+ column( :ticket_id, String )
+ column( :file_size, Integer )
+ column( :file_name, String )
+ column( :file_mime, String )
+ column( :file_data, File )
+ end
end
+ db_close
end
- db_close
- end
- # returns the version in the rsence_version table
- def table_version
- db_open
- rsence_version = @db[:rsence_version].select(:version).all[0][:version]
- db_close
- return rsence_version
- end
+ # returns the version in the rsence_version table
+ def table_version
+ db_open
+ rsence_version = @db[:rsence_version].select(:version).all[0][:version]
+ db_close
+ return rsence_version
+ end
- ## Checks database connectivity and loads stored sessions from the database
- def db_init
+ ## Checks database connectivity and loads stored sessions from the database
+ def db_init
- create_session_table
- create_version_table
- create_uploads_table
+ create_session_table
+ create_version_table
+ create_uploads_table
- ## Used for future upgrades:
- # version = table_version
+ ## Used for future upgrades:
+ # version = table_version
- if @config[:reset_sessions]
- puts "Resetting all sessions..."
- reset_sessions()
- else
- restore_sessions()
- end
+ if @config[:reset_sessions]
+ puts "Resetting all sessions..."
+ reset_sessions()
+ else
+ restore_sessions()
+ end
- return true
- end
-
- ## Deletes all rows from rsence_session as well as rsence_uploads
- def reset_sessions
- unless @db_avail
- puts "Warning: Can't reset sessions: No database!" if RSence.args[:verbose]
- return
+ return true
end
- db_open
- @db[:rsence_session].delete if @db.table_exists?(:rsence_session)
- @db[:rsence_uploads].delete if @db.table_exists?(:rsence_uploads)
- db_close
- end
- ## Restores all saved sessions from db to ram
- def restore_sessions
- unless @db_avail
- puts "Warning: Can't restore sessions: No database!" if RSence.args[:verbose]
- return
+ ## Deletes all rows from rsence_session as well as rsence_uploads
+ def reset_sessions
+ unless @db_avail
+ puts "Warning: Can't reset sessions: No database!" if RSence.args[:verbose]
+ return
+ end
+ db_open
+ @db[:rsence_session].delete if @db.table_exists?(:rsence_session)
+ @db[:rsence_uploads].delete if @db.table_exists?(:rsence_uploads)
+ db_close
end
- puts "Restoring sessions..." if RSence.args[:verbose]
- db_open
- @db[:rsence_session].all do |ses_row|
- ses_id = ses_row[:id]
- ses_data_dump = ses_row[:ses_data]
+
+ ## Restores all saved sessions from db to ram
+ def restore_sessions
+ unless @db_avail
+ puts "Warning: Can't restore sessions: No database!" if RSence.args[:verbose]
+ return
+ end
+ puts "Restoring sessions..." if RSence.args[:verbose]
+ db_open
+ @db[:rsence_session].all do |ses_row|
+ ses_id = ses_row[:id]
+ ses_data_dump = ses_row[:ses_data]
- if ses_data_dump == nil
- @db[:rsence_session].filter(:id => ses_id).delete
- @db[:rsence_uploads].filter(:ses_id => ses_id).delete
- else
- ses_data = Marshal.restore( ses_data_dump )
- ses_key = ses_data[:ses_key]
- @sessions[ses_id] = ses_data
- @session_keys[ ses_key ] = ses_id
- @session_cookie_keys[ ses_data[:cookie_key] ] = ses_id
+ if ses_data_dump == nil
+ @db[:rsence_session].filter(:id => ses_id).delete
+ @db[:rsence_uploads].filter(:ses_id => ses_id).delete
+ else
+ ses_data = Marshal.restore( ses_data_dump )
+ ses_key = ses_data[:ses_key]
+ @sessions[ses_id] = ses_data
+ @session_keys[ ses_key ] = ses_id
+ @session_cookie_keys[ ses_data[:cookie_key] ] = ses_id
+ end
end
+ db_close
end
- db_close
- end
- ## Stores all sessions to db from ram
- def store_sessions
- unless @db_avail
- puts "Warning: Can't store sessions: No database!" if RSence.args[:verbose]
- return
+ ## Stores all sessions to db from ram
+ def store_sessions
+ unless @db_avail
+ puts "Warning: Can't store sessions: No database!" if RSence.args[:verbose]
+ return
+ end
+ puts "Storing sessions..." if RSence.args[:verbose]
+ db_open
+ @sessions.each_key do |ses_id|
+ ses_data = @sessions[ ses_id ]
+ ses_data_dump = Marshal.dump( ses_data )
+ @db[:rsence_session].filter(
+ :id => ses_id
+ ).update(
+ :cookie_key => ses_data[:cookie_key],
+ :ses_key => ses_data[:ses_key],
+ :user_id => ses_data[:user_id],
+ :ses_data => ses_data_dump.to_sequel_blob,
+ :ses_timeout => ses_data[:timeout],
+ :ses_stored => Time.now.to_i
+ )
+ end
+ db_close
end
- puts "Storing sessions..." if RSence.args[:verbose]
- db_open
- @sessions.each_key do |ses_id|
- ses_data = @sessions[ ses_id ]
- ses_data_dump = Marshal.dump( ses_data )
- @db[:rsence_session].filter(
- :id => ses_id
- ).update(
- :cookie_key => ses_data[:cookie_key],
- :ses_key => ses_data[:ses_key],
- :user_id => ses_data[:user_id],
- :ses_data => ses_data_dump.to_sequel_blob,
- :ses_timeout => ses_data[:timeout],
- :ses_stored => Time.now.to_i
- )
+
+ ## Shut-down signal, triggers store_sessions for now
+ def shutdown
+ @accept_requests = false
+ puts "Session shutdown in progress..." if RSence.args[:verbose]
+ store_sessions
+ puts "Session shutdown complete." if RSence.args[:verbose]
end
- db_close
- end
- ## Shut-down signal, triggers store_sessions for now
- def shutdown
- @accept_requests = false
- puts "Session shutdown in progress..." if RSence.args[:verbose]
- store_sessions
- puts "Session shutdown complete." if RSence.args[:verbose]
- end
-
- ## Returns a new, unique session identifier by storing the params to the database
- def new_ses_id( cookie_key, ses_key, timeout_secs, user_id=0 )
- unless @db_avail
- @id_counter += 1
- return @id_counter
+ ## Returns a new, unique session identifier by storing the params to the database
+ def new_ses_id( cookie_key, ses_key, timeout_secs, user_id=0 )
+ unless @db_avail
+ @id_counter += 1
+ return @id_counter
+ end
+ db_open
+ new_id = @db[:rsence_session].insert(
+ :cookie_key => cookie_key,
+ :ses_key => ses_key,
+ :ses_timeout => timeout_secs,
+ :user_id => user_id
+ )
+ db_close
+ return new_id
end
- db_open
- new_id = @db[:rsence_session].insert(
- :cookie_key => cookie_key,
- :ses_key => ses_key,
- :ses_timeout => timeout_secs,
- :user_id => user_id
- )
- db_close
- return new_id
- end
- ## Expires a session by its identifier
- def expire_session( ses_id )
+ ## Expires a session by its identifier
+ def expire_session( ses_id )
- return unless @sessions.has_key? ses_id
+ return unless @sessions.has_key? ses_id
- ses_data = @sessions[ ses_id ]
+ ses_data = @sessions[ ses_id ]
- # Makes the session invalid for xhr's by deleting its key
- @session_keys.delete( ses_data[:ses_key] )
+ # Makes the session invalid for xhr's by deleting its key
+ @session_keys.delete( ses_data[:ses_key] )
- # Makes the session invalid for all requests by deleting its cookie key
- @session_cookie_keys.delete( ses_data[:cookie_key] )
+ # Makes the session invalid for all requests by deleting its cookie key
+ @session_cookie_keys.delete( ses_data[:cookie_key] )
- # Deletes the session data itself
- @sessions.delete( ses_id )
+ # Deletes the session data itself
+ @sessions.delete( ses_id )
- # Removes all ticket-based storage bound to the session
- @plugins[:ticketservices].expire_ses( ses_id ) if @plugins
+ # Removes all ticket-based storage bound to the session
+ @plugins[:ticketservices].expire_ses( ses_id ) if @plugins
- # target -> source cleanup
- if @clone_sources.has_key?( ses_id )
- source_id = @clone_sources[ ses_id ]
- @clone_sources.delete( ses_id ) if @clone_sources.has_key?( ses_id )
- @clone_targets[ source_id ].delete( ses_id ) if @clone_targets.has_key?( source_id )
- end
+ # target -> source cleanup
+ if @clone_sources.has_key?( ses_id )
+ source_id = @clone_sources[ ses_id ]
+ @clone_sources.delete( ses_id ) if @clone_sources.has_key?( ses_id )
+ @clone_targets[ source_id ].delete( ses_id ) if @clone_targets.has_key?( source_id )
+ end
- # source -> targets cleanup
- if @clone_targets.has_key?( ses_id )
- @clone_targets[ ses_id ].each do |target_id|
- @clone_sources.delete( target_id ) if @clone_sources.has_key?( target_id )
+ # source -> targets cleanup
+ if @clone_targets.has_key?( ses_id )
+ @clone_targets[ ses_id ].each do |target_id|
+ @clone_sources.delete( target_id ) if @clone_sources.has_key?( target_id )
+ end
+ @clone_targets.delete( ses_id ) if @clone_targets.has_key?( ses_id )
end
- @clone_targets.delete( ses_id ) if @clone_targets.has_key?( ses_id )
- end
- if @db_avail
- db_open
- # Deletes the session's row from the database
- @db[:rsence_session].filter(:id => ses_id).delete
- db_close
- end
+ if @db_avail
+ db_open
+ # Deletes the session's row from the database
+ @db[:rsence_session].filter(:id => ses_id).delete
+ db_close
+ end
- end
+ end
- ## Expires all sessions that meet the timeout criteria
- def expire_sessions
+ ## Expires all sessions that meet the timeout criteria
+ def expire_sessions
- # Loop through all sessions in memory:
- @sessions.each_key do |ses_id|
+ # Loop through all sessions in memory:
+ @sessions.each_key do |ses_id|
- timed_out = @sessions[ ses_id ][:timeout] < Time.now.to_i
+ timed_out = @sessions[ ses_id ][:timeout] < Time.now.to_i
- ## Deletes the session, if the session is too old
- expire_session( ses_id ) if timed_out
+ ## Deletes the session, if the session is too old
+ expire_session( ses_id ) if timed_out
+ end
end
end
-
end
-
-end
-
-