mvcStudentXD 0.1.0 → 1.0.1

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 6c85e24e0f4472cee6a1a943cd1a2f823ec331950b233a8f0a8e215c6abe0446
4
- data.tar.gz: 3b5c12e96488be86df0f2a3e2bd1b3c623db04763b579c59d013d0c2fae9a326
3
+ metadata.gz: 05bfbb2529d8c939220be36718ce9cbb3c90ff7056babd6bff767525894754dc
4
+ data.tar.gz: 2cd7ca8f883728d63d2f7c49ff24e6582cfdae96c3f7635be8e74ecfead31e54
5
5
  SHA512:
6
- metadata.gz: 84c75d83870ef1e21e9595f6592d7c73d6d96ae2a56b9050ee09a9d2801af0015373897e0915117d6527c6f1fb2d9a5b289248d4e23fba788d89ad4376983404
7
- data.tar.gz: 560303d9b1ea449470212b9f583fd2d7b7ad5ad0e63471dcf3ee4d3ff851e8e71e37098f52dc2ff6377e2e46c5247c14e3fb9ce54ce5aa88e6c3867e79353735
6
+ metadata.gz: 9b762d1821aba2a08e7afba5bac14ae0094ccff1a767faaefab8ca2fc47dd2a4106440e1776f56f8f69edf237f2fd0d82f909000d45119a355a7b1352ce982eb
7
+ data.tar.gz: 52b6e6fa83cee5074086b0aef86a87df14ff08eb6b333c870430b66b012428afeb350ef4fe0acb54ea44c0fb3f9e742605fee34227ab6870afa4519734ffe567
data/lib/Converter.rb ADDED
@@ -0,0 +1,11 @@
1
+ class Converter
2
+ private_class_method :new
3
+
4
+ def read_file(file_content)
5
+ raise NotImplementedError, 'Abstract class!'
6
+ end
7
+
8
+ def write_file(hash_students)
9
+ raise NotImplementedError, 'Abstract class!'
10
+ end
11
+ end
@@ -0,0 +1,14 @@
1
+ require 'json'
2
+ require_relative 'Converter'
3
+ class ConverterJSON < Converter
4
+ public_class_method :new
5
+
6
+ def read_file(file_content)
7
+ JSON.parse(file_content, {symbolize_names: true})
8
+ end
9
+
10
+ def write_file(hash_students)
11
+ JSON.pretty_generate(hash_students)
12
+ end
13
+
14
+ end
@@ -0,0 +1,26 @@
1
+ require_relative 'Converter'
2
+ class ConverterTxt < Converter
3
+ public_class_method :new
4
+
5
+ def read_file(data)
6
+ result = []
7
+ file_content = data.split("\n")
8
+ file_content.each do |line|
9
+ hash = {}
10
+ puts(line)
11
+ pairs = line.split(',').map{|pair| pair.gsub(/\s+/, '').split(':')}
12
+ pairs.each do |pair|
13
+ hash[pair[0].to_sym]=(pair[0]=="id") ? pair[1].to_i : pair[1]
14
+ end
15
+ result << hash
16
+ end
17
+ result
18
+ end
19
+
20
+ def write_file(hash_students)
21
+ string_arr = hash_students.map do |hash|
22
+ hash.map{|k,v| "#{k}:#{v}"}.join(',')
23
+ end.join("\n")
24
+ end
25
+
26
+ end
@@ -0,0 +1,14 @@
1
+ require 'yaml'
2
+ require_relative 'Converter'
3
+ class ConverterYAML < Converter
4
+ public_class_method :new
5
+
6
+ def read_file(file_content)
7
+ YAML.safe_load(file_content).map{ |h| h.transform_keys(&:to_sym)}
8
+ end
9
+
10
+ def write_file(hash_students)
11
+ YAML.dump(hash_students.map{ |h| h.transform_keys(&:to_s)})
12
+ end
13
+
14
+ end
data/lib/Data_list.rb ADDED
@@ -0,0 +1,66 @@
1
+ class DataList
2
+ private_class_method :new
3
+
4
+ attr_accessor :selected_num, :objects
5
+
6
+ def initialize(*elems)
7
+ self.objects = elems
8
+ @listeners = []
9
+ end
10
+
11
+ def add_listener(listener)
12
+ @listeners << listener
13
+ end
14
+
15
+ def remove_listener(listener)
16
+ @listeners.delete(listener)
17
+ end
18
+
19
+ def notify
20
+ @listeners.each { |lst| lst.on_datalist_changed(data_table) }
21
+ end
22
+
23
+ def select_element(number)
24
+ self.selected_num = number < objects.size ? number : nil
25
+ end
26
+
27
+ def selected_id
28
+ objects[selected_num].id
29
+ end
30
+
31
+ def get_names
32
+ self.objects.first.instance_variables.map{|v| v.to_s[1..-1]}
33
+ end
34
+
35
+ def table_fields(_obj)
36
+ []
37
+ end
38
+
39
+ def data_table
40
+ result = []
41
+ counter = 0
42
+ objects.each do |obj|
43
+ row = []
44
+ row << counter
45
+ row.push(*table_fields(obj))
46
+ result << row
47
+ counter += 1
48
+ end
49
+ DataTable.new(result)
50
+ end
51
+
52
+ def append(new_data)
53
+ self.objects.append(new_data)
54
+ end
55
+
56
+ def replace_objects(objects)
57
+ self.objects = objects.dup
58
+ notify
59
+ end
60
+
61
+ private
62
+ def instance_variables_wout_id(object)
63
+ object.instance_variables.reject{|v| v.to_sym ==:@id}.map{|v| object.instance_variable_get(v)}
64
+ end
65
+
66
+ end
@@ -0,0 +1,17 @@
1
+ require_relative 'Student_short'
2
+ require_relative 'Data_table'
3
+ require_relative 'Data_list'
4
+ class DataListStudentShort < DataList
5
+
6
+ public_class_method :new
7
+
8
+ def get_names
9
+ ['Фамилия И.О.','Гит','Контакт']
10
+ end
11
+
12
+
13
+ def table_fields(obj)
14
+ [obj.fio, obj.git, obj.contact]
15
+ end
16
+
17
+ end
data/lib/Data_table.rb ADDED
@@ -0,0 +1,25 @@
1
+ class DataTable
2
+
3
+ attr_accessor :data
4
+
5
+ def initialize(data)
6
+ self.data = data
7
+ end
8
+
9
+ def get_cell(row,col)
10
+ self.data[row][col]
11
+ end
12
+
13
+ def num_columns
14
+ self.data[0].length
15
+ end
16
+
17
+ def num_rows
18
+ self.data.length
19
+ end
20
+
21
+ def to_2d_array
22
+ data.dup
23
+ end
24
+
25
+ end
data/lib/Student.rb ADDED
@@ -0,0 +1,106 @@
1
+ require 'json'
2
+ require_relative 'StudentBase'
3
+ class Student < StudentBase
4
+
5
+ public_class_method :new
6
+ attr_writer :id
7
+ public
8
+ attr_reader :last_name, :first_name, :parental_name, :id, :phone, :git, :telegram, :email
9
+
10
+ def initialize(last_name, first_name, parental_name, options = {})
11
+ super(last_name, first_name, parental_name)
12
+ self.id = options[:id]
13
+ self.phone = options[:phone]
14
+ self.git = options[:git]
15
+ self.telegram = options[:telegram]
16
+ self.email = options[:email]
17
+ end
18
+
19
+ def to_s
20
+ [
21
+ "#{last_name} #{first_name} #{parental_name}",
22
+ id ? "id: #{id}" : nil,
23
+ git ? "git: #{git}" : nil,
24
+ phone ? "phone: #{phone}" : nil,
25
+ telegram ? "telegram: #{telegram}" : nil,
26
+ email ? "email: #{email}" : nil
27
+ ].compact.join(' ')
28
+ end
29
+
30
+ #Setters
31
+ def phone=(phone)
32
+ raise ArgumentError, "ERROR phone=#{phone}" unless phone.nil? || StudentBase.validate_phone?(phone)
33
+ @phone = phone
34
+ end
35
+
36
+ def telegram=(tg_name)
37
+ raise ArgumentError, "ERROR telegram=#{tg_name}" unless telegram.nil? || StudentBase.validate_git_tg?(tg_name)
38
+ @telegram=tg_name
39
+ end
40
+
41
+ def git=(git_name)
42
+ raise ArgumentError, "ERROR git=#{git_name}" unless git.nil? || StudentBase.validate_git_tg?(git_name)
43
+ @git=git_name
44
+ end
45
+
46
+ def email=(email1)
47
+ raise ArgumentError, "ERROR email=#{email1}" unless email.nil? || StudentBase.validate_email?(email1)
48
+ @email=email1
49
+ end
50
+
51
+ def set_contacts(contacts={})
52
+ self.phone=contacts[:phone]
53
+ self.telegram=contacts[:telegram]
54
+ self.email=contacts[:email]
55
+ end
56
+
57
+ def self.from_str(string)
58
+ stud = string.split(',')
59
+ .map{|v| v.split(':')}
60
+ .map{|v| [v[0].to_sym, v[1]]}
61
+ .to_h
62
+ last_name, first_name, parental_name = stud[:fio].split(' ')
63
+ Student.new(last_name, first_name, parental_name, stud)
64
+ end
65
+
66
+ def self.from_hash(hash)
67
+ raise ArgumentError,"Missing req fields" unless hash.key?(:last_name) && hash.key?(:first_name) && hash.key?(:parental_name)
68
+ #переделал этот метод после тестов. Теперь вынимаю обязательные параметры из хэша, не удаляя из него
69
+ Student.new(hash[:last_name], hash[:first_name], hash[:parental_name], hash)
70
+ end
71
+
72
+ def get_short_fio
73
+ "fio:#{last_name} #{first_name[0]}. #{parental_name[0]}."
74
+ end
75
+
76
+
77
+ def get_short_contact
78
+ contact = %i[telegram phone email].find{|cont| send(cont)}
79
+ {type: contact, val: send(contact)} if contact
80
+ end
81
+
82
+ def get_git
83
+ "git:#{git}"
84
+ end
85
+
86
+ def get_info
87
+ "#{get_short_fio},#{get_short_contact[:type]}:#{get_short_contact[:val]},#{get_git}"
88
+ end
89
+
90
+ def get_info_hash
91
+ info={}
92
+ info[:fio] = get_short_fio
93
+ info[:contact] = get_short_contact
94
+ info[:git] = git
95
+ info
96
+ end
97
+
98
+ def to_hash
99
+ fields = {}
100
+ %i[last_name first_name parental_name id phone git telegram email].each do |field|
101
+ field_val = send(field)
102
+ fields[field] = field_val unless field_val.nil?
103
+ end
104
+ fields
105
+ end
106
+ end
@@ -0,0 +1,50 @@
1
+ require 'json'
2
+ class StudentBase
3
+ private_class_method :new
4
+
5
+ def self.validate_phone?(phone)
6
+ return phone.match(/^\+?[7,8] ?\(?\d{3}\)? ?\d{3}-?\d{2}-?\d{2}$/)
7
+ end
8
+
9
+ def self.validate_email?(email)
10
+ return email.match(/^[A-Za-z0-9\-_]+@[A-Za-z]+(\.[A-Za-z]+)?\.[A-Za-z]+$/)
11
+ end
12
+
13
+ def self.validate_git_tg?(acc_name)
14
+ return acc_name.match(/^@[A-Za-z0-9\-_]+$/)
15
+ end
16
+
17
+ def self.validate_name?(prof_name)
18
+ return prof_name.match(/(^[А-Я][а-я]+$)|(^[A-Z][a-z]+$)/)
19
+ end
20
+
21
+ def valid_cont?
22
+ !email.nil? || !telegram.nil? || !phone.nil?
23
+ end
24
+
25
+ def validate?
26
+ !git.nil? && valid_cont?
27
+ end
28
+
29
+ def initialize(last_name, first_name, parental_name)
30
+ self.last_name = last_name
31
+ self.first_name = first_name
32
+ self.parental_name = parental_name
33
+ end
34
+
35
+ def first_name=(first_name1)
36
+ raise ArgumentError, "ERROR first_name=#{first_name1}" unless StudentBase.validate_name?(first_name1)
37
+ @first_name=first_name1
38
+ end
39
+
40
+ def last_name=(last_name1)
41
+ raise ArgumentError, "ERROR last_name=#{last_name1}" unless StudentBase.validate_name?(last_name1)
42
+ @last_name=last_name1
43
+ end
44
+
45
+ def parental_name=(parental_name1)
46
+ raise ArgumentError, "ERROR parental_name=#{parental_name1}" unless StudentBase.validate_name?(parental_name1)
47
+ @parental_name=parental_name1
48
+ end
49
+
50
+ end
@@ -0,0 +1,65 @@
1
+ class StudentList
2
+ private
3
+ attr_accessor :students, :gen_id, :typer
4
+
5
+ public
6
+ def initialize(typer)
7
+ self.students = []
8
+ self.gen_id = students.count + 1
9
+ self.typer = typer
10
+ end
11
+
12
+ def read_file(file_path)
13
+ raise ArgumentError.new("File not found #{file_path}") unless File.file?(file_path)
14
+ hash_students = typer.read_file(File.read(file_path))
15
+ self.students = hash_students.map{|h| Student.from_hash(h)}
16
+ nextId
17
+ end
18
+
19
+ def write_file(file_path)
20
+ hash_students = students.map(&:to_hash)
21
+ File.write(file_path, typer.write_file(hash_students))
22
+ end
23
+
24
+ def get_student(stud_id)
25
+ students.find{|s| s.id == stud_id}
26
+ end
27
+
28
+ def sorted
29
+ students.sort_by(&:fio)
30
+ end
31
+
32
+ def add_student(student)
33
+ students << student
34
+ student.id = gen_id
35
+ nextId
36
+ end
37
+
38
+ def get_students_pag(k,n,existing_data = nil)
39
+ skip = (k-1) * n
40
+ new_data = students[skip, n].map{|s| StudentShort.from_student_class(s)}
41
+
42
+ return DataListStudentShort.new(new_data) if existing_data.nil?
43
+
44
+ existing_data.replace_objects(new_data)
45
+ existing_data
46
+ end
47
+
48
+ def replace_student(student_id, student)
49
+ idx = student.find{|s| s.id==student.id}
50
+ self.students[idx]=student
51
+ end
52
+
53
+ def remove_student(student_id)
54
+ self.students.reject! {|s| s.id==student_id}
55
+ end
56
+
57
+ def count
58
+ self.students.count
59
+ end
60
+
61
+ def nextId
62
+ self.gen_id=students.max_by(&:id).id + 1
63
+ end
64
+
65
+ end
@@ -0,0 +1,40 @@
1
+ require_relative 'StudentBase'
2
+ class StudentShort < StudentBase
3
+
4
+ public_class_method :new
5
+
6
+ #У нас уже есть некоторые гет\сет в базе, зачем же ещё?
7
+ private
8
+ attr_writer :fio, :contact, :git, :id
9
+
10
+ public
11
+ attr_reader :fio, :contact, :git, :id
12
+
13
+ def self.from_student_class(student)
14
+ puts("In studentShort: #{student.to_s}")
15
+ StudentShort.new(student.id, student.get_info)
16
+ end
17
+
18
+ def initialize(id, str)
19
+ info_short = str.split(',')
20
+ .map{|x| x.split(':')}
21
+ .map{|x| [x[0].to_sym, x[1]]}
22
+ .to_h
23
+ raise ArgumentError, 'Missing fields: fio' if info_short[:fio].nil?
24
+ print(info_short)
25
+ self.id=id
26
+ self.fio = info_short[:fio]
27
+ self.git = info_short[:git]
28
+ info_short.delete_if{|k,v| k==:fio||k==:git}
29
+ self.contact = info_short.values.first
30
+ end
31
+
32
+
33
+ def to_s
34
+
35
+ [
36
+ "#{id}, #{fio}, #{git}, #{contact}"
37
+ ].compact.join(' ')
38
+ end
39
+
40
+ end
@@ -0,0 +1,10 @@
1
+ CREATE TABLE IF NOT EXISTS student(
2
+ id INT NOT NULL auto_increment PRIMARY KEY,
3
+ last_name CHAR(255) NOT NULL,
4
+ first_name CHAR(255) NOT NULL,
5
+ parental_name CHAR(255) NOT NULL,
6
+ git CHAR(255),
7
+ phone CHAR(255),
8
+ email CHAR(255),
9
+ telegram CHAR(255)
10
+ );
@@ -0,0 +1,4 @@
1
+ INSERT INTO student (last_name, first_name, parental_name, git, phone, email, telegram) VALUES
2
+ ROW("Худокормов", "Дмитрий", "Александрович", "@KiTTeNqz", NULL, NULL, "@KiTTeNqzi"),
3
+ ROW("Александров", "Александр", "Александрович", "@AleXxx", "89094494499", NULL, NULL),
4
+ ROW("Ермаков", "Ермак", "Ермакович", "@yaErmak1", NULL, "ERMAK@yandex.ru", NULL)
@@ -0,0 +1,41 @@
1
+ # frozen_string_literal: true
2
+ require_relative './students_db.rb'
3
+
4
+ class StudentListDB
5
+ attr_accessor :database
6
+
7
+ @@instance = nil
8
+
9
+ def self.instance
10
+ @@instance ||= StudentListDB.new
11
+ end
12
+
13
+
14
+ def initialize
15
+ self.database = StudentDB.new()
16
+ end
17
+
18
+ def get_student(id)
19
+ Student.from_hash(database.select_by_id(id).transform_keys(&:to_sym))
20
+ end
21
+
22
+ def remove_student(id)
23
+ database.remove_by_id(id)
24
+ end
25
+
26
+ def replace_student(id, student)
27
+ database.replace_by_id(id, student)
28
+ end
29
+
30
+ def add_student(student)
31
+ database.add_student(student.to_hash)
32
+ end
33
+
34
+ def get_students_pag(k, n, data)
35
+ database.get_students_pag(k, n, data)
36
+ end
37
+
38
+ def count
39
+ database.count
40
+ end
41
+ end
@@ -0,0 +1,82 @@
1
+ # frozen_string_literal: true
2
+ # #encoding: UTF-8
3
+ require 'mysql2'
4
+ require_relative '../Data_list_student_short'
5
+ require_relative '../Data_list'
6
+ require_relative '../Student'
7
+ require_relative '../Student_short'
8
+ class StudentDB
9
+
10
+ attr_accessor :db_connection
11
+
12
+ def initialize
13
+ self.db_connection = Mysql2::Client.new(:host => "localhost", :username => "dimas", :password => "qwe123")
14
+ self.db_connection.query('CREATE DATABASE IF NOT EXISTS stud_db')
15
+ self.db_connection.query('USE stud_db')
16
+ self.db_connection.query('DROP TABLE IF EXISTS student')
17
+ self.db_connection.query(File.read('C:/Users/Dmitry/RubymineProjects/RubyLabs/mvcStudentXD/lib/database/scripts/create_table.sql'))
18
+ self.insert_data
19
+ end
20
+
21
+ def insert_data
22
+ db_connection.query(File.read('C:/Users/Dmitry/RubymineProjects/RubyLabs/mvcStudentXD/lib/database/scripts/insert_data.sql'))
23
+ end
24
+
25
+ def select_by_id(id)
26
+ db_connection.query("SELECT * FROM student WHERE id = #{id}").map{|x| x}[0]
27
+ end
28
+
29
+ def remove_by_id(id)
30
+ db_connection.query("DELETE FROM student WHERE id = #{id}")
31
+ end
32
+
33
+ def parseNil(attr)
34
+ if attr == nil
35
+ "NULL"
36
+ else
37
+ attr
38
+ end
39
+ end
40
+
41
+ def add_student(student_data)
42
+
43
+ db_connection.query("""
44
+ INSERT INTO student (last_name, first_name, parental_name, git, phone, email, telegram) VALUES
45
+ ROW(
46
+ \"#{parseNil(student_data[:last_name])}\",
47
+ \"#{parseNil(student_data[:first_name])}\",
48
+ \"#{parseNil(student_data[:parental_name])}\",
49
+ \"#{parseNil(student_data[:git])}\",
50
+ \"#{parseNil(student_data[:phone])}\",
51
+ \"#{parseNil(student_data[:email])}\",
52
+ \"#{parseNil(student_data[:telegram])}\"
53
+ )
54
+ """)
55
+ end
56
+
57
+ def replace_by_id(id, student_data)
58
+ self.remove_by_id(id)
59
+ self.add_student(student_data.to_hash)
60
+ end
61
+
62
+ def get_students_pag(k, n, existing_data = nil)
63
+ rows = db_connection.query("SELECT * FROM student ORDER BY id LIMIT #{n} OFFSET #{(k-1)*n}")
64
+ data_list = DataListStudentShort.new
65
+ rows.each do |row|
66
+ row_sym = row.transform_keys{|key| key.to_sym}
67
+ data_list.append(StudentShort.from_student_class(Student.from_hash(row_sym)))
68
+ end
69
+ return data_list if existing_data.nil?
70
+ existing_data.replace_objects(data_list.objects)
71
+ existing_data
72
+ end
73
+
74
+ def count
75
+ result = db_connection.query("SELECT count(*) FROM student")
76
+ result.first.values.first
77
+ end
78
+
79
+ end
80
+
81
+ students_db = StudentDB.new
82
+ students_db.insert_data
data/lib/main.rb ADDED
@@ -0,0 +1,23 @@
1
+ require_relative 'Student'
2
+ require_relative 'Student_short'
3
+ require_relative 'Data_list'
4
+ require_relative 'Data_list_student_short'
5
+ require_relative 'Student_list'
6
+ require_relative 'Converter_yaml'
7
+ require_relative 'Converter_txt'
8
+ require_relative 'Converter_json'
9
+ require_relative 'database/student_list_db'
10
+ require_relative 'student_list_adv.rb'
11
+ require_relative 'student_list_adapter.rb'
12
+ require 'mysql2'
13
+
14
+ db = StudentListDB.instance
15
+ puts db.get_student(2)
16
+ puts db.count
17
+
18
+ studentsList = StudentListAdv.new(StudentsListDBAdapter.new(StudentListDB.instance))
19
+ json = StudentList.new(ConverterJSON.new)
20
+ studentsList2 = StudentListAdv.new(StudentsListConverterAdapter.new(json, 'C:/Users/Дмитрий/RubymineProjects/RubyLabs/Lab2/studentsRead.json'))
21
+ puts studentsList.get_student(3)
22
+
23
+ puts studentsList2.get_student(2)
@@ -0,0 +1,28 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'glimmer-dsl-libui'
4
+ require_relative 'tab_students'
5
+
6
+ class MainWindow
7
+ include Glimmer
8
+
9
+ def initialize
10
+ @view_tab_students = TabStudents.new
11
+ end
12
+
13
+ def create
14
+ window('Универ', 600, 300) {
15
+ tab {
16
+ tab_item('Студенты') {
17
+ @view_tab_students.create
18
+ }
19
+
20
+ tab_item('Вкладка 2') { }
21
+ tab_item('Вкладка 3') { }
22
+ }
23
+ }
24
+ end
25
+ end
26
+
27
+ main_window = MainWindow.new.create
28
+ main_window.show
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module MvcStudentXD
4
- VERSION = "0.1.0"
4
+ VERSION = "1.0.1"
5
5
  end
