How does one initialise a test database exactly as one wishes?

2016-02-12 Thread Vinay Sajip
I have a project (using Django 1.8) where I want to initialise a test 
database with some fixture data obtained from doing a manage.py dumpdata 
from a development instance of the database (with an identical schema to 
the test database). The fixture data contains *everything* in the source 
database, including e.g. stuff from the auth_permission and 
django_content_type tables. This causes integrity violations because the 
population of things like django_content_type is not deterministic, and the 
test database just after creation contains records in e.g. auth_permission 
and django_content_type tables. So, I wrote a custom test runner (based on 
DiscoverRunner) which overrides setup_databases() and, after calling the 
superclass to initialise the test database, I do a call_command('flush') 
with load_initial_data set to False and inhibit_post_migrate set to True. 
Following that, I do a call_command('loaddata') passing my fixture 
filename. However, the call_command('flush') does not appear to clear out 
the records, leading to the integrity violations I'm trying to avoid.

I broke out the debugger and stepped into the call_command('flush') call to 
see what was going on. It generated a list of DELETE FROM statements for 
*all* the tables, as expected. There was a loop executing those statements, 
and stepping over those execute() calls, no exceptions were raised. This is 
a SQLite3 database, and I was monitoring the contents of the tables using 
the SQLite manager client. On exit from the with transaction.atomic() which 
wrapped the DELETE FROM statements, the records are still in the tables! 
Can anyone tell me what's going on, or point to some other way of 
initialising a test database *completely* from a fixture file?

Regards,

Vinay Sajip

-- 
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to django-users+unsubscr...@googlegroups.com.
To post to this group, send email to django-users@googlegroups.com.
Visit this group at https://groups.google.com/group/django-users.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/django-users/d7880059-77b1-466f-9528-e6917d7b6390%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.


Re: Unintuitive behaviour of management commands with multiple databases

2016-02-02 Thread 'Vinay Sajip' via Django users
Dear Carl,

On Tuesday, February 2, 2016 at 7:51:20 PM UTC, Carl Meyer wrote:
>
>
> There's nothing wrong with connections[options.get('database')] if you 
> want to get a specific database connection object; that's public API and 
> you can use it. In the case of the built-in commands, that's useful 
>

OK, perhaps I misunderstood what you said in an earlier comment - I see you 
were talking against using the *internals* of the connection rather the 
connection itself.

because they need to do low-level things with the connection; I don't 
> think it helps you for regular ORM use. It doesn't allow changing the 
> default connection for ORM usage. Where the built-in management commands 
> do use the higher-level ORM, they use the public `using` APIs. 
>
 
That's fine for simple use, but it's not good have lots of using() calls 
for models when it's not a "real" multi-DB scenario,
 

> If you want to write a management command that has a --database option 
> like the built-in ones and makes heavy use of the ORM, you can a) 
> explicitly provide `using` where needed , b) use 
> django-dynamic-db-router, or c) hold your nose and monkeypatch 
> DEFAULT_DB_ALIAS, since it's just a one-shot management command and you 
> don't need to be as concerned about cleaning up after yourself. 
>
> Personally I would go for (a) or (b), depending on just how much I was 
> using the ORM in the management command. I'm not convinced that a fourth 
> (or third supported public) option is necessary here. If it's just a few 
> queries, you use `using`, if it's more than that and you want a broader 
> policy applied, you use a database router. 
>
 
OK, thanks for the suggestion - you've been very helpful, as always. I'll 
mull things over and see what's the best for the specifics of the specific 
project.

Regards,

Vinay Sajip

-- 
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to django-users+unsubscr...@googlegroups.com.
To post to this group, send email to django-users@googlegroups.com.
Visit this group at https://groups.google.com/group/django-users.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/django-users/832b093d-1d5a-4d24-9125-9eeb9297bbd0%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.


Re: Unintuitive behaviour of management commands with multiple databases

2016-02-02 Thread 'Vinay Sajip' via Django users
ed to database B, or more complex 
> schemes), and dynamically-scoped routing (such as that provided by 
> `in_database`) isn't as commonly needed. 
>

Agree, this is not a very common use case, 

Django provides the database router abstraction, which is a very 
> flexible system for implementing whatever kind of multi-db routing you 
> need. The burden of proof is heavy on any particular routing scheme to 
> demonstrate that it is so frequently needed that it should be bundled 
> with Django itself, rather than being a separate reusable package for 
> those who need it. 
>

I'm not arguing for any particular different routing scheme to be included 
- only for management commands to be able to be written to respect --data 
arguments passed to them, and which can easily treat the passed value as 
the default database to use just for that command invocation, when that 
value is different to whatever settings.DATABASES['default'] is. A quick 
look at the builtin management commands shows there's a lot of usage of 
connections[options.get('database')] going on, and yet externally written 
management commands aren't encouraged to use the same approach, and 
multiple settings files are the suggested alternative?

Regards,

Vinay Sajip

-- 
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to django-users+unsubscr...@googlegroups.com.
To post to this group, send email to django-users@googlegroups.com.
Visit this group at https://groups.google.com/group/django-users.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/django-users/887c16ac-e226-42a1-a102-4b48407ddad0%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.


Re: Unintuitive behaviour of management commands with multiple databases

