packages feed

git-annex 3.20120721 → 3.20120807

raw patch · 75 files changed

+1049/−354 lines, 75 filesbinary-added

Files

CHANGELOG view
@@ -1,3 +1,13 @@+git-annex (3.20120807) unstable; urgency=low++  * initremote: Avoid recording remote's description before checking+    that its config is valid.+  * unused, status: Avoid crashing when ran in bare repo.+  * Avoid crashing when "git annex get" fails to download from one+    location, and falls back to downloading from a second location.++ -- Joey Hess <joeyh@debian.org>  Tue, 07 Aug 2012 13:35:07 -0400+ git-annex (3.20120721) unstable; urgency=low    * get, move, copy: Now refuse to do anything when the requested file
Command/Get.hs view
@@ -65,7 +65,8 @@ 			| Remote.hasKeyCheap r = 				either (const False) id <$> Remote.hasKey r key 			| otherwise = return True-		docopy r continue = download (Remote.uuid r) key (Just file) $ do-			showAction $ "from " ++ Remote.name r-			ifM (Remote.retrieveKeyFile r key (Just file) dest)-				( return True , continue)+		docopy r continue = do+			ok <- download (Remote.uuid r) key (Just file) $ do+				showAction $ "from " ++ Remote.name r+				Remote.retrieveKeyFile r key (Just file) dest+			if ok then return ok else continue
Command/InitRemote.hs view
@@ -38,18 +38,19 @@ 	t <- findType fullconfig  	showStart "initremote" name-	next $ perform t u $ M.union config c+	next $ perform t u name $ M.union config c  	where 		config = Logs.Remote.keyValToConfig ws -perform :: RemoteType -> UUID -> R.RemoteConfig -> CommandPerform-perform t u c = do+perform :: RemoteType -> UUID -> String -> R.RemoteConfig -> CommandPerform+perform t u name c = do 	c' <- R.setup t u c-	next $ cleanup u c'+	next $ cleanup u name c' -cleanup :: UUID -> R.RemoteConfig -> CommandCleanup-cleanup u c = do+cleanup :: UUID -> String -> R.RemoteConfig -> CommandCleanup+cleanup u name c = do+	describeUUID u name 	Logs.Remote.configSet u c         return True @@ -61,7 +62,6 @@ 	where 		generate = do 			uuid <- liftIO genUUID-			describeUUID uuid name 			return (uuid, M.insert nameKey name M.empty)  findByName' :: String ->  M.Map UUID R.RemoteConfig -> Maybe (UUID, R.RemoteConfig)
Command/Unused.hs view
@@ -229,9 +229,12 @@ withKeysReferenced' :: v -> (Key -> v -> Annex v) -> Annex v withKeysReferenced' initial a = go initial =<< files 	where-		files = do-			top <- fromRepo Git.repoPath-			inRepo $ LsFiles.inRepo [top]+		files = ifM isBareRepo+			( return []+			, do+				top <- fromRepo Git.repoPath+				inRepo $ LsFiles.inRepo [top]+			) 		go v [] = return v 		go v (f:fs) = do 			x <- Backend.lookupFile f
INSTALL view
@@ -9,8 +9,8 @@ * [[ArchLinux]] * [[NixOS]] * [[Gentoo]]-* Windows: [[sorry, not possible yet|todo/windows_support]] * [[ScientificLinux5]] - This should cover RHEL5 clones such as CentOS5 and so on+* Windows: [[sorry, not possible yet|todo/windows_support]]  ## Using cabal 
Logs/Transfer.hs view
@@ -98,8 +98,8 @@ 			writeFile tfile $ writeTransferInfo info 			return fd 		cleanup tfile fd = do-			removeFile tfile-			removeFile $ transferLockFile tfile+			void $ tryIO $ removeFile tfile+			void $ tryIO $ removeFile $ transferLockFile tfile 			closeFd fd  {- If a transfer is still running, returns its TransferInfo. -}
Makefile view
@@ -3,20 +3,29 @@ sources=Build/SysConfig.hs Utility/Touch.hs all=$(bins) $(mans) docs +CFLAGS=-Wall+ OS:=$(shell uname | sed 's/[-_].*//') ifeq ($(OS),Linux)-BASEFLAGS_OPTS+=-DWITH_INOTIFY+BASEFLAGS_OPTS=-DWITH_INOTIFY clibs=Utility/libdiskfree.o else-BASEFLAGS_OPTS+=-DWITH_KQUEUE+# BSD system+BASEFLAGS_OPTS=-DWITH_KQUEUE clibs=Utility/libdiskfree.o Utility/libkqueue.o+ifeq ($(OS),Darwin)+# Ensure OSX compiler builds for 32 bit when using 32 bit ghc+GHCARCH:=$(shell ghc -e 'print System.Info.arch')+ifeq ($(GHCARCH),i386)+CFLAGS=-Wall -m32 endif+endif+endif  PREFIX=/usr IGNORE=-ignore-package monads-fd -ignore-package monads-tf BASEFLAGS=-Wall $(IGNORE) -outputdir tmp -IUtility -DWITH_ASSISTANT -DWITH_S3 $(BASEFLAGS_OPTS) GHCFLAGS=-O2 $(BASEFLAGS)-CFLAGS=-Wall  ifdef PROFILE GHCFLAGS=-prof -auto-all -rtsopts -caf-all -fforce-recomp $(BASEFLAGS)
Utility/DataUnits.hs view
@@ -3,31 +3,10 @@  - Copyright 2011 Joey Hess <joey@kitenet.net>  -  - Licensed under the GNU GPL version 3 or higher.- -}--module Utility.DataUnits (-	dataUnits,-	storageUnits,-	memoryUnits,-	bandwidthUnits,-	oldSchoolUnits,--	roughSize,-	compareSizes,-	readSize-) where--import Data.List-import Data.Char--type ByteSize = Integer-type Name = String-type Abbrev = String-data Unit = Unit ByteSize Abbrev Name-	deriving (Ord, Show, Eq)--{- And now a rant:   -+ -+ - And now a rant: + -  - In the beginning, we had powers of two, and they were good.  -  - Disk drive manufacturers noticed that some powers of two were@@ -55,6 +34,27 @@  - complain at me for not being standards compliant. And we call this  - progress?  -}++module Utility.DataUnits (+	dataUnits,+	storageUnits,+	memoryUnits,+	bandwidthUnits,+	oldSchoolUnits,++	roughSize,+	compareSizes,+	readSize+) where++import Data.List+import Data.Char++type ByteSize = Integer+type Name = String+type Abbrev = String+data Unit = Unit ByteSize Abbrev Name+	deriving (Ord, Show, Eq)  dataUnits :: [Unit] dataUnits = storageUnits ++ memoryUnits
− Utility/Mounts.hs
@@ -1,75 +0,0 @@-{-# LINE 1 "Utility/Mounts.hsc" #-}-{- Interface to mtab (and fstab)-{-# LINE 2 "Utility/Mounts.hsc" #-}- - - - Derived from hsshellscript, originally written by- - Volker Wysk <hsss@volker-wysk.de>- - - - Modified to support BSD and Mac OS X by- - Joey Hess <joey@kitenet.net>- -- - Licensed under the GNU LGPL version 2.1 or higher.- -}--{-# LANGUAGE ForeignFunctionInterface #-}--module Utility.Mounts (-	Mntent(..),-	getMounts-) where--import Control.Monad-import Foreign-import Foreign.C-import GHC.IO hiding (finally, bracket)-import Prelude hiding (catch)---{-# LINE 26 "Utility/Mounts.hsc" #-}--{- This is a stripped down mntent, containing only- - fields available everywhere. -}-data Mntent = Mntent-	{ mnt_fsname :: String-	, mnt_dir :: String-	, mnt_type :: String-	} deriving (Read, Show, Eq, Ord)--getMounts :: IO [Mntent]-getMounts = do-	h <- c_mounts_start-	when (h == nullPtr) $-		throwErrno "getMounts"-	mntent <- getmntent h []-	_ <- c_mounts_end h-	return mntent--	where-		getmntent h c = do-			ptr <- c_mounts_next h-			if (ptr == nullPtr)-				then return $ reverse c-				else do-					mnt_fsname_str <- (\hsc_ptr -> peekByteOff hsc_ptr 0) ptr >>= peekCString-{-# LINE 51 "Utility/Mounts.hsc" #-}-					mnt_dir_str <- (\hsc_ptr -> peekByteOff hsc_ptr 4) ptr >>= peekCString-{-# LINE 52 "Utility/Mounts.hsc" #-}-					mnt_type_str <- (\hsc_ptr -> peekByteOff hsc_ptr 8) ptr >>= peekCString-{-# LINE 53 "Utility/Mounts.hsc" #-}-					let ent = Mntent-						{ mnt_fsname = mnt_fsname_str-						, mnt_dir = mnt_dir_str-						, mnt_type = mnt_type_str-						}-					getmntent h (ent:c)--{- Using unsafe imports because the C functions are belived to never block.- - Note that getmntinfo is called with MNT_NOWAIT to avoid possibly blocking;- - while getmntent only accesses a file in /etc (or /proc) that should not- - block. -}-foreign import ccall unsafe "libmounts.h mounts_start" c_mounts_start-        :: IO (Ptr ())-foreign import ccall unsafe "libmounts.h mounts_next" c_mounts_next-        :: Ptr () -> IO (Ptr ())-foreign import ccall unsafe "libmounts.h mounts_end" c_mounts_end-        :: Ptr () -> IO CInt
debian/changelog view
@@ -1,3 +1,13 @@+git-annex (3.20120807) unstable; urgency=low++  * initremote: Avoid recording remote's description before checking+    that its config is valid.+  * unused, status: Avoid crashing when ran in bare repo.+  * Avoid crashing when "git annex get" fails to download from one+    location, and falls back to downloading from a second location.++ -- Joey Hess <joeyh@debian.org>  Tue, 07 Aug 2012 13:35:07 -0400+ git-annex (3.20120721) unstable; urgency=low    * get, move, copy: Now refuse to do anything when the requested file
+ doc/bugs/Build_failure_at_commit_1efe4f3.mdwn view
@@ -0,0 +1,45 @@+Applying this++<pre>+laplace:git-annex jtang$ git diff+diff --git a/Assistant/WebApp/Configurators.hs b/Assistant/WebApp/Configurators.hs+index b9630b1..bf36e59 100644+--- a/Assistant/WebApp/Configurators.hs++++ b/Assistant/WebApp/Configurators.hs+@@ -101,7 +101,7 @@ checkRepositoryPath p = do+  -+  - If run in another directory, the user probably wants to put it there. -}+ defaultRepositoryPath :: Bool -> IO FilePath+-defaultRepositoryPath firstrun = do++defaultRepositoryPath firstRun = do+        cwd <- liftIO $ getCurrentDirectory+        home <- myHomeDir+        if home == cwd && firstRun+</pre>++Causes this to occur,++<pre>+Assistant/WebApp/Configurators.hs:114:17:+    Couldn't match expected type `Control.Monad.Trans.RWS.Lazy.RWST+                                    (Maybe (Env, FileEnv), WebApp, [Yesod.Form.Types.Lang])+                                    Enctype+                                    Ints+                                    (GHandler WebApp WebApp)+                                    t0'+                with actual type `Text'+    Expected type: String+                   -> Control.Monad.Trans.RWS.Lazy.RWST+                        (Maybe (Env, FileEnv), WebApp, [Yesod.Form.Types.Lang])+                        Enctype+                        Ints+                        (GHandler WebApp WebApp)+                        t0+      Actual type: String -> Text+    In the first argument of `(.)', namely `T.pack'+    In the first argument of `(<$>)', namely+      `T.pack . addTrailingPathSeparator'+make: *** [git-annex] Error 1+</pre>++> [[fixed|done]] --[[Joey]] 
+ doc/bugs/fat_support/comment_6_a3b6000330c9c376611c228d746a1d55._comment view
@@ -0,0 +1,8 @@+[[!comment format=mdwn+ username="https://www.google.com/accounts/o8/id?id=AItOawkZRoTRyW3tox-FD2DQWxskgI6_tkEtHL4"+ nickname="Ben"+ subject="comment 6"+ date="2012-07-23T16:11:52Z"+ content="""+The above would work fine for me but the files in my annex (e.g. .git/annex/objects/xx/yy/blah.ogg) don't have extensions like that, so my media player doesn't recognize them as media files. How do I get the files under \"objects\" to keep the extensions of the original files like in Joey's example?+"""]]
+ doc/bugs/fat_support/comment_7_a0ac7f2c44efc8116940c7b94b35e9d0._comment view
@@ -0,0 +1,7 @@+[[!comment format=mdwn+ username="http://joeyh.name/"+ subject="comment 7"+ date="2012-07-24T14:51:50Z"+ content="""+You can get the extensions by migrating to the SHA1E (or SHA256E) backend. +"""]]
+ doc/bugs/git_annex_initremote_needs_some___34__error_checking__34__.mdwn view
@@ -0,0 +1,65 @@+_git annex initremote_ without a complete command set still adds an entry to the uuid.log etc... and thus clutters up the state of the annex. I would not have expected this behaviour as a user.++_initremote_ should fail and not do anything if the commands that it has been given are incomplete or incorrect. I was initialising a few rsync repos and noticed that i ended up having mutiple rsync remotes with the same name but different uuid's. I know its hard if not impossible to remove these uuid's so I have just marked them as "dead" in my live annexes.++Here's a transcript of the problem++<pre>+x00:sandbox jtang$ mkdir atest+x00:sandbox jtang$ cd atest/+x00:atest jtang$ git init+Initialized empty Git repository in /Users/jtang/sandbox/atest/.git/+x00:atest jtang$ git annex init +init  ok+(Recording state in git...)+x00:atest jtang$ git annex status+supported backends: SHA256 SHA1 SHA512 SHA224 SHA384 SHA256E SHA1E SHA512E SHA224E SHA384E WORM URL+supported remote types: git S3 bup directory rsync web hook+trusted repositories: 0+semitrusted repositories: 2+	00000000-0000-0000-0000-000000000001 -- web+ 	cbb58e1c-d737-11e1-b682-83239d5ff2e0 -- here+untrusted repositories: 0+dead repositories: 0+transfers in progress: none+available local disk space: 185 gigabytes (+1 megabyte reserved)+local annex keys: 0+local annex size: 0 bytes+known annex keys: 0+known annex size: 0 bytes+bloom filter size: 16 mebibytes (0% full)+backend usage: +x00:atest jtang$ git annex initremote foo+git-annex: Specify the type of remote with type=+x00:atest jtang$ git annex initremote foo type=rsync+(Recording state in git...)+initremote foo git-annex: Specify encryption=key or encryption=none or encryption=shared+x00:atest jtang$ git annex initremote foo type=rsync+(Recording state in git...)+initremote foo git-annex: Specify encryption=key or encryption=none or encryption=shared+x00:atest jtang$ git annex status+supported backends: SHA256 SHA1 SHA512 SHA224 SHA384 SHA256E SHA1E SHA512E SHA224E SHA384E WORM URL+supported remote types: git S3 bup directory rsync web hook+trusted repositories: (Recording state in git...)+0+semitrusted repositories: 5+	00000000-0000-0000-0000-000000000001 -- web+ 	cbb58e1c-d737-11e1-b682-83239d5ff2e0 -- here+ 	d3adfcd0-d737-11e1-b15b-b7032388f8aa -- foo+ 	d6d8e1e0-d737-11e1-956a-0b3d3451226a -- foo+ 	d78d795c-d737-11e1-ac98-4fe3d6fdfd54 -- foo+untrusted repositories: 0+dead repositories: 0+transfers in progress: none+available local disk space: 185 gigabytes (+1 megabyte reserved)+local annex keys: 0+local annex size: 0 bytes+known annex keys: 0+known annex size: 0 bytes+bloom filter size: 16 mebibytes (0% full)+backend usage: +x00:atest jtang$ +</pre>++> Indeed, I broke that in June by making it record the name in a much too+> early stage. Now fixed. [[done]] --[[Joey]]
+ doc/bugs/journal_commit_error_when_using_annex.mdwn view
@@ -0,0 +1,21 @@+Sorry for the noise - notabug - [[done]]++Setup:++* git-annex version: 3.20120629 on Debian unstable.+* external RAID1 array connected via usb++I did: <code> git-annex add \<a specific album of ogg files\> </code>++When it gets to the fourth song, there is a long delay and a bunch of "journal commit I/O error" from the kernel start appearing. Then GNOME helpfully tells me that my drive was just connected (implying that it thought it was disconnected momentarily)++Log outputs:++Both trying to add whole album, failing at song 4++* <http://paste.mitechie.com/show/745/>+* <http://paste.mitechie.com/show/746/>++Just trying to add song 4 individually++* <http://paste.mitechie.com/show/747/> (lots o' journal commit I/O errors that time)
+ doc/bugs/lsof__47__committer_thread_loops_occassionally.mdwn view
@@ -0,0 +1,49 @@+I've noticed this to occur occassionally ++<pre>+laplace:atest jtang$ ls+1@  2@	3@  4@	5@  readme.txt@+laplace:atest jtang$ git annex watch -d --foreground+watch . [2012-07-29 11:49:26 IST] read: git ["--git-dir=/Users/jtang/sandbox/atest/.git","--work-tree=/Users/jtang/sandbox/atest","show-ref","git-annex"] +[2012-07-29 11:49:26 IST] read: git ["--git-dir=/Users/jtang/sandbox/atest/.git","--work-tree=/Users/jtang/sandbox/atest","show-ref","--hash","refs/heads/git-annex"] +[2012-07-29 11:49:26 IST] read: git ["--git-dir=/Users/jtang/sandbox/atest/.git","--work-tree=/Users/jtang/sandbox/atest","log","refs/heads/git-annex..f85faa60e73efabc2e92f837b19c3918d3ab030f","--oneline","-n1"] +[2012-07-29 11:49:26 IST] chat: git ["--git-dir=/Users/jtang/sandbox/atest/.git","--work-tree=/Users/jtang/sandbox/atest","cat-file","--batch"] +(scanning...) [2012-07-29 11:49:26 IST] Assistant: all threads started+[2012-07-29 11:49:26 IST] Merger: watching /Users/jtang/sandbox/atest/.git/refs/heads/synced+[2012-07-29 11:49:26 IST] TransferWatcher: watching for transfers+[2012-07-29 11:49:26 IST] read: git ["--git-dir=/Users/jtang/sandbox/atest/.git","--work-tree=/Users/jtang/sandbox/atest","symbolic-ref","HEAD"] +[2012-07-29 11:49:26 IST] call: git ["--git-dir=/Users/jtang/sandbox/atest/.git","--work-tree=/Users/jtang/sandbox/atest","add","--update"] +[2012-07-29 11:49:26 IST] Merger: merging changes into Just refs/heads/master+[2012-07-29 11:49:26 IST] call: git ["--git-dir=/Users/jtang/sandbox/atest/.git","--work-tree=/Users/jtang/sandbox/atest","merge","--no-edit","refs/heads/synced/master"] +(started...) [2012-07-29 11:49:26 IST] Watcher: watching .+[2012-07-29 11:49:26 IST] WebApp: running on port 60042+Already up-to-date.+[2012-07-29 11:49:26 IST] Watcher: add symlink ./1+[2012-07-29 11:49:26 IST] chat: git ["--git-dir=/Users/jtang/sandbox/atest/.git","--work-tree=/Users/jtang/sandbox/atest","cat-file","--batch"] +[2012-07-29 11:49:26 IST] Watcher: add symlink ./2+[2012-07-29 11:49:26 IST] Watcher: add symlink ./3+[2012-07-29 11:49:26 IST] Watcher: add symlink ./4+[2012-07-29 11:49:26 IST] Watcher: add symlink ./5+[2012-07-29 11:49:26 IST] Watcher: add symlink ./readme.txt+[2012-07-29 11:49:27 IST] Committer: committing 6 changes+(Recording state in git...)+[2012-07-29 11:49:27 IST] feed: git ["--git-dir=/Users/jtang/sandbox/atest/.git","--work-tree=/Users/jtang/sandbox/atest","update-index","-z","--index-info"] +[2012-07-29 11:49:27 IST] call: git ["--git-dir=/Users/jtang/sandbox/atest/.git","--work-tree=/Users/jtang/sandbox/atest","commit","--allow-empty-message","-m","","--allow-empty","--quiet"] +[2012-07-29 11:49:28 IST] read: git ["--git-dir=/Users/jtang/sandbox/atest/.git","--work-tree=/Users/jtang/sandbox/atest","symbolic-ref","HEAD"] +[2012-07-29 11:49:28 IST] Pusher: pushing to []+[2012-07-29 11:49:28 IST] call: git ["--git-dir=/Users/jtang/sandbox/atest/.git","--work-tree=/Users/jtang/sandbox/atest","branch","-f","synced/master"] +[2012-07-29 11:49:28 IST] read: git ["--git-dir=/Users/jtang/sandbox/atest/.git","--work-tree=/Users/jtang/sandbox/atest","symbolic-ref","HEAD"] +[2012-07-29 11:49:28 IST] Merger: merging changes into Just refs/heads/master+[2012-07-29 11:49:28 IST] call: git ["--git-dir=/Users/jtang/sandbox/atest/.git","--work-tree=/Users/jtang/sandbox/atest","merge","--no-edit","refs/heads/synced/master"] +Already up-to-date.+[2012-07-29 11:49:43 IST] Watcher: file added ./.gitignore+[2012-07-29 11:49:43 IST] read: lsof ["-F0can","+d","/Users/jtang/sandbox/atest/.git/annex/tmp/"] +[2012-07-29 11:49:44 IST] Committer: delaying commit of 0 changes+[2012-07-29 11:49:45 IST] read: lsof ["-F0can","+d","/Users/jtang/sandbox/atest/.git/annex/tmp/"] +[2012-07-29 11:49:46 IST] Committer: delaying commit of 0 changes+[2012-07-29 11:49:47 IST] read: lsof ["-F0can","+d","/Users/jtang/sandbox/atest/.git/annex/tmp/"] +[2012-07-29 11:49:48 IST] Committer: delaying commit of 0 changes+[2012-07-29 11:49:49 IST] read: lsof ["-F0can","+d","/Users/jtang/sandbox/atest/.git/annex/tmp/"] +</pre>++I ran " git annex watch -d --foreground" to watch what was going one, and just created a .gitignore file and the the commiter/lsof thread just loops over and over.... I only noticed as my laptop battery had drained at somepoint when git-annex was running in the background.
+ doc/bugs/yesod-default_is_needed_as_a_dependancy.mdwn view
@@ -0,0 +1,10 @@+Seems like there is a needed dependancy, yesod-default is needed on OSX.++<pre>+Utility/Yesod.hs:10:8:+    Could not find module `Yesod.Default.Util'+    Use -v to see a list of the files searched for.+make: *** [git-annex] Error 1+</pre>++> Only on OSX apparently. Weird. Added. [[done]] --[[Joey]] 
doc/design/assistant/android.mdwn view
@@ -26,6 +26,10 @@ * <http://stackoverflow.com/questions/5151858/running-a-haskell-program-on-the-android-os> * <http://www.reddit.com/r/haskell/comments/ful84/haskell_on_android/> +I've heard anecdoally that ipwnstudios not only has an IPhone GHC port,+but also Android. Need to get in touch with them.+<http://ipwnstudios.com/>+ ### Android specific features  The app should be aware of power status, and avoid expensive background
+ doc/design/assistant/blog/day_42__the_answer.mdwn view
@@ -0,0 +1,27 @@+Made the MountWatcher update state for remotes located in a drive that+gets mounted. This was tricky code. First I had to make remotes declare+when they're located in a local directory. Then it has to rescan git+configs of git remotes (because the git repo mounted at a mount point may+change), and update all the state that a newly available remote can affect.++And it works: I plug in a drive containing one of my git remotes, and the+assistant automatically notices it and syncs the git repositories.++---++But, data isn't transferred yet. When a disconnected remote becomes+connected, keys should be transferred in both directions to get back into+sync.++To that end, added Yet Another Thread; the TransferScanner thread+will scan newly available remotes to find keys, and queue low priority+transfers to get them fully in sync.++(Later, this will probably also be used for network remotes that become+available when moving between networks. I think network-manager sends+dbus events it could use..)++This new thread is missing a crucial peice, it doesn't yet have a way to+find the keys that need to be transferred. Doing that efficiently (without+scanning the whole git working copy) is Hard. I'm considering design+possibilities..
+ doc/design/assistant/blog/day_43__simple_scanner.mdwn view
@@ -0,0 +1,37 @@+Milestone: I can run `git annex assistant`, plug in a USB drive, and it+automatically transfers files to get the USB drive and current repo back in+sync.++I decided to implement the naive scan, to find files needing to be+transferred. So it walks through `git ls-files` and checks each file+in turn. I've deferred less expensive, more sophisticated approaches to later.++I did some work on the TransferQueue, which now keeps track of the length+of the queue, and can block attempts to add Transfers to it if it gets too+long. This was a nice use of STM, which let me implement that without using+any locking.++[[!format haskell """+atomically $ do+        sz <- readTVar (queuesize q)+        if sz <= wantsz+                then enqueue schedule q t (stubInfo f remote)+                else retry -- blocks until queuesize changes+"""]]++Anyway, the point was that, as the scan finds Transfers to do,+it doesn't build up a really long TransferQueue, but instead is blocked+from running further until some of the files get transferred. The resulting+interleaving of the scan thread with transfer threads means that transfers+start fairly quickly upon a USB drive being plugged in, and kind of hides+the innefficiencies of the scanner, which will most of the time be+swamped out by the IO bound large data transfers.++---++At this point, the assistant should do a good job of keeping repositories+in sync, as long as they're all interconnected, or on removable media+like USB drives. There's lots more work to be done to handle use cases+where repositories are not well-connected, but since the assistant's+[[syncing]] now covers at least a couple of use cases, I'm ready to move+on to the next phase. [[Webapp]], here we come!
+ doc/design/assistant/blog/day_44__webapp_basics.mdwn view
@@ -0,0 +1,83 @@+After an all-nighter, I have `git annex webapp` launching a WebApp!++It doesn't do anything useful yet, just uses Yesod to display a couple of+hyperlinked pages and a favicon, securely.++The binary size grew rather alarmingly, BTW. :) Indeed, it's been growing+for months..++	-rwxr-xr-x 1 root root 9.4M Jul 21 16:59 git-annex-no-assistant-stripped+	-rwxr-xr-x 1 joey joey  12M Jul 25 20:54 git-annex-no-webapp-stripped+	-rwxr-xr-x 1 joey joey  17M Jul 25 20:52 git-annex-with-webapp-stripped++----++Along the way, some Not Invented Here occurred:++I didn't use the yesod scaffolded site, because it's a lot of what+seems mostly to be cruft in this use case. And because I don't like+code generated from templates that people are then expected to edit. Ugh.+That's my least favorite part of Yesod. This added some pain, since+I had to do everything the hard way.++I didn't use [wai-handler-launch](http://hackage.haskell.org/package/wai-handler-launch)+because:++  * It seems broken on IPv6 capable machines (it always opens+    `http://127.0.0.1:port/` even though it apparently doesn't always+    listen there.. I think it was listening on my machine's ipv6 address+    instead. I know, I know; I should file a bug about this..)+  * It always uses port 4587, which is **insane**. What if you have two+    webapps?+  * It requires javascript in the web browser, which+    is used to ping the server, and shut it down when the web browser closes+    (which behavior is wrong for git-annex anyway, since the daemon should+    stay running across browser closes).+  * It opens the webapp on web server startup, which is wrong for git-annex; +    instead the command `git annex webapp` will open the webapp,+    after `git annex assistant` started the web server.++Instead, I rolled my own WAI webapp laucher, that binds to any free port+on localhost, It does use `xdg-open` to launch the web browser, +like wai-handler-launch (or just `open` on OS X).++Also, I wrote my own WAI logger, which logs using System.Log.Logger,+instead of to stdout, like `runDebug` does.++----++The webapp only listens for connections from localhost, but that's+not sufficient "security". Instead, I added a secret token to+every url in the webapp, that only `git annex webapp` knows about.++But, if that token is passed to `xdg-open` on its command line,+it will be briefly visible to local attackers in the parameters of+`xdg-open`.. And if the web browser's not already running, it'll run+with it as a parameter, and be *very* visible.++So instead, I used a nasty hack. On startup, the assistant+will create a html file, readably only by the user, that redirects+the user to the real site url. Then `git annex webapp` will run+xdg-open on that file.++----++Making Yesod check the `auth=` parameter (to verify that the secret token+is right) is when using Yesod started to pay off. Yesod has a simple+`isAuthorized` method that can be overridden to do your own authentication+like this.++But Yesod really started to shine when I went to add the `auth=` parameter+to every url in the webapp. There's a `joinPath` method can can be used+to override the default url builder. And every type-safe url in the+application goes through there, so it's perfect for this.++I just had to be careful to make it not add `auth=` to the url for the+favicon, which is included in the "Permission Denied" error page. That'd be+an amusing security hole..++----++Next up: Doing some AJAX to get a dynamic view of the state of the daemon,+including currently running transfers, in the webapp. AKA stuff I've never+done before, and that, unlike all this heavy Haskell Yesod, scares me. :)
+ doc/design/assistant/blog/day_45__long_polling.mdwn view
@@ -0,0 +1,66 @@+The webapp now displays actual progress bars, for the actual transfers+that the assistant is making! And it's seriously shiny.++[[!img full.png]]++Yes, I used Bootstrap. I can see why so many people are using it,+that the common complaint is everything looks the same. I spent a few hours+mocking up the transfer display part of the WebApp using Bootstrap, and+arrived at something that doesn't entirely suck remarkably quickly.++The really sweet thing about Bootstrap is that when I resized my browser to+the shape of a cell phone, it magically redrew the WebApp like so:++[[!img phone.png]]++---++To update the display, the WebApp uses two techniques. On noscript+browsers, it just uses a meta refresh, which is about the best I can do. I+welcome feedback; it might be better to just have an "Update" button in+this case.++With javascript enabled, it uses long polling, done over AJAX. There are+some other options I considered, including websockets, and server-sent+events. Websockets seem too new, and while there's a WAI module supporting+server-sent events, and even an example of them in the Yesod book, the+module is not packaged for Debian yet. Anyway, long polling is the most+widely supported, so a good starting place. It seems to work fine too, I+don't really anticipate needing the more sophisticated methods.++(Incidentially, this's the first time I've ever written code that uses AJAX.)++Currently the status display is rendered in html by the web server, and+just updated into place by javascript. I like this approach since it+keeps the javascript code to a minimum and the pure haskell code to a+maximum. But who knows, I may have to switch to JSON that gets rendered by+javascript, for some reason, later on.++---++I was very happy with Yesod when I managed to factor out a+general purpose widget that adds long-polling and meta-refresh to any+other widget. I was less happy with Yesod when I tried to include+jquery on my static site and it kept serving up a truncated version of it.+Eventually worked around what's seemingly a bug in the default WAI+middleware, by disabling that middleware.++----++Also yesterday I realized there were about 30 comments stuck in moderation on+this website. I thought I had a feed of those, but obviously I didn't. I've+posted them all, and also read them all.++----++Next up is probably some cleanup of bugs and minor todos. Including+figuring out why `watch` has started to segfault on OSX when it was+working fine before.++After that, I need to build a way to block the long polling request+until the DaemonStatus and/or TransferQueue change from the version+previously displayed by the WebApp. An interesting concurrency problem..++Once I have that working, I can reduce the current 3 second delay between+refreshes to a very short delay, and the WebApp will update in+near-realtime as changes come in.
+ doc/design/assistant/blog/day_45__long_polling/full.png view

