Commit e3959cbc authored by James Ramsay's avatar James Ramsay

Refactor file locking docs

There are two forms of file lock supported by GitLab. These were
documented in two different location. This merge request centralizes all
file locking documentation in a single location, and explains the
difference.

Detailed documentation has been added to explain how the `git-lfs` file
locking commands can be used not only for LFS files, but any file. This
is important for partial clone workflows involving large files.
parent a7caebd8
......@@ -111,69 +111,7 @@ To remove objects from LFS:
> [Introduced](https://gitlab.com/gitlab-org/gitlab-foss/-/issues/35856) in GitLab 10.5.
The first thing to do before using File Locking is to tell Git LFS which
kind of files are lockable. The following command will store PNG files
in LFS and flag them as lockable:
```shell
git lfs track "*.png" --lockable
```
After executing the above command a file named `.gitattributes` will be
created or updated with the following content:
```shell
*.png filter=lfs diff=lfs merge=lfs -text lockable
```
You can also register a file type as lockable without using LFS
(In order to be able to lock/unlock a file you need a remote server that implements the LFS File Locking API),
in order to do that you can edit the `.gitattributes` file manually:
```shell
*.pdf lockable
```
After a file type has been registered as lockable, Git LFS will make
them read-only on the file system automatically. This means you will
need to lock the file before editing it.
### Managing Locked Files
Once you're ready to edit your file you need to lock it first:
```shell
git lfs lock images/banner.png
Locked images/banner.png
```
This will register the file as locked in your name on the server:
```shell
git lfs locks
images/banner.png joe ID:123
```
Once you have pushed your changes, you can unlock the file so others can
also edit it:
```shell
git lfs unlock images/banner.png
```
You can also unlock by ID:
```shell
git lfs unlock --id=123
```
If for some reason you need to unlock a file that was not locked by you,
you can use the `--force` flag as long as you have a `maintainer` access on
the project:
```shell
git lfs unlock --id=123 --force
```
TODO
## Troubleshooting
......
---
stage: Create
group: Source Code
info: "To determine the technical writer assigned to the Stage/Group associated with this page, see https://about.gitlab.com/handbook/engineering/ux/technical-writing/#designated-technical-writers"
type: reference, howto
---
# File Locking
# File Locking **(PREMIUM)**
When working with binary files in a collaborative project, file locking helps
prevent multiple people changing the same file at the same time. Branching works
for source code and plain text because different versions can be merged
together, but this does not work for binary files.
> [Introduced](https://gitlab.com/gitlab-org/gitlab/-/merge_requests/440) in [GitLab Premium](https://about.gitlab.com/pricing/) 8.9.
When a file is locked, only the user who locked the file may modify it. This
user is said to "hold the lock" or have "taken the lock", since only one user
may lock a file at a time. When a file or directory is unlocked, the user is
said to have "released the lock".
GitLab supports two different modes of file locking:
- [Exclusive locks](#exclusive-file-locks) for binary files, to
prevent locked files being modified on any branch.
- [Default branch locks](#default-branch-file-and-directory-locks) to prevent
locked files and directories being modified on the default branch.
## Permissions
Only the user who locked the file or directory can edit locked files. Others
users will be prevented from modifying locked files through by pushing, merging
or any other means, and will be shown an error like: `The path '.gitignore' is
locked by Administrator`
Locks can be created by any person who has [push access](../permissions.md) to
the repository, Developer permissions and above.
Working with multiple people on the same file can be a risk. Conflicts when merging a non-text file are hard to overcome and will require a lot of manual work to resolve. File Locking helps you avoid these merge conflicts and better manage your binary files.
Locks can be only be removed by their author, or any user with Maintainer
permissions and above.
With File Locking, you can lock any file or directory, make your changes, and
then unlock it so another member of the team can edit it.
## Exclusive file locks **(CORE)**
## Overview
> [Introduced](https://gitlab.com/gitlab-org/gitlab-foss/-/issues/35856) in GitLab 10.5.
Working with multiple people on the same file can be a risk. Conflicts
when merging a non-text file are hard to overcome and will require a lot
of manual work to resolve. With GitLab Premium, File
Locking helps you avoid merge conflicts and better manage your binary
files by preventing everyone, except you, from modifying a specific file
or entire directory.
Preventing wasted work caused by unresolvable merge conflicts prevents requires
a different way of working. This means explicitly requesting write permissions,
and verifying no one else is editing the same file before editing begins.
## Use-cases
When file locking is setup, lockable files are **read only** by default.
The file locking feature is useful in situations when:
1. To edit a file, request the lock. This verifies that no one else is editing
the file, and prevents anyone else editing the file until you're done.
- Multiple people are working on the same file and you want to avoid merge
conflicts.
- Your repository contains binary files in which situation there is no easy
way to tell the diff between yours and your colleagues' changes.
- Prevent design assets from being overwritten.
```shell
git lfs lock path/to/file.png
```
Locked directories are locked recursively, which means that everything that
lies under them is also locked.
1. When you're done, return the lock. This communicates that you finished
editing the file, and allows other people to edit the file.
## Locking a file or a directory
```shell
git lfs unlock path/to/file.png
```
TODO: workflow suggestion - don't unlock until the change is in the default
branch. Maybe this can be a follow up on practical workflows.
NOTE: **Note:**
Locking only works for the default branch you have set in the project's settings
(usually `master`).
Although multi-branch file locks can be created and managed through the Git LFS
command line interface, file locks can be created for any file.
To lock a file:
### Getting started (user)
1. Navigate to your project's **Repository > Files**.
1. Pick the file you want to lock.
1. Click the "Lock" button.
TODO: how do I use file locks on an existing project that someone has already
setup. E.g. what do I do after running `git clone`
![Locking file](img/file_lock.png)
1. Install Git LFS
```shell
git lfs install
```
1. Fetch the current file lock status, and update file permissions so that
lockable files are read only.
```shell
git lfs locks
git checkout .
```
To lock an entire directory, look for the "Lock" link next to "History".
### Configure lockable files (maintainer)
The first thing to do before using File Locking is to tell Git LFS which
kind of files are lockable. The following command will store PNG files
in LFS and flag them as lockable:
```shell
git lfs track "*.png" --lockable
```
After executing the above command a file named `.gitattributes` will be
created or updated with the following content:
```shell
*.png filter=lfs diff=lfs merge=lfs -text lockable
```
You can also register a file type as lockable without using LFS
(In order to be able to lock/unlock a file you need a remote server that implements the LFS File Locking API),
in order to do that you can edit the `.gitattributes` file manually:
```shell
*.pdf lockable
```
After you lock a file or directory, it will appear as locked in the repository
view.
After a file type has been registered as lockable, Git LFS will make
them read-only on the file system automatically. This means you will
need to lock the file before editing it.
![Repository view](img/file_lock_repository_view.png)
TODO: reminder that `.gitattributes` should be commited to the repo!
Once locked, any merge request to the default branch will fail
to merge until the file becomes unlocked.
### Managing locked files
## Unlocking a file or a directory
Once you're ready to edit your file you need to lock it first:
To unlock a file or a directory, follow the same procedure as when you locked
them. For a detailed view of every existing lock, see the next section on
"Viewing and managing existing locks".
```shell
git lfs lock images/banner.png
Locked images/banner.png
```
You can unlock a file that yourself or someone else previously locked as long
as you have Maintainer or above [permissions](../permissions.md) to the project.
This will register the file as locked in your name on the server:
## Viewing and managing existing locks
```shell
git lfs locks
images/banner.png joe ID:123
```
To view or manage every existing lock, navigate to the
**Project > Repository > Locked Files** area. There, you can view all existing
locks and [remove the ones you have permission for](#permissions-on-file-locking).
Once you have pushed your changes, you can unlock the file so others can
also edit it:
## Permissions on file locking
```shell
git lfs unlock images/banner.png
```
The user that locks a file or directory **is the only one** that can edit and
push their changes back to the repository where the locked objects are located.
You can also unlock by ID:
Locks can be created by any person who has [push access](../permissions.md) to the repository; i.e.,
Developer and higher level, and can be removed solely by their author and any
user with Maintainer permissions and above.
```shell
git lfs unlock --id=123
```
If a file is locked and you are not the author of its locked state, a
pre-receive hook will reject your changes when you try to push. In the
following example, a user who has no permissions on the locked `.gitignore`
file will see the message below:
If for some reason you need to unlock a file that was not locked by you,
you can use the `--force` flag as long as you have a `maintainer` access on
the project:
```shell
Counting objects: 3, done.
Delta compression using up to 4 threads.
Compressing objects: 100% (3/3), done.
Writing objects: 100% (3/3), 320 bytes | 0 bytes/s, done.
Total 3 (delta 1), reused 0 (delta 0)
remote: GitLab: The path '.gitignore' is locked by Administrator
To https://example.com/gitlab-org/gitlab-foss.git
! [remote rejected] master -> master (pre-receive hook declined)
error: failed to push some refs to 'https://example.com/gitlab-org/gitlab-foss.git'
git lfs unlock --id=123 --force
```
Similarly, when a user that is not the author of the locked state of a file
accepts a merge request, an error message will appear stating that the file
is locked.
## Default branch file and directory locks **(PREMIUM)**
> [Introduced](https://gitlab.com/gitlab-org/gitlab/-/merge_requests/440) in [GitLab Premium](https://about.gitlab.com/pricing/) 8.9.
Default branch file and directory locks only apply to the default branch set in
the project's settings (usually `master`).
Changes to locked files on the default branch will be blocked, including merge
requests that modify locked files. Unlock the file to allow changes.
### Locking and unlocking a file or a directory
To lock a file:
1. Open the file or directory in GitLab.
1. Click the **Lock** button, located near the Web IDE button.
![Locking file](img/file_lock.png)
An **Unlock** button will be displayed if the file is already locked, and
will be disabled if you do not have permission to unlock the file.
If you did not lock the file, hovering your cursor over the button will show who
locked the file.
### Viewing and remove existing locks
The **Locked Files**, accessed from **Project > Repository** left menu, lists
all file and directory locks. Locks can be removed by their author, or any user
with Maintainer permissions and above.
![Merge request error message](img/file_lock_merge_request_error_message.png)
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment