From b8243e3ee940a9ade4436f29a14b555795442215 Mon Sep 17 00:00:00 2001 From: ngn Date: Thu, 9 May 2024 23:17:18 +0300 Subject: [PATCH] update: add support for redirect --- Makefile | 4 +-- README.md | 1 + locale/tr/LC_MESSAGES/mc.po | 56 +++++++++++++++++++++++---------- src/error.h | 9 ++++++ src/pull.c | 12 +++++++ src/url.c | 62 ++++++++++++++++++++++++++++++++++--- 6 files changed, 122 insertions(+), 22 deletions(-) diff --git a/Makefile b/Makefile index 54d29cc..7a7e5d0 100644 --- a/Makefile +++ b/Makefile @@ -6,7 +6,7 @@ PO_SRCS = $(wildcard locale/*/*/*.po) PO_OUTS = $(patsubst locale/%.po,locale/%.mo,$(PO_SRCS)) PO_DIRS = $(wildcard locale/*/*) -VERSION = 24.01 +VERSION = 24.02 prefix = /usr CC = gcc @@ -14,7 +14,7 @@ all: dist/mc $(PO_OUTS) dist/mc: $(CSRCS) $(HEADERS) mkdir -p dist - $(CC) $(CFLAGS) $(CSRCS) -o $@ -DVERSION=\"${VERSION}\" -linih -lgit2 -lcrypto + $(CC) $(CFLAGS) $(CSRCS) -o $@ -DVERSION=\"${VERSION}\" -linih -lgit2 -lcurl -lcrypto locale/%.mo: locale/%.po msgfmt $^ -o $@ diff --git a/README.md b/README.md index b9390ad..4d289d2 100644 --- a/README.md +++ b/README.md @@ -10,6 +10,7 @@ To compile `mc` and to use it, you will need the following: - make - gettext - libinih +- curl - doas (or sudo) After installing these dependencies, **download the latest diff --git a/locale/tr/LC_MESSAGES/mc.po b/locale/tr/LC_MESSAGES/mc.po index 62148d0..a361b12 100644 --- a/locale/tr/LC_MESSAGES/mc.po +++ b/locale/tr/LC_MESSAGES/mc.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: PACKAGE VERSION\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2024-05-05 20:10+0300\n" +"POT-Creation-Date: 2024-05-09 23:17+0300\n" "PO-Revision-Date: 2024-05-01 13:34+0300\n" "Last-Translator: \n" "Language-Team: Turkish \n" @@ -78,19 +78,19 @@ msgstr "" msgid "Failed to change directory to the specified directory" msgstr "" -#: src/gen.c:29 src/gen.c:36 src/pull.c:83 +#: src/gen.c:29 src/gen.c:36 src/pull.c:95 msgid "Loaded repository configuration" msgstr "" -#: src/gen.c:31 src/pull.c:78 +#: src/gen.c:31 src/pull.c:90 msgid "Failed to load the configuration file (mc.cfg):" msgstr "" -#: src/gen.c:42 src/pull.c:110 +#: src/gen.c:42 src/pull.c:122 msgid "Copying all the targets" msgstr "" -#: src/gen.c:48 src/pull.c:124 +#: src/gen.c:48 src/pull.c:136 msgid "Failed to copy the target:" msgstr "" @@ -173,51 +173,51 @@ msgstr "" msgid "Please specify a config name or a URL" msgstr "" -#: src/pull.c:57 +#: src/pull.c:69 #, c-format msgid "Cloning %s" msgstr "" -#: src/pull.c:62 +#: src/pull.c:74 #, c-format msgid "Failed to clone the %s:" msgstr "" -#: src/pull.c:73 +#: src/pull.c:85 #, c-format msgid "Failed to chdir to %s" msgstr "" -#: src/pull.c:86 +#: src/pull.c:98 msgid "Do you want to continue?" msgstr "" -#: src/pull.c:92 +#: src/pull.c:104 msgid "Checking all the targets" msgstr "" -#: src/pull.c:98 +#: src/pull.c:110 #, c-format msgid "Failed to access the source for the target \"%s\"" msgstr "" -#: src/pull.c:107 +#: src/pull.c:119 msgid "All the target checks were successful" msgstr "" -#: src/pull.c:118 +#: src/pull.c:130 msgid "Install the target?" msgstr "" -#: src/pull.c:119 +#: src/pull.c:131 msgid "Skipping target" msgstr "" -#: src/pull.c:157 +#: src/pull.c:169 msgid "Installing all the requirements" msgstr "" -#: src/pull.c:160 +#: src/pull.c:172 msgid "Failed to run the mp-install command" msgstr "" @@ -253,6 +253,30 @@ msgstr "" msgid "Description" msgstr "" +#: src/url.c:44 +msgid "Failed to init curl" +msgstr "" + +#: src/url.c:55 +msgid "Request failed" +msgstr "" + +#: src/url.c:62 +msgid "Failed to get the response code" +msgstr "" + +#: src/url.c:68 +msgid "Response is not a redirect" +msgstr "" + +#: src/url.c:75 +msgid "Failed to get the location header" +msgstr "" + +#: src/url.c:81 +msgid "Invalid location header" +msgstr "" + #: src/util.c:115 src/util.c:126 #, c-format msgid "Failed to create directory: %s" diff --git a/src/error.h b/src/error.h index ad76102..83bcd62 100644 --- a/src/error.h +++ b/src/error.h @@ -16,6 +16,15 @@ enum ErrorCodes { RunNoRoot = 943, RunCmdNotFound = 942, RunCmdFail = 941, + + UrlCurlFail = 940, + UrlReqFail = 939, + + UrlReqCodeFail = 938, + UrlReqBadCode = 937, + + UrlLocationFail = 936, + UrlLocationBad = 935 }; extern int errno; diff --git a/src/pull.c b/src/pull.c index 3927e2f..283a38e 100644 --- a/src/pull.c +++ b/src/pull.c @@ -44,6 +44,18 @@ bool pull_cmd() { else repo_url = url_ensure_protocol(args.list[1]); + if (NULL == repo_url) { + switch (errno) { + case UrlReqBadCode: + error("Specified configuration is not found"); + break; + default: + error("Failed to access the URL"); + details(errch); + } + goto END; + } + rmrf(mc_tmp_path); repo_root = mc_tmp_path; diff --git a/src/url.c b/src/url.c index d3e0556..69809d9 100644 --- a/src/url.c +++ b/src/url.c @@ -1,4 +1,7 @@ +#include "error.h" +#include "intl.h" #include "util.h" +#include #include #include #include @@ -6,7 +9,7 @@ #include #include -#define HUB_URL "https://matterlinux.xyz/hub/" +#define HUB_URL "https://matterlinux.xyz/hub" bool url_is_name(char *name) { for (char *c = name; *c != '\0'; c++) { @@ -30,10 +33,61 @@ bool url_is_local(char *url) { } char *url_complete(char *name) { - char *url = malloc(strlen(name) + strlen(HUB_URL) + 1); - + char url[strlen(name) + strlen(HUB_URL) + 1]; sprintf(url, "%s/%s", HUB_URL, name); - return url; + + char *location = NULL; + long code = 0; + + CURL *curl = curl_easy_init(); + if (NULL == curl) { + error_set(_("Failed to init curl")); + errno = UrlCurlFail; + return NULL; + } + + curl_easy_setopt(curl, CURLOPT_URL, url); + curl_easy_setopt(curl, CURLOPT_USERAGENT, "libcurl/mp"); + curl_easy_setopt(curl, CURLOPT_FOLLOWLOCATION, 0L); + CURLcode res = curl_easy_perform(curl); + + if (res != CURLE_OK) { + error_set(_("Request failed")); + errno = UrlReqFail; + goto CLEANUP; + } + + res = curl_easy_getinfo(curl, CURLINFO_RESPONSE_CODE, &code); + if (res != CURLE_OK) { + error_set(_("Failed to get the response code")); + errno = UrlReqCodeFail; + goto CLEANUP; + } + + if ((code / 100) != 3) { + error_set(_("Response is not a redirect")); + errno = UrlReqBadCode; + goto CLEANUP; + } + + res = curl_easy_getinfo(curl, CURLINFO_REDIRECT_URL, &location); + if (res != CURLE_OK) { + error_set(_("Failed to get the location header")); + errno = UrlLocationFail; + goto CLEANUP; + } + + if (NULL == location) { + error_set(_("Invalid location header")); + errno = UrlLocationBad; + goto CLEANUP; + } + + location = strdup(location); + +CLEANUP: + curl_easy_cleanup(curl); + return location; } char *url_ensure_protocol(char *url) {