--Chaquez du contenu textuel au fil du temps pour voir s'il a été mis à jour par rapport à la dernière fois.
GitLab Docs > API Docs > API resources
Ubuntu 20.04
$ python3 --version
Python 3.8.2
Maintenant, commençons. Utilisez le GitLab sur site comme serveur git. Cette fois, nous l'introduirons rapidement localement avec Docker. Après avoir déplacé vers un répertoire approprié sur le terminal, exécutez ce qui suit.
git clone https://github.com/sameersbn/docker-gitlab
cd docker-gitlab
docker-compose up -d
Quand j'ai attendu un moment après avoir lancé le conteneur et exécuté "docker-compose ps", ce qui suit était affiché.
Name Command State Ports
----------------------------------------------------------------------------------------------------------------------------------
docker-gitlab_gitlab_1 /sbin/entrypoint.sh app:start Up (healthy) 0.0.0.0:10022->22/tcp, 443/tcp, 0.0.0.0:10080->80/tcp
docker-gitlab_postgresql_1 /sbin/entrypoint.sh Up 5432/tcp
docker-gitlab_redis_1 docker-entrypoint.sh --log ... Up 6379/tcp
Le port http du conteneur GitLab est 10080, accédez donc à http: // localhost: 10080 / avec votre navigateur. Lorsque l'écran ci-dessous apparaît, modifiez le mot de passe root.
Allez à l'écran ci-dessous et créez un utilisateur de développement (le nom d'utilisateur peut être n'importe quoi).
Après vous être connecté en tant qu'utilisateur de développement, sélectionnez Créer un projet dans l'écran ci-dessous.
Le nom du projet est "ethercalc_backup" comme indiqué ci-dessous, mais le nom peut être n'importe quoi. Appuyez sur le bouton Créer un projet pour créer un projet.
Le projet a été créé comme suit. L'ID de projet est affiché sous le nom du projet (3 dans cet article). Vous utiliserez cet ID plus tard dans votre code Python.
Vous utiliserez plus tard l'API GitLab à partir de votre code Python. À ce moment-là, vous aurez besoin d'un jeton d'accès, alors obtenez-le. Comme indiqué ci-dessous, affichez le menu déroulant en haut à droite du navigateur et sélectionnez "Paramètres".
Sur l'écran ci-dessous, sélectionnez «Jetons d'accès» dans le menu de gauche.
Sur l'écran ci-dessous, entrez un nom arbitraire dans Nom, Scopes vérifiera l'API, et appuyez sur le bouton "Créer un jeton d'accès personnel".
Le jeton d'accès a été créé comme suit. Copiez-le dans le presse-papiers et enregistrez-le. Dans cet article, nous utiliserons "6f8YXyrZ1SCSADHTJ2L9" comme jeton d'accès.
En tant que fournisseur de contenu textuel, nous utiliserons EtherCalc pour cet article. Comme avec GitLab, déployez-le localement avec Docker. Après avoir déplacé vers un répertoire approprié différent de GitLab sur le terminal, créez docker-compose.yml avec le même contenu que https://github.com/audreyt/ethercalc/blob/master/docker-compose.yml et créez un conteneur. Commencez.
wget https://raw.githubusercontent.com/audreyt/ethercalc/master/docker-compose.yml
docker-compose up -d
Quand j'ai attendu un moment après avoir lancé le conteneur et exécuté "docker-compose ps", ce qui suit était affiché.
Name Command State Ports
--------------------------------------------------------------------------------------------
docker-ethercalc_ethercalc_1 sh -c REDIS_HOST=$REDIS_PO ... Up 0.0.0.0:80->8000/tcp
docker-ethercalc_redis_1 docker-entrypoint.sh redis ... Up 6379/tcp
Comme le port http du conteneur EtherCalc est 80, essayez d'accéder à http: // localhost / avec un navigateur.
Faites deux feuilles EtherCalc pour les tests. Lancez un éditeur de texte, créez de nouveaux foo.sc et bar.sc et enregistrez.
editor foo.sc
foo.sc
socialcalc:version:1.0
MIME-Version: 1.0
Content-Type: multipart/mixed; boundary=SocialCalcSpreadsheetControlSave
--SocialCalcSpreadsheetControlSave
Content-type: text/plain; charset=UTF-8
# SocialCalc Spreadsheet Control Save
version:1.0
part:sheet
part:edit
part:audit
--SocialCalcSpreadsheetControlSave
Content-type: text/plain; charset=UTF-8
version:1.5
cell:A1:t:foo1
cell:A2:t:foo2
sheet:c:1:r:2:tvf:1
valueformat:1:text-wiki
--SocialCalcSpreadsheetControlSave
Content-type: text/plain; charset=UTF-8
version:1.0
rowpane:0:1:1
colpane:0:1:1
ecell:A1
--SocialCalcSpreadsheetControlSave
Content-type: text/plain; charset=UTF-8
--SocialCalcSpreadsheetControlSave--
editor bar.sc
bar.sc
socialcalc:version:1.0
MIME-Version: 1.0
Content-Type: multipart/mixed; boundary=SocialCalcSpreadsheetControlSave
--SocialCalcSpreadsheetControlSave
Content-type: text/plain; charset=UTF-8
# SocialCalc Spreadsheet Control Save
version:1.0
part:sheet
part:edit
part:audit
--SocialCalcSpreadsheetControlSave
Content-type: text/plain; charset=UTF-8
version:1.5
cell:A1:t:bar1
cell:A2:t:bar2
sheet:c:1:r:2:tvf:1
valueformat:1:text-wiki
--SocialCalcSpreadsheetControlSave
Content-type: text/plain; charset=UTF-8
version:1.0
rowpane:0:1:1
colpane:0:1:1
ecell:A1
--SocialCalcSpreadsheetControlSave
Content-type: text/plain; charset=UTF-8
--SocialCalcSpreadsheetControlSave--
Les fichiers foo.sc et bar.sc ci-dessus sont des fichiers texte au format SocialCalc qui peuvent être importés dans EtherCalc. L'exportation / importation au format SocialCalc présente l'avantage que le format de feuille (apparence) peut également être récupéré. Vous pouvez également importer des fichiers au format CSV, mais vous ne pouvez pas récupérer le format de feuille.
Procédez comme suit pour importer.
curl -X PUT -H 'Content-Type: text/x-socialcalc' --data-binary @foo.sc http://localhost/_/foo
curl -X PUT -H 'Content-Type: text/x-socialcalc' --data-binary @bar.sc http://localhost/_/bar
Accédez à http: // localhost / foo et http: // localhost / bar dans votre navigateur. Si la cellule de la feuille contient les données suivantes, l'importation est réussie.
Nous téléchargerons les fichiers aux formats SocialCalc et CSV à partir de ces URL et les gérerons dans GitLab.
Veuillez me pardonner pour le code étant divers et mal comporté.
La procédure de traitement logique est la suivante. Pour chacun des contenus de foo et bar
--Téléchargez des fichiers depuis EtherCalc et GitLab (formats SocialCalc et csv) --Si le fichier n'existe pas dans GitLab, ajoutez-en un nouveau au référentiel git.
Voici le code Python. Le code utilise une variable appelée logger, mais veuillez noter que le code autour de la journalisation a été omis.
ethercalc_backup.py
import time
import datetime
import urllib.request
import urllib.parse
import json
import pprint
import re
import base64
#URL du contenu ethercalc géré par git
ethercalc_uris = [ "http://localhost/foo", "http://localhost/bar" ]
#Liés à GitLab
gitlab_base_uri = "http://localhost:10080/"
#Destination de sauvegarde dans le référentiel git
gitlab_backup_directory = "ethercalc"
gitlab_private_token = "6f8YXyrZ1SCSADHTJ2L9"
gitlab_project_id = 3
#maintenant
str_now = datetime.datetime.today().strftime("%Y%m%d_%H%M%S")
#nouvelle ligne
LF = '\n'
def get_gitlab_file(private_token, file_path):
"""
Obtenez 1 fichier du référentiel GitLab
Parameters
----------
private_token : str
Jeton d'accès pour l'API GitLab
file_path : str
Chemin du fichier depuis le haut du référentiel git
Returns
-------
anonymous : json
Réponse de GitLab
"""
# https://docs.gitlab.com/ee/api/repository_files.html
gitlab_uri = f"{gitlab_base_uri}api/v4/projects/{gitlab_project_id}/repository/files/{urllib.parse.quote(file_path, safe='')}?ref=master"
logger.info(f"gitlab_uri={gitlab_uri}")
headers = {
"PRIVATE-TOKEN": private_token
}
request = urllib.request.Request(gitlab_uri, headers=headers)
try:
with urllib.request.urlopen(request) as res:
res_files = json.loads(res.read())
except urllib.error.HTTPError as ee:
if ee.code == 404:
return {}
else:
raise
except:
raise
else:
# logger.debug(f"gitlab res_commit={LF}{pprint.pformat(res_files)}")
return res_files
def compare_ethercalc_and_gitlab(actions, ethercalc_uri, git_filename):
"""
Obtenez des fichiers à partir des référentiels EtherCalc et GitLab, comparez et ajoutez des actions à la variable d'actions s'il y a des différences
Parameters
----------
actions : list
Variable Actions transmise plus tard à l'API commits de GitLab
ethercalc_uri : str
URI EtherCalc
git_filename : str
Nom de fichier dans le référentiel git
Returns
-------
Aucun
"""
logger.info(f"ethercalc URL={ethercalc_uri}")
#Télécharger depuis EtherCalc
request = urllib.request.Request(ethercalc_uri)
with urllib.request.urlopen(request) as res:
content_ethercalc = res.read().decode("utf-8")
# logger.debug(f"content_ethercalc={LF}{content_ethercalc}")
#Télécharger depuis GitLab
action_str = ""
file_path = f"{gitlab_backup_directory}/{git_filename}"
res_gitlab_file = get_gitlab_file(gitlab_private_token, file_path)
try:
content_gitlab = base64.b64decode(res_gitlab_file["content"]).decode("utf-8")
except KeyError:
#S'il n'y a pas de fichier dans GitLab, créez-en un nouveau plus tard et git commit & push
action_str = "create"
except:
raise
else:
# logger.debug(f"content_gitlab={LF}{content_gitlab}")
#Comparez les fichiers téléchargés depuis EtherCalc et GitLab
if content_ethercalc == content_gitlab:
logger.info("content_ethercalc == content_gitlab")
else:
logger.info("content_ethercalc != content_gitlab")
#Quand il y a une différence dans le contenu du fichier, git commit et push plus tard
action_str = "update"
#Enregistré dans la variable d'actions lorsque l'action est créée ou mise à jour
if 0 < len(action_str):
action = {
"action": action_str,
"file_path": file_path,
"content": content_ethercalc
}
actions.append(action)
def main():
# ethercalc_Traitez chaque URL d'uris
actions = list()
count_commit = 0
re_compile = re.compile(r".*/(.*?)$")
for index, ethercalc_uri in enumerate(ethercalc_uris):
basename, = re_compile.match(ethercalc_uri).groups() #Chaîne"foo"、"bar"Sortir
socialcalc_uri = ethercalc_uri[::-1].replace(basename[::-1], basename[::-1] + "/_", 1)[::-1]
csv_uri = ethercalc_uri + ".csv"
logger.info(f"[{index}] {basename}")
#Téléchargez depuis EtherCalc et GitLab au format SocialCalc et comparez le contenu des fichiers
time.sleep(0.5) #Dormez correctement pour ne pas être une attaque DoS
compare_ethercalc_and_gitlab(actions, socialcalc_uri, f"{basename}.sc")
#Téléchargez depuis EtherCalc et GitLab au format csv et comparez le contenu des fichiers
time.sleep(0.5) #Dormez correctement pour ne pas être une attaque DoS
compare_ethercalc_and_gitlab(actions, csv_uri, f"{basename}.csv")
if len(actions) == 0:
#Ne git commit s'il n'y a pas de différence dans le contenu des fichiers d'EtherCalc et de GitLab
continue
# git commit & push
# https://docs.gitlab.com/ee/api/commits.html
gitlab_uri = f"{gitlab_base_uri}api/v4/projects/{gitlab_project_id}/repository/commits"
commit_message = datetime.datetime.today().strftime(f"backup {str_now} {basename}")
logger.info(f'git commit -m "{commit_message}"')
headers = {
"method": "POST",
"PRIVATE-TOKEN": gitlab_private_token,
"Content-Type": "application/json"
}
payload = {
"branch": "master",
"commit_message": commit_message,
"actions": actions
}
logger.debug(f"payload={LF}{pprint.pformat(payload)}")
request = urllib.request.Request(gitlab_uri, json.dumps(payload).encode("utf-8"), headers=headers)
with urllib.request.urlopen(request) as res:
res_commit = json.loads(res.read())
logger.debug(f"gitlab res_commit={LF}{pprint.pformat(res_commit)}")
#git diff et sortie dans le journal
# https://docs.gitlab.com/ee/api/commits.html
gitlab_uri = f"{gitlab_base_uri}api/v4/projects/{gitlab_project_id}/repository/commits/{res_commit['id']}/diff"
logger.info(f"git diff ( {res_commit['id']} )")
headers = {
"PRIVATE-TOKEN": gitlab_private_token,
}
request = urllib.request.Request(gitlab_uri, headers=headers)
with urllib.request.urlopen(request) as res:
res_diff = json.loads(res.read())
logger.info(f"gitlab res_diff={LF}{pprint.pformat(res_diff)}")
count_commit += 1
actions = list()
logger.info(f"{count_commit}Git commit")
if __name__ == '__main__':
try:
main()
except Exception as ee:
logger.exception(ee)
La première fois, le référentiel GitLab est vide. Procédez comme suit sur votre terminal:
python3 ethercalc_backup.py
Ce qui suit est affiché à la fin du message d'exécution.
2 commits git
Vérifiez le projet sur l'écran GitLab. Il a 2 Commits comme indiqué ci-dessous, et un nouveau répertoire ethercalc a été créé.
Lorsque je suis passé sous ethercalc, il y avait deux types de commits, foo et bar, comme indiqué ci-dessous, et deux nouveaux fichiers, le format SocialCalc et le format csv, ont été créés pour chaque commit.
Vous pouvez vérifier le contenu en cliquant sur le nom du fichier.
La deuxième fois, je ne changerai que le contenu de foo avec EtherCalc et exécuterai le code Python. J'ai ajouté Hello etc. comme suit.
Procédez comme suit sur votre terminal:
python3 ethercalc_backup.py
Ce qui suit est affiché à la fin du message d'exécution.
1 git commit
Vérifiez le projet sur l'écran GitLab. Il s'agit de 3 Commits comme indiqué ci-dessous.
3 Lorsque je clique sur Commits, j'ai ajouté un récent commit foo comme indiqué ci-dessous, mais rien pour bar.
Lorsque j'ai cliqué sur le commit du toto ajouté, la différence avec le commit précédent était affiché comme indiqué ci-dessous.
La troisième fois, j'essaierai d'exécuter le code Python sans changer EtherCalc.
python3 ethercalc_backup.py
Ce qui suit est affiché à la fin du message d'exécution.
0 git commits
c'est tout.