2016-02-02 Thread 'Vinay Sajip' via Django users
Dear Carl,

On Tuesday, February 2, 2016 at 5:08:40 PM UTC, Carl Meyer wrote: 
>
> You can't (well, you might be able to by poking around in the internals 
> of the django.db.connections object, but I'd strongly advise against 
> that). The proper (and thread-safe) way to achieve the equivalent is to 
>

Well, for any given run of the application (on which the example I posted 
is based), only one database is ever used. The idea of multiple databases 
was to allow us to select which one is used for any particular Python 
process run, and we expected to be able to run management commands which 
would (based on a settings configuration) determine both which database to 
use and e.g. how to populate parts of it ready for deployment to particular 
customers. Oddly, setting django.db.utils.DEFAULT_DB_ALIAS = alias does the 
trick. Yes, I know that's a no-no, but it seems to me that for this kind of 
case where you don't need run-time routing, something like 
django-dynamic-db-router shouldn't really be needed, useful though it might 
be for the run-time routing case. Everything else works off the settings 
module, and the fact that Django caches the default database to use such 
that a management command can't change it seems like a design flaw. I 
suppose I was expecting transaction.atomic(using=XXX) to not just open a 
transaction on that database, but also make it the default for the scope of 
the block (except if explicitly overridden by using() for particular models 
in code called from that block). The current behaviour seems to violate the 
principle of least surprise (this my first encounter with multiple 
databases). Is there really no case for an in_database() context manager in 
Django itself? Though I would still expect that behaviour from 
transaction.atomic(), of course, but backwards compatibility is a 
constraint I'm aware of :-)

Regards,

Vinay Sajip

-- 
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to django-users+unsubscr...@googlegroups.com.
To post to this group, send email to django-users@googlegroups.com.
Visit this group at https://groups.google.com/group/django-users.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/django-users/66079ae6-f7e8-4771-acd0-30537bcb1c84%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.


Re: Unintuitive behaviour of management commands with multiple databases

2016-02-02 Thread 'Vinay Sajip' via Django users

On Tuesday, February 2, 2016 at 3:27:10 PM UTC, Carl Meyer wrote:
>
> Nothing in your code ever "overrides" settings.DATABASES['default']. 
>

Dear Carl,

Thanks for the quick response. I *had* thought of that, and tried adding 
the statement settings.DATABASES['default'] = settings.DATABASES[alias] 
just before the with block, and it had no effect - the result was the same 
- so I took it out. How else are you supposed to override the default 
database?

Regards,

Vinay Sajip

-- 
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to django-users+unsubscr...@googlegroups.com.
To post to this group, send email to django-users@googlegroups.com.
Visit this group at https://groups.google.com/group/django-users.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/django-users/39fea9af-584b-45e2-b8c8-dec665f0bd2e%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.


Unintuitive behaviour of management commands with multiple databases

2016-02-02 Thread 'Vinay Sajip' via Django users
I've set up a simple project using with two databases, foo and bar in 
settings.py:

DATABASES = {
'foo': {
'ENGINE': 'django.db.backends.sqlite3',
'NAME': os.path.join(BASE_DIR, 'foo.sqlite'),
},
'bar': {
'ENGINE': 'django.db.backends.sqlite3',
'NAME': os.path.join(BASE_DIR, 'bar.sqlite'),
}
}
DATABASES['default'] = DATABASES['foo']


I have a simple model:

class Thing(models.Model):
name = models.CharField(max_length=20, unique=True)

I have a simple management command:

class Command(BaseCommand):
help = 'Add all the things.'


def add_arguments(self, parser):
parser.add_argument('--database', nargs='?', metavar='DATABASE',
default='default',
help='Database alias to use')
parser.add_argument('things', nargs='+', metavar='THING',
help='Things to add')


def handle(self, *args, **options):
alias = options['database']
self.stdout.write('using alias %s' % alias)
with transaction.atomic(using=alias):
for name in options['things']:
try:
Thing.objects.create(name=name)
self.stdout.write('Added %s.\n' % name)
except IntegrityError as e:
self.stderr.write('Failed to add thing %r: %s' % (name, 
e))
break

After running migrations to set up the two databases, using python 
manage.py migrate --data foo and python manage.py migrate --data bar, I 
then run python manage.py add_things fizz buzz which results in two records 
being added to foo.sqlite, as expected. 

If I then run python manage.py add_things fizz buzz --data bar, it seems 
reasonable to expect it to add the records to bar.sqlite. However, this is 
not what happens: it tries to add them to foo.sqlite, even though I've 
specified using=alias with the alias set to bar. So I get a constraint 
violation:

using alias bar
Failed to add thing 'fizz': UNIQUE constraint failed: hello_thing.name

What have I overlooked? In a real case the atomic block might be 
manipulating lots of models in nested code, and I can't see that it's 
practical to call using() for every model. Somewhere, it looks like Django 
code is caching a connection based on what settings.DATABASES['default'] 
was when settings was imported, even though it is being overridden in the 
command line. If not actually a bug, this behaviour doesn't seem 
particularly intuitive, so any advice would be gratefully received.

Regards,

Vinay Sajip

