You are on page 1of 35

2.

1 Τα θεμελιώδη στοιχεία του Git -


Αποκτώντας ένα αποθετήριο Git
Αν μπορείτε να διαβάσετε μόνο ένα κεφάλαιο για το Git τότε αυτό είναι το κατάλληλο για εσάς. Το
κεφάλαιο αυτό καλύπτει κάθε βασική εντολή που χρειάζεστε για να κάνετε την συντριπτική
πλειοψηφία των ενεργειών που μπορείτε να κάνετε με το Git. Με το τέλος αυτού το κεφαλαίου, θα
μπορείτε να διαμορφώνετε και να αρχικοποιείτε ένα αποθετήριο, να ξεκινήσετε και να σταματήσετε
τον εντοπισμό αλλαγών σε αρχεία, να καταχωρείτε καθώς και να υποβάλλετε αλλαγές. Θα σας
δείξουμε επίσης πως να ρυθμίσετε το Git ώστε να αγνοεί ορισμένα αρχεία και μοτίβα αρχείων, πως
να αναιρέσετε λάθη εύκολα και γρήγορα, πως να περιηγηθείτε στο ιστορικό του έργου σας ώστε να
δείτε τις αλλαγές μεταξύ των υποβολών και πως να ωθήσετε και να τραβήξετε από απομακρυσμένα
αποθετήρια.

Αποκτώντας ένα αποθετήριο Git


Μπορείτε να δημιουργήσετε ένα έργο στο Git χρησιμοποιώντας δύο βασικές προσεγγίσεις. Η
πρώτη παίρνει ένα υπάρχον έργο ή κατάλογο και το εισάγει μέσα στο Git. Η δεύτερη κλωνοποιεί
ένα υπάρχον αποθετήριο Git από έναν άλλο διακομιστή. You can get a Git project using two main
approaches. The first takes an existing project or directory and imports it into Git. The second
clones an existing Git repository from another server.

Αρχικοποιώντας ένα Αποθετήριο σε έναν Υπάρχοντα Κατάλογο


Αν θέλετε να ξεκινήσετε τον εντοπισμό ένα υπάρχοντος έργου στο Git, θα χρειαστεί να πάτε στον
κατάλογο του έργου σας και να πληκτρολογήσετε
$ git init

Η εντολή αυτή δημιουργεί έναν νέο υπο-κατάλογο με το όνομα .git ο οποίος περιέχει όλα τα
απαραίτητα αρχεία για το αποθετήριο. Ουσιαστικό ο υπο-κατάλογος αυτός αποτελεί ένα σκελετό
για το αποθετήριό σας. Στο σημείο αυτό, τίποτα δεν έχει εντοπιστεί ακόμα από το έργο σας. (Βλ.
Git Internals για περισσότερες πληροφορίες σχετικά με το τι ακριβώς αρχεία περιέχονται στον
κατάλογο .git που μόλις δημιουργήσατε.)

Αν θέλετε να ξεκινήσετε τον έλεγχο έκδοσης στα υπάρχοντα αρχεία, θα πρέπει να ξεκινήσετε τον
εντοπισμό στα αρχεία αυτά και να κάνετε μια πρώτη υποβολή τους. Για να το επιτύχετε αυτό θα
χρειαστείτε μερικές εντολές git add οι οποίες προσδιορίζουν τα αρχεία που θέλετε να
εντοπίσετε και μια εντολή git commit:
$ git add *.c
$ git add LICENSE
$ git commit -m 'initial project version'

θα εξετάσουμε σε λίγο τι κάνουν οι παραπάνω εντολές. Στο σημείο αυτό, έχουμε ένα αποθετήριο
Git με κάποια εντοπισμένα αρχεία και μια αρχική υποβολή.
Κλωνοποιώντας ένα Υπάρχον Αποθετήριο
Αν θέλετε να αποκτήσετε ένα αντίγραφο ενός υπάρχοντος αποθετηρίου Git - για παράδειγμα, ένα
έργο στο οποιό θα θέλατε να συνεισφέρετε - η εντολή που χρειάζεστε είναι git clone. Αν είστε
εξεικοιωμένοι με άλλα συστήματα ελέγχου έκδοσης όπως το Subversion, θα παρατηρήσετε ότι η
εντολή είναι "clone" και όχι "checkout". Αυτή είναι μια σημαντική διάκριση - το Git παίρνει ένα
πλήρες αντίγραφο σχεδόν όλων των δεδομένων που έχει ο διακομιστής αντί για ένα απλό
αντίγραφο. Με την εντολή git clone όλες οι εκδόσεις του κάθε αρχείου του έργου
αποθηκεύονται τοπικά. Στην πραγματικότητα, αν ο δίσκος του διακομιστή σας αλλοιωθεί, μπορείτε
να χρησιμοποιήσετε οποιονδήποτε από τους κλώνους του ώστε να θέσετε τον διακομιστή στην
κατάσταση που ήταν όταν κλωνοποιήθηκε.
Για να κλωνοποιήσετε ένα αποθετήριο, εκτελείτε την εντολή git clone [url]. Για
παράδειγμα, αν θέλετε την κλωνοποιήσετε την βιβλιοθήκη libgit2 του Git, θα πρέπει να εκτελέσετε:
$ git clone https://github.com/libgit2/libgit2

Η εντολή αυτή δημιουργεί έναν κατάλογο με το όνομα “libgit2”, αρχικοποιεί έναν κατάλογο .git
μέσα σε αυτόν, κατεβάζει όλα τα δεδομένα για αυτό το αποθετήριο καθώς και ένα αντίγραφο από
την τελευταία έκδοση. Αν περιηγηθείτε στον καινούριο κατάλογο libgit2, θα δείτε τα αρχεία
του έργου μέσα σε αυτόν, έτοιμα για να χρησιμοποιηθούν. Αν θέλετε να κλωνοποιήσετε το
αποθετήριο σε έναν κατάλογο με διαφορετικό όνομα, μπορείτε να το ορίσετε με την παρακάτω
εναλλακτική της εντολής:
$ git clone https://github.com/libgit2/libgit2 mylibgit

Η εντολή αυτή έχει το ίδιο αποτέλεσμα με την προηγούμενη, αλλά ο κατάλογος που θα
δημιουργηθεί ονομάζεται mylibgit.

Το Git έχει διάφορα πρωτόκολλα μεταφοράς που μπορείτε να χρησιμοποιήσετε. Το προηγούμενο


παράδειγμα χρησιμοποεί το πρωτόκολλο https://, ενδέχεται επίσης να δείτε το git:// ή το
user@server:path/to/repo.git το οποίο χρησιμοποιεί το πρωτόκολλο μεταφοράς SSH.
Στο κεφάλαιο Git on the Server θα σας παρουσιάσουμε όλες τις διαθέσιμες εναλλακτικές που
μπορεί να χρησιμοποιήσει ο διακομιστής ώστε να αποκτήσει πρόσβαση στο αποθετήριο Git σας,
καθώς και τα πλεονεκτήματα και μειονεκτή΄ματα της κάθε εναλλακτικής.
2.2 Τα θεμελιώδη στοιχεία του Git -
Καταχωρώντας αλλαγές στο αποθετήριο
Καταχωρώντας αλλαγές στο αποθετήριο
Έχετε λοιπόν ένα ολοκαίνουριο αποθετήριο Git και μια ενημερωμένη έκδοση των αρχείων του
έργου. Η διαδικασία που θα ακολουθήσουμε είναι να κάνουμε μερικές αλλαγές στο έργο και να
υποβάλλουμε ένα στιγμιότυπο από αυτές τις αλλαγές στο αποθετήριο κάθε φορά που θέλουμε να
καταγράψουμε την εκάστοτε κατάσταση του έργου μας.
Θυμηθείτε ότι κάθε αρχείο στον κατάλογο που δουλεύετε μπορεί να βρίσκεται σε δύο καταστάσεις:
εντοπισμένο ή μη εντοπισμένο. Τα εντοπισμένα αρχεία είναι αυτά που βρίσκονταν στο τελευταίο
στιγμιότυπο και μπορούν να είναι τροποποιημένα, ατροποποίητα ή καταχωρημένα. Τα μη
εντοπισμένα αρχεία από την άλλη μπορούν να είναι οτιδήποτε άλλο. Τα αρχεία αυτά μπορούν να
είναι οποιοδήποτε αρχεία στον κατάλογο εργασίας σας τα οποία δεν βρίσκονταν στο τελευταίο
στιγμιότυπο και ούτε έχουν καταχωρηθεί ακόμα. Για παράδειγμα, όταν κλωνοποιείτε για πρώτη
φορά ένα αποθετήριο, όλα τα αρχεία θα είναι εντοπισμένα και ατροποποίητα καθώς μόλις τα
ενημερώσατε και δεν τα έχετε επεξεργαστεί ακόμα.
Καθώς επεξεργάζεστε τα αρχεία, το Git θα τα αναγνωρίζει ως τροποποιημένα καθώς έχουν αλλάξει
από την τελευταία φορά που υποβάλλατε κάποια αρχεία. Τα επόμενα στάδια είναι η καταχώρηση
των τροποποιημένων αρχείων και η υποβολή τους, η διαδικασία αυτή θα επαναλαμβάνεται
συνέχεια.

Figure 8. The lifecycle of the status of your files.


Ελέγχοντας την Κατάσταση των Αρχείων σας
Το βασικό εργαλείο που μπορείτε να χρησιμοποιήσετε ώστε να δείτε την τρέχουσα κατάσταση των
αρχείων είναι η εντολή git status. Αν εκτελέσετε την εντολή αυτή αμέσως αφού
κλωνοποιήσετε ένα αποθετήριο, θα δείτε στην γραμμή εντολών το παρακάτω μήνυμα:
$ git status
On branch master
nothing to commit, working directory clean

Το μήνυμα αυτό σημαίνει ότι έχετε ένα καθαρό κατάλογο εργασίας. Με άλλα λόγια, δεν υπάρχουν
τροποποιημένα ή εντοπισμένα αρχεία. Επίσης δεν υπάρχουν ούτε μη εντοπισμένα αρχεία αλλιώς το
Git θα τα είχε καταγράψει στο παραπάνω μήνυμα. Επίσης, η εντολή αυτή μας ενημερώνει σε ποιον
κλάδο βρισκόμαστε καθώς και ότι δεν έχει αποκλίνει από τον αντίστοιχο κλάδο του διακομιστή.
Προς το παρόν χρησιμοποιούμε τον κύριο κλάδο, “master”, ο οποίος είναι και ο προεπιλεγμένος.
Θα αναφερθούμε πιο αναλυτικά στους κλάδους στο κεφάλαιο Διακλαδώσεις στο Git.
Έστω ότι έχουμε προσθέσει ένα νέο αρχείο στο έργο μας, ένα απλό αρχείο README. Αν το αρχείο
αυτό δεν προυπήρχε και εκτελέσουμε την εντολή git status, θα δείτε το μη εντοπισμένο
αρχείο σας ως εξής:
$ echo 'My Project' > README
$ git status
On branch master
Untracked files:
(use "git add <file>..." to include in what will be committed)

README

nothing added to commit but untracked files present (use "git add" to track)

Βλέπουμε λοιπόν ότι το αρχείο README είναι μη εντοπισμένο καθώς βρίσκεται κάτω από την
κατηγορία “Untracked files”. Ένα μη εντοπισμένο αρχείο ουσιαστικά σημαίνει ότι το Git βλέπει
ένα αρχείο το οποίο δεν υπήρχε στο προηγούμενο στιγμιότυπο (την τελευταία φορά που
υποβάλλατε αρχεία). Το Git δεν θα συμπεριλάβει το αρχείο αυτό στα επόμενα στιγμιότυπα που θα
υποβάλλετε αν δεν το ζητήσετε ρητά. Αυτό γίνεται ώστε να μην συμπεριλάβετε κατά λάθος στο
έργο σας αρχεία τα οποία δεν θέλατε, για παράδειγμα δυαδικά αρχεία. Στην περίπτωσή μας,
θέλουμε να συμπεριλάβουμε το αρχείο README στο έργο μας οπότε πάμε να ενημερώσουμε το
Git ώστε να το εντοπίσει.

Εντοπίζοντας Νέα Αρχεία


Για να εντοπίσει το Git ένα καινούριο αρχείο, χρησιμοποιούμε την εντολή git add. Ξεκινάμε τον
εντοπισμό του αρχείου REAMDE με την εντολή:
$ git add README

