Something like Datalog in Ruby. Aries a placeholder name, can't think of something clever right now.
Du kannst nicht mehr als 25 Themen auswählen Themen müssen entweder mit einem Buchstaben oder einer Ziffer beginnen. Sie können Bindestriche („-“) enthalten und bis zu 35 Zeichen lang sein.

114 Zeilen
2.3KB

  1. # frozen_string_literal: true
  2. require_relative "aries/version"
  3. require_relative "aries/database"
  4. require "json"
  5. require "socket"
  6. # require "profile"
  7. module Aries
  8. class Error < StandardError; end
  9. # Your code goes here...
  10. def self.action callable
  11. begin
  12. [callable.call, nil]
  13. rescue => e
  14. pp e.backtrace << e
  15. [nil, e]
  16. end
  17. end
  18. def self.valid? commands
  19. for command in commands
  20. command.keys.each do |k|
  21. if ! ["add", "find", "first", "last"].include? k
  22. return [nil, "Undefined command key '#{k}'"]
  23. end
  24. end
  25. end
  26. return [true, nil]
  27. end
  28. host = "localhost"
  29. port = 1234
  30. server = TCPServer.new host, port
  31. puts "Server started, listening #{host}:#{port}"
  32. dbs = {}
  33. db_factory = lambda do |n|
  34. if ! dbs.keys.include? n
  35. dbs[n] = Database.new n
  36. puts "Initialized database #{n}"
  37. end
  38. dbs[n]
  39. end
  40. # ticker thread
  41. Thread.new do
  42. limit = 60 * 10
  43. loop do
  44. dbs.keys.each do |n|
  45. db = dbs[n]
  46. if db.used_at and ((db.used_at.to_i + limit) < Time.now.to_i)
  47. puts "Closing database #{n} it was last used more than #{limit} seconds ago"
  48. dbs.delete n
  49. puts "Closed database #{n}"
  50. end
  51. end
  52. sleep 1
  53. end
  54. end
  55. loop do
  56. Thread.start server.accept do |client|
  57. # client = server.accept
  58. connection = JSON.parse(client.gets)
  59. db = db_factory.call connection['database']
  60. # client.puts "Connected to Aries"
  61. puts "Client connected #{client}"
  62. while commands = client.gets
  63. commands, err = action -> { JSON.parse commands }
  64. if ! err.nil?
  65. client.puts JSON.generate(err: err)
  66. next
  67. end
  68. _, err = valid? commands
  69. if ! err.nil?
  70. client.puts JSON.generate(err: err)
  71. next
  72. end
  73. results = {}
  74. commands.each_with_index do |command, idx|
  75. func, vals = command.to_a.first
  76. begin
  77. results[idx] = db.send(func, vals)
  78. db.used_at = Time.now.to_i
  79. rescue => e
  80. pp [e.backtrace << e]
  81. results = {err: e}
  82. break
  83. end
  84. end
  85. client.puts JSON.generate(results)
  86. end
  87. client.close
  88. puts "Client disconnected #{client}"
  89. end
  90. end
  91. end