-
Notifications
You must be signed in to change notification settings - Fork 1
/
Copy pathconsole.py
executable file
·249 lines (222 loc) · 8.72 KB
/
console.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
#!/usr/bin/env python3
"""This is the entry point of the interprerter"""
import cmd
import re
from models.base_model import BaseModel
from models.user import User
from models.state import State
from models.city import City
from models.amenity import Amenity
from models.place import Place
from models.review import Review
from models import storage
from models.engine.file_storage import FileStorage
class HBNBCommand(cmd.Cmd):
"""Creates the command interpreter class"""
prompt = "(hbnb) "
valid_classes = ['BaseModel', 'User', 'State', 'City',
'Amenity', 'Place', 'Review']
# Basic instance methods
def emptyline(self):
"""Handles emptyline + ENTER from the interpreter"""
pass
# Instance do_*() methods
def do_quit(self, line):
"""
`quit` | `EOF`: command exits the program.
"""
return True
def do_EOF(self, line):
"""
`EOF` | `quit`: command exits the program.
"""
return True
def do_create(self, line):
"""
create <class>: creates a new instance of <class>, and saves the
new <class> instance into a JSON file, then prints/return the
instace id of new <class> instance.
valid <classes>: ['BaseModel', 'User', 'State', 'City',
'Amenity', 'Place', 'Review']
"""
argv = line.split()
if len(argv) == 0:
print("** class name missing **")
elif len(argv) >= 1 and argv[0] not in self.valid_classes:
print("** class doesn't exist **")
else:
obj = eval("{}()".format(argv[0]))
obj.save()
print(obj.id)
def do_show(self, line):
"""
show <class> <instance id>: Prints the string representation
of the instance with matching `instance id`.
valid <classes>: ['BaseModel', 'User', 'State', 'City',
'Amenity', 'Place', 'Review']
"""
argv = line.split()
if len(argv) == 0:
print("** class name missing **")
elif len(argv) >= 1 and argv[0] not in self.valid_classes:
print("** class doesn't exist **")
elif len(argv) == 1:
print("** instance id missing **")
else:
# print the string representation of the object
storage.reload()
objs = storage.all()
key = "{}.{}".format(argv[0], argv[1])
try:
obj = objs[key]
print(obj)
except KeyError:
print("** no instance found **")
def do_destroy(self, line):
"""
destroy <class> <instance id>: Destroy the object instance
of with the matching `instance id`.
valid <classes>: ['BaseModel', 'User', 'State', 'City',
'Amenity', 'Place', 'Review']
"""
argv = line.split()
if len(argv) == 0:
print("** class name missing **")
elif len(argv) >= 1 and argv[0] not in self.valid_classes:
print("** class doesn't exist **")
elif len(argv) == 1:
print("** instance id missing **")
else:
#
# Destroy macthing instance following these stages:
#
objs = storage.all()
key = "{}.{}".format(argv[0], argv[1])
try:
del objs[key]
storage.save()
except KeyError:
print("** no instance found **")
def do_all(self, line):
"""
all [class]: Prints a list containing string representation
of all instances in the storage path, optional `[class]` name
can be passed to print only a list of matching object with
the class.
valid <classes>: ['BaseModel', 'User', 'State', 'City',
'Amenity', 'Place', 'Review']
"""
argv = line.split()
if len(argv) >= 1 and argv[0] not in self.valid_classes:
print("** class doesn't exist **")
elif len(argv) >= 1 and argv[0] in self.valid_classes:
# Print a list containing only specified class objects
return_list = []
storage.reload()
objs = storage.all()
for key, obj in objs.items():
if key == ("" + argv[0] + "." + obj.__dict__["id"]):
return_list.append(obj.__str__())
print(return_list)
else:
# Print a list containing all class objects in storage
return_list = []
storage.reload()
objs = storage.all()
for key, obj in objs.items():
return_list.append(obj.__str__())
print(return_list)
def do_update(self, line):
"""
update <class> <instance id> <attribute name> <attribute value>:
Updates matching instance with a new or existing attribute.
valid <classes>: ['BaseModel', 'User', 'State', 'City',
'Amenity', 'Place', 'Review']
"""
argv = line.split()
if len(argv) == 0:
print("** class name missing **")
elif len(argv) >= 1 and argv[0] not in self.valid_classes:
print("** class doesn't exist **")
elif len(argv) == 1:
print("** instance id missing **")
elif len(argv) == 2:
print("** attribute name missing **")
elif len(argv) == 3:
print("** value missing **")
else:
# Update macthing instance while assuming:
# + arguments are always in the right order
# + Each arguments are separated by a space
# + String argument with a space must be between quotes
#
try:
storage.reload()
objs = storage.all()
key = "{}.{}".format(argv[0], argv[1])
obj = objs[key]
try:
Type = type(obj.__dict__[argv[2]])
obj.__dict__[argv[2]] = Type(argv[3].strip("\""))
except KeyError:
obj.__dict__[argv[2]] = argv[3].strip("\"")
obj.save()
except KeyError:
print("** no instance found **")
def parseline(self, line):
"""
Parse every line before returning it back to the console.
Looking out for match such as the following for extra
processing:
+ <class name>.all()
+ <class name>.count()
+ <class name>.show(<id>)
+ <class name>.destroy(<id>)
+ <class name>.update(<id>, <attribute name>, <attribute value>)
+ <class name>.update(<id>, <dictionary representation>)
"""
lone_commands = ['all', 'quit', 'EOF', 'help']
argv = line.split()
matched = re.search(r"\w+\.\w+\(", line)
if len(argv) == 0: # Handles empty line
return line, line, line
if (len(argv) != 1 or argv[0] in lone_commands) and not matched:
# Do for commands that required arguements or
# commands that works alone.
return argv[0], " ".join(argv[1:]), line
# Additional parsing for aliases listed in string doc.
# example: class.command(args)
if matched:
_class, argv = line.split(".", 1) # ['class', 'command(args)']
cmd, argv = argv.split("(", 1) # ['command', 'args)']
argv = argv.replace(")", '') # 'args)' -> 'args'
matched = re.search(r"{.+}", argv) # checking for dict definition
if matched: # if dictionary exists in arguements
objs = storage.all()
import json
obj_id, argv_dict = argv.split(", ", 1) # ['<id>', '<dict>']
argv_dict = argv_dict.replace("'", "\"")
obj_id = obj_id.replace("\"", "")
argv_dict = json.loads(argv_dict)
key = "{}.{}".format(_class, obj_id)
try:
obj = objs[key]
obj.__dict__.update(argv_dict)
obj.save()
except KeyError:
print("** no instance found **")
line = ""
return line, line, line
if cmd == "count": # handles <class>.count()
objs = storage.all()
count = 0
for key, obj in objs.items():
if obj.__class__.__name__ == _class:
count = count + 1
print(count)
line = ''
return line, line, line
return cmd, _class + " " + " ".join(argv.split(", ")), line
return argv[0], " ".join(argv[1:]), line
if __name__ == '__main__':
HBNBCommand().cmdloop()