Each worker thread requires at least 3 file descriptors to run the
forked 'git fetch' child to operate against the local repository.
Mac OS X has the RLIMIT_NOFILE set to 256 by default, which means
a sync -j128 often fails when the workers run out of pipes within
the Python parent process.
Change-Id: I2cdb14621b899424b079daf7969bc8c16b85b903
Signed-off-by: Shawn O. Pearce <sop@google.com>
This prints a simple line after a command ends, providing
information about how long it executed for using real wall
clock time. Its mostly useful for looking at sync times.
Change-Id: Ie0997df0a0f90150270835d94b58a01a10bc3956
Signed-off-by: Shawn O. Pearce <sop@google.com>
This allows our progress meter to be used for bytes transferred, by
setting the units to KB or MB to let the user know the size.
Change-Id: Ie8653d4a40d79439026c18bd51915845b2c5bba9
Signed-off-by: Shawn O. Pearce <sop@google.com>
Teach repo how to resolve URLs using the url.insteadof feature
that C Git natively uses during clone, fetch or push. This will
later allow repo to resolve a URL before accessing it directly.
We do not want to pre-resolve things and store the resolved URL
into individual projects, as this makes it impossible for the
user to undo the insteadof mapping at a later date.
Change-Id: I0f62e811197c53fbc8a8be424e3cabf4ed07b4cb
Signed-off-by: Shawn O. Pearce <sop@google.com>
If repo tries to access a URL over HTTP and the user needs to
authenticate, offer a match from ~/.netrc. This matches behavior
with the Git command line client.
Change-Id: I803f3c5d562177ea0330941350cff3cc1e1bef08
Signed-off-by: Shawn O. Pearce <sop@google.com>
Setting REPO_CURL_VERBOSE=1 in the environment will register a debug
level HTTPHandler on the urllib2 library, showing HTTP requests and
responses on the stderr channel of repo.
During any HTTP or HTTPS request created inside of the repo process,
a custom User-Agent header is now defined:
User-Agent: git-repo/1.7.5 (Linux) git/1.7.7 Python/2.6.5
Change-Id: Ia5026fb1e1500659bd2af27416d85e205048bf26
Signed-off-by: Shawn O. Pearce <sop@google.com>
If the http_proxy environment variable was set, honor it during
the entire repo session for any Python created HTTP connections.
Change-Id: Ib4ae833cb2cdd47ab0126949f6b399d2c142887d
Signed-off-by: Shawn O. Pearce <sop@google.com>
The manifest project has - by design - not a review URL associated
with it. It is actually not even a 'project' in repo's sense.
This will prevent the commit-msg hook from being added, which is
not necessarily wanted as the project is managed in gerrit.
This commit will enable the commit-msg hook, which in turn will
add the Change-Id-line to every new commit in it. This simplifies
replacing patch sets (by git push ... refs/for/...).
Change-Id: I42d0f6fd79e6282d9d47074a3819e68d968999a7
Signed-off-by: Victor Boivie <victor.boivie@sonyericsson.com>
This is an evolution of 'smart-sync' that adds a new option, -t,
that allows you to specify a tag/label to use instead of the
"latest good build" on the current manifest branch which -s does.
Signed-off-by: Victor Boivie <victor.boivie@sonyericsson.com>
Change-Id: I8c20fd91104a6aafa0271d4d33f6c4850aade17e
'repo upload' makes http request using urllib2 python library.
Unfortunately this library does not work (by default) in case
if the user behind a proxy.
This change adds proxy handler in case if 'http_proxy' environment
variable is set.
Change-Id: Ic4176ad733fc21bd5b59661b3eacc2f0a7c3c1ff
This commit adds a --br=<branch> option to repo upload.
repo currently examines every non-published branch. This is problematic
for my workflow. I have many branches in my kernel tree. Many of these
branches are based off of upstream remotes (I have many remotes) and
will never be uploaded (they'll get sent upstream as a patch).
Having repo scan these branches adds to my upload processing time
and clutters the branch selection buffer. I've also seen repo get
confused when one of my branches is 1000s of commits different from
m/master.
Change-Id: I68fa18951ea59ba373277b57ffcaf8cddd7e7a40
It is undesired to have the same Change-Id:-line for two separate
commits, and when cherry-picking, the user must manually change it.
If this is not done, bad things may happen (such as when the user
is uploading the cherry-picked commit to Gerrit, it will instead
see it as a new patch-set for the original change, or worse).
repo cherry-pick works the same was as git cherry-pick, except that
it replaces the Change-Id with a new one and adds a reference
back to the commit from where it was picked.
On failures (when git can not successfully apply the cherry-picked
commit), instructions will be written to the user.
Change-Id: I5a38b89839f91848fad43386d43cae2f6cdabf83
In the current version of repo checkout, we often get the error:
error: no project has branch xyzzy
...even when the actual error was something else. This fixes it
to only report the 'no project has branch' when that is actually true.
This fix is very similar to one made for 'repo abandon':
https://review.source.android.com/#change,22207
The repo checkout error is filed as: <http://crosbug.com/6514>
TEST=manual
A sample creating a case where 'git checkout' will fail:
$ repo start branch1 .
$ repo start branch2 .
$ touch bogusfile
$ git add bogusfile
$ git commit -m "create bogus file"
[branch2 f8b6b08] create bogus file
0 files changed, 0 insertions(+), 0 deletions(-)
create mode 100644 bogusfile
$ echo "More" >> bogusfile
$ repo checkout branch1 .
error: chromite/: cannot checkout branch1
A sample case showing that we still fail if no project has a branch:
$ repo checkout xyzzy .
error: no project has branch xyzzy
Change-Id: I48a8e258fa7a9c1f2800dafc683787204bbfcc63
This is the simplest fix: if we had problems syncing the
manifest.git directory and we were the ones that created it,
we should delete it. This doesn't try to do anything complex
like try to recover from a .repo directory that got broken in
some other way.
This is filed as: <http://crosbug.com/13403>
TEST=manual
Init once with a bad URL:
$ repo init -u http://foobar.example.com
Getting manifest ...
from http://foobar.example.com
Connection closed by 172.22.121.77
error: Couldn't resolve host 'foobar.example.com' while accessing http://foobar.example.com/info/refs
fatal: HTTP request failed
fatal: cannot obtain manifest http://foobar.example.com
Init again: identical to the first. Good:
$ repo init -u http://foobar.example.com
Getting manifest ...
from http://foobar.example.com
Connection closed by 172.22.121.77
error: Couldn't resolve host 'foobar.example.com' while accessing http://foobar.example.com/info/refs
fatal: HTTP request failed
fatal: cannot obtain manifest http://foobar.example.com
Init with correct URL:
$ repo init -u http://git.chromium.org/git/manifest -m minilayout.xml
Getting manifest ...
from http://git.chromium.org/git/manifest
[ ... cut ... ]
repo initialized in /.../repoiniterr
Try a bad URL after a good one; it doesn't get saved (good):
$ repo init -u http://foobar.example.com
Connection closed by 172.22.121.77
error: Couldn't resolve host 'foobar.example.com' while accessing http://foobar.example.com/info/refs
fatal: HTTP request failed
fatal: cannot obtain manifest http://foobar.example.com
Just to confirm, I can still do a good one after a bad...
$ repo init -u http://git.chromium.org/git/manifest -m minilayout.xml
Your Name [George Washington]:
Your Email [george@washington.example.com]:
Your identity is: George Washington <george@washington.example.com>
is this correct [y/n]? y
repo initialized in /.../repoiniterr
Change-Id: I1692821a330d97b1d218b2e191a93245b33f2362
The main fix is to give an error message if nothing was actually
abandoned. See <http://crosbug.com/6041>.
The secondary fix is to list projects where the abandon happened.
This could be done in a separate CL or dropped altogether if requested.
TEST=manual
$ repo abandon dougabc; echo $?
Abandon dougabc: 100% (127/127), done.
Abandoned in 2 project(s):
chromite
src/platform/init
0
$ repo abandon dougabc; echo $?
Abandon dougabc: 100% (127/127), done.
error: no project has branch dougabc
1
$ repo abandon dougabc; echo $?
Abandon dougabc: 100% (127/127), done.
error: chromite/: cannot abandon dougabc
1
Change-Id: I79520cc3279291acadc1a24ca34a761e9de04ed4
Event.isSet was renamed to is_set in 2.6, but we should
use the earlier syntax to avoid breaking compatibility
with older Python installations.
Change-Id: I41888ed38df278191d7496c1a6eed15e881733f4
If git-rerere is enabled, it uses the rr-cache directory that
repo currently creates a symlink from, but doesn't create the
destination directory (inside the project's directory). Git
will then complain during merges and rebases.
This commit creates the rr-cache directory inside the project.
Change-Id: If8b57a04f022fc6ed6a7007d05aa2e876e6611ee
The bug that this is fixing is described here:
http://code.google.com/p/chromium-os/issues/detail?id=6813
This fix allows the helper threads to signal the main thread that they
saw an error. When the main thread sees the error, it will let all
existing threads finish, then exit with an error.
Change-Id: If3019bc6b0b3ab9304d49ed2eea53e9d57f3095a
All repo-level hooks are expected to live in a single project at the
top level of that project. The name of the hooks project is provided
in the manifest.xml. The manifest also lists which hooks are enabled
to make it obvious if a file somehow failed to sync down (or got
deleted).
Before running any hook, we will prompt the user to make sure that it
is OK. A user can deny running the hook, allow once, or allow
"forever" (until hooks change). This tries to keep with the git
spirit of not automatically running anything on the user's computer
that got synced down. Note that individual repo commands can add
always options to avoid these prompts as they see fit (see below for
the 'upload' options).
When hooks are run, they are loaded into the current interpreter (the
one running repo) and their main() function is run. This mechanism is
used (instead of using subprocess) to make it easier to expand to a
richer hook interface in the future. During loading, the
interpreter's sys.path is updated to contain the directory containing
the hooks so that hooks can be split into multiple files.
The upload command has two options that control hook behavior:
- no-verify=False, verify=False (DEFAULT):
If stdout is a tty, can prompt about running upload hooks if needed.
If user denies running hooks, the upload is cancelled. If stdout is
not a tty and we would need to prompt about upload hooks, upload is
cancelled.
- no-verify=False, verify=True:
Always run upload hooks with no prompt.
- no-verify=True, verify=False:
Never run upload hooks, but upload anyway (AKA bypass hooks).
- no-verify=True, verify=True:
Invalid
Sample bit of manifest.xml code for enabling hooks (assumes you have a
project named 'hooks' where hooks are stored):
<repo-hooks in-project="hooks" enabled-list="pre-upload" />
Sample main() function in pre-upload.py in hooks directory:
def main(project_list, **kwargs):
print ('These projects will be uploaded: %s' %
', '.join(project_list))
print ('I am being a good boy and ignoring anything in kwargs\n'
'that I don\'t understand.')
print 'I fail 50% of the time. How flaky.'
if random.random() <= .5:
raise Exception('Pre-upload hook failed. Have a nice day.')
Change-Id: I5cefa2cd5865c72589263cf8e2f152a43c122f70
Fix for the bug that leaves a fractional .git directory after attempting to
perform an initial sync to a nonexistent revision. Moved the initialization of
the working directory to after the revision ID has already been checked. Now,
no project/.git directory gets created at all if the revision ID is bad.
Change-Id: I0c9b2a59573410f1d11de7661591bf02e4ce326b
This renaming was done for two reasons:
1. The hooks are actually project-level hooks, not repo-level
hooks. Since we are talking about adding repo-level hooks,
It keeps things less confusing if we name the existing hooks
to be "ProjectHooks"
2. The function is a private function in project.py and so
should have capitalization to match.
I also added a docstring describing this function.
Change-Id: I1d30f5de08e8f9f99f78146e68c76f906782d97e
There was a minor typo that would cause repo to (I believe)
mistakenly identify any file that contained a substring of the
word 'commit-msg' as a commit message hook. For example, the file
'mit' or the file 'msg' would be treated as a commit message hook.
I believe that it was intended that repo only recognize files
named exactly 'commit-msg'.
Change-Id: I93edbddf3da3cf0935641e6efb19b0a8ee6e2308
Commit "Make path references OS independent" (df14a70c45)
broke mirror clients by trying to invoke replace() on None
when there is no worktree.
Change-Id: Ie0a187058358f7dcdf83119e45cc65409c980f11
Users may wind up with a lot of loose object content in projects they
don't frequently make changes in, but that are modified by others.
Since we bypass many git code paths that would have otherwise called
out to `git gc --auto`, its possible for these projects to have
their loose object database grow out of control. To help prevent
that, we now invoke it ourselves during the network half of sync.
Signed-off-by: Shawn O. Pearce <sop@google.com>
(cherry picked from commit 1875ddd47c)
Instead of giving a Python backtrace when there is a connectivity
problem during repo upload, report that we cannot access the host,
and why, with a halfway decent error message.
Bug: REPO-45
Change-Id: I9a45b387e86e48073a2d99bd6d594c1a7d6d99d4
Signed-off-by: Shawn O. Pearce <sop@google.com>
(cherry picked from commit d2dfac81ad)
If a project is missing locally, it might be OK to skip over it
and continue running the same command in other projects.
Bug: REPO-43
Change-Id: I64f97eb315f379ab2c51fc53d24ed340b3d09250
Signed-off-by: Shawn O. Pearce <sop@google.com>
(cherry picked from commit d4cd69bdef)
Windows allows the environment to have unicode values.
This will cause Python to fail to execute the command.
Change-Id: I37d922c3d7ced0d5b4883f0220346ac42defc5e9
Signed-off-by: Shawn O. Pearce <sop@google.com>
The complete help text is printed, so the program executed successfully.
Some tools (like OpenGrok) detects the availibility of a program by
running it with a known set of options and check the return code.
It is an easy and portable way of checking for the existence of a program
instead of searching the path (and handle extensions) ourselves.
Change-Id: Ic13428c77be4a36d599ccb8c86d893308818eae3
This fixes the SSH Control Masters to be managed in a thread-safe
fashion. This is important because "repo sync -jN" uses threads to
sync more than one repository at the same time. The problem didn't
show up earlier because it was masked if all of the threads tried to
connect to the same host that was used on the "repo init" line.
This feature is used to convey information on a when a branch has
ceased development or if it is an experimental branch with a few
gotchas, etc.
You add it to your manifest XML by doing something like this:
<manifest>
<notice>
NOTE TO DEVELOPERS:
If you checkin code, you have to pinky-swear that it contains no bugs.
Anyone who breaks their promise will have tomatoes thrown at them in the
team meeting. Be sure to bring an extra set of clothes.
</notice>
<remote ... />
...
</manifest>
Carriage returns and indentation are relevant for the text in this tag.
This feature was requested by Anush Elangovan on the ChromiumOS team.
This adds a new flag -f/--force-broken that will allow the rest of
the sync process to continue instead of bailing when a particular
project fails to sync.
Change-Id: I23680f2ee7927410f7ed930b1d469424c9aa246e
Signed-off-by: Andrei Warkentin <andreiw@motorola.com>
Signed-off-by: Shawn O. Pearce <sop@google.com>
It hasn't been necessary for a long time, and its
functionality can be accomplished with 'git push'.
Change-Id: Ic00d3adbe4cee7be3955117489c69d6e90106559
Use git clone to initialize a new repository, and when possible
allow callers to use --reference to reuse an existing checkout as
the initial object storage area for the new checkout.
Change-Id: Ie27f760247f311ce484c6d3e85a90d94da2febfc
Signed-off-by: Shawn O. Pearce <sop@google.com>
os.remove() raises OSError if the file being removed doesn't exist.
Check before calling to ensure we don't raise a useless exception
on an already deleted file.
Change-Id: I44c1c7dd97a47fcab8afb6c18fdf179158b6dab7
Signed-off-by: Shawn O. Pearce <sop@google.com>
To avoid connectivity problems, we don't want the ssh process
that is started by git fetch to become a ControlMaster for the
overall sync task. If it did, we would lose connectivity when
git fetch was finished with the current project, causing later
projects to not fetch efficiently.
Change-Id: I8d0dcf9b361276ff8c8b5a6324cbd4a501e9c4dd
Signed-off-by: Shawn O. Pearce <sop@google.com>
Be more thorough about checking for an existing ssh master by
running a test command first, and only opening up a new master
if the test fails to connect.
Change-Id: I56fe8e7b4dbc123675b7f259e81d359ed0cd55cf
Signed-off-by: Shawn O. Pearce <sop@google.com>
The shell swallows the 0th arg, which was the filename. Simple fix
is to pass in an extra arg for the shell to swallow.
Change-Id: Iad6304ba9ccea6e7262ee06ef87d3dac57dbde81