-- 
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to django-users+unsubscr...@googlegroups.com.
To post to this group, send email to django-users@googlegroups.com.
Visit this group at https://groups.google.com/group/django-users.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/django-users/c61ddb5b-a5cb-460d-a109-b30ccd7d2a78%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.


Re: Meta-information for model and form fields

2009-01-31 Thread Vinay Sajip



On Jan 30, 1:36 am, Malcolm Tredinnick <malc...@pointy-stick.com>
wrote:
> On Wed, 2009-01-28 at 23:21 -0800, Vinay Sajip wrote:
>
> [...]
>
> > I was hoping there was another way. Of course subclassing's not hard
> > to do, but it means doing it for every field class. I was looking at
> > moving an application over from SQLAlchemy, which offers this feature
> > both for models and fields.
>
> That's not very natural Python behaviour, though. You can't expect to
> pass in extra arbitrary arguments to class constructors for normal
> Python classes and have them hold onto it for later collection.
>

I didn't find anything unusual about it. SQLAlchemy does this by
design [1], to allow users to attach additional meta-data, which the
SQLAlchemy team haven't thought of, to their tables and columns. In
the particular application I am looking at, this meta information is
used to control generation of test data and specific client-side UI
behaviour - it's not for the bread-and-butter case.

Their keyword arg is documented as

info – A dictionary which defaults to {}. A space to store application
specific data. This must be a dictionary.

This is available on both table and column abstractions. I certainly
found it a good way of attaching the information I needed, though of
course there are other ways it could have been done.

Regards,

Vinay

[1] 
http://www.sqlalchemy.org/docs/05/reference/sqlalchemy/schema.html#tables-and-columns

--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to 
django-users+unsubscr...@googlegroups.com
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



Re: Meta-information for model and form fields

2009-01-28 Thread Vinay Sajip


On Jan 29, 12:35 am, Malcolm Tredinnick <malc...@pointy-stick.com>
wrote:
> On Wed, 2009-01-28 at 04:27 -0800, Vinay Sajip wrote:
> > I'd like to attach some user-defined meta-information to individual
> > model fields and have it also be available in the corresponding form
> > fields. Ideally, I'd have liked to have a keyword arg on the fields...
>
> > class MyModel(models.Model):
> > name = models.CharField(max_length=100, info=some_object)
> > active = models.BooleanField(info=some_other_object)
>
> > Ideally, this information would be available in the corresponding form
> > field.
>
> > What's the best way of achieving this DRY-ly?
>
> Creating form and model field subclasses. You'll need to override the
> model field's __init__ method to handle the extra kwarg and the
> formfield() method.
>

I was hoping there was another way. Of course subclassing's not hard
to do, but it means doing it for every field class. I was looking at
moving an application over from SQLAlchemy, which offers this feature
both for models and fields.

Thanks,

Vinay Sajip
--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to 
django-users+unsubscr...@googlegroups.com
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



Meta-information for model and form fields

2009-01-28 Thread Vinay Sajip

I'd like to attach some user-defined meta-information to individual
model fields and have it also be available in the corresponding form
fields. Ideally, I'd have liked to have a keyword arg on the fields...

class MyModel(models.Model):
name = models.CharField(max_length=100, info=some_object)
active = models.BooleanField(info=some_other_object)

Ideally, this information would be available in the corresponding form
field.

What's the best way of achieving this DRY-ly?

Regards,

Vinay Sajip
--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to 
django-users+unsubscr...@googlegroups.com
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



Re: how to avoid hardcoding of logfile path in logging.conf file

2009-01-28 Thread Vinay Sajip



On Jan 28, 11:07 am, Rama Vadakattu <ramaakrish...@gmail.com> wrote:
> Thanks bruno desthuilliers
> the tip which you have given is working.
>

I think it's better just to have the logging configuration done at the
bottom of settings.py (either programmatically or via fileConfig).
Typically, if you have code in your apps which adds logging handlers,
and if your code gets imported more than once, you have to be careful
not to add handlers multiple times (otherwise your log messages get
emitted multiple times). Then, in your app modules, you only have to
use loggers:

import logging

logger = logging.getLogger(__name__) # name of module

...

logger.debug("A debug message")

...

Typically, you change logging configuration on a site-wide basis (e.g.
turning verbosity up and down for different apps in the site) so
settings.py is a reasonable place to keep this. Then individual apps
never need be concerned about where their logging output is going (in
fact they shouldn't hardcode this type of information, especially if
they are meant to be reusable).

Regards,

Vinay Sajip

--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to 
django-users+unsubscr...@googlegroups.com
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



Re: reportlab - filename of generated PDF

2009-01-26 Thread Vinay Sajip



On Jan 26, 7:59 am, Ivan Mincik <ivan.min...@gmail.com> wrote:
> Dear django users,
> we have a problem with filename of resulting PDF generated by reportlab and 
> then downloaded by browser.
>
> Generated PDF is OK, but filename is incorrect. It is allways something like 
> "randomstring.pdf.part". (for example sa34sdfasdf.pdf.part)
>
> in the "view.py" there are these lines:
> response = HttpResponse(mimetype='application/pdf')
> response['Content-Disposition'] = 'filename=gisplan.pdf'
>
> Please, can anybody see where can be the problem ?

It looks like a temporary filename generated by whatever is
downloading the file. For example, Firefox, while downloading, would
name the file "gisplan.pdf.part" and rename it to "gisplan.pdf" after
the download completed. If the downloader completed the download
(accounting for the OK PDF file) but failed to rename it, you might
get the result which you observed.

I use a slightly different content-disposition, indicating explicitly
that it's an attachment:

response['Content-Disposition'] = 'attachment; filename=gisplan.pdf'

With this approach, everything works as expected for me.

Regards,

Vinay Sajip
--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to 
django-users+unsubscr...@googlegroups.com
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



Re: PDF in Django (not via reportlab)

2008-09-15 Thread Vinay Sajip



On Sep 15, 12:53 pm, Bobo <[EMAIL PROTECTED]> wrote:
> Hi everyone,
>
> I'm looking for a smart and simple way to create a PDF document from a
> HTML page.
>
> I've a page with some tables that contains several numbers and I want
> my users to be able to create those tables into a PDF document they
> can send or download to their harddrive.
>
> In my search I found the documentation for the Django PDF via
> Reportlab but to be honest it seem way to advanced and complex
> compared to what I've in mind.
>
> I searched google and found some extern web-services that can create
> PDFs from a HTML page but they take money for it and I rather not be
> depending on another webservice. They might be down or have overload
> or something that can make problems.
>
> So my question is if anyone out there knows about a way to get around
> my little problem.
>
> Thanks in advance
> Bobo

Rather than a server-side solution, what about a client-side PDF
printer? PDFCreator is a free download for Windows clients, and on
Linux you should be able to set up a PDF printer under CUPS. See:

http://www.pdfforge.org/

http://www.linuxquestions.org/linux/answers/Applications_GUI_Multimedia/Setting_up_a_PDF_printer_in_CUPS_in_my_case_in_Slackware

Of course with a PDF printer you don't get full control of the PDF
produced. For better control, ReportLab is the ticket, and not as hard
as it looks - especially if you use the Platypus package.

Regards,

Vinay Sajip
--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



Re: ANN: Updated Django Cheat Sheet

2008-09-09 Thread Vinay Sajip



On Sep 4, 6:46 pm, Fraser Nevett <[EMAIL PROTECTED]> wrote:
> Thanks for all the feedback both on list and via email.
>
> Our plan is to wait a day or two to see if there are any further
> corrections required and then to release an updated edition early next
> week. At this time we'll also produce a alternative version which will
> be more suited for non-colour printing.
>

Nice cheat sheet. Hope it's not too late to offer a suggestion - it
would be useful to have the forloop special variables in the cheat
sheet. Not sure where you'll find room, though ;-)

Regards,

Vinay Sajip
--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



Re: Alternative approach to UserProfile

2007-05-27 Thread Vinay Sajip


On May 27, 4:45 pm, EL AATIFI Sidi Mohamed <[EMAIL PROTECTED]> wrote:

Another possibility is mentioned here:

http://groups.google.com/group/django-users/browse_thread/thread/324eb0c2283bd5/7ad65aeac8bb72ac?lnk=gst=__getattribute__=1#7ad65aeac8bb72ac

Whereby you can avoid user.get_profile().attr and use user.attr
instead.

Regards,

Vinay Sajip


--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



Re: Multiple Profiles

2007-05-27 Thread Vinay Sajip



On May 14, 10:15 am, Bram - Smartelectronix <[EMAIL PROTECTED]>
wrote:
> In my opinion there's only one easy solution which doesn't create
> ridiculous overhead and that is to be able to add fields to the User
> model without having to hack the actual code of the User model. Does
> anyone agree with this?

That'll probably be possible if and when we have a more generalized
framework for object inheritance - then you could inherit from the
User and add fields in the subclass.

Regards,

Vinay


--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



Re: Feisty-updates now contains Python-2.5.1final

2007-05-27 Thread Vinay Sajip


On May 27, 4:07 am, Mike Axiak <[EMAIL PROTECTED]> wrote:
> Yes, I'm sorry...let me be more clear:
>
> Feisty Fawn currently ships with Python 2.5.1c1.
> Python tried to change its API for dictionaries (which even broke
> pickle [1]) -- a change with which Django is not compatible [2].
> They decided to pull out this change for 2.5.1-final, and as of
> yesterday (5/25) Feisty-updates has 2.5.1-final.

Thanks for the update, Mike, but I can't seem to get this latest
version - the Python I can get is dated May 2:

[EMAIL PROTECTED]:~$ sudo apt-get update
[snip]
Get: 5 http://archive.ubuntu.com feisty-updates/main Packages [20.1kB]
Get: 6 http://archive.ubuntu.com feisty-updates/restricted Packages
[14B]
Get: 7 http://archive.ubuntu.com feisty-updates/main Sources [4974B]
Get: 8 http://archive.ubuntu.com feisty-updates/restricted Sources
[14B]
Fetched 57.8kB in 1s (40.4kB/s)
Reading package lists... Done
[EMAIL PROTECTED]:~$ sudo apt-get install python2.5
Reading package lists... Done
Building dependency tree
Reading state information... Done
python2.5 is already the newest version.
0 upgraded, 0 newly installed, 0 to remove and 0 not upgraded.
[EMAIL PROTECTED]:~$ python
Python 2.5.1 (r251:54863, May  2 2007, 16:56:35)
[GCC 4.1.2 (Ubuntu 4.1.2-0ubuntu4)] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>>

