Työhakemistot
Git-työhakemistot mahdollistavat useiden työhakemistojen käytön yhden arkiston kanssa. Jokaisella työhakemistolla on oma uloskirjaus (HEAD, indeksi ja tiedostot), mutta ne jakavat pääarkiston kanssa oliotallennustilan, asetukset ja pakatut viitteet. Pitmaster voi luoda, luetteloida, lukita ja poistaa linkitettyjä työhakemistoja sekä avata ne arkistoina. Karsimista, siirtämistä ja korjaamista ei ole toteutettu.
Käsitteet
Tavallisessa git-arkistossa on yksi työhakemisto:
project/
.git/ (directory)
src/
README.md
Työhakemistojen avulla voit tehdä lisäuloskirjauksia:
project/ (main worktree)
.git/ (the actual git directory)
worktrees/
review/ (metadata for linked worktree)
HEAD
commondir
gitdir
/tmp/review/ (linked worktree)
.git (file, not directory)
src/
README.md
Linkitetyn työhakemiston .git on tiedosto (ei hakemisto), joka sisältää suhteellisen polun työhakemistoon:
gitdir: ../../path/to/project/.git/worktrees/review
Työhakemiston luominen
$repo = Pitmaster::open('/path/to/project');
// Create a linked worktree on a new branch
$wt = $repo->addWorktree('/tmp/review', 'feature/review');
echo $wt->path; // '/tmp/review'
echo $wt->branch; // 'feature/review'
echo $wt->gitDir; // '/path/to/project/.git/worktrees/review'
var_dump($wt->isMain); // bool(false)
var_dump($wt->isDetached); // bool(false)
addWorktree() tekee seuraavaa:
- Luo haaran, jos sitä ei ole (HEADistä tai määritetystä
$from-commitista) - Luo metatietohakemiston kohteeseen
.git/worktrees/<name>/ - Kirjoittaa
.git-tiedoston työhakemiston hakemistoon - Kirjoittaa metatietotiedostot
HEAD,commondirjagitdir - Ottaa haaran puun käyttöön työhakemiston hakemistossa
- Kirjoittaa työhakemiston indeksin
Jos haara on jo olemassa, $from ohitetaan. Toisin kuin git, addWorktree() ei kieltäydy luomasta haaraa, joka on jo otettu käyttöön toisessa työhakemistossa, eikä suorita post-checkout-koukkua.
Määritetyllä metatietonimellä
Käytä valinnaista name-argumenttia, kun useat linkitetyt työhakemistot voivat jakaa saman uloskirjauksen perusnimen.
$wt = $repo->addWorktree(
'/tmp/sandboxes/app',
'feature/review',
name: 'sandbox-app',
);
Metatietonimeä käytetään kohteessa .git/worktrees/<name>/ kohteen basename($path) sijaan.
Tietystä commitista
$wt = $repo->addWorktree('/tmp/hotfix', 'hotfix/urgent', $repo->resolve('v1.0.0'));
Työhakemistojen luettelointi
$worktrees = $repo->worktrees();
foreach ($worktrees as $wt) {
$type = $wt->isMain ? 'main' : 'linked';
$branch = $wt->branch ?? 'detached';
$locked = $wt->isLocked ? ' [locked]' : '';
echo "{$wt->path} ({$type}) [{$branch}]{$locked}\n";
}
Luettelo sisältää aina ensin päätyöhakemiston, jota seuraavat linkitetyt työhakemistot. Kutsu worktrees()-metodia pääarkiston kahvalla: linkitetyn työhakemiston kahvalla päämerkintä ilmoittaa tällä hetkellä linkitetyn työhakemiston oman polun (#14).
Työhakemiston poistaminen
$repo->removeWorktree('review'); // by metadata name
$repo->removeWorktree('/tmp/review'); // or by worktree path
// Force remove (even if locked)
$repo->removeWorktree('review', force: true);
Työhakemiston poistaminen:
- Tarkistaa, onko työhakemisto lukittu (epäonnistuu, ellei
$forceole true) - Poistaa työhakemiston hakemistosta
.git-tiedoston - Poistaa metatietohakemiston kohteesta
.git/worktrees/
Työhakemiston tiedostoja ei poisteta automaattisesti. Haara säilyy.
Linkitetyn työhakemiston avaaminen
Voit avata linkitetyn työhakemiston kuten minkä tahansa arkiston:
$repo = Pitmaster::open('/tmp/review');
// Pitmaster detects the .git file and follows the gitdir reference
echo $repo->isLinkedWorktree(); // true
echo $repo->gitDir(); // '/path/to/project/.git/worktrees/review'
echo $repo->commonGitDir(); // '/path/to/project/.git'
echo $repo->workDir(); // '/tmp/review'
Arkistotoiminnot ratkaisevat polut seuraavasti:
- Oliot: luetaan yhteisestä git-hakemistosta ja kirjoitetaan siihen (
project/.git/objects/) - Asetukset: luetaan yhteisestä git-hakemistosta (
project/.git/config) - Pakatut viitteet: luetaan yhteisestä git-hakemistosta
- HEAD: työhakemistokohtainen (jokainen työhakemisto seuraa omaa haaraansa), samoin kuin
ORIG_HEAD,MERGE_HEADja muut toimintaviitteet - Indeksi: työhakemistokohtainen (jokaisella työhakemistolla on oma valmistelualue)
- Löysät viitteet: haarat ja tunnisteet jaetaan yhteisessä hakemistossa (
project/.git/refs/) - Koukut: luetaan työhakemistokohtaisesta git-hakemistosta, joten jaetut koukut eivät toimi (#12)
Stash ei vielä tue linkitettyjä työhakemistoja: se lukee identiteetin työhakemistokohtaisesta hakemistosta, jossa ei ole asetuksia, ja kirjoittaa reflogin sinne (#14).
Työhakemiston arvokohde
use Pitmaster\Worktree\Worktree;
$wt->name; // Metadata name (null for the main worktree)
$wt->path; // Working directory path
$wt->gitDir; // Per-worktree git dir
$wt->branch; // Branch name (null if detached)
$wt->head; // ObjectId of HEAD commit
$wt->isMain; // true for the main worktree
$wt->isDetached; // true if HEAD is detached
$wt->isLocked; // true if worktree is locked
$wt->lockReason; // Lock reason, or null when there is none (an empty reason is also null)
WorktreeManager
Matalan tason työhakemistojen hallintaan. WorktreeManager::add() kirjoittaa vain metatiedot ja .git-tiedoston: se ei luo haaraa, ota tiedostoja käyttöön eikä kirjoita indeksiä. Käytä $repo->addWorktree()-toimintoa käyttökelpoisen uloskirjauksen luomiseen. Haaran on oltava olemassa (tai sen on oltava täydellinen viitenimi, kuten refs/tags/v1.0.0, jolloin HEAD irrotetaan).
use Pitmaster\Worktree\WorktreeManager;
$manager = new WorktreeManager($repo->commonGitDir(), $mainWorkDir);
// List
$worktrees = $manager->list();
// Add
$wt = $manager->add('/tmp/review', 'feature/review');
$wt = $manager->add('/tmp/review', 'feature/review', 'review-app');
// Remove
$manager->remove('review');
$manager->remove('review', force: true);
// Lock/unlock (metadata name only)
$manager->lock('review', 'Do not delete, code review in progress');
$manager->unlock('review');
Työhakemistojen lukitseminen
// Lock (prevents removal)
$manager->lock('review', 'Code review in progress');
// Attempt to remove locked worktree
try {
$manager->remove('review');
} catch (\RuntimeException $e) {
// "Worktree is locked: review (Code review in progress)"
}
// Force remove ignores the lock
$manager->remove('review', force: true);
// Unlock
$manager->unlock('review');
Lukitus tallennetaan tiedostoon kohteessa .git/worktrees/<name>/locked. Tiedosto sisältää lukituksen syyn (voi olla tyhjä).
Työhakemistojen tunnistaminen
// Check if a path is a linked worktree
if (Pitmaster::isWorktree('/tmp/review')) {
echo "This is a linked worktree\n";
}
// Resolve the common git dir from any path
$common = Pitmaster::commonGitDir('/tmp/review');
// '/path/to/project/.git'
// Resolve a .git file to the actual git directory
$gitDir = WorktreeManager::resolveGitFile('/tmp/review');
// '/path/to/project/.git/worktrees/review'
Tiedostorakenne
Linkitettyjen työhakemistojen päätyöhakemiston metatiedot
.git/worktrees/<name>/
HEAD Per-worktree HEAD (symbolic ref or detached hash)
commondir Relative path to the shared git dir ("../..")
gitdir Path back to the worktree's .git file, as passed to addWorktree()
locked Present if locked (content = reason)
index Per-worktree index/staging area
Linkitetyn työhakemiston .git-tiedosto
gitdir: <relative path to>/project/.git/worktrees/<name>
Jaetut resurssit
| Resurssi | Sijainti | Jaettu? |
|---|---|---|
| Oliot | $commonDir/objects/ |
Kyllä |
| Asetukset | $commonDir/config |
Kyllä |
| Pakatut viitteet | $commonDir/packed-refs |
Kyllä |
| Koukut | $gitDir/hooks/ |
Ei: Pitmaster ei suorita linkitettyjen työhakemistojen jaettuja koukkuja |
| HEAD | $gitDir/HEAD |
Ei (työhakemistokohtainen) |
| Indeksi | $gitDir/index |
Ei (työhakemistokohtainen) |
| Löysät viitteet | $commonDir/refs/ |
Kyllä (HEAD ja toimintaviitteet, kuten MERGE_HEAD, ovat työhakemistokohtaisia) |