Reputation: 24322
I want to use git to allow me to work on several features in a module I'm writing concurrently. I'm currently using SVN, with only one workspace, so I just have the workspace on my PYTHONPATH. I'm realizing this is less than ideal, so I was wondering if anyone could suggest a more 'proper' way of doing this.
Let me elaborate with a hypothetical situation: I say I have a module 'eggs', with sub-modules 'foo' and 'bar'. Components in 'bar' use code in foo, so eggs/bar/a.py may 'import eggs.foo'.
Say that 'eggs' is in a git repository. I want to try out some changes to 'foo', so I copy it. The problem is that 'import eggs.foo' in eggs/bar finds the original repository in the PYTHONPATH, so it ends up using the old 'foo' instead of my modified one.
How do I set myself up such that each copy of the module uses its own associated 'foo'? Thanks.
edit- Thanks for the pointer to relative imports. I've read up on it and I can see how to apply it. One problem I'd have with using it is that I've built up a fairly large codebase, and I haven't been too neat about it so most modules have a quick 'self-test' under if __name__ == '__main__':
, which from what I've read does not play with relative imports:
http://mail.python.org/pipermail/python-list/2006-October/408945.html
http://www.velocityreviews.com/forums/t502905-relative-import-broken.html
The other solution I've been able to google up is to deliberately manipulate sys.path, which seems like an even worse hack. Are there any other possibilities?
edit - Thanks for the suggestions. I'd originally misunderstood git branches, so as pointed out branches are exactly what I want. Nonetheless, I hadn't heard of relative imports before so thanks for that as well. I've learnt something new and may incorporate its use.
Upvotes: 2
Views: 2788
Reputation: 414685
Relative imports (PEP 328) might help:
eggs/
__init__.py
foo.py
bar.py
# foo.py
from __future__ import absolute_import
from . import bar
See How do you organize Python modules? for other options.
EDIT:
Yet another option is to use S.Lott's and Jim's suggestions i.e, restructure your package to factor out a eggs.foo
part used by eggs.bar.a
and use git
to work on experimental branches (see Git Community Book).
Here's an example:
$ git status
# On branch master
nothing to commit (working directory clean)
[just to make sure that all is good]
$ git checkout -b experimental
Switched to a new branch "experimental"
[work on experimental stuff]
$ git commit -a
[commit to experimental branch]
$ git checkout master
Switched to branch "master"
[work on master branch]
$ git commit -a
To merge changes into master branch:
$ git merge experimental
See chapter Basic Branching and Merging from the above book.
Upvotes: 3
Reputation: 109416
Maybe I'm not understanding correctly, but it seems that git would be the solution here, since git's branches don't need separate paths.
Create a branch for each working version of your eggs module. Then when you checkout that branch, the entire module is changed to a state matching the version of your sub-module. You could then merge what you need back and forth between the branches.
And as S.Lott pointed out, may a little refactoring couldn't hurt either ;)
Upvotes: 1
Reputation: 391962
"say I have a module 'eggs', with sub-modules 'foo' and 'bar'. Components in 'bar' use code in foo, so eggs/bar/a.py may 'import eggs.foo'."
This may not be the best structure. I suggest you have some other modules struggling to get out.
You have eggs.bar.a
depending on eggs.foo
. I'm guessing other stuff on eggs
depends on eggs.foo
. Further, I suspect that eggs.foo
could be partitioned into eggs.foo
and eggs.quux
and things might be simpler.
I'd recommend refactoring this to get a better structure. The PYTHONPATH
issues are symptomatic of too many things in the wrong places in the module tree.
Upvotes: 1