It's labelled Python 2.5.1, but are we talking about the same version?

Regards,

Vinay Sajip


--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



Re: Securing static files

2007-05-18 Thread Vinay Sajip


On May 18, 12:30 pm, Guyon Morée <[EMAIL PROTECTED]> wrote:
>
> I agree that would be nice, but wouldnt that mean that django is
> serving the files?
>

Not necessarily. The wrapper view could check permissions and issue a
redirect to the static site if the user has a right to see the image,
or render_to_response an error page otherwise. It's not ideal, since
the Django site is having to take a hit for every image request, but
it may be better than doing the image I/O from the Django site.
However, this approach is really not all that secure - in theory a
user could access the static site directly and try to guess filenames.
Also, would the static site be available to crawlers? The only sure-
fire way of providing security would seem to be to accept the cost of
handling the image I/O on the Django site.

Regards,

Vinay


--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



Discussion on urgently-looking-for-python-with-django-developers---london

2007-05-14 Thread Vinay Sajip

Are you looking for contract developers, permanent developers or
either?


--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



Re: Translation of class names

2007-05-12 Thread Vinay Sajip



On May 11, 4:20 pm, Maxim Bodyansky <[EMAIL PROTECTED]> wrote:
> Hmmm. It just works. And i18n for module names works too :)
> Many-many thanks, Ivan :)

Это не Иван, это - Vinay


--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



Re: Translation of class names

2007-05-11 Thread Vinay Sajip

On May 11, 2:44 pm, Malcolm Tredinnick <[EMAIL PROTECTED]>
wrote:

> it doesn't look too bad from a quick scan. So now is a good time to
> start getting real-world feedback and you guys can keep Vinay busy by
> finding all the problems with it. :-)

