2011-11-10 21:33:01 +04:00
|
|
|
Create user cache directory
|
|
|
|
|
|
|
|
$ USERCACHE=`pwd`/cache; export USERCACHE
|
|
|
|
$ cat <<EOF >> ${HGRCPATH}
|
|
|
|
> [extensions]
|
|
|
|
> hgext.largefiles=
|
|
|
|
> [largefiles]
|
|
|
|
> usercache=${USERCACHE}
|
|
|
|
> EOF
|
|
|
|
$ mkdir -p ${USERCACHE}
|
|
|
|
|
|
|
|
Create source repo, and commit adding largefile.
|
|
|
|
|
|
|
|
$ hg init src
|
|
|
|
$ cd src
|
|
|
|
$ echo large > large
|
|
|
|
$ hg add --large large
|
|
|
|
$ hg commit -m 'add largefile'
|
2013-02-28 16:44:59 +04:00
|
|
|
$ hg rm large
|
2016-01-24 04:51:17 +03:00
|
|
|
$ hg commit -m 'branchhead without largefile' large
|
2013-02-28 16:44:59 +04:00
|
|
|
$ hg up -qr 0
|
2016-01-24 08:10:19 +03:00
|
|
|
$ rm large
|
|
|
|
$ echo "0000000000000000000000000000000000000000" > .hglf/large
|
|
|
|
$ hg commit -m 'commit missing file with corrupt standin' large
|
|
|
|
abort: large: file not found!
|
|
|
|
[255]
|
|
|
|
$ hg up -Cqr 0
|
2011-11-10 21:33:01 +04:00
|
|
|
$ cd ..
|
|
|
|
|
|
|
|
Discard all cached largefiles in USERCACHE
|
|
|
|
|
|
|
|
$ rm -rf ${USERCACHE}
|
|
|
|
|
2011-11-11 03:06:12 +04:00
|
|
|
Create mirror repo, and pull from source without largefile:
|
2011-11-10 21:33:01 +04:00
|
|
|
"pull" is used instead of "clone" for suppression of (1) updating to
|
2014-04-13 21:01:00 +04:00
|
|
|
tip (= caching largefile from source repo), and (2) recording source
|
2011-11-10 21:33:01 +04:00
|
|
|
repo as "default" path in .hg/hgrc.
|
|
|
|
|
|
|
|
$ hg init mirror
|
|
|
|
$ cd mirror
|
|
|
|
$ hg pull ../src
|
|
|
|
pulling from ../src
|
|
|
|
requesting all changes
|
|
|
|
adding changesets
|
|
|
|
adding manifests
|
|
|
|
adding file changes
|
2013-02-28 16:44:59 +04:00
|
|
|
added 2 changesets with 1 changes to 1 files
|
2011-11-10 21:33:01 +04:00
|
|
|
(run 'hg update' to get a working copy)
|
|
|
|
|
|
|
|
Update working directory to "tip", which requires largefile("large"),
|
|
|
|
but there is no cache file for it. So, hg must treat it as
|
|
|
|
"missing"(!) file.
|
|
|
|
|
2013-02-28 16:44:59 +04:00
|
|
|
$ hg update -r0
|
2011-11-10 21:33:01 +04:00
|
|
|
getting changed largefiles
|
2014-01-28 00:39:25 +04:00
|
|
|
large: largefile 7f7097b041ccf68cc5561e9600da4655d21c6d18 not available from file:/*/$TESTTMP/mirror (glob)
|
2011-11-10 21:33:01 +04:00
|
|
|
0 largefiles updated, 0 removed
|
2013-01-23 03:51:53 +04:00
|
|
|
1 files updated, 0 files merged, 0 files removed, 0 files unresolved
|
2011-11-10 21:33:01 +04:00
|
|
|
$ hg status
|
|
|
|
! large
|
|
|
|
|
|
|
|
Update working directory to null: this cleanup .hg/largefiles/dirstate
|
|
|
|
|
|
|
|
$ hg update null
|
|
|
|
getting changed largefiles
|
|
|
|
0 largefiles updated, 0 removed
|
2013-01-23 03:51:53 +04:00
|
|
|
0 files updated, 0 files merged, 1 files removed, 0 files unresolved
|
2011-11-10 21:33:01 +04:00
|
|
|
|
|
|
|
Update working directory to tip, again.
|
|
|
|
|
2013-02-28 16:44:59 +04:00
|
|
|
$ hg update -r0
|
2011-11-10 21:33:01 +04:00
|
|
|
getting changed largefiles
|
2014-01-28 00:39:25 +04:00
|
|
|
large: largefile 7f7097b041ccf68cc5561e9600da4655d21c6d18 not available from file:/*/$TESTTMP/mirror (glob)
|
2011-11-10 21:33:01 +04:00
|
|
|
0 largefiles updated, 0 removed
|
2013-01-23 03:51:53 +04:00
|
|
|
1 files updated, 0 files merged, 0 files removed, 0 files unresolved
|
2011-11-10 21:33:01 +04:00
|
|
|
$ hg status
|
|
|
|
! large
|
2012-06-19 03:43:41 +04:00
|
|
|
$ cd ..
|
|
|
|
|
2013-02-28 16:45:18 +04:00
|
|
|
Verify that largefiles from pulled branchheads are fetched, also to an empty repo
|
|
|
|
|
|
|
|
$ hg init mirror2
|
|
|
|
$ hg -R mirror2 pull src -r0
|
|
|
|
pulling from src
|
|
|
|
adding changesets
|
|
|
|
adding manifests
|
|
|
|
adding file changes
|
|
|
|
added 1 changesets with 1 changes to 1 files
|
|
|
|
(run 'hg update' to get a working copy)
|
|
|
|
|
2012-06-19 03:43:41 +04:00
|
|
|
#if unix-permissions
|
2012-02-23 16:22:55 +04:00
|
|
|
|
|
|
|
Portable way to print file permissions:
|
|
|
|
|
|
|
|
$ cat > ls-l.py <<EOF
|
|
|
|
> #!/usr/bin/env python
|
|
|
|
> import sys, os
|
|
|
|
> path = sys.argv[1]
|
|
|
|
> print '%03o' % (os.lstat(path).st_mode & 0777)
|
|
|
|
> EOF
|
|
|
|
$ chmod +x ls-l.py
|
|
|
|
|
|
|
|
Test that files in .hg/largefiles inherit mode from .hg/store, not
|
|
|
|
from file in working copy:
|
|
|
|
|
|
|
|
$ cd src
|
|
|
|
$ chmod 750 .hg/store
|
|
|
|
$ chmod 660 large
|
|
|
|
$ echo change >> large
|
|
|
|
$ hg commit -m change
|
2013-02-28 16:44:59 +04:00
|
|
|
created new head
|
2012-02-23 16:22:55 +04:00
|
|
|
$ ../ls-l.py .hg/largefiles/e151b474069de4ca6898f67ce2f2a7263adf8fea
|
|
|
|
640
|
2012-02-23 16:37:10 +04:00
|
|
|
|
|
|
|
Test permission of with files in .hg/largefiles created by update:
|
|
|
|
|
|
|
|
$ cd ../mirror
|
|
|
|
$ rm -r "$USERCACHE" .hg/largefiles # avoid links
|
|
|
|
$ chmod 750 .hg/store
|
|
|
|
$ hg pull ../src --update -q
|
|
|
|
$ ../ls-l.py .hg/largefiles/e151b474069de4ca6898f67ce2f2a7263adf8fea
|
|
|
|
640
|
2012-02-23 16:37:10 +04:00
|
|
|
|
|
|
|
Test permission of files created by push:
|
|
|
|
|
|
|
|
$ hg serve -R ../src -d -p $HGPORT --pid-file hg.pid \
|
|
|
|
> --config "web.allow_push=*" --config web.push_ssl=no
|
|
|
|
$ cat hg.pid >> $DAEMON_PIDS
|
|
|
|
|
|
|
|
$ echo change >> large
|
|
|
|
$ hg commit -m change
|
|
|
|
|
|
|
|
$ rm -r "$USERCACHE"
|
|
|
|
|
|
|
|
$ hg push -q http://localhost:$HGPORT/
|
|
|
|
|
|
|
|
$ ../ls-l.py ../src/.hg/largefiles/b734e14a0971e370408ab9bce8d56d8485e368a9
|
|
|
|
640
|
2012-06-11 03:40:51 +04:00
|
|
|
|
|
|
|
$ cd ..
|
2012-06-19 03:43:41 +04:00
|
|
|
|
|
|
|
#endif
|
largefiles: fix a spurious missing file warning with 'remove -A' (issue4053)
The bug report doesn't mention largefiles, but the given recipe doesn't fail
unless the largefiles extension is loaded. The problem only affected normal
files, whether or not any largefiles are committed, and only files that have
not been committed yet. (Files with an 'a' state are dropped from dirstate,
not marked removed.) Further, if the named normal file never existed, the
warning would be printed out twice.
The problem is that the core implementation of remove() calls repo.status(),
which eventually triggers a dirstate.walk(). When the file isn't seen in the
filesystem during the walk, the exception handling finds the file in
dirstate, so it doesn't complain. However, the largefiles implementation
called status() again with all of the original files (including the normal
ones, just dropped). This time, the exception handler doesn't find the file
in dirstate and does complain. This simply excludes the normal files from
the second repo.status() call, which the largefiles extension has no interest
is processing anyway.
2014-12-21 23:04:13 +03:00
|
|
|
|
|
|
|
Test issue 4053 (remove --after on a deleted, uncommitted file shouldn't say
|
2015-01-18 04:38:57 +03:00
|
|
|
it is missing, but a remove on a nonexistent unknown file still should. Same
|
2014-12-21 23:06:54 +03:00
|
|
|
for a forget.)
|
largefiles: fix a spurious missing file warning with 'remove -A' (issue4053)
The bug report doesn't mention largefiles, but the given recipe doesn't fail
unless the largefiles extension is loaded. The problem only affected normal
files, whether or not any largefiles are committed, and only files that have
not been committed yet. (Files with an 'a' state are dropped from dirstate,
not marked removed.) Further, if the named normal file never existed, the
warning would be printed out twice.
The problem is that the core implementation of remove() calls repo.status(),
which eventually triggers a dirstate.walk(). When the file isn't seen in the
filesystem during the walk, the exception handling finds the file in
dirstate, so it doesn't complain. However, the largefiles implementation
called status() again with all of the original files (including the normal
ones, just dropped). This time, the exception handler doesn't find the file
in dirstate and does complain. This simply excludes the normal files from
the second repo.status() call, which the largefiles extension has no interest
is processing anyway.
2014-12-21 23:04:13 +03:00
|
|
|
|
|
|
|
$ cd src
|
|
|
|
$ touch x
|
|
|
|
$ hg add x
|
|
|
|
$ mv x y
|
|
|
|
$ hg remove -A x y ENOENT
|
|
|
|
ENOENT: * (glob)
|
|
|
|
not removing y: file is untracked
|
|
|
|
[1]
|
2014-12-21 23:06:54 +03:00
|
|
|
$ hg add y
|
|
|
|
$ mv y z
|
|
|
|
$ hg forget y z ENOENT
|
|
|
|
ENOENT: * (glob)
|
|
|
|
not removing z: file is already untracked
|
|
|
|
[1]
|
largefiles: use the share source as the primary local store (issue4471)
The benefit of retargeting the local store to the share source is that all
shares will always have access to the largefiles any one of them commit, even if
the user cache is deleted (which is documented to be OK to do). Further, any
push into the source (and now any shares), will likewise make the largefile(s)
visible to all related repositories.
In order to maintain compatibility with existing repos, where the largefiles
would be cached only in the local share, fallback to searching the local share
if it isn't found at the share source.
The unshare command should probably be taught to copy the source store into the
store for the repo being unshared to complete the loop.
This patch changes the test like this:
@@ -159,6 +159,5 @@
$ hg share -q src share_dst --config extensions.share=
$ hg -R share_dst update -r0
getting changed largefiles
- large: largefile $HASH not available from file:///$TESTTMP\share_dst
- 0 largefiles updated, 0 removed
+ 1 largefiles updated, 0 removed
1 files updated, 0 files merged, 0 files removed, 0 files unresolved
The issue writeup mentions pushing a largefile from a remote repo to the main
local repo, and the largefile is then not available in any shares. Since the
push doesn't cache the largefile in $USERCACHE, the trashed $USERCACHE in this
test is equivalent.
2015-04-05 02:06:43 +03:00
|
|
|
|
|
|
|
Largefiles are accessible from the share's store
|
|
|
|
$ cd ..
|
|
|
|
$ hg share -q src share_dst --config extensions.share=
|
|
|
|
$ hg -R share_dst update -r0
|
|
|
|
getting changed largefiles
|
|
|
|
1 largefiles updated, 0 removed
|
|
|
|
1 files updated, 0 files merged, 0 files removed, 0 files unresolved
|
|
|
|
|
|
|
|
$ echo modified > share_dst/large
|
|
|
|
$ hg -R share_dst ci -m modified
|
|
|
|
created new head
|
|
|
|
|
|
|
|
Only dirstate is in the local store for the share, and the largefile is in the
|
|
|
|
share source's local store. Avoid the extra largefiles added in the unix
|
|
|
|
conditional above.
|
|
|
|
$ hash=`hg -R share_dst cat share_dst/.hglf/large`
|
|
|
|
$ echo $hash
|
|
|
|
e2fb5f2139d086ded2cb600d5a91a196e76bf020
|
|
|
|
|
|
|
|
$ find share_dst/.hg/largefiles/* | sort
|
|
|
|
share_dst/.hg/largefiles/dirstate
|
|
|
|
|
|
|
|
$ find src/.hg/largefiles/* | egrep "(dirstate|$hash)" | sort
|
|
|
|
src/.hg/largefiles/dirstate
|
|
|
|
src/.hg/largefiles/e2fb5f2139d086ded2cb600d5a91a196e76bf020
|
2015-10-23 22:27:29 +03:00
|
|
|
|
2016-06-07 09:32:33 +03:00
|
|
|
Verify that backwards compatibility is maintained for old storage layout
|
|
|
|
$ mv src/.hg/largefiles/$hash share_dst/.hg/largefiles
|
|
|
|
$ hg verify --quiet --lfa -R share_dst --config largefiles.usercache=
|
|
|
|
|
2015-10-23 22:27:29 +03:00
|
|
|
Inject corruption into the largefiles store and see how update handles that:
|
|
|
|
|
|
|
|
$ cd src
|
2016-02-02 18:24:11 +03:00
|
|
|
$ hg up -qC tip
|
2015-10-23 22:27:29 +03:00
|
|
|
$ cat large
|
|
|
|
modified
|
|
|
|
$ rm large
|
|
|
|
$ cat .hglf/large
|
|
|
|
e2fb5f2139d086ded2cb600d5a91a196e76bf020
|
|
|
|
$ mv .hg/largefiles/e2fb5f2139d086ded2cb600d5a91a196e76bf020 ..
|
|
|
|
$ echo corruption > .hg/largefiles/e2fb5f2139d086ded2cb600d5a91a196e76bf020
|
|
|
|
$ hg up -C
|
|
|
|
getting changed largefiles
|
2015-11-09 20:51:58 +03:00
|
|
|
large: data corruption in $TESTTMP/src/.hg/largefiles/e2fb5f2139d086ded2cb600d5a91a196e76bf020 with hash 6a7bb2556144babe3899b25e5428123735bb1e27 (glob)
|
2015-10-23 22:27:29 +03:00
|
|
|
0 largefiles updated, 0 removed
|
2015-10-23 22:27:29 +03:00
|
|
|
0 files updated, 0 files merged, 0 files removed, 0 files unresolved
|
2016-03-16 04:56:01 +03:00
|
|
|
[12] other heads for branch "default" (re)
|
2015-10-23 22:27:29 +03:00
|
|
|
$ hg st
|
2015-10-23 22:27:29 +03:00
|
|
|
! large
|
2015-10-23 22:27:29 +03:00
|
|
|
? z
|
|
|
|
$ rm .hg/largefiles/e2fb5f2139d086ded2cb600d5a91a196e76bf020
|
2015-10-23 22:27:29 +03:00
|
|
|
|
|
|
|
#if serve
|
|
|
|
|
|
|
|
Test coverage of error handling from putlfile:
|
|
|
|
|
|
|
|
$ mkdir $TESTTMP/mirrorcache
|
|
|
|
$ hg serve -R ../mirror -d -p $HGPORT1 --pid-file hg.pid --config largefiles.usercache=$TESTTMP/mirrorcache
|
|
|
|
$ cat hg.pid >> $DAEMON_PIDS
|
|
|
|
|
|
|
|
$ hg push http://localhost:$HGPORT1 -f --config files.usercache=nocache
|
|
|
|
pushing to http://localhost:$HGPORT1/
|
|
|
|
searching for changes
|
2017-04-01 21:48:39 +03:00
|
|
|
abort: remotestore: could not open file $TESTTMP/src/.hg/largefiles/e2fb5f2139d086ded2cb600d5a91a196e76bf020: HTTP Error 403: ssl required (glob)
|
2015-10-23 22:27:29 +03:00
|
|
|
[255]
|
|
|
|
|
|
|
|
$ rm .hg/largefiles/e2fb5f2139d086ded2cb600d5a91a196e76bf020
|
|
|
|
|
|
|
|
Test coverage of 'missing from store':
|
|
|
|
|
|
|
|
$ hg serve -R ../mirror -d -p $HGPORT2 --pid-file hg.pid --config largefiles.usercache=$TESTTMP/mirrorcache --config "web.allow_push=*" --config web.push_ssl=no
|
|
|
|
$ cat hg.pid >> $DAEMON_PIDS
|
|
|
|
|
|
|
|
$ hg push http://localhost:$HGPORT2 -f --config largefiles.usercache=nocache
|
|
|
|
pushing to http://localhost:$HGPORT2/
|
|
|
|
searching for changes
|
|
|
|
abort: largefile e2fb5f2139d086ded2cb600d5a91a196e76bf020 missing from store (needs to be uploaded)
|
|
|
|
[255]
|
|
|
|
|
2016-03-27 23:00:28 +03:00
|
|
|
Verify that --lfrev controls which revisions are checked for largefiles to push
|
|
|
|
|
|
|
|
$ hg push http://localhost:$HGPORT2 -f --config largefiles.usercache=nocache --lfrev tip
|
|
|
|
pushing to http://localhost:$HGPORT2/
|
|
|
|
searching for changes
|
|
|
|
abort: largefile e2fb5f2139d086ded2cb600d5a91a196e76bf020 missing from store (needs to be uploaded)
|
|
|
|
[255]
|
|
|
|
|
|
|
|
$ hg push http://localhost:$HGPORT2 -f --config largefiles.usercache=nocache --lfrev null
|
|
|
|
pushing to http://localhost:$HGPORT2/
|
|
|
|
searching for changes
|
|
|
|
remote: adding changesets
|
|
|
|
remote: adding manifests
|
|
|
|
remote: adding file changes
|
|
|
|
remote: added 1 changesets with 1 changes to 1 files (+1 heads)
|
|
|
|
|
2015-10-23 22:27:29 +03:00
|
|
|
#endif
|