todolist_project 1.0.0

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.
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 6d593e00021e6fa21566e654914f42d39fa66a2f
4
+ data.tar.gz: 6da49642516223bcbed99225602223f647409c6b
5
+ SHA512:
6
+ metadata.gz: e2179c3ee5d89990ec69363ef7bbd82f946d9601e7c889fa79bd27c593fe214b5ba12ffb900fecabe069b59cd24febc938b1fbad03f9051fcf16e909c0969fc9
7
+ data.tar.gz: af6cbdffb2da4538d1c5db111b2c68556cfa07799626453ab86ebc4abe236e957809c941ad99f78462a3d147a62efa78ee6a0584c0668c1223f81709acc966f4
@@ -0,0 +1,152 @@
1
+ # This class represents a todo item and its associated
2
+ # data: name and description. There's also a "done"
3
+ # flag to show whether this todo item is done.
4
+ require 'bundler/setup'
5
+ require 'stamp'
6
+
7
+ class Todo
8
+ DONE_MARKER = 'X'
9
+ UNDONE_MARKER = ' '
10
+
11
+ attr_accessor :title, :description, :done, :due_date
12
+
13
+ def initialize(title, description='')
14
+ @title = title
15
+ @description = description
16
+ @done = false
17
+ end
18
+
19
+ def done!
20
+ self.done = true
21
+ end
22
+
23
+ def done?
24
+ done
25
+ end
26
+
27
+ def undone!
28
+ self.done = false
29
+ end
30
+
31
+ def to_s # replaces original #to_s method
32
+ result = "[#{done? ? DONE_MARKER : UNDONE_MARKER}] #{title}"
33
+ result += due_date.stamp(' (Due: Friday January 6)') if due_date
34
+ result
35
+ end
36
+ end
37
+
38
+ # This class represents a collection of Todo objects.
39
+ # You can perform typical collection-oriented actions
40
+ # on a TodoList object, including iteration and selection.
41
+
42
+ class TodoList
43
+ attr_accessor :title
44
+
45
+ def initialize(title)
46
+ @title = title
47
+ @todos = []
48
+ end
49
+
50
+ def size
51
+ @todos.size
52
+ end
53
+
54
+ def first
55
+ @todos.first
56
+ end
57
+
58
+ def last
59
+ @todos.last
60
+ end
61
+
62
+ def shift
63
+ @todos.shift
64
+ end
65
+
66
+ def pop
67
+ @todos.pop
68
+ end
69
+
70
+ def done?
71
+ @todos.all? { |todo| todo.done? }
72
+ end
73
+
74
+ def <<(todo)
75
+ raise TypeError, 'can only add Todo objects' unless todo.instance_of? Todo
76
+
77
+ @todos << todo
78
+ end
79
+ alias_method :add, :<<
80
+
81
+ def item_at(idx)
82
+ @todos.fetch(idx)
83
+ end
84
+
85
+ def mark_done_at(idx)
86
+ item_at(idx).done!
87
+ end
88
+
89
+ def mark_undone_at(idx)
90
+ item_at(idx).undone!
91
+ end
92
+
93
+ def done!
94
+ @todos.each_index do |idx|
95
+ mark_done_at(idx)
96
+ end
97
+ end
98
+
99
+ def remove_at(idx)
100
+ @todos.delete(item_at(idx))
101
+ end
102
+
103
+ def to_s
104
+ text = "---- #{title} ----\n"
105
+ text << @todos.map(&:to_s).join("\n")
106
+ text
107
+ end
108
+
109
+ def to_a
110
+ @todos
111
+ end
112
+
113
+ def each
114
+ @todos.each do |todo|
115
+ yield(todo)
116
+ end
117
+ self
118
+ end
119
+
120
+ def select
121
+ list = TodoList.new(title)
122
+ each do |todo|
123
+ list.add(todo) if yield(todo)
124
+ end
125
+ list
126
+ end
127
+
128
+ # returns first Todo by title, or nil if no match
129
+ def find_by_title(title)
130
+ select { |todo| todo.title == title }.first
131
+ end
132
+
133
+ def all_done
134
+ select { |todo| todo.done? }
135
+ end
136
+
137
+ def all_not_done
138
+ select { |todo| !todo.done? }
139
+ end
140
+
141
+ def mark_done(title)
142
+ find_by_title(title) && find_by_title(title).done!
143
+ end
144
+
145
+ def mark_all_done
146
+ each { |todo| todo.done! }
147
+ end
148
+
149
+ def mark_all_undone
150
+ each { |todo| todo.undone! }
151
+ end
152
+ end
@@ -0,0 +1,183 @@
1
+ require 'bundler/setup'
2
+ require 'date'
3
+ require 'minitest/autorun'
4
+ require 'minitest/reporters'
5
+ Minitest::Reporters.use!
6
+
7
+ require_relative '../lib/todolist_project'
8
+
9
+ class TodoListTest < MiniTest::Test
10
+ def setup
11
+ @todo1 = Todo.new('Buy milk')
12
+ @todo2 = Todo.new('Clean room')
13
+ @todo3 = Todo.new('Go to gym')
14
+ @todos = [@todo1, @todo2, @todo3]
15
+
16
+ @list = TodoList.new("Today's Todos")
17
+ @list.add(@todo1)
18
+ @list.add(@todo2)
19
+ @list.add(@todo3)
20
+ end
21
+
22
+ def test_to_a
23
+ assert_equal(@todos, @list.to_a)
24
+ end
25
+
26
+ def test_add_raise_error
27
+ assert_raises(TypeError) { @list.add(1) }
28
+ assert_raises(TypeError) { @list.add('hi') }
29
+ end
30
+
31
+ def test_add_alias
32
+ new_todo = Todo.new('Walk the dog')
33
+ @list.add(new_todo)
34
+ todos = @todos << new_todo
35
+
36
+ assert_equal(todos, @list.to_a)
37
+ end
38
+
39
+ def test_size
40
+ assert_equal(3, @list.size)
41
+ end
42
+
43
+ def test_first
44
+ assert_equal(@todo1, @list.first)
45
+ end
46
+
47
+ def test_last
48
+ assert_equal(@todo3, @list.last)
49
+ end
50
+
51
+ def test_shift
52
+ todo = @list.shift
53
+ assert_equal(@todo1, todo)
54
+ assert_equal([@todo2, @todo3], @list.to_a)
55
+ end
56
+
57
+ def test_pop
58
+ todo = @list.pop
59
+ assert_equal(@todo3, todo)
60
+ assert_equal([@todo1, @todo2], @list.to_a)
61
+ end
62
+
63
+ def test_done_question
64
+ assert_equal(false, @list.done?)
65
+ end
66
+
67
+ def test_item_at
68
+ assert_raises(IndexError) { @list.item_at(100) }
69
+ assert_equal(@todo1, @list.item_at(0))
70
+ assert_equal(@todo2, @list.item_at(1))
71
+ end
72
+
73
+ def test_mark_done_at
74
+ assert_raises(IndexError) { @list.mark_done_at(100) }
75
+ @list.mark_done_at(1)
76
+ assert_equal(false, @todo1.done?)
77
+ assert_equal(true, @todo2.done?)
78
+ assert_equal(false, @todo3.done?)
79
+ end
80
+
81
+ def test_mark_undone_at
82
+ assert_raises(IndexError) { @list.mark_undone_at(100) }
83
+ @todo1.done!
84
+ @todo2.done!
85
+ @todo3.done!
86
+
87
+ @list.mark_undone_at(1)
88
+
89
+ assert_equal(true, @todo1.done?)
90
+ assert_equal(false, @todo2.done?)
91
+ assert_equal(true, @todo3.done?)
92
+ end
93
+
94
+ def test_done_bang
95
+ @list.done!
96
+ assert_equal(true, @todo1.done?)
97
+ assert_equal(true, @todo2.done?)
98
+ assert_equal(true, @todo3.done?)
99
+ assert_equal(true, @list.done?)
100
+ end
101
+
102
+ def test_remove_at
103
+ assert_raises(IndexError) { @list.remove_at(100) }
104
+ @list.remove_at(1)
105
+ assert_equal([@todo1, @todo3], @list.to_a)
106
+ end
107
+
108
+ def test_to_s
109
+ output = <<-OUTPUT.chomp.gsub(/^\s+/, '')
110
+ ---- Today's Todos ----
111
+ [ ] Buy milk
112
+ [ ] Clean room
113
+ [ ] Go to gym
114
+ OUTPUT
115
+
116
+ assert_equal(output, @list.to_s)
117
+ end
118
+
119
+ def test_to_s_2
120
+ output = <<-OUTPUT.chomp.gsub(/^\s+/, '')
121
+ ---- Today's Todos ----
122
+ [ ] Buy milk
123
+ [X] Clean room
124
+ [ ] Go to gym
125
+ OUTPUT
126
+
127
+ @list.mark_done_at(1)
128
+ assert_equal(output, @list.to_s)
129
+ end
130
+
131
+ def test_to_s_3
132
+ output = <<-OUTPUT.chomp.gsub(/^\s+/, '')
133
+ ---- Today's Todos ----
134
+ [X] Buy milk
135
+ [X] Clean room
136
+ [X] Go to gym
137
+ OUTPUT
138
+
139
+ @list.done!
140
+ assert_equal(output, @list.to_s)
141
+ end
142
+
143
+ def test_each
144
+ result = []
145
+ @list.each { |todo| result << todo }
146
+ assert_equal([@todo1, @todo2, @todo3], result)
147
+ end
148
+
149
+ def test_each_returns_original_list
150
+ assert_equal(@list, @list.each {|todo| nil })
151
+ end
152
+
153
+ def test_select
154
+ @todo1.done!
155
+ list = TodoList.new(@list.title)
156
+ list.add(@todo1)
157
+
158
+ assert_equal(list.title, @list.title)
159
+ assert_equal(list.to_s, @list.select{ |todo| todo.done? }.to_s)
160
+ end
161
+
162
+ def test_no_due_date
163
+ assert_nil(@todo1.due_date)
164
+ end
165
+
166
+ def test_due_date
167
+ due_date = Date.today + 3
168
+ @todo2.due_date = due_date
169
+ assert(@todo2.due_date, due_date)
170
+ end
171
+
172
+ def test_to_s_with_due_date
173
+ @todo2.due_date = Date.new(2017, 4, 15)
174
+ output = <<-OUTPUT.chomp.gsub(/^\s+/, '')
175
+ ---- Today's Todos ----
176
+ [ ] Buy milk
177
+ [ ] Clean room (Due: Saturday April 15)
178
+ [ ] Go to gym
179
+ OUTPUT
180
+
181
+ assert_equal(output, @list.to_s)
182
+ end
183
+ end
metadata ADDED
@@ -0,0 +1,44 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: todolist_project
3
+ version: !ruby/object:Gem::Version
4
+ version: 1.0.0
5
+ platform: ruby
6
+ authors:
7
+ - Pete Williams
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2017-04-01 00:00:00.000000000 Z
12
+ dependencies: []
13
+ description: This is a simple todo list manager!
14
+ email: pw@example.com
15
+ executables: []
16
+ extensions: []
17
+ extra_rdoc_files: []
18
+ files:
19
+ - lib/todolist_project.rb
20
+ - test/todolist_project_test.rb
21
+ homepage: http://example.com/todolist_project
22
+ licenses: []
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
+ rubyforge_project:
40
+ rubygems_version: 2.6.7
41
+ signing_key:
42
+ specification_version: 4
43
+ summary: Todo List Manager!
44
+ test_files: []