tin_can_api 0.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (63) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +24 -0
  3. data/.rspec +2 -0
  4. data/Gemfile +4 -0
  5. data/LICENSE.txt +22 -0
  6. data/README.md +80 -0
  7. data/Rakefile +12 -0
  8. data/lib/tin_can_api/about.rb +15 -0
  9. data/lib/tin_can_api/activity.rb +41 -0
  10. data/lib/tin_can_api/activity_definition.rb +139 -0
  11. data/lib/tin_can_api/agent.rb +44 -0
  12. data/lib/tin_can_api/agent_account.rb +33 -0
  13. data/lib/tin_can_api/attachment.rb +64 -0
  14. data/lib/tin_can_api/client.rb +402 -0
  15. data/lib/tin_can_api/context.rb +54 -0
  16. data/lib/tin_can_api/context_activities.rb +102 -0
  17. data/lib/tin_can_api/documents/activity_profile_document.rb +15 -0
  18. data/lib/tin_can_api/documents/agent_profile_document.rb +15 -0
  19. data/lib/tin_can_api/documents/document.rb +20 -0
  20. data/lib/tin_can_api/documents/state_document.rb +15 -0
  21. data/lib/tin_can_api/enum.rb +42 -0
  22. data/lib/tin_can_api/errors.rb +9 -0
  23. data/lib/tin_can_api/group.rb +37 -0
  24. data/lib/tin_can_api/interaction_component.rb +32 -0
  25. data/lib/tin_can_api/interaction_type.rb +58 -0
  26. data/lib/tin_can_api/lrs_response.rb +14 -0
  27. data/lib/tin_can_api/query_result_format.rb +6 -0
  28. data/lib/tin_can_api/remote_lrs.rb +15 -0
  29. data/lib/tin_can_api/result.rb +45 -0
  30. data/lib/tin_can_api/score.rb +39 -0
  31. data/lib/tin_can_api/statement.rb +53 -0
  32. data/lib/tin_can_api/statement_ref.rb +31 -0
  33. data/lib/tin_can_api/statements/statements_base.rb +70 -0
  34. data/lib/tin_can_api/statements_query.rb +42 -0
  35. data/lib/tin_can_api/statements_query_v095.rb +42 -0
  36. data/lib/tin_can_api/statements_result.rb +17 -0
  37. data/lib/tin_can_api/sub_statement.rb +19 -0
  38. data/lib/tin_can_api/tcapi_version.rb +27 -0
  39. data/lib/tin_can_api/verb.rb +35 -0
  40. data/lib/tin_can_api/version.rb +4 -0
  41. data/lib/tin_can_api.rb +37 -0
  42. data/spec/fixtures/about.json +10 -0
  43. data/spec/fixtures/statement.json +33 -0
  44. data/spec/spec_helper.rb +106 -0
  45. data/spec/support/helpers.rb +43 -0
  46. data/spec/tin_can_api/activity_definition_spec.rb +37 -0
  47. data/spec/tin_can_api/activity_spec.rb +23 -0
  48. data/spec/tin_can_api/agent_account_spec.rb +13 -0
  49. data/spec/tin_can_api/agent_spec.rb +24 -0
  50. data/spec/tin_can_api/attachment_spec.rb +26 -0
  51. data/spec/tin_can_api/client_spec.rb +44 -0
  52. data/spec/tin_can_api/context_activities_spec.rb +57 -0
  53. data/spec/tin_can_api/context_spec.rb +32 -0
  54. data/spec/tin_can_api/group_spec.rb +15 -0
  55. data/spec/tin_can_api/interaction_component_spec.rb +18 -0
  56. data/spec/tin_can_api/result_spec.rb +26 -0
  57. data/spec/tin_can_api/score_spec.rb +12 -0
  58. data/spec/tin_can_api/statement_ref_spec.rb +19 -0
  59. data/spec/tin_can_api/statement_spec.rb +57 -0
  60. data/spec/tin_can_api/sub_statement_spec.rb +30 -0
  61. data/spec/tin_can_api/verb_spec.rb +17 -0
  62. data/tin_can_api.gemspec +30 -0
  63. metadata +238 -0