Αν τώρα εκτελέσετε την εντολή για να δείτε την τρέχουσα κατάσταση του αποθετηρίου, θα δείτε
ότι το αρχείο README είναι πλέον εντοπισμένο και καταχωρημένο ώστε να είναι έτοιμο να
υποβληθεί:
$ git status
On branch master
Changes to be committed:
(use "git reset HEAD <file>..." to unstage)

new file: README

Το αρχείο πλέον βρίσκεται κάτω από την κατηγορία “Changes to be committed” που σημαίνει ότι
είναι καταχωρημένο. Αν σε αυτό το σημείο κάνετε υποβολή των αρχείων σας, η έκδοση του
αρχείου README όταν εκτελέσατε την εντολή git add είναι αυτή που θα αποθηκευτεί στο
στιγμιότυπο. Προηγουμένως κάναμε κάτι αντίστοιχο, εκτελέσαμε την εντολή git init
ακολουθούμενη από git add (files). Με τον τρόπο αυτό ξεκινήσαμε τον εντοπισμό των
αρχείων του καταλόγου. Η εντολή git add μπορεί να ακολουθείται είτε από ένα αρχείο είτε από
έναν κατάλογο. Αν ακολουθείται από κατάλογο τότε η εντολή θα καταχωρήσει όλα τα αρχεία του
συγκεκριμένου καταλόγου αναδρομικά.

Καταχωρώντας Τροποποιημένα Αρχεία


Πάμε λοιπόν να τροποποιήσουμε ένα αρχείο το οποίο είναι ήδη εντοπισμένο. Έστω ότι
τροποποιήτε ένα ήδη εντοπισμένο αρχείο, το “CONTRIBUTING.md” και εκτελείτε την εντολή
git status ξανά:
$ git status
On branch master
Changes to be committed:
(use "git reset HEAD <file>..." to unstage)

new file: README

Changes not staged for commit:


(use "git add <file>..." to update what will be committed)
(use "git checkout -- <file>..." to discard changes in working directory)

modified: CONTRIBUTING.md

Το αρχείο “CONTRIBUTING.md” βρίσκεται κάτω από την κατηγορία “Changed but not staged for
commit”, που σημαίνει ότι ένα ήδη εντοπισμένο αρχείο έχει τροποποιηθεί στο κατάλογο εργασίας
αλλά δεν έχει καταχωρηθεί ακόμα. Για να το καταχωρήσουμε θα πρέπει να εκτελέσουμε την εντολή
git add. Η εντολή git add έχει πολλές λειτουργίες: την χρησιμοποιείτε για να ξεκινήσετε τον
εντοπισμό καινούριων αρχείων, για να καταχωρήσετε αρχεία αλλά και για άλλες λειτουργίες όπως
το να σημειώσετε αρχεία που προέρχονται από συγκρούσεις συγχώνευσης (merge conflicts) ως
επιλυμένα. Μπορείτε να σκεφτείτε την εντολή ως “πρόσθεσε αυτό το περιεχόμενο σε ό,τι
υποβάλλεις την επόμενη φορά” αντί για “πρόσθεσε αυτό το αρχείο στο έργο”. Πάμε λοιπόν να
εκτελέσουμε την εντολή git add για να καταχωρήσουμε το αρχείο`‘CONTRIBUTING.md’' και
έπειτα να δούμε την τρέχουσα κατάσταση του αποθετηρίου:
$ git add CONTRIBUTING.md
$ git status
On branch master
Changes to be committed:
(use "git reset HEAD <file>..." to unstage)

new file: README


modified: CONTRIBUTING.md
Και τα δύο αρχεία πλέον είναι καταχωρημένα και θα συμπεριληφθούν στην επόμενη υποβολή
στιγμιοτύπου. Στο σημείο αυτό, ας υποθέσουμε ότι θυμάστε μια μικρή αλλαγή που θέλετε να
κάνετε στο αρχείο CONTRIBUTING.md πριν το υποβάλλετε. Αφού κάνετε την αλλαγή που θέλετε,
είσαστε έτοιμοι για την υποβολή. Παρ' όλα αυτά ας εκτελέσουμε git status άλλη μια φορά:
$ vim CONTRIBUTING.md
$ git status
On branch master
Changes to be committed:
(use "git reset HEAD <file>..." to unstage)

new file: README


modified: CONTRIBUTING.md

Changes not staged for commit:


(use "git add <file>..." to update what will be committed)
(use "git checkout -- <file>..." to discard changes in working directory)

modified: CONTRIBUTING.md

Περίεργο ε; Το αρχείο CONTRIBUTING.md αναφέρεται πλέον ως καταχωρημένο αλλά και ως μη


καταχωρημένο. Πως είναι αυτό δυνατόν? Αυτό που συμβαίνει είναι ότι το Git καταχωρεί ένα
αρχείο ακριβώς όπως είναι την στιγμή που εκτελείτε την εντολή git add. Αν υποβάλλετε το
στιγμιότυπο τώρα, η έκδοση του αρχείου CONTRIBUTING.md που υπήρχε όταν εκτελέσατε την
εντολή git add είναι αυτή που θα συμπεριληφθεί στην υποβολή (και όχι η τωρινή έκδοση του
αρχείου). Γενικά, αν τροποποιήσετε ένα αρχείο αφότου έχει εκτελέσει την εντολή git add, θα
πρέπει να την εκτελέσετε ξανά ώστε να καταχωρήσετε την τελευταία έκσοτη του αρχείου:
$ git add CONTRIBUTING.md
$ git status
On branch master
Changes to be committed:
(use "git reset HEAD <file>..." to unstage)

new file: README


modified: CONTRIBUTING.md

Σύντομη κατάσταση
Ενώ η εντολή git status μας δίνει αρκετά περιεκτική πληροφορία, είναι επίσης και πολύ
μακροσκελής. Στο Git μπορείτε να δείτε και μια πιο σύντομη περιγραφή της κατάστασης του
αποθετηρίου. Αν εκτελέσετε git status -s ή git status --short θα έχετε ένα πιο
απλοποιημένο αποτέλεσμα.
$ git status -s
M README
MM Rakefile
A lib/git.rb
M lib/simplegit.rb
?? LICENSE.txt

Τα καινούργια αρχεία που δεν έχουν εντοπιστεί ακόμα συμβολίζονται με ??, τα καινούρια αρχεία
που έχουν καταχωρηθεί με A, τα τροποποιημένα αρχεία με M κ.ο.κ. Το αποτέλεσμα της εντολής
περιλαμβάνει δύο σύμβολα για το κάθε αρχείο. Το αριστερό σύμβολο υποδηλώνει ότι το αρχείο
έχει καταχωρηθεί και το δεξί ότι έχει τροποποιηθεί. Για παράδειγμα, το αρχείο README είναι
τροποιποιημένο στο κατάλογο εργασίας αλλά δεν έχει καταχωρηθεί ακόμα. Το αρχείο
lib/simplegit.rb είναι τροποποιημένο και καταχωρημένο. Το αρχείο Rakefile από την
άλλη έχει τροποποιηθεί, καταχωρηθεί, και τροποποιηθεί ξανά που σημαίνει ότι υπάρχουν κάποιες
αλλαγές που έχουν καταχωρηθεί και κάποιες που δεν έχουν.

Αγνοώντας αρχεία
Είναι συχνό φαινόμενο να υπάρχει μια κατηγορία αρχείων που δεν θέλετε να καταχωρηθούν
αυτόματα από το Git αλλά ούτε και να τα βλέπετε ως μη εντοπισμένα. Συνήθως αυτά είναι αρχεία
που δημιουργούνται αυτόματα όπως αρχεία καταγραφής ή αρχεία που δημιουργούνται από τον
μεταγλωττιστή. Σε αυτές τις περιπτώσεις μπορείτε να βρείτε το μοτίβο των ονομάτων των αρχείων
που δεν χρειάζεστε και να τα καταχωρήσετε στο αρχείο .gitignore. Ας δούμε ένα παράδειγμα
αρχείου .gitignore:
$ cat .gitignore
*.[oa]
*~

Η πρώτη γραμμή ενημερώνει το Git ώστε να αγνοεί όλα τα αρχεία που τελειώνουν σε “.o” ή “.a”. Η
δεύτερη γραμμή ενημερώνει το Git ώστε να αγνοεί όλα τα αρχεία που τελειώνουν με τον
χαρακτήρα της ισπανικής περισπωμένης (~), το οποίο χρησιμοποιείται από πολλούς επεξεργαστές
κειμένου, όπως ο Emacs, για να δηλώσει τα προσωρινά αρχεία. Μπορείτε επίσεις να
συμπεριλάβεται καταλόγους που περιλαμβάνουν αρχεία καταγραφής, προσωρινούς καταλόγους
κ.ό.κ. Γενικά είναι καλή ιδέα να ρυθμίσετε το αρχείο .gitignore νωρίς ώστε να μην
υποβάλλετε κατά λάθος αρχεία που δεν θέλετε να βρίσκονται στο αποθετήριο.
Οι κανόνες για τα μοτίβα που μπορείτε να δηλώσετε στο αρχείο .gitignore είναι οι εξής:

• Οι κενές γραμμές ή οι γραμμές που ξεκινούν με # θα αγνοηθούν.

• Μπορείτε να χρησιμοποιήσετε τα κλασικά μοτίβα για ονόματα αρχείων (glob patterns).


• Μπορείτε να ξεκινήσετε τα μοτίβα σας με μια κάθετο (/) ώστε να αποφύγετε την
αναδρομικότητα
• Μπορείτε να τελειώσετε τα μοτίβα σας με μια κάθετο (/) ώστε να ορίσετε έναν κατάλογο.

• Μπορείτε να αντιστρέψετε ένα μοτίβο χρησιμοποιώντας ένα θαυμαστικό (!) στην αρχή του.

Τα μοτίβα αυτά είναι σαν απλοποιημένες κανονικές εκφράσεις (regular expressions) που
χρησιμοποιούν τα λειτουργικά συστήματα. Ένας αστερίσκος (*) αντιστοιχεί σε 0 ή περισσότερους
χαρακτήρες. Το [abc] αντιστοιχεί σε οποιονδήποτε χαρακτήρα βρίσκεται μέσα στις αγκύλες. Το
σύμβολο του αγγλικού ερωτηματικού (?) αντιστοιχεί σε έναν και μόνο χαρακτήρα. Αν οι αγκύλες
περιέχουν 2 χαρακτήρες που μεταξύ τους χωρίζονται με παύλα ([0-9]) τότε αυτή η έκφραση
αντιστοιχεί σε όλους τους χαρακτήρες που υπάρχουν μεταξύ των 2 χαρακτήρων (στην περίπτωσή
μας, όλοι οι αριθμοί από το 0 μέχρι το 9). Μπορείτε επίσης να χρησιμοποιήσετε 2 αστερίσκους για
να αντιστοιχίσετε εμφωλευμένους καταλόγους: η έκφραση a/**/z αντιστοιχεί στους καταλόγους
a/z, a/b/z, a/b/c/z κ.ό.κ.
Ας δούμε άλλο ένα παράδειγμα ενός αρχείου .gitignore:
# no .a files
*.a

# but do track lib.a, even though you're ignoring .a files above


!lib.a

# only ignore the TODO file in the current directory, not subdir/TODO
/TODO

# ignore all files in the build/ directory


build/

# ignore doc/notes.txt, but not doc/server/arch.txt


doc/*.txt

# ignore all .pdf files in the doc/ directory


doc/**/*.pdf

Αν θέλετε κάποια παραδείγματα για να ξεκινήσετε, το GitHub συντηρεί μια λίστα με


παραδείγματαα αρχείων .gitignore για πολλές γλώσσες προγραμματισμού στην
Tip
διεύθυνση https://github.com/github/gitignore.

Βλέποντας τις καταχωρημένες και μη αλλαγές


Αν η εντολή git status είναι πολύ αόριστη για εσάς και θέλετε να δείτε ακριβώς τι έχετε
αλλάξει (και όχι μόνο ποια αρχεία έχουν αλλάξει), μπορείτε να χρησιμοποιήσετε την εντολή git
diff. Θα καλύψουμε την εντολή αυτή πιο αναλυτικά αργότερα, αλλά θα την χρησιμοποιείτε
συχνά για να απαντήσετε σε 2 ερωτήσεις: Τι έχετε αλλάξει και δεν έχετε καταχωρήσει ακόμα; Και
επίσης, τι έχετε καταχωρήσει που είναι έτοιμο για να υποβληθεί; Ενώ η εντολή git status
απαντά σε αυτές τις ερωτήσεις πολύ γενικά, απαριθμώντας τα ονόματα των αρχείων, η εντολή git
diff θα σας δείξει ακριβώς ποιες γραμμές προστέθηκαν ή αφαιρέθηκαν.

Έστω λοιπόν ότι επεξεργάζεστε και καταχωρείτε το αρχείο README και μετά επεξεργάζεστε το
αρχείο CONTRIBUTING.md χωρίς να το καταχωρήσετε. Αν τώρα εκτελέσετε την εντολή git
status, θα δείτε κάτι τέτοιο:
$ git status
On branch master
Changes to be committed:
(use "git reset HEAD <file>..." to unstage)

new file: README

Changes not staged for commit:


(use "git add <file>..." to update what will be committed)
(use "git checkout -- <file>..." to discard changes in working directory)

modified: CONTRIBUTING.md

Για να δείτε τι έχετε αλλάξει αλλά δεν έχετε καταχωρήσει ακόμα, πληκτρολογήστε git diff:
$ git diff
diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md
index 8ebb991..643e24f 100644
--- a/CONTRIBUTING.md
+++ b/CONTRIBUTING.md
@@ -65,7 +65,8 @@ branch directly, things can get messy.
Please include a nice description of your changes when you submit your PR;
if we have to read the whole diff to figure out why you're contributing
in the first place, you're less likely to get feedback and have your change
-merged in.
+merged in. Also, split your changes into comprehensive chunks if your patch is
+longer than a dozen lines.

If you are starting to work on a particular area, feel free to submit a PR


that highlights your work in progress (and note in the PR title that it's

Η εντολή αυτή συγκρίνει τον κατάλογο εργασίας σας με ό,τι υπάρχει στην περιοχή καταχώρησης.
Το αποτέλεσμά της λοιπόν θα περιλαμβάνει τις αλλαγές που έχετε κάνει αλλά δεν έχετε
καταχωρήσει ακόμα.
Αν θέλετε να δείτε τι έχετε καταχωρήσει μέχρι τώρα, που θα είναι και μέρος της επόμενης
υποβολής, μπορείτε να χρησιμοποιήσετε την εντολή git diff --staged. Η εντολή αυτή
συγκρίνει τις καταχωρημένες αλλαγές με την τελευταία υποβολή:
$ git diff --staged
diff --git a/README b/README
new file mode 100644
index 0000000..03902a1
--- /dev/null
+++ b/README
@@ -0,0 +1 @@
+My Project

Είναι σημαντικό να σημειώσουμε ότι η εντολή git diff από μόνη της δεν μας εμφανίζει τις
αλλαγές που έγιναν από την τελευταία υποβολή, παρά μόνο τις αλλαγές που δεν έχουν ακόμα
καταχωρηθεί. Το γεγονός αυτό μπορεί να προκαλεί σύγχυση καθώς για παράδειγμα αν έχετε
καταχωρήσει όλες σας τις αλλαγές, η εντολή git diff δεν θα σας επιστρέψει κάποιο
αποτέλεσμα.
Για να καταλάβουμε καλύτερα την χρήση της εντολής αυτής, ας δούμε άλλο ένα παράδειγμα. Έστω
ότι έχουμε ένα αρχείο CONTRIBUTING.md που έχουμε ήδη καταχωρήσει, και έπειτα το έχουμε
τροποποιήσει. Μπορούμε να χρησιμοποιήσουμε την εντολή git diff για να δούμε ποιες
ακριβώς αλλαγές του αρχείου έχουν καταχωρηθεί και ποιες όχι. Αν λοιπόν το περιβάλλον εργασίας
μας είναι κάπως έτσι:
$ git add CONTRIBUTING.md
$ echo '# test line' >> CONTRIBUTING.md
$ git status
On branch master
Changes to be committed:
(use "git reset HEAD <file>..." to unstage)

modified: CONTRIBUTING.md

Changes not staged for commit:


(use "git add <file>..." to update what will be committed)
(use "git checkout -- <file>..." to discard changes in working directory)

modified: CONTRIBUTING.md
Μπορούμε να χρησιμοποιήσουμε την εντολή git diff για να δούμε τι δεν έχει καταχωρηθεί
ακόμα
$ git diff
diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md
index 643e24f..87f08c8 100644
--- a/CONTRIBUTING.md
+++ b/CONTRIBUTING.md
@@ -119,3 +119,4 @@ at the
## Starter Projects

See our [projects


list](https://github.com/libgit2/libgit2/blob/development/PROJECTS.md).
+# test line

καθώς και την εντολή git diff --cached για να δούμε τι έχει καταχωρηθεί μέχρι τώρα (τα --
staged και --cached είναι συνώνυμα):
$ git diff --cached
diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md
index 8ebb991..643e24f 100644
--- a/CONTRIBUTING.md
+++ b/CONTRIBUTING.md
@@ -65,7 +65,8 @@ branch directly, things can get messy.
Please include a nice description of your changes when you submit your PR;
if we have to read the whole diff to figure out why you're contributing
in the first place, you're less likely to get feedback and have your change
-merged in.
+merged in. Also, split your changes into comprehensive chunks if your patch is
+longer than a dozen lines.

If you are starting to work on a particular area, feel free to submit a PR


that highlights your work in progress (and note in the PR title that it's

Note Χρησιμοποιώντας την εντολή Git Diff μέσω άλλου προγράμματος


Θα συνεχίσουμε να χρησιμοποιούμε την εντολή git diff με διάφορους τρόπους στο βιβλίο. Αν
όμως προτιμάτε να βλέπετε τις διαφορές μεταξύ των αρχείων με κάποιο γραφικό εργαλείο (και όχι
μέσα από την γραμμή εντολών), υπάρχει και άλλος τρόπος. Αν εκτελέσετε την εντολή git
difftool αντί για git diff μπορείτε να δείτε τις διαφορές των αρχείων με προγράμματα
όπως τα Araxis, emerge, vimdiff και άλλα. Δοκιμάστε να εκτελέσετε την εντολή git difftool
--tool-help για να δείτε τι προγράμματα είναι διαθέσιμα για το σύστημά σας.

Υποβάλλοντας τις αλλαγές σας


Τώρα που η περιοχή καταχώρησης περιέχει τις αλλαγές που θέλετε, είσαστε έτοιμοι να τις
υποβάλλετε. Θυμηθείτε ότι όλα τα μη καταχωρημένα αρχεία, δηλαδή όσα αρχεία έχετε
δημιουργήσει ή τροποποιήσει και για τα οποία δεν εκτελέσατε την εντολή git add, δεν θα
συμπεριληφθούν σε αυτή την υποβολή. Αντί γι αυτό, θα παραμείνουν ως τροποποιημένα αρχεία
στον δίσκο σας. Στην περίπτωσή μας, έστω ότι έχουμε εκτελέσει την εντολή git status και
βλέπουμε ότι όλες οι αλλαγές που θέλουμε είναι καταχωρημένες. Είμαστε έτοιμοι πλέον να
υποβάλλουμε τις αλλαγές μας. Ο πιο απλός τρόπος για να υποβάλλετε αλλαγές είναι να
πληκτρολογήσετε git commit:
$ git commit
Με την εντολή αυτή θα εκκινήσετε τον προεπιλεγμένο επεξεργαστή κειμένου. Αυτός είναι
καθορισμένος από την μεταβλητή περιβάλλοντος (environment variable) $EDITOR της γραμμής
εντολών, συνήθως είναι το vim ή το emacs. Παρ' όλα αυτά μπορείτε να χρησιμοποιήσετε την
εντολή git config --global core.editor ώστε να χρησιμοποιήσετε τον επεξεργαστή
κειμένου της αρεσκείας σας, όπως είδαμε στο κεφάλαιο Ξεκινώντας.
Ο επεξεργαστής κειμένου θα σας εμφανίσει το παρακάτω κείμενο (στο παράδειγμά μας
χρησιμοποιούμε το Vim):
# Please enter the commit message for your changes. Lines starting
# with '#' will be ignored, and an empty message aborts the commit.
# On branch master
# Changes to be committed:
# new file: README
# modified: CONTRIBUTING.md
#
~
~
~
".git/COMMIT_EDITMSG" 9L, 283C

Βλέπετε ότι το προεπιλεγμένο μήνυμα υποβολής περιέχει το τελευταίο αποτέλεσμα της ενοτλής
git status μέσα σε σχόλια (οι γραμμές που ξεκινούν με την δίεση, #, αποτελούν σχόλια) και
μια κενή γραμμή στην αρχή. Μπορείτε να αφαιρέσετε τα σχόλια αυτά και να γράψετε το δικό σας
μήνυμα υποβολής ή να τα αφήσετε ως έχουν ώστε να σας βοηθήσουν αργότερα να θυμηθείτε ποι
αρχεία υποβάλλετε. (Για να έχετε μια ακόμα πιο ρητή υπενθύμιση των αλλαγών που έχετε κάνει,
μπορείτε να χρησιμοποιήσετε την επιλογή -v στην εντολή git commit. Με τον τρόπο αυτό, θα
εισάγετε τις αλλαγές σας στον επεξεργαστή κειμένου ώστε να δείτε ακριβώς ποιες αλλαγές θα
υποβάλλετε.) Αφού κλείσετε τον επεξεργαστή κειμένου, το Git θα δημιουργήσει την υποβολή σας
με το παραπάνω μήνυμα (τα σχόλια θα αφαιρεθούν).
Εναλλακτικά, μπορείτε να γράψετε το μήνυμα υποβολής σας μαζί με την εντολή commit,
χρησιμοποιώντας την επιλογή -m ως εξής:
$ git commit -m "Story 182: Fix benchmarks for speed"
[master 463dc4f] Story 182: Fix benchmarks for speed
2 files changed, 2 insertions(+)
create mode 100644 README

Μόλις κάνατε την πρώτη σας υποβολή! Βλέπετε ότι η υποβολή αυτή σας έχει δώσει κάποιες
πληροφορίες: τον κλάδο στον οποίο υποβάλλατε τις αλλαγές σας (master στην περίπτωσή μας),
το SHA-1 άθροισμα ελέγχου (SHA-1 checksum) της υποβολής (463dc4f), πόσα αρχεία αλλάξατε,
καθώς και στατιστικά για το πόσες γραμμές προσθέσατε και αφαιρέσατε στην υποβολή αυτή.
Θυμηθείτε ότι η υποβολή αλλαγών καταγράφει το στιγμιότυπο το οποίο είχατε εκείνη την στιγμή
στην περιοχή καταχώρησης. Οτιδήποτε δεν είχατε καταχωρήσει θα παραμένει εκεί τροποποιημένο,
μπορείτε να το υποβάλλετε αργότερα. Κάθε φορά που πραγματοποιείτε μια υποβολή, καταγράφετε
ένα στιγμιότυπο του έργου σας, το οποίο μπορείτε να χρησιμοποιήσετε ώστε να επανέλθετε σε
αυτό ή να το συγκρίνετε με το έργο σας αργότερα.
Παραλείποντας την περιοχή καταχώρησης
Παρ' όλο που η περιοχή καταχώρησης είναι πολύ χρήσιμη για να διαμορφώνετε τις υποβολές σας
ακριβώς όπως θέλετε, κάποιες φορές είναι πιο περίπλοκη από όσο χρειάζεστε για την εργασία σας.
Αν θέλετε να παραλείψετε την περιοχή καταχώρησης, το Git παρέχει μια απλή συντόμευση.
Προσθέτοντας την επιλογή -a στην εντολή git commit κάνει το Git να καταχωρεί αυτόματα
κάθε αρχείο το οποίο είναι ήδη εντοπισμένο πριν κάνετε την υποβολή. Με αυτόν τον τρόπο
μπορείτε να παραλείψετε την εντολή git add:
$ git status
On branch master
Changes not staged for commit:
(use "git add <file>..." to update what will be committed)
(use "git checkout -- <file>..." to discard changes in working directory)

modified: CONTRIBUTING.md

no changes added to commit (use "git add" and/or "git commit -a")
$ git commit -a -m 'added new benchmarks'
[master 83e38c7] added new benchmarks
1 file changed, 5 insertions(+), 0 deletions(-)

Παρατηρήστε πως στην περίπτωση αυτή, δεν έχετε να εκτελέσετε την εντολή git add στο αρχείο
“CONTRIBUTING.md” πριν κάνετε την υποβολή σας.

Αφαιρώντας αρχεία
Για να αφαιρέσετε ένα αρχείο από το Git, θα πρέπει να το αφαιρέσετε από τη λίστα με τα
εντοπισμένα αρχεία (ή πιο σωστά, να το αφαιρέσετε από την περιοχή καταχώρησης) και έπειτα να
το υποβάλλετε. Αυτό πραγματοποιείτε με την εντολή git rm, η οποία επίσης θα αφαιρέσει το
αρχείο από τον κατάλογο εργασίας σας έτσι ώστε να μην το έχετε ως μη εντοπισμένο αρχείο.
Αν απλά αφαιρέσετε το αρχείο από τον κατάλογο εργασίας σας, θα εμφανίζεται κάτω από την
κατηγορία “Changed but not updated” (που ουσιαστικά σημαίνει μη καταχωρημένο) του
αποτελέσματος της εντολής git status:
$ rm PROJECTS.md
$ git status
On branch master
Your branch is up-to-date with 'origin/master'.
Changes not staged for commit:
(use "git add/rm <file>..." to update what will be committed)
(use "git checkout -- <file>..." to discard changes in working directory)

deleted: PROJECTS.md

no changes added to commit (use "git add" and/or "git commit -a")

Έπειτα η εντολή git rm θα καταχωρήσει την αφαίρεση του αρχείου:


$ git rm PROJECTS.md
rm 'PROJECTS.md'
$ git status
On branch master
Changes to be committed:
(use "git reset HEAD <file>..." to unstage)
deleted: PROJECTS.md

Στην επόμενη φορά υποβολή σας, το αρχείο θα έχει αφαιρεθεί και δεν θα είναι πια εντοπισμένο. Αν
είχατε τροποποιήσειτο αρχείο και είχαε ήδη προσθέσει στην περιοχή καταχώρησης, θα πρέπει να
εξαναγκάσετε την αφαίρεσή του με την επιλογή -f. Αυτό είναι μια λειτουργία για λόγους
ασφάλειας του Git ώστε να αποτρέψει τυχαία αφαίρεση δεδομένων που δεν έχουν ακόμα
καταγραφεί σε κάποιο στιγμιότυπο και δεν μπορούν να ανακτηθούν από το Git.
Ένα ακόμα χρήσιμο πράγμα που μπορεί να θέλετε είναι να κρατήσετε το αρχείο στον κατάλογο
εργασίας σας αλλά να το αφαιρέσετε από την περιοχή καταχώρησης. Με άλλα λόγια, μπορεί να
θέλετε να κρατήσετε το αρχείο στον σκληρό σας δίσκο, αλλά να μην θέλετε να εντοπίζεται από το
Git πλέον. Αυτό μπορεί να αποδειχτεί πολύ χρήσιμο αν ξεχάσατε να προσθέσετε κάτι στο αρχείο
.gitignore και να καταχωρήσατε κάτι κατά λάθος, όπως για παράδειγμα μεταγλωττισμένα
αρχεία. Για να το κάνετε αυτό, χρησιμοποιείστε την επιλογή --cached:
$ git rm --cached README

Μπορείτε να χρησιμοποιείσετε την παραπάνω εντολή με αρχεία, καταλόγους και μοτίβα αρχείων.
Αυτό σημαίνει ότι μπορείτε να εκτελέσετε εντολές όπως
$ git rm log/\*.log

Προσέξτε την ανάποδη κάθετο (\) μπροστά από τον αστερίσκο, *. Αυτή είναι απαραίτητη επειδή
το Git χρησιμοποιεί τον δικό του τρόπο ώστε να επεκτείνει το όνομα των αρχείων, επιπροσθέτως
του τρόπου που χρησιμοποιεί η γραμμή εντολών σας. Η παραπάνω εντολή αφαιρεί όλα τα αρχεία
που έχουν την κατάληξη .log στον κατάλογο log/. Επίσης, θα μπορούσατε να κάνετε κάτι
τέτοιο:
$ git rm \*~

Η εντολή αυτή αφαιρεί όλα τα αρχεία που τελειώνουν με τον χαρακτήρα ~.

Μετακινώντας αρχεία
Σε αντίθεση με άλλα συστήματα ελέγχου έκδοσης, το Git δεν εντοπίζει τις μετακινήσεις αρχείων
από μόνο του. Αν μετονομάσετε ένα αρχείο στο Git, δεν θα αποθηκευτεί καμιά πληροφορία που να
ενημερώνει το Git ότι μετονομάσατε το αρχείο. Παρ' όλα αυτά, το Git είναι αρκετά έξυπνο ώστε να
καταλάβει κάτι τέτοιο - θα ασχοληθούμε λίγο αργότερα με το πως εντοπίζεται η μετακίνηση
αρχείων.
Έτσι, είναι λίγο περίπλοκο το γεγονός ότι το Git έχει την εντολή mv. Αν θέλετε να μετονομάσετε
ένα αρχείο στο Git, μπορείτε να το κάνετε κάπως έτσι
$ git mv file_from file_to

το οποίο θα λειτουργήσει τέλεια. Στην πραγματικότητα, αν εκτελέσετε κάτι τέτοιο και έπειτα
κοιτάξτε στην κατάσταση του αποθετηρίου, θα δείτε ότι το Git το υπολογίζει ως μετονομασμένο
αρχείο:
$ git mv README.md README
$ git status
On branch master
Changes to be committed:
(use "git reset HEAD <file>..." to unstage)

renamed: README.md -> README

Η εντολή αυτή όμως, είναι ισοδύναμη με το να εκτελέσετε κάτι τέτοιο:


$ mv README.md README
$ git rm README.md
$ git add README

Το Git μπορεί να καταλάβει ότι έμμεσα πρόκειται για μετονομασία. Συνεπώς, δεν έχει σημασία αν
μετονομάσετε ένα αρχείο με αυτόν τον τρόπο ή με την εντολή mv. Η μόνη πραγματική αλλαγή
είναι ότι η εντολή mv είναι μία εντολή αντί για τρεις - το χρησιμοποιούμε για ευκολία. Σε κάθε
περίπτωση, μπορείτε να χρησιμοποιείσετε όποιο εργαλείο θέλετε για να μετονομάσετε ένα αρχείο,
και να λύσετε το πρόβλημα του add/rm αργότερα, πριν την υποβολή.
2.3 Τα θεμελιώδη στοιχεία του Git -
Χρησιμοποιώντας το ιστορικό υποβολών
Χρησιμοποιώντας το ιστορικό υποβολών
Αφού έχετε δημιουργήσει αρκετές υποβολές, ή έχετε κλωνοποιήσει ένα αποθετήριο με υπάρχων
ιστορικό υποβολών, θα χρειαστείτε πιθανότατα να κοιτάξετε στο παρελθόν για να δείτε τι έχει
γίνει. Το πιο βασικό και ισχυρό εργαλείο για να το κάνετε αυτό είναι η εντολη΄git log.

Τα παρακάτω παραδείγματα χρησιμοποιούν ένα πολύ απλό έργο που το ονομάζουμε “simplegit”.
Για να αποκτήσετε το έργο, μπορείτε να εκτελέσετε:
git clone https://github.com/schacon/simplegit-progit

Έπειτα, εκτελώντας την εντολή git log σε αυτό το έργο, θα λάβετε ένα αποτέλεσμα που θα
μοιάζει κάπως έτσι:
$ git log
commit ca82a6dff817ec66f44342007202690a93763949
Author: Scott Chacon <schacon@gee-mail.com>
Date: Mon Mar 17 21:52:11 2008 -0700

changed the version number

commit 085bb3bcb608e1e8451d4b2432f8ecbe6306e7e7
Author: Scott Chacon <schacon@gee-mail.com>
Date: Sat Mar 15 16:40:33 2008 -0700

removed unnecessary test

commit a11bef06a3f659402fe7563abf99ad00de2209e6
Author: Scott Chacon <schacon@gee-mail.com>
Date: Sat Mar 15 10:31:28 2008 -0700

first commit

Από προεπιλογή, η εντολή git log καταγράφει όλες τις υποβολές που έχουν γίνει στο
αποθετήριο σε αντίθετη χρονολογική σειρά (οι πιο πρόσφατες υποβολές εμφανίζονται πρώτες).
Όπως μπορείτε να δείτε, η εντολή καταγράφει κάθε υποβολή μαζί με το άθροισμα ελέγχου SHA-1,
το όνομα και την ηλεκτρονική διεύθυνση του δημιουργού, την ημερομηνία εγραφής, καθώς και το
μήνυμα της υποβολής.
Έχουμε μια πληθώρα επιλογών για την συγκεκριμένη εντολή ώστε να βρείτε ακριβώς αυτό που
ψάχνετε. Θα σας δείξουμε κάποιες από τις πιο δημοφιλείς.
Μια από τις πιο χρήσιμες επιλογές είναι η -p, η οποία δείχνει την διαφορά που εισήχθη σε κάθε
υποβολή. Μπορείτε επίσης να χρησιμοποιήσετε την -2, η οποία θα περιορίσει το αποτέλεσμα στις
δύο μόνο τελευταίες εγγραφές (υποβολές):
$ git log -p -2
commit ca82a6dff817ec66f44342007202690a93763949
Author: Scott Chacon <schacon@gee-mail.com>
Date: Mon Mar 17 21:52:11 2008 -0700
changed the version number

diff --git a/Rakefile b/Rakefile


index a874b73..8f94139 100644
--- a/Rakefile
+++ b/Rakefile
@@ -5,7 +5,7 @@ require 'rake/gempackagetask'
spec = Gem::Specification.new do |s|
s.platform = Gem::Platform::RUBY
s.name = "simplegit"
- s.version = "0.1.0"
+ s.version = "0.1.1"
s.author = "Scott Chacon"
s.email = "schacon@gee-mail.com"
s.summary = "A simple gem for using Git in Ruby code."

commit 085bb3bcb608e1e8451d4b2432f8ecbe6306e7e7
Author: Scott Chacon <schacon@gee-mail.com>
Date: Sat Mar 15 16:40:33 2008 -0700

removed unnecessary test

diff --git a/lib/simplegit.rb b/lib/simplegit.rb


index a0a60ae..47c6340 100644
--- a/lib/simplegit.rb
+++ b/lib/simplegit.rb
@@ -18,8 +18,3 @@ class SimpleGit
end

end
-
-if $0 == __FILE__
- git = SimpleGit.new
- puts git.show
-end
\ No newline at end of file

Η επιλογή αυτή εμφανίζει τις ίδιες πληροφορίες αλλά κάθε υποβολή ακολουθείται και από τις
διαφορές που εισήγαγε. Αυτή μπορεί να είναι πολύ χρήσιμη για περίπτωση που θέλετε να
επανεξετάσετε κάποιον κώδικα ή για να μπορέσετε να καταλάβετε γρήγορα τι έγινε σε μια
ακολουθία υποβολών που εισήγαγε ένας συνεργάτης σας. Μπορείτε επίσης να χρησιμοποιήσετε
επιλογές ανακεφαλαίωσης με την git log. Για παράδειμα, αν θέλετε να δείτε κάποια
συντομευμένα στατιστικά για την κάθε υποβολή, μπορείτε να χρησιμοποιήσετε την επιλογή --
stat:
$ git log --stat
commit ca82a6dff817ec66f44342007202690a93763949
Author: Scott Chacon <schacon@gee-mail.com>
Date: Mon Mar 17 21:52:11 2008 -0700

changed the version number

Rakefile | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)

commit 085bb3bcb608e1e8451d4b2432f8ecbe6306e7e7
Author: Scott Chacon <schacon@gee-mail.com>
Date: Sat Mar 15 16:40:33 2008 -0700
removed unnecessary test

lib/simplegit.rb | 5 -----
1 file changed, 5 deletions(-)

commit a11bef06a3f659402fe7563abf99ad00de2209e6
Author: Scott Chacon <schacon@gee-mail.com>
Date: Sat Mar 15 10:31:28 2008 -0700

first commit

README | 6 ++++++
Rakefile | 23 +++++++++++++++++++++++
lib/simplegit.rb | 25 +++++++++++++++++++++++++
3 files changed, 54 insertions(+)

Όπως μπορείτε να δείτε, η επιλογή --stat μας εκτυπώνει κάτω από κάθε υποβολή, μια λίστα με
τα τροποποιημένα αρχεία, πόσα αρχεία άλλαξαν, καθώς και πόσες γραμμές προστέθηκαν ή
αφαιρέθηκαν σε αυτά τα αρχεία. Επίσης, μας εκτυπώνει και μια περίληψη αυτών των πληροφοριών
στο τέλος.
Μια ακόμα χρήσιμη επιλογή είναι η --pretty. Η επιλογή αυτή αλλάζει το αποτέλεσμα της
εντολής δίνοντάς του διαφορετική μορφή. Υπάρχουν μερικές προυπάρχουσες τιμές για να
χρησιμοποιήσετε για αυτή την επιλογή. Η τιμή oneline εκτυπώνει κάθε υποβολή σε μία γραμμή,
κάτι το οποίο μπορεί να σας φανεί χρήσιμο αν ψάχνετε σε πολλές υποβολές. Επιπλέον, οι τιμές
short, full, και fuller εμφανίζουν το ίδιο αποτέλεσμα σε παρόμοια μορφή αλλά με λιγότερες
ή περισσότερες πληροφορίες αντίστοιχα:
$ git log --pretty=oneline
ca82a6dff817ec66f44342007202690a93763949 changed the version number
085bb3bcb608e1e8451d4b2432f8ecbe6306e7e7 removed unnecessary test
a11bef06a3f659402fe7563abf99ad00de2209e6 first commit

Η πιο ενδιαφέρουσα επιλογή είναι η format, η οποία σας επιτρέπει να προσδιορίσετε την δικιά
σας μορφή που θα έχει το αποτέλεσμα. Αυτό είναι εξαιρετικά χρήσιμο σε περιπτώσεις που θέλετε
το αποτέλεσμα να μπορεί να είναι αναγνώσιμο από κάποιο αυτοματοποιημένο σύστημα. Γνωρίζετε
ότι η μορφή του αποτελέσματος δεν θα αλλάξει καθώς το έχετε προσδιορίσει ρητά:
$ git log --pretty=format:"%h - %an, %ar : %s"
ca82a6d - Scott Chacon, 6 years ago : changed the version number
085bb3b - Scott Chacon, 6 years ago : removed unnecessary test
a11bef0 - Scott Chacon, 6 years ago : first commit

Useful options for git log --pretty=format lists some of the more useful options that
format takes.

Table 1. Useful options for git log --pretty=format


Option Description of Output
%H Commit hash

%h Abbreviated commit hash

%T Tree hash
Option Description of Output

%t Abbreviated tree hash

%P Parent hashes

%p Abbreviated parent hashes

%an Author name

%ae Author e-mail

%ad Author date (format respects the --date=option)

%ar Author date, relative

%cn Committer name

%ce Committer email

%cd Committer date

%cr Committer date, relative

%s Subject

Σε αυτό το σημείο, μπορεί να αναρωτιέστε ποια η διαφορά μεταξύ του author (δημιουργού,
συγγραφέα) και του committer (αυτός που έκανε την υποβολή). Ο δημιουργός είναι το πρόσωπο
που έγραψε αρχικά την δουλειά, ενώ o committer είναι αυτός που την υπέβαλε τελευταίος.
Συνεπώς, αν στείλετε μια επιδιόρθωση λογισμικού για ένα έργο και ένα άλλο πρόσωπο το
υποβάλλει, θα πρέπει και οι δύο να πιστωθείτε την δουλειά: εσείς ως ο δημιουργός και το άλλο
πρόσωπο ως αυτός που το υπέβαλλε. Θα καλύψουμε την διαφορά αυτή σε λίγο, στο κεφάλαιο
Distributed Git.
Οι επιλογές oneline και format είναι ιδιαίτερα χρήσιμες με μια άλλη επιλογή (πάντα για την
εντολή log) που ονομάζεται --graph. Η επιλογή αυτή προσθέτει ένα μικρό παραστατικό
γράφημα με χαρακτήρες ASCII που δείχνει το ιστορικό των κλάδων και των συγχωνεύσεων:
$ git log --pretty=format:"%h %s" --graph
* 2d3acf9 ignore errors from SIGCHLD on trap
* 5e3ee11 Merge branch 'master' of git://github.com/dustin/grit
|\
| * 420eac9 Added a method for getting the current branch.
* | 30e367c timeout code and tests
* | 5a09431 add timeout protection to grit
* | e1193f8 support for heads with slashes in them
|/
* d6016bc require time for xmlschema
* 11d191e Merge branch 'defunkt' into local
Αυτή η μορφή του αποτελέσματος θα γίνει πιο ενδιαφέρουσα αργότερα, στο επόμενο κεφάλαιο,
όταν θα καλύψουμε τους κλάδους και τις συγχωνεύσεις.
Όλες αυτές είναι μερικές απλές επιλογές ώστε να διαμορφώσετε το αποτέλεσμα της εντολής git
log, υπάρχουν και πολλές άλλες. Ο πίνακας Common options to git log καταγράφει όλες τις
επιλογές που καλύψαμε μέχρι στιγμής, καθώς και κάποιες άλλες επιλογές διαμόρφωσης που μπορεί
να σας φανούν χρήσιμες μαζί με μια περιγραφή της λειτουργίας τους.

Table 2. Common options to git log


Option Description
-p Show the patch introduced with each commit.

--stat Show statistics for files modified in each commit.

--shortstat Display only the changed/insertions/deletions line from the --stat


command.

--name-only Show the list of files modified after the commit information.

--name-status Show the list of files affected with added/modified/deleted information as


well.

--abbrev-commit Show only the first few characters of the SHA-1 checksum instead of all
40.

--relative-date Display the date in a relative format (for example, “2 weeks ago”) instead
of using the full date format.

--graph Display an ASCII graph of the branch and merge history beside the log
output.

--pretty Show commits in an alternate format. Options include oneline, short, full,
fuller, and format (where you specify your own format).

Περιορίζοντας το αποτέλεσμα της log


Επιπλέον, η εντολή git log χρησιμοποιείται με πολλές επιλογές για περιορισμό των
αποτελεσμάτων της. Οι επιλογές αυτές θα σε αφήσουν να δείτε μόνο ένα υποσύνολο των
συνολικών υποβολών. Έχετε ήδη δει μια τέτοια επιλογή, την -2, η οποία θα σας εμφανίσει τις δύο
τελευταίες υποβολές μόνο. Στην πραγματικότητα, μπορείτε να χρησιμοποιήσετε -<n>, όπου n
είναι ένας ακέραιος που αντιστοιχεί στις τελευταίες n υποβολές. Στην πραγματικότητα βέβαια,
είναι σχετικά απίθανο να χρησιμοποιείτε αυτή την επιλογή συχνά, καθώς το Git από προεπιλογή
εμφανίζει μόνο μια σελίδα με τα στοιχεία καταγραφής κάθε φορά.
Ωστόσο, θα σας φανούν πολύ χρήσιμες οι επιλογές που περιορίζουν τον αριθμό των
αποτελεσμάτων με χρονικά κριτήρια. Για παράδειγμα, η εντολή αυτή θα σας δώσει μια λίστα με τις
υποβολές που έγιναν τις τελευταίες δύο εβδομάδες:
$ git log --since=2.weeks

Η εντολή αυτή χρησιμοποιείται με πολλές διαφορετικές μορφές. Μπορείτε να προσδιορίσετε για


παράδειγμα μια συγκεκριμένη μέρα, "2008-01-15", ή μια σχετική μέρα όπως "2 years 1
day 3 minutes ago".

Μπορείτε επίσης να φιλτράρετε την λίστα με τις υποβολές με βάση κάποια κριτήρια. Η επιλογή --
author σας επιτρέπει να φιλτράρεται με βάση έναν συγκεκριμένο δημιουργό. Η επιλογή --grep
σας επιτρέπει να ψάξετε για λέξεις-κλειδιά στα μηνύματα των υποβολών. (Σημειώστε ότι αν θέλετε
να χρησιμοποιήσετε και τις δύο παραπάνω επιλογές ταυτόχρονα, θα πρέπει να προσθέσετε την
επιλογή --all-match`)
Ένα ακόμα πολύ χρήσιμο φίλτρο είναι η επιλογή -S η οποία παίρνει μια συμβολοσειρά και μας
δείχνει μόνο τις υποβολές που εισήγαγαν κάποια αλλαγή στον κώδικα η οποία προσέθεσε ή
αφαίρεσε την συμβολοσειρά αυτή. Για παράδειγμα, αν θέλετε να βρείτε την τελευταία υποβολή που
προσέθεσε ή αφαίρεσε μια αναφορα σε μια συγκεκριμένη συνάρτηση, θα γράφατε:
$ git log -Sfunction_name

Η τελευταία χρήσιμη επιλογή που μπορείτε να χρησιμοποιήσετε μαζή με την git log είναι να
φιλτράρετε τα αποτελέσματα με βάση τον κατάλογό τους. Αν προσδιορίσετε έναν κατάλογο ή ένα
όνομα αρχείου, μπορείτε να περιορίσετε το αποτέλεσμα της εντολής ώστε να σας εμφανίσει μόνο
τις υποβολές που επέφεραν αλλαγές σε αυτά τα αρχεία. Συνήθως, αυτή είναι και η τελευταία
επιλογή και σε γενικές γραμμές χρησιμοποιούμε μια διπλή παύλα προηγουμένως (--) ώστε να
ξεχωρίσουμε τις διαδρομές των αρχείων από τις επιλογές.
Στον πίνακα Options to limit the output of git log καταγράφουμε κάποιες από τις επιλογές αυτές
ώστε να έχετε μια αναφορά.

Table 3. Options to limit the output of git log


Option Description
-(n) Show only the last n commits

--since, --after Limit the commits to those made after the specified date.

--until, --before Limit the commits to those made before the specified date.

--author Only show commits in which the author entry matches the specified string.

--committer Only show commits in which the committer entry matches the specified
string.

--grep Only show commits with a commit message containing the string

-S Only show commits adding or removing code matching the string


Για παράδειγμα, αν θέλετε να δείτε ποιες υποβολές τροποποίησαν αρχεία τεστ στο ιστορικό του
πηγαίου κώδικα του Git από τον Junio Hamano και δεν αποτελούσαν συγχωνεύσεις, στον
Οκτώβριο του 2008, μπορείτε να εκτελέσετε κάτι τέτοιο:
$ git log --pretty="%h - %s" --author=gitster --since="2008-10-01" \
--before="2008-11-01" --no-merges -- t/
5610e3b - Fix testcase failure when extended attributes are in use
acd3b9e - Enhance hold_lock_file_for_{update,append}() API
f563754 - demonstrate breakage of detached checkout with symbolic link HEAD
d1a43f2 - reset --hard/read-tree --reset -u: remove unmerged new paths
51a94af - Fix "checkout --track -b newbranch" on detached HEAD
b0ad11e - pull: allow "git pull origin $something:$current_branch" into an
unborn branch

Από τις περίπου 40.000 υποβολές στο ιστορικό του πηγαίου κώδικα του Git, η εντολη΄αυτή θα σας
δείξει μόνο έξι που να ταιριάζουν με τα παραπάνω κριτήρια.
2.4 Τα θεμελιώδη στοιχεία του Git -
Αναιρώντας κάτι
Αναιρώντας κάτι
Μπορείτε να αναιρέσετε κάποια αλλαγή οποιαδήποτε στιγμή. Σε αυτό το κεφάλαιο, θα αναλύσουμε
κάποια βασικά εργαλεία για να αναιρέσετε αλλαγές που έχετε ήδη κάνει. Θα χρειαστεί να είστε
προσεκτικοί γιατί δεν θα μπορείτε πάντα να αναιρέσετε κάποιες από αυτές τις αναιρέσεις. Θα
δούμε κάποιες από τις ελάχιστες περιπτώσεις στο Git όπου μπορεί να χάσετε μέρος της δουλειάς
σας αν χρησιμοποιήσετε με λάθος τρόπο τις εντολές.
Μια συχνή αναίρεση που χρησιμοποιείται είναι η περίπτωση όπου υποβάλλετε κάτι πολύ νωρίς
αλλά ξεχάσατε να προσθέσετε κάποια αρχεία ή μπερδέψατε το μήνυμα υποβολής. Αν θέλετε να
προσπαθήσετε ξανά την συγκεκριμένη υποβολή, θα πρέπει να χρησιμοποιήσετε την επιλογή --
amend:
$ git commit --amend

Η εντολή αυτή παίρνει την περιοχή καταχώρησης και την χρησιμοποιεί για την υποβολή. Αν δεν
έχετε κάνει περαιτέρω αλλαγές από την τελευταία σας υποβολή (για παράδειγμα, αν εκτελέσετε την
εντολή αμέσως μετά από μια υποβολή), τότε το στιγμιότυπο του αποθετηρίου θα είναι ακριβώς το
ίδιο και το μόνο που θα αλλάξετε είναι το μήνυμα υποβολής.
Όταν εκτελέσετε την εντολή, θα σας εμφανιστεί το μήνυμα από την προηγούμενή σας υποβολή. Το
μήνυμα αυτό μπορείτε να το επεξεργαστείτε, αλλά η τελευταία υποβολή θα αντικατασταθεί.
Για παράδειγμα, αν κάνετε μια υποβολή και μετά διαπιστώσετε ότι ξεχάσατε να καταχωρήσετε τις
αλλαγές ενός αρχείου που θέλατε να συμπεριλάβετε στην υποβολή αυτή, τότε μπορείτε να:
$ git commit -m 'initial commit'
$ git add forgotten_file
$ git commit --amend

Έτσι καταλήγετε με μια και μοναδική υποβολή. Η δεύτερη υποβολή αντικαθιστά τα αποτελέσματα
της πρώτης.

Unstaging a Staged File


Στις επόμενες δύο ενότητες θα δούμε πως μπορείτε να διαχειριστείτε τις αλλαγές στην περιοχή
καταχώρησης και στον κατάλογο εργασίας. Κάτι που θα σας φανεί πολύ χρήσιμο είναι ότι η εντολή
που μας προσδιορίζει την κατάσταση αυτών των περιοχών, μας υπενθυμίζει και πως να
αναιρέσουμε τις αλλαγές σε αυτές. Για παράδειγμα, έστω ότι έχετε κάνει αλλαγές σε δύο αρχεία και
θέλετε να τα υποβάλλετε ως ξεχωριστές αλλαγές, αλλά τα καταχωρήσατε και τα δύο κατά λάθος με
την εντολή git add *. Πως μπορούμε να αναιρέσουμε την καταχώρηση του ενός από τα δύο; Η
εντολή git status μας υπενθυμίζει:
$ git add *
$ git status
On branch master
Changes to be committed:
(use "git reset HEAD <file>..." to unstage)

renamed: README.md -> README


modified: CONTRIBUTING.md

Όπως βλέπετε, το κείμενο της εντολής μας συμβουλεύει να χρησιμοποιήσουμε την εντολή git
reset HEAD <file>... ώστε να αναιρέσουμε μια καταχώρηση. Ας χρησιμοποιήσουμε
λοιπόν τη συμβουλή αυτή για το αρχείο CONTRIBUTING.md:
$ git reset HEAD CONTRIBUTING.md
Unstaged changes after reset:
M CONTRIBUTING.md
$ git status
On branch master
Changes to be committed:
(use "git reset HEAD <file>..." to unstage)

renamed: README.md -> README

Changes not staged for commit:


(use "git add <file>..." to update what will be committed)
(use "git checkout -- <file>..." to discard changes in working directory)

modified: CONTRIBUTING.md

Η εντολή φαίνεται λίγο περίεργη, αλλά δουλεύει. Το αρχείο CONTRIBUTING.md είναι


τροποποιημένο αλλά δεν βρίσκεται στην περιοχή καταχώρησης.

Ενώ η εντολή git reset μπορεί να είναι επικίνδυνη αν την καλέσετε με την επιλογή --
hard, στην προηγούμενη περίπτωση το αρχείο στον κατάλογο εργασίας σας δεν
Note τροποποιείται από την εντολή. Η εκτέλεση της εντολής git reset χωρίς επιπλέον
επιλογές δεν είναι επικίνδυνη, τροποποιεί μόνο την περιοχή καταχώρησης.

Προς το παρόν, το μόνο που χρειάζεται να γνωρίζετε για την εντολή git reset είναι η
παραπάνω χρήση της. Θα μπούμε σε περισσότερες λεπτομέρειες για την εντολή αυτή καθώς και για
πιο ενδιαφέροντα πράγματα που μπορείτε να κάνετε με αυτήν στο κεφάλαιο Reset Demystified.

Αναιρώντας τροποποιήσεις ενός αρχείου


Τι μπορείτε να κάνετε όμως αν διαπιστώσετε ότι δεν θέλετε να κρατήσετε τις αλλαγές που κάνατε
στο αρχείο CONTRIBUTING.md; Πως μπορείτε να τις αναιρέσετε εύκολα και να φέρετε το αρχείο
στη μορφή που είχε στην τελευταία του υποβολή (ή όπως βρισκόταν αρχικά στον κατάλογο
εργασίας σας); Η εντολή git status μας βοηθάει εδώ και πάλι. Στο αποτέλεσμα του
προηγούμενου παραδείγματος, η περιοχή με τα μη καταχωρημένα αρχεία ήταν κάπως έτσι:
Changes not staged for commit:
(use "git add <file>..." to update what will be committed)
(use "git checkout -- <file>..." to discard changes in working directory)

modified: CONTRIBUTING.md

Η εντολή μας ενημερώνει αναλυτικά πως να απορρίψετε τις αλλαγές που έχετε κάνει. Ας
ακολουθήσουμε τι λέει:
$ git checkout -- CONTRIBUTING.md
$ git status
On branch master
Changes to be committed:
(use "git reset HEAD <file>..." to unstage)

renamed: README.md -> README

Μπορείτε να δείτε πλέον ότι οι αλλαγές σας έχουν απορριφθεί.

Είναι σημαντικό να καταλάβετε ότι η εντολή git checkout -- [file] είναι


αρκετά επικίνδυνη. Όλες οι αλλαγές που έχετε κάνει σε αυτό το αρχείο έχουν πλέον
χαθεί καθώς έχετε αντιγράψει ένα αρχείο πάνω από αυτό. Μην χρησιμοποιείτε την
Important
εντολή αυτή παρά μόνο αν είσαστε σίγουροι ότι δεν θέλετε να κρατήσετε τις αλλαγές
σας.

Αν θέλετε να κρατήσετε τις αλλαγές που κάνατε στο αρχείο, αλλά παρόλα αυτά χρειάζεστε να το
κάνετε στην άκρη, θα πρέπει να εξετάσουμε την εναπόθεση (stashing) και την διακλάδωση
(branching) στο κεφάλαιο Διακλαδώσεις στο Git.
Να θυμάστε ότι οτιδήποτε είναι υποβεβλημένο στο Git μπορεί να ανακτηθεί. Μπορείτε να
ανακτήσετε ακόμα και υποβολές σε κλάδους που έχουν διαγραφεί ή υποβολές που
επανεγγράφηκαν, με την εντολή git commit --amend (βλ. Data Recovery για περισσότερα
πάνω στην ανάκτηση δεδομένων). Ωστόσο, αν κάτι δεν είναι υποβεβλημένο και το χάσετε, είναι
πολύ πιθανό να μην μπορέσετε να το ανακτήσετε.
2.5 Τα θεμελιώδη στοιχεία του Git -
Δουλεύοντας με απομακρυσμένα αποθετήρια
Δουλεύοντας με απομακρυσμένα αποθετήρια
Για να μπορέσετε να συνεργαστείτε σε οποιοδήποτε έργο στο Git, θα πρέπει να γνωρίζετε πως να
διαχειρίζεστε τα απομακρυσμένα αποθετήριά σας. Τα απομακρυσμένα αποθετήρια είναι
συγκεκριμένες εκδόσεις ενός έργου οι οποίες βρίσκονται στο διαδίκτυο ή σε κάποιο δίκτυο.
Μπορείτε να δημιουργήσετε όσα θέλετε, συνήθως τα αποθετήρια αυτά είναι προσβάσιμα από εσάς
μόνο. Για να μπορέσετε να συνεργαστείτε με άλλους και να τους κοινοποιήσετε την δουλειά σας,
θα πρέπει να μπορείτε να διαχειριστείτε τα αποθετήρια αυτά, να τραβάτε και να ωθείτε δεδομένα
σε αυτά. Η διαχείριση τέτοιων αποθετηρίων χρειάζεται ικανότητες όπως: πρόσθεση καινούριων
απομακρυσμένων αποθετηρίων, διαγραφή αποθετηρίων που δεν είναι πλέον σε ισχύ, διαχείριση
απομακρυσμένων κλάδων και πολλά άλλα. Στο κεφάλαιο αυτό, θα ασχοληθούμε με κάποιες από
αυτές τις ικανότητες.

Showing Your Remotes


Για να δείτε τους απομακρυσμένους διακομιστές που έχετε ρυθμίσει, εκτελέστε την εντολή git
remote. Η εντολή αυτή θα μας επιστρέψει μια λίστα με τα ονόματα των απομακρυσμένων που
έχετε ορίσει. Αν έχετε κλωνοποιήσει το δικό σας αποθετήριο, θα πρέπει να πάρετε σαν αποτέλεσμα
το όνομα origin. Αυτό είναι το προεπιλεγμένο όνομα που δίνει το Git στον διακομιστή από τον
οποίο μόλις κλωνοποιήσατε:
$ git clone https://github.com/schacon/ticgit
Cloning into 'ticgit'...
remote: Reusing existing pack: 1857, done.
remote: Total 1857 (delta 0), reused 0 (delta 0)
Receiving objects: 100% (1857/1857), 374.35 KiB | 268.00 KiB/s, done.
Resolving deltas: 100% (772/772), done.
Checking connectivity... done.
$ cd ticgit
$ git remote
origin

Μπορείτε επίσης να χρησιμοποιήσετε την επιλογή -v, η οποία θα σας επιστρέψει τα ονόματα των
απομακρυσμένων αποθετηρίων σας μαζί με τις διευθύνσεις που είναι συσχετισμένες για εγγραφή
και ανάγνωση σε αυτά:
$ git remote -v
origin https://github.com/schacon/ticgit (fetch)
origin https://github.com/schacon/ticgit (push)

Αν έχετε περισσότερα απομακρυσμένα, η εντολή αυτή θα τα απαριθμήσει όλα. Για παράδειγμα, αν


συνεργάζονται πολλά άτομα σε ένα αποθετήριο τότε μπορεί να έχει και αντίστοιχα πολλά
απομακρυσμένα:
$ cd grit
$ git remote -v
bakkdoor https://github.com/bakkdoor/grit (fetch)
bakkdoor https://github.com/bakkdoor/grit (push)
cho45 https://github.com/cho45/grit (fetch)
cho45 https://github.com/cho45/grit (push)
defunkt https://github.com/defunkt/grit (fetch)
defunkt https://github.com/defunkt/grit (push)
koke git://github.com/koke/grit.git (fetch)
koke git://github.com/koke/grit.git (push)
origin git@github.com:mojombo/grit.git (fetch)
origin git@github.com:mojombo/grit.git (push)

Αυτό μας βοηθάει ώστε να πάρουμε τις αλλαγές και τις συνεισφορές των άλλων χρηστών αρκετά
εύκολα. Επιπλέον μπορούμε, αν έχουμε τη εξουσιοδότηση, να ωθήσουμε αλλαγές σε αυτά. Η
εντολή αυτή δεν μας δίνει πληροφορίες για το αν έχουμε την εξουσιοδότηση αυτή.
Σημειώστε ότι τα απομακρυσμένα αποθετήρια χρησιμοποιούν μια πληθώρα από πρωτόκολλα. Θα
καλύψουμε αναλυτικά τα πρωτόκολλα αυτά στο κεφάλαιο Git on the Server.

Προσθέτοντας απομακρυσμένα αποθετήρια


Πάμε να δούμε λοιπόν πως να προσθέσουμε απομακρυσμένα αποθετήρια πιο αναλυτικά (έχουμε
αναφερθεί πιο περιληπτικά σε αυτό σε προηγούμενα κεφάλαια). Για να δώσετε ένα συντομευμένο
όνομα στο απομακρυσμένο αποθετήριο ώστε να μπορείτε να αναφέρεστε σε αυτό εύκολα,
εκτελέστε την εντολή git remote add [shortname] [url]:
$ git remote
origin
$ git remote add pb https://github.com/paulboone/ticgit
$ git remote -v
origin https://github.com/schacon/ticgit (fetch)
origin https://github.com/schacon/ticgit (push)
pb https://github.com/paulboone/ticgit (fetch)
pb https://github.com/paulboone/ticgit (push)

