A shared “drop-box” using Samba [Updated]

Here’s a neat thing I managed to sort out the other day.

If you have read any of the “Untangle, Asterisk and File Server; All-in-One” series of posts before, then you will know that I’ve got a neat little VIA CN700 server for our home that is running all sorts of good stuff.

One of the things I have wanted to do for a while was to create a shared directory on the server so any family member can put stuff in there (like music files etc) but not be able to delete anything so as to prevent accidentally removing thousands of MP3s or irreplaceable digital pictures for example. This facility is apparently called a “drop-box”.

Hmmmm. Now let me think… Linux file permissions are rwx: Read Write eXecute. So, if you have write access, you can delete too. How can I fix this?

After some Googling and reading the Samba documentation it is actually pretty straightforward. Here’s how to make a drop-box on a Linux file server using Samba (CIFS) as the file sharing protocol and access mechanism.

  • Create a directory somewhere on your server and give it a sensible name: I called it “shared” and put it under the /home tree.
  • Create a Linux group for all users who you want to access the drop-box: I called the group “shared”. Then add your users to that group.
  • Using sudo or running as root, change the the directory settings as follows:
    • chmod 770 shared. This prevents access to the directory by anyone other than root, and the owner and group members.
    • chown nobody:shared shared. This changes the directory ownership to a user “nobody” and the group “shared”. It is important that you use a user who is NOT a member of the shared group. Any user will do, but it must be defined in/etc/passwd. I chose “nobody” as it has very minimal permissions and is unlikely to pose any sort of security hazard. On my server, the user nobody is configured thus:nobody:x:99:99:Unprivileged User:/dev/null:/bin/false
    • chmod g+s shared/. This sets the directory’s SGID bit so that any new files or directories created in our shared directory will have their group id set to that of the of the shared directory. This ensures all members of the shared group can read the contents.
    • chmod +t shared This sets the “sticky bit” of our shared directory. On Linux, setting the sticky bit, means items inside the directory can be renamed or deleted only by the item’s owner, the directory’s owner, or the superuser; without the sticky bit set, any user with write and execute permissions for the directory can rename or delete contained files, regardless of owner.
    • Here’s a listing of the directory showing how it should look now:drwxrws--T 3 nobody shared 62 2008-04-15 21:48 shared

Now we can set-up our share in Samba as follows:


[shared]
comment = Our Shared Data/Media
path = /home/shared/
read only = no
valid users = @shared
browseable = yes
inherit owner = yes

The valid users @shared line tells samba that only members of the “shared” group can access this share. And the line inherit owner = yes is what makes it all work. This tells samba to set the owner of any files created to the owner of the directory we are in. In this case the owner is “nobody”. As the sticky bit is set on this directory, only the user “nobody” or the superuser can remove files as their ownership is instantly changed by Samba when first created from the actual user to the user “nobody”.

After dropping a file into the shared directory over a samba connection the listing looks like this:

-rwxr--r-- 1 nobody shared 1272366 2008-04-17 14:17 14_-_Jubilee.mp3.

See how the file is owned by “nobody:shared” and only has group and other read set.

It might sound like a bit of a palaver, but it doesn’t take very long to set up. This is a very useful way of creating drop-boxes for many kinds of applications.

I hope someone finds this useful, and please leave a comment if you do!

[UPDATE]

A big thanks to Simbul who noted the obvious flaw in my suggestion. Although you could safely drop files into this folder, you couldn’t create directories which was a bit of a PITA to be honest. However Simbul made a simple addition to the [shared] section that fixes this issue (See the comments at the bottom of this post for details):


[shared]
comment = Our Shared Data/Media
path = /home/shared/
read only = no
valid users = @shared
browseable = yes
inherit owner = yes

Add the following two lines:

directory mode = 3770
force directory mode = 3770

And that’s it. Thanks Simbul. It works a treat.

Tags: , ,

