untis 1.0.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (3) hide show
  1. checksums.yaml +7 -0
  2. data/lib/untis.rb +347 -0
  3. metadata +43 -0
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA256:
3
+ metadata.gz: 8a74e98496d1dba08aae22dab8e48a803b61be6cc2c633ab2e9b57aec423a95e
4
+ data.tar.gz: 27ef6140d9ca1c9716372c84770549e7e4f352a0962c004d31e1ae7c89e6b332
5
+ SHA512:
6
+ metadata.gz: 9d96ccd0094f044bb70424c1163e75a0d80d1e047451d7c5a45b4108f54c147c82a217685fb9a042e24291390c136342603390feb1e7ee3d76b30495b7aa08ce
7
+ data.tar.gz: eb0c1b0cd868fe9daa2ae7d48396c545fbf935dbbe36d54c8873a0a08fc06f75023a49b4cfc93c5560448bc8c86df16469b2ffbe8473a7616bcb1582d43223f4
@@ -0,0 +1,347 @@
1
+ require 'net/http'
2
+ require 'securerandom'
3
+ require 'json'
4
+ require 'date'
5
+
6
+ class UntisWorker
7
+ attr_accessor :login, :password, :client_id,
8
+ :session_id, :person_id, :person_type,
9
+ :api_base_url, :school_name, :school_name_url,
10
+ :api_url, :api_url_base, :api_version,
11
+ :api_version_sv
12
+
13
+ def initialize(**args)
14
+ @login = args[:login]
15
+ @password = args[:password]
16
+ @client_id = args[:client_id] || self.generate_client_id
17
+ @session_id = args[:session_id]
18
+ @person_id = args[:person_id]
19
+ @person_type = args[:person_type]
20
+ @api_base_url = args[:api_base_url] || "https://kephiso.webuntis.com/WebUntis"
21
+ @school_name = args[:school_name] || "Example School"
22
+ @school_name_url = URI::escape @school_name.gsub(/\s/, '+')
23
+ @api_url_base = URI "#{@api_base_url}/jsonrpc.do"
24
+ @api_url = URI "#{@api_base_url}/jsonrpc.do?school=#{@school_name_url}"
25
+ @api_version = '2.0'
26
+ @api_version_sv = @api_version
27
+ end
28
+
29
+ def generate_client_id
30
+ "UW-#{SecureRandom.hex}"
31
+ end
32
+
33
+ def generate_id
34
+ SecureRandom.hex
35
+ end
36
+
37
+ private
38
+
39
+ def build_fields(**args)
40
+ { 'id' => generate_id, 'jsonrpc' => @api_version, 'method' => args[:method], 'params' => args[:params].delete_if do |k, v| v.nil? end }
41
+ end
42
+
43
+ def post(url, data)
44
+ response = nil
45
+
46
+ data.delete_if do |k, v|
47
+ v.nil?
48
+ end
49
+
50
+ begin
51
+ if @session_id.nil?
52
+ response = Net::HTTP.post url, data.to_json, 'Content-Type' => 'application/json'
53
+ else
54
+ response = Net::HTTP.post url, data.to_json, 'Content-Type' => 'application/json', 'Cookie' => "JSESSIONID=#{@session_id}"
55
+ end
56
+ rescue
57
+ puts 'Request failed!'
58
+ sleep 1
59
+ puts 'Retrying...'
60
+ return post url, data
61
+ end
62
+
63
+ response_data = JSON.parse response.body
64
+
65
+ # Catch non-auth
66
+ if response_data['error'] && (response_data['error']['code'] == -8520 || response_data['error']['message'] == 'not authenticated')
67
+ puts 'Request failed, authentication expired! Re-Authing...'
68
+ sleep 0.25
69
+ authenticate!
70
+ sleep 1
71
+ puts 'Retrying...'
72
+ return post url, data
73
+ end
74
+
75
+ response_data
76
+ end
77
+
78
+ public
79
+
80
+ def date_from_str(date_str)
81
+ Date::strptime date_str, '%Y%m%d'
82
+ end
83
+
84
+ def date_to_str(date)
85
+ date.strftime '%Y%m%d'
86
+ end
87
+
88
+ def time_from_str(time_str)
89
+ Time::strptime time_str, '%H%M'
90
+ end
91
+
92
+ def time_to_str(time)
93
+ time.strftime '%H%M'
94
+ end
95
+
96
+ def authenticate!
97
+ result = post @api_url, build_fields(
98
+ method: 'authenticate',
99
+ params: {
100
+ 'user' => @login,
101
+ 'password' => @password,
102
+ 'client' => @client_id
103
+ }
104
+ )
105
+
106
+ if result['result']
107
+ puts 'Auth OK!'
108
+
109
+ @session_id = result['result']['sessionId']
110
+ @person_type = result['result']['personType']
111
+ @person_id = result['result']['personId']
112
+ @api_version_sv = result['jsonrpc']
113
+ else
114
+ puts 'Auth error!'
115
+ puts result['error']['message']
116
+ end
117
+
118
+ result
119
+ end
120
+
121
+ def get_teachers
122
+ post @api_url, build_fields(
123
+ method: 'getTeachers',
124
+ params: []
125
+ )
126
+ end
127
+
128
+ def get_students
129
+ post @api_url, build_fields(
130
+ method: 'getStudents',
131
+ params: []
132
+ )
133
+ end
134
+
135
+ def get_classes(**args)
136
+ post @api_url, build_fields(
137
+ method: 'getKlassen',
138
+ params: {
139
+ schoolyearId: args[:school_year] || args[:year] || args[:schoolyearId] || args[:school_year_id]
140
+ }
141
+ )
142
+ end
143
+
144
+ def get_subjects
145
+ post @api_url, build_fields(
146
+ method: 'getSubjects',
147
+ params: []
148
+ )
149
+ end
150
+
151
+ def get_rooms
152
+ post @api_url, build_fields(
153
+ method: 'getRooms',
154
+ params: []
155
+ )
156
+ end
157
+
158
+ def get_departments
159
+ post @api_url, build_fields(
160
+ method: 'getDepartments',
161
+ params: []
162
+ )
163
+ end
164
+
165
+ def get_holidays
166
+ post @api_url, build_fields(
167
+ method: 'getHolidays',
168
+ params: []
169
+ )
170
+ end
171
+
172
+ def get_timegrid
173
+ post @api_url, build_fields(
174
+ method: 'getTimegridUnits',
175
+ params: []
176
+ )
177
+ end
178
+
179
+ def get_status_data
180
+ post @api_url, build_fields(
181
+ method: 'getStatusData',
182
+ params: []
183
+ )
184
+ end
185
+
186
+ def get_current_school_year
187
+ post @api_url, build_fields(
188
+ method: 'getCurrentSchoolyear',
189
+ params: []
190
+ )
191
+ end
192
+
193
+ def get_school_years
194
+ post @api_url, build_fields(
195
+ method: 'getSchoolyears',
196
+ params: []
197
+ )
198
+ end
199
+
200
+ def get_timetable(**args)
201
+ if args[:options].nil?
202
+ post @api_url, build_fields(
203
+ method: 'getTimetable',
204
+ params: {
205
+ id: args[:id],
206
+ type: args[:type],
207
+ startDate: date_to_str(args[:start_date] || args[:startDate]),
208
+ endDate: date_to_str(args[:end_date] || args[:endDate])
209
+ }
210
+ )
211
+ else
212
+ opts = args[:options]
213
+
214
+ post @api_url, build_fields(
215
+ method: 'getTimetable',
216
+ params: {
217
+ options: {
218
+ element: {
219
+ id: opts[:element][:id],
220
+ type: opts[:element][:type],
221
+ keyType: opts[:element][:key_type] || opts[:element][:keyType] || 'id'
222
+ },
223
+ startDate: date_to_str(opts[:start_date] || opts[:startDate] || Date.today),
224
+ endDate: date_to_str(opts[:end_date] || opts[:endDate] || Date.today),
225
+ onlyBaseTimetable: opts[:only_base_timetable] || opts[:onlyBaseTimetable] || false,
226
+ showBooking: opts[:show_booking] || opts[:showBooking] || false,
227
+ showInfo: opts[:show_info] || opts[:showInfo] || false,
228
+ showSubstText: opts[:show_subst_text] || opts[:showSubstText] || false,
229
+ showLsText: opts[:show_ls_text] || opts[:showLsText] || false,
230
+ showStudentgroup: opts[:show_student_group] || opts[:showStudentgroup] || false,
231
+ klasseFields: opts[:class_fields] || opts[:klasseFields],
232
+ roomFields: opts[:room_fields] || opts[:roomFields],
233
+ subjectFields: opts[:subject_fields] || opts[:subjectFields],
234
+ teacherFields: opts[:teacher_fields] || opts[:teacherFields]
235
+ }
236
+ }
237
+ )
238
+ end
239
+ end
240
+
241
+ def get_latest_import_time
242
+ post @api_url, build_fields(
243
+ method: 'getLatestImportTime',
244
+ params: []
245
+ )
246
+ end
247
+
248
+ def get_person_id(**args)
249
+ post @api_url, build_fields(
250
+ method: 'getPersonId',
251
+ params: {
252
+ type: args[:type] || 5,
253
+ sn: args[:sn] || args[:surname] || args[:last_name],
254
+ fn: args[:fn] || args[:forename] || args[:name] || args[:first_name],
255
+ dob: args[:dob] || args[:birthday] || args[:birth_date] || 0,
256
+ }
257
+ )
258
+ end
259
+
260
+ def get_substitutions(**args)
261
+ post @api_url, build_fields(
262
+ method: 'getSubstitutions',
263
+ params: {
264
+ endDate: date_to_str(args[:end_date] || args[:endDate]),
265
+ startDate: date_to_str(args[:start_date] || args[:startDate]),
266
+ departmentId: args[:department_id] || args[:departmentId] || 0,
267
+ }
268
+ )
269
+ end
270
+
271
+ def get_class_reg_events(**args)
272
+ post @api_url, build_fields(
273
+ method: 'getClassregEvents',
274
+ params: {
275
+ endDate: args[:end_date] || args[:endDate],
276
+ startDate: args[:start_date] || args[:startDate],
277
+ }
278
+ )
279
+ end
280
+
281
+ def get_exams(**args)
282
+ post @api_url, build_fields(
283
+ method: 'getExams',
284
+ params: {
285
+ endDate: args[:end_date] || args[:endDate],
286
+ startDate: args[:start_date] || args[:startDate],
287
+ examTypeId: args[:exam_type_id] || args[:exam_type] || args[:examTypeId] || args[:exam_id]
288
+ }
289
+ )
290
+ end
291
+
292
+ def get_exam_types
293
+ post @api_url, build_fields(
294
+ method: 'getExamTypes',
295
+ params: []
296
+ )
297
+ end
298
+
299
+ def get_timetable_with_absences(**args)
300
+ opts = args[:options] || args
301
+
302
+ post @api_url, build_fields(
303
+ method: 'getTimetableWithAbsences',
304
+ params: {
305
+ options: {
306
+ endDate: opts[:end_date] || opts[:endDate],
307
+ startDate: opts[:start_date] || opts[:startDate]
308
+ }
309
+ }
310
+ )
311
+ end
312
+
313
+ def get_class_reg_categories
314
+ post @api_url, build_fields(
315
+ method: 'getClassregCategories',
316
+ params: []
317
+ )
318
+ end
319
+
320
+ def get_class_reg_category_groups
321
+ post @api_url, build_fields(
322
+ method: 'getClassregCategoryGroups',
323
+ params: []
324
+ )
325
+ end
326
+
327
+ def get_class_reg_events_for_element(**args)
328
+ opts = args[:options] || args
329
+
330
+ opts[:element] = {} if opts[:element].nil?
331
+
332
+ post @api_url, build_fields(
333
+ method: 'getClassregEvents',
334
+ params: {
335
+ options: {
336
+ endDate: opts[:end_date] || opts[:endDate],
337
+ startDate: opts[:start_date] || opts[:startDate],
338
+ element: {
339
+ id: opts[:element][:id],
340
+ type: opts[:element][:type],
341
+ keyType: opts[:element][:keyType] || opts[:element][:key_type] || 'id',
342
+ }
343
+ }
344
+ }
345
+ )
346
+ end
347
+ end
metadata ADDED
@@ -0,0 +1,43 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: untis
3
+ version: !ruby/object:Gem::Version
4
+ version: 1.0.1
5
+ platform: ruby
6
+ authors:
7
+ - Meow the Cat
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2019-05-07 00:00:00.000000000 Z
12
+ dependencies: []
13
+ description: WebUntis Timetable Management system wrapper for Ruby.
14
+ email: meowdakat@gmail.com
15
+ executables: []
16
+ extensions: []
17
+ extra_rdoc_files: []
18
+ files:
19
+ - lib/untis.rb
20
+ homepage: https://github.com/Meow/untis
21
+ licenses:
22
+ - MIT
23
+ metadata: {}
24
+ post_install_message:
25
+ rdoc_options: []
26
+ require_paths:
27
+ - lib
28
+ required_ruby_version: !ruby/object:Gem::Requirement
29
+ requirements:
30
+ - - ">="
31
+ - !ruby/object:Gem::Version
32
+ version: '0'
33
+ required_rubygems_version: !ruby/object:Gem::Requirement
34
+ requirements:
35
+ - - ">="
36
+ - !ruby/object:Gem::Version
37
+ version: '0'
38
+ requirements: []
39
+ rubygems_version: 3.0.3
40
+ signing_key:
41
+ specification_version: 4
42
+ summary: Untis Timetable system wrapper.
43
+ test_files: []