From c1e2162ce27871ea410294355c27a479033b55ec Mon Sep 17 00:00:00 2001 From: Yessiest Date: Sun, 30 Apr 2023 09:48:12 +0400 Subject: [PATCH] starting everything from scratch --- .rubocop.yml | 14 +++++++ .solargraph.yml | 22 +++++++++++ proto.rb | 101 ------------------------------------------------ server.rb | 98 ---------------------------------------------- 4 files changed, 36 insertions(+), 199 deletions(-) create mode 100644 .rubocop.yml create mode 100644 .solargraph.yml delete mode 100644 proto.rb delete mode 100644 server.rb diff --git a/.rubocop.yml b/.rubocop.yml new file mode 100644 index 0000000..d3fea44 --- /dev/null +++ b/.rubocop.yml @@ -0,0 +1,14 @@ +# The behavior of RuboCop can be controlled via the .rubocop.yml +# configuration file. It makes it possible to enable/disable +# certain cops (checks) and to alter their behavior if they accept +# any parameters. The file can be placed either in your home +# directory or in some project directory. +# +# RuboCop will start looking for the configuration file in the directory +# where the inspected file is and continue its way up to the root directory. +# +# See https://docs.rubocop.org/rubocop/configuration +require: standard + +inherit_gem: + standard: config/base.yml diff --git a/.solargraph.yml b/.solargraph.yml new file mode 100644 index 0000000..a8ef410 --- /dev/null +++ b/.solargraph.yml @@ -0,0 +1,22 @@ +--- +include: +- "**/*.rb" +exclude: +- spec/**/* +- test/**/* +- vendor/**/* +- ".bundle/**/*" +require: [] +domains: [] +reporters: +- rubocop +- require_not_found +formatter: + rubocop: + cops: safe + except: [] + only: [] + extra_args: [] +require_paths: [] +plugins: [] +max_files: 5000 diff --git a/proto.rb b/proto.rb deleted file mode 100644 index 256e475..0000000 --- a/proto.rb +++ /dev/null @@ -1,101 +0,0 @@ -require "date" -def validate(*a) - # Check arguments against either a list of acceptable classes or just a class - raise ArgumentError, "expected an even number of arguments" if a.count%2 != 0 - for i in (0..a.count-1).step(2) do - if a[i+1].kind_of?(Class) then - raise TypeError, "expected argument #{i/2} of type #{a[i+1].to_s}" unless a[i].kind_of?(a[i+1]) - elsif a[i+1].kind_of?(Array) then - raise TypeError, "expected argument #{i/2} of any of the types #{a[i+1].to_s}" unless a[i+1].include?(a[i].class) - end - end -end -module Heimdall - # Core protocol - class NetEntity - # Abstraction that stores basic object properties - @createdAt - def initialize() - @createdAt = DateTime.new - end - attr_reader :createdAt - end - - class User < NetEntity - # User abstraction (not bound to a group chat) - @username - @nickname - def initialize(username,nickname = nil) - validate( - username, String, - nickname, [String,NilClass] - ) - super() - nickname = username if not nickname - @username = username - @nickname = nickname - end - attr_reader :username - attr_accessor :nickname - end - - class Channel < NetEntity - # Channel abstraction (not bound to a group) - # Practically acts as a message stack - # Read access to all elements - # Write access only to top - @messages - def initialize() - validate( - id, String - ) - super() - @messages = [] - end - def [](index) - @messages[id] - end - def <<(message) - @messages.append(message) - end - def top(count = 1) - return @messages[-1] if count == 1 - @messages[(-1*count)..-1] - end - def filter(&block) - @messages.filter(block) - end - def snapshot() - @messages.clone - end - end - - class Message < NetEntity - # Message abstraction with edits and content history (not bound to a group) - @content - @author - @editedAt - @contentHist - def initialize(content,author,channel) - validate( - content, String, - author, Heimdall::User, - channel, Heimdall::Channel - ) - super() - @editedAt = DateTime.new - @contentHist = [content] - @content = content - @author = author - end - def edit(content) - @content = content - @editedAt = DateTime.new - @contentHist.append(content) - end - attr_reader :content - attr_reader :author - attr_reader :contentHist - attr_reader :editedAt - end -end diff --git a/server.rb b/server.rb deleted file mode 100644 index 65fd5b1..0000000 --- a/server.rb +++ /dev/null @@ -1,98 +0,0 @@ -# Prototype of the heimdall server -$LOAD_PATH << "." -$VERSION = "0.1" -$PORT = 9128 -require "proto" -require "socket" - -PROTO_CODES = { - :SUCCESS => 0, - :BADJSON => 1, - :NOMETHOD => 2, - :INVPARAM => 3, - :NOTIMPL => 4 -} - -PROTO_MESSAGES = { - :SUCCESS => "Done", - :BADJSON => "Invalid JSON object", - :NOMETHOD => "Invalid method", - :INVPARAM => "Invalid parameters", - :NOTIMPL => "Not implemented" -} - -class Server - @channelPool - @channelListeners - @methods - def initialize() - @channelPool = {} - @channelListeners = {} - @methods = [ - "join", - "useradd", - "userdel", - "userinfo", - "lusers", - "lchannels", - "chantop", - "chansend", - "chanedit" - ] - end - - def send(client,message) - client.puts JSON.dump(message) - end - - def err(client,code) - client.puts JSON.dump({ - :error=>PROTO_MESSAGES[code], - :code=>PROTO_CODES[code] - }) - client.close - end - - def serve(client) - # basic validation steps - begin - # 1. JSON validation - data = client.gets - data = JSON.load(data) - rescue JSON::ParserError - err(client,:BADJSON) - end - # 2. Method validation - method = data[:method] - err(client,:NOMETHOD) if not @methods.include?(method) - # last but not least: calling the given method - if not self.methods.include?(method) then - err(client,:NOTIMPL) - return - end - send(client,self.method(method).call(client,data)) - end - - def join(client,data) - chaind = data["chanid"] - chanid = rand(89999999)+10000000 if not chanid - if not @channelPool[chanid] then - @channelPool[chanid] = Heimdall::Channel.new - @channelListeners - end - return { - :code=>PROTO_CODE[:SUCCESS], - :method=>"join", - :chanid=>chanid, - } - end -end - -puts "Starting heimdall v#{$VERSION} server on port #{$PORT}..." -server = TCPServer.new 9128 -loop do - Thread.start(server.accept) do |client| - puts "Received client connection on #{client.addr}" - - end -end