xaizek / rocketgit (License: AGPLv3+) (since 2018-12-09)
Light and fast Git hosting solution suitable to serve both as a hub or as a personal code storage with its tickets, pull requests, API and much more.
Commit d931fe7c4170643e46404c32659f4dce031d4cb4

Mostly merge request display fixes; log delete
Author: Catalin(ux) M. BOIE
Author date (UTC): 2015-04-08 18:39
Committer name: Catalin(ux) M. BOIE
Committer date (UTC): 2015-04-08 18:39
Parent(s): 2d64b6d16a45ced4f751b6b64972cb0c3cf7d21c
Signing key:
Tree: 14a7dd9b206284b85acf77d14acc4985bc7ba868
File Lines added Lines deleted
TODO 16 16
duilder.conf 1 1
inc/admin.inc.php 35 0
inc/git.inc.php 65 1
inc/init.inc.php 3 0
inc/user.inc.php 1 0
inc/user/repo-page.php 10 31
inc/user/repo/bug/show/show.php 5 5
inc/util.inc.php 0 7
root/themes/default/repo/log/line.html 1 1
root/themes/default/repo/mr/list/header.html 0 1
root/themes/default/repo/mr/list/line.html 1 2
root/themes/default/repo/mr/page.html 4 3
samples/config.php 3 0
samples/cron 3 1
scripts/cron.php 11 0
scripts/cron.sh 1 1
scripts/q.sh 4 0
File TODO changed (mode: 100644) (index a9d0a84..f976f0b)
1 1 == Where I stopped last time == == Where I stopped last time ==
2 [ ] In merge request page, must be presents also the patch, exactly like
3 on 'Log' page.
4 [ ] Detaliile despre merge request nu contin 'refs', cu toate ca apar in tabelul
5 din pagina precedenta.
6 [ ] Test push for the virtual machine and release it.
7 Push by ssh is working.
8 git not: Please make sure you have the correct access rights
9 and the repository exists.
10 It is working also for git; it is transformed into a merge request.
11 [ ] I am able to disable pull requests? Anon yes, but the other ones?
12 [ ] Seems the session expires even if I make some activity. Unit test?
2 [ ] Add "Spread the word!" on website.
3
4 [ ] I am able to disable merge/pull requests? Anon yes, but the other ones?
13 5 [ ] Check 'description_nice' and apply this everywhere. Maybe we should unset [ ] Check 'description_nice' and apply this everywhere. Maybe we should unset
14 6 'description', so people will not be tempted to use it. 'description', so people will not be tempted to use it.
15 7 Maybe just overwrite 'description'. Maybe just overwrite 'description'.
 