13 Comments

  • Simbul says:

    Very useful. Only issue I had with it, you can only drop files in the box, not directories containing other files.
    I added this little modification to the [shared] stanza in smb.conf and now it works also for directories:

    directory mode = 0770
    force directory mode = 0770

  • Alan Lord says:

    Hi Simbul,

    Thanks for commenting. I had been wondering if there was a way to fix that particular limitation. I have just tested it and it works very well.

    Thanks very much!

    I will update the post and add your suggestion.

  • Alan Lord says:

    @Simbul,

    If you read this (or anyone else for that matter) your addition enables us to create a directory in the top level, but it doesn’t seem to cascade down, so you can’t create a tree of directories… Anyone got any ideas how you might do this?

  • Simbul says:

    Uhm, strange. I’m pretty sure I managed to copy a whole directory tree in my samba share – that was the whole point of my modification, actually.
    I’ll check things tomorrow and let you know πŸ˜‰

  • Alan Lord says:

    Hi Simbul, glad you could drop by…

    I can drop a tree into the drop-box, sorry. I thought I couldn’t add files to the drop-box later on inside the newly created tree structure, but having just tried this, I was totally wrong.

    But the scary part, is you can delete everything inside the top-level directory…

    In my test I opened Nautilus and mounted my music drop-box share. I dragged a small structure from my local disk to the drop box and it copied in fine:

    $ ls -l tolc-1.5/
    total 40
    drwxrws— 2 nobody shared 4096 2008-12-01 20:38 css
    -rwxr–r– 1 nobody shared 2988 2008-12-01 20:38 frontpage.php
    drwxrws— 2 nobody shared 4096 2008-12-01 20:38 images
    -rwxr–r– 1 nobody shared 5889 2008-12-01 20:38 index.php
    drwxrws— 2 nobody shared 31 2008-12-01 20:38 js
    -rwxr–r– 1 nobody shared 0 2008-12-01 20:38 params.ini
    -rwxr–r– 1 nobody shared 2958 2008-12-01 20:38 templateDetails.xml
    -rwxr–r– 1 nobody shared 2931 2008-12-01 20:38 templateDetails.xml~
    -rwxr–r– 1 nobody shared 10962 2008-12-01 20:38 template_thumbnail.png

    But now, for some reason I do not fully understand, if I highlight the top-level directory in Nautilus (tolc-1.5) and hit enter and accept the “permanently delete” option, I get a pop up saying it can’t delete tolc-1.5 but everything below it has been removed… The directory is now completely empty.

    One thing to note is the *files* are being created rwxr–r– whereas prior to your suggestion they were being flagged rw-r–r–.

    Thanks.

    Alan

  • Simbul says:

    I think that Nautilus is actually being a little smug about its actions: it says it’s removing the parent directory but is in fact also removing the single items in the directory. But that’s not the real issue.

    The actual problem is that our “current” configuration blocks deletion of first-level children of the root directory, but it doesn’t put any constraint on the children of the subdirectories.
    In fact, the problem is that the sticky bit is not cascaded on the subdirectories, i.e. the structure we’re building is not fully recursive.

    A possible solution:
    directory mode = 3770
    force directory mode = 3770

    The first octal number basically forces the sticky bit (+1) and the SGID bit (+2). This should make every files and directory dropped in the share a perfect copy of the root directory (as far as permissions go).

    Let me know if it works for you πŸ˜‰

  • Alan Lord says:

    Brilliant!

    That seems to work a treat! I have only done a quick test but I copied over a directory structure with some files, tried deleting through Nautilus – failed. Then I copied a new file into one of the new subdirectories and it worked. And I couldn’t delete again it either.

    I’ll update the post. And I’ll let you know if anything further crops up.

    Thanks again,

    Alan

  • Kev says:

    Hey, thanks for the guide, works perfectly across W7 and XP! However, Mac OS X 10.5 will not let me copy filers to the “Drop Box”, it tells em I do not have sufficient privileges to complete the operation. Any ideas/suggestions please?

    Thanks!

  • CJM says:

    Thanx for this and it was VERY cool of you to explain what you do by every command. I have seen some HowTos that expect you to run commands blindly (scary!!) So thank you for these explanations.

  • Topper says:

    Perfect howto but…
    We have users in LDAP, how to use ldap group in this dropbox share?
    Please advice.

  • Dieguin says:

    Hello, id like to ask one little thing.
    The really good thing of dropbox is that once someone shares something, its uploaded to all shared computers automatically, they also have a folder… yes… but the good thing is that it is syncronized (not like an ftp on a normal folder). Any ideas on how to do this?

  • Yoda says:

    Hi,

    The above works well apart from one thing.
    When I create a new folder on Windows XP I cannot rename the folder during the create folder process.
    I get
    New Folder
    New Folder (1) etc.
    Is there a way around this?

    Thanks

    • Alan Lord says:

      Create your folder hierarchy and put the files where you want them before doing the copy and do the copy in one go.

      Because the folder is created immediately you can’t rename it again (unless you ssh to the server and use a privileged account to rename it).

      I realise this is not a perfect solution but at least it stops family being able to accidentally delete stuff.

Leave a Reply to Dieguin

XHTML: You can use these tags:
<a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <s> <strike> <strong>