diff --git a/CHANGELOG.md b/CHANGELOG.md index 2185549..9c80fdb 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,6 @@ # 0.2.0 * ファイル名はパラメートルを付いたら、ファイル名は拡張子に +* 名前として保存オプション # 0.1.0 * 最初リリース diff --git a/main.c b/main.c index 2415780..4280305 100644 --- a/main.c +++ b/main.c @@ -2,6 +2,7 @@ #include #include #include +#include #include @@ -9,6 +10,11 @@ const char* sofname = "odl"; const char* version = "0.2.0"; char* filename; +int opt; +int output_flag = 0; +int version_flag = 0; +int err_flag = 0; + char* get_filename(const char* url) { char* fn_start = strrchr(url, '/'); if (fn_start == NULL) { @@ -71,19 +77,113 @@ int progress_callback(void *cp, double dt, double dn, double ut, double un) { return 0; } +void handle_o(int argc, char* argv[]) { + output_flag = 1; + if (optind < argc) { + if (filename != NULL) { + fprintf( + stderr, + "-oをご利用する場合、1つのファイルだけをダウンロード出来ます。\n" + ); + } + filename = argv[optind]; + } else { + fprintf(stderr, "-oの後でファイル名がありません。"); + err_flag = 1; + } +} + +void flags(int opt, int argc, char* argv[]) { + switch (opt) { + case 'o': + handle_o(argc, argv); + break; + case 'v': + version_flag = 1; + break; + default: + err_flag = 1; + printf("usage: %s-%s [-ov] [url ...]\n", sofname, version); + break; + } +} + +int downloader(CURL* curl, char* filename, const char* url) { + curl_easy_setopt(curl, CURLOPT_PROGRESSFUNCTION, progress_callback); + curl_easy_setopt(curl, CURLOPT_NOPROGRESS, 0L); + + FILE* file = fopen(filename, "wb"); + if (!file) { + perror("ファイルを開けません。"); + curl_easy_cleanup(curl); + return -1; + } + + curl_easy_setopt(curl, CURLOPT_URL, url); + curl_easy_setopt(curl, CURLOPT_WRITEDATA, file); + CURLcode res = curl_easy_perform(curl); + fclose(file); + + if (res != CURLE_OK) { + fprintf(stderr, "\nダウンロードに失敗: %s\n", curl_easy_strerror(res)); + curl_easy_cleanup(curl); + return -1; + } + + printf("\n"); + + return 0; +} + int main(int argc, char* argv[]) { if (argc < 2) { - printf("usage: %s-%s [url ...]\n", sofname, version); + printf("usage: %s-%s [-ov] [url ...]\n", sofname, version); return 1; } + while ((opt = getopt(argc, argv, "ov")) != -1) { + flags(opt, argc, argv); + } + + if (err_flag == 1) { + return 1; + } + + if (version_flag == 1) { + printf("%s-%s\n", sofname, version); + return 0; + } + CURL* curl = curl_easy_init(); if (!curl) { perror("curlを初期設置に失敗。"); return -1; } - for (int i = 1; i < argc; i++) { + // 一つのファイルだけが可能 + if (output_flag == 1) { + if (optind >= argc) { + fprintf(stderr, "-oの後でURLがありません。"); + return 1; + } + + if (filename == NULL) { + fprintf(stderr, "-oの後でファイル名がありません。"); + return 1; + } + + filename = argv[optind]; + const char* url = argv[optind+1]; + downloader(curl, filename, url); + + curl_easy_cleanup(curl); + printf("\nダウンロードに完了しました。\n"); + + return 0; + } + + // 複数ファイル名可能 + for (int i = optind; i < argc; i++) { const char* url = argv[i]; filename = get_filename(url); if (filename == NULL) { @@ -91,32 +191,10 @@ int main(int argc, char* argv[]) { continue; } - curl_easy_setopt(curl, CURLOPT_PROGRESSFUNCTION, progress_callback); - curl_easy_setopt(curl, CURLOPT_NOPROGRESS, 0L); - - FILE* file = fopen(filename, "wb"); - if (!file) { - curl_easy_cleanup(curl); - perror("ファイルを開けません。"); - return -1; - } - - curl_easy_setopt(curl, CURLOPT_URL, url); - curl_easy_setopt(curl, CURLOPT_WRITEDATA, file); - CURLcode res = curl_easy_perform(curl); - fclose(file); - - if (res != CURLE_OK) { - curl_easy_cleanup(curl); - fprintf(stderr, "ダウンロードに失敗: %s\n", curl_easy_strerror(res)); - return -1; - } - - printf("\n"); + downloader(curl, filename, url); } curl_easy_cleanup(curl); - printf("\nダウンロードに完了しました。\n"); return 0;