21 13 proiectului, e nevoie. Dar intr-un form, in textarea, nu e nevoie. proiectului, e nevoie. Dar intr-un form, in textarea, nu e nevoie.
22 14 Apoi as putea elimina description_nice. Apoi as putea elimina description_nice.
23 15 [ ] Security: Link-uri + xss (Ionut) [ ] Security: Link-uri + xss (Ionut)
24 [ ] Use a cache var to signal all daemons that we are ready to go.
25 Or better, a file in /var/lib/rocketgit?
26 16 [ ] We need to be able to delete old log files! We cannot release the vm [ ] We need to be able to delete old log files! We cannot release the vm
27 17 without this! without this!
18 Done, check if any SELinux AVC shows up.
28 19 [ ] Upload kvm image to downloads.rocketgit.com. Sign it? sha256 it? [ ] Upload kvm image to downloads.rocketgit.com. Sign it? sha256 it?
29 20 [ ] Security: validate sparas! [ ] Security: validate sparas!
30 [ ] Add "Spread the word!" on website.
31 21 [ ] Menus - change color for selected items, not the background color. [ ] Menus - change color for selected items, not the background color.
32 [ ] Merge requests are not ok - still using files.
33 22 [ ] Daca creez repo, nu-mi creaza dir-ul (de fapt, nu marcheaza in cache ca l-a [ ] Daca creez repo, nu-mi creaza dir-ul (de fapt, nu marcheaza in cache ca l-a
34 23 creat din cauza event-ului care nu poate sa se conecteze la cache: creat din cauza event-ului care nu poate sa se conecteze la cache:
35 24 broken pipe. Foarte ciudat. De ce nu ar putea trimite? broken pipe. Foarte ciudat. De ce nu ar putea trimite?
 
37 26 [ ] Seems that 'token_key' is not created at boot time! Bad! [ ] Seems that 'token_key' is not created at boot time! Bad!
38 27 [ ] I can do a select before write to be sure socket is open. [ ] I can do a select before write to be sure socket is open.
39 28 If I get a error signal from select, reopen the socket. If I get a error signal from select, reopen the socket.
40 [ ] Implement 'clone' because is easy. The mrs will be a little bit harder.
41 29 [ ] SPF? mail-ul ajunge in spam! [ ] SPF? mail-ul ajunge in spam!
30 [ ] Release virtual machine.
42 31 [ ] [ ]
43 32
44 33 == BEFORE NEXT RELEASE == == BEFORE NEXT RELEASE ==
34 [ ] Merge requests are not ok - still using files.
35 But, we also insert entries in database!
36 [ ] Need to add comments for merge request. Find a way to propagate them in the
37 git repo?
38 [ ] Implement 'clone' because is easy. The mrs will be a little bit harder.
39 [ ] Because I show the merge re request id, somebody can change the commits.
40 Somehow, it should be locked?
41 [ ] Maybe we should not allow bug creation as anonymous?
42 How do the anonymous person will edit it? A cookie?
43 [ ] When a user push something, give them some statistics after.
44 [ ] When a push failes with a non-fastforward error, show who "broke" the flow.
45 45 [ ] We should clean anon namespaces if they fail? name them 'something.tmp' [ ] We should clean anon namespaces if they fail? name them 'something.tmp'
46 46 till after succesfully run receive-pack. Or just compare with till after succesfully run receive-pack. Or just compare with
47 47 the db? the db?
File duilder.conf changed (mode: 100644) (index d7feed3..60cd188)
1 1 PRJ="rocketgit" PRJ="rocketgit"
2 VER="0.24"
2 VER="0.25"
3 3 REV="1" REV="1"
4 4 EXCLUDE=".exclude" EXCLUDE=".exclude"
5 5 EXPORT_PATH="/data/www/umbrella/kernel/us/rocketgit" EXPORT_PATH="/data/www/umbrella/kernel/us/rocketgit"
File inc/admin.inc.php changed (mode: 100644) (index 160cb41..a398336)
... ... function rg_admin_report1($db, $rg)
314 314 rg_mail_template("mail/admin/report1", $rg); rg_mail_template("mail/admin/report1", $rg);
315 315 } }
316 316
317 /*
318 * Function to clean the log files
319 * It is called by both crons (under apache and under rocketgit users)
320 */
321 function rg_clean_logs($dir)
322 {
323 global $rg_logs_lifetime;
324
325 if ($rg_logs_lifetime == 0)
326 return;
327
328 $files = glob($dir . "/*.log");
329 if ($files === FALSE) {
330 rg_log("Cannot select logs for delete");
331 return FALSE;
332 }
333
334 $limit_ts = gmmktime(0, 0, 0, gmdate('m'), gmdate('d') - $rg_logs_lifetime);
335 $limit = gmdate("Ymd", $limit_ts);
336 rg_log("limit_ts=$limit_ts limit=$limit");
337
338 foreach ($files as $file) {
339 $ymd = preg_replace('/.*-([0-9]*)\.log/', '$1', $file);
340 rg_log("file=$file ymd=$ymd");
341
342 if ($ymd >= $limit)
343 continue;
344
345 rg_log("Deleting file $file");
346 $r = unlink($file);
347 if ($r === FALSE)
348 rg_log("Cannot delete file $file!");
349 }
350 }
351
317 352 ?> ?>
File inc/git.inc.php changed (mode: 100644) (index ef629ff..f524c9d)
... ... function rg_git_log($path, $max, $from, $to, $also_patch)
709 709 foreach ($blocks as $junk => $block) { foreach ($blocks as $junk => $block) {
710 710 $y = array("vars" => array(), "files" => array()); $y = array("vars" => array(), "files" => array());
711 711
712 // some defaults
713 $y['vars']['commit_url'] = "";
714
712 715 // split block in two: vars and patches // split block in two: vars and patches
713 716 $parts = explode("\0ROCKETGIT_END_OF_VARS\0", $block, 2); $parts = explode("\0ROCKETGIT_END_OF_VARS\0", $block, 2);
714 717
 
... ... function rg_git_diff($a, $template_file)
886 889 $ret .= "<br />\n"; $ret .= "<br />\n";
887 890
888 891 $f = rg_xss_safe($finfo['file']); $f = rg_xss_safe($finfo['file']);
889 $ret .= "<a name=\"$f\">\n";
892 $ret .= "<a name=\"$f\"></a>\n";
890 893
891 894 $ret .= "<table class=\"chunk\" width=\"100%\">\n"; $ret .= "<table class=\"chunk\" width=\"100%\">\n";
892 895 $ret .= "<tr style=\"border: 1px; background: #dddddd\"><td colspan=\"4\">"; $ret .= "<tr style=\"border: 1px; background: #dddddd\"><td colspan=\"4\">";
 
... ... function rg_git_content_by_file($treeish, $file)
1414 1417 return $ret; return $ret;
1415 1418 } }
1416 1419
1420 /*
1421 * High level function that shows commits between two points
1422 * Input is the array returned by rg_git_log()
1423 * @commit_table - TRUE if you want commit table to show (FALSE for log/commit
1424 */
1425 function rg_git_log2listing($log, $rg, $commit_table)
1426 {
1427 if ($log === FALSE)
1428 return rg_template('repo/not_init.html', $rg);
1429
1430 $ret = '';
1431
1432 if ($commit_table) {
1433 // Show a short list of commits
1434 // Set 'url'
1435 foreach ($log as $index => $i)
1436 $log[$index]['vars']['commit_url'] =
1437 rg_xss_safe($rg['mr'])
1438 . "#" . rg_xss_safe($i['vars']['sha1_short']);
1439 $ret .= rg_git_log_template($log, 'repo/log', $rg);
1440 }
1441
1442 // TODO: move this into a template!
1443 foreach ($log as $junk => $i) {
1444 // Some info about commit
1445 $ret .= "<br /><b>"
1446 . "<a name=\"" . rg_xss_safe($i['vars']['sha1_short']) . "\">"
1447 . "Commit " . rg_xss_safe($i['vars']['sha1_short'])
1448 . "</a></b> - " . rg_xss_safe($i['vars']['subject']) . "\n";
1449
1450 if (!empty($i['vars']['body']))
1451 $ret .= "<br />\n"
1452 . nl2br(rg_xss_safe($i['vars']['body']));
1453
1454 $ret .= "<br />\n"
1455 . "<b>Author</b>: " . rg_xss_safe($i['vars']['author name']);
1456
1457 if (!empty($i['vars']['commiter name']))
1458 $ret .= "<br />\n"
1459 . "<b>Commiter</b>: " . rg_xss_safe($i['vars']['commiter name']);
1460
1461 $ret .= "<br />\n"
1462 . "<b>Date (UTC)</b>: " . gmdate("Y-m-d H:i", $i['vars']['author date']);
1463 $ret .= "<br />\n";
1464
1465 // stats
1466 $r = rg_git_files_stats($i['files'], 'repo/fstat');
1467 if ($r === FALSE)
1468 return "Internal error";
1469 $ret .= $r;
1470
1471 // diff
1472 $r = rg_git_diff($i['files'], 'repo/diff.html');
1473 if ($r === FALSE)
1474 return "Internal error";
1475 $ret .= $r;
1476 }
1477
1478 return $ret;
1479 }
1480
1417 1481 ?> ?>
File inc/init.inc.php changed (mode: 100644) (index 04649fb..4592ecb)
... ... if (!isset($rg_scripts))
28 28 if (!isset($rg_theme_dir)) if (!isset($rg_theme_dir))
29 29 $rg_theme_dir = $rg_scripts . "/root/themes"; $rg_theme_dir = $rg_scripts . "/root/themes";
30 30
31 if (!isset($rg_logs_lifitime))
32 $rg_logs_lifetime = 31;
33
31 34 ?> ?>
File inc/user.inc.php changed (mode: 100644) (index 82da6bd..2a05360)
... ... function rg_user_login_by_sid($db, &$rg)
697 697 $rg['login_ui']['is_admin'] = 0; $rg['login_ui']['is_admin'] = 0;
698 698 $rg['login_ui']['rights'] = ""; $rg['login_ui']['rights'] = "";
699 699 $rg['login_ui']['username'] = ""; $rg['login_ui']['username'] = "";
700 $rg['login_ui']['organization'] = 0;
700 701
701 702 $ret = FALSE; $ret = FALSE;
702 703 while (1) { while (1) {
File inc/user/repo-page.php changed (mode: 100644) (index 0ad1436..489ae5b)
... ... if (strcmp($_subop, "history") == 0) {
169 169 $second = $commit; $second = $commit;
170 170 } }
171 171
172 $_repo_body .= "<br /><b>Commit " . rg_xss_safe($commit) . "</b><br />\n";
173
174 172 $log = rg_git_log($repo_path, 1, $first, $second, TRUE); $log = rg_git_log($repo_path, 1, $first, $second, TRUE);
175 if ($log === FALSE) {
176 $_repo_body .= rg_template("repo/not_init.html", $rg);
177 } else {
178 // stats
179 //rg_log("DEBUG: log[0]['files']: " . rg_array2string($log[0]['files']));
180 $_r = rg_git_files_stats($log[0]['files'], "repo/fstat");
181 //rg_log("DEBUG: files_stats: " . $_r);
182 if ($_r === FALSE)
183 rg_internal_error("Could not generate file stats"
184 . " (" . rg_git_error() . ")!");
185 else
186 $_repo_body .= $_r;
187
188 // diff
189 rg_log("DEBUG: log[0]['files']: " . rg_array2string($log[0]['files']));
190 $_r = rg_git_diff($log[0]['files'], "repo/diff.html");
191 //rg_log("DEBUG: git_diff: " . $_r);
192 if ($_r === FALSE)
193 rg_internal_error("Could not generate patches"
194 . " (" . rg_git_error() . ").");
195 else
196 $_repo_body .= $_r;
197 }
173 $_repo_body .= rg_git_log2listing($log, $rg, FALSE);
198 174 } }
199 175 } }
200 176 } else if (strcmp($_subop, "bug") == 0) { } else if (strcmp($_subop, "bug") == 0) {
 
... ... if (strcmp($_subop, "history") == 0) {
208 184 } else if (strcmp($_subop, "mr") == 0) { } else if (strcmp($_subop, "mr") == 0) {
209 185 if ($rg['ri']['git_dir_done'] == 0) { if ($rg['ri']['git_dir_done'] == 0) {
210 186 $_repo_body .= rg_template("repo/no_git_dir.html", $rg); $_repo_body .= rg_template("repo/no_git_dir.html", $rg);
211 } else if (empty($paras)) {
187 } else {
212 188 $_repo_body .= rg_template("repo/mrs.html", $rg); $_repo_body .= rg_template("repo/mrs.html", $rg);
213 189
214 190 $r = rg_mr_load($db, $rg['ri']['repo_id'], 20); $r = rg_mr_load($db, $rg['ri']['repo_id'], 20);
 
... ... if (strcmp($_subop, "history") == 0) {
218 194 } else { } else {
219 195 $_repo_body .= rg_template_table("repo/mr/list", $r, $rg); $_repo_body .= rg_template_table("repo/mr/list", $r, $rg);
220 196 } }
221 } else {
222 $mr = preg_replace('/[^0-9a-zA-Z_]/', '', array_shift($paras));
197
223 198 while (1) { while (1) {
199 if (empty($paras))
200 break;
201
202 $mr = preg_replace('/[^0-9a-zA-Z_]/', '', array_shift($paras));
203 $rg['mr'] = $mr;
224 204 $mri = rg_mr_load_one($db, $rg['ri']['repo_id'], $mr); $mri = rg_mr_load_one($db, $rg['ri']['repo_id'], $mr);
225 205 if ($mri === FALSE) { if ($mri === FALSE) {
226 206 $_repo_body .= "Error getting merge request (" . rg_mr_error() . ")."; $_repo_body .= "Error getting merge request (" . rg_mr_error() . ").";
 
... ... if (strcmp($_subop, "history") == 0) {
234 214 break; break;
235 215 } }
236 216
237 $mri['HTML:diff'] = rg_git_log_template($_log,
238 "repo/log", $rg);
239 $_repo_body .= rg_template("repo/mr/page.html", $mri, $rg);
217 $mri['HTML:diff'] = rg_git_log2listing($_log, $rg, TRUE);
218 $_repo_body .= rg_template("repo/mr/page.html", $mri);
240 219
241 220 break; break;
242 221 } }
File inc/user/repo/bug/show/show.php changed (mode: 100644) (index 01339c2..f04bfef)
... ... while (1) {
148 148
149 149 if (rg_rights_allow($db, $rg['ri']['repo_id'], "repo", $rg['ri']['uid'], if (rg_rights_allow($db, $rg['ri']['repo_id'], "repo", $rg['ri']['uid'],
150 150 $rg['login_ui']['uid'], "d", $rg['ip'], "") !== TRUE) { $rg['login_ui']['uid'], "d", $rg['ip'], "") !== TRUE) {
151 rg_template("repo/bug/deny_delete.html", $rg);
151 $delete_error = rg_template("repo/bug/deny_delete.html", $rg);
152 152 break; break;
153 153 } }
154 154
155 155 if (!rg_valid_referer()) { if (!rg_valid_referer()) {
156 $delete_error = "Invalid referer; try again";
156 $delete_error = rg_warning("Invalid referer; try again", $rg);
157 157 break; break;
158 158 } }
159 159
160 160 if (!rg_token_valid($db, $rg, FALSE)) { if (!rg_token_valid($db, $rg, FALSE)) {
161 $delete_error = "Invalid token; try again.";
161 $delete_error = rg_warning("Invalid token; try again.", $rg);
162 162 break; break;
163 163 } }
164 164
165 165 $ret = rg_bug_delete_undelete($db, $rg['login_ui']['uid'], $ret = rg_bug_delete_undelete($db, $rg['login_ui']['uid'],
166 166 $rg['ri']['repo_id'], $ibug['bug_id'], $del_undel); $rg['ri']['repo_id'], $ibug['bug_id'], $del_undel);
167 167 if ($ret === FALSE) { if ($ret === FALSE) {
168 $delete_error = rg_bug_error();
168 $delete_error = rg_warning(rg_bug_error(), $rg);
169 169 break; break;
170 170 } }
171 171 break; break;
172 172 } }
173 $rg['HTML:button_error'] = rg_warning($delete_error, $rg);
173 $rg['HTML:button_error'] = $delete_error;
174 174
175 175
176 176 // We must look it up again because it can be edited above; no prob, is in cache // We must look it up again because it can be edited above; no prob, is in cache
File inc/util.inc.php changed (mode: 100644) (index 56a9b5e..8e772dd)
... ... function rg_re_userpage($ui)
185 185
186 186 function rg_re_repopage($ui, $repo_name) function rg_re_repopage($ui, $repo_name)
187 187 { {
188 if (!isset($ui['organization'])) {
189 rg_internal_error("rg_re_repopage called with wrong ui"
190 . " (no 'organization' field): " . rg_array2string($ui));
191 rg_log("ui: " . print_r($ui, TRUE));
192 exit(1);
193 }
194
195 188 $s = rg_re_userpage($ui) . "/" . rawurlencode($repo_name); $s = rg_re_userpage($ui) . "/" . rawurlencode($repo_name);
196 189
197 190 return rg_re_url($s); return rg_re_url($s);
File root/themes/default/repo/log/line.html changed (mode: 100644) (index 30d7b57..4cd08d1)
1 1 <tr> <tr>
2 2 <td>@@subject@@</td> <td>@@subject@@</td>
3 <td><a href="@@url_repo@@/source/log/commit/@@sha1_short@@">@@sha1_short@@</a></td>
3 <td><a href="@@if("@@commit_url@@" != ""){{@@commit_url@@}}{{@@url_repo@@/source/log/commit/@@sha1_short@@}}">@@sha1_short@@</a></td>
4 4 <td>@@author name@@ (@@author email@@)</td> <td>@@author name@@ (@@author email@@)</td>
5 5 <td>@@author date UTC@@</td> <td>@@author date UTC@@</td>
6 6 </tr> </tr>
File root/themes/default/repo/mr/list/header.html changed (mode: 100644) (index 29449db..0b689e6)
4 4 <th>Date / time</th> <th>Date / time</th>
5 5 <th>Ref</th> <th>Ref</th>
6 6 @@if(@@can_admin@@ == 1){{<th>IP</th>}}{{}} @@if(@@can_admin@@ == 1){{<th>IP</th>}}{{}}
7 <th>Go to</th>
8 7 </tr> </tr>
9 8
File root/themes/default/repo/mr/list/line.html changed (mode: 100644) (index 669e4f1..b649404)
1 1 <tr> <tr>
2 <td>@@namespace@@</td>
2 <td><a href="@@url_repo@@/mr/@@namespace@@">@@namespace@@</a></td>
3 3 <td>@@date_utc@@</td> <td>@@date_utc@@</td>
4 4 <td>@@refname@@</td> <td>@@refname@@</td>
5 5 @@if(@@can_admin@@ == 1){{<td>@@ip@@</td>}}{{}} @@if(@@can_admin@@ == 1){{<td>@@ip@@</td>}}{{}}
6 <td><a href="@@url_repo@@/mr/@@namespace@@">Details</a></td>
7 6 </tr> </tr>
File root/themes/default/repo/mr/page.html changed (mode: 100644) (index cc13c69..d704360)
1 1 <br /> <br />
2 Merge request @@namespace@@ (@@old_rev_short@@ -> @@new_rev_short@@)<br />
3 Date: @@date_utc@@<br />
4 IP: @@ip@@<br />
2 <b>Merge request @@namespace@@</b> (@@old_rev_short@@ -> @@new_rev_short@@)<br />
3 <b>Ref</b>: @@refname@@<br />
4 <b>Date</b>: @@date_utc@@<br />
5 @@if(@@can_admin@@ == 1){{<b>IP</b>: @@ip@@<br />}}{{}}
5 6
6 7 @@diff@@ @@diff@@
File samples/config.php changed (mode: 100644) (index 49155f6..ab7d4ba)
... ... $rg_git_port = 9418;
84 84 // Allow events to be registered, even if user press "stop" // Allow events to be registered, even if user press "stop"
85 85 ignore_user_abort(TRUE); ignore_user_abort(TRUE);
86 86
87 // How many days to keep the log files? Put 0 to not delete it.
88 $rg_logs_lifetime = 31;
89
87 90 ?> ?>
File samples/cron changed (mode: 100644) (index cca23b9..2220987)
1 * * * * * rocketgit /usr/share/rocketgit/scripts/cron.sh
1 * * * * * apache /usr/share/rocketgit/scripts/cron.sh apache
2
3 * * * * * rocketgit /usr/share/rocketgit/scripts/cron.sh rocketgit
2 4 * * * * * rocketgit /usr/share/rocketgit/scripts/events.sh * * * * * rocketgit /usr/share/rocketgit/scripts/events.sh
3 5 * * * * * rocketgit /usr/share/rocketgit/scripts/cache.sh * * * * * rocketgit /usr/share/rocketgit/scripts/cache.sh
File scripts/cron.php changed (mode: 100644) (index 783b378..31f2b68)
... ... require_once($INC . "/mr.inc.php");
19 19 require_once($INC . "/admin.inc.php"); require_once($INC . "/admin.inc.php");
20 20 require_once($INC . "/ver.php"); require_once($INC . "/ver.php");
21 21
22 $user = isset($_SERVER['argv'][1]) ? $_SERVER['argv'][1] : "rocketgit";
23
24 if (strcmp($user, "apache") == 0) {
25 rg_log_set_file($rg_web_log_dir . "/cron.log");
26 rg_log_set_sid("000000"); // to spread the logs
27
28 rg_clean_logs('/var/log/rocketgit-web');
29
30 exit(0);
31 }
32
22 33 rg_log_set_file($rg_log_dir . "/cron.log"); rg_log_set_file($rg_log_dir . "/cron.log");
23 34 rg_log_set_sid("000000"); // to spread the logs rg_log_set_sid("000000"); // to spread the logs
24 35
File scripts/cron.sh changed (mode: 100755) (index 5f8c29b..b233cb5)
4 4
5 5 check_context check_context
6 6
7 exec php /usr/share/rocketgit/scripts/cron.php
7 exec php /usr/share/rocketgit/scripts/cron.php "${@}"
File scripts/q.sh added (mode: 100755) (index 0000000..380fa2f)
1 #!/bin/bash
2
3 # Nothing to do here.
4 # It is still present so old instalations to not get error messages from cron
Hints

Before first commit, do not forget to setup your git environment:
git config --global user.name "your_name_here"
git config --global user.email "your@email_here"

Clone this repository using HTTP(S):
git clone https://code.reversed.top/user/xaizek/rocketgit

Clone this repository using ssh (do not forget to upload a key first):
git clone ssh://rocketgit@code.reversed.top/user/xaizek/rocketgit

You are allowed to anonymously push to this repository.
This means that your pushed commits will automatically be transformed into a pull request:
... clone the repository ...
... make some changes and some commits ...
git push origin master