Python calling documentation of defined function - python-2.7

I am a newbie to python. Just try to get the comments defined in function using doc but getting the error.
Here's my code:
def nam(i):
"""passing the name to
a function"""
print('hello '+i+' good mornin')
And here's the error:
Traceback (most recent call last):
File "<pyshell#2>", line 1, in <module>
print(nam._doc_)
AttributeError: 'function' object has no attribute '_doc_'

Replace _doc_ (single underline on each side) with __doc__ (double underlines)
To illustrate, let's define your function and display the documentation:
>>> def nam(i):
... """passing the name to
... a function"""
... print('hello '+i+' good mornin')
...
>>> nam.__doc__
'passing the name to\n a function'
The method above works. The method below, however, fails:
>>> nam._doc_
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
AttributeError: 'function' object has no attribute '_doc_'
The reason is that __doc__ needs two underline characters on each side, not just one.
Documentation
From the python online documentation:
docstring A string literal which appears as the first expression
in a class, function or module. While ignored when the suite is
executed, it is recognized by the compiler and put into the __doc__
attribute of the enclosing class, function or module. Since it is
available via introspection, it is the canonical place for
documentation of the object.

Related

Why isdigit is working but isdecimal is not for a simple age code

This is the part of code I am talking about:
while True:
print 'What is your age(only numeric):'
age = raw_input()
if age.isdigit():
break
print 'Please try again. We take only numeric value.'
When I replace isdigit with isdecimal, I get this error no matter what value i enter.
Traceback (most recent call last):
File "test.py", line 4, in <module>
if age.isdecimal():
AttributeError: 'str' object has no attribute 'isdecimal'
Although it runs fine with isdigit.
Also, when I replace raw_input with input, it give this error.
Traceback (most recent call last):
File "test.py", line 4, in <module>
if age.isdigit():
AttributeError: 'int' object has no attribute 'isdigit'
Am I doing something wrong which I am not able to catch? I am new to python and did my research about isdigit, is decimal, input and raw_input before putting down question here. It may be very minute error but I am not sure what is it.
For the first part:
In Python 2, isdecimal is a method of the unicode class, not of str (i.e. bytes). Hence:
>>> '3.2'.isdecimal()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
AttributeError: 'str' object has no attribute 'isdecimal'
>>> u'3.2'.isdecimal()
For the second part, input tries to guess what kind of input it gets, and will properly cast "1" into an int, while raw_input will always return the raw string. Since isdigit is a method defined in the str class, you get the error.

Retrieve stack trace in django Middleware

How can I get the stack trace when something fails on the server side in the django middleware?
Here is what I've tried that only gives me the message, not the full stack.
class MonitorMiddleware(object):
def process_exception(self, request, exception):
self.error = exception.message
Answer to "retrieve the error stack trace to save to the database" from comment:
https://docs.python.org/3/library/traceback.html
Use the methods of traceback to convert the trace of the exception into a string which you can then store in the database.
Also on the above page:
New in version 3.5.
StackSummary objects represent a call stack ready for formatting.
The short short example with an exception object:
>>> an_error = IndexError('tuple index out of range')
>>> traceback.print_exception(type(an_error), an_error, an_error.__traceback__)
Traceback (most recent call last):
File "<stdin>", line 2, in <module>
IndexError: list index out of range
See also Extract traceback info from an exception object:
You don't need to re-raise the exception, though, the traceback is in the __traceback__ attribute.

Is there a reason `tolist()` can't operate on a list?

I often think it would be nice to have the following work even if the original object is a list... Is there a reason why this functionality is not implemented (in python 2.7)?
Example:
>>> a = [1,2,3,4]
>>> a.tolist()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
AttributeError: 'list' object has no attribute 'tolist'

Formatting error reporting