binary file changed (absent → 55185 bytes)

+ doc/design/assistant/blog/day_45__long_polling/phone.png view

binary file changed (absent → 41602 bytes)

+ doc/design/assistant/blog/day_46__notification_pools.mdwn view
@@ -0,0 +1,68 @@+Focus today was writing a notification broadcaster library. This is a way to+send a notification to a set of clients, any of which can be blocked+waiting for a new notification to arrive. A complication is that any number+of clients may be be dead, and we don't want stale notifications for those+clients to pile up and leak memory.++It took me 3 tries to find the solution, which turns out to be head-smackingly+simple: An array of SampleVars, one per client.++Using SampleVars means that clients only see the most recent notification,+but when the notification is just "the assistant's state changed somehow;+display a refreshed rendering of it", that's sufficient.++----++First use of that was to make the thread that woke up every 10 minutes+and checkpointed the daemon status to disk also wait for a notification+that it changed. So that'll be more current, and use less IO.++----++Second use, of course, was to make the WebApp block long polling clients+until there is really a change since the last time the client polled.++To do that, I made one change to my Yesod routes:++[[!format diff """+	-/status StatusR GET+	+/status/#NotificationId StatusR GET+"""]]++Now I find another reason to love Yesod, because after doing that,+I hit "make".. and fixed the type error. And hit make.. and fixed+the type error. And then it just freaking worked! Html was generated with+all urls to /status including a `NotificationId`, and the handler for+that route got it and was able to use it:++[[!format haskell """+	{- Block until there is an updated status to display. -}+	b <- liftIO $ getNotificationBroadcaster webapp+	liftIO $ waitNotification $ notificationHandleFromId b nid+"""]]++And now the WebApp is able to display transfers in realtime!+When I have both the WebApp and `git annex get` running on the same screen,+the WebApp displays files that git-annex is transferring about as fast+as the terminal updates.++The [[progressbars]] still need to be sorted out, but otherwise+the WebApp is a nice live view of file transfers.++---++I also had some fun with Software Transactional Memory. Now when the+assistant moves a transfer from its queue of transfers to do, to its map of+transfers that are currently running, it does so in an atomic transaction.+This will avoid the transfer seeming to go missing (or be listed twice) if+the webapp refreshes at just the wrong point in time. I'm really starting+to get into STM.++----++Next up, I will be making the WebApp maintain a list of notices, displayed+on its sidebar, scrolling new notices into view, and removing ones the user+closes, and ones that expire. This will be used for displaying errors, as+well as other communication with the user (such as displaying a notice+while a git sync is in progress with a remote, etc). Seems worth doing now,+so the basic UI of the WebApp is complete with no placeholders.
+ doc/design/assistant/blog/day_47__alert_messages.mdwn view
@@ -0,0 +1,14 @@+Some days I spend 2 hours chasing red herrings (like "perhaps my JSON ajax+calls arn't running asynchronoously?") that turn out to be a simple+one-word typo. This was one of them.++However, I did get the sidebar displaying alert messages, which can be+easily sent to the user from any part of the assistant. This includes+transient alerts of things it's doing, which disappear once the action+finishes, and long-term alerts that are displayed until the user closes+them. It even supports rendering arbitrary Yesod widgets as alerts, so+they can also be used for asking questions, etc.++Time for a screencast!++<video controls src="http://joeyh.name/screencasts/git-annex-webapp.ogg"></video>
+ doc/design/assistant/blog/day_48__intro.mdwn view
@@ -0,0 +1,8 @@+Lots of WebApp UI improvements, mostly around the behavior when+displaying alert messages. Trying to make the alerts informative+without being intrusively annoying, think I've mostly succeeded now.++Also, added an intro display. Shown is the display with only one repo;+if there are more repos it also lists them all.++[[!img screenshot/intro.png]]
+ doc/design/assistant/blog/day_49__first_run_experience.mdwn view
@@ -0,0 +1,37 @@+Started work on the interface displayed when the webapp is started +with no existing git-annex repository. All this needs to do is walk the user+through setting up a repository, as simply as possible.++A tricky part of this is that most of git-annex runs in the Annex monad,+which requires a git-annex repository. Luckily, much of the webapp+does not run in Annex, and it was pretty easy to work around the parts that+do. Dodged a bullet there.++There will, however, be a tricky transition from this first run webapp,+to a normally fully running git-annex assistant and webapp. I think the+first webapp will have to start up all the normal threads once it makes the+repository, and then redirect the user's web browser to the full webapp.++Anyway, the UI I've made is very simple: A single prompt, for the+directory where the repository should go. With, eventually, tab completion,+sanity checking (putting the repository in "/" is not good, and making it+all of "$HOME" is probably unwise).++[[!img screenshot/firstrun.png]]++Ideally most users will accept the default, which will be something+like `/home/username/Desktop/Annex`, and be through this step in seconds.++Suggestions for a good default directory name appreciated.. Putting it on a+folder that will appear on the desktop seems like a good idea, when there's+a Desktop directory. I'm unsure if I should name it something specific like+"GitAnnex", or something generic like "Synced".++Time for the first of probably many polls!++What should the default directory name used by the git-annex assistant be?++[[!poll open=no 19 "Annex" 7 "GitAnnex" 10 "Synced" 0 "AutoSynced" 1 "Shared" 10 "something lowercase!" 1 "CowboyNeal" 1 "Annexbox"]]++(Note: This is a wiki. You can edit this page to add your own+[[ikiwiki/directive/poll]] options!)
+ doc/design/assistant/blog/day_50__directory_name.mdwn view
@@ -0,0 +1,20 @@+Based on the results of yesterday's poll, the WebApp defaults to+`~/Desktop/annex` when run in the home directory. If there's no `Desktop`+directory, it uses just `~/annex`. And if run from some other place than+the home directory, it assumes you want to use cwd. Of course, you can+change this default, but I think it's a good one for most use cases.++----++My work today has all been on making **one second** of the total lifetime+of the WebApp work. It's the very tricky second in between clicking on+"Make repository" and being redirected to a WebApp running in your new+repository. The trickiness involves threads, and MVars, and+multiple web servers, and I don't want to go into details here.+I'd rather forget. ;-)++Anyway, it works; you can run "git annex webapp" and be walked right+through to having a usable repository! Now I need to see about adding+that to the desktop menus, and making "git annex webapp", when run a second+time, remembering where your repository is. I'll use+`~/.config/git-annex/repository` for storing that.
+ doc/design/assistant/blog/day_51__desktop.mdwn view
@@ -0,0 +1,34 @@+Now installing git-annex automatically generates a freedesktop.org .desktop+file, and installs it, either system-wide (root) or locally (user). So+`Menu -> Internet -> Git Annex` will start up the web app.++(I don't entirely like putting it on the Internet menu, but the+Accessories menu is not any better (and much more crowded here), +and there's really no menu where it entirely fits.)++I generated that file by writing a generic library to deal with+freedesktop.org desktop files and locations. Which seemed like overkill at+the time, but then I found myself continuing to use that library. Funny how+that happens.++So, there's also another .desktop file that's used to autostart the+`git-annex assistant` daemon when the user logs into the desktop.++This even works when git-annex is installed to the ugly non-PATH location+`.cabal/bin/git-annex` by Cabal! To make that work, it records the path+the binary is at to a freedesktop.org data file, at install time.++---++That should all work in Gnome, KDE, XFCE, etc. Not Mac OSX I'm guessing...++---++Also today, I added a sidebar notification when the assistant notices new+files. To make that work well, I implemented merging of related sidebar+action notifications, so the effect is that there's one notification that+collectes a list of recently added files, and transient notifications that+show up if a really big file is taking a while to checksum.++I'm pleased that the notification interface is at a point where I was able+to  implement all that, entirely in pure functional code.
+ doc/design/assistant/blog/day_52__file_browser.mdwn view
@@ -0,0 +1,21 @@+Today I added a "Files" link in the navbar of the WebApp. It looks like a+regular hyperlink, but clicking on it opens up your desktop's native file+manager, to manage the files in the repository!++Quite fun to be able to do this kind of thing from a web page. :)++---++Made `git annex init` (and the WebApp) automatically generate a description+of the repo when none is provided.++---++Also worked on the configuration pages some. I don't want to get ahead+of myself by diving into the full configuration stage yet, but I am at+least going to add a configuration screen to clone the repo to a removable+drive.++After that, the list of transfers on the dashboard needs some love.+I'll probably start by adding UI to cancel running transfers, and then+try to get drag and drop reordering of transfers working.
+ doc/design/assistant/blog/day_54__adding_removable_drives.mdwn view
@@ -0,0 +1,99 @@+Spent yesterday and today making the WebApp handle adding removable drives.++While it needs more testing, I think that it's now possible to use the WebApp+for a complete sneakernet usage scenario.++* Start up the webapp, let it make a local repo.+* Add some files, by clicking to open the file manager, and dragging them in.+* Plug in a drive, and tell the webapp to add it.+* Wait while files sync..+* Take the drive to another computer, and repeat the process there.++No command-line needed, and files will automatically be synced between+two or more computers using the drive.++Sneakernet is only one usage scenario for the git-annex assistant, but I'm+really happy to have one scenario 100% working!++Indeed, since the assistant and webapp can now actually do something+useful, I'll probably be merging them into `master` soon.++Details follow..++---++So, yesterday's part of this was building the configuration page to add+a removable drive. That needs to be as simple as possible, and it currently+consists of a list of things git-annex thinks might be mount points of+removable drives, along with how much free space they have. Pick a drive,+click the pretty button, and away it goes..++(I decided to make the page so simple it doesn't even ask where you want+to put the directory on the removable drive. It always puts it in+a "annex" directory. I might add an expert screen later, but experts can+always set this up themselves at the command line too.)++I also fought with Yesod and Bootstrap rather a lot to make the form look good.+Didn't entirely succeed, and had to file a bug on Yesod about its handling of+check boxes. (Bootstrap also has a bug, IMHO; its drop down lists are not+always sized wide enough for their contents.)++Ideally this configuration page would listen for mount events, and refresh+its list. I may add that eventually; I didn't have a handy channel it+could use to do that, so defferred it. Another idea is to have the mount+event listener detect removable drives that don't have an annex on them yet,+and pop up an alert with a link to this configuration page.++----++Making the form led to a somewhat interesting problem: How to tell if a mounted+filesystem is a removable drive, or some random thing like `/proc` or+a fuse filesystem. My answer, besides checking that the user can+write to it, was various heuristics, which seem to work ok, at least here..++[[!format haskell """+               sane Mntent { mnt_dir = dir, mnt_fsname = dev }+                        {- We want real disks like /dev/foo, not+                         - dummy mount points like proc or tmpfs or+                         - gvfs-fuse-daemon. -}+                        | not ('/' `elem` dev) = False+                        {- Just in case: These mount points are surely not+                         - removable disks. -}+                        | dir == "/" = False+                        | dir == "/tmp" = False+                        | dir == "/run/shm" = False+                        | dir == "/run/lock" = False+"""]]++----++Today I did all the gritty coding to make it create a git repository on the+removable drive, and tell the Annex monad about it, and ensure it gets synced.++As part of that, it detects when the removable drive's filesystem doesn't+support symlinks, and makes a bare repository in that case. Another expert+level config option that's left out for now is to always make a bare+repository, or even to make a directory special remote rather than a git+repository at all. (But directory special remotes cannot support the+sneakernet use case by themselves...)++----++Another somewhat interesting problem was what to call the git remotes+that it sets up on the removable drive and the local repository.+Again this could have an expert-level configuration, but the defaults+I chose are to use the hostname as the remote name on the removable drive,+and to use the basename of the mount point of the removable drive as the +remote name in the local annex.++----++Originally, I had thought of this as cloning the repository to the drive.+But, partly due to luck, I started out just doing a `git init` to make+the repository (I had a function lying around to do that..).++And as I worked on it some more, I realized this is not as simple as a+clone. It's a bi-directional sync/merge, and indeed the removable drive may+have all the data already in it, and the local repository have just been+created. Handling all the edge cases of that (like, the local repository+may not have a "master" branch yet..) was fun!
+ doc/design/assistant/blog/day_55__alerts.mdwn view
@@ -0,0 +1,10 @@+Nothing flashy today; I was up all night trying to download photos taken +by a robot lowered onto Mars by a skycrane.++Some work on alerts. Added an alert when a file transfer succeeds or fails.+Improved the alert combining code so it handles those alerts, and+simplified it a lot, and made it more efficient.++Also made the text of action alerts change from present to past tense when+the action finishes. To support that I wrote a fun data type, a `TenseString`+that can be rendered in either tense.
+ doc/design/assistant/comment_10_f2233fad55c20686cf299bf6788f1f23._comment view
@@ -0,0 +1,10 @@+[[!comment format=mdwn+ username="http://www.klomp.eu/"+ ip="95.91.241.82"+ subject="Watch also possible with git?"+ date="2012-06-15T17:25:30Z"+ content="""+Hi,++it seems that you put a lot of efforts in handling race conditions. Thats great. I wonder if the watch can also be used with git (i.e. changes are commited into git and not as annex)? I know that other projects follow this idea but why using different tools if the git-annex assistant could handle both...+"""]]
+ doc/design/assistant/comment_9_d052e2142da8b4838fb1edf791ea23ae._comment view
@@ -0,0 +1,10 @@+[[!comment format=mdwn+ username="http://wiggy.net/"+ nickname="Wichert"+ subject="macports"+ date="2012-06-12T13:00:34Z"+ content="""+The average OSX user has a) no idea what macports is, and b) will not be able to install it. Anything that requires a user to do anything with a commandline (or really anything other than using a GUI installer) is effectively a dealbreaker. For our use cases OSX is definitely a requirement, but it must only use standard OSX installation methods in order to be usable. Being in the appstore would be ideal, but standard dmg/pkg installers are still common enough that they are also acceptable.++FWIW this is the same reason many git GUIs were not usable for our OSX users: they required separate installation of the git commandline tools.+"""]]
+ doc/design/assistant/screenshot/firstrun.png view

binary file changed (absent → 54347 bytes)

+ doc/design/assistant/screenshot/intro.png view

binary file changed (absent → 50730 bytes)

doc/design/assistant/syncing.mdwn view
@@ -3,20 +3,20 @@  ## immediate action items -* At startup, and possibly periodically, look for files we have that-  location tracking indicates remotes do not, and enqueue Uploads for-  them. Also, enqueue Downloads for any files we're missing.-* After git sync, identify content that we don't have that is now available-  on remotes, and transfer. But first, need to ensure that when a remote-  receives content, and updates its location log, it syncs that update-  out.-* When MountWatcher detects a newly mounted drive, rescan git remotes-  in order to get ones on the drive, and do a git sync and file transfers-  to sync any repositories on it.+* At startup, and possibly periodically, or when the network connection+  changes, or some heuristic suggests that a remote was disconnected from+  us for a while, queue remotes for processing by the TransferScanner.+* Ensure that when a remote receives content, and updates its location log,+  it syncs that update back out. Prerequisite for:+* After git sync, identify new content that we don't have that is now available+  on remotes, and transfer. (Needed when we have a uni-directional connection+  to a remote, so it won't be uploading content to us.) Note: Does not+  need to use the TransferScanner, if we get and check a list of the changed+  files.  ## longer-term TODO -* Test MountWatcher on Gnome (should work ok) and LXDE (dunno).+* Test MountWatcher on LXDE. * git-annex needs a simple speed control knob, which can be plumbed   through to, at least, rsync. A good job for an hour in an   airport somewhere.@@ -36,6 +36,12 @@ * speed up git syncing by using the cached ssh connection for it too   (will need to use `GIT_SSH`, which needs to point to a command to run,   not a shell command line)+* Map the network of git repos, and use that map to calculate+  optimal transfers to keep the data in sync. Currently a naive flood fill+  is done instead.+* Find a more efficient way for the TransferScanner to find the transfers+  that need to be done to sync with a remote. Currently it walks the git+  working copy and checks each file.  ## data syncing @@ -59,6 +65,47 @@ reachable remote. This is worth doing first, since it's the simplest way to get the basic functionality of the assistant to work. And we'll need this anyway.++## TransferScanner++The TransferScanner thread needs to find keys that need to be Uploaded+to a remote, or Downloaded from it.++How to find the keys to transfer? I'd like to avoid potentially+expensive traversals of the whole git working copy if I can.+(Currently, the TransferScanner does do the naive and possibly expensive+scan of the git working copy.)++One way would be to do a git diff between the (unmerged) git-annex branches+of the git repo, and its remote. Parse that for lines that add a key to+either, and queue transfers. That should work fairly efficiently when the+remote is a git repository. Indeed, git-annex already does such a diff+when it's doing a union merge of data into the git-annex branch. It+might even be possible to have the union merge and scan use the same+git diff data.++But that approach has several problems:++1. The list of keys it would generate wouldn't have associated git+   filenames, so the UI couldn't show the user what files were being+   transferred.+2. Worse, without filenames, any later features to exclude+   files/directories from being transferred wouldn't work.+3. Looking at a git diff of the git-annex branches would find keys+   that were added to either side while the two repos were disconnected.+   But if the two repos' keys were not fully in sync before they+   disconnected (which is quite possible; transfers could be incomplete),+   the diff would not show those older out of sync keys.++The remote could also be a special remote. In this case, I have to either+traverse the git working copy, or perhaps traverse the whole git-annex+branch (which would have the same problems with filesnames not being+available).++If a traversal is done, should check all remotes, not just+one. Probably worth handling the case where a remote is connected+while in the middle of such a scan, so part of the scan needs to be+redone to check it.  ## done 
doc/design/assistant/webapp.mdwn view
@@ -2,19 +2,23 @@  ## security -* Listen only to localhost.+* Listen only to localhost. **done** * Instruct the user's web browser to open an url that contains a secret-  token. This guards against other users on the same system.-* I would like to avoid passwords or other authentication methods,-  it's your local system.+  token. This guards against other users on the same system. **done**+  (I would like to avoid passwords or other authentication methods,+  it's your local system.)+* Don't pass the url with secret token directly to the web browser,+  as that exposes it to `ps`. Instead, write a html file only the user can read,+  that redirects to the webapp. **done** * Alternative for Linux at least would be to write a small program using   GTK+ Webkit, that runs the webapp, and can know what user ran it, avoiding   needing authentication.  ## interface -* list of files uploading and downloading-* progress bars for each file+* list of files uploading and downloading **done**+* button to open file browser on repo (`xdg-open $DIR`) **done**+* progress bars for each file (see [[progressbars]]) * drag and drop to reorder * cancel and pause * keep it usable w/o javascript, and accessible to blind, etc@@ -25,14 +29,16 @@   over http by the web app * Display any relevant warning messages. One is the `inotify max_user_watches`   exceeded message.--## implementation--Hope to use Yesod.+* possibly add a desktop file to the top of the repository that can be used+  to open the webapp (rather than using the menus). Would be complicated+  some by the path to git-annex sometimes needing to be hardcoded and varying+  across systems, so it would need to be a symlink to `.git/annex/desktop`+  which would be per-system. -TODO: Ensure that Yesod will work on arm. Necessary for later Android port.-Will its template haskell cause a problem? Does new GHC support TH on ARM?-Will it use too much memory or be too slow?+## first start **done** -Hopefully Yesod comes with some good UI widgets. Otherwise, need to use-Jquery or similar.+* make git repo **done**+* generate a nice description like "joey@hostname Desktop/annex" **done**+* record repository that was made, and use it next time run **done**+* write a pid file, to prevent more than one first-start process running+  at once **done**
+ doc/forum/DS__95__Store_files_are_not_added.mdwn view
@@ -0,0 +1,3 @@+The "git annex add" command adds new file to the annex. However ".DS_Store" files are ignored by git-annex. Is there a list of files that are being ignored? ++Maybe sometimes it's useful to add .DS_Store extended attribute data to the annex to ensure a complete sync of Mac files...
+ doc/forum/Delete_unused_files__47__metadata.mdwn view
@@ -0,0 +1,7 @@+After moving some files (about 1G, some big and some small files) in and out the annex, I noticed that the size of the repository has grown quite a bit. My empty repository now is over 100 MB (even after  "git annex dropunused ..." and "git gc").++Most of this size is not Git metadata but many small files in the git-annex branch that seem to hold information about files I deleted (even in the other known repositories).++So is there a way to get rid of these useless but space consuming information?++(Maybe there is no (elegant) way to remove the symlink versions from the Git history (is there?), but it would already be nice if those small git-annex metadata files could be removed)
+ doc/forum/Fixing_up_corrupt_annexes.mdwn view
@@ -0,0 +1,10 @@+I was wondering how does one recover from...++<pre>+(Recording state in git...)+error: invalid object 100644 8f154c946adc039af5240cc650a0a95c840e6fa6 for '041/5a4/SHA256-s6148--7ddcf853e4b16e77ab8c3c855c46867e6ed61c7089c334edf98bbdd3fb3a89ba.log'+fatal: git-write-tree: error building trees+git-annex: failed to read sha from git write-tree+</pre>++The above was caught when i ran a "git annex fsck --fast" to check stash of files"
+ doc/forum/Git_repositories_in_the_annex__63__.mdwn view
@@ -0,0 +1,5 @@+First of all thanks for the great work. git-annex looks very nice already!++I wonder if it's possible to add Git repositories to the annex. In my current Dropbox setup I drop some small Git repositories into the Dropbox to keep them in sync on two computers. ++This is obviously not possible with git-annex, as the annex itself is a Git repository and sub-repositories (directories with .git folders) are ignored. But in some cases people might want to be able to drop "anything" into the annex, maybe even Git repositories (e.g. the "nomad" usecase)...
+ doc/forum/Looking_at_the_webapp_on_OSX.mdwn view
@@ -0,0 +1,18 @@+Not logging this in the bugs section, but poking at the new webapp feature...++<pre>+laplace:annex jtang$ git annex webapp -d+[2012-07-26 19:02:50 IST] read: git ["--git-dir=/Users/jtang/annex/.git","--work-tree=/Users/jtang/annex","show-ref","git-annex"] +[2012-07-26 19:02:50 IST] read: git ["--git-dir=/Users/jtang/annex/.git","--work-tree=/Users/jtang/annex","show-ref","--hash","refs/heads/git-annex"] +[2012-07-26 19:02:50 IST] read: git ["--git-dir=/Users/jtang/annex/.git","--work-tree=/Users/jtang/annex","log","refs/heads/git-annex..731005d121426a38b206c4544da02cdb3b974974","--oneline","-n1"] +[2012-07-26 19:02:50 IST] read: git ["--git-dir=/Users/jtang/annex/.git","--work-tree=/Users/jtang/annex","log","refs/heads/git-annex..d36d8d88847decc2320f0be22892ad94a8abe594","--oneline","-n1"] +[2012-07-26 19:02:50 IST] read: git ["--git-dir=/Users/jtang/annex/.git","--work-tree=/Users/jtang/annex","log","refs/heads/git-annex..57bcddc14d03b61028f7002e2dabcc5181d74f3d","--oneline","-n1"] +[2012-07-26 19:02:50 IST] read: git ["--git-dir=/Users/jtang/annex/.git","--work-tree=/Users/jtang/annex","log","refs/heads/git-annex..372aceaf49b60ebe31cc3fe2e52ba4fbe99c134f","--oneline","-n1"] +[2012-07-26 19:02:50 IST] chat: git ["--git-dir=/Users/jtang/annex/.git","--work-tree=/Users/jtang/annex","cat-file","--batch"] +[2012-07-26 19:02:50 IST] read: git ["config","--null","--list"] +[2012-07-26 19:02:50 IST] call: open ["file:///Users/jtang/annex/.git/annex/webapp.html"] +The file /Users/jtang/annex/.git/annex/webapp.html does not exist.+git-annex: failed to start web browser on url file:///Users/jtang/annex/.git/annex/webapp.html+</pre>++I would have expected the open command to open up http://localhost:port/ instead of a file on my machine. Anyway, its just an observation on the current state of the webapp feature, not expecting it to work enough for me to test it ;)
+ doc/forum/Wishlist:_Don__39__t_make_files_readonly.mdwn view
@@ -0,0 +1,3 @@+Maybe this explained somewhere else, but what is the purpose of marking files readonly. To me this is an annoyance that doesn't make sense. I want to be able to change my files, having to go through an unlock step, to do that seems like unnecessary work. Interestingly, Microsoft's Team Foundation Server source control does the same thing and I don't like it there either.++In addition why replace files with symlinks? Why not just leave the real files in place, or do the reverse and put the symlink to the file in the repository.
+ doc/forum/git_unannex_speed.mdwn view
@@ -0,0 +1,1 @@+It was fast to git annex a bunch of files. But git unannex seems a lot slower. Is there a faster way to get files out of git annex? Or to replace the symlinks with real files and then I could just remove the .git directory? I shouldn't have put so many in as a test but they are there now.
+ doc/forum/public-web-frontend.mdwn view
@@ -0,0 +1,16 @@+Hi,++Use case: I would like to have a "Public" top-level directory in my annex, which gets files in there published over HTTP on a particular server.++How I see doing this:++1. Put my annex to an http server with exported-over-http `/Public/` directory.+2. Configure a `post-update` hook with the following:++        $ git annex fix++3. Push files on `/Public/` to that annex.++Does it make sense? If yes, are there any gotchas I should beware of?++Thanks.
doc/install.mdwn view
@@ -9,8 +9,8 @@ * [[ArchLinux]] * [[NixOS]] * [[Gentoo]]-* Windows: [[sorry, not possible yet|todo/windows_support]] * [[ScientificLinux5]] - This should cover RHEL5 clones such as CentOS5 and so on+* Windows: [[sorry, not possible yet|todo/windows_support]]  ## Using cabal 
+ doc/install/Debian/comment_3_4d922e11249627634ecc35bba4044d9e._comment view
@@ -0,0 +1,8 @@+[[!comment format=mdwn+ username="https://www.google.com/accounts/o8/id?id=AItOawkstq9oH1vHXY_VP0nYO9Gg3eKnKerDGRI"+ nickname="Hadi"+ subject="ARM"+ date="2012-07-31T15:13:06Z"+ content="""+is there any package for Debian armhf? I'd love to install git-annex on my raspberry pi+"""]]
+ doc/install/Debian/comment_4_2a93ab18b05ccb90e7acc5885866fca2._comment view
@@ -0,0 +1,9 @@+[[!comment format=mdwn+ username="http://joeyh.name/"+ subject="comment 4"+ date="2012-07-31T15:41:43Z"+ content="""+Yes, git-annex is available for every Debian architecture which supports Haskell, including all arm ports:++<pre>git-annex | 3.20120629         | wheezy            | source, amd64, armel, armhf, i386, kfreebsd-amd64, kfreebsd-i386, mips, mipsel, powerpc, s390, s390x, sparc</pre>+"""]]
doc/install/Fedora.mdwn view
@@ -1,5 +1,11 @@-Installation recipe for Fedora 14 thruough 17.+git-annex is recently finding its way into Fedora. +* [Status of getting a Fedora package](https://bugzilla.redhat.com/show_bug.cgi?id=662259)+* [Koji build for F17](http://koji.fedoraproject.org/koji/buildinfo?buildID=328654)+* [Koji build for F16](http://koji.fedoraproject.org/koji/buildinfo?buildID=328656)++Installation recipe for Fedora 14 thruough 15.+ <pre> sudo yum install ghc cabal-install pcre-devel git clone git://git-annex.branchable.com/ git-annex@@ -15,6 +21,3 @@ Note: You can't just use `cabal install git-annex`, because Fedora does not yet ship ghc 7.4. -* [Status of getting a Fedora package](https://bugzilla.redhat.com/show_bug.cgi?id=662259)a-* [Koji build for F17](http://koji.fedoraproject.org/koji/buildinfo?buildID=328654)-* [Koji build for F16](http://koji.fedoraproject.org/koji/buildinfo?buildID=328656)
− doc/install/OSX/comment_10_798000aab19af2944b6e44dbc550c6fe._comment
@@ -1,10 +0,0 @@-[[!comment format=mdwn- username="http://joeyh.name/"- ip="4.153.2.25"- subject="comment 10"- date="2012-06-25T15:38:44Z"- content="""-@Agustin you should be able to work around that with: cabal install git-annex --flags=-Inotify--I've fixed it properly for the next release, it should only be using that library on Linux.-"""]]
− doc/install/OSX/comment_11_707a1a27a15b2de8dfc8d1a30420ab4c._comment
@@ -1,10 +0,0 @@-[[!comment format=mdwn- username="https://www.google.com/accounts/o8/id?id=AItOawkwR9uOA38yi5kEUvcEWNtRiZwpxXskayE"- nickname="Agustin"- subject="comment 11"- date="2012-06-27T08:54:52Z"- content="""-Hi @joey! Perfect!... I'll do that then!--Thanks for your time man!-"""]]
− doc/install/OSX/comment_12_60d13f2c8e008af1041bea565a392c83._comment
@@ -1,8 +0,0 @@-[[!comment format=mdwn- username="https://www.google.com/accounts/o8/id?id=AItOawnHrjHxJAm39x8DR4bnbazQO6H0nMNuY9c"- nickname="Damien"- subject="sha256 alternative"- date="2012-06-30T14:34:11Z"- content="""-in reply to comment 6: On my Mac (10.7.4) there's `/usr/bin/shasum -a 256 <file>` command that will produce the same output as `sha256sum <file>`.-"""]]
− doc/install/OSX/comment_13_a6f48c87c2d6eabe379d6e10a6cac453._comment
@@ -1,8 +0,0 @@-[[!comment format=mdwn- username="https://www.google.com/accounts/o8/id?id=AItOawnHrjHxJAm39x8DR4bnbazQO6H0nMNuY9c"- nickname="Damien"- subject="gnu commands"- date="2012-07-01T17:03:57Z"- content="""-…and another approach to the same problem: apparently git-annex also relies on the GNU coreutils (for instance, when doing `git annex get .`, `cp` complains about `illegal option -- -`). I do have the GNU coreutils installed with Homebrew, but they are all prefixed with `g`. So maybe you should try `gsha256sum` and `gcp` before `sha256sum` and `cp`, that seems like a more general solution.-"""]]
− doc/install/OSX/comment_14_6ef2ddb7b11ce6ad54578ae118ed346e._comment
@@ -1,9 +0,0 @@-[[!comment format=mdwn- username="http://joeyh.name/"- subject="comment 14"- date="2012-07-04T12:43:54Z"- content="""-@Damien, hmm, it should not be using any cp options, unless when it was built there was a cp in the path that supported some option like -p. Can you check with --debug what cp parameters it's trying to use?---"""]]
− doc/install/OSX/comment_15_6fd1fad5b6d9f36620e5a0e99edd2f89._comment
@@ -1,9 +0,0 @@-[[!comment format=mdwn- username="http://joeyh.name/"- subject="comment 15"- date="2012-07-04T13:14:00Z"- content="""-git-annex will now fall back to slower pure Haskell hashing code if `sha256sum`, etc programs are not in PATH. I'd still recommend installing the coreutils, as they're probably faster.--(The `shasum` command seems to come from a perl library, so I have not tried to make git-annex use that one.)-"""]]
− doc/install/OSX/comment_2_0327c64b15249596add635d26f4ce67f._comment
@@ -1,19 +0,0 @@-[[!comment format=mdwn- username="https://www.google.com/accounts/o8/id?id=AItOawkEUhIcw37X2Kh-dznSMIb9Vgcq0frfdWs"- nickname="Ethan"- subject="GHC 7"- date="2012-03-28T19:06:51Z"- content="""-The Haskell Platform installer for OSX uses GHC 7.0.4, which doesn't seem able to support the current version of git-annex.--Cabal throws a very cryptic error about not being able to use the proper base package.--I was able to install it by --1.  cloning the repo-2.  merging the ghc7.0 branch-3.  resolving merge conflicts in git-annex.cabal-4.  cabal install git-annex.cabal--(Note I also tried this with homebrew and had similar results)-"""]]
+ doc/install/OSX/comment_2_25552ff2942048fafe97d653757f1ad6._comment view
@@ -0,0 +1,7 @@+[[!comment format=mdwn+ username="http://joeyh.name/"+ subject="comment 2"+ date="2012-07-24T15:09:29Z"+ content="""+I've moved some outdated comments about installing on OSX to [[old_comments]].+"""]]
− doc/install/OSX/comment_3_47c682a779812dda77601c24a619923c._comment
@@ -1,8 +0,0 @@-[[!comment format=mdwn- username="http://joey.kitenet.net/"- nickname="joey"- subject="ghc 7.0"- date="2012-03-28T19:18:58Z"- content="""-You did the right thing, although just checking out the ghc-7.0 branch will avoid merge conflicts. I am trying to keep it fairly close to up-to-date.-"""]]
+ doc/install/OSX/comment_3_733147cebe501c60f2141b711f1d7f24._comment view
@@ -0,0 +1,16 @@+[[!comment format=mdwn+ username="https://www.google.com/accounts/o8/id?id=AItOawnnIQkoUQo4RYzjUNyiB3v6yJ5aR41WG8k"+ nickname="Markus"+ subject="Updated install instructions with homebrew"+ date="2012-08-07T06:46:47Z"+ content="""+To install git annex with homebrew simply do:++    brew update+    brew install haskell-platform git ossp-uuid md5sha1sum coreutils pcre+    cabal install git-annex++Then link the binary to your `PATH` e.g. with++    ln -s ~/.cabal/bin/git-annex* /usr/local/bin/+"""]]
− doc/install/OSX/comment_4_e6109a964064a2a799768a370e57801d._comment
@@ -1,30 +0,0 @@-[[!comment format=mdwn- username="https://www.google.com/accounts/o8/id?id=AItOawkO9tsPZkAxEulq2pGCdwz4md-LqB0RcMw"- nickname="Reimund"- subject="Problems with Base & Crypto"- date="2012-04-25T22:56:18Z"- content="""-I got the following error message trying to install git-annex:--    cabal: cannot configure git-annex-3.20120418. It requires base >=4.5 && <5-    For the dependency on base >=4.5 && <5 there are these packages: base-4.5.0.0.-    However none of them are available.-    base-4.5.0.0 was excluded because of the top level dependency base -any--These are the steps I performed to make it work--1. Download [Ghc 7.4](http://www.haskell.org/ghc/download).-2. Run `sudo cabal install git-annex --bindir=$HOME/bin`.-3. Compilation of the Crypto-4.2.4 dependency failed since it's not updated to work with Ghc 7.4. You need to patch SHA2.hs (steps below).-4. Run `sudo cabal install git-annex --bindir=$HOME/bin` a second time.--The steps I did to patch the SHA2.hs file in Crypto-4.2.4:--1. `cabal unpack crypto-4.2.4`-2. `cd Crypto-4.2.4`-3. `patch -p1 < crypto-4.2.4-ghc-7.4.patch`-4. `sudo cabal install`.--PS: I used [this patchfile](http://sources.gentoo.org/cgi-bin/viewvc.cgi/gentoo-x86/dev-haskell/crypto/files/crypto-4.2.4-ghc-7.4.patch?revision=1.1).-Then I did the last step a third time.-"""]]
− doc/install/OSX/comment_5_50777853f808d57b957f8ce9a0f84b3d._comment
@@ -1,10 +0,0 @@-[[!comment format=mdwn- username="https://www.google.com/accounts/o8/id?id=AItOawnHrjHxJAm39x8DR4bnbazQO6H0nMNuY9c"- nickname="Damien"- subject="sha256"- date="2012-06-01T16:13:05Z"- content="""-If you're missing the `sha256sum` command with Homebrew, it's provided by `coreutils`. You have to change your `$PATH` before running `cabal install git-annex.cabal`:--    PATH=\"$(brew --prefix coreutils)/libexec/gnubin:$PATH\"-"""]]
− doc/install/OSX/comment_6_18a8df794aa0ddd294dbf17d3d4c7fe2._comment
@@ -1,7 +0,0 @@-[[!comment format=mdwn- username="http://joeyh.name/"- subject="comment 6"- date="2012-06-01T17:24:29Z"- content="""-Last night I made it look in /opt/local/libexec/gnubin .. if there's another directory it could look in, let me know. I am reluctant to make it run the brew command directly.-"""]]
− doc/install/OSX/comment_7_2ce7acab15403d3f993cec94ec7f3bc6._comment
@@ -1,14 +0,0 @@-[[!comment format=mdwn- username="http://www.davidhaslem.com/"- nickname="David"- subject="comment 7"- date="2012-06-19T04:41:27Z"- content="""-$(brew --prefix) should, in most cases, be /usr/local.  That's the recommended install location for homebrew.--I already had git installed and homebrew as my package manager - my install steps were as follows:--1. brew install haskell-platform ossp-uuid md5sha1sum coreutils pcre-2. PATH=\"$(brew --prefix coreutils)/libexec/gnubin:$PATH\" cabal install git-annex--"""]]
− doc/install/OSX/comment_8_a93ad4b67c5df4243268bcf32562f6be._comment
@@ -1,39 +0,0 @@-[[!comment format=mdwn- username="https://www.google.com/accounts/o8/id?id=AItOawkwR9uOA38yi5kEUvcEWNtRiZwpxXskayE"- nickname="Agustin"- subject="Installation not working on OS X 10.6.8"- date="2012-06-25T02:21:40Z"- content="""-I try installing with brew because I already had brew setup in my machine, but all run ok but when I try to run cabal install git-annex I got an error with the hinotify-0.3.2 library complaining about a header file.--Full trace:--~~~-sudo cabal install git-annex-Resolving dependencies...-Configuring hinotify-0.3.2...-Building hinotify-0.3.2...-Preprocessing library hinotify-0.3.2...-INotify.hsc:35:25: error: sys/inotify.h: No such file or directory-INotify.hsc: In function ‘main’:-INotify.hsc:259: error: invalid use of undefined type ‘struct inotify_event’-INotify.hsc:260: error: invalid use of undefined type ‘struct inotify_event’-INotify.hsc:261: error: invalid use of undefined type ‘struct inotify_event’-INotify.hsc:262: error: invalid use of undefined type ‘struct inotify_event’-INotify.hsc:265: error: invalid use of undefined type ‘struct inotify_event’-INotify.hsc:266: error: invalid application of ‘sizeof’ to incomplete type ‘struct inotify_event’ -compiling dist/build/System/INotify_hsc_make.c failed (exit code 1)-command was: /usr/bin/gcc -c dist/build/System/INotify_hsc_make.c -o dist/build/System/INotify_hsc_make.o -m64 -fno-stack-protector -m64 -D__GLASGOW_HASKELL__=704 -Ddarwin_BUILD_OS -Ddarwin_HOST_OS -Dx86_64_BUILD_ARCH -Dx86_64_HOST_ARCH -I/usr/local/Cellar/ghc/7.4.1/lib/ghc-7.4.1/directory-1.1.0.2/include -Idist/build/autogen -include dist/build/autogen/cabal_macros.h -I/usr/local/Cellar/ghc/7.4.1/lib/ghc-7.4.1/unix-2.5.1.0/include -Idist/build/autogen -include dist/build/autogen/cabal_macros.h -I/usr/local/Cellar/ghc/7.4.1/lib/ghc-7.4.1/old-time-1.1.0.0/include -Idist/build/autogen -include dist/build/autogen/cabal_macros.h -Idist/build/autogen -include dist/build/autogen/cabal_macros.h -Idist/build/autogen -include dist/build/autogen/cabal_macros.h -Idist/build/autogen -include dist/build/autogen/cabal_macros.h -Idist/build/autogen -include dist/build/autogen/cabal_macros.h -I/usr/local/Cellar/ghc/7.4.1/lib/ghc-7.4.1/bytestring-0.9.2.1/include -Idist/build/autogen -include dist/build/autogen/cabal_macros.h -Idist/build/autogen -include dist/build/autogen/cabal_macros.h -I/usr/local/Cellar/ghc/7.4.1/lib/ghc-7.4.1/base-4.5.0.0/include -Idist/build/autogen -include dist/build/autogen/cabal_macros.h -Idist/build/autogen -include dist/build/autogen/cabal_macros.h -Idist/build/autogen -include dist/build/autogen/cabal_macros.h -I/usr/local/Cellar/ghc/7.4.1/lib/ghc-7.4.1/include -Idist/build/autogen -include dist/build/autogen/cabal_macros.h -I/usr/local/Cellar/ghc/7.4.1/lib/ghc-7.4.1/include/-cabal: Error: some packages failed to install:-git-annex-3.20120624 depends on hinotify-0.3.2 which failed to install.-hinotify-0.3.2 failed during the building phase. The exception was:-ExitFailure 1-~~~--Anyone has an idea how can I solve this.--Thanks for the time!--Agustin--"""]]
− doc/install/OSX/comment_9_ae3ed5345bc84f57e44251d2e6c39342._comment
@@ -1,14 +0,0 @@-[[!comment format=mdwn- username="https://www.google.com/accounts/o8/id?id=AItOawkwR9uOA38yi5kEUvcEWNtRiZwpxXskayE"- nickname="Agustin"- subject="For the moment"- date="2012-06-25T02:51:10Z"- content="""-Hi Joey! I just comment that I could not install it but the issue is with the last version (the one you just release today, so no problem!! man on sunday??  you're awesome!!!) so I installed the previous one and no problem at all--Thanks for all the efford and if you need me to try os whatever, feel free to ask!--Thanks again--Agustin-"""]]
+ doc/install/OSX/old_comments.mdwn view
@@ -0,0 +1,1 @@+Moved a bunch of outdated comments here, AFAIK all these issues are fixed.
− doc/news/version_3.20120614.mdwn
@@ -1,6 +0,0 @@-git-annex 3.20120614 released with [[!toggle text="these changes"]]-[[!toggleable text="""-   * addurl: Was broken by a typo introduced 2 released ago, now fixed.-     Closes: #[677576](http://bugs.debian.org/677576)-   * Install man page when run by cabal, in a location where man will-     find it, even when installing under $HOME. Thanks, Nathan Collins"""]]
+ doc/news/version_3.20120807.mdwn view
@@ -0,0 +1,7 @@+git-annex 3.20120807 released with [[!toggle text="these changes"]]+[[!toggleable text="""+   * initremote: Avoid recording remote's description before checking+     that its config is valid.+   * unused, status: Avoid crashing when ran in bare repo.+   * Avoid crashing when "git annex get" fails to download from one+     location, and falls back to downloading from a second location."""]]
doc/sync.mdwn view
@@ -1,7 +1,7 @@ The `git annex sync` command provides an easy way to keep several repositories in sync.  -Often git is used in a centralized fashion with a central bare repositry+Often git is used in a centralized fashion with a central bare repository which changes are pulled and pushed to using normal git commands. That works fine, if you don't mind having a central repository. 
+ doc/tips/assume-unstaged/comment_1_44abd811ef79a85e557418e17a3927be._comment view
@@ -0,0 +1,10 @@+[[!comment format=mdwn+ username="https://me.yahoo.com/a/2djv2EYwk43rfJIAQXjYt_vfuOU-#a11a6"+ nickname="Olivier R"+ subject="It doesn't work 100%"+ date="2012-05-03T21:42:54Z"+ content="""+When you remove tracked files... it doesn't show the new status. it's like if the file was ignored.+++"""]]
doc/tips/what_to_do_when_you_lose_a_repository.mdwn view
@@ -16,4 +16,4 @@ If you later found the drive, you could let git-annex know it's found like so: -	git annex semitrusted usbdrive+	git annex semitrust usbdrive
+ doc/todo/windows_support/comment_3_bd0a12f4c9b884ab8a06082842381a01._comment view
@@ -0,0 +1,8 @@+[[!comment format=mdwn+ username="http://xolus.net/openid/max"+ nickname="B0FH"+ subject="What about NTFS support ?"+ date="2012-08-02T17:45:10Z"+ content="""+Has git-annex been tested with an NTFS-formatted disk under Linux ? NTFS is supposed to be case-sensitive and to allow symlinks, and these are supposed to work with ntfs3g.+"""]]
git-annex.cabal view
@@ -1,5 +1,5 @@ Name: git-annex-Version: 3.20120721+Version: 3.20120807 Cabal-Version: >= 1.8 License: GPL Maintainer: Joey Hess <joey@kitenet.net>