@@ -0,0 +1,56 @@
1
+ # frozen_string_literal: true
2
+
3
+ class StudentEditFormController
4
+ def initialize(parent_controller, existing_student_id)
5
+ @parent_controller = parent_controller
6
+ @existing_student_id = existing_student_id
7
+ end
8
+
9
+ def set_view(view)
10
+ @view = view
11
+ end
12
+
13
+ def on_view_created
14
+ begin
15
+ @student_list = StudentListAdv.new(StudentsListDBAdapter.new(StudentListDB.instance))
16
+ rescue Mysql2::Error::ConnectionError
17
+ on_db_conn_error
18
+ end
19
+ @existing_student = @student_list.get_student(@existing_student_id)
20
+ @view.make_readonly(:git, :telegram, :email, :phone)
21
+ print("IM IN ONVIEW EDIT")
22
+ populate_fields(@existing_student)
23
+ end
24
+
25
+ def populate_fields(student)
26
+ @view.set_value(:last_name, student.last_name)
27
+ @view.set_value(:first_name, student.first_name)
28
+ @view.set_value(:parental_name, student.parental_name)
29
+ @view.set_value(:git, student.git)
30
+ @view.set_value(:telegram, student.telegram)
31
+ @view.set_value(:email, student.email)
32
+ @view.set_value(:phone, student.phone)
33
+ print("IM IN Populate EDIT")
34
+ end
35
+
36
+ def process_fields(fields)
37
+ begin
38
+ new_student = Student.from_hash(fields)
39
+ print("IM IN PROCESS EDIT")
40
+ @student_list.replace_student(@existing_student_id, new_student)
41
+
42
+ @view.close
43
+ rescue ArgumentError => e
44
+ api = Win32API.new('user32', 'MessageBox', ['L', 'P', 'P', 'L'], 'I')
45
+ api.call(0, e.message, 'Error', 0)
46
+ end
47
+ end
48
+
49
+ private
50
+
51
+ def on_db_conn_error
52
+ api = Win32API.new('user32', 'MessageBox', ['L', 'P', 'P', 'L'], 'I')
53
+ api.call(0, "No connection to DB", "Error", 0)
54
+ @view.close
55
+ end
56
+ end
@@ -0,0 +1,72 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'glimmer-dsl-libui'
4
+ require_relative 'student_input_form_controller'
5
+ require_relative 'StudentBase'
6
+ require 'win32api'
7
+
8
+ class StudentInputForm
9
+ include Glimmer
10
+
11
+ def initialize(controller, existing_student = nil)
12
+ @existing_student = existing_student.to_hash unless existing_student.nil?
13
+ @controller = controller
14
+ @entries = {}
15
+ end
16
+
17
+ def on_create
18
+ @controller.on_view_created
19
+ end
20
+
21
+ def create
22
+ @root_container = window('Универ', 300, 150) {
23
+ resizable false
24
+
25
+ vertical_box {
26
+ @student_form = form {
27
+ stretchy false
28
+
29
+ fields = [[:last_name, 'Фамилия', false], [:first_name, 'Имя', false], [:parental_name, 'Отчество', false], [:git, 'Гит', true], [:telegram, 'Телеграм', true], [:email, 'Почта', true], [:phone, 'Телефон', true]]
30
+
31
+ fields.each do |field|
32
+ @entries[field[0]] = entry {
33
+ label field[1]
34
+ text @existing_student[field[0]] unless @existing_student.nil?
35
+
36
+ read_only field[2] unless @existing_student.nil?
37
+ }
38
+ end
39
+ }
40
+
41
+ button('Сохранить') {
42
+ stretchy false
43
+
44
+ on_clicked {
45
+ values = @entries.transform_values { |v| v.text.force_encoding("utf-8").strip }
46
+ values.transform_values! { |v| v.empty? ? nil : v}
47
+ print
48
+ print values
49
+ @controller.process_fields(values)
50
+ }
51
+ }
52
+ }
53
+ }
54
+ on_create
55
+ @root_container
56
+ end
57
+
58
+ def set_value(field, value)
59
+ return unless @entries.include?(field)
60
+ @entries[field].text = value
61
+ end
62
+
63
+ def make_readonly(*fields)
64
+ fields.each do |field|
65
+ @entries[field].read_only = true
66
+ end
67
+ end
68
+
69
+ def close
70
+ @root_container.destroy
71
+ end
72
+ end
@@ -0,0 +1,47 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'win32api'
4
+
5
+ class StudentInputFormController
6
+ def initialize(parent_controller)
7
+ @parent_controller = parent_controller
8
+ end
9
+
10
+ def set_view(view)
11
+ @view = view
12
+ end
13
+
14
+ def on_view_created
15
+ begin
16
+ @student_list = StudentListAdv.new(StudentsListDBAdapter.new(StudentListDB.instance))
17
+ rescue Mysql2::Error::ConnectionError
18
+ on_db_conn_error
19
+ end
20
+ end
21
+
22
+ def process_fields(fields)
23
+ begin
24
+ last_name = fields.delete(:last_name)
25
+ first_name = fields.delete(:first_name)
26
+ parental_name = fields.delete(:parental_name)
27
+
28
+ return if last_name.nil? || first_name.nil? || parental_name.nil?
29
+
30
+ student = Student.new(last_name, first_name, parental_name, **fields)
31
+
32
+ @student_list.add_student(student)
33
+
34
+ @view.close
35
+ rescue ArgumentError => e
36
+ api = Win32API.new('user32', 'MessageBox', ['L', 'P', 'P', 'L'], 'I')
37
+ api.call(0, e.message, 'Error', 0)
38
+ end
39
+ end
40
+
41
+
42
+ def on_db_conn_error
43
+ api = Win32API.new('user32', 'MessageBox', ['L', 'P', 'P', 'L'], 'I')
44
+ api.call(0, "No connection to DB", "Error", 0)
45
+ @view.close
46
+ end
47
+ end
@@ -0,0 +1,95 @@
1
+ # frozen_string_literal: true
2
+ require_relative 'Student_list'
3
+ class StudentsListAdapter
4
+ private_class_method :new
5
+ def get_student(id)
6
+ end
7
+
8
+ def remove_student(id)
9
+ end
10
+
11
+ def replace_student(id, student)
12
+ end
13
+
14
+ def get_students_pag(k, n, data)
15
+ end
16
+
17
+ def add_student(student)
18
+ end
19
+
20
+ def count
21
+ end
22
+ end
23
+
24
+ class StudentsListDBAdapter < StudentsListAdapter
25
+ private
26
+ attr_accessor :database_list
27
+
28
+ public_class_method :new
29
+
30
+ public
31
+ def initialize(database_list)
32
+ self.database_list = database_list
33
+ end
34
+
35
+ def get_student(id)
36
+ database_list.get_student(id)
37
+ end
38
+
39
+ def remove_student(id)
40
+ database_list.remove_student(id)
41
+ end
42
+
43
+ def replace_student(id, student)
44
+ database_list.replace_student(id, student)
45
+ end
46
+
47
+ def get_students_pag(from, to, data)
48
+ database_list.get_students_pag(from, to, data)
49
+ end
50
+
51
+ def add_student(student)
52
+ database_list.add_student(student)
53
+ end
54
+
55
+ def count
56
+ database_list.count
57
+ end
58
+ end
59
+
60
+ class StudentsListConverterAdapter < StudentsListAdapter
61
+ private
62
+ attr_accessor :file_list
63
+
64
+ public_class_method :new
65
+
66
+ public
67
+ def initialize(file_list, filename)
68
+ self.file_list = file_list
69
+ self.file_list.read_file(filename)
70
+ end
71
+
72
+ def get_student(id)
73
+ file_list.get_student(id)
74
+ end
75
+
76
+ def remove_student(id)
77
+ file_list.remove_student(id)
78
+ end
79
+
80
+ def replace_student(id, student)
81
+ file_list.replace_student(id, student)
82
+ end
83
+
84
+ def get_students_pag(k, n, data=nil)
85
+ file_list.get_students_pag(k, n, data)
86
+ end
87
+
88
+ def add_student(student)
89
+ file_list.add_student(student)
90
+ end
91
+
92
+ def count
93
+ file_list.count
94
+ end
95
+ end
@@ -0,0 +1,35 @@
1
+ # frozen_string_literal: true
2
+
3
+ class StudentListAdv
4
+ private
5
+ attr_accessor :students_list_adapter
6
+ public
7
+ def initialize(students_list_adapter)
8
+ self.students_list_adapter = students_list_adapter
9
+ end
10
+
11
+ def get_student(id)
12
+ students_list_adapter.get_student(id)
13
+ end
14
+
15
+ def remove_student(id)
16
+ students_list_adapter.remove_student(id)
17
+ end
18
+
19
+ def replace_student(id, student)
20
+ students_list_adapter.replace_student(id, student)
21
+ end
22
+
23
+ def get_students_pag(k, n, data)
24
+ students_list_adapter.get_students_pag(k, n, data)
25
+ end
26
+
27
+ def add_student(student)
28
+ students_list_adapter.add_student(student)
29
+ end
30
+
31
+ def count
32
+ students_list_adapter.count
33
+ end
34
+
35
+ end
@@ -0,0 +1,72 @@
1
+ # frozen_string_literal: true
2
+
3
+ # frozen_string_literal: true
4
+ require_relative 'student_list_adv'
5
+ require_relative 'student_list_adapter'
6
+ require_relative 'database/student_list_db'
7
+ require_relative 'Converter_json'
8
+ require_relative 'Converter'
9
+ require_relative 'Student_list'
10
+ require_relative 'student_edit_form_controller'
11
+ require 'win32api'
12
+ require 'mysql2'
13
+ class StudentListController
14
+ def initialize(view)
15
+ @view = view
16
+ @data_list = DataListStudentShort.new
17
+ @data_list.add_listener(@view)
18
+ end
19
+
20
+ def on_view_created
21
+ begin
22
+ @student_list = StudentListAdv.new(StudentsListDBAdapter.new(StudentListDB.instance))
23
+ rescue Mysql2::Error::ConnectionError
24
+ on_db_conn_error
25
+ end
26
+ end
27
+
28
+ def delete_selected(current_page, per_page, selected_row)
29
+ begin
30
+ student_num = (current_page - 1) * per_page + selected_row
31
+ @data_list.select_element(student_num)
32
+ student_id = @data_list.selected_id
33
+ @student_list.remove_student(student_id)
34
+ rescue
35
+ on_db_conn_error
36
+ end
37
+ end
38
+
39
+ def show_modal_add
40
+ controller = StudentInputFormController.new(self)
41
+ view = StudentInputForm.new(controller)
42
+ controller.set_view(view)
43
+ view.create.show
44
+ end
45
+
46
+ def show_modal_edit(current_page, per_page, selected_row)
47
+ student_num = (current_page - 1) * per_page + selected_row
48
+ @data_list.select_element(student_num)
49
+ student_id = @data_list.selected_id
50
+ controller = StudentEditFormController.new(self, student_id)
51
+ view = StudentInputForm.new(controller)
52
+ controller.set_view(view)
53
+ view.create.show
54
+ end
55
+
56
+ def refresh_data(page, per_page)
57
+ begin
58
+ @data_list = @student_list.get_students_pag(page, per_page, @data_list)
59
+ @view.update_student_count(@student_list.count)
60
+ rescue
61
+ on_db_conn_error
62
+ end
63
+ end
64
+
65
+ private
66
+ def on_db_conn_error
67
+ api = Win32API.new('user32', 'MessageBox', ['L', 'P', 'P', 'L'], 'I')
68
+ api.call(0, "No connection to DB", "Error", 0)
69
+ exit(false)
70
+ end
71
+
72
+ end
@@ -0,0 +1,152 @@
1
+ # frozen_string_literal: true
2
+
3
+ # frozen_string_literal: true
4
+ require 'glimmer-dsl-libui'
5
+ require_relative 'student_list_controller'
6
+ require_relative 'student_input_form'
7
+
8
+ class TabStudents
9
+ include Glimmer
10
+ STUDENTS_PER_PAGE = 20
11
+
12
+ def initialize
13
+ @controller = StudentListController.new(self)
14
+ @current_page = 1
15
+ @total_count = 0
16
+ end
17
+
18
+ def on_create
19
+ @controller.on_view_created
20
+ @controller.refresh_data(@current_page, STUDENTS_PER_PAGE)
21
+ end
22
+
23
+ # Метод наблюдателя datalist
24
+ def on_datalist_changed(new_table)
25
+ arr = new_table.to_2d_array
26
+ @table.model_array = arr
27
+ end
28
+
29
+ def update_student_count(new_cnt)
30
+ @total_count = new_cnt
31
+ @page_label.text = "#{@current_page} / #{(@total_count / STUDENTS_PER_PAGE.to_f).ceil}"
32
+ end
33
+
34
+ def create
35
+ root = horizontal_box {
36
+ # Секция 1
37
+ vertical_box {
38
+ stretchy false
39
+
40
+ form {
41
+ stretchy false
42
+
43
+ @filter_last_name_initials = entry {
44
+ label 'ФИО'
45
+ }
46
+
47
+ @filters = {}
48
+ fields = [[:git, 'Github'], [:email, 'Почта'], [:phone, 'Телефон'], [:telegram, 'Телеграм']]
49
+
50
+ fields.each do |field|
51
+ @filters[field[0]] = {}
52
+
53
+ @filters[field[0]][:combobox] = combobox {
54
+ label "#{field[1]}?"
55
+ items ['Не важно', 'Есть', 'Нет']
56
+ selected 0
57
+
58
+ on_selected do
59
+ if @filters[field[0]][:combobox].selected == 1
60
+ @filters[field[0]][:entry].read_only = false
61
+ else
62
+ @filters[field[0]][:entry].text = ''
63
+ @filters[field[0]][:entry].read_only = true
64
+ end
65
+ end
66
+ }
67
+
68
+ @filters[field[0]][:entry] = entry {
69
+ label field[1]
70
+ read_only true
71
+ }
72
+ end
73
+ }
74
+ }
75
+
76
+ # Секция 2
77
+ vertical_box {
78
+ @table = refined_table(
79
+ table_editable: false,
80
+ filter: lambda do |row_hash, query|
81
+ utf8_query = query.force_encoding("utf-8")
82
+ row_hash['Фамилия И. О'].include?(utf8_query)
83
+ end,
84
+ table_columns: {
85
+ '#' => :text,
86
+ 'Фамилия И. О' => :text,
87
+ 'Гит' => :text,
88
+ 'Контакт' => :text,
89
+ },
90
+ per_page: STUDENTS_PER_PAGE
91
+ )
92
+
93
+ @pages = horizontal_box {
94
+ stretchy false
95
+
96
+ button("<") { stretchy true }
97
+ button("<") {
98
+ stretchy true
99
+
100
+ on_clicked do
101
+ @current_page = [@current_page - 1, 1].max
102
+ @controller.refresh_data(@current_page, STUDENTS_PER_PAGE)
103
+ end
104
+
105
+ }
106
+ @page_label = label("...") { stretchy false }
107
+ button(">") { stretchy true }
108
+ button(">") {
109
+ stretchy true
110
+
111
+ on_clicked do
112
+ @current_page = [@current_page + 1, (@total_count / STUDENTS_PER_PAGE.to_f).ceil].min
113
+ @controller.refresh_data(@current_page, STUDENTS_PER_PAGE)
114
+ end
115
+ }
116
+ }
117
+ }
118
+
119
+ # Секция 3
120
+ vertical_box {
121
+ stretchy true
122
+
123
+ button('Добавить') {
124
+ stretchy false
125
+
126
+ on_clicked {
127
+ @controller.show_modal_add
128
+ }
129
+ }
130
+ button('Изменить') {
131
+ stretchy false
132
+
133
+ on_clicked {
134
+ @controller.show_modal_edit(@current_page, STUDENTS_PER_PAGE, @table.selection) unless @table.selection.nil?
135
+ }
136
+ }
137
+ button('Удалить') {
138
+ stretchy false
139
+
140
+ on_clicked {
141
+ @controller.delete_selected(@current_page, STUDENTS_PER_PAGE, @table.selection) unless @table.selection.nil?
142
+ @controller.refresh_data(@current_page, STUDENTS_PER_PAGE)
143
+ }
144
+ }
145
+ button('Обновить') { stretchy false }
146
+ }
147
+ }
148
+ on_create
149
+ root
150
+ end
151
+
152
+ end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: mvcStudentXD
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.0
4
+ version: 1.0.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - papaSquid
@@ -23,8 +23,32 @@ files:
23
23
  - Gemfile
