Skip to content
Merged
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
3 changes: 3 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,5 +1,8 @@
# See https://help.github.com/articles/ignoring-files/ for more about ignoring files.

# Ignore sqlite database files
*.db

*/bin
*/include
*/lib
Expand Down
10 changes: 10 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
# GitHub Inventory

A better way to manage your GitHub.

## Useful Tools for this repo

- Draw.io Integration (VSCode extension)
- Draw.io Integration: Mermaid plugin (VSCode extension)
- Draw.io Integration: Markdown plug (VSCode extension)
- SQLite client/browser
17 changes: 17 additions & 0 deletions database/manager.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
import sqlite3

class DatabaseManager:
def __init__(self, db_path="inventory.db"):
self.db_path = db_path

def __enter__(self):
self.conn = sqlite3.connect(self.db_path)
self.cursor = self.conn.cursor()
return self.cursor

def __exit__(self, exc_type, exc_val, exc_tb):
if exc_type is None:
self.conn.commit()
else:
self.conn.rollback()
self.conn.close()
15 changes: 15 additions & 0 deletions database/util.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
import sqlite3

conn = sqlite3.connect('inventory.db')
cursor = conn.cursor()

cursor.execute('''
CREATE TABLE IF NOT EXISTS repositories (
id TEXT PRIMARY KEY,
name TEXT,
url TEXT
)
''')

conn.commit()
conn.close()
32 changes: 32 additions & 0 deletions github/gh_actions.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
import os
from typing import Dict, List, Any
import requests

def __request_repo_workflows(owner: str, repo: str) -> List[Any]:

token = os.environ.get('GITHUB_TOKEN')
headers = {
'Authorization': f'token {token}',
'X-GitHub-Api-Version': '2022-11-28',
'Accept': 'application/vnd.github+json'
}
timeout = 10

params: Dict[str, int] = { 'per_page': 100, 'page': 1 }
data = []

try:
continue_paging = True
while continue_paging:
r = requests.get(f'https://api.github.com/repos/{owner}/{repo}/actions/workflows',
headers = headers,
params = params,
timeout = timeout
)
result = r.json()
data = result['workflows']
except Exception as e:
# logging.error(f"--- ERROR --- {e}")
print(f"--- ERROR --- {e}")

return data
41 changes: 41 additions & 0 deletions github/models/workflow.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@


class GitHubWorkflow:
def __init__(
self,
id: int,
node_id: str,
name: str,
path: str,
state: str,
created_at: str,
updated_at: str,
url: str,
html_url: str,
badge_url: str
):
self.id: int = id
self.node_id: str = node_id
self.name: str = name
self.path: str = path
self.state: str = state
self.created_at: str = created_at
self.updated_at: str = updated_at
self.url: str = url
self.html_url: str = html_url
self.badge_url: str = badge_url

@classmethod
def from_dict(cls, data):
return cls(
data['id'],
data['node_id'],
data['name'],
data['path'],
data['state'],
data['created_at'],
data['updated_at'],
data['url'],
data['html_url'],
data['badge_url']
)
48 changes: 45 additions & 3 deletions github/repos.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,16 @@
"""Handle repository actions with GitHub
"""

import os
import logging
import uuid
from typing import Dict, List, Any
import requests
from rich.console import Console
from rich.table import Table
from github.gh_actions import __request_repo_workflows
from github.models.workflow import GitHubWorkflow
from database.manager import DatabaseManager

def __request_repos_for_user(username: str) -> List[Any]:
"""Get repos for a GitHub user
Expand Down Expand Up @@ -40,15 +49,48 @@ def __request_repos_for_user(username: str) -> List[Any]:

return repos

def insert_repo(repo):
repo_id = str(uuid.uuid4())
with DatabaseManager() as db:
db.execute('''
INSERT INTO repositories (id, name, url)
VALUES (?, ?, ?)
''', (repo_id, repo['name'], repo['html_url'])
)

def user_repos_report(username: str):
"""Handle reporting GitHub repos for user
"""

repos = __request_repos_for_user(username)
print(repos)

console = Console()
table = Table(title="GitHub Repositories")

table.add_column("Name", style="cyan", no_wrap=True)
table.add_column("Private", justify="center", style="magenta")
table.add_column("Language", style="green")
table.add_column("Stars", justify="right", style="yellow")

for repo in repos:
# insert_repo(repo)
table.add_row(
repo["name"],
"🔒" if repo["private"] else "🌐",
repo["language"] or "—",
str(repo["stargazers_count"])
)

# Render table
console.print(table)

def handle_args(args):
print(f"IN github/repos.py args: {args}")

if args.report == 'list':
user_repos_report(args.user)
user_repos_report(args.user)

if args.report == 'workflows':
wfs = __request_repo_workflows(owner = 'meddlin', repo = 'github-inventory')
for w in wfs:
workflow = GitHubWorkflow.from_dict(w)
print(workflow.name)
3 changes: 2 additions & 1 deletion main.py
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@

import argparse
import textwrap
import github.repos as gh_repos
from dotenv import load_dotenv
import github.repos as gh_repos

def start_repl():
print("Welcome to the REPL")
Expand Down Expand Up @@ -38,6 +38,7 @@ def main():

repo_parser = gh_subparser.add_parser('repo', help = 'GitHub repo commands')
repo_parser.add_argument('--name', type = str, help = 'Name of repository')
repo_parser.add_argument('--owner', type = str, help = 'Owner of repository')
repo_parser.add_argument('--report', type = str, help = 'Type of report to execute')
repo_parser.add_argument('--user', type = str, help = 'GitHub username')
repo_parser.add_argument('--csv', action = argparse.BooleanOptionalAction)
Expand Down