Yes indeed! I'm interested in any feedback, and particularly from
Joseph Kocherhans, whose ideas I used from an earlier patch to the
same ticket (#3591). If the patch works for you - please take the
trouble to feed that back to the list, too.

Regards,

Vinay Sajip


--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



Re: Translation of class names

2007-05-11 Thread Vinay Sajip



On May 11, 2:10 pm, Maximbo <[EMAIL PROTECTED]> wrote:
> > now i want modules to be called in russian.
>
> Are you want to translate name of module (app) or model (child of a
> models.Model class)? Is second case, you smoke a bamboo, because there
> is no way to use i18n with module names :( AFAIK

If you want to translate class names: use verbose_name and
verbose_name_plural attributes in a Meta class defined in your model
class.
For example:

class OrgUnit(models.Model):
code = models.CharField(_("code"), unique=True, maxlength=10)
name = models.CharField(_("name"), maxlength=100)

class Meta:
verbose_name = _("Organisation unit")

or

class Category(models.Model):
class Meta:
verbose_name_plural = _("Categories")

If you want to show the names of your Django apps in Russian (or any
other language), use this patch:

http://code.djangoproject.com/attachment/ticket/3591/app_labels.5.diff

Then, run make-messages.py, update the translations in the .po files,
run compile-messages.py and you should be able to show
internationalized app names and model class names.

Наилучшие пожелания (Regards),

Vinay Sajip



--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



Re: Multiple Profiles

2007-05-09 Thread Vinay Sajip



On May 9, 7:21 pm, Vinay Sajip <[EMAIL PROTECTED]> wrote:
> It appears not. Just to see if it would work, I tried just adding
> overriding __getattribute__ (which just calls the superclass
> behaviour) and it causes some unexpected behaviour in the unit tests.

False alarm - it was a typo on my part. How about this in
django.contrib.auth.User:

def __getattribute__(self, attrname):
if attrname == '_profile_cache':
return models.Model.__getattribute__(self, attrname)
try:
rv = models.Model.__getattribute__(self, attrname)
except AttributeError, e:
if not settings.AUTH_PROFILE_MODULE:
raise
try:
profile = self.get_profile()
rv = getattr(profile, attrname)
except SiteProfileNotAvailable:
raise e
return rv

This would appear to allow access to profile attributes directly on a
User instance, without the need to explicitly show ".get_profile()".

Regards,

Vinay Sajip


--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



Re: Multiple Profiles

2007-05-09 Thread Vinay Sajip



On May 9, 6:37 pm, Vinay Sajip <[EMAIL PROTECTED]> wrote:
> part of the user model. Is the intention just to avoid saying
> user.get_profile().xxx? Can't this be done by judiciously overriding
> __getattribute__ in User, to delegate to a profile if one is defined?

It appears not. Just to see if it would work, I tried just adding
overriding __getattribute__ (which just calls the superclass
behaviour) and it causes some unexpected behaviour in the unit tests.

Regards,

Vinay


--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



Re: Multiple Profiles

2007-05-09 Thread Vinay Sajip



On May 8, 2:57 pm, "Jeremy Dunck" <[EMAIL PROTECTED]> wrote:
> On 5/8/07, Amit Upadhyay <[EMAIL PROTECTED]> wrote:
>
> I'm having this issue currently as well-- an app I'm working on is
> heavily based on profiles and relations to it, so most code is
> constantly doing user.get_profile.something.
>
> However, consider that this alternate approach forces apps to be
> coupled within a project.
>
> I don't see a simple solution to this.  :-/

One simple problem with Amit's approach, as written, is that you have
to deal with "fuser" and "duser", which feels a little kludgy (I
realise he was just demonstrating the concept, but the problem still
remains that you want to think of all the profile information as just
part of the user model. Is the intention just to avoid saying
user.get_profile().xxx? Can't this be done by judiciously overriding
__getattribute__ in User, to delegate to a profile if one is defined?

Regards,

Vinay Sajip


--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



Re: ./manage loaddata (fixtures) problem with postgresql

2007-04-29 Thread Vinay Sajip



On Apr 29, 9:42 pm, Michel Thadeu Sabchuk <[EMAIL PROTECTED]> wrote:
> Sorry by the late response, I'm too busy these days. I try to load
> fixtures from xml data (instead of json data), I got the same error. I
> put a sample application for download on the following address:

I believe this is the same error as logged in ticket #3954, for which
a fix has been checked in (changeset #5102).

Regards,

Vinay Sajip


--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



Re: loaddata on User bug?

2007-04-26 Thread Vinay Sajip

On Apr 26, 10:49 pm, "[EMAIL PROTECTED]" <[EMAIL PROTECTED]>
wrote:
> I have dumped the User model on one db using dumpdata. I have a single
> json fixture file with one record (see below). When I run the loadata
> I get the error below. I use ptyhon 2.5 with psycopg2 on macOSX. I
> have tested on Ubuntu and I get a similar error. Is it a bug?
>

It's logged on the tracker - see

http://code.djangoproject.com/ticket/3954

The good news is, it's a one-line patch - there's a missing call to
disable_termcolors() in load_data().

Regards,

Vinay Sajip


--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



Re: Django performance and logging

2007-04-23 Thread Vinay Sajip


On Apr 8, 2:01 pm, "Deryck Hodge" <[EMAIL PROTECTED]> wrote:
> On 4/8/07, Vinay Sajip <[EMAIL PROTECTED]> wrote:
>
> I have a logger setup for use at work, and I control it via a
> LOG_LEVEL setting in settings.py.  I don't have logging statements
> throughout my code, only in things like the signal receiver that sends
> an email alert when a new object is created, so I don't notice any
> performance hit.  This is a subjective feeling, though, and not
> benchmarked.  I mainly use logging just to track that certain code
> paths are doing what I expect when run normally.
>
> I would think you would want it configurable, however, not automatic
> on debug.  We run development in DEBUG, which I assume is common, and
> that could generate noisy logs.  And what if I just wanted critical
> notices?  Changing a log level setting seems the right way to do this.

You can do this in settings.py - configure the root logger with a
level of logging.DEBUG (in a dev/test environment) and e.g.
logging.CRITICAL (in a production environment). If you don't do any
other configuration, all loggers will use the root logger's level by
default. If you want to turn on verbosity on specific loggers only,
even after going into production, you can change the settings to e.g.

logging.getLogger("my.app.module").setLevel(logging.DEBUG)

while leaving the root logger's level at logging.CRITICAL, say...then
you will turn up verbosity for that part of the app only, without
affecting other parts you're not interested in at the moment. And
because of the hierarchical setup, if you turn up the verbosity on
"my.app.module", you also do so on "my.app.module.submodule1",
"my.app.module.submodule2" etc.

> However, I know from talking to Adrian that he's not warm to the idea
> of logging in Django itself. :-)  And for understandable reasons.  It
> would be interesting to actually test the impact of a logger, though,
> just to know for sure.

Well, fair enough. I'm not sure what Adrian's reasons are, but I
suspect performance. Logging will obviously involve *some* overhead,
so there's always a trade-off to be made. As an initial exercise, I
added some very simple logging for SQL in django/db/backends/util.py,
which just logs the SQL and parameters using logger.debug(). In
settings.py, I configured logging. I ran an application from the shell
in three specific scenarios:

(a) Without the logging code in utils.py
(b) With the logging code in utils.py, and logging configured to use a
level of logging.DEBUG (so SQL would actually be logged)
(c) With the logging code in utils.py, and logging configured to use a
level of logging.INFO (so SQL would not be logged)

For each run, the application (migrating some legacy HR data into a
test sqlite database) saved around 4500 employee, 650 org unit and
5700 position model instances, twice over in each run. Now the
following is hardly a rigorous study (!), but it gives a rough idea:

No logging code in utils.py
===
Save employees #1: 79.3 secs
Save org units #1: 11.1 secs
Save positions #1: 104.4 secs
Save employees #2: 82.0 secs
Save org units #2: 12.1 secs
Save positions #2: 108.9 secs

Logging code in utils.py, logging configuration set to INFO (no actual
logging output produced)
===
Save employees #1: 78.0 secs
Save org units #1: 11.1 secs
Save positions #1: 101.6 secs
Save employees #2: 82.5 secs
Save org units #2: 11.5 secs
Save positions #2: 112.3 secs

Logging code in utils.py, logging configuration set to INFO (logging
output produced)
=
Save employees #1: 88.6 secs
Save org units #1: 11.5 secs
Save positions #1: 106.6 secs
Save employees #2: 82.1 secs
Save org units #2: 11.6 secs
Save positions #2: 120.6 secs

This is really only anecdotal, of course - your mileage will no doubt
vary. Here's the code from settings.py:

import logging
logging.basicConfig(level=logging.DEBUG, filename='/tmp/mysite.log',
filemode='w', format="%(levelname)-8s %(name)-20s %(message)s")

and here's the logging code in utils.py:

=== modified file 'django/db/backends/util.py'
--- django/db/backends/util.py
+++ django/db/backends/util.py
@@ -1,5 +1,8 @@
 import datetime
 from time import time
+import logging
+
+logger = logging.getLogger('django.db.sql')

 class CursorDebugWrapper(object):
 def __init__(self, cursor, db):
@@ -9,6 +12,8 @@
 def execute(self, sql, params=()):
 start = time()
 try:
+if logger.isEnabledFor(logging.DEBUG):
+logger.debug('%s %% %s', sql, params)
 return self.cursor.execute(sql, params)
 finally:
 stop = time()

Best regards,


Vinay Sajip


--~--~-~--~~~---~--~

Re: Enforcing model representation invariants

2007-04-17 Thread Vinay Sajip



On Apr 17, 4:06 am, Malcolm Tredinnick <[EMAIL PROTECTED]>
wrote:
> > My "big stick" solution is just to override the save() method of the
> > model, and to have it swap the start and end fields.
>
> A conceptual problem with this approach is that it's doing validation in
> the wrong place. Validation and saving are intentionally separated in
> Django. The idea is that if you have any validation failure, you can go
> back to the data supplier and get more information. Saving should
> *never* raise a validation problem. We cannot avoid errors entirely,
> because database integrity errors may be thrown (another process,
> completely unrelated to Django may have put data in the database that
> caused the problem before we saved), however, in most cases, saving is a
> "safe" operation.

Malcolm is right when he's talking about validation of user-entered
data. However, invariants are also used to catch programming errors;
it's certainly possible to have buggy business logic code which causes
invariant checks to fail. An alternative to overriding the save()
method is to hook the pre_save event and call a model-class invariant
method to check if, from the model point of view, the model instance
is valid. (Note that the model point of view can be stricter and also
more complex than database constraints can easily capture.) If the
invariant fails, an exception can be thrown, and caught in the view to
display an appropriate user-friendly message.

Just my 2 cents,


Vinay Sajip


--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



_checklogin decorator error checking is too specific

2007-04-16 Thread Vinay Sajip

The _checklogin decorator in django/contrib/admin/views/decorators.py
is very helpful - if a user enters an email address as their username,
and authentication fails, it gives a message saying that email
addresses are not allowable as usernames.

In a particular app, I am using email addresses as usernames, but
still using the existing admin infrastructure. It seems to be working
fine, except for the error message referred to above which is
displayed on authentication failure. I think that the checking for '@'
is usernames in decorators.py should be conditional either on a
setting in settings.py or a module-level variable which can be set on
a per-deployment basis to turn off the checking, so that the vanilla
"Please enter a correct username and password..." message can be shown
rather than the usually friendlier, but sometimes inappropriate more
specific message.

I'd be happy to submit a patch - just wanted to canvass opinion here
before raising a ticket.

Cheers,

Vinay Sajip


--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



Re: Django performance and logging

2007-04-08 Thread Vinay Sajip

> To be fair (because otherwise somebody will claim I'm missing an obvious
> point), yes, this could be done via syslog on systems that have it
> available. It is still a performance hit (writing to disk isn't free). I
> did an experiment early last year to put in calls to the python logging
> module throughout various paths in Django. It had a noticeable impact.

As author of the logging package in Python and a (new) Django user,
I'm very interested in this. Can you give me a little more
information? What sort of impact did it have, quantitatively speaking?
Did you use e.g. logger.isEnabledFor() to avoid computing the
arguments unnecessarily? I would like to see if it is possible for
Django to use Python logging (perhaps only in debug mode), and if
there are bottlenecks which preclude this, I would like to see what
can be done to improve matters - so I would appreciate your feedback.

Thanks,

Vinay Sajip


--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



Re: AttributeError: 'module' object has no attribute 'myapp'

2007-04-02 Thread Vinay Sajip

> The problem is caused by the way that Django loads and indexes
> applications. I haven't tried putting code in __init__.py, but it
> certainly doesn't surprise me that it has caused you difficulties.
>
> > If this is not the
> > case, where
> > is the best place to do the kind of initialisation I want to?
>
> Well... this depends on exactly what sort of initialization do you
> want to do. I'm still a little unclear on what you want to initialize,
> and why this initialization needs to be done on module load, rather
> than model synchronization, model definition or instance
> instantiation).

Thanks Russ, I figured it out. It didn't really need to be done on
module load - I was justy trying to do it as early as possible.
Anyway, model definition time is fine, and when I moved the code from
__init__.py to models.py, the problems went away.

Best regards,

Vinay Sajip


--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~--~~~~--~~--~--~---



AttributeError: 'module' object has no attribute 'myapp'

2007-03-30 Thread Vinay Sajip

I created a vanilla project using 'django-admin.py startproject
mysite' and then created a vanilla app in mysite using 'manage.py
startapp myapp'. I ensured that 'mysite.myapp' was added to
mysite.settings.INSTALLED_APPS, and also updated some other settings
in mysite.settings.py. All well and good.

Now, myapp is the package for my application, and so in its
__init__.py, I want to do some setting up. I wanted some information
from the User model in django.contrib.auth.models, and so I imported
django.contrib.auth.models - this led to an error, though I was able
to import django.contrib.auth without any problems.

With the following myapp/__init__.py:

import django.contrib.auth
print django.contrib.auth
#import django.contrib.auth.models

When I ran 'manage.py diffsettings', I got the following output, as
expected
(please excuse line-wrap if it happens):

[EMAIL PROTECTED]:~/projects/mysite$ ./manage.py diffsettings

DATABASE_ENGINE = 'sqlite3'
DATABASE_NAME = '/home/vinay/projects/mysite.db'
DEBUG = True
INSTALLED_APPS = ['django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions', 'django.contrib.sites', 'mysite.myapp']
LANGUAGE_CODE = 'en-gb'
MIDDLEWARE_CLASSES = ('django.middleware.common.CommonMiddleware',
'django.contrib.sessions.middleware.SessionMiddleware',
'django.contrib.auth.middleware.AuthenticationMiddleware',
'django.middleware.doc.XViewMiddleware')
ROOT_URLCONF = 'mysite.urls'  ###
SECRET_KEY = 'u_wf!1^!3y7iz!)=3cs8-=clsg^#g&2y16cavha2!fca3macrw'
SETTINGS_MODULE = 'mysite.settings'  ###
SITE_ID = 1  ###
TEMPLATE_DEBUG = True
TIME_ZONE = 'Europe/London'

However, uncommenting the last line in myapp/__init__.py and running
'manage.py
diffsettings' led to an error:

[EMAIL PROTECTED]:~/projects/mysite$ ./manage.py diffsettings

Traceback (most recent call last):
  File "./manage.py", line 11, in ?
execute_manager(settings)
  File "/usr/lib/python2.4/site-packages/django/core/management.py",
line 1680, in execute_manager
execute_from_command_line(action_mapping, argv)
  File "/usr/lib/python2.4/site-packages/django/core/management.py",
line 1572, in execute_from_command_line
translation.activate('en-us')
  File
"/usr/lib/python2.4/site-packages/django/utils/translation/
trans_real.py", line 195, in activate
_active[currentThread()] = translation(language)
  File
"/usr/lib/python2.4/site-packages/django/utils/translation/
trans_real.py", line 184, in translation
default_translation = _fetch(settings.LANGUAGE_CODE)
  File
"/usr/lib/python2.4/site-packages/django/utils/translation/
trans_real.py", line
167, in _fetch
app = getattr(__import__(appname[:p], {}, {}, [appname[p+1:]]),
appname[p+1:])
  File "/home/vinay/projects/mysite/../mysite/myapp/__init__.py", line
3, in ?
import django.contrib.auth.models
  File "/usr/lib/python2.4/site-packages/django/contrib/auth/
models.py", line 4,
in ?
from django.contrib.contenttypes.models import ContentType
  File "/usr/lib/python2.4/site-packages/django/contrib/contenttypes/
models.py",
line 33, in ?
class ContentType(models.Model):
  File "/usr/lib/python2.4/site-packages/django/db/models/base.py",
line 30, in
__new__
new_class.add_to_class('_meta', Options(attrs.pop('Meta', None)))
  File "/usr/lib/python2.4/site-packages/django/db/models/base.py",
line 169, in
add_to_class
value.contribute_to_class(cls, name)
  File "/usr/lib/python2.4/site-packages/django/db/models/options.py",
line 53,
in contribute_to_class
setattr(self, 'verbose_name_plural',
meta_attrs.pop('verbose_name_plural',
self.verbose_name + 's'))
  File "/usr/lib/python2.4/site-packages/django/utils/functional.py",
line 42,
in __wrapper__
res = self.__func(*self.__args, **self.__kw)
  File
"/usr/lib/python2.4/site-packages/django/utils/translation/
trans_real.py", line
255, in gettext
_default = translation(settings.LANGUAGE_CODE)
  File
"/usr/lib/python2.4/site-packages/django/utils/translation/
trans_real.py", line
184, in translation
default_translation = _fetch(settings.LANGUAGE_CODE)
  File
"/usr/lib/python2.4/site-packages/django/utils/translation/
trans_real.py", line
167, in _fetch
app = getattr(__import__(appname[:p], {}, {}, [appname[p+1:]]),
appname[p+1:])
AttributeError: 'module' object has no attribute 'myapp'

Now, why should this be? The traceback is mystifying to me - can
anyone shed any
light? I certainly want, in myapp's setup, to do some things based on
django.contrib.auth.models.User. (For example, I might want to set the
email
field to be unique, which it is not by default). It seemed reasonable
to assume
that all the apps would be initialised in the order that they appear
in
INSTALLED_APPS, and mysite.myapp (being last in the list) should be
able to rely
on the prec