Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
132 changes: 126 additions & 6 deletions .github/workflows/release.yml
Original file line number Diff line number Diff line change
@@ -1,12 +1,13 @@
name: Publish to PyPI
name: Release

on:
release:
types: [published]
workflow_dispatch:

jobs:
build:
build-python:
name: Build Python package
runs-on: ubuntu-latest
permissions:
contents: read
Expand All @@ -27,21 +28,140 @@ jobs:
- name: Upload artifact
uses: actions/upload-artifact@v4
with:
name: dist
name: python-dist
path: dist/

publish:
needs: build
build-deb:
name: Build .deb (${{ matrix.arch }})
runs-on: ${{ matrix.runner }}
permissions:
contents: read
strategy:
matrix:
include:
# Build on Ubuntu 22.04 for max compatibility
# Works on Ubuntu 22.04+, Debian 12+
- arch: amd64
runner: ubuntu-22.04
- arch: arm64
runner: ubuntu-22.04-arm
steps:
- uses: actions/checkout@v4

- name: Install build dependencies
run: ./scripts/build-deb.sh --install-deps

- name: Update changelog for release
run: |
# Get version from tag or pyproject.toml
if [ -n "${{ github.event.release.tag_name }}" ]; then
VERSION="${{ github.event.release.tag_name }}"
VERSION="${VERSION#v}" # Remove 'v' prefix if present
else
VERSION=$(grep '^version = ' pyproject.toml | sed 's/version = "\(.*\)"/\1/')
fi

# Update changelog version
sed -i "s/cortex-linux ([^)]*)/cortex-linux ($VERSION)/" debian/changelog

Comment on lines +54 to +66
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major

Add robust version extraction + validation in release workflow.
The current grep/sed can return empty or wrong VERSION, leading to a malformed changelog and bad package versioning during releases.

✅ Suggested fix
       - name: Update changelog for release
         run: |
+          set -euo pipefail
           # Get version from tag or pyproject.toml
           if [ -n "${{ github.event.release.tag_name }}" ]; then
             VERSION="${{ github.event.release.tag_name }}"
             VERSION="${VERSION#v}"  # Remove 'v' prefix if present
           else
