[Tutor] What's the best way to ask forgiveness here?
Brian Jones
bkjones at gmail.com
Mon Sep 13 21:12:12 CEST 2010
Thanks for the replies so far. One thing that's probably relevant: once a
directory is created, I can expect to write a couple of hundred files to it,
so doing a 'try os.makedirs' right off the bat strikes me as coding for the
*least* common case instead of the *most* common (which is that the
directory exists and the file write succeeds). If this were a one-off file
write.... well then things get easier, but I'd like to avoid attempting a
makedirs 100 times when 99 of those times I know it'll give me an error.
brian
On Mon, Sep 13, 2010 at 3:07 PM, Evert Rol <evert.rol at gmail.com> wrote:
> > I've been coding Python long enough that 'asking forgiveness instead of
> permission' is my first instinct, but the resulting code is sometimes
> clumsy, and I wonder if someone can suggest something I'm missing, or at
> least validate what's going on here in some way.
> >
> > What I'm trying to do is write a file to a directory. However, the
> directory may not exist the first time I try to write a file there, so I'm
> going to first try to write the file, and if I get an exception, create the
> directory (er, *try* to), and *then* write the file there.
>
> That would work.
> Though I would just try to create the error directory first. If that fails,
> I check the error message/code in the except clause: if it indicates the
> directory already exists, I pass the exception, otherwise reraise it.
> Then I continue with creating the file within the directory I now am
> certain of exists.
> Note 1: certain is only half: some other process could remove the directory
> in the split second between my code creating it and my code creating the
> file. If you think that could happen, you'll need to look at the other ways
> to do this.
> Note 2: the directory can exist, but not have write access to your process.
> So between the try-except for creating a directory and the try-except for
> creating a file, you may put in a try-except for chmod. Of course, if you're
> not the owner, both the chmod and file creation will fail (I'm assuming some
> *nix platform here, btw).
>
> > Here's my first shot at the code:
> >
> > try:
> > self.save_file(picfile_fullpath, picdata)
> > except IOError as err:
> > # directory doesn't exist. Try to create it.
>
> Careful: you're not checking the actually error given by the exception.
> There may be more than one reason that the file can't be created (examples:
> the permissions mentioned above, or some file creation limit in a
> directory).
>
>
> > try:
> > os.makedirs(picfile_fullpath)
> > except OSError as oserr:
> > logging.error("Can't create file path: %s (%s)" %
> (picfile_fullpath, oserr))
> > else:
> > # Created dir, now write file.
> > try:
> > self.save_file(picfile_fullpath, picdata)
> > except IOError as err:
> > logging.error("Bailing. Couldn't save file %s (%s)" %
> (picfile_fullpath, err))
> > return False
> >
> > Doesn't this seem less readable than the 'ask permission' equivalent? I
> think it does, but in this case asking permission for every single operation
> when the dir will only need to be created a single time (and then may be
> written to several hundred times) is pretty wasteful.
>
> One of the things I once read (but I forgot where) on this issue, is the
> usual "it depends". It depends whether you except that often, the directory
> doesn't exist and the file can't directly be created. In that case, if may
> be quicker to ask permission first (simple if-statement). If you expect that
> in general, you can immediately create the file within the directory (so an
> exception is unlikely to occur), then use a try-except clause.
> But don't take my word for it; I'd be curious what others on this list say
> about this.
>
>
> >
> > I suppose I could set some sentinel variable and check for it in a while
> loop, but then I need some other scaffolding code to make sure I don't
> infinitely loop trying to create the directory, and probably some other
> stuff I'm forgetting, so it strikes me as being just as messy.
> >
> > Is there a clean sort of pattern to apply in instances like this?
>
> I guess not, though readability of code is an important thing to consider.
> In this case, I don't find the correctly unreadable, but at some point,
> these things do tend to get out of hand and you're better off coding it
> differently (perhaps even using functions).
>
>
> Evert
>
>
--
Brian K. Jones
My Blog http://www.protocolostomy.com
Follow me http://twitter.com/bkjones
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.python.org/pipermail/tutor/attachments/20100913/4edc9346/attachment-0001.html>
More information about the Tutor
mailing list