@@ -0,0 +1,37 @@
1
+ # encoding: utf-8
2
+ module TinCanApi
3
+ # Group model class
4
+ class Group < Agent
5
+
6
+ attr_accessor :members
7
+
8
+ def initialize(options={}, &block)
9
+ super(options, &block)
10
+
11
+ @object_type = 'Group'
12
+ @members = []
13
+ json = options.fetch(:json, nil)
14
+ if json
15
+ attributes = JSON.parse(json)
16
+ attributes['member'].each do |member|
17
+ members << Agent.new(json: member.to_json)
18
+ end
19
+ else
20
+ self.members = options.fetch(:members, nil)
21
+
22
+ if block_given?
23
+ block[self]
24
+ end
25
+ end
26
+ end
27
+
28
+ def serialize(version)
29
+ node = super(version)
30
+ if members.any?
31
+ node['member'] = members.map {|member| member.serialize(version)}
32
+ end
33
+ node
34
+ end
35
+
36
+ end
37
+ end
@@ -0,0 +1,32 @@
1
+ # encoding: utf-8
2
+ module TinCanApi
3
+ # InteractionComponent Class Description
4
+ class InteractionComponent
5
+
6
+ attr_accessor :id, :description
7
+
8
+ def initialize(options={}, &block)
9
+ json = options.fetch(:json, nil)
10
+ if json
11
+ attributes = JSON.parse(json)
12
+ self.id = attributes['id'] if attributes['id']
13
+ self.description = attributes['description'] if attributes['description']
14
+ else
15
+ self.id = options.fetch(:id, nil)
16
+ self.description = options.fetch(:description, nil)
17
+
18
+ if block_given?
19
+ block[self]
20
+ end
21
+ end
22
+ end
23
+
24
+ def serialize(version)
25
+ node = {}
26
+ node['id'] = id if id
27
+ node['description'] = description if description
28
+ node
29
+ end
30
+
31
+ end
32
+ end
@@ -0,0 +1,58 @@
1
+ # encoding: utf-8
2
+ module TinCanApi
3
+ # Possible interaction types
4
+ module InteractionType
5
+
6
+ CHOICE = {
7
+ to_s: 'choice',
8
+ get_value: proc{'choice'}
9
+ }
10
+
11
+ SEQUENCING = {
12
+ to_s: 'sequencing',
13
+ get_value: proc{'sequencing'}
14
+ }
15
+
16
+ LIKERT = {
17
+ to_s: 'likert',
18
+ get_value: proc{'likert'}
19
+ }
20
+
21
+ MATCHING = {
22
+ to_s: 'matching',
23
+ get_value: proc{'matching'}
24
+ }
25
+
26
+ PERFORMANCE = {
27
+ to_s: 'performance',
28
+ get_value: proc{'performance'}
29
+ }
30
+
31
+ TRUE_FALSE = {
32
+ to_s: 'true-false',
33
+ get_value: proc{'true-false'}
34
+ }
35
+
36
+ FILL_IN = {
37
+ to_s: 'fill-in',
38
+ get_value: proc{'fill-in'}
39
+ }
40
+
41
+ NUMERIC = {
42
+ to_s: 'numeric',
43
+ get_value: proc{'numeric'}
44
+ }
45
+
46
+ OTHER = {
47
+ to_s: 'other',
48
+ get_value: proc{'other'}
49
+ }
50
+
51
+ def type_by_string(type)
52
+ values.select{|v| v.to_s == type}.first
53
+ end
54
+
55
+ extend TinCanApi::Enum
56
+
57
+ end
58
+ end
@@ -0,0 +1,14 @@
1
+ # encoding: utf-8
2
+ module TinCanApi
3
+ class LrsResponse
4
+ attr_accessor :success, :error_message, :content, :status
5
+
6
+ def initialize(&block)
7
+ if block_given?
8
+ block[self]
9
+ end
10
+ end
11
+
12
+
13
+ end
14
+ end
@@ -0,0 +1,6 @@
1
+ # encoding: utf-8
2
+ module TinCanApi
3
+ module QueryResultFormat
4
+
5
+ end
6
+ end
@@ -0,0 +1,15 @@
1
+ # encoding: utf-8
2
+ require 'tin_can_api/tcapi_version'
3
+ module TinCanApi
4
+ # Class used to communicate with a TCAPI endpoint synchronously
5
+ class RemoteLRS
6
+ include TinCanApi::TCAPIVersion
7
+
8
+ attr_accessor :end_point, :user_name, :password, :version
9
+
10
+ def initialize(version=V101)
11
+ @version = version
12
+ end
13
+
14
+ end
15
+ end
@@ -0,0 +1,45 @@
1
+ # encoding: utf-8
2
+ require 'ruby-duration'
3
+ module TinCanApi
4
+ # Result Model class
5
+ class Result
6
+
7
+ attr_accessor :score, :success, :completion, :duration, :response, :extensions
8
+
9
+ def initialize(options={}, &block)
10
+ json = options.fetch(:json, nil)
11
+ if json
12
+ attributes = JSON.parse(json)
13
+ self.score = TinCanApi::Score.new(json: attributes['score'].to_json) if attributes['score']
14
+ self.success = attributes['success'] if attributes['success']
15
+ self.completion = attributes['completion'] if attributes['completion']
16
+ self.duration = Duration.new(attributes['duration']) if attributes['duration']
17
+ self.response = attributes['response'] if attributes['response']
18
+ self.extensions = attributes['extensions'] if attributes['extensions']
19
+ else
20
+ self.score = options.fetch(:score, nil)
21
+ self.success = options.fetch(:success, nil)
22
+ self.completion = options.fetch(:completion, nil)
23
+ self.duration = options.fetch(:duration, nil)
24
+ self.response = options.fetch(:response, nil)
25
+ self.extensions = options.fetch(:extensions, nil)
26
+
27
+ if block_given?
28
+ block[self]
29
+ end
30
+ end
31
+ end
32
+
33
+ def serialize(version)
34
+ node = {}
35
+ node['score'] = score.serialize(version) if score
36
+ node['success'] = success if success
37
+ node['completion'] = completion if completion
38
+ node['duration'] = duration.iso8601 if duration
39
+ node['response'] = response if response
40
+ node['extensions'] = extensions if extensions
41
+
42
+ node
43
+ end
44
+ end
45
+ end
@@ -0,0 +1,39 @@
1
+ # encoding: utf-8
2
+ module TinCanApi
3
+ # Score model class
4
+ class Score
5
+
6
+ attr_accessor :scaled, :raw, :min, :max
7
+
8
+ def initialize(options={}, &block)
9
+ json = options.fetch(:json, nil)
10
+ if json
11
+ attributes = JSON.parse(json)
12
+ self.scaled = attributes['scaled'] if attributes['scaled']
13
+ self.raw = attributes['raw'] if attributes['raw']
14
+ self.min = attributes['min'] if attributes['min']
15
+ self.max = attributes['max'] if attributes['max']
16
+ else
17
+ self.scaled = options.fetch(:scaled, nil)
18
+ self.raw = options.fetch(:raw, nil)
19
+ self.min = options.fetch(:min, nil)
20
+ self.max = options.fetch(:max, nil)
21
+
22
+ if block_given?
23
+ block[self]
24
+ end
25
+ end
26
+
27
+ end
28
+
29
+ def serialize(version)
30
+ node = {}
31
+ node['scaled'] = scaled if scaled
32
+ node['raw'] = raw if raw
33
+ node['min'] = min if min
34
+ node['max'] = max if max
35
+ node
36
+ end
37
+
38
+ end
39
+ end
@@ -0,0 +1,53 @@
1
+ # encoding: utf-8
2
+ module TinCanApi
3
+ # Statement Class
4
+ class Statement < Statements::StatementsBase
5
+
6
+ attr_accessor :id, :stored, :authority, :version, :voided
7
+
8
+ def initialize(options={}, &block)
9
+ super(options, &block)
10
+ json = options.fetch(:json, nil)
11
+ if json
12
+ attributes = JSON.parse(json)
13
+ self.id = attributes['id'] if attributes['id']
14
+ self.stored = Time.parse(attributes['stored']) if attributes['stored']
15
+ self.authority = TinCanApi::Agent.new(json: attributes['authority'].to_json) if attributes['authority']
16
+ self.version = attributes['version'] if attributes['version']
17
+ self.voided = attributes['voided'] if attributes['voided']
18
+ else
19
+ self.id = options.fetch(:id, nil)
20
+ self.stored = options.fetch(:stored, nil)
21
+ self.authority = options.fetch(:authority, nil)
22
+ self.version = options.fetch(:version, nil)
23
+ self.voided = options.fetch(:voided, nil)
24
+
25
+ if block_given?
26
+ block[self]
27
+ end
28
+ end
29
+ end
30
+
31
+ def serialize(version)
32
+ node = super(version)
33
+
34
+ node['id'] = id if id
35
+ node['stored'] = stored.strftime('%FT%T%:z') if stored
36
+ node['authority'] = authority.serialize(version) if authority
37
+
38
+ if version == TinCanApi::TCAPIVersion::V095
39
+ node['voided'] = voided if voided
40
+ end
41
+
42
+ if version.ordinal <= TinCanApi::TCAPIVersion::V100.ordinal
43
+ node['version'] = version.to_s if version
44
+ end
45
+ node
46
+ end
47
+
48
+ def stamp
49
+ @id = SecureRandom.uuid
50
+ @timestamp = Time.now
51
+ end
52
+ end
53
+ end
@@ -0,0 +1,31 @@
1
+ # encoding: utf-8
2
+ module TinCanApi
3
+ # StatementRef Class used when referencing another statement from a statement's object property
4
+ class StatementRef
5
+
6
+ attr_accessor :object_type, :id
7
+
8
+ def initialize(options={}, &block)
9
+ @object_type = 'StatementRef'
10
+ json = options.fetch(:json, nil)
11
+ if json
12
+ attributes = JSON.parse(json)
13
+ self.id = attributes['id'] if attributes['id']
14
+ else
15
+ self.id = options.fetch(:id, nil)
16
+
17
+ if block_given?
18
+ block[self]
19
+ end
20
+ end
21
+ end
22
+
23
+ def serialize(version)
24
+ node = {}
25
+ node['id'] = id if id
26
+ node['objectType'] = object_type
27
+ node
28
+ end
29
+
30
+ end
31
+ end
@@ -0,0 +1,70 @@
1
+ # encoding: utf-8
2
+ module TinCanApi
3
+ module Statements
4
+ class StatementsBase
5
+
6
+ attr_accessor :actor, :verb, :object, :result, :context, :timestamp, :attachments, :voided
7
+
8
+ def initialize(options={}, &block)
9
+ @attachments = []
10
+ json = options.fetch(:json, nil)
11
+ if json
12
+ attributes = JSON.parse(json)
13
+ self.actor = TinCanApi::Agent.new(json: attributes['actor'].to_json) if attributes['actor']
14
+ self.verb = TinCanApi::Verb.new(json: attributes['verb'].to_json) if attributes['verb']
15
+ object_node = attributes['object']
16
+ if object_node
17
+ case object_node['objectType']
18
+ when 'Group', 'Agent'
19
+ self.object = TinCanApi::Agent.new(json: object_node.to_json)
20
+ when 'StatementRef'
21
+ self.object = TinCanApi::StatementRef.new(json: object_node.to_json)
22
+ when 'SubStatement'
23
+ self.object = TinCanApi::SubStatement.new(json: object_node.to_json)
24
+ else
25
+ self.object = TinCanApi::Activity.new(json: object_node.to_json)
26
+ end
27
+ end
28
+ self.result = TinCanApi::Result.new(json: attributes['result'].to_json) if attributes['result']
29
+ self.context = TinCanApi::Context.new(json: attributes['context'].to_json) if attributes['context']
30
+ self.timestamp = Time.parse(attributes['timestamp']) if attributes['timestamp']
31
+ self.voided = attributes['voided'] if attributes['voided']
32
+ if attributes['attachments']
33
+ attributes['attachments'].each do |attachment|
34
+ attachments << TinCanApi::Attachment.new(json: attachment.to_json)
35
+ end
36
+ end
37
+ else
38
+ self.actor = options.fetch(:actor, nil)
39
+ self.verb = options.fetch(:verb, nil)
40
+ self.object = options.fetch(:object, nil)
41
+ self.result = options.fetch(:result, nil)
42
+ self.context = options.fetch(:context, nil)
43
+ self.timestamp = options.fetch(:timestamp, nil)
44
+ self.attachments = options.fetch(:attachments, nil)
45
+ self.voided = options.fetch(:voided, nil)
46
+
47
+ if block_given?
48
+ block[self]
49
+ end
50
+ end
51
+ end
52
+
53
+ def serialize(version)
54
+ node = {}
55
+ node['actor'] = actor.serialize(version)
56
+ node['verb'] = verb.serialize(version)
57
+ node['object'] = object.serialize(version)
58
+ node['result'] = result.serialize(version) if result
59
+ node['context'] = context.serialize(version) if context
60
+ node['timestamp'] = timestamp.strftime('%FT%T%:z') if timestamp
61
+ if version.ordinal <= TinCanApi::TCAPIVersion::V100.ordinal
62
+ if attachments && attachments.any?
63
+ node['attachments'] = attachments.map {|element| element.serialize(version)}
64
+ end
65
+ end
66
+ node
67
+ end
68
+ end
69
+ end
70
+ end
@@ -0,0 +1,42 @@
1
+ # encoding: utf-8
2
+ module TinCanApi
3
+ class StatementsQuery
4
+
5
+ attr_reader :version, :verb_id
6
+ attr_accessor :agent, :activity_id, :registration, :related_activities, :related_agents
7
+ attr_accessor :stored_since, :stored_until, :limit, :format, :ascending
8
+
9
+ def initialize(&block)
10
+ self.version = TCAPIVersion::V101
11
+ if block_given?
12
+ block[self]
13
+ end
14
+ end
15
+
16
+ def verb_id=(value)
17
+ if value.is_a?(Verb)
18
+ @verb_id = value.id
19
+ else
20
+ @verb_id = Addressable::URI.parse(value)
21
+ end
22
+ end
23
+
24
+ def parameter_map
25
+ params = {}
26
+ params['agent'] = agent.serialize(version) if agent
27
+ params['verb'] = verb_id.to_s if verb_id
28
+ params['activity'] = activity_id.to_s if activity_id
29
+ params['registration'] = registration if registration
30
+ params['related_activities'] = related_activities if related_activities
31
+ params['related_agents'] = related_agents if related_agents
32
+ params['since'] = stored_since.strftime('%FT%T%:z') if stored_since
33
+ params['until'] = stored_until.strftime('%FT%T%:z') if stored_until
34
+ params['limit'] = limit if limit
35
+ params['format'] = format if format
36
+ params['ascending'] = ascending if ascending
37
+
38
+ params
39
+ end
40
+
41
+ end
42
+ end
@@ -0,0 +1,42 @@
1
+ # encoding: utf-8
2
+ module TinCanApi
3
+ class StatementsQueryV095
4
+
5
+ attr_reader :version, :verb_id
6
+ attr_accessor :object, :registration, :context, :actor, :stored_since, :stored_until, :limit
7
+ attr_accessor :authoritative, :sparse, :instructor, :ascending
8
+
9
+ def initialize(&block)
10
+ self.version = TCAPIVersion::V095
11
+ if block_given?
12
+ block[self]
13
+ end
14
+ end
15
+
16
+ def verb_id=(value)
17
+ if value.is_a?(Verb)
18
+ @verb_id = value.id
19
+ else
20
+ @verb_id = Addressable::URI.parse(value)
21
+ end
22
+ end
23
+
24
+ def parameter_map
25
+ params = {}
26
+ params['verb'] = verb_id.to_s if verb_id
27
+ params['object'] = object.serialize(version) if object
28
+ params['registration'] = registration if registration
29
+ params['context'] = context if context
30
+ params['actor'] = actor if actor
31
+ params['since'] = stored_since.strftime('%FT%T%:z') if stored_since
32
+ params['until'] = stored_until.strftime('%FT%T%:z') if stored_until
33
+ params['limit'] = limit if limit
34
+ params['authoritative'] = authoritative if authoritative
35
+ params['sparse'] = sparse if sparse
36
+ params['instructor'] = instructor.serialize(version) if instructor
37
+ params['ascending'] = ascending if ascending
38
+
39
+ params
40
+ end
41
+ end
42
+ end
@@ -0,0 +1,17 @@
1
+ # encoding: utf-8
2
+ module TinCanApi
3
+ # Statements result model class, returned by LRS calls to get multiple statements
4
+ class StatementsResult
5
+
6
+ attr_accessor :statements, :more_url
7
+
8
+ def initialize(options={})
9
+ json = options.fetch(:json, nil)
10
+ self.statements = []
11
+ if json
12
+ self.statements = json['statements'].map {|statement| Statement.new(json: statement)} if json['statements']
13
+ self.more_url = json['more'] if json['more']
14
+ end
15
+ end
16
+ end
17
+ end
@@ -0,0 +1,19 @@
1
+ # encoding: utf-8
2
+ module TinCanApi
3
+ class SubStatement < Statements::StatementsBase
4
+
5
+ attr_accessor :object_type
6
+
7
+ def initialize(options={}, &block)
8
+ @object_type = 'SubStatement'
9
+ super(options, &block)
10
+ end
11
+
12
+ def serialize(version)
13
+ node = super(version)
14
+ node['objectType'] = object_type
15
+ node
16
+ end
17
+
18
+ end
19
+ end
@@ -0,0 +1,27 @@
1
+ # encoding: utf-8
2
+ module TinCanApi
3
+ module TCAPIVersion
4
+
5
+ V101 = {
6
+ to_s: '1.0.1',
7
+ get_value: proc{'1.0.1'}
8
+ }
9
+
10
+ V100 = {
11
+ to_s: '1.0.0',
12
+ get_value: proc{'1.0.0'}
13
+ }
14
+
15
+ V095 = {
16
+ to_s: '0.95',
17
+ get_value: proc{'0.95'}
18
+ }
19
+
20
+ def latest_version
21
+ V101
22
+ end
23
+
24
+ extend TinCanApi::Enum
25
+
26
+ end
27
+ end
@@ -0,0 +1,35 @@
1
+ # encoding: utf-8
2
+ module TinCanApi
3
+ class Verb
4
+
5
+ attr_accessor :id, :display
6
+
7
+ def initialize(options={}, &block)
8
+ json = options.fetch(:json, nil)
9
+ if json
10
+ attributes = JSON.parse(json)
11
+ self.id = attributes['id'] if attributes['id']
12
+ self.display = attributes['display'] if attributes['display']
13
+ else
14
+ self.id = options.fetch(:id, nil)
15
+ self.display = options.fetch(:display, nil)
16
+
17
+ if block_given?
18
+ block[self]
19
+ end
20
+ end
21
+ end
22
+
23
+ def id=(value)
24
+ @id = Addressable::URI.parse(value) if value
25
+ end
26
+
27
+ def serialize(version)
28
+ node = {}
29
+ node['id'] = id.to_s if id
30
+ node['display'] = display if display
31
+ node
32
+ end
33
+
34
+ end
35
+ end
@@ -0,0 +1,4 @@
1
+ # encoding: utf-8
2
+ module TinCanApi
3
+ VERSION = "0.0.1"
4
+ end
@@ -0,0 +1,37 @@
1
+ # encoding: utf-8
2
+ require 'tin_can_api/errors'
3
+ require 'tin_can_api/enum'
4
+ require 'tin_can_api/version'
5
+ require 'tin_can_api/interaction_type'
6
+ require 'tin_can_api/about'
7
+ require 'tin_can_api/agent_account'
8
+ require 'tin_can_api/agent'
9
+ require 'tin_can_api/group'
10
+ require 'tin_can_api/verb'
11
+ require 'tin_can_api/interaction_component'
12
+ require 'tin_can_api/documents/document'
13
+ require 'tin_can_api/score'
14
+ require 'tin_can_api/result'
15
+ require 'tin_can_api/attachment'
16
+ require 'tin_can_api/activity_definition'
17
+ require 'tin_can_api/activity'
18
+ require 'tin_can_api/context_activities'
19
+ require 'tin_can_api/context'
20
+ require 'tin_can_api/statements/statements_base'
21
+ require 'tin_can_api/statement'
22
+ require 'tin_can_api/sub_statement'
23
+ require 'tin_can_api/statement_ref'
24
+ require 'tin_can_api/statements_query'
25
+ require 'tin_can_api/statements_query_v095'
26
+ require 'tin_can_api/lrs_response'
27
+ require "tin_can_api/remote_lrs"
28
+ require 'tin_can_api/client'
29
+
30
+ begin
31
+ require 'pry'
32
+ rescue LoadError
33
+ end
34
+
35
+ module TinCanApi
36
+ # Your code goes here...
37
+ end
@@ -0,0 +1,10 @@
1
+ {
2
+ "extensions" : {
3
+ "http://id.tincanapi.com/extension/powered-by" : {
4
+ "name" : "Tin Can Engine",
5
+ "homePage" : "http://tincanapi.com/lrs-lms/lrs-for-lmss-home/",
6
+ "version" : "2012.1.0.8c644"
7
+ }
8
+ },
9
+ "version" : [ "0.9", "0.95", "1.0.1" ]
10
+ }
@@ -0,0 +1,33 @@
1
+ {
2
+ "id": "06a6cbbb-b09c-4618-88a8-e8aa6884ad42",
3
+ "actor": {
4
+ "mbox": "mailto:tincanruby@tincanapi.com",
5
+ "objectType": "Agent"
6
+ },
7
+ "verb": {
8
+ "id": "http://adlnet.gov/expapi/verbs/experienced",
9
+ "display": {
10
+ "en-GB": "experienced",
11
+ "en-US": "experienced"
12
+ }
13
+ },
14
+ "timestamp": "2015-03-27T13:14:42.081Z",
15
+ "stored": "2015-03-27T13:14:42.081Z",
16
+ "authority": {
17
+ "account": {
18
+ "homePage": "http://example.com/",
19
+ "name": "ABCDEFGHI"
20
+ },
21
+ "objectType": "Agent"
22
+ },
23
+ "version": "1.0.1",
24
+ "object": {
25
+ "id": "http://tincanapi.com/TinCanRuby/Test/Unit/0",
26
+ "definition": {
27
+ "name": {"en-US": "TinCanJava Tests: Unit 0"},
28
+ "description": {"en-US": "Unit test 0 in the test suite for the Tin Can Ruby library."},
29
+ "type": "http://id.tincanapi.com/activitytype/unit-test"
30
+ },
31
+ "objectType": "Activity"
32
+ }
33
+ }