-            VERSION=$(grep '^version = ' pyproject.toml | sed 's/version = "\(.*\)"/\1/')
+            VERSION=$(
+              awk '
+                /^\[project\]/{in_proj=1; next}
+                /^\[/{in_proj=0}
+                in_proj && $0 ~ /^version[[:space:]]*=/ {
+                  if (match($0, /"([^"]+)"/, m)) { print m[1]; exit }
+                }
+              ' pyproject.toml
+            )
           fi
+          if [ -z "${VERSION:-}" ]; then
+            echo "Error: version not found in [project] section of pyproject.toml" >&2
+            exit 1
+          fi
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
- name: Update changelog for release
run: |
# Get version from tag or pyproject.toml
if [ -n "${{ github.event.release.tag_name }}" ]; then
VERSION="${{ github.event.release.tag_name }}"
VERSION="${VERSION#v}" # Remove 'v' prefix if present
else
VERSION=$(grep '^version = ' pyproject.toml | sed 's/version = "\(.*\)"/\1/')
fi
# Update changelog version
sed -i "s/cortex-linux ([^)]*)/cortex-linux ($VERSION)/" debian/changelog
- name: Update changelog for release
run: |
set -euo pipefail
# Get version from tag or pyproject.toml
if [ -n "${{ github.event.release.tag_name }}" ]; then
VERSION="${{ github.event.release.tag_name }}"
VERSION="${VERSION#v}" # Remove 'v' prefix if present
else
VERSION=$(
awk '
/^\[project\]/{in_proj=1; next}
/^\[/{in_proj=0}
in_proj && $0 ~ /^version[[:space:]]*=/ {
if (match($0, /"([^"]+)"/, m)) { print m[1]; exit }
}
' pyproject.toml
)
fi
if [ -z "${VERSION:-}" ]; then
echo "Error: version not found in [project] section of pyproject.toml" >&2
exit 1
fi
# Update changelog version
sed -i "s/cortex-linux ([^)]*)/cortex-linux ($VERSION)/" debian/changelog
🤖 Prompt for AI Agents
In @.github/workflows/release.yml around lines 54 - 66, The workflow currently
sets VERSION from github.event.release.tag_name or by grepping pyproject.toml
but doesn’t validate it; update the release step to robustly extract and
validate VERSION: when reading RELEASE tag (github.event.release.tag_name) strip
any leading "v" into VERSION and validate against a semantic-version regex, and
when falling back to pyproject.toml parse the file reliably (e.g., using a small
python/toml parse) to populate VERSION; if VERSION is empty or fails the regex,
fail the job with a clear error instead of proceeding; finally, use the
validated VERSION in the sed replacement that updates debian/changelog (the sed
-i "s/cortex-linux ([^)]*)/cortex-linux ($VERSION)/" line).

# Set distribution to jammy (built on 22.04 for compatibility)
sed -i "s/) unstable;/) jammy;/" debian/changelog

- name: Build .deb package
run: ./scripts/build-deb.sh --no-sign

- name: Upload artifact
uses: actions/upload-artifact@v4
with:
name: deb-${{ matrix.arch }}
path: dist/*.deb

publish-pypi:
needs: build-python
runs-on: ubuntu-latest
if: github.event_name == 'release'
environment: pypi
permissions:
id-token: write
steps:
- name: Download artifact
uses: actions/download-artifact@v4
with:
name: dist
name: python-dist
path: dist/

- name: Publish to PyPI
uses: pypa/gh-action-pypi-publish@release/v1

upload-release-assets:
needs: [build-python, build-deb]
runs-on: ubuntu-latest
if: github.event_name == 'release'
permissions:
contents: write
steps:
- name: Download all artifacts
uses: actions/download-artifact@v4
with:
path: artifacts/

- name: Upload to GitHub Release
uses: softprops/action-gh-release@v2
with:
files: |
artifacts/python-dist/*
artifacts/deb-*/*.deb
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}

# ========================================================================
# Trigger APT Repository Update
# ========================================================================
# This sends a repository_dispatch event to the apt-repo with package URLs
# The apt-repo will download, commit (LFS), and deploy to GitHub Pages
trigger-apt-repo:
needs: upload-release-assets
runs-on: ubuntu-latest
permissions:
contents: read
if: github.event_name == 'release'
steps:
- name: Download deb artifacts
uses: actions/download-artifact@v4
with:
pattern: deb-*
path: release/
merge-multiple: true

- name: Get package info for APT repo
id: packages
run: |
cd release
# Build JSON array of packages with metadata
PACKAGES="[]"
for deb in *.deb; do
if [ -f "$deb" ]; then
# Extract package name and version from filename
PKG_NAME=$(echo "$deb" | sed 's/_.*//')
URL="https://github.com/${{ github.repository }}/releases/download/${{ github.ref_name }}/${deb}"
PACKAGES=$(echo "$PACKAGES" | jq --arg name "$PKG_NAME" --arg url "$URL" --arg file "$deb" \
'. += [{"name": $name, "url": $url, "file": $file}]')
fi
done
echo "packages=$PACKAGES" >> $GITHUB_OUTPUT
echo "📦 Packages to publish: $PACKAGES"

- name: Trigger APT Repository Update
if: steps.packages.outputs.packages != '[]'
uses: peter-evans/repository-dispatch@v3
with:
token: ${{ secrets.APT_REPO_PAT }}
repository: cortexlinux/apt-repo
event-type: add-packages
client-payload: |
{
"packages": ${{ steps.packages.outputs.packages }},
"version": "${{ github.ref_name }}",
"suite": "cortex",
"source_repo": "${{ github.repository }}"
}
11 changes: 11 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -59,3 +59,14 @@ htmlcov/
*.log
logs/
coverage.xml

# Debian packaging
debian/cortex-linux/
debian/.debhelper/
debian/debhelper-build-stamp
debian/files
debian/*.substvars
debian/*.debhelper
*.deb
*.buildinfo
*.changes
3 changes: 1 addition & 2 deletions MANIFEST.in
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
include README.md
include LICENSE
recursive-include LLM *.py
recursive-include cortex *.py
include LLM/requirements.txt
recursive-include cortex/i18n/locales *.yaml
36 changes: 28 additions & 8 deletions Makefile
Original file line number Diff line number Diff line change
@@ -1,19 +1,25 @@
# Cortex Linux - Developer Makefile
# Usage: make [target]

.PHONY: dev test lint format check clean help
.PHONY: dev test lint format check clean help deb deb-deps deb-install deb-clean

PYTHON ?= python3

help:
@echo "Cortex Linux - Development Commands"
@echo ""
@echo " make dev Install development dependencies"
@echo " make test Run test suite"
@echo " make lint Run linters (ruff, black check)"
@echo " make format Auto-format code"
@echo " make check Run all checks (format + lint + test)"
@echo " make clean Remove build artifacts"
@echo " make dev Install development dependencies"
@echo " make test Run test suite"
@echo " make lint Run linters (ruff, black check)"
@echo " make format Auto-format code"
@echo " make check Run all checks (format + lint + test)"
@echo " make clean Remove build artifacts"
@echo ""
@echo "Debian Packaging:"
@echo " make deb-deps Install .deb build dependencies"
@echo " make deb Build .deb package"
@echo " make deb-install Build and install .deb package"
@echo " make deb-clean Clean debian build artifacts"
@echo ""

dev:
Expand Down Expand Up @@ -42,4 +48,18 @@ clean:
rm -rf build/ dist/ *.egg-info/
find . -type d -name __pycache__ -exec rm -rf {} + 2>/dev/null || true
find . -type f -name "*.pyc" -delete
@echo "✅ Cleaned"
@echo "Cleaned"

# Debian packaging targets
deb-deps:
./scripts/build-deb.sh --install-deps

deb:
./scripts/build-deb.sh --no-sign

deb-install: deb
sudo dpkg -i dist/*.deb || sudo apt-get install -f -y
@echo "Package installed"

deb-clean:
./scripts/build-deb.sh --clean
9 changes: 9 additions & 0 deletions debian/changelog
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
cortex-linux (0.1.0) unstable; urgency=medium

* Initial release.
* AI-powered package manager with natural language support
* Multiple LLM provider support (Anthropic, OpenAI)
* Secure sandbox execution environment
* Rich terminal UI with interactive dashboard

-- Cortex Linux <mike@cortexlinux.com> Tue, 21 Jan 2025 00:00:00 +0000
29 changes: 29 additions & 0 deletions debian/control
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
Source: cortex-linux
Section: admin
Priority: optional
Maintainer: Cortex Linux <mike@cortexlinux.com>
Build-Depends: debhelper-compat (= 13),
dh-virtualenv (>= 1.2),
python3,
python3-dev,
python3-venv,
python3-pip,
python3-setuptools
Standards-Version: 4.6.0
Homepage: https://github.com/cortexlinux/cortex
Vcs-Browser: https://github.com/cortexlinux/cortex
Vcs-Git: https://github.com/cortexlinux/cortex.git

Package: cortex-linux
Architecture: any
Depends: ${misc:Depends}, python3
Description: AI-powered package manager for Debian/Ubuntu
Cortex is an AI-powered package manager that understands natural language
commands for installing, updating, and managing packages on Debian and
Ubuntu systems.
.
Features:
- Natural language package management
- AI-assisted dependency resolution
- Hardware profiling for optimal package selection
- Integration with apt, snap, and flatpak
27 changes: 27 additions & 0 deletions debian/copyright
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
Format: https://www.debian.org/doc/packaging-manuals/copyright-format/1.0/
Upstream-Name: cortex-linux
Upstream-Contact: Cortex Linux <mike@cortexlinux.com>
Source: https://github.com/cortexlinux/cortex

Files: *
Copyright: 2024-2025 Cortex Linux
License: BUSL-1.1

License: BUSL-1.1
Business Source License 1.1
.
Licensor: Cortex Linux
.
Licensed Work: Cortex
.
Additional Use Grant: None
.
Change Date: Four years from the date the Licensed Work is published.
.
Change License: Apache License, Version 2.0
.
For information about the Business Source License, please see
https://mariadb.com/bsl11/
.
The full license text is available in the LICENSE file in the source
distribution or at https://github.com/cortexlinux/cortex/blob/main/LICENSE
1 change: 1 addition & 0 deletions debian/cortex-linux.links
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
opt/venvs/cortex-linux/bin/cortex usr/bin/cortex
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🔴 Critical

Scope the symlink to cortex-linux to avoid package file conflicts.

Line 1 in debian/links will be applied to all binary packages, so cortexd will also ship /usr/bin/cortex, causing a dpkg conflict if both packages are installed. Move this to a package-specific links file.

🔧 Proposed fix
- opt/venvs/cortex-linux/bin/cortex usr/bin/cortex

Create a new file: debian/cortex-linux.links with:

opt/venvs/cortex-linux/bin/cortex usr/bin/cortex
🤖 Prompt for AI Agents
In `@debian/links` at line 1, The global symlink in debian/links
("opt/venvs/cortex-linux/bin/cortex usr/bin/cortex") will be applied to all
binary packages and cause dpkg conflicts (e.g., cortexd also shipping
/usr/bin/cortex); move that single line out of debian/links and into a
package-scoped file named debian/cortex-linux.links containing the same symlink
entry so only the cortex-linux package creates /usr/bin/cortex.

8 changes: 8 additions & 0 deletions debian/cortex-linux.postrm
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
#!/bin/sh
set -e

if [ "$1" = "purge" ]; then
rm -rf /opt/venvs/cortex-linux
fi

#DEBHELPER#
1 change: 1 addition & 0 deletions debian/dirs
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
usr/bin
36 changes: 36 additions & 0 deletions debian/rules
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
#!/usr/bin/make -f

# Debian rules file for cortex-linux
# Uses dh-virtualenv for Python packaging

export DH_VERBOSE = 1
export DEB_BUILD_MAINT_OPTIONS = hardening=+all
export PYBUILD_NAME = cortex-linux

# Virtualenv installation directory
VENV_DIR = /opt/venvs/cortex-linux

# Package directory
DESTDIR = debian/cortex-linux

%:
dh $@ --with python-virtualenv

override_dh_virtualenv:
dh_virtualenv \
--install-suffix cortex-linux \
--python /usr/bin/python3 \
--upgrade-pip \
--preinstall setuptools \
--preinstall wheel \
--builtin-venv

override_dh_auto_test:
# Skip tests during package build
# Tests should be run separately in CI

override_dh_strip:
dh_strip --no-automatic-dbgsym

override_dh_shlibdeps:
dh_shlibdeps -l$(DESTDIR)$(VENV_DIR)/lib
1 change: 1 addition & 0 deletions debian/source/format
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
3.0 (native)
Loading