I am logging all errors to a file, since there is no other way to see them properly in my case, especially in prod environment. Like this:
sys.stderr = open('py/log/my_logfile.error.log', 'a')
I am getting something similar to this:
Traceback (most recent call last):
File "my_awesome_file.py", line 50, in <module>
revision = session.Query()
AttributeError: 'Awesome' object has no attribute 'SomeSortOfAttribute'
Traceback (most recent call last):
File "my_awesome_file.py", line 50, in <module>
revision = session.Query()
AttributeError: 'Awesome' object has no attribute 'SomeSortOfAttribute'
It's two errors here (well, same error logged twice). I'd like to have if formatted a bit nicer (i.e. additional newline in between errors), and add a datetime if possible. Can I do it using this method of error logging?
After a little bit of reading Python manuals, it seems the solution is rather easy - instead of directly using file open() as a stream for stderr, I just have to use a custom stream. It's so painfully obvious it puzzles me why I didn't come up with it immediately. Well, it was Friday evening after all.
A very basic version would be:
import time
class LogStream(object):
def write(self, text):
f = open('py/log/my.custom.error.log', 'a')
f.write(time.strftime("%H:%M:%S ") + text + "\r\n")
f.close()
And then
sys.stderr = LogStream()
Result:
12:03:05 Traceback (most recent call last):
12:03:05 File "py/stuff.py", line 38, in <module>
12:03:05
12:03:05 raise Exception("just some test")
12:03:05 Exception
12:03:05 :
12:03:05 just some test
12:03:05
I might want to customize it a bit more but it's good enough already.

Django-Adaptors TypeError: "delimiter" must be an 1-character string

I am getting an error when trying to import some data into my model. The error I'm getting is TypeError: complaining about the delimiter I'm using.
Below is my model for the CSV import, I am using the default delimiter suggested by the documentation.
class SkuCsvModel(CsvModel):
sku_num = models.CharField()
sku_category = models.ForeignKey(SkuCategory)
short_desc = models.CharField()
class Meta:
delimiter = ";"
dbModel = Sku
The CSV file I'm trying to use is below:
1365400;9;3/8 BALL VALVE
1401901;9;BRASS ELBOW
1406300;9;HOSE BARB, NPT
The code I'm testing in the manage.py shell is:
>>> from core.models import SkuCsvModel
>>> my_csv_list = SkuCsvModel.import_data(data = open("labconco.csv"))
And finally the error I'm getting is:
Traceback (most recent call last):
File "<console>", line 1, in <module>
File "E:\bin\Python27\lib\site-packages\adaptor\model.py", line 197, in import_data
return importer.import_data(data)
File "E:\bin\Python27\lib\site-packages\adaptor\model.py", line 466, in import_data
for line in csv.reader(data, delimiter=self.delimiter):
TypeError: "delimiter" must be an 1-character string
So I've been fiddling around with the django-adaptor tools, and this error is coming from the import_data() method of the CsvImporter, when I try and put a delimiter directly into the csv.reader(data, delimiter=';') this works fine and I'm able to see the file correctly. But no matter how I try and enter this import_data method sending in a ';' will generate an error.
Look at the snippet below. If I provide an integer as a delimiter, it fails with the same exception as in your example. If I provide a semicolon as a delimiter to csv.reader it works. This is basically what is done in model.CsvImporter.import_data() as you already found out.
>>> import csv
>>> import StringIO
>>> io = StringIO.StringIO('name;surname\nsascha;gottfried')
>>> for line in csv.reader(io, delimiter=10):
... print line
...
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: "delimiter" must be an 1-character string
>>> for line in csv.reader(io, delimiter=';'):
... print line
...
['name', 'surname']
['sascha', 'gottfried']
To debug the situation dump the current value of 'self.delimiter' to the console or similar before it will be passed as a delimiter to csv.reader(). It must be a different value and/or type than ';'. Looking at the code of django-adaptors you can validate your django-adaptors model definition with this base class method as well to debug. This call should print out what you defined as Meta.delimiter.
>>> from core.models import SkuCsvModel
>>> SkuCsvModel.has_class_delimiter()
But it is pretty fine to omit a delimiter definition and call 'import_from_file' on the model. Make sure there is no class delimiter defined. If so the importer runs a CSV sniff to detect the delimiter from the file you passed. If you provide the file you mentioned, the sniffer will detect a ';' and sets self.delimiter.
>>> from core.models import SkuCsvModel
>>> SkuCsvModel.has_class_delimiter()
None
>>> my_csv_list = SkuCsvModel.import_from_file(file = open("labconco.csv"))