24
24
  - README.md
25
25
  - Rakefile
26
+ - lib/Converter.rb
27
+ - lib/Converter_json.rb
28
+ - lib/Converter_txt.rb
29
+ - lib/Converter_yaml.rb
30
+ - lib/Data_list.rb
31
+ - lib/Data_list_student_short.rb
32
+ - lib/Data_table.rb
33
+ - lib/Student.rb
34
+ - lib/StudentBase.rb
35
+ - lib/Student_list.rb
36
+ - lib/Student_short.rb
37
+ - lib/database/scripts/create_table.sql
38
+ - lib/database/scripts/insert_data.sql
39
+ - lib/database/student_list_db.rb
40
+ - lib/database/students_db.rb
41
+ - lib/main.rb
42
+ - lib/main_window.rb
26
43
  - lib/mvcStudentXD.rb
27
44
  - lib/mvcStudentXD/version.rb
45
+ - lib/student_edit_form_controller.rb
46
+ - lib/student_input_form.rb
47
+ - lib/student_input_form_controller.rb
48
+ - lib/student_list_adapter.rb
49
+ - lib/student_list_adv.rb
50
+ - lib/student_list_controller.rb
51
+ - lib/tab_students.rb
28
52
  - sig/mvcStudentXD.rbs
29
53
  homepage: https://github.com/KiTTeNqz/mvcStudentXD
30
54
  licenses: