Skip to content

Git version control

Version control in projects is important, but might be still a difficult thing.

Different projects are called (in Git language) as "repositories". In the slang of the IT field this repository/project term is often mixed.

Git tool was formed from the need of the Linux Kernel community to get a distributed version control system for source code tracking. After this, Git has developed to encompass a lot of other things, but it is still strongly for source code tracking.

Few recommended videos about the motivation to create and use Git: - Linus Torvalds interview of Git - Linus Torvalds speech on Git

Markdown

On the course we will use the Markdown writing format.

Markdown is a convenient file/writing format, because:

  1. Writing is simple
  2. It is the basic file format for different Git development environments to create web pages

This whole course has been written in the Markdown format.

Gitxyz development environment

Development environments bring other functionalities around git. E.g., Issue Tracker and Continuous Integration chains (Note! You don't have to understand them at this point).

These development environments give the basic user its most valuable asset in controlling the repository: the web browser (front end). In theory you do not even have to use the command-line interface, if you do not wish to do so. On this course we use the command-line interface to understand the technical functionality of the git version control.

Gitlab

Gitlab is an open source Git repository management software. It also includes a bunch of handy features.

On this course we use Gitlab (rather than Github), because it can be (if necessary) installed locally on a virtual machine. You can separately control the entire Git environment. This is how you understand the technical functionality of Git.

Github

Github is more popular than Gitlab (and older) management software. Github can be called the 'social media of programmers', in which you can follow the projects/repositories of your favourite programmers. The Github profile page has developed into a "CV" of programmers.

Github can be used with the learning outcomes of this course, but you cannot install a local virtual machine of Github. It is left for the student to decide which product they might choose to use later on in their (coding) projects.

Usually the exporting and importing of repositories out of one environment to another is painless. There are of course some features of each individual management system that might have valuable information to you and might be left behind.

Version Control

Version control follows the changes in a file (or multiple files) over a time span. This time could be for example the lifespan of a project.

Local Version Control System

At its simplest form the version control system could be utilized in local files (or local hard drive).

Local

We might for example have a folder C:/HomeAssignments/. This folder might then include files such as:

  • Assignment_v01.docx
  • Assignment_v02.docx
  • Assignment_v03.docx

It is a failry simple structure, but effective. Unfortunately us humans are very irregular people and we usually make mistakes. Also the distribution of the folder is a cumbersome task. Email could be one way of sending version back and forth, but changes made are dependant on the file formating and its support for multiple users (and their version control).

On the video below, I am working with two different virtual machines: Windows 10 ja Ubuntu. Noticeable is that the changes on another computers local harddrive aren't seen on the other computer.

Watch video: localharddrive.webm

The files have to be moved by an USB stick, email, or by some other transferrable media.

Centralized Version Control System

Next step is towards a centralized version control (Version Control System - VCS) such as network drives (or cloud services as you now might know them). A certain Group has been given writing permissions on a network drive (or a cloud service folder). Still the changes made, naming and such are hard things. Very likely a few different people do different judgements in the same folder.

Also a centralized version control has the problem of collaboration. Also it is a "Single Point of Failure", because if the network drive (or network connectivity) fails. No one can work on the files.

Centralized

On the next video I am using LabraNet:s network disk service under //ghost.labranet.jamk.fi/temp/verkkolevy folder. Notice that both of the computers can see the same network drive (on the server), thus changes can be seen by both. There are conflicting situations, if both are working on the same file.

Watch video: networkdrive.webm

How network drives handle these race situations concerning locking/writing on files is a subject outside of this course.

Distributed Version Control System

Distributed Version Control System ... distributes the files to all the users. Each of them have a copy of the files, but the server also contains those files. It would be preferrable that changes made to your own files should be uploaded to the centralized server once in a while. This distribution of working mandates a few steps when you work, but Git does these steps controllable.

Distributed

The hard part is to get people learn how the Git -tool works and how to take those necessary steps. When the student learns (or masters) of the benefits of Git, they usually start to demand it in several projects that they do (e.g. school assignments).

On the video below I show the basics of git very quickly to demonstrate its effectiveness.

Watch video: git.webm

Note! The video takes a bit more time to create the repositories, but the version control addition per file starts to overtake the "nuisance" of using the commands eventually. In a short while you do not even notice the given commands.

Source: Chacon, S. & Straub, B. 2014. Pro Git.

Markdown & Git

Importing a Repository

Sign into https://gitlab.labranet.jamk.fi with the credentials you were provided and select New project.

image

From the resulting webpage select Import project.

image

The file you were provided was an Gitlab export and so we select it.

image

Fill in the repository name (note! gitlab-course is just an example) and press Browse... (in the screenshot the button is in Finnish: Selaa...).

image

Find the suitable file for importing and press Open. Once the file is visible in the browser next to the Browse button, you can select Import Project.

image

The importing takes a while for the file to upload and then the server to process the contents. Be sure that you do not extract the file e.g. gitlab-course.tar.gz would be gitlab-course.tar (this is common on the Safari browser). The file uploaded to the server has to have a .tar.gz ending.

Once the project has bee imported correctly you can find the Clone button to proceed in the steps below.

image

Markdown file creation and the basics of Git

Next lets make the following steps to create one file.md to move between local version control and the distributed version control.

The markdown files are the backbone of git repository documentation. You can add other files into repository for the version control tracking similarly. Go through the basics and at the end there is instructions for other types of files.

Git basics

We mainly work on the command-line interface on this course. This means that you should use in Windows e.g. Git Bash (can be found after the installation by pressing right mouse button in the desktop or folder)

image

The following commands are written in git bash.

Lets first create a folder where we use the version control (e.g. C:/Users/user/git/ or /home/user/git/). Below a example from the Git Bash command-line interface.

Sahka-Laptop@DESKTOP-U189FED MINGW64 ~
$ pwd
/c/Users/Sahka-Laptop

Sahka-Laptop@DESKTOP-U189FED MINGW64 ~
$ mkdir git

Sahka-Laptop@DESKTOP-U189FED MINGW64 ~
$ cd git

Sahka-Laptop@DESKTOP-U189FED MINGW64 ~/git
$ pwd
/c/Users/Sahka-Laptop/git

Lets clone the workspace under the git -folder. Notice that the user credentials have to be your own student number. E.g. https://gitlab.labranet.jamk.fi/k1234/gitlab-course.git (look at the video below)

Repository link

When you find the link (Note! HTTPS in this part of the studies) start to follow the instructions below.

Sahka-Laptop@DESKTOP-U189FED MINGW64 ~/git
$ git clone https://gitlab.labranet.jamk.fi/sahka/gitlab-course.git
Cloning into 'gitlab-course'...

Your own credentials

Username for 'https://gitlab.labranet.jamk.fi': sahka

Your own password

Password for 'https://sahka@gitlab.labranet.jamk.fi': <password>

If the login goes correctly, the repository/project contents are copied to your local hard drive ... as the folder .../git/gitlab-course/ -folder.

remote: Counting objects: 129, done.
remote: Compressing objects: 100% (66/66), done.
remote: Total 129 (delta 42), reused 44 (delta 20)
Receiving objects: 100% (129/129), 348.25 KiB | 0 bytes/s, done.
Resolving deltas: 100% (58/58), done.
Checking connectivity... done.

Lets check the folder contents with the ls command and move to gitlab-course folder with cd command.

Sahka-Laptop@DESKTOP-U189FED MINGW64 ~/git
$ ls
gitlab-course/

Sahka-Laptop@DESKTOP-U189FED MINGW64 ~/git
$ cd gitlab-course/

Lets check the situation of the folder with the git status -command.

Sahka-Laptop@DESKTOP-U189FED MINGW64 ~/git/gitlab-course (master)
$ git status
On branch master
Your branch is up-to-date with 'origin/master'.
nothing to commit, working directory clean

In the text above is the most important part is nothing to commit, which means that the folder (and its contents) have no changes.

Lets make a file named firstname_surname_studentnumber.md and lets copy the content below (# topic...).

Open e.g. notepad++ and create the file into the folder. Check that the file end is not firstname_surname_studentnumber.md.txt, but firstname_surname_studentnumber.md.

Copy the text below into the file

# topic

texts...

Lets save the file under the gitlab-course -folder e.g. .../git/gitlab-course/karo_saharinen_sahka.md and check the command-line interface of the changes within the folder.

git status
On branch master
Your branch is up-to-date with 'origin/master'.
Untracked files:
  (use "git add <file>..." to include in what will be committed)

    karo_saharinen_sahka.md

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

Git notices a new file, which isn't (version) tracked ("Untracked files:").

The file can be added for tracking/into the repository with the command.

Sahka-Laptop@DESKTOP-U189FED MINGW64 ~/git/gitlab-course (master)
$ git add karo_saharinen_sahka.md

After this command lets check the status once again.

Sahka-Laptop@DESKTOP-U189FED MINGW64 ~/git/gitlab-course (master)
$ git status
On branch master
Your branch is up-to-date with 'origin/master'.
Changes to be committed:
  (use "git reset HEAD <file>..." to unstage)

    new file:   karo_saharinen_sahka.md

The file has now been taken a part of the version control/repository, but notice that it has to be committed. So it is staged, but not confirmed/committed into the repository. Lets commit to this change.

Sahka-Laptop@DESKTOP-U189FED MINGW64 ~/git/gitlab-course (master)
$ git commit -m "My own markdown file to the project"

-m addition to the command adds a change text, which can be used afterwards. Here we conclude that the first file has been created.

If you commit for the first time, the git program might inform you the following:

*** Please tell me who you are.

Run

  git config --global user.email "you@example.com"
  git config --global user.name "Your Name"

to set your account's default identity.
Omit --global to set the identity only in this repository.

fatal: unable to auto-detect email address (got 'sahka@sahka-VirtualBox.(none)')

So define your user (with your own information of course)

git config --global user.email "karo.saharinen@jamk.fi"
git config --global user.name "Karo Saharinen"

After the commands above the command git commit goes through.

git commit -m "My own markdown file to the project"
[master 8255e11] My own markdown file to the project
 1 file changed, 3 insertions(+)
 create mode 100644 karo_saharinen_sahka.md

Now changes are committed in your local version control. These have to be published to the server.

Sahka-Laptop@DESKTOP-U189FED MINGW64 ~/git/gitlab-course (master)
$ git push

warning: push.default is unset; its implicit value has changed in
Git 2.0 from 'matching' to 'simple'. To squelch this message
and maintain the traditional behavior, use:

  git config --global push.default matching

To squelch this message and adopt the new behavior now, use:

  git config --global push.default simple

When push.default is set to 'matching', git will push local branches
to the remote branches that already exist with the same name.

Since Git 2.0, Git defaults to the more conservative 'simple'
behavior, which only pushes the current branch to the corresponding
remote branch that 'git pull' uses to update the current branch.

See 'git help config' and search for 'push.default' for further information.
(the 'simple' mode was introduced in Git 1.7.11. Use the similar mode
'current' instead of 'simple' if you sometimes use older versions of Git)

Username for 'https://gitlab.labranet.jamk.fi': <k1234>
Password for 'https://sahka@gitlab.labranet.jamk.fi': <salasana>
Counting objects: 3, done.
Delta compression using up to 2 threads.
Compressing objects: 100% (2/2), done.
Writing objects: 100% (3/3), 356 bytes | 0 bytes/s, done.
Total 3 (delta 0), reused 0 (delta 0)
To https://gitlab.labranet.jamk.fi/sahka/gitlab-course.git
   7a3f1b5..8255e11  master -> master

Now the changes have been sent to the server. Now the version control between the server and your local hard drive is coherent.

When you use your browser to look at the repository, you can see your file within the server.

Other files can be copied now into your repository folder (the example had gitlab-course) such as report.pdf, data.json or python.py.

  1. Copy the file to the repository
  2. in Git Bash
    • git add *
    • `git commit -m "my new file to the repository"
    • git push

Be vary of using the https/web front end for the uploading of files. If you upload files to the server directly from your browser, You need to download them locally with git pull.

GPG

Typically GPG comes pre-installed on Linux distributions.

Sahka@sahka-virtualbox:~$ gpg --help
gpg (GnuPG) 2.2.27
libgcrypt 1.9.4
Copyright (C) 2021 Free Software Foundation, Inc.
License GNU GPL-3.0-or-later <https://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.

Home: /home/sahka/.gnupg
Supported algorithms:
Pubkey: RSA, ELG, DSA, ECDH, ECDSA, EDDSA
Cipher: IDEA, 3DES, CAST5, BLOWFISH, AES, AES192, AES256, TWOFISH,
        CAMELLIA128, CAMELLIA192, CAMELLIA256
Hash: SHA1, RIPEMD160, SHA256, SHA384, SHA512, SHA224
Compression: Uncompressed, ZIP, ZLIB, BZIP2

Syntax: gpg [options] [files]
Sign, check, encrypt or decrypt
Default operation depends on the input data

Commands:

 -s, --sign                  make a signature
     --clear-sign            make a clear text signature
 -b, --detach-sign           make a detached signature
 -e, --encrypt               encrypt data
 -c, --symmetric             encryption only with symmetric cipher
 -d, --decrypt               decrypt data (default)
     --verify                verify a signature

.....

GPG Key Generation

Generate keys with the command gpg --gen-key

Notice the parameters below:

  • Real Name: use your firstname lastname
  • Email address: use your email address

Verify the input by inserting O (for Okay).

sahka@sahka-virtualbox:~$ gpg --gen-key
gpg (GnuPG) 2.2.27; Copyright (C) 2021 Free Software Foundation, Inc.                                                                   
This is free software: you are free to change and redistribute it.                                                                      
There is NO WARRANTY, to the extent permitted by law. 

gpg: directory '/home/sahka/.gnupg' created                                                                                             
gpg: keybox '/home/sahka/.gnupg/pubring.kbx' created                                                                                    
Note: Use "gpg --full-generate-key" for a full featured key generation dialog.   

GnuPG needs to construct a user ID to identify your key. 

Real name: Edgar Example                                                                                                                
Email address: edgar@example.com                                                                                                        
You selected this USER-ID:                                                                                                              
    "Edgar Example <edgar@example.com>"                                                                                                 

Change (N)ame, (E)mail, or (O)kay/(Q)uit? O
Change (N)ame, (E)mail, or (O)kay/(Q)uit? O
We need to generate a lot of random bytes. It is a good idea to perform
some other action (type on the keyboard, move the mouse, utilize the
disks) during the prime generation; this gives the random number
generator a better chance to gain enough entropy.

The prompt asks for you to protect the private key with a password.

signing

At this point to create enough randomization for cryptographic key generation

.... type randomly on your keyboard or move your mouse until the terminal prints the following ...

gpg: /home/sahka/.gnupg/trustdb.gpg: trustdb created
gpg: key DC657F1356DDD0CF marked as ultimately trusted
gpg: directory '/home/sahka/.gnupg/openpgp-revocs.d' created
gpg: revocation certificate stored as '/home/sahka/.gnupg/openpgp-revocs.d/A0ABA5BE7187F70224338470DC657F1356DDD0CF.rev'
public and secret key created and signed.

pub   rsa3072 2023-10-12 [SC] [expires: 2025-10-11]
      A0ABA5BE7187F70224338470DC657F1356DDD0CF
uid                      Edgar Example <edgar@example.com>
sub   rsa3072 2023-10-12 [E] [expires: 2025-10-11]

sahka@sahka-virtualbox:~$                     

Now the keys have been generated.

Checking the generated keys

You can now inspect the keys within your keychain.

sahka@sahka-virtualbox:~$ gpg --list-keys
gpg: checking the trustdb
gpg: marginals needed: 3  completes needed: 1  trust model: pgp
gpg: depth: 0  valid:   1  signed:   0  trust: 0-, 0q, 0n, 0m, 0f, 1u
gpg: next trustdb check due at 2025-10-11
/home/sahka/.gnupg/pubring.kbx
------------------------------
pub   rsa3072 2023-10-12 [SC] [expires: 2025-10-11]
      A0ABA5BE7187F70224338470DC657F1356DDD0CF
uid           [ultimate] Edgar Example <edgar@example.com>
sub   rsa3072 2023-10-12 [E] [expires: 2025-10-11]

sahka@sahka-virtualbox:~$ 

Exporting the Public Key

And export your public key with naming the file e.g. gpg_public_key_<firstname>_<lastname>.asc.

sahka@sahka-virtualbox:~$ gpg --export -a A0ABA5BE7187F70224338470DC657F1356DDD0CF > gpg_public_key_edgar_example.asc
sahka@sahka-virtualbox:~$ more gpg_public_key_edgar_example.asc 
-----BEGIN PGP PUBLIC KEY BLOCK-----

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
a9w+iCZA63Awyv9pdajvF5CJ4hM+0qrryw==
=CZpL
-----END PGP PUBLIC KEY BLOCK-----
sahka@sahka-virtualbox:~$

You can now send the public key to anyone you would like to communicate with (e.g. as an email attachment).

Importing a public key from another person

Download the public key of Karo Saharinen (SahKa). In the example this is done with wget rather than a graphical browser.

sahka@sahka-virtualbox:~$ wget https://student.labranet.jamk.fi/~sahka/taustamateriaali/sahka_gpg_publickey.asc
--2023-10-12 15:16:16--  https://student.labranet.jamk.fi/~sahka/taustamateriaali/sahka_gpg_publickey.asc
Resolving student.labranet.jamk.fi (student.labranet.jamk.fi)... 195.148.26.130
Connecting to student.labranet.jamk.fi (student.labranet.jamk.fi)|195.148.26.130|:443... connected.
HTTP request sent, awaiting response... 200 OK
Length: 4795 (4,7K) [text/plain]
Saving to: ‘sahka_gpg_publickey.asc’

sahka_gpg_publickey.asc           100%[=============================================================>]   4,68K  --.-KB/s    in 0s      

2023-10-12 15:16:16 (2,74 GB/s) - ‘sahka_gpg_publickey.asc’ saved [4795/4795]

sahka@sahka-virtualbox:~$ ls
sahka_gpg_publickey.asc

Import the public key by using gpg --import <filelocation>

sahka@sahka-virtualbox:~$ gpg --import Downloads/sahka_gpg_publickey.asc 
gpg: key 14672610C5AEF029: 3 signatures not checked due to missing keys
gpg: key 14672610C5AEF029: public key "Karo Saharinen <karo.saharinen@jamk.fi>" imported
gpg: Total number processed: 1
gpg:               imported: 1
gpg: marginals needed: 3  completes needed: 1  trust model: pgp
gpg: depth: 0  valid:   1  signed:   0  trust: 0-, 0q, 0n, 0m, 0f, 1u
gpg: next trustdb check due at 2025-10-11
sahka@sahka-virtualbox:~$ 

You can check that only the public key has been imported

sahka@sahka-virtualbox:~$ gpg --list-public-keys
/home/sahka/.gnupg/pubring.kbx
------------------------------
pub   rsa3072 2023-10-12 [SC] [expires: 2025-10-11]
      A0ABA5BE7187F70224338470DC657F1356DDD0CF
uid           [ultimate] Edgar Example <edgar@example.com>
sub   rsa3072 2023-10-12 [E] [expires: 2025-10-11]

pub   rsa4096 2018-03-16 [SC] [expires: 2028-05-22]
      7CA48F68FB98A8F0C1857D0614672610C5AEF029
uid           [ unknown] Karo Saharinen <karo.saharinen@jamk.fi>
sub   rsa4096 2018-03-16 [E] [expires: 2028-05-22]

sahka@sahka-virtualbox:~$ gpg --list-secret-keys
/home/sahka/.gnupg/pubring.kbx
------------------------------
sec   rsa3072 2023-10-12 [SC] [expires: 2025-10-11]
      A0ABA5BE7187F70224338470DC657F1356DDD0CF
uid           [ultimate] Edgar Example <edgar@example.com>
ssb   rsa3072 2023-10-12 [E] [expires: 2025-10-11]

sahka@sahka-virtualbox:~$ 

Encrypting files to another person

Create a file that you would like to encrypt for Karo. vim is a text editor used to write down the contents of the text file. more prints out the contents of the text file.

sahka@sahka-virtualbox:~$ vim very_sensitive_email_message.txt
sahka@sahka-virtualbox:~$ more very_sensitive_email_message.txt 
This is a very sensitive email message
sahka@sahka-virtualbox:~$

Encrypt the file by using the ID 7CA48F68FB98A8F0C1857D0614672610C5AEF029 (notice! it is the ID of Karo's public key). The prompt gives out a warning on your level of trust towards this key, but this trust is granted by pressing yes at the end.

sahka@sahka-virtualbox:~$ gpg --armor --encrypt -r 7CA48F68FB98A8F0C1857D0614672610C5AEF029 very_sensitive_email_message.txt 
gpg: EEF77C45B874D457: There is no assurance this key belongs to the named user

sub  rsa4096/EEF77C45B874D457 2018-03-16 Karo Saharinen <karo.saharinen@jamk.fi>
 Primary key fingerprint: 7CA4 8F68 FB98 A8F0 C185  7D06 1467 2610 C5AE F029
      Subkey fingerprint: 8F02 8FBE 8FE4 9246 27A9  E18C EEF7 7C45 B874 D457

It is NOT certain that the key belongs to the person named
in the user ID.  If you *really* know what you are doing,
you may answer the next question with yes.

Use this key anyway? (y/N) y
sahka@sahka-virtualbox:~$ 

Check that the file was encrypted. It now has .asc file extension. This is because the file was created using --armor which allows the data to be sent e.g. in the body of an email.

sahka@sahka-virtualbox:~$ more very_sensitive_email_message.txt.asc 
-----BEGIN PGP MESSAGE-----

hQIMA+73fEW4dNRXAQ//Wf7IKqBTOGNU13AeDKY4oSMmaKTnDOo1+o9ipstf3WzV
+hy175izeMNetuAppLMsTXHfvAJmnHXxD2MRUfK/YQbgyxXLY9MC2T4GVfGb5D+J
qtPdWA/rEly9lxM7bwODgq+eXF6s3Q42A+iBBOkSmD3bJ8sj6fei3q1aw1GKUCsi
PuWFQnWe0puDVx8HSNMgj+5xY+S9cvrTKdXi4RC56erYMhFSUOLAR0zd7LjrggF4
vIr5bri0iFvo/XfHU6LY5zJKJJt/8fAirQioZ9TGvpC17GvhwfzkKfcpHmlhzsOJ
1nyZCMYe0KLf9zPTP32KKZxAI2LA9wyBmfEISq52r4G2x+qHQ7ogRfKTnPm9QIhy
G2c+Yvynn7FQHV08GVFL7mRbGO2JCY0DmJNdCbY8MYmwTjOoQoBvGKcsSyzCAFjS
qktWyuk30/YBIrlzSmmDH7QL2xNrXzf76zFu9bzRWJFgffipJC2HAWm62Zeg1wkl
IHcjLhE6BC0COHJL1i20E82VKJeFgEwTkrrLCsJbpsTHFpF2WxXYtjPzabWCSM3i
Q0MzrDIqcDrTbcJ5rkwOXHdgR5kMoMWJTyNFjio5NCRlSBbbbps8668X1BcuedoU
80yJMLii1Bjm5qOVpetyVurytANeS3dzRgqBVO9lOtH3X4dwSm7av52BNcxWPnjS
bgFdoPpcbzmuP2b+39ltDtJ2E/pht+b/xxi3DCzBRqMPP7gC3vYqW45HIekFpV2v
QxKEEz7diPw0H7r0WTY7U+gW9zgeNniRw4ci44s4uOux5nNMHv/rUTThC6wV4Yds
MSAUZ7MSYjqGv46affrD
=Jqfj
-----END PGP MESSAGE-----
sahka@sahka-virtualbox:~$

Use some transfer methods to get the file (e.g. file transfer through USB/email/...) to its recipient.

Decrypting files from another person

Once the file is at computer of the person intended (and they are in posession of their private key), the recipient can decrypt the encrypted file to read the message.

Karo@Saharinen-PC MINGW64 ~/Downloads
$ gpg --decrypt very_sensitive_email_message.txt.asc > very_sensitive_email_message.txt

You need a passphrase to unlock the secret key for
user: "Karo Saharinen <karo.saharinen@jamk.fi>"
4096-bit RSA key, ID B874D457, created 2018-03-16 (main key ID C5AEF029)

gpg: encrypted with 4096-bit RSA key, ID B874D457, created 2018-03-16
      "Karo Saharinen <karo.saharinen@jamk.fi>"

Karo@Saharinen-PC MINGW64 ~/Downloads $ more very_sensitive_email_message.txt
This is a very sensitive email message

Karo@Saharinen-PC MINGW64 ~/Downloads

Signing Files

Notice that while the file was encrypted using the recipients public key, there is no proof that the file came from you specifically. This proof is added by making a cryptographic signature (.sig file) which requires the senders secret key.

sahka@sahka-virtualbox:~$ gpg --armor --output very_sensitive_email_message.sig --detach-sig very_sensitive_email_message.txt.asc
sahka@sahka-virtualbox:~$ ls very*
very_sensitive_email_message.sig  very_sensitive_email_message.txt  very_sensitive_email_message.txt.asc
sahka@sahka-virtualbox:~$

Signing requires you to use your private key which is protected by password. Thus, the computer requires you to insert the password for the public key (which was established when creating the key).

signing

Verifying the Signature of Files

The signature can be verified by the recipient (they need your public key for this). It is common to somehow either publish the public key or send the public key as an attachment to your collaborator.

Karo@Saharinen-PC MINGW64 ~/Downloads $ gpg --verify very_sensitive_email_message.sig very_sensitive_email_message.txt
gpg: Signature made Thu, Oct 12, 2023  3:36:33 PM FLEDT using RSA key ID 56DDD0CF
gpg: Good signature from "Edgar Example <edgar@example.com>"
gpg: WARNING: This key is not certified with a trusted signature!
gpg:          There is no indication that the signature belongs to the owner.
Primary key fingerprint: A0AB A5BE 7187 F702 2433  8470 DC65 7F13 56DD D0CF

Karo@Saharinen-PC MINGW64 ~/Downloads