From 8926f839720471cc86fd4f7c6371d63b8f71b91d Mon Sep 17 00:00:00 2001 From: dacctal <120422854+dacctal@users.noreply.github.com> Date: Wed, 21 Jan 2026 23:56:39 -0500 Subject: initial commit --- src/build_pkg.cc | 36 +++++++++++++++++ src/build_systems.cc | 111 +++++++++++++++++++++++++++++++++++++++++++++++++++ src/cmd_out.cc | 18 +++++++++ src/create_pkg.cc | 20 ++++++++++ src/fetch_git.cc | 24 +++++++++++ src/fetch_src.cc | 7 ++++ src/help.cc | 39 ++++++++++++++++++ src/install_pkg.cc | 9 +++++ src/is_updated.cc | 6 +++ src/link_install.cc | 33 +++++++++++++++ src/main.cc | 41 ++++++++++++++++++- src/name_from_url.cc | 5 +++ src/setup_dirs.cc | 9 +++++ src/setup_pkgit.cc | 5 +++ src/setup_repo.cc | 4 ++ src/update_pkg.cc | 12 ++++++ src/vars.cc | 75 ++++++++++++++++++++++++++++++++++ 17 files changed, 453 insertions(+), 1 deletion(-) create mode 100644 src/build_pkg.cc create mode 100644 src/build_systems.cc create mode 100644 src/cmd_out.cc create mode 100644 src/create_pkg.cc create mode 100644 src/fetch_git.cc create mode 100644 src/fetch_src.cc create mode 100644 src/help.cc create mode 100644 src/install_pkg.cc create mode 100644 src/is_updated.cc create mode 100644 src/link_install.cc create mode 100644 src/name_from_url.cc create mode 100644 src/setup_dirs.cc create mode 100644 src/setup_pkgit.cc create mode 100644 src/setup_repo.cc create mode 100644 src/update_pkg.cc create mode 100644 src/vars.cc (limited to 'src') diff --git a/src/build_pkg.cc b/src/build_pkg.cc new file mode 100644 index 0000000..67c67b8 --- /dev/null +++ b/src/build_pkg.cc @@ -0,0 +1,36 @@ +#include + +#include "build_systems.cc" + +const std::map> builds = { + {"bldit", bldit_build}, + {"compile.sh", compilesh_build}, + {"build.sh", buildsh_build}, + {"autogen.sh", autogen_build}, + {"configure", autotools_build}, + {"configure.ac", autotools_build}, + {"Makefile", make_build}, + {"Makefile.am", make_build}, + {"CMakeLists.txt", cmake_build}, + {"meson.build", meson_build}, + {"build.ninja", ninja_build}, + {"Cargo.toml", cargo_build}, + {"go.mod", go_build}, + {"gradle.build", gradle_build}, + {"pnpm-lock.yaml", pnpm_build}, + {"pyproject.toml", python_build}, + {"build.zig", zig_build} +}; + +void build_pkg(std::filesystem::path build_dir) { + if (build_dir != fs::current_path().string()) { + fs::current_path(build_dir); + } + for (auto const& dir_entry : fs::directory_iterator(fs::current_path().string())) { + for (auto build : builds) { + if (dir_entry.path().filename() == build.first) { + build.second(); + } + } + } +} diff --git a/src/build_systems.cc b/src/build_systems.cc new file mode 100644 index 0000000..2e402e7 --- /dev/null +++ b/src/build_systems.cc @@ -0,0 +1,111 @@ +#include + +#include "toml.hh" + +#include "vars.cc" + +void autogen_build() { + system("./autogen.sh"); + system("make"); +} + +void autotools_build() { + system("./configure"); + for (auto const& dir_entry : fs::directory_iterator(fs::current_path().string())) { + if (dir_entry.path().filename() == "CMakeLists.txt") { + fs::create_directories("build"); + fs::current_path("build"); + system("cmake .."); + } + } + for (auto const& dir_entry : fs::directory_iterator(fs::current_path().string())) { + if (dir_entry.path().filename() == "Makefile") { + system("make"); + } + } +} + +void bldit_build() { + system("./bldit"); +} + +void buildsh_build() { + system("./build.sh"); +} + +void compilesh_build() { + system("./compile.sh"); +} + +void cargo_build() { + system("cargo build --release"); +} + +void cmake_build() { + fs::create_directories("build"); + fs::current_path("build"); + system("cmake .."); + system("make"); +} + +void go_build() { + for (auto const& dir_entry : fs::directory_iterator(fs::current_path().string())) { + if (dir_entry.path().filename() == "main.go") { + system("go build main.go"); + } + } +} + +void gradle_build() { + system("gradle build"); +} + +void make_build() { + for (auto const& dir_entry : fs::directory_iterator(fs::current_path().string())) { + if (dir_entry.path().filename() == "autogen.sh") { + autogen_build(); + return; + } + } + for (auto const& dir_entry : fs::directory_iterator(fs::current_path().string())) { + if (dir_entry.path().filename() == "configure.ac") { + autotools_build(); + return; + } + } + system("make"); +} + +void meson_build() { + system("meson setup --wipe build"); + system("meson compile -C build"); +} + +void ninja_build() { + system("ninja"); +} + +void nim_build() { + system("nimble build"); +} + +void pnpm_build() { + system("pnpm install"); + system("pnpm run build"); +} + +void python_build() { + toml::parse_result pyproject_toml = toml::parse_file("pyproject.toml"); + std::string pypkg = pyproject_toml["project"]["name"].ref(); + std::string commands[] = { + "export PIPX_BIN_DIR=" + bin, + "pipx install " + pypkg + }; + for (int i = 0; i < sizeof(commands)/sizeof(commands[0]); i++) { + system(commands[i].c_str()); + } +} + +void zig_build() { + system("zig build"); +} diff --git a/src/cmd_out.cc b/src/cmd_out.cc new file mode 100644 index 0000000..a855add --- /dev/null +++ b/src/cmd_out.cc @@ -0,0 +1,18 @@ +#include +#include +#include +#include +#include + +std::string cmd_out(const char* cmd) { + std::array buffer; + std::string result; + std::unique_ptr pipe(popen(cmd, "r"), pclose); + if (!pipe) { + throw std::runtime_error("popen() failed!"); + } + while (fgets(buffer.data(), static_cast(buffer.size()), pipe.get()) != nullptr) { + result += buffer.data(); + } + return result; +} diff --git a/src/create_pkg.cc b/src/create_pkg.cc new file mode 100644 index 0000000..b243afd --- /dev/null +++ b/src/create_pkg.cc @@ -0,0 +1,20 @@ +#include +#include + +#include "vars.cc" +#include "name_from_url.cc" + +Pkg create_pkg(std::string arg) { + Pkg pkg; + + if (arg.rfind("http", 0) == 0) { + pkg.url = arg; + pkg.name = name_from_url(arg); + } + + pkg.ver = "HEAD"; + + pkg.src = pkgblds + "/" + pkg.name + "/" + pkg.ver; + + return pkg; +} diff --git a/src/fetch_git.cc b/src/fetch_git.cc new file mode 100644 index 0000000..3306e42 --- /dev/null +++ b/src/fetch_git.cc @@ -0,0 +1,24 @@ +#include + +#include "vars.cc" + +int fetch_git(Pkg pkg) { + std::string clone_cmds[] = { + "git -c advice.detachedHead=false clone --depth 1 " + pkg.url + " " + + pkg.src.c_str(), + "git -c advice.detachedHead=false clone --branch " + pkg.ver + + " --depth 1 " + pkg.url + " " + pkg.src.c_str()}; + if (strcmp(pkg.ver.c_str(), "HEAD") == 0) { + if (WEXITSTATUS(system(clone_cmds[0].c_str())) == 0x10) { + return 0; + } else { + return 1; + } + } else { + if (WEXITSTATUS(system(clone_cmds[1].c_str())) == 0x10) { + return 0; + } else { + return 1; + } + } +} diff --git a/src/fetch_src.cc b/src/fetch_src.cc new file mode 100644 index 0000000..27a4b23 --- /dev/null +++ b/src/fetch_src.cc @@ -0,0 +1,7 @@ +#include +#include "fetch_git.cc" + +void fetch_src(Pkg pkg) { + if (fs::exists(pkg.src)) { fs::remove_all(pkg.src); } + if (fetch_git(pkg) == 0) { return; } else { exit(EXIT_FAILURE); } +} diff --git a/src/help.cc b/src/help.cc new file mode 100644 index 0000000..a4d022a --- /dev/null +++ b/src/help.cc @@ -0,0 +1,39 @@ +#include + +#include "vars.cc" + +void help() { + std::cout << ""+bold_magenta+" , \n"; + std::cout << " "+bold_magenta+"/ \\ \n"; + std::cout << " "+bold_magenta+"/ \\ \n"; + std::cout << " "+bold_magenta+"__-' '-__ \n"; + std::cout << " "+bold_magenta+"''--__ __--'' "+bold_yellow+"\n"; + std::cout << " "+bold_yellow+"_--"+bold_magenta+"\\ /"+bold_yellow+"--_ \n"; + std::cout << " "+bold_yellow+"_--' "+bold_magenta+"\\ /"+bold_yellow+" '--_ \n"; + std::cout << " "+bold_yellow+"'-__ "+bold_magenta+"'"+bold_yellow+" __-'\n"; + std::cout << " "+bold_yellow+"'-__ __-' \n"; + std::cout << " "+bold_yellow+"'-_-' "+color_reset+"\n"; + std::cout << "\n"; + std::cout << " pkgit\n"; + std::cout << " "+italic+""+gray+"- package it! -"+color_reset+"\n"; + std::cout << " "+magenta+"v"+version+""+color_reset+"\n"; + std::cout << "\n"; + std::cout << ""+red+"subcommands"+color_reset+":\n"; + std::cout << ""+color_reset+"├─ "+green+"a"+color_reset+", "+yellow+"add "+blue+"[url, file] "+gray+"# add a repo/repopkg\n"; + std::cout << ""+color_reset+"├─ "+green+"b"+color_reset+", "+yellow+"build "+blue+"[path] "+gray+"# build a package\n"; + std::cout << ""+color_reset+"│└── "+green+"-v"+color_reset+", "+yellow+"--verbose"+blue+"[tag] "+gray+"# give full output of build\n"; + std::cout << ""+color_reset+"├┬ "+green+"i"+color_reset+", "+yellow+"install "+blue+"[pkgs, urls] "+gray+"# install a package/repo\n"; + std::cout << ""+color_reset+"│├── "+green+"-v"+color_reset+", "+yellow+"--verbose"+blue+"[tag] "+gray+"# give full output of install\n"; + std::cout << ""+color_reset+"│├── "+green+"-t:"+color_reset+", "+yellow+"--tag:"+blue+"[tag] "+gray+"# specify a version\n"; + std::cout << ""+color_reset+"│└── "+green+"-l:"+color_reset+", "+yellow+"--list:"+blue+"[filename] "+gray+"# install from a package list\n"; + std::cout << ""+color_reset+"├┬ "+green+"r"+color_reset+", "+yellow+"remove "+blue+"[pkgs] "+gray+"# remove an installed package\n"; + std::cout << ""+color_reset+"│└── "+green+"-r:"+color_reset+", "+yellow+"--repo:"+blue+"[repo] "+gray+"# remove a repo\n"; + std::cout << ""+color_reset+"├─ "+green+"f"+color_reset+", "+yellow+"files "+blue+"[pkgs] "+gray+"# list all files of a package\n"; + std::cout << ""+color_reset+"├─ "+green+"s"+color_reset+", "+yellow+"search "+blue+"[pkgs] "+gray+"# search for packages\n"; + std::cout << ""+color_reset+"├─ "+green+"l"+color_reset+", "+yellow+"list "+gray+"# list installed packages\n"; + std::cout << ""+color_reset+"└─ "+green+"u"+color_reset+", "+yellow+"update "+gray+"# update all installed packages\n"; + std::cout << "\n"; + std::cout << ""+red+"flags"+color_reset+":\n"; + std::cout << ""+color_reset+"├─ "+green+"-h"+color_reset+", "+yellow+"--help "+gray+"# display this help message\n"; + std::cout << ""+color_reset+"└─ "+green+"-v"+color_reset+", "+yellow+"--version "+gray+"# display version number\n"; +} diff --git a/src/install_pkg.cc b/src/install_pkg.cc new file mode 100644 index 0000000..a710831 --- /dev/null +++ b/src/install_pkg.cc @@ -0,0 +1,9 @@ +#include "fetch_src.cc" +#include "build_pkg.cc" +#include "link_install.cc" + +void install_pkg(Pkg pkg) { + fetch_src(pkg); + build_pkg(pkg.src); + link_install(pkg.src); +} diff --git a/src/is_updated.cc b/src/is_updated.cc new file mode 100644 index 0000000..96c7fe6 --- /dev/null +++ b/src/is_updated.cc @@ -0,0 +1,6 @@ +#include "cmd_out.cc" + +bool is_updated(std::string src) { + if (cmd_out("git pull") == "Already up to date.") { return true; } + return false; +} diff --git a/src/link_install.cc b/src/link_install.cc new file mode 100644 index 0000000..f4d9777 --- /dev/null +++ b/src/link_install.cc @@ -0,0 +1,33 @@ +#include +#include +#include +#include + +#include "vars.cc" + +namespace fs = std::filesystem; + +void link_install(std::filesystem::path build_dir) { + for (auto const& dir_entry : fs::recursive_directory_iterator(build_dir)) + if (dir_entry.path().extension().string().rfind(".so", 0) == 0) { + if (!fs::exists(lib+"/"+dir_entry.path().filename().string())) { + create_symlink(dir_entry, lib+"/"+dir_entry.path().filename().string()); + std::cout << print_pkgit << "linked library: " << dir_entry << "\n"; + } else { std::cout << print_pkgit << "library already exists: " << dir_entry << "\n"; } + + } else if (!access(dir_entry.path().c_str(), X_OK) && !is_directory(dir_entry.path())) { + if (!fs::exists(bin+"/"+dir_entry.path().filename().string()) && + dir_entry.path().filename().string() == "bldit" && + dir_entry.path().filename().string() == "build.sh" && + dir_entry.path().filename().string() == "compile.sh") { + create_symlink(dir_entry, bin+"/"+dir_entry.path().filename().string()); + std::cout << print_pkgit << "linked executable: " << dir_entry << "\n"; + } else { std::cout << print_pkgit << "executable already exists: " << dir_entry << "\n"; } + + } else if (dir_entry.path().extension() == ".h") { + if (!fs::exists(include+"/"+dir_entry.path().filename().string())) { + create_symlink(dir_entry, include+"/"+dir_entry.path().filename().string()); + std::cout << print_pkgit << "linked include: " << dir_entry << "\n"; + } else { std::cout << print_pkgit << "include already exists: " << dir_entry << "\n"; } + } +} diff --git a/src/main.cc b/src/main.cc index b920482..c020c87 100644 --- a/src/main.cc +++ b/src/main.cc @@ -1 +1,40 @@ -#include penis +#include +#include +#include + +#include "create_pkg.cc" +#include "help.cc" +#include "setup_pkgit.cc" +#include "install_pkg.cc" + +int main(int argc, char *argv[]) { + setup_pkgit(); + Pkg pkg; + + if (argv[1]) { + if (strcmp(argv[1], "build") == 0 || strcmp(argv[1], "b") == 0) { + if (argv[2]) { + build_pkg(argv[2]); + } else { + build_pkg(fs::current_path().string()); + } + } else if (strcmp(argv[1], "install") == 0 || strcmp(argv[1], "i") == 0) { + pkg = create_pkg(argv[2]); + if (argv[2]) { + install_pkg(pkg); + } else { + std::cout << print_error << "Not enough arguments! Try: `pkgit install [url]`"; + } + } else if (strcmp(argv[1], "help") == 0 || strcmp(argv[1], "h") == 0) { + help(); + } else if (strcmp(argv[1], "type") == 0) { + link_install(fs::current_path().string()); + } else { + help(); + } + } else { + help(); + } + + return 0; +} diff --git a/src/name_from_url.cc b/src/name_from_url.cc new file mode 100644 index 0000000..2aaddac --- /dev/null +++ b/src/name_from_url.cc @@ -0,0 +1,5 @@ +#include + +std::string name_from_url(std::string url) { + return url.substr(url.find_last_of('/') + 1); +} diff --git a/src/setup_dirs.cc b/src/setup_dirs.cc new file mode 100644 index 0000000..457c13d --- /dev/null +++ b/src/setup_dirs.cc @@ -0,0 +1,9 @@ +#include + +#include "vars.cc" + +void setup_dirs() { + for(unsigned int a = 0; a < sizeof(all_dirs)/sizeof(all_dirs[0]); a++) { + std::filesystem::create_directories(all_dirs[a]); + } +} diff --git a/src/setup_pkgit.cc b/src/setup_pkgit.cc new file mode 100644 index 0000000..3184044 --- /dev/null +++ b/src/setup_pkgit.cc @@ -0,0 +1,5 @@ +#include "setup_dirs.cc" + +void setup_pkgit() { + setup_dirs(); +} diff --git a/src/setup_repo.cc b/src/setup_repo.cc new file mode 100644 index 0000000..8a21d45 --- /dev/null +++ b/src/setup_repo.cc @@ -0,0 +1,4 @@ + + +void setup_repo() { +} diff --git a/src/update_pkg.cc b/src/update_pkg.cc new file mode 100644 index 0000000..4b35793 --- /dev/null +++ b/src/update_pkg.cc @@ -0,0 +1,12 @@ +#include "is_updated.cc" +#include "build_pkg.cc" +#include "link_install.cc" +#include "vars.cc" + +void update_pkg(Pkg pkg) { + if (is_updated(pkg.src)) { + build_pkg(pkg.src); + link_install(pkg.src); + } + else { std::cout << print_skipped << pkg.name << " is already up to date."; } +} diff --git a/src/vars.cc b/src/vars.cc new file mode 100644 index 0000000..4957be4 --- /dev/null +++ b/src/vars.cc @@ -0,0 +1,75 @@ +#ifndef vars +#define vars + +#include +#include + +namespace fs = std::filesystem; + +struct Pkg { + std::string url; + std::string name; + std::string ver; + fs::path src; +}; + +const std::string home_dir = std::getenv("HOME"); + +const std::string bin = home_dir + "/.local/bin"; +const std::string lib = home_dir + "/.local/lib"; +const std::string include = home_dir + "/.local/include"; +const std::string pkgblds = home_dir + "/.local/share/pkgit"; + +const std::string all_dirs[] = { + bin, + lib, + include, + pkgblds +}; + +// version +const std::string version = "0.1.0-breakout"; + +// colors +const std::string red = "\e[0;31m"; +const std::string green = "\e[0;32m"; +const std::string yellow = "\e[0;33m"; +const std::string blue = "\e[0;34m"; +const std::string magenta = "\e[0;35m"; +const std::string cyan = "\e[0;36m"; +const std::string gray = "\e[0;37m"; +// bright +const std::string bright_red = "\e[0;91m"; +const std::string bright_green = "\e[0;92m"; +const std::string bright_yellow = "\e[0;93m"; +const std::string bright_blue = "\e[0;94m"; +const std::string bright_magenta = "\e[0;95m"; +const std::string bright_cyan = "\e[0;96m"; +const std::string bright_gray = "\e[0;97m"; +// bold +const std::string bold_red = "\e[1;31m"; +const std::string bold_green = "\e[1;32m"; +const std::string bold_yellow = "\e[1;33m"; +const std::string bold_blue = "\e[1;34m"; +const std::string bold_magenta = "\e[1;35m"; +const std::string bold_cyan = "\e[1;36m"; +const std::string bold_gray = "\e[1;37m"; +const std::string bold_white = "\e[1;38m"; +// bold bright +const std::string bold_bright_red = "\e[1;91m"; +const std::string bold_bright_green = "\e[1;92m"; +const std::string bold_bright_yellow = "\e[1;93m"; +const std::string bold_bright_blue = "\e[1;94m"; +const std::string bold_bright_magenta = "\e[1;95m"; +const std::string bold_bright_cyan = "\e[1;96m"; +const std::string bold_bright_gray = "\e[1;97m"; +// italic +const std::string italic = "\e[3m"; +// reset +const std::string color_reset = "\e[0m"; + +const std::string print_pkgit = bold_yellow + "[" + bold_magenta + "pkgit" + bold_yellow + "]\t" + color_reset; +const std::string print_skipped = print_pkgit + blue + "[SKIPPED]\t" + color_reset; +const std::string print_error = print_pkgit + red + "[ERROR]\t" + color_reset; + +#endif -- cgit v1.2.3