4 Commits

Author SHA1 Message Date
7a0ebb43a5 remove one project deps 2026-02-18 21:08:56 +08:00
4c628ff336 update CHANGELOG.md 2026-02-18 21:05:36 +08:00
95324ce199 chore: translate CLI and installer messages to English 2026-02-18 21:04:28 +08:00
d1e23a3179 Update project docs lang to Eng
Add FAQ.md and docs/
2026-02-18 19:53:39 +08:00
21 changed files with 658 additions and 301 deletions

View File

@@ -1,5 +1,12 @@
# Changelog
## [0.2.1] - 2026-02-18
Changed:
- Translated user-facing CLI messages to English
- Unified error and warning output via `utils::log::{error, warn}`
- Updated `--help` output: translated headers and examples to English, used `printc`, and applied `BOLD_*` styles
- Translated installer script messages in `install.sh` and `install.ps1` to English
## [0.2.0] - 2026-02-17
Изменено:
- Проект переведен с Python на Rust

2
Cargo.lock generated
View File

@@ -62,7 +62,7 @@ checksum = "613afe47fcd5fac7ccf1db93babcb082c5994d996f20b8b159f2ad1658eb5724"
[[package]]
name = "dcr"
version = "0.2.0"
version = "0.2.1"
dependencies = [
"reqwest",
"self-replace",

View File

@@ -1,10 +1,10 @@
[package]
name = "dcr"
version = "0.2.0"
version = "0.2.1"
edition = "2024"
build = "build.rs"
[dependencies]
reqwest = { version = "0.12", default-features = false, features = ["blocking", "json", "rustls-tls"] }
serde = { version = "1", features = ["derive"] }
self-replace = "1"
self-replace = "1"

102
FAQ.md Normal file
View File

@@ -0,0 +1,102 @@
# FAQ
## What is this project about?
`dcr` is a tool for managing C/C++ projects and their dependencies.
It is inspired by Cargo, but it is not a direct equivalent of Makefile, CMake, or other classic build systems.
The goal is to provide a simpler and easier-to-configure development workflow.
## How is the project developed?
The project is written in Rust and is primarily developed by one maintainer, Dexoron.
AI tools are used during development, but they do not write the project end-to-end. Their role is limited to supporting specific tasks (for example, suggestions, wording checks, and translations).
## Which tools are used for development?
Main development stack:
- `RustRover` 2025 - development IDE.
- `Codex` (`GPT-5.3-Codex (medium)`) - primary AI tool, integrated via JetBrains AI Chat.
- `Rust` - main project language.
- `Cargo` - tool for building, testing, and dependency management in Rust projects.
## Is the project open source?
Yes, the project is open source.
You can propose ideas, report issues, and contribute code changes.
The project is distributed under the MIT license (see `LICENSE`).
## How can I contribute?
Thank you for contributing.
You can:
- help with code;
- help with translations;
- help with documentation;
- suggest an idea or report a bug.
### If you want to submit changes (code, translation, documentation)
1. Fork the required repository: `dexoron/dcr` (main project) or `dexoron/dcr-site` (project website).
2. Make your changes following the rules in `CONTRIBUTING.md`.
3. Push changes to your fork.
4. Open a Pull Request.
5. Wait for review.
### If you want to report a problem or suggest an idea
1. Open the relevant repository: `dexoron/dcr` or `dexoron/dcr-site`.
2. Go to the `Issues` tab.
3. Create an Issue and specify its type (bug, suggestion, question/help).
4. Describe the problem or idea clearly and concisely.
5. Wait for feedback.
## How do I install `dcr`?
Available installation methods may vary by project version.
Recommended path:
- check instructions in `README.md`;
- if there is no prebuilt package for your platform, build from source using `cargo build --release`.
## How can I get started quickly?
Minimal workflow:
1. Install `dcr`.
2. Create a project (or open an existing C/C++ project).
3. Initialize `dcr` configuration.
4. Add project dependencies.
5. Build using `dcr`.
For detailed commands and examples, see `README.md` and the project documentation.
## What is the project status?
`dcr` is under active development.
This means some interfaces and behaviors may change between versions.
Before upgrading, check the changelog and release notes.
## Which systems does `dcr` support?
`dcr` targets modern C/C++ development environments.
Actual compatibility depends on the `dcr` version, operating system, and toolchain.
Before starting, check documentation for:
- supported operating systems;
- supported compilers and linkers;
- version-specific limitations.
## How is `dcr` different from Make/CMake?
`dcr` does not aim to be a direct replacement for Make/CMake.
Its main focus is simplifying project and dependency management with a Cargo-like experience.
If you need low-level, full control over build steps, classic tools may be a better fit.
If you want a simpler and more uniform configuration model, `dcr` may be more convenient.
## Where can I find documentation and examples?
Primary sources:
- `README.md` in the repository;
- project documentation (see the project website);
- `Issues` for known problems and discussions.
## How do I report a bug properly?
To make a bug report easy to reproduce, include:
1. `dcr` version.
2. OS and compiler/toolchain version.
3. Steps to reproduce.
4. Expected behavior.
5. Actual behavior and error output.
6. Minimal project example (if possible).
Submit bugs and issues through `Issues` in the relevant repository.

102
README.md
View File

@@ -1,31 +1,31 @@
# DCR (Dexoron Cargo Realization)
DCR — это утилита для управления проектами на C/C++ в стиле Cargo.
DCR is a utility for managing C/C++ projects in a Cargo-like style.
Текущая реализация написана на Rust.
The current implementation is written in Rust.
## Зачем DCR
- Единая структура проекта без ручной настройки
- Простые команды для типовых задач
- Прозрачная компиляция и предсказуемые профили сборки
## Why DCR
- Unified project structure without manual setup
- Simple commands for common tasks
- Transparent compilation and predictable build profiles
## Возможности
- Создание нового проекта или инициализация текущей директории
- Сборка проекта в профилях `debug` и `release`
- Запуск собранного бинарника
- Очистка результатов сборки
- Генерация минимального шаблона C-проекта
- Обновление бинарника через `dcr --update` (GitHub Releases)
## Features
- Create a new project or initialize the current directory
- Build a project with `debug` and `release` profiles
- Run the compiled binary
- Clean build artifacts
- Generate a minimal C project template
- Update the binary via `dcr --update` (GitHub Releases)
## Поддерживаемые платформы
## Supported Platforms
- Linux: `x86_64-unknown-linux-gnu`
- macOS Intel: `x86_64-apple-darwin`
- macOS Apple Silicon: `aarch64-apple-darwin`
- Windows: `x86_64-pc-windows-msvc`
## Установка
## Installation
### Из исходников
### From Source
```sh
git clone https://github.com/dexoron/dcr.git
@@ -35,37 +35,37 @@ mkdir -p ~/.local/bin
ln -sf "$PWD/target/release/dcr" ~/.local/bin/dcr
```
### Через install.sh (Linux/macOS)
### Via `install.sh` (Linux/macOS)
```sh
curl -fsSL https://raw.githubusercontent.com/dexoron/dcr/master/install.sh | bash
curl -fsSL https://dcr.dexoron.su/install.sh | bash
```
### Через install.ps1 (Windows)
### Via `install.ps1` (Windows)
```powershell
irm https://raw.githubusercontent.com/dexoron/dcr/master/install.ps1 | iex
irm https://dcr.dexoron.su/install.ps1 | iex
```
Оба скрипта при запуске спрашивают:
- скачать готовый бинарник из GitHub Release
- или собрать проект из `git`
When executed, both scripts ask whether to:
- download a prebuilt binary from GitHub Releases
- or build the project from `git`
Релизные ассеты:
Release assets:
- `dcr-x86_64-unknown-linux-gnu`
- `dcr-x86_64-apple-darwin`
- `dcr-aarch64-apple-darwin`
- `dcr-x86_64-pc-windows-msvc.exe`
## Быстрый старт
## Quick Start
Создать новый проект:
Create a new project:
`dcr new hello`
Или инициализировать текущую директорию (директория должна быть пустой):
Or initialize the current directory (the directory must be empty):
`dcr init`
Структура проекта:
Project structure:
```txt
hello/
@@ -74,38 +74,38 @@ hello/
- dcr.toml
```
Сборка и запуск проекта:
`dcr run` или `dcr run --release`
Build and run the project:
`dcr run` or `dcr run --release`
## Команды
## Commands
### `dcr new <name>`
Создает проект в текущей директории с указанным именем.
Creates a project with the specified name in the current directory.
### `dcr init`
Создает проект в текущей директории. Имя проекта будет равно имени директории. Директория должна быть пустой.
Creates a project in the current directory. The project name is taken from the directory name. The directory must be empty.
### `dcr build [profile]`
Собирает проект. Если профиль не указан, используется `--debug`.
Builds the project. If no profile is specified, `--debug` is used.
### `dcr run [profile]`
Собирает проект и запускает бинарник. Если профиль не указан, используется `--debug`.
Builds the project and runs the binary. If no profile is specified, `--debug` is used.
Запуск вручную:
Run manually:
`./target/<profile>/main`
### `dcr clean`
Удаляет папку `target` в корне проекта.
Removes the `target` directory in the project root.
## Профили сборки
Поддерживаются два профиля:
- `--debug` (по умолчанию) — флаги: `-O0 -g -Wall -Wextra -fno-omit-frame-pointer -DDEBUG`
- `--release` — флаги: `-O3 -DNDEBUG -march=native`
## Build Profiles
Two profiles are supported:
- `--debug` (default) - flags: `-O0 -g -Wall -Wextra -fno-omit-frame-pointer -DDEBUG`
- `--release` - flags: `-O3 -DNDEBUG -march=native`
## Конфигурация
Основной файл проекта — `dcr.toml`.
## Configuration
The main project file is `dcr.toml`.
Пример `dcr.toml`:
Example `dcr.toml`:
```toml
[package]
@@ -117,12 +117,12 @@ compiler = "clang"
[dependencies]
```
## Требования
- Rust toolchain (`rustc`, `cargo`) - Для ручной сборки DCR
- C-компилятор (`clang`, `gcc` или другие)
## Requirements
- Rust toolchain (`rustc`, `cargo`) - for building DCR from source
- C compiler (`clang`, `gcc`, or others)
## Релизы
Релизы собираются автоматически через GitHub Actions (`.github/workflows/release.yml`) при пуше тега формата `v*`.
## Releases
Releases are built automatically via GitHub Actions (`.github/workflows/release.yml`) when a tag matching `v*` is pushed.
## Лицензия
См. файл `LICENSE`.
## License
See `LICENSE`.

57
docs/CONTRIBUTING_ru.md Normal file
View File

@@ -0,0 +1,57 @@
# Вклад в проект
Спасибо за интерес к проекту.
## Требования
- Использовать Rust stable.
- Перед PR код должен проходить форматирование, линт и сборку.
## Быстрый старт
```bash
git clone https://github.com/dexoron/dcr.git
cd dcr
cargo check
```
## Стиль кода
- Форматируйте код через `cargo fmt`.
- Проверяйте предупреждения через `cargo clippy`.
- Держите функции небольшими и сфокусированными.
- Предпочитайте понятные имена вместо "хитрых".
## Проверки
Перед PR запускайте:
```bash
cargo fmt --all
cargo clippy --all-targets --all-features -- -D warnings
cargo check
```
## CI/CD и релизы
- CI: `.github/workflows/ci.yml`
- Release: `.github/workflows/release.yml`
- Релиз запускается по тегу `v*` и публикует бинарники для:
- `x86_64-unknown-linux-gnu`
- `x86_64-apple-darwin`
- `aarch64-apple-darwin`
- `x86_64-pc-windows-msvc`
## Коммиты и PR
- Делайте коммиты понятными.
- В PR указывайте краткое описание и мотивацию изменений.
- Обновляйте документацию при изменении поведения.
## Вопросы
Если что-то непонятно, открой issue или задайте вопрос в PR.
Также можно задать вопрос напрямую:
- TG: @dexoron
- DS: dexoron

102
docs/FAQ_ru.md Normal file
View File

@@ -0,0 +1,102 @@
# FAQ
## В чем суть проекта?
`dcr` - это инструмент для управления C/C++ проектами и их зависимостями.
Он вдохновлен Cargo, но не является аналогом Makefile, CMake или других классических систем сборки.
Цель проекта - дать более простую и удобную в настройке среду для разработки.
## Как разрабатывается проект?
Проект написан на Rust и в основном развивается одним разработчиком - Dexoron.
В работе используются ИИ-инструменты, но они не пишут проект целиком: их роль - помощь с отдельными задачами (например, советы, проверка формулировок, переводы и т.д.).
## Какие инструменты используются для разработки?
Основной стек разработки:
- `RustRover` 2025 - IDE для разработки.
- `Codex` (`GPT-5.3-Codex (medium)`) - основной ИИ-инструмент, интегрированный через JetBrains AI Chat.
- `Rust` - основной язык проекта.
- `Cargo` - инструмент сборки, тестов и управления зависимостями Rust-проектов.
## Проект открытый?
Да, проект открыт (Open Source).
Вы можете предлагать идеи, находить ошибки и вносить изменения в код.
Проект распространяется по лицензии MIT (см. `LICENSE`).
## Как внести вклад?
Спасибо за желание помочь проекту.
Вы можете:
- помочь с кодом;
- помочь с переводом;
- помочь с документацией;
- предложить идею или сообщить о баге.
### Если вы хотите внести изменения (код, перевод, документация)
1. Сделайте форк нужного репозитория: `dexoron/dcr` (основной проект) или `dexoron/dcr-site` (сайт проекта).
2. Внесите изменения с учетом правил из `CONTRIBUTING.md`.
3. Отправьте изменения в свой форк.
4. Создайте Pull Request.
5. Дождитесь ревью.
### Если вы хотите сообщить о проблеме или предложить идею
1. Откройте нужный репозиторий: `dexoron/dcr` или `dexoron/dcr-site`.
2. Перейдите во вкладку `Issues`.
3. Создайте Issue и укажите тип (баг, предложение, вопрос/помощь).
4. Опишите проблему или идею кратко и понятно.
5. Дождитесь обратной связи.
## Как установить `dcr`?
Актуальные способы установки зависят от текущей версии проекта.
Рекомендуемый путь:
- проверьте инструкции в `README.md`;
- если готового пакета для вашей платформы нет, соберите проект из исходников через `cargo build --release`.
## Как быстро начать работу?
Минимальный сценарий:
1. Установите `dcr`.
2. Создайте проект (или перейдите в существующий C/C++ проект).
3. Инициализируйте конфигурацию `dcr`.
4. Добавьте зависимости проекта.
5. Запустите сборку через `dcr`.
Подробные команды и примеры смотрите в `README.md` и документации проекта.
## На какой стадии проект?
`dcr` активно развивается.
Это означает, что интерфейсы и поведение некоторых функций могут меняться между версиями.
Перед обновлением рекомендуется читать changelog и проверять заметки к релизу.
## С какими системами работает `dcr`?
`dcr` ориентирован на современные среды разработки C/C++.
Фактическая совместимость зависит от версии `dcr`, операционной системы и используемого toolchain.
Перед началом работы проверьте в документации:
- поддерживаемые ОС;
- поддерживаемые компиляторы и линкеры;
- ограничения конкретной версии.
## Чем `dcr` отличается от Make/CMake?
`dcr` не пытается быть прямой заменой Make/CMake.
Главный фокус `dcr` - упростить управление проектом и зависимостями в стиле, близком к опыту Cargo.
Если вам нужен низкоуровневый полный контроль над процессом сборки, классические инструменты могут быть привычнее.
Если нужна более простая и единообразная модель конфигурации - `dcr` может быть удобнее.
## Где смотреть документацию и примеры?
Основные источники:
- `README.md` в репозитории;
- документация проекта (смотреть сайт проекта);
- `Issues` для известных проблем и обсуждений;
## Как правильно сообщить о баге?
Чтобы баг-репорт можно было быстро воспроизвести, укажите:
1. Версию `dcr`.
2. ОС и версию компилятора/toolchain.
3. Шаги воспроизведения.
4. Ожидаемое поведение.
5. Фактическое поведение и текст ошибки.
6. Минимальный пример проекта (по возможности).
Баги и проблемы отправляйте через `Issues` в соответствующем репозитории.

128
docs/README_ru.md Normal file
View File

@@ -0,0 +1,128 @@
# DCR (Dexoron Cargo Realization)
DCR — это утилита для управления проектами на C/C++ в стиле Cargo.
Текущая реализация написана на Rust.
## Зачем DCR
- Единая структура проекта без ручной настройки
- Простые команды для типовых задач
- Прозрачная компиляция и предсказуемые профили сборки
## Возможности
- Создание нового проекта или инициализация текущей директории
- Сборка проекта в профилях `debug` и `release`
- Запуск собранного бинарника
- Очистка результатов сборки
- Генерация минимального шаблона C-проекта
- Обновление бинарника через `dcr --update` (GitHub Releases)
## Поддерживаемые платформы
- Linux: `x86_64-unknown-linux-gnu`
- macOS Intel: `x86_64-apple-darwin`
- macOS Apple Silicon: `aarch64-apple-darwin`
- Windows: `x86_64-pc-windows-msvc`
## Установка
### Из исходников
```sh
git clone https://github.com/dexoron/dcr.git
cd dcr
cargo build --release
mkdir -p ~/.local/bin
ln -sf "$PWD/target/release/dcr" ~/.local/bin/dcr
```
### Через install.sh (Linux/macOS)
```sh
curl -fsSL https://dcr.dexoron.su/install.sh | bash
```
### Через install.ps1 (Windows)
```powershell
irm https://dcr.dexoron.su/install.ps1 | iex
```
Оба скрипта при запуске спрашивают:
- скачать готовый бинарник из GitHub Release
- или собрать проект из `git`
Релизные ассеты:
- `dcr-x86_64-unknown-linux-gnu`
- `dcr-x86_64-apple-darwin`
- `dcr-aarch64-apple-darwin`
- `dcr-x86_64-pc-windows-msvc.exe`
## Быстрый старт
Создать новый проект:
`dcr new hello`
Или инициализировать текущую директорию (директория должна быть пустой):
`dcr init`
Структура проекта:
```txt
hello/
- src/
- - main.c
- dcr.toml
```
Сборка и запуск проекта:
`dcr run` или `dcr run --release`
## Команды
### `dcr new <name>`
Создает проект в текущей директории с указанным именем.
### `dcr init`
Создает проект в текущей директории. Имя проекта будет равно имени директории. Директория должна быть пустой.
### `dcr build [profile]`
Собирает проект. Если профиль не указан, используется `--debug`.
### `dcr run [profile]`
Собирает проект и запускает бинарник. Если профиль не указан, используется `--debug`.
Запуск вручную:
`./target/<profile>/main`
### `dcr clean`
Удаляет папку `target` в корне проекта.
## Профили сборки
Поддерживаются два профиля:
- `--debug` (по умолчанию) — флаги: `-O0 -g -Wall -Wextra -fno-omit-frame-pointer -DDEBUG`
- `--release` — флаги: `-O3 -DNDEBUG -march=native`
## Конфигурация
Основной файл проекта — `dcr.toml`.
Пример `dcr.toml`:
```toml
[package]
name = "hello"
version = "0.1.0"
language = "c"
compiler = "clang"
[dependencies]
```
## Требования
- Rust toolchain (`rustc`, `cargo`) - Для ручной сборки DCR
- C-компилятор (`clang`, `gcc` или другие)
## Релизы
Релизы собираются автоматически через GitHub Actions (`.github/workflows/release.yml`) при пуше тега формата `v*`.
## Лицензия
См. файл `LICENSE`.

View File

@@ -13,27 +13,27 @@ function Fail($msg) { Write-Host "[ERROR] $msg" -ForegroundColor Red; exit 1 }
function Require-Cmd($name) {
if (-not (Get-Command $name -ErrorAction SilentlyContinue)) {
Fail "Не найдено: $name"
Fail "Not found: $name"
}
}
function Select-Mode {
Write-Host "Выбери способ установки:"
Write-Host " 1) Скачать готовый бинарник из GitHub Release (рекомендуется)"
Write-Host " 2) Собрать из git"
$choice = Read-Host "Введите 1 или 2 [1]"
Write-Host "Choose installation mode:"
Write-Host " 1) Download prebuilt binary from GitHub Release (recommended)"
Write-Host " 2) Build from git"
$choice = Read-Host "Enter 1 or 2 [1]"
if ([string]::IsNullOrWhiteSpace($choice)) { $choice = '1' }
switch ($choice) {
'1' { return 'release' }
'2' { return 'build' }
default { Fail 'Неизвестный вариант' }
default { Fail 'Unknown option' }
}
}
function Get-Target {
if ($env:PROCESSOR_ARCHITECTURE -ne 'AMD64') {
Fail "Поддерживается только x86_64 Windows, текущая архитектура: $env:PROCESSOR_ARCHITECTURE"
Fail "Only x86_64 Windows is supported, current architecture: $env:PROCESSOR_ARCHITECTURE"
}
return 'x86_64-pc-windows-msvc'
}
@@ -44,17 +44,17 @@ function Install-FromRelease {
New-Item -ItemType Directory -Path $InstallPath -Force | Out-Null
$assetName = "dcr-$target.exe"
Info "Получение последнего релиза..."
Info "Fetching latest release..."
$release = Invoke-RestMethod -Method Get -Uri $ApiUrl
$asset = $release.assets | Where-Object { $_.name -eq $assetName } | Select-Object -First 1
if (-not $asset) {
Fail "Не найден ассет $assetName в релизе $($release.tag_name)"
Fail "Asset $assetName not found in release $($release.tag_name)"
}
Info "Скачивание $assetName..."
Info "Downloading $assetName..."
Invoke-WebRequest -Uri $asset.browser_download_url -OutFile $BinaryPath
Ok "Скачан бинарник $assetName"
Ok "Binary downloaded: $assetName"
}
function Install-FromSource {
@@ -66,17 +66,17 @@ function Install-FromSource {
$tmp = Join-Path $env:TEMP 'dcr-install'
if (Test-Path $tmp) { Remove-Item -Recurse -Force $tmp }
Info 'Клонирование репозитория...'
Info 'Cloning repository...'
git clone --depth 1 $RepoUrl $tmp | Out-Null
Info 'Сборка release-бинарника...'
Info 'Building release binary...'
Push-Location $tmp
cargo build --release --target $target
Pop-Location
New-Item -ItemType Directory -Path $InstallPath -Force | Out-Null
Copy-Item (Join-Path $tmp "target\$target\release\dcr.exe") $BinaryPath -Force
Ok 'Установлен бинарник из исходников'
Ok 'Binary installed from source'
Remove-Item -Recurse -Force $tmp
}
@@ -93,13 +93,13 @@ function Setup-Path {
$newPath = if ($userPath) { "$userPath;$BinPath" } else { $BinPath }
[Environment]::SetEnvironmentVariable('Path', $newPath, 'User')
$env:Path = "$env:Path;$BinPath"
Warn "Добавлен путь в PATH: $BinPath"
Warn "Added path to PATH: $BinPath"
}
Ok "Команда dcr доступна через $linkPath"
Ok "dcr command is available via $linkPath"
}
Info 'Запуск установки DCR'
Info 'Starting DCR installation'
$mode = Select-Mode
$target = Get-Target
@@ -110,4 +110,4 @@ if ($mode -eq 'build') {
}
Setup-Path
Ok 'Установка завершена успешно'
Ok 'Installation completed successfully'

View File

@@ -22,12 +22,12 @@ success() { echo -e "${GREEN}✔ $1${NC}"; }
warn() { echo -e "${YELLOW}⚠ $1${NC}"; }
error() { echo -e "${RED}✖ $1${NC}"; }
trap 'error "Ошибка на строке $LINENO"; exit 1' ERR
trap 'error "Error on line $LINENO"; exit 1' ERR
check_os() {
case "$(uname -s)" in
Linux|Darwin) ;;
*) error "Поддерживаются только Linux и macOS"; exit 1 ;;
*) error "Only Linux and macOS are supported"; exit 1 ;;
esac
}
@@ -40,32 +40,32 @@ detect_target() {
Linux:x86_64) TARGET_TRIPLE="x86_64-unknown-linux-gnu" ;;
Darwin:x86_64) TARGET_TRIPLE="x86_64-apple-darwin" ;;
Darwin:arm64|Darwin:aarch64) TARGET_TRIPLE="aarch64-apple-darwin" ;;
*) error "Неподдерживаемая платформа: $os/$arch"; exit 1 ;;
*) error "Unsupported platform: $os/$arch"; exit 1 ;;
esac
ASSET_NAME="dcr-${TARGET_TRIPLE}"
}
check_common_dependencies() {
command -v curl >/dev/null 2>&1 || { error "curl не установлен"; exit 1; }
command -v curl >/dev/null 2>&1 || { error "curl is not installed"; exit 1; }
}
check_build_dependencies() {
command -v git >/dev/null 2>&1 || { error "git не установлен"; exit 1; }
command -v cargo >/dev/null 2>&1 || { error "cargo не установлен"; exit 1; }
command -v git >/dev/null 2>&1 || { error "git is not installed"; exit 1; }
command -v cargo >/dev/null 2>&1 || { error "cargo is not installed"; exit 1; }
}
prepare_sources() {
log "Получение исходников..."
log "Fetching sources..."
rm -rf "$TMPDIR"
git clone --depth 1 "$REPO_URL" "$TMPDIR"
success "Исходники получены"
success "Sources fetched"
}
build_binary() {
log "Сборка release-бинарника..."
log "Building release binary..."
(cd "$TMPDIR" && cargo build --release)
success "Сборка завершена"
success "Build completed"
}
fetch_latest_release_json() {
@@ -73,47 +73,47 @@ fetch_latest_release_json() {
}
download_binary() {
log "Получение последнего релиза..."
log "Fetching latest release..."
local release_json download_url tag
release_json="$(fetch_latest_release_json)"
tag="$(printf '%s\n' "$release_json" | sed -n 's/.*"tag_name": "\([^"]*\)".*/\1/p' | head -n1)"
if [[ -z "$tag" ]]; then
error "Не удалось определить версию релиза"
error "Failed to determine release version"
exit 1
fi
download_url="$(printf '%s\n' "$release_json" | sed -n "s#.*\"browser_download_url\": \"\([^\"]*${ASSET_NAME}\)\".*#\1#p" | head -n1)"
if [[ -z "$download_url" ]]; then
error "Не найден ассет ${ASSET_NAME} в релизе ${tag}"
error "Asset ${ASSET_NAME} not found in release ${tag}"
exit 1
fi
mkdir -p "$INSTALL_PATH"
curl -fL "$download_url" -o "$INSTALL_PATH/dcr"
chmod +x "$INSTALL_PATH/dcr"
success "Скачан бинарник ${ASSET_NAME} (${tag})"
success "Binary ${ASSET_NAME} downloaded (${tag})"
}
install_built_binary() {
mkdir -p "$INSTALL_PATH"
cp "$TMPDIR/target/release/dcr" "$INSTALL_PATH/dcr"
chmod +x "$INSTALL_PATH/dcr"
success "Установлен бинарник из исходников"
success "Binary installed from source"
}
install_link() {
log "Создание симлинка..."
log "Creating symlink..."
mkdir -p "$BINPATH"
ln -sf "$INSTALL_PATH/dcr" "$BINPATH/dcr"
success "Команда 'dcr' добавлена в $BINPATH"
success "Command 'dcr' added to $BINPATH"
}
check_path() {
if ! echo "$PATH" | grep -q "$BINPATH"; then
warn "Каталог $BINPATH не найден в PATH"
echo "Добавь в ~/.bashrc или ~/.zshrc:"
warn "Directory $BINPATH not found in PATH"
echo "Add this to ~/.bashrc or ~/.zshrc:"
echo "export PATH=\"$BINPATH:\$PATH\""
fi
}
@@ -123,20 +123,20 @@ cleanup() {
}
select_install_mode() {
echo "Выбери способ установки:"
echo " 1) Скачать готовый бинарник из GitHub Release (рекомендуется)"
echo " 2) Собрать из git"
read -r -p "Введите 1 или 2 [1]: " choice
echo "Choose installation mode:"
echo " 1) Download prebuilt binary from GitHub Release (recommended)"
echo " 2) Build from git"
read -r -p "Enter 1 or 2 [1]: " choice
case "${choice:-1}" in
1) INSTALL_MODE="release" ;;
2) INSTALL_MODE="build" ;;
*) error "Неизвестный вариант"; exit 1 ;;
*) error "Unknown option"; exit 1 ;;
esac
}
main() {
log "Запуск установки DCR"
log "Starting DCR installation"
check_os
detect_target
@@ -157,8 +157,8 @@ main() {
check_path
cleanup
success "Установка завершена успешно"
log "Лог сохранён в $LOGFILE"
success "Installation completed successfully"
log "Log saved to $LOGFILE"
}
main "$@"

View File

@@ -1,14 +1,13 @@
use crate::config::{PROFILE, PROJECT_COMPILER, flags};
use crate::utils::fs::check_dir;
use crate::utils::text::{BOLD, BRIGHT_GREEN, BRIGHT_RED, colored};
use crate::utils::log::{error, warn};
use crate::utils::text::{BOLD_GREEN, colored};
use std::fs;
use std::process::Command;
use std::time::Instant;
pub fn build(args: &[String]) -> i32 {
let mut active_profile = PROFILE.to_string();
let red_bold = BRIGHT_RED.to_owned() + BOLD;
let green_bold = BRIGHT_GREEN.to_owned() + BOLD;
let project_name = std::env::current_dir()
.ok()
.and_then(|p| p.file_name().map(|v| v.to_string_lossy().to_string()))
@@ -16,7 +15,7 @@ pub fn build(args: &[String]) -> i32 {
let items = check_dir(None).unwrap_or_default();
if !items.contains(&"dcr.toml".to_string()) {
println!("{}: не найден файл dcr.toml", colored("error", &red_bold));
error("dcr.toml file not found");
return 1;
}
@@ -26,20 +25,20 @@ pub fn build(args: &[String]) -> i32 {
if flags(candidate).is_some() {
active_profile = candidate.to_string();
} else {
println!("{}: неизвестный флаг сборки", colored("error", &red_bold));
warn("Unknown build flag");
return 1;
}
} else {
println!("{}: неизвестный аргумент", colored("error", &red_bold));
warn("Unknown argument");
return 1;
}
}
println!(
" Сборка проекта `{}`\n Профиль: {}\n Компилятор: {}\n",
colored(&project_name, &green_bold),
colored(&active_profile, &green_bold),
colored(PROJECT_COMPILER, &green_bold)
" Building project `{}`\n Profile: {}\n Compiler: {}\n",
colored(&project_name, BOLD_GREEN),
colored(&active_profile, BOLD_GREEN),
colored(PROJECT_COMPILER, BOLD_GREEN)
);
if !items.contains(&"target".to_string()) {
@@ -65,14 +64,14 @@ pub fn build(args: &[String]) -> i32 {
Ok(status) if status.success() => {
let times = ((start_time.elapsed().as_secs_f64() * 100.0).trunc()) / 100.0;
println!(
" {} Сборка завершена успешно, за {} секунд",
colored("✔", &green_bold),
colored(&times.to_string(), &green_bold)
" {} Build completed successfully in {} seconds",
colored("✔", BOLD_GREEN),
colored(&times.to_string(), BOLD_GREEN)
);
return 0;
}
_ => {
println!("{}: сборка не удалась", colored("error", &red_bold));
error("Build failed");
return 1;
}
}

View File

@@ -1,13 +1,10 @@
use crate::config::flags;
use crate::utils::fs::check_dir;
use crate::utils::text::{BOLD, BRIGHT_GREEN, BRIGHT_RED, BRIGHT_YELLOW, colored};
use crate::utils::log::{error, warn};
use crate::utils::text::{BOLD_GREEN, colored};
use std::fs;
pub fn clean(args: &[String]) -> i32 {
let red_bold = BRIGHT_RED.to_owned() + BOLD;
let green_bold = BRIGHT_GREEN.to_owned() + BOLD;
let yellow_bold = BRIGHT_YELLOW.to_owned() + BOLD;
let project_name = std::env::current_dir()
.ok()
.and_then(|p| p.file_name().map(|v| v.to_string_lossy().to_string()))
@@ -15,23 +12,20 @@ pub fn clean(args: &[String]) -> i32 {
let items = check_dir(None).unwrap_or_default();
if args.len() > 1 {
println!("{}: неизвестный аргумент", colored("error", &red_bold));
error("Unknown argument");
return 1;
}
if !items.contains(&"dcr.toml".to_string()) {
println!("{}: не найден файл dcr.toml", colored("error", &red_bold));
error("dcr.toml file not found");
return 1;
}
println!(
" Очистка проекта `{}`",
colored(&project_name, &green_bold)
" Cleaning project `{}`",
colored(&project_name, BOLD_GREEN)
);
if !items.contains(&"target".to_string()) {
println!(
"{}: директория target не найдена",
colored("warn", &yellow_bold)
);
warn("Directory target not found");
return 1;
}
@@ -41,32 +35,29 @@ pub fn clean(args: &[String]) -> i32 {
profile = profile.trim_start_matches("--").to_string();
}
if flags(&profile).is_none() {
println!("{}: неизвестный профиль", colored("error", &red_bold));
error("Unknown profile");
return 1;
}
let target_items = check_dir(Some("target")).unwrap_or_default();
if !target_items.contains(&profile) {
println!(
"{}: директория target/{profile} не найдена",
colored("warn", &yellow_bold)
);
warn(&format!("Directory target/{profile} not found"));
return 1;
}
println!(" Профиль: {}", colored(&profile, &green_bold));
println!(" Profile: {}", colored(&profile, BOLD_GREEN));
let _ = fs::remove_dir_all(format!("target/{profile}"));
println!(
"{} Удалена директория target/{profile}",
colored("\n ✔", &green_bold)
"{} Removed directory target/{profile}",
colored("\n ✔", BOLD_GREEN)
);
return 0;
}
let _ = fs::remove_dir_all("target");
println!(
"{} Удалена директория target",
colored("\n ✔", &green_bold)
"{} Removed directory target",
colored("\n ✔", BOLD_GREEN)
);
0
}

View File

@@ -1,3 +1,4 @@
use crate::utils::log::{error, warn};
use reqwest::blocking::Client;
use serde::Deserialize;
use std::fs;
@@ -20,7 +21,7 @@ struct ReleaseAsset {
pub fn flag_update(args: &[String]) -> i32 {
if !args.is_empty() {
println!("Ошибка: команда не поддежривает аргументы");
warn("Command does not support additional arguments");
return 1;
}
@@ -29,7 +30,7 @@ pub fn flag_update(args: &[String]) -> i32 {
let client = match Client::builder().user_agent("dcr-updater").build() {
Ok(client) => client,
Err(_) => {
println!("Ошибка: не удалось инициализировать HTTP клиент");
error("Failed to initialize HTTP client");
return 1;
}
};
@@ -37,14 +38,14 @@ pub fn flag_update(args: &[String]) -> i32 {
let release = match fetch_latest_release(&client) {
Ok(release) => release,
Err(err) => {
println!("Ошибка: не удалось проверить обновления: {err}");
error(&format!("Failed to check for updates: {err}"));
return 1;
}
};
let latest_version = release.tag_name.trim_start_matches('v');
if latest_version == current_version {
println!("Установлена последняя версия: {current_version}");
println!("Latest version is already installed: {current_version}");
return 0;
}
@@ -54,14 +55,14 @@ pub fn flag_update(args: &[String]) -> i32 {
.iter()
.find(|asset| candidate_names.iter().any(|name| name == &asset.name))
else {
println!("Ошибка: не найден бинарник для таргета {target}");
error(&format!("Binary for target {target} not found"));
return 1;
};
let bytes = match download_asset(&client, &asset.browser_download_url) {
Ok(bytes) => bytes,
Err(err) => {
println!("Ошибка: не удалось скачать обновление: {err}");
error(&format!("Failed to download update: {err}"));
return 1;
}
};
@@ -69,26 +70,26 @@ pub fn flag_update(args: &[String]) -> i32 {
let current_exe = match std::env::current_exe() {
Ok(path) => path,
Err(_) => {
println!("Ошибка: не удалось определить путь текущего бинарника");
error("Failed to resolve current binary path");
return 1;
}
};
let temp_path = temp_binary_path(&current_exe);
if fs::write(&temp_path, &bytes).is_err() {
println!("Ошибка: не удалось записать временный бинарник");
error("Failed to write temporary binary");
return 1;
}
set_executable_permissions(&temp_path);
if self_replace::self_replace(&temp_path).is_err() {
let _ = fs::remove_file(&temp_path);
println!("Ошибка: не удалось заменить текущий бинарник");
error("Failed to replace current binary");
return 1;
}
let _ = fs::remove_file(&temp_path);
println!("Обновление завершено: {current_version} -> {latest_version}");
println!("Update completed: {current_version} -> {latest_version}");
0
}
@@ -96,31 +97,31 @@ fn fetch_latest_release(client: &Client) -> Result<Release, String> {
let response = client
.get(LATEST_RELEASE_URL)
.send()
.map_err(|_| "запрос к GitHub API завершился ошибкой".to_string())?;
.map_err(|_| "GitHub API request failed".to_string())?;
if !response.status().is_success() {
return Err(format!("GitHub API вернул статус {}", response.status()));
return Err(format!("GitHub API returned status {}", response.status()));
}
response
.json::<Release>()
.map_err(|_| "ответ GitHub API имеет неожиданный формат".to_string())
.map_err(|_| "GitHub API response has an unexpected format".to_string())
}
fn download_asset(client: &Client, url: &str) -> Result<Vec<u8>, String> {
let response = client
.get(url)
.send()
.map_err(|_| "запрос на скачивание завершился ошибкой".to_string())?;
.map_err(|_| "Download request failed".to_string())?;
if !response.status().is_success() {
return Err(format!("скачивание вернуло статус {}", response.status()));
return Err(format!("Download returned status {}", response.status()));
}
response
.bytes()
.map(|bytes| bytes.to_vec())
.map_err(|_| "не удалось прочитать скачанные данные".to_string())
.map_err(|_| "Failed to read downloaded data".to_string())
}
fn asset_candidates(target: &str) -> Vec<String> {

View File

@@ -1,36 +1,33 @@
use crate::utils::text::{BOLD, BRIGHT_CYAN, BRIGHT_GREEN, colored};
use crate::utils::text::{BOLD_CYAN, BOLD_GREEN, printc};
pub fn help() -> i32 {
let green_bold = BRIGHT_GREEN.to_owned() + BOLD;
let cyan_bold = BRIGHT_CYAN.to_owned() + BOLD;
println!("DCR (Dexoron Cargo Realization)");
println!("Менеджер C-проектов, вдохновленный Cargo.");
println!("C project manager inspired by Cargo.");
println!();
println!("{}", colored("ИСПОЛЬЗОВАНИЕ:", &green_bold));
println!("{}", colored(" dcr <команда> [опции]", &cyan_bold));
printc("USAGE:", BOLD_GREEN);
printc(" dcr <command> [options]", BOLD_CYAN);
println!();
println!("{}", colored("КОМАНДЫ:", &green_bold));
println!(" new <name> Создать новый проект");
println!(" init Инициализировать текущую директорию как проект");
println!(" build [--profile] Собрать проект (по умолчанию: --debug)");
println!(" run [--profile] Собрать и запустить (по умолчанию: --debug)");
println!(" clean Удалить директорию target");
println!("{}", colored("ФЛАГИ:", &green_bold));
println!(" --help Показать справку по команде");
println!(" --update Обновить dcr до актуальной версии");
println!(" --version Показать версию dcr");
printc("COMMANDS:", BOLD_GREEN);
println!(" new <name> Create a new project");
println!(" init Initialize the current directory as a project");
println!(" build [--profile] Build the project (default: --debug)");
println!(" run [--profile] Build and run the project (default: --debug)");
println!(" clean Remove the target directory");
printc("FLAGS:", BOLD_GREEN);
println!(" --help Show command help");
println!(" --update Update dcr to the latest version");
println!(" --version Show dcr version");
println!();
println!("{}", colored("ОПЦИИ:", &green_bold));
println!(" --debug Сборка с профилем debug");
println!(" --release Сборка с профилем release");
printc("OPTIONS:", BOLD_GREEN);
println!(" --debug Build with debug profile");
println!(" --release Build with release profile");
println!();
println!("{}", colored("ПРИМЕРЫ:", &green_bold));
println!("{}", colored(" dcr new hello", &cyan_bold));
println!("{}", colored(" dcr build --release", &cyan_bold));
println!("{}", colored(" dcr run --debug", &cyan_bold));
printc("EXAMPLES:", BOLD_GREEN);
printc(" dcr new hello", BOLD_CYAN);
printc(" dcr build --release", BOLD_CYAN);
printc(" dcr run --debug", BOLD_CYAN);
println!();
println!("{}", colored("ПОДСКАЗКА:", &green_bold));
println!(" Запусти 'dcr <команда> --help' для справки по команде.");
printc("TIP:", BOLD_GREEN);
println!(" Run 'dcr <command> --help' for command-specific help.");
0
}

View File

@@ -1,19 +1,13 @@
use crate::config::{FILE_MAIN_C, file_dcr_toml};
use crate::utils::fs::check_dir;
use crate::utils::text::{BOLD, BRIGHT_CYAN, BRIGHT_GREEN, BRIGHT_RED, colored, printc};
use crate::utils::log::{error, warn};
use crate::utils::text::{BOLD_CYAN, BOLD_GREEN, colored, printc};
use std::fs;
use std::io::Write;
pub fn init(args: &[String]) -> i32 {
let red_bold = BRIGHT_RED.to_owned() + BOLD;
let green_bold = BRIGHT_GREEN.to_owned() + BOLD;
let cyan_bold = BRIGHT_CYAN.to_owned() + BOLD;
if !args.is_empty() {
println!(
"{}: команда не поддерживает доп. аргументы",
colored("error", &red_bold)
);
warn("Command does not support additional arguments");
return 1;
}
@@ -24,22 +18,19 @@ pub fn init(args: &[String]) -> i32 {
.unwrap_or_else(|| "project".to_string());
if !items.is_empty() {
println!("{}: директория не пуста", colored("error", &red_bold));
error("Directory not empty");
return 1;
}
let cwd = std::env::current_dir()
.map(|v| v.to_string_lossy().to_string())
.unwrap_or_else(|_| ".".to_string());
println!("Инициализация проекта в {cwd}");
println!("Initializing the project in {cwd}");
let mut dcr_toml = match fs::File::create("./dcr.toml") {
Ok(file) => file,
Err(_) => {
println!(
"{}: не удалось создать dcr.toml",
colored("error", &red_bold)
);
error("Failed to create dcr.toml");
return 1;
}
};
@@ -47,50 +38,41 @@ pub fn init(args: &[String]) -> i32 {
.write_all(file_dcr_toml(&project_name).as_bytes())
.is_err()
{
println!(
"{}: не удалось записать dcr.toml",
colored("error", &red_bold)
);
error("Failed to write dcr.toml");
return 1;
}
println!(
" {} Создан файл {}",
colored("✔", &green_bold),
colored("dcr.toml", &cyan_bold)
" {} Created file {}",
colored("✔", BOLD_CYAN),
colored("dcr.toml", BOLD_CYAN)
);
if fs::create_dir("src").is_err() {
println!("{}: не удалось создать src", colored("error", &red_bold));
error("Failed to create src/");
return 1;
}
let mut main_c = match fs::File::create("./src/main.c") {
Ok(file) => file,
Err(_) => {
println!(
"{}: не удалось создать src/main.c",
colored("error", &red_bold)
);
error("Failed to create src/main.c");
return 1;
}
};
if main_c.write_all(FILE_MAIN_C.as_bytes()).is_err() {
println!(
"{}: не удалось записать src/main.c",
colored("error", &red_bold)
);
error("Failed to write src/main.c");
return 1;
}
println!(
" {} Создан файл {}\n",
colored("✔", &green_bold),
colored("src/main.c", &cyan_bold)
" {} Created file {}\n",
colored("✔", BOLD_GREEN),
colored("src/main.c", BOLD_CYAN)
);
println!(
"Проект `{}` успешно создан\n",
colored(&project_name, &green_bold)
"Project `{}` successfully created\n",
colored(project_name.as_str(), BOLD_GREEN)
);
printc("Следуюший шаг:", &green_bold);
printc(" dcr run", &cyan_bold);
printc("Next step:", BOLD_GREEN);
printc(" cd {}\n dcr run", project_name.as_str());
0
}

View File

@@ -1,60 +1,48 @@
use crate::config::{FILE_MAIN_C, file_dcr_toml};
use crate::utils::fs::check_dir;
use crate::utils::text::{BOLD, BRIGHT_CYAN, BRIGHT_GREEN, BRIGHT_RED, colored, printc};
use crate::utils::log::{error, warn};
use crate::utils::text::{BOLD_CYAN, BOLD_GREEN, colored, printc};
use std::fs;
use std::io::Write;
pub fn new(args: &[String]) -> i32 {
let items = check_dir(None).unwrap_or_default();
let red_bold = BRIGHT_RED.to_owned() + BOLD;
let green_bold = BRIGHT_GREEN.to_owned() + BOLD;
let cyan_bold = BRIGHT_CYAN.to_owned() + BOLD;
if args.is_empty() {
println!(
"{}: не указанно название проекта",
colored("error", &red_bold)
);
error("Project name not specified");
return 1;
}
if args.len() > 1 {
println!(
"{}: команда не поддерживает доп. аргументы",
colored("error", &red_bold)
);
warn("Command does not support additional arguments");
return 1;
}
let project_name = &args[0];
println!(
"Создание проекта `{}`...",
colored(project_name, &green_bold)
"Creating a Project `{}`...",
colored(project_name, BOLD_CYAN)
);
if items.contains(project_name) {
error(&format!(
"Directory `{}` already exists\n",
colored(project_name, BOLD_CYAN)
));
printc("Подсказка:", BOLD_CYAN);
println!(
"{}: директория `{}` уже существует\n",
colored("error", &red_bold),
colored(project_name, &green_bold)
);
printc("Подсказка:", &green_bold);
println!(
" Используй `{}` для инициализации существующего проекта\n или задай другое имя проекта",
colored("dcr init", &cyan_bold)
" Use `{}` to initialize an existing project\n or specify a different project name",
colored("dcr init", BOLD_CYAN)
);
return 1;
}
if fs::create_dir(project_name).is_err() {
println!(
"{}: не удалось создать директорию",
colored("error", &red_bold)
);
error("Failed to create directory");
return 1;
}
println!(
" {} Создана директория {}",
colored("✔", &green_bold),
" {} Directory created {}",
colored("✔", BOLD_CYAN),
project_name
);
@@ -62,10 +50,7 @@ pub fn new(args: &[String]) -> i32 {
let mut dcr_toml = match fs::File::create(&toml_path) {
Ok(file) => file,
Err(_) => {
println!(
"{}: не удалось создать dcr.toml",
colored("error", &red_bold)
);
error("Failed to create dcr.toml");
return 1;
}
};
@@ -73,51 +58,42 @@ pub fn new(args: &[String]) -> i32 {
.write_all(file_dcr_toml(project_name).as_bytes())
.is_err()
{
println!(
"{}: не удалось записать dcr.toml",
colored("error", &red_bold)
);
error("Failed to write dcr.toml");
return 1;
}
println!(
" {} Создан файл {}",
colored("✔", &green_bold),
colored("dcr.toml", &cyan_bold)
" {} Created file {}",
colored("✔", BOLD_CYAN),
colored("dcr.toml", BOLD_CYAN)
);
if fs::create_dir_all(format!("./{project_name}/src")).is_err() {
println!("{}: не удалось создать src", colored("error", &red_bold));
error("Failed to create src/");
return 1;
}
let main_c_path = format!("./{project_name}/src/main.c");
let mut main_c = match fs::File::create(&main_c_path) {
Ok(file) => file,
Err(_) => {
println!(
"{}: не удалось создать src/main.c",
colored("error", &red_bold)
);
error("Failed to create src/main.c");
return 1;
}
};
if main_c.write_all(FILE_MAIN_C.as_bytes()).is_err() {
println!(
"{}: не удалось записать src/main.c",
colored("error", &red_bold)
);
error("Failed to write src/main.c");
return 1;
}
println!(
" {} Создан файл {}\n",
colored("✔", &green_bold),
colored("src/main.c", &cyan_bold)
" {} Created file {}\n",
colored("✔", BOLD_GREEN),
colored("src/main.c", BOLD_CYAN)
);
println!(
"Проект `{}` успешно создан\n",
colored(project_name, &green_bold)
"Project `{}` successfully created\n",
colored(project_name, BOLD_GREEN)
);
printc("Следуюший шаг:", &green_bold);
printc(&format!(" cd {project_name}\n dcr run"), &cyan_bold);
printc("Next step:", BOLD_GREEN);
printc(" cd {}\n dcr run", project_name);
0
}

View File

@@ -1,16 +1,16 @@
use crate::cli::build::build;
use crate::config::{PROFILE, flags};
use crate::utils::fs::check_dir;
use crate::utils::text::{BOLD, BRIGHT_RED, colored};
use crate::utils::log::{error, warn};
use crate::utils::text::{BOLD_GREEN, colored};
use std::process::Command;
pub fn run(args: &[String]) -> i32 {
let red_bold = BRIGHT_RED.to_owned() + BOLD;
let mut active_profile = PROFILE.to_string();
let items = check_dir(None).unwrap_or_default();
if !items.contains(&"dcr.toml".to_string()) {
println!("{}: не найден файл dcr.toml", colored("error", &red_bold));
error("dcr.toml file not found");
return 1;
}
@@ -20,18 +20,21 @@ pub fn run(args: &[String]) -> i32 {
if flags(candidate).is_some() {
active_profile = candidate.to_string();
} else {
println!("{}: неизвестный флаг сборки", colored("error", &red_bold));
warn("Unknown build flag");
return 1;
}
} else {
println!("{}: неизвестный аргумент", colored("error", &red_bold));
warn("Unknown argument");
return 1;
}
}
let build_status = build(args);
if build_status == 0 {
println!("\n Запуск target/{active_profile}/main");
println!(
"\n {} target/{active_profile}/main",
colored("Running", BOLD_GREEN)
);
println!("--------------------------------");
return Command::new(format!("./target/{active_profile}/main"))
.status()
@@ -43,13 +46,13 @@ pub fn run(args: &[String]) -> i32 {
.unwrap_or_default()
.contains(&active_profile)
{
println!("Запуск последнего релиза");
warn("Launch of the latest release");
return Command::new(format!("./target/{active_profile}/main"))
.status()
.map(|status| status.code().unwrap_or(1))
.unwrap_or(1);
}
println!("Исправьте ошибки в коде для запуска проекта");
error("Fix errors in the code to run the project");
0
}

View File

@@ -1,3 +1,4 @@
use crate::utils::log::error;
mod cli;
mod config;
mod utils;
@@ -25,7 +26,7 @@ fn main() {
"--help" => cli::help::help(),
"--update" => cli::flag_update::flag_update(rest),
_ => {
println!("Неизвестная команда или аргумент");
error("Unknown command or argument");
0
}
};

View File

@@ -1,6 +1,7 @@
use std::io;
use std::path::PathBuf;
#[allow(dead_code)]
pub fn check_dir(dir: Option<&str>) -> io::Result<Vec<String>> {
let path: PathBuf = match dir {
None | Some(".") | Some("./") => std::env::current_dir()?,

View File

@@ -1,30 +1,24 @@
use crate::utils::text::{BOLD, BRIGHT_GREEN, BRIGHT_RED, BRIGHT_YELLOW, colored};
use crate::utils::text::{BOLD_CYAN, colored};
#[allow(dead_code)]
pub fn error(msg: &str) {
println!(
"{}: {msg}",
colored("error", &(BRIGHT_RED.to_owned() + BOLD))
);
println!("{}: {msg}", colored("error", BOLD_CYAN),);
}
#[allow(dead_code)]
pub fn warn(msg: &str) {
println!(
"{}: {msg}",
colored("warn", &(BRIGHT_YELLOW.to_owned() + BOLD))
);
println!("{}: {msg}", colored("warn", BOLD_CYAN),);
}
#[allow(dead_code)]
pub fn info(msg: &str) {
println!("{}: {msg}", colored("info", BOLD));
}
#[allow(dead_code)]
pub fn ok(msg: &str) {
println!(
"{}: {msg}",
colored("ok", &(BRIGHT_GREEN.to_owned() + BOLD))
);
}
// #[allow(dead_code)]
// pub fn info(msg: &str) {
// println!("{}: {msg}", colored("info", BOLD));
// }
//
// #[allow(dead_code)]
// pub fn ok(msg: &str) {
// println!(
// "{}: {msg}",
// colored("ok", &(BRIGHT_GREEN.to_owned() + BOLD))
// );
// }

View File

@@ -1,16 +1,32 @@
#[allow(dead_code)]
pub const RESET: &str = "\x1b[0m";
#[allow(dead_code)]
pub const BOLD: &str = "\x1b[1m";
#[allow(dead_code)]
pub const BRIGHT_RED: &str = "\x1b[91m";
#[allow(dead_code)]
pub const BRIGHT_GREEN: &str = "\x1b[92m";
#[allow(dead_code)]
pub const BRIGHT_YELLOW: &str = "\x1b[93m";
#[allow(dead_code)]
pub const BRIGHT_CYAN: &str = "\x1b[96m";
#[allow(dead_code)]
pub const BOLD_RED: &str = "\x1b[1m\x1b[91m";
#[allow(dead_code)]
pub const BOLD_GREEN: &str = "\x1b[1m\x1b[92m";
#[allow(dead_code)]
pub const BOLD_YELLOW: &str = "\x1b[1m\x1b[93m";
#[allow(dead_code)]
pub const BOLD_CYAN: &str = "\x1b[1m\x1b[96m";
#[allow(dead_code)]
pub fn colored(msg: &str, style: &str) -> String {
format!("{style}{msg}{RESET}")
}
#[allow(dead_code)]
pub fn printc(msg: &str, style: &str) {
println!("{style}{msg}{RESET}");
}