Τώρα πλέον μπορείτε να χρησιμοποιείτε στη γραμμή εντολών την συμβολοσειρά pb αντί για
ολόκληρη την διεύθυνση του αποθετηρίου. Για παράδειγμα, αν θέλετε να πάρετε όλες τις
πληροφορίες που έχει ο Paul στο αποθετήριό του, μπορείτε να εκτελέσετε την εντολή git fetch
pb:
$ git fetch pb
remote: Counting objects: 43, done.
remote: Compressing objects: 100% (36/36), done.
remote: Total 43 (delta 10), reused 31 (delta 5)
Unpacking objects: 100% (43/43), done.
From https://github.com/paulboone/ticgit
* [new branch] master -> pb/master
* [new branch] ticgit -> pb/ticgit

Πλέον έχετε πρόσβαση στον κύριο κλάδο του Paul ως pb/master. Μπορείτε να κάνετε διάφορες
ενέργειες όπως για παράδειγμα να τον συγχωνεύσετε σε έναν από τους δικούς σας κλάδους, ή να
ενημερώσετε έναν τοπικό σας κλάδο. Θα δούμε περισσότερα για τους κλάδους και πως μπορείτε να
τους χρησιμοποιήσετε στο κεφάλαιο Διακλαδώσεις στο Git.
Παίρνοντας δεδομένα από απομακρυσμένα αποθετήρια
Όπως μόλις είδαμε, για να πάρουμε δεδομένα από απομακρυσμένα έργα, μπορούμε να
εκτελέσουμε:
$ git fetch [remote-name]

Η εντολή αυτή θα τραβήξει από το απομακρυσμένο έργο όλα τα δεδομένα του που δεν έχετε
ακόμα. Αφού εκτελέσετε την εντολή αυτή, θα έχετε πρόσβαση σε όλους τους κλάδους αυτού του
απομακρυσμένου έργου. Τους κλάδους αυτούς μπορείτε έπειτα να τους συγχωνεύσετε ή να τους
αναλύσετε περαιτέρω.
Αν κλωνοποιήσετε ένα αποθετήριο, ουσιαστικά το αποθηκεύετε με το όνομα “origin”. Οπότε, η
εντολή git fetch origin θα τραβήξει όλες τις νέες αλλαγές που έχουν γίνει από τότε που
κλωνοποιήσατε το αποθετήριο ή τραβήξατε δεδομένα για τελευταία φορά από αυτό. Είναι
σημαντικό να τονίσουμε ότι η εντολή git fetch τραβάει δεδομένα στο τοπικό σας αποθετήριο.
Η εντολή αυτή δεν συγχωνεύει τα δεδομένα αυτά με διάφορες αλλαγές που μπορεί να έχετε κάνει
εσείς τοπικά. Για αυτό, θα πρέπει να κάνετε την συγχώνευση χειροκίνητα όταν είσαστε εσείς
έτοιμοι
Αν έχετε δημιουργήσει έναν κλάδο για να παρακολουθείτε έναν απομακρυσμένα κλάδο
(περισσότερες λεπτομέρειες για αυτό στο επόμενο κεφάλαιο, Διακλαδώσεις στο Git), μπορείτε να
χρησιμοποιήσετε την εντολή git pull. Η εντολή αυτή θα πάρει έναν απομακρυσμένο κλάδο και
θα τον συγχωνεύσει αυτόματα στον τρέχοντα κλάδο σας. Αυτή η ροή εργασιών είναι γενικά πιο
εύκολη για εσάς. Η εντολή git clone θέτει αυτόματα τον τοπικό σας κύριο κλάδο να
παρακολουθεί τις αλλαγές το απομακρυσμένου κύριου κλάδου (ή όπως έχετε ονομάσει τον
προεπιλεγμένο σας κλάδο). Εκτελώντας έπειτα την εντολή git pull, τραβάτε δεδομένα από τον
διακομιστή που αρχικά είχατε κλωνοποιήσει, και συγχωνεύετε τα δεδομένα αυτά με τον κώδικα
στον οποίο δουλεύετε.

Ώθηση δεδομένων σε απομακρυσμένα αποθετήρια


Όταν έχετε κάποιο έργο στο οποίο έχετε κάνει αλλαγές και το έχετε φτάσει σε σημείο που θέλετε
να το κοινοποιήσσετε, θα πρέπει να το ωθήσετε. Η εντολή είναι απλή: git push [remote-
name] [branch-name]. Αν θέλετε για παράδειγμα να ωθήσετε τον τοπικό σας κύριο κλάδο
στον απομακρυσμένο διακομιστή origin (η εντολή κλωνοποίησης ενός αποθετηρίου μας βοηθάει
για να έχουμε ρυθμισμένα σωστά τα ονόματα αυτά), θα πρέπει να εκτελέσετε την εντολή αυτή έτσι
ώστε να στείλετε όσες υποβολές έχετε κάνει πίσω στον διακομιστή:
$ git push origin master

Η εντολή αυτή θα εκτελεστεί επιτυχώς μόνο αν έχετε κλωνοποιήσει από έναν διακομιστή στον
οποίο έχετε δικαιώματα εγγραφής δεδομένων και αν κανείς άλλος δεν έχει ωθήσει δεδομένα στο
μεσοδιάστημα Αν εσείς και κάποιος άλλος έχετε κλωνοποιήσει το έργο την ίδια ώρα και αυτός
ωθήσει δεδομένα πίσω στον διακομιστή πριν από εσάς, η δικιάς σας εντολή για ώθηση δεδομένων
θα απορριφθεί. Αυτό που θα πρέπει να κάνετε είναι να τραβήξετε τις αλλαγές του άλλου και να τις
ενσωματώσετε στις δικές σας, ώστε να μπορείτε να ωθήσετε. Στο κεφάλαιο Διακλαδώσεις στο Git
θα δείτε περισσότερες πληροφορίες σχετικά με την ώθηση δεδομένων σε απομακρυσμένους
διακομιστές.

Εξετάζοντας ένα απομακρυσμένο αποθετήριο


Αν θέλετε να δείτε περισσότερες πληροφορίες σχετικά με ένα απoμακρυσμένο αποθετήριο,
μπορείτε να χρησιμοποιήσετε την εντολή git remote show [remote-name]. Αν για
παράδειγμα εκτελέσουμε την εντολή αυτή για ένα αποθετήριο με το συντομευμένο όνομα
origin, θα δούμε ως αποτέλεσμα:
$ git remote show origin
* remote origin
Fetch URL: https://github.com/schacon/ticgit
Push URL: https://github.com/schacon/ticgit
HEAD branch: master
Remote branches:
master tracked
dev-branch tracked
Local branch configured for 'git pull':
master merges with remote master
Local ref configured for 'git push':
master pushes to master (up to date)

Όπως βλέπουμε, η εντολή μας επιστρέφει την διεύθυνση του απομακρυσμένου αποθετηρίου καθώς
και τους κλάδους που παρακολουθούμε. Επίσης μας ενημερώνει ότι αν βρισκόμαστε στον κύριο
κλάδο και εκτελέσουμε git pull, θα συγχωνευτούν ο κύριος κλάδος με τον απομακρυσμένο
κύριο κλάδο. Επίσης μας ενημερώνει για τους απομακρυσμένους κλάδους που έχει τραβήξει.
Το παραπάνω είναι ένα απλό παράδειγμα που μπορεί να συναντήσετε. Όταν αρχίσετε να
χρησιμοποιείτε πιο εκτεταμένα το Git, μπορεί να δείτε πολύ περισσότερες πληροφορίες με την
εντολή git remote show, για παράδειγμα:
$ git remote show origin
* remote origin
URL: https://github.com/my-org/complex-project
Fetch URL: https://github.com/my-org/complex-project
Push URL: https://github.com/my-org/complex-project
HEAD branch: master
Remote branches:
master tracked
dev-branch tracked
markdown-strip tracked
issue-43 new (next fetch will store in
remotes/origin)
issue-45 new (next fetch will store in
remotes/origin)
refs/remotes/origin/issue-11 stale (use 'git remote prune' to remove)
Local branches configured for 'git pull':
dev-branch merges with remote dev-branch
master merges with remote master
Local refs configured for 'git push':
dev-branch pushes to dev-branch (up
to date)
markdown-strip pushes to markdown-strip (up
to date)
master pushes to master (up
to date)
Η εντολή μας δείχνει σε αυτή την περίπτωση σε ποιον κλάδο ωθείτε δεδομένα όταν βρίσκεστε σε
συγκεκριμένους κλάδους και εκτελείτε την εντολή git push. Επίσης μας δείχνει ποιους
απομακρυσμένους κλάδους του διακομιστή δεν έχετε ακόμα, τους απομακρυσμένους κλάδους που
έχετε αλλά έχουν αφαιρεθεί από τον διακομιστή, καθώς και τους κλάδους που θα συγχωνευτούν
αυτόματα αν εκτελέσετε την εντολή git pull.

Αφαιρώντας και μετονομάζοντας απομακρυσμένα αποθετήρια


Αν θέλετε να μετονομάσετε την αναφορά που έχετε σε ένα απομακρυσμένο αποθετήριο, εκτελέστε
την εντολή git remote rename ώστε να αλλάξετε το συντομευμένο όνομά του. Για
παράδειγμα, αν θέλετε να μετονομάσετε το pb σε paul, μπορείτε να εκτελέσετε git remote
rename:
$ git remote rename pb paul
$ git remote
origin
paul

Αξίζει να σημειώσουμε ότι η εντολή αυτή αλλάζει επίσης και τα ονόματα των απομακρυσμένων
κλάδων. Για παράδειγμα, ένας κλάδος που αναφερόταν ως pb/master πλέον θα αναφέρεται ως
paul/master.

Μπορεί επίσης για κάποιο λόγο να θέλετε να διαγράψετε ένα απομακρυσμένο αποθετήριο. Για
παράδειγμα, μπορεί να έχετε μετακινήσει τον διακομιστή σε άλλη διεύθυνση, ή να μην
χρησιμοποιείτε το συγκεκριμένο αποθετήριο, ή απλά να μην θέλετε να συνεισφέρετε πλέον σε
αυτό. Σε αυτή την περίπτωση μπορείτε να χρησιμοποιήσετε την εντολή git remote rm:
$ git remote rm paul
$ git remote
origin
2.6 Τα θεμελιώδη στοιχεία του Git -
Χρησιμοποιώντας ετικέτες
Χρησιμοποιώντας ετικέτες
Το Git, όπως και τα περισσότερα συστήματα ελέγχου έκδοσης, δίνει την δυνατότητα να βάλετε
ετικέτες σε συγκεκριμένα σημεία του ιστορικού ενός έργου. Η λειτουργικότητα αυτή
χρησιμοποείται συνήθως για σημειωθούν συγκεκριμένες εκδόσεις (π.χ. έκδοση 1.0 κ.ο.κ.). Στο
κεφάλαιο αυτό θα μάθετε πως να βλέπετε αυτές τις ετικέτες σε ένα έργο, πως να τις δημιουργείτε
καθώς και ποιοι διαφορετικοί τύποι ετικετών υπάρχουν.

Απαριθμώντας τις ετικέτες


Για να δείτε τις ετικέτες ενός έργου, η εντολή στο Git είναι αρκετά σαφής. Απλά πληκτρολογήστε
git tag:
$ git tag
v0.1
v1.3

Η εντολή θα απαριθμήσει τις ετικέτες σε αλφαβητική σειρά, αν και η σειρά αυτή δεν έχει κάποια
ιδιαίτερη σημασία.
Μπορείτε επίσης να αναζητήσετε ετικέτες με συγκεκριμένα μοτίβα. Για παράδειγμα, το αποθετήριο
με τον πηγαίο κώδικα του Git περιέχει περισσότερες από 500 ετικέτες. Αν ενδιαφέρεστε να δείτε
μόνο αυτές που έχουν σχέση με την έκδοση 1.8.5, τότε μπορείτε να εκτελέσετε:
$ git tag -l 'v1.8.5*'
v1.8.5
v1.8.5-rc0
v1.8.5-rc1
v1.8.5-rc2
v1.8.5-rc3
v1.8.5.1
v1.8.5.2
v1.8.5.3
v1.8.5.4
v1.8.5.5

Δημιουργώντας ετικέτες
Το Git χρησιμοποιεί δύο κατηγορίες ετικετών, τις ελαφρείς (lightweight) και τις ετικέτες με
σημειώσεις (annotated).
Μια ελαφριά ετικέτα μοιάζει πολύ με έναν κλάδο που δεν αλλάζει. Η ετικέτα αυτού του τύπου είναι
απλά ένας δείκτης σε μια συγκεκριμένη υποβολή.
Οι ετικέτες με σημειώσειες από την άλλη, αποθηκεύονται στη βάση δεδομένων του Git. Για κάθε
μία ετικέτα με σημειώσεις, υπολογίζεται το checksum της το οποίο περιέχει: το όνομα αυτού που
βάζει την ετικέτα, την διεύθυνση e-mail του, την ημερομηνία, καθώς και το μήνυμα της ετικέτας. Η
ετικέτα αυτή μπορεί να υπογραφεί και να επαληθευθεί μέσω του GNU Privacy Guard (GPG). Είναι
γενικά προτιμώμενο να χρησιμοποιείτε ετικέτες με σημειώσεις έτσι ώστε να έχετε όλη αυτή την
πληροφορία. Παρ' όλα αυτά, αν για κάποιο λόγο θέλετε να χρησιμοποιήσετε μια ετικέτα χωρίς
περεταίρω πληροφορίες για αυτή, μπορείτε να χρησιμοποιήσετε τις ελαφρείς ετικέτες.

Ετικέτες με σημειώσεις
Η δημιουργία μιας ετικέτας με σημειώσεις είναι απλή. Ο ευκολότερος τρόπος είναι να
χρησιμοποιήσετε την επιλογή -a όταν εκτελείτε την εντολή tag:
$ git tag -a v1.4 -m 'my version 1.4'
$ git tag
v0.1
v1.3
v1.4

Η επιλογή -m προσδιορίζει το μήνυμα της ετικέτας, το οποίο και αποθηκεύεται μαζί με την ετικέτα.
Αν δεν προσδιορίσετε κάποιο μήνυμα σε μια καινούρια ετικέτα με σημειώσεις, τότε το Git θα
εκκινήσει έναν επεξεργαστή κειμένου ώστε να γράψετε το μήνυμα εκεί.
Χρησιμοποιώντας την εντολή git show μπορείτε να δείτε τις πληροφορίες που περιέχει μια
ετικέτα:
$ git show v1.4
tag v1.4
Tagger: Ben Straub <ben@straub.cc>
Date: Sat May 3 20:19:12 2014 -0700

my version 1.4

commit ca82a6dff817ec66f44342007202690a93763949
Author: Scott Chacon <schacon@gee-mail.com>
Date: Mon Mar 17 21:52:11 2008 -0700

changed the version number

Η εντολή αυτή μας δείχνει πληροφορίες για τον χρήστη που έβαλε την ετικέτα, την ημερομηνία που
χρησιμοποιήθηκε η ετικέτα στην υποβολή, καθώς και το μήνυμά της.

Ελαφρείς ετικέτες
Ένας άλλος τρόπος για να βάλετε ετικέτες στις υποβολές είναι οι ελαφρείς ετικέτες. Η ετικέτα δεν
περιλαμβάνει καμία περαιτέρω πληροφορία εκτός από το checksum της υποβολής σας. Για να
δημιουργήσετε μια τέτοια ετικέτα, θα πρέπει να μην χρησιμοποιήσετε τις επιλογές -a, -s, ή -m:
$ git tag v1.4-lw
$ git tag
v0.1
v1.3
v1.4
v1.4-lw
v1.5

Αν τώρα εκτελέσετε την εντολή git show για την συγκεκριμένη ετικέτα, δεν θα δείτε τις
επιπλέον πληροφορίες μιας ετικέτας. Η εντολή θα μας δείξει απλά την υποβολή:
$ git show v1.4-lw
commit ca82a6dff817ec66f44342007202690a93763949
Author: Scott Chacon <schacon@gee-mail.com>
Date: Mon Mar 17 21:52:11 2008 -0700

changed the version number

Αναθέτοντας ετικέτες αργότερα


Μπορείτε επίσης να αναθέσετε ετικέτες σε παλαιότερες υποβολές. Έστω λοιπόν ότι το ιστορικό
υποβολών σας είναι κάπως έτσι:
$ git log --pretty=oneline
15027957951b64cf874c3557a0f3547bd83b3ff6 Merge branch 'experiment'
a6b4c97498bd301d84096da251c98a07c7723e65 beginning write support
0d52aaab4479697da7686c15f77a3d64d9165190 one more thing
6d52a271eda8725415634dd79daabbc4d9b6008e Merge branch 'experiment'
0b7434d86859cc7b8c3d5e1dddfed66ff742fcbc added a commit function
4682c3261057305bdd616e23b64b0857d832627b added a todo file
166ae0c4d3f420721acbb115cc33848dfcc2121a started write support
9fceb02d0ae598e95dc970b74767f19372d61af8 updated rakefile
964f16d36dfccde844893cac5b347e7b3d44abbc commit the todo
8a5cbc430f1a9c3d00faaeffd07798508422908a updated readme

Ας υποθέσουμε τώρα ότι ξεχάσατε να βάλετε ετικέτα στο άργο σας στην έκδοση 1.2 που ήταν η
υποβολή με το μήνυμα “updated rakefile”. Μπορείτε να βάλετε την ετικέτα όποτε θέλετε. Για να το
κάνετε αυτό, θα πρέπει να προσδιορίσετε το checksum της υποβολής σας (ή ένα μέρος του) στο
τέλος της εντολής:
$ git tag -a v1.2 9fceb02

Μπορείτε τώρα να δείτε ότι έχετε προσθέσει την ετικέτα στην υποβολή:
$ git tag
v0.1
v1.2
v1.3
v1.4
v1.4-lw
v1.5

$ git show v1.2


tag v1.2
Tagger: Scott Chacon <schacon@gee-mail.com>
Date: Mon Feb 9 15:32:16 2009 -0800

version 1.2
commit 9fceb02d0ae598e95dc970b74767f19372d61af8
Author: Magnus Chacon <mchacon@gee-mail.com>
Date: Sun Apr 27 20:43:35 2008 -0700

updated rakefile
...

Κοινωποιώντας τις ετικέτες


Από προεπιλογή, η εντολή git push δεν μεταφέρει ετικέτες στους διακομιστές. Θα πρέπει να
ορίσετε σαφώς ότι θέλετε να ωθήσσετε τις ετικέτες στον διακομιστή, αφού πρώτα τις
δημιουργήσετε. Η διαδικασία αυτή είναι παρόμοια με το να κοινωποιείτε απομακρυσμένους
κλάδους. Θα πρέπει λοιπόν να εκτελέσουμε την εντολή git push origin [tagname].
$ git push origin v1.5
Counting objects: 14, done.
Delta compression using up to 8 threads.
Compressing objects: 100% (12/12), done.
Writing objects: 100% (14/14), 2.05 KiB | 0 bytes/s, done.
Total 14 (delta 3), reused 0 (delta 0)
To git@github.com:schacon/simplegit.git
* [new tag] v1.5 -> v1.5

Αν έχετε πολλές ετικέτες που θέλετε να ωθήσετε με τη μία, μπορείτε επίσης να χρησιμοποιήσετε
την επιλογή --tags στην εντολή git push. Με τον τρόπο αυτό θα μεταφέρετε στον διακομιστή
όλες τις ετικέτες που δεν είναι ήδη εκεί.
$ git push origin --tags
Counting objects: 1, done.
Writing objects: 100% (1/1), 160 bytes | 0 bytes/s, done.
Total 1 (delta 0), reused 0 (delta 0)
To git@github.com:schacon/simplegit.git
* [new tag] v1.4 -> v1.4
* [new tag] v1.4-lw -> v1.4-lw

Έπειτα, όταν κάποιος κλωνοποιήσει ή τραβήξει δεδομένα από το αποθετήριό σας, θα λάβει μαζί
και όλες τις υπάρχουσες ετικέτες.

Ενημερώνοντας τις ετικέτες


Λόγω του γεγονότος ότι οι ετικέτες δεν μπορούν να μετακινηθούν, δεν μπορούμε να κάνουμε
κανονική ενημέρωση του αποθετηρίου μας με βάση μια ετικέτα. Αν θέλετε να βάλετε μια έκδοση
του αποθετηρίου σας στον κατάλογο εργασίας σας, η οποία να μοιάζει με μια συγκεκριμένη
ετικέτα, μπορείτε να δημιουργήσετε έναν καινούριο κλάδο σε μια συγκεριμένη ετικέτα με την
εντολή git checkout -b [branchname] [tagname]:
$ git checkout -b version2 v2.0.0
Switched to a new branch 'version2'

Αν βέβαια εκτελέσετε την παραπάνω εντολή και πραγματοποιήσετε μια υποβολή, ο κλάδος
version2 θα είναι λίγο διαφορετικός από την ετικέτα v2.0.0 καθώς θα περιλαμβάνει και τις
καινούριες σας αλλαγές.
2.7 Τα θεμελιώδη στοιχεία του Git -
Συντομεύεσεις στο Git
Συντομεύεσεις στο Git
Πριν τελειώσουμε το κεφάλαιο αυτό, υπάρχει μια μικρή συμβουλή που μπορείτε να ακολουθήσετε
για να κάνετε την εμπειρία σας με το Git πιο απλή: χρησιμοποιήστε τις συντομεύσεις. Δεν θα
αναφερθούμε για αυτές στη συνέχεια του βιβλίου αλλά καλό θα ήταν να ξέρετε πως να τις
χρησιμοποιείτε.
Το Git μπορεί να καταλάβει μια εντολή μόνο αν την γράψετε ολόκληρη. Αν δεν θέλετε να
πληκτρολογήσετε όλα τα γράμματα μιας εντολής, μπορείτε να ορίσετε μια συντόμευση για κάθε
εντολή χρησιμοποιώντας την git config. Μερικά παραδείγματα για το πως μπορείτε να
ορίσετε μερικές συντομεύσεις:
$ git config --global alias.co checkout
$ git config --global alias.br branch
$ git config --global alias.ci commit
$ git config --global alias.st status

Αυτό σημαίναι ότι μπορείτε, για παράδειγμα, να πληκτρολογήσετε git ci αντί για git
commit. Καθώς χρησιμοποιείτε το Git, θα δείτε ότι υπάρχουν και άλλες εντολές που
χρησιμοποιείτε συχνά. Μην παραλείψετε να δημιουργήσετε συντομεύσεις και για αυτές.
Η τεχνική αυτή μπορεί να φανεί χρήσιμη για εντολές που πιστεύετε ότι θα έπρεπε να υπήρχαν. Για
παράδειγμα, αν θέλετε να κάνετε πιο εύχρηστη την διαδικασία ακύρωσης καταχώρησης ενός
αρχείου, μπορείτε να δημιουργήσετε μια συντόμευση για αυτή:
$ git config --global alias.unstage 'reset HEAD --'

Με αυτόν τον τρόπο, οι δύο παρακάτω εντολές γίνονται ισοδύναμες:


$ git unstage fileA
$ git reset HEAD fileA

Η εντολή που εκτελούμε φαίνεται πλέον πιο καθαρά. Η συντόμευση last είναι επίσης πολύ
συνηθισμένη:
$ git config --global alias.last 'log -1 HEAD'

Με τον τρόπο αυτό μπορείτε να δείτε εύκολα την τελευταία υποβολή:


$ git last
commit 66938dae3329c7aebe598c2246a8e6af90d04646
Author: Josh Goebel <dreamer3@example.com>
Date: Tue Aug 26 19:48:51 2008 +0800

test for current head

Signed-off-by: Scott Chacon <schacon@example.com>


Όπως μπορείτε να δείτε, το Git μπορεί να αντικαταστήσει μια εντολή με οποιαδήποτε συντόμευση
ορίσετε. Παρ' όλα αυτά, μπορεί αντί για μια εντολή του Git, να θέλετε να εκτελέσετε μια εξωτερική
εντολή. Στην περίπτωση αυτή, θα πρέπει να ξεκινήσετε την εντολή με τον χαρακτήρα του
θαυμαστικού, !. Αυτό θα σας φανεί χρήσιμο αν χρησιμοποείτε εργαλεία που δουλεύουν με
αποθετήρια Git. Για παράδειγμα, μπορούμε να χρησιμοποιήσουμε την συντόμευση git visual
για να εκτελέσουμε την εντολή gitk:
$ git config --global alias.visual '!gitk'

You might also like