From 2ee3e7af7b9133da946dff2643505a3d7013b3c0 Mon Sep 17 00:00:00 2001 From: Christian Cleberg Date: Sat, 28 Dec 2024 11:30:03 -0600 Subject: restructure directories --- applications/github/README.org | 112 ++++++++++++++++++ applications/github/github_admins.py | 76 ++++++++++++ applications/github/github_audit_log.py | 59 ++++++++++ applications/github/github_branch_protections.py | 78 ++++++++++++ applications/github/github_commits.py | 75 ++++++++++++ databases/administrators/mssql_admins.sql | 144 +++++++++++++++++++++++ databases/administrators/mysql_admins.sh | 1 + databases/administrators/mysql_admins.sql | 1 + databases/administrators/mysql_admins_alt.sql | 18 +++ databases/administrators/oracle_admins.sql | 15 +++ databases/administrators/oracle_admins_alt.sql | 4 + databases/passwords/sql/data.csv | 9 ++ databases/passwords/sql/get_data.sql | 30 +++++ databases/passwords/sql/test.py | 77 ++++++++++++ db_admins/mssql_admins.sql | 144 ----------------------- db_admins/mysql_admins.sh | 1 - db_admins/mysql_admins.sql | 1 - db_admins/mysql_admins_alt.sql | 18 --- db_admins/oracle_admins.sql | 15 --- db_admins/oracle_admins_alt.sql | 4 - db_passwords/sql/data.csv | 9 -- db_passwords/sql/get_data.sql | 30 ----- db_passwords/sql/test.py | 77 ------------ github/README.org | 112 ------------------ github/github_admins.py | 76 ------------ github/github_audit_log.py | 59 ---------- github/github_branch_protections.py | 78 ------------ github/github_commits.py | 75 ------------ 28 files changed, 699 insertions(+), 699 deletions(-) create mode 100644 applications/github/README.org create mode 100644 applications/github/github_admins.py create mode 100644 applications/github/github_audit_log.py create mode 100644 applications/github/github_branch_protections.py create mode 100644 applications/github/github_commits.py create mode 100644 databases/administrators/mssql_admins.sql create mode 100644 databases/administrators/mysql_admins.sh create mode 100644 databases/administrators/mysql_admins.sql create mode 100644 databases/administrators/mysql_admins_alt.sql create mode 100644 databases/administrators/oracle_admins.sql create mode 100644 databases/administrators/oracle_admins_alt.sql create mode 100644 databases/passwords/sql/data.csv create mode 100644 databases/passwords/sql/get_data.sql create mode 100644 databases/passwords/sql/test.py delete mode 100644 db_admins/mssql_admins.sql delete mode 100644 db_admins/mysql_admins.sh delete mode 100644 db_admins/mysql_admins.sql delete mode 100644 db_admins/mysql_admins_alt.sql delete mode 100644 db_admins/oracle_admins.sql delete mode 100644 db_admins/oracle_admins_alt.sql delete mode 100644 db_passwords/sql/data.csv delete mode 100644 db_passwords/sql/get_data.sql delete mode 100644 db_passwords/sql/test.py delete mode 100644 github/README.org delete mode 100644 github/github_admins.py delete mode 100644 github/github_audit_log.py delete mode 100644 github/github_branch_protections.py delete mode 100644 github/github_commits.py diff --git a/applications/github/README.org b/applications/github/README.org new file mode 100644 index 0000000..0ac08ae --- /dev/null +++ b/applications/github/README.org @@ -0,0 +1,112 @@ +#+title: GitHub Scripts + +*NOTE*: I used the same [[https://docs.github.com/en/authentication/keeping-your-account-and-data-secure/managing-your-personal-access-tokens][PAT]] for all scripts within this folder. Note that you can likely reduce permissions for certain scripts - it's best practice to define a PAT for a specific purpose and avoid using a single PAT with broad permissions. + +- Personal Access Token: + - [X] Repository Permissions + - [X] Actions: read-only + - [X] Contents: read-only + - [X] Metadata: read-only + - [X] Workflows: read-only + - [X] Organization Permissions + - [X] Administration: read-only + +* =github_admins.py= + +#+begin_src sh +python ./github_admins.py +#+end_src + +#+begin_src text +Members of the organization 'your_organization': + +Repositories in the organization 'your_organization': +- demo-repository + +Collaborators for the repository 'demo-repository': +- user1: admin +#+end_src + +* =github_audit_log.py= + +*NOTE*: Requires an active GitHub Enterprise subscription. + +#+begin_src sh +python ./github_audit_log.py +#+end_src + +#+begin_src text +TODO: Need to get an Enterprise subscription to test this script. +#+end_src + +* =github_branch_protections.py= + + +#+begin_src sh +python ./github_branch_protections.py +#+end_src + +#+begin_src text +Total branches in the repository 'demo-repository': 1 + +Branch: main +No protection settings + +Repository rulesets for 'demo-repository': +[{'id': 2311373, 'name': 'default', 'target': 'branch', 'source_type': 'Repository', 'source': 'phryq/demo-repository', 'enforcement': 'active', 'node_id': 'RRS_lACqUmVwb3NpdG9yec40LV1PzgAjRM0', '_links': {'self': {'href': 'https://api.github.com/repos/phryq/demo-repository/rulesets/2311373'}, 'html': {'href': 'https://github.com/phryq/demo-repository/rules/2311373'}}, 'created_at': '2024-10-19T15:59:35.200-05:00', 'updated_at': '2024-10-19T15:59:35.200-05:00'}] +#+end_src + +* =github_commits.py= + +#+begin_src sh +python ./github_commits.py +#+end_src + +#+begin_src text +Total commits in the repository 'demo-repository' on branch 'main': 3 + +Commit SHA: 13c488a2cdda08e4043f8ef36ced5fdd429e9718 +Author: Christian Cleberg <156287552+ccleberg@users.noreply.github.com> +Date: 2024-10-19T20:57:55Z +Message: Merge pull request #2 from phryq/1-test-issue + +fixes +URL: https://github.com/phryq/demo-repository/commit/13c488a2cdda08e4043f8ef36ced5fdd429e9718 +Files changed: + - .gitignore (added) + Additions: 0, Deletions: 0, Changes: 0 + - README.md (removed) + Additions: 0, Deletions: 4, Changes: 4 + - README.org (added) + Additions: 7, Deletions: 0, Changes: 7 + +Commit SHA: 6bfde238a2a34a93ce8ee02082eaf4ab3c189368 +Author: Christian Cleberg +Date: 2024-10-19T20:56:50Z +Message: fixes +URL: https://github.com/phryq/demo-repository/commit/6bfde238a2a34a93ce8ee02082eaf4ab3c189368 +Files changed: + - .gitignore (added) + Additions: 0, Deletions: 0, Changes: 0 + - README.md (removed) + Additions: 0, Deletions: 4, Changes: 4 + - README.org (added) + Additions: 7, Deletions: 0, Changes: 7 + +Commit SHA: be1ddf31e08fc790f54d68f8067b7b2f3805f999 +Author: Christian Cleberg <156287552+ccleberg@users.noreply.github.com> +Date: 2024-10-19T20:54:08Z +Message: Initial commit +URL: https://github.com/phryq/demo-repository/commit/be1ddf31e08fc790f54d68f8067b7b2f3805f999 +Files changed: + - .github/workflows/auto-assign.yml (added) + Additions: 19, Deletions: 0, Changes: 19 + - .github/workflows/proof-html.yml (added) + Additions: 11, Deletions: 0, Changes: 11 + - README.md (added) + Additions: 4, Deletions: 0, Changes: 4 + - index.html (added) + Additions: 1, Deletions: 0, Changes: 1 + - package.json (added) + Additions: 9, Deletions: 0, Changes: 9 +#+end_src \ No newline at end of file diff --git a/applications/github/github_admins.py b/applications/github/github_admins.py new file mode 100644 index 0000000..d737887 --- /dev/null +++ b/applications/github/github_admins.py @@ -0,0 +1,76 @@ +""" +Gather all members of a GitHub organization, all repos within that organization, +and list each user's permission per repo. +""" + +import requests + +GITHUB_TOKEN = 'your_personal_access_token' +ORGANIZATION = 'your_organization' +TIMEOUT = 30 + +# Headers for authentication +headers = { + 'Authorization': f'token {GITHUB_TOKEN}', + 'Accept': 'application/vnd.github.v3+json' +} + +def get_org_members(org): + """ + Get members of an organization + """ + url = f'https://api.github.com/orgs/{org}/members' + response = requests.get(url, headers=headers, timeout=TIMEOUT) + response.raise_for_status() + return response.json() + +def get_org_repos(org): + """ + Get repositories of an organization + """ + url = f'https://api.github.com/orgs/{org}/repos' + response = requests.get(url, headers=headers, timeout=TIMEOUT) + response.raise_for_status() + return response.json() + +def get_repo_collaborators(org, repo): + """ + Get collaborators of a repository with their permissions + """ + url = f'https://api.github.com/repos/{org}/{repo}/collaborators' + response = requests.get(url, headers=headers, timeout=TIMEOUT) + response.raise_for_status() + return response.json() + +def get_user_permissions(org, repo, user): + """ + Get a user's permissions for a repository + """ + url = f'https://api.github.com/repos/{org}/{repo}/collaborators/{user}/permission' + response = requests.get(url, headers=headers, timeout=TIMEOUT) + response.raise_for_status() + return response.json() + +# Main script +if __name__ == '__main__': + # Get organization members + members = get_org_members(ORGANIZATION) + print(f"Members of the organization '{ORGANIZATION}':") + for member in members: + print(f"- {member['login']}") + + # Get organization repositories + repositories = get_org_repos(ORGANIZATION) + print(f"\nRepositories in the organization '{ORGANIZATION}':") + for repository in repositories: + print(f"- {repository['name']}") + + # Get collaborators for each repository and their permissions + for repository in repositories: + repository_name = repository['name'] + collaborators = get_repo_collaborators(ORGANIZATION, repository_name) + print(f"\nCollaborators for the repository '{repository_name}':") + for collaborator in collaborators: + user_login = collaborator['login'] + permissions = get_user_permissions(ORGANIZATION, repository_name, user_login) + print(f"- {user_login}: {permissions['permission']}") diff --git a/applications/github/github_audit_log.py b/applications/github/github_audit_log.py new file mode 100644 index 0000000..0937764 --- /dev/null +++ b/applications/github/github_audit_log.py @@ -0,0 +1,59 @@ +""" +Extract a specific list of events from the GitHub Audit Log API. + +NOTE: REQUIRES A GITHUB ENTERPRISE SUBSCRIPTION TO ACCESS THE API. +""" + +import requests + +GITHUB_TOKEN = 'your_personal_access_token' +ORGANIZATION = 'your_organization' +TIMEOUT = 30 + +# Headers for authentication +headers = { + 'Authorization': f'token {GITHUB_TOKEN}', + 'Accept': 'application/vnd.github.v3+json' +} + +def get_audit_log_events(org, actions): + """ + Get audit log events for specific actions + """ + events = [] + page = 1 + while True: + url = (f'https://api.github.com/orgs/{org}/audit-log?page={page}&per_page=100' + f'&action={",".join(actions)}') + response = requests.get(url, headers=headers, timeout=TIMEOUT) + response.raise_for_status() + page_events = response.json() + if not page_events: + break + events.extend(page_events) + page += 1 + return events + +if __name__ == '__main__': + try: + # Define the actions to filter + action_filters = ['protected_branch', + 'repository_branch_protection_evaluation', + 'repository_ruleset'] + + # Get audit log events for the specified actions + audit_log_events = get_audit_log_events(ORGANIZATION, action_filters) + print(f"Total audit log events for specified actions: {len(audit_log_events)}") + + # Print detailed information for each event + for event in audit_log_events: + print(f"\nEvent ID: {event['@id']}") + print(f"Action: {event['action']}") + print(f"Actor: {event['actor']}") + print(f"Repository: {event.get('repo', 'N/A')}") + print(f"Created At: {event['created_at']}") + print(f"Details: {event}") + except requests.exceptions.Timeout: + print("The request timed out") + except requests.exceptions.RequestException as e: + print(f"An error occurred: {e}") diff --git a/applications/github/github_branch_protections.py b/applications/github/github_branch_protections.py new file mode 100644 index 0000000..73c94b6 --- /dev/null +++ b/applications/github/github_branch_protections.py @@ -0,0 +1,78 @@ +""" +Gathers branch protection rules for a repository. +""" + +import requests + +GITHUB_TOKEN = 'your_personal_access_token' +ORGANIZATION = 'your_organization' +REPOSITORY = 'your_repository' +TIMEOUT = 30 + +headers = { + 'Authorization': f'token {GITHUB_TOKEN}', + 'Accept': 'application/vnd.github.v3+json' +} + +def get_all_branches(org, repo): + """ + Get all branches in a repository + """ + all_branches = [] + page = 1 + while True: + url = f'https://api.github.com/repos/{org}/{repo}/branches?page={page}&per_page=100' + response = requests.get(url, headers=headers, timeout=TIMEOUT) + response.raise_for_status() + page_branches = response.json() + if not page_branches: + break + all_branches.extend(page_branches) + page += 1 + return all_branches + +def get_branch_protection(org, repo, repo_branch): + """ + Get branch protection settings + """ + url = f'https://api.github.com/repos/{org}/{repo}/branches/{repo_branch}/protection' + response = requests.get(url, headers=headers, timeout=TIMEOUT) + if response.status_code == 404: + return None # No protection settings for this branch + response.raise_for_status() + return response.json() + +def get_repository_rulesets(org, repo): + """ + Get repository rulesets + """ + url = f'https://api.github.com/repos/{org}/{repo}/rulesets' + response = requests.get(url, headers=headers, timeout=TIMEOUT) + response.raise_for_status() + return response.json() + +if __name__ == '__main__': + try: + # Get all branches in the repository + branches = get_all_branches(ORGANIZATION, REPOSITORY) + print(f"Total branches in the repository '{REPOSITORY}': {len(branches)}") + + # Get protection settings for each branch + for branch in branches: + branch_name = branch['name'] + protection_settings = get_branch_protection(ORGANIZATION, REPOSITORY, branch_name) + print(f"\nBranch: {branch_name}") + if protection_settings: + print(f"Protection settings: {protection_settings}") + else: + print("No protection settings") + + # Get repository rulesets + rulesets = get_repository_rulesets(ORGANIZATION, REPOSITORY) + print(f"\nRepository rulesets for '{REPOSITORY}':") + print(rulesets) + + except requests.exceptions.Timeout: + print("The request timed out") + except requests.exceptions.RequestException as e: + print(f"An error occurred: {e}") diff --git a/applications/github/github_commits.py b/applications/github/github_commits.py new file mode 100644 index 0000000..f35d5d6 --- /dev/null +++ b/applications/github/github_commits.py @@ -0,0 +1,75 @@ +""" +Gather all commits from a specific branch of a repository in a GitHub organization. +""" + +import requests + +GITHUB_TOKEN = 'your_personal_access_token' +ORGANIZATION = 'your_organization' +REPOSITORY = 'your_repository' +BRANCH = 'your_branch' + +# Headers for authentication +headers = { + 'Authorization': f'token {GITHUB_TOKEN}', + 'Accept': 'application/vnd.github.v3+json' +} + +# Define a timeout value (in seconds) +TIMEOUT = 10 + +def get_commit_log(org, repo, branch): + """ + Get the full commit log for a repository branch + """ + commits = [] + page = 1 + while True: + url = (f'https://api.github.com/repos/{org}/{repo}/commits?sha={branch}' + f'&page={page}&per_page=100') + response = requests.get(url, headers=headers, timeout=TIMEOUT) + response.raise_for_status() + page_commits = response.json() + if not page_commits: + break + commits.extend(page_commits) + page += 1 + return commits + +def get_commit_details(org, repo, sha): + """ + Get detailed information for a specific commit + """ + url = f'https://api.github.com/repos/{org}/{repo}/commits/{sha}' + response = requests.get(url, headers=headers, timeout=TIMEOUT) + response.raise_for_status() + return response.json() + +if __name__ == '__main__': + try: + # Get the full commit log for the specified branch + commit_log = get_commit_log(ORGANIZATION, REPOSITORY, BRANCH) + print(f"Total commits in the repository '{REPOSITORY}' on branch " + f"'{BRANCH}': {len(commit_log)}") + + # Get detailed information for each commit + for commit in commit_log: + sha_hash = commit['sha'] + commit_details = get_commit_details(ORGANIZATION, REPOSITORY, + sha_hash) + print(f"\nCommit SHA: {commit_details['sha']}") + print(f"Author: {commit_details['commit']['author']['name']} " + f"<{commit_details['commit']['author']['email']}>") + print(f"Date: {commit_details['commit']['author']['date']}") + print(f"Message: {commit_details['commit']['message']}") + print(f"URL: {commit_details['html_url']}") + print("Files changed:") + for file in commit_details['files']: + print(f" - {file['filename']} ({file['status']})") + print(f" Additions: {file['additions']}, " + f"Deletions: {file['deletions']}, " + f"Changes: {file['changes']}") + except requests.exceptions.Timeout: + print("The request timed out") + except requests.exceptions.RequestException as e: + print(f"An error occurred: {e}") diff --git a/databases/administrators/mssql_admins.sql b/databases/administrators/mssql_admins.sql new file mode 100644 index 0000000..278fafc --- /dev/null +++ b/databases/administrators/mssql_admins.sql @@ -0,0 +1,144 @@ +/* +Security Audit Report +1) List all access provisioned to a sql user or windows user/group directly +2) List all access provisioned to a sql user or windows user/group through a database or application role +3) List all access provisioned to the public role + +Columns Returned: +UserName : SQL or Windows/Active Directory user account. This could also be an Active Directory group. +UserType : Value will be either 'SQL User' or 'Windows User'. This reflects the type of user defined for the + SQL Server user account. +DatabaseUserName: Name of the associated user as defined in the database user account. The database user may not be the + same as the server user. +Role : The role name. This will be null if the associated permissions to the object are defined at directly + on the user account, otherwise this will be the name of the role that the user is a member of. +PermissionType : Type of permissions the user/role has on an object. Examples could include CONNECT, EXECUTE, SELECT + DELETE, INSERT, ALTER, CONTROL, TAKE OWNERSHIP, VIEW DEFINITION, etc. + This value may not be populated for all roles. Some built in roles have implicit permission + definitions. +PermissionState : Reflects the state of the permission type, examples could include GRANT, DENY, etc. + This value may not be populated for all roles. Some built in roles have implicit permission + definitions. +ObjectType : Type of object the user/role is assigned permissions on. Examples could include USER_TABLE, + SQL_SCALAR_FUNCTION, SQL_INLINE_TABLE_VALUED_FUNCTION, SQL_STORED_PROCEDURE, VIEW, etc. + This value may not be populated for all roles. Some built in roles have implicit permission + definitions. +ObjectName : Name of the object that the user/role is assigned permissions on. + This value may not be populated for all roles. Some built in roles have implicit permission + definitions. +ColumnName : Name of the column of the object that the user/role is assigned permissions on. This value + is only populated if the object is a table, view or a table value function. +*/ + +--List all access provisioned to a sql user or windows user/group directly +SELECT + [UserName] = CASE princ.[type] + WHEN 'S' THEN princ.[name] + WHEN 'U' THEN ulogin.[name] COLLATE Latin1_General_CI_AI + END, + [UserType] = CASE princ.[type] + WHEN 'S' THEN 'SQL User' + WHEN 'U' THEN 'Windows User' + END, + [DatabaseUserName] = princ.[name], + [Role] = null, + [PermissionType] = perm.[permission_name], + [PermissionState] = perm.[state_desc], + [ObjectType] = obj.type_desc,--perm.[class_desc], + [ObjectName] = OBJECT_NAME(perm.major_id), + [ColumnName] = col.[name] +FROM + --database user + sys.database_principals princ +LEFT JOIN + --Login accounts + sys.login_token ulogin on princ.[sid] = ulogin.[sid] +LEFT JOIN + --Permissions + sys.database_permissions perm ON perm.[grantee_principal_id] = princ.[principal_id] +LEFT JOIN + --Table columns + sys.columns col ON col.[object_id] = perm.major_id + AND col.[column_id] = perm.[minor_id] +LEFT JOIN + sys.objects obj ON perm.[major_id] = obj.[object_id] +WHERE + princ.[type] in ('S','U') +UNION +--List all access provisioned to a sql user or windows user/group through a database or application role +SELECT + [UserName] = CASE memberprinc.[type] + WHEN 'S' THEN memberprinc.[name] + WHEN 'U' THEN ulogin.[name] COLLATE Latin1_General_CI_AI + END, + [UserType] = CASE memberprinc.[type] + WHEN 'S' THEN 'SQL User' + WHEN 'U' THEN 'Windows User' + END, + [DatabaseUserName] = memberprinc.[name], + [Role] = roleprinc.[name], + [PermissionType] = perm.[permission_name], + [PermissionState] = perm.[state_desc], + [ObjectType] = obj.type_desc,--perm.[class_desc], + [ObjectName] = OBJECT_NAME(perm.major_id), + [ColumnName] = col.[name] +FROM + --Role/member associations + sys.database_role_members members +JOIN + --Roles + sys.database_principals roleprinc ON roleprinc.[principal_id] = members.[role_principal_id] +JOIN + --Role members (database users) + sys.database_principals memberprinc ON memberprinc.[principal_id] = members.[member_principal_id] +LEFT JOIN + --Login accounts + sys.login_token ulogin on memberprinc.[sid] = ulogin.[sid] +LEFT JOIN + --Permissions + sys.database_permissions perm ON perm.[grantee_principal_id] = roleprinc.[principal_id] +LEFT JOIN + --Table columns + sys.columns col on col.[object_id] = perm.major_id + AND col.[column_id] = perm.[minor_id] +LEFT JOIN + sys.objects obj ON perm.[major_id] = obj.[object_id] +UNION +--List all access provisioned to the public role, which everyone gets by default +SELECT + [UserName] = '{All Users}', + [UserType] = '{All Users}', + [DatabaseUserName] = '{All Users}', + [Role] = roleprinc.[name], + [PermissionType] = perm.[permission_name], + [PermissionState] = perm.[state_desc], + [ObjectType] = obj.type_desc,--perm.[class_desc], + [ObjectName] = OBJECT_NAME(perm.major_id), + [ColumnName] = col.[name] +FROM + --Roles + sys.database_principals roleprinc +LEFT JOIN + --Role permissions + sys.database_permissions perm ON perm.[grantee_principal_id] = roleprinc.[principal_id] +LEFT JOIN + --Table columns + sys.columns col on col.[object_id] = perm.major_id + AND col.[column_id] = perm.[minor_id] +JOIN + --All objects + sys.objects obj ON obj.[object_id] = perm.[major_id] +WHERE + --Only roles + roleprinc.[type] = 'R' AND + --Only public role + roleprinc.[name] = 'public' AND + --Only objects of ours, not the MS objects + obj.is_ms_shipped = 0 +ORDER BY + princ.[Name], + OBJECT_NAME(perm.major_id), + col.[name], + perm.[permission_name], + perm.[state_desc], + obj.type_desc--perm.[class_desc] diff --git a/databases/administrators/mysql_admins.sh b/databases/administrators/mysql_admins.sh new file mode 100644 index 0000000..6faa2c9 --- /dev/null +++ b/databases/administrators/mysql_admins.sh @@ -0,0 +1 @@ +mysql -u root -p diff --git a/databases/administrators/mysql_admins.sql b/databases/administrators/mysql_admins.sql new file mode 100644 index 0000000..9efa567 --- /dev/null +++ b/databases/administrators/mysql_admins.sql @@ -0,0 +1 @@ +SELECT ** FROM information_schema.user_privileges; diff --git a/databases/administrators/mysql_admins_alt.sql b/databases/administrators/mysql_admins_alt.sql new file mode 100644 index 0000000..ac855f4 --- /dev/null +++ b/databases/administrators/mysql_admins_alt.sql @@ -0,0 +1,18 @@ +-- Global Permissions +SELECT ... FROM mysql.user; + +-- Database Permissions +SELECT ... FROM mysql.db +WHERE db = @db_name; + +-- Table Permissions +SELECT ... FROM mysql.tables +WHERE db = @db_name; + +-- Column Permissions +SELECT ... FROM mysql.columns_priv +WHERE db = @db_name; + +-- Password Configuration +SHOW GLOBAL VARIABLES LIKE 'validate_password%'; +SHOW VARIABLES LIKE 'validate_password%'; diff --git a/databases/administrators/oracle_admins.sql b/databases/administrators/oracle_admins.sql new file mode 100644 index 0000000..bac5934 --- /dev/null +++ b/databases/administrators/oracle_admins.sql @@ -0,0 +1,15 @@ +SELECT + grantee AS "User", + privilege AS "Privilege" +FROM + dba_sys_privs +WHERE + grantee IN (SELECT DISTINCT grantee FROM dba_sys_privs) +UNION ALL +SELECT + grantee AS "User", + privilege AS "Privilege" +FROM + dba_tab_privs +WHERE + grantee IN (SELECT DISTINCT grantee FROM dba_tab_privs); diff --git a/databases/administrators/oracle_admins_alt.sql b/databases/administrators/oracle_admins_alt.sql new file mode 100644 index 0000000..4486829 --- /dev/null +++ b/databases/administrators/oracle_admins_alt.sql @@ -0,0 +1,4 @@ +SELECT ** FROM sys.dba_role_privs; +SELECT ** FROM sys.dba_sys_privs; +SELECT ** FROM sys.dba_tab_privs; +SELECT ** FROM sys.dba_users; diff --git a/databases/passwords/sql/data.csv b/databases/passwords/sql/data.csv new file mode 100644 index 0000000..fc925ea --- /dev/null +++ b/databases/passwords/sql/data.csv @@ -0,0 +1,9 @@ +name,principal_id,sid,type,type_desc,is_disabled,create_date,modify_date,default_database_name,default_language_name,credential_id,is_policy_checked,is_expiration_checked,password_hash,IsMustChange,IsLocked,LockoutTime,PasswordLastSetTime,IsExpired,BadPasswordCount,BadPasswordTime,HistoryLength +user1,1,,S,SQL_LOGIN,0,2023-01-15 10:35:00,2023-01-15 10:35:00,master,us_english,NULL,1,0,0x01004086CEB6772AE2356381B9B069D4E02C0185D5A06CFA3822,0,0,,2023-01-15 10:35:00,0,0,,5 +user2,267,,S,SQL_LOGIN,0,2023-02-20 20:49:00,2023-02-20 20:49:00,master,us_english,NULL,0,0,0x01003E3A7A6F88A8F548540ECB2043946AC2545120424CCD8782,1,0,,2023-02-20 20:49:00,0,1,2023-02-20 20:50:00,3 +user3,268,,S,SQL_LOGIN,0,2023-03-10 11:20:00,2023-03-10 11:20:00,secondary,us_english,NULL,1,0,0x010042516769FBC191A67840731CB36B41EFDACC97BE8264281F,0,0,,2023-03-10 11:20:00,0,0,,4 +user4,269,,S,SQL_LOGIN,0,2023-04-01 10:40:00,2023-04-01 11:32:00,secondary,us_english,NULL,1,0,0x01005F3B351B26E2DB7C7FD3C7ED02B3FD2EDC09BB2BF13DA3E5,0,1,2023-04-01 11:32:00,2023-04-01 10:40:00,0,3,2023-04-01 11:30:00,2 +user5,270,,S,SQL_LOGIN,0,2023-05-05 12:33:00,2023-05-05 12:33:00,master,us_english,NULL,1,0,0x0100AE15D55972BB3D6C6283921711CD4A208747888BEEFED71B,0,0,,2023-05-05 12:33:00,0,0,,6 +user6,272,,S,SQL_LOGIN,0,2023-06-15 11:46:00,2023-06-15 11:46:00,secondary,us_english,NULL,1,1,0x0100F12FAE790FCE0FF356A0948211AE4052653503E1BBC28FAB,0,0,,2023-06-15 11:46:00,0,0,,7 +user7,279,,S,SQL_LOGIN,0,2023-07-20 12:50:00,2023-07-20 12:50:00,secondary,us_english,NULL,1,1,0x01004856A222264E62219236AB6AC7E5B622F1E53D1CCA2AF9B8,0,0,,2023-07-20 12:50:00,0,0,,8 +user8,284,,S,SQL_LOGIN,0,2023-08-25 13:56:00,2023-08-25 13:56:00,master,us_english,NULL,1,1,0x0100723BEDBE69779CD3087C0E60AD69C33CC7E969F78DA2498A,0,0,,2023-08-25 13:56:00,0,0,,9 \ No newline at end of file diff --git a/databases/passwords/sql/get_data.sql b/databases/passwords/sql/get_data.sql new file mode 100644 index 0000000..b5bef36 --- /dev/null +++ b/databases/passwords/sql/get_data.sql @@ -0,0 +1,30 @@ +/* +References: +1. https://learn.microsoft.com/en-us/sql/relational-databases/security/password-policy +2. https://learn.microsoft.com/en-us/sql/t-sql/functions/loginproperty-transact-sql +*/ + +SELECT + name, + principal_id, + sid, + type, + type_desc, + is_disabled, + create_date, + modify_date, + default_database_name, + default_language_name, + credential_id, + is_policy_checked, + is_expiration_checked, + password_hash, + LOGINPROPERTY(name, 'IsMustChange') AS IsMustChange, + LOGINPROPERTY(name, 'IsLocked') AS IsLocked, + LOGINPROPERTY(name, 'LockoutTime') AS LockoutTime, + LOGINPROPERTY(name, 'PasswordLastSetTime') AS PasswordLastSetTime, + LOGINPROPERTY(name, 'IsExpired') AS IsExpired, + LOGINPROPERTY(name, 'BadPasswordCount') AS BadPasswordCount, + LOGINPROPERTY(name, 'BadPasswordTime') AS BadPasswordTime, + LOGINPROPERTY(name, 'HistoryLength') AS HistoryLength +FROM sys.sql_logins; diff --git a/databases/passwords/sql/test.py b/databases/passwords/sql/test.py new file mode 100644 index 0000000..bfacb20 --- /dev/null +++ b/databases/passwords/sql/test.py @@ -0,0 +1,77 @@ +""" +Checks SQL Server user data for compliance with Windows policies. +""" + +# Import packages +import pandas as pd + +# Load the data into a pandas DataFrame +df_input = pd.read_csv('./data.csv') + +# Function to apply rules and generate report +def apply_rules_and_report(df): + """ + Apply defined rules against the input data. + + Parameters: + df (pandas.DataFrame): SQL login data + + Returns: + report (list): List of dictionaries containing test results + """ + report = [] + for _, row in df.iterrows(): + result = { + 'Name': row['name'], + 'Type Check': '', + 'Policy Check': '', + 'Expiration Check': '', + 'Reason': '' + } + + # Check the type_desc + if row['type_desc'] == 'SQL_LOGIN': + result['Type Check'] = 'SQL_LOGIN' + elif row['type_desc'] == 'WINDOWS_LOGIN': + result['Type Check'] = 'N/A' + result['Reason'] = 'Refer to Windows password policy.' + else: + result['Type Check'] = 'Manual Review' + result['Reason'] = 'Reviewer to manually review.' + + # Check if password policy is enforced + if row['is_policy_checked'] == 1: + result['Policy Check'] = 'PASS' + result['Reason'] += '''Password policy is enforced. Reviewer to + check the assigned policy.''' + else: + result['Policy Check'] = 'FAIL' + result['Reason'] += 'Password policy is not enforced.' + + # Check if password expiration is enforced + if row['is_expiration_checked'] == 1: + result['Expiration Check'] = 'PASS' + result['Reason'] += '''Password expiration is enforced. Reviewer to + check the expiration policy.''' + else: + result['Expiration Check'] = 'FAIL' + result['Reason'] += 'Password expiration is not enforced.' + + report.append(result) + + return report + +# Main function to run the script +def main(): + """ + Apply defined rules against the input data and print the results. + """ + # Apply rules and generate report + report = apply_rules_and_report(df_input) + report_df = pd.DataFrame(report) + + # Print the report + print(report_df) + +if __name__ == "__main__": + main() diff --git a/db_admins/mssql_admins.sql b/db_admins/mssql_admins.sql deleted file mode 100644 index 278fafc..0000000 --- a/db_admins/mssql_admins.sql +++ /dev/null @@ -1,144 +0,0 @@ -/* -Security Audit Report -1) List all access provisioned to a sql user or windows user/group directly -2) List all access provisioned to a sql user or windows user/group through a database or application role -3) List all access provisioned to the public role - -Columns Returned: -UserName : SQL or Windows/Active Directory user account. This could also be an Active Directory group. -UserType : Value will be either 'SQL User' or 'Windows User'. This reflects the type of user defined for the - SQL Server user account. -DatabaseUserName: Name of the associated user as defined in the database user account. The database user may not be the - same as the server user. -Role : The role name. This will be null if the associated permissions to the object are defined at directly - on the user account, otherwise this will be the name of the role that the user is a member of. -PermissionType : Type of permissions the user/role has on an object. Examples could include CONNECT, EXECUTE, SELECT - DELETE, INSERT, ALTER, CONTROL, TAKE OWNERSHIP, VIEW DEFINITION, etc. - This value may not be populated for all roles. Some built in roles have implicit permission - definitions. -PermissionState : Reflects the state of the permission type, examples could include GRANT, DENY, etc. - This value may not be populated for all roles. Some built in roles have implicit permission - definitions. -ObjectType : Type of object the user/role is assigned permissions on. Examples could include USER_TABLE, - SQL_SCALAR_FUNCTION, SQL_INLINE_TABLE_VALUED_FUNCTION, SQL_STORED_PROCEDURE, VIEW, etc. - This value may not be populated for all roles. Some built in roles have implicit permission - definitions. -ObjectName : Name of the object that the user/role is assigned permissions on. - This value may not be populated for all roles. Some built in roles have implicit permission - definitions. -ColumnName : Name of the column of the object that the user/role is assigned permissions on. This value - is only populated if the object is a table, view or a table value function. -*/ - ---List all access provisioned to a sql user or windows user/group directly -SELECT - [UserName] = CASE princ.[type] - WHEN 'S' THEN princ.[name] - WHEN 'U' THEN ulogin.[name] COLLATE Latin1_General_CI_AI - END, - [UserType] = CASE princ.[type] - WHEN 'S' THEN 'SQL User' - WHEN 'U' THEN 'Windows User' - END, - [DatabaseUserName] = princ.[name], - [Role] = null, - [PermissionType] = perm.[permission_name], - [PermissionState] = perm.[state_desc], - [ObjectType] = obj.type_desc,--perm.[class_desc], - [ObjectName] = OBJECT_NAME(perm.major_id), - [ColumnName] = col.[name] -FROM - --database user - sys.database_principals princ -LEFT JOIN - --Login accounts - sys.login_token ulogin on princ.[sid] = ulogin.[sid] -LEFT JOIN - --Permissions - sys.database_permissions perm ON perm.[grantee_principal_id] = princ.[principal_id] -LEFT JOIN - --Table columns - sys.columns col ON col.[object_id] = perm.major_id - AND col.[column_id] = perm.[minor_id] -LEFT JOIN - sys.objects obj ON perm.[major_id] = obj.[object_id] -WHERE - princ.[type] in ('S','U') -UNION ---List all access provisioned to a sql user or windows user/group through a database or application role -SELECT - [UserName] = CASE memberprinc.[type] - WHEN 'S' THEN memberprinc.[name] - WHEN 'U' THEN ulogin.[name] COLLATE Latin1_General_CI_AI - END, - [UserType] = CASE memberprinc.[type] - WHEN 'S' THEN 'SQL User' - WHEN 'U' THEN 'Windows User' - END, - [DatabaseUserName] = memberprinc.[name], - [Role] = roleprinc.[name], - [PermissionType] = perm.[permission_name], - [PermissionState] = perm.[state_desc], - [ObjectType] = obj.type_desc,--perm.[class_desc], - [ObjectName] = OBJECT_NAME(perm.major_id), - [ColumnName] = col.[name] -FROM - --Role/member associations - sys.database_role_members members -JOIN - --Roles - sys.database_principals roleprinc ON roleprinc.[principal_id] = members.[role_principal_id] -JOIN - --Role members (database users) - sys.database_principals memberprinc ON memberprinc.[principal_id] = members.[member_principal_id] -LEFT JOIN - --Login accounts - sys.login_token ulogin on memberprinc.[sid] = ulogin.[sid] -LEFT JOIN - --Permissions - sys.database_permissions perm ON perm.[grantee_principal_id] = roleprinc.[principal_id] -LEFT JOIN - --Table columns - sys.columns col on col.[object_id] = perm.major_id - AND col.[column_id] = perm.[minor_id] -LEFT JOIN - sys.objects obj ON perm.[major_id] = obj.[object_id] -UNION ---List all access provisioned to the public role, which everyone gets by default -SELECT - [UserName] = '{All Users}', - [UserType] = '{All Users}', - [DatabaseUserName] = '{All Users}', - [Role] = roleprinc.[name], - [PermissionType] = perm.[permission_name], - [PermissionState] = perm.[state_desc], - [ObjectType] = obj.type_desc,--perm.[class_desc], - [ObjectName] = OBJECT_NAME(perm.major_id), - [ColumnName] = col.[name] -FROM - --Roles - sys.database_principals roleprinc -LEFT JOIN - --Role permissions - sys.database_permissions perm ON perm.[grantee_principal_id] = roleprinc.[principal_id] -LEFT JOIN - --Table columns - sys.columns col on col.[object_id] = perm.major_id - AND col.[column_id] = perm.[minor_id] -JOIN - --All objects - sys.objects obj ON obj.[object_id] = perm.[major_id] -WHERE - --Only roles - roleprinc.[type] = 'R' AND - --Only public role - roleprinc.[name] = 'public' AND - --Only objects of ours, not the MS objects - obj.is_ms_shipped = 0 -ORDER BY - princ.[Name], - OBJECT_NAME(perm.major_id), - col.[name], - perm.[permission_name], - perm.[state_desc], - obj.type_desc--perm.[class_desc] diff --git a/db_admins/mysql_admins.sh b/db_admins/mysql_admins.sh deleted file mode 100644 index 6faa2c9..0000000 --- a/db_admins/mysql_admins.sh +++ /dev/null @@ -1 +0,0 @@ -mysql -u root -p diff --git a/db_admins/mysql_admins.sql b/db_admins/mysql_admins.sql deleted file mode 100644 index 9efa567..0000000 --- a/db_admins/mysql_admins.sql +++ /dev/null @@ -1 +0,0 @@ -SELECT ** FROM information_schema.user_privileges; diff --git a/db_admins/mysql_admins_alt.sql b/db_admins/mysql_admins_alt.sql deleted file mode 100644 index ac855f4..0000000 --- a/db_admins/mysql_admins_alt.sql +++ /dev/null @@ -1,18 +0,0 @@ --- Global Permissions -SELECT ... FROM mysql.user; - --- Database Permissions -SELECT ... FROM mysql.db -WHERE db = @db_name; - --- Table Permissions -SELECT ... FROM mysql.tables -WHERE db = @db_name; - --- Column Permissions -SELECT ... FROM mysql.columns_priv -WHERE db = @db_name; - --- Password Configuration -SHOW GLOBAL VARIABLES LIKE 'validate_password%'; -SHOW VARIABLES LIKE 'validate_password%'; diff --git a/db_admins/oracle_admins.sql b/db_admins/oracle_admins.sql deleted file mode 100644 index bac5934..0000000 --- a/db_admins/oracle_admins.sql +++ /dev/null @@ -1,15 +0,0 @@ -SELECT - grantee AS "User", - privilege AS "Privilege" -FROM - dba_sys_privs -WHERE - grantee IN (SELECT DISTINCT grantee FROM dba_sys_privs) -UNION ALL -SELECT - grantee AS "User", - privilege AS "Privilege" -FROM - dba_tab_privs -WHERE - grantee IN (SELECT DISTINCT grantee FROM dba_tab_privs); diff --git a/db_admins/oracle_admins_alt.sql b/db_admins/oracle_admins_alt.sql deleted file mode 100644 index 4486829..0000000 --- a/db_admins/oracle_admins_alt.sql +++ /dev/null @@ -1,4 +0,0 @@ -SELECT ** FROM sys.dba_role_privs; -SELECT ** FROM sys.dba_sys_privs; -SELECT ** FROM sys.dba_tab_privs; -SELECT ** FROM sys.dba_users; diff --git a/db_passwords/sql/data.csv b/db_passwords/sql/data.csv deleted file mode 100644 index fc925ea..0000000 --- a/db_passwords/sql/data.csv +++ /dev/null @@ -1,9 +0,0 @@ -name,principal_id,sid,type,type_desc,is_disabled,create_date,modify_date,default_database_name,default_language_name,credential_id,is_policy_checked,is_expiration_checked,password_hash,IsMustChange,IsLocked,LockoutTime,PasswordLastSetTime,IsExpired,BadPasswordCount,BadPasswordTime,HistoryLength -user1,1,,S,SQL_LOGIN,0,2023-01-15 10:35:00,2023-01-15 10:35:00,master,us_english,NULL,1,0,0x01004086CEB6772AE2356381B9B069D4E02C0185D5A06CFA3822,0,0,,2023-01-15 10:35:00,0,0,,5 -user2,267,,S,SQL_LOGIN,0,2023-02-20 20:49:00,2023-02-20 20:49:00,master,us_english,NULL,0,0,0x01003E3A7A6F88A8F548540ECB2043946AC2545120424CCD8782,1,0,,2023-02-20 20:49:00,0,1,2023-02-20 20:50:00,3 -user3,268,,S,SQL_LOGIN,0,2023-03-10 11:20:00,2023-03-10 11:20:00,secondary,us_english,NULL,1,0,0x010042516769FBC191A67840731CB36B41EFDACC97BE8264281F,0,0,,2023-03-10 11:20:00,0,0,,4 -user4,269,,S,SQL_LOGIN,0,2023-04-01 10:40:00,2023-04-01 11:32:00,secondary,us_english,NULL,1,0,0x01005F3B351B26E2DB7C7FD3C7ED02B3FD2EDC09BB2BF13DA3E5,0,1,2023-04-01 11:32:00,2023-04-01 10:40:00,0,3,2023-04-01 11:30:00,2 -user5,270,,S,SQL_LOGIN,0,2023-05-05 12:33:00,2023-05-05 12:33:00,master,us_english,NULL,1,0,0x0100AE15D55972BB3D6C6283921711CD4A208747888BEEFED71B,0,0,,2023-05-05 12:33:00,0,0,,6 -user6,272,,S,SQL_LOGIN,0,2023-06-15 11:46:00,2023-06-15 11:46:00,secondary,us_english,NULL,1,1,0x0100F12FAE790FCE0FF356A0948211AE4052653503E1BBC28FAB,0,0,,2023-06-15 11:46:00,0,0,,7 -user7,279,,S,SQL_LOGIN,0,2023-07-20 12:50:00,2023-07-20 12:50:00,secondary,us_english,NULL,1,1,0x01004856A222264E62219236AB6AC7E5B622F1E53D1CCA2AF9B8,0,0,,2023-07-20 12:50:00,0,0,,8 -user8,284,,S,SQL_LOGIN,0,2023-08-25 13:56:00,2023-08-25 13:56:00,master,us_english,NULL,1,1,0x0100723BEDBE69779CD3087C0E60AD69C33CC7E969F78DA2498A,0,0,,2023-08-25 13:56:00,0,0,,9 \ No newline at end of file diff --git a/db_passwords/sql/get_data.sql b/db_passwords/sql/get_data.sql deleted file mode 100644 index b5bef36..0000000 --- a/db_passwords/sql/get_data.sql +++ /dev/null @@ -1,30 +0,0 @@ -/* -References: -1. https://learn.microsoft.com/en-us/sql/relational-databases/security/password-policy -2. https://learn.microsoft.com/en-us/sql/t-sql/functions/loginproperty-transact-sql -*/ - -SELECT - name, - principal_id, - sid, - type, - type_desc, - is_disabled, - create_date, - modify_date, - default_database_name, - default_language_name, - credential_id, - is_policy_checked, - is_expiration_checked, - password_hash, - LOGINPROPERTY(name, 'IsMustChange') AS IsMustChange, - LOGINPROPERTY(name, 'IsLocked') AS IsLocked, - LOGINPROPERTY(name, 'LockoutTime') AS LockoutTime, - LOGINPROPERTY(name, 'PasswordLastSetTime') AS PasswordLastSetTime, - LOGINPROPERTY(name, 'IsExpired') AS IsExpired, - LOGINPROPERTY(name, 'BadPasswordCount') AS BadPasswordCount, - LOGINPROPERTY(name, 'BadPasswordTime') AS BadPasswordTime, - LOGINPROPERTY(name, 'HistoryLength') AS HistoryLength -FROM sys.sql_logins; diff --git a/db_passwords/sql/test.py b/db_passwords/sql/test.py deleted file mode 100644 index bfacb20..0000000 --- a/db_passwords/sql/test.py +++ /dev/null @@ -1,77 +0,0 @@ -""" -Checks SQL Server user data for compliance with Windows policies. -""" - -# Import packages -import pandas as pd - -# Load the data into a pandas DataFrame -df_input = pd.read_csv('./data.csv') - -# Function to apply rules and generate report -def apply_rules_and_report(df): - """ - Apply defined rules against the input data. - - Parameters: - df (pandas.DataFrame): SQL login data - - Returns: - report (list): List of dictionaries containing test results - """ - report = [] - for _, row in df.iterrows(): - result = { - 'Name': row['name'], - 'Type Check': '', - 'Policy Check': '', - 'Expiration Check': '', - 'Reason': '' - } - - # Check the type_desc - if row['type_desc'] == 'SQL_LOGIN': - result['Type Check'] = 'SQL_LOGIN' - elif row['type_desc'] == 'WINDOWS_LOGIN': - result['Type Check'] = 'N/A' - result['Reason'] = 'Refer to Windows password policy.' - else: - result['Type Check'] = 'Manual Review' - result['Reason'] = 'Reviewer to manually review.' - - # Check if password policy is enforced - if row['is_policy_checked'] == 1: - result['Policy Check'] = 'PASS' - result['Reason'] += '''Password policy is enforced. Reviewer to - check the assigned policy.''' - else: - result['Policy Check'] = 'FAIL' - result['Reason'] += 'Password policy is not enforced.' - - # Check if password expiration is enforced - if row['is_expiration_checked'] == 1: - result['Expiration Check'] = 'PASS' - result['Reason'] += '''Password expiration is enforced. Reviewer to - check the expiration policy.''' - else: - result['Expiration Check'] = 'FAIL' - result['Reason'] += 'Password expiration is not enforced.' - - report.append(result) - - return report - -# Main function to run the script -def main(): - """ - Apply defined rules against the input data and print the results. - """ - # Apply rules and generate report - report = apply_rules_and_report(df_input) - report_df = pd.DataFrame(report) - - # Print the report - print(report_df) - -if __name__ == "__main__": - main() diff --git a/github/README.org b/github/README.org deleted file mode 100644 index 0ac08ae..0000000 --- a/github/README.org +++ /dev/null @@ -1,112 +0,0 @@ -#+title: GitHub Scripts - -*NOTE*: I used the same [[https://docs.github.com/en/authentication/keeping-your-account-and-data-secure/managing-your-personal-access-tokens][PAT]] for all scripts within this folder. Note that you can likely reduce permissions for certain scripts - it's best practice to define a PAT for a specific purpose and avoid using a single PAT with broad permissions. - -- Personal Access Token: - - [X] Repository Permissions - - [X] Actions: read-only - - [X] Contents: read-only - - [X] Metadata: read-only - - [X] Workflows: read-only - - [X] Organization Permissions - - [X] Administration: read-only - -* =github_admins.py= - -#+begin_src sh -python ./github_admins.py -#+end_src - -#+begin_src text -Members of the organization 'your_organization': - -Repositories in the organization 'your_organization': -- demo-repository - -Collaborators for the repository 'demo-repository': -- user1: admin -#+end_src - -* =github_audit_log.py= - -*NOTE*: Requires an active GitHub Enterprise subscription. - -#+begin_src sh -python ./github_audit_log.py -#+end_src - -#+begin_src text -TODO: Need to get an Enterprise subscription to test this script. -#+end_src - -* =github_branch_protections.py= - - -#+begin_src sh -python ./github_branch_protections.py -#+end_src - -#+begin_src text -Total branches in the repository 'demo-repository': 1 - -Branch: main -No protection settings - -Repository rulesets for 'demo-repository': -[{'id': 2311373, 'name': 'default', 'target': 'branch', 'source_type': 'Repository', 'source': 'phryq/demo-repository', 'enforcement': 'active', 'node_id': 'RRS_lACqUmVwb3NpdG9yec40LV1PzgAjRM0', '_links': {'self': {'href': 'https://api.github.com/repos/phryq/demo-repository/rulesets/2311373'}, 'html': {'href': 'https://github.com/phryq/demo-repository/rules/2311373'}}, 'created_at': '2024-10-19T15:59:35.200-05:00', 'updated_at': '2024-10-19T15:59:35.200-05:00'}] -#+end_src - -* =github_commits.py= - -#+begin_src sh -python ./github_commits.py -#+end_src - -#+begin_src text -Total commits in the repository 'demo-repository' on branch 'main': 3 - -Commit SHA: 13c488a2cdda08e4043f8ef36ced5fdd429e9718 -Author: Christian Cleberg <156287552+ccleberg@users.noreply.github.com> -Date: 2024-10-19T20:57:55Z -Message: Merge pull request #2 from phryq/1-test-issue - -fixes -URL: https://github.com/phryq/demo-repository/commit/13c488a2cdda08e4043f8ef36ced5fdd429e9718 -Files changed: - - .gitignore (added) - Additions: 0, Deletions: 0, Changes: 0 - - README.md (removed) - Additions: 0, Deletions: 4, Changes: 4 - - README.org (added) - Additions: 7, Deletions: 0, Changes: 7 - -Commit SHA: 6bfde238a2a34a93ce8ee02082eaf4ab3c189368 -Author: Christian Cleberg -Date: 2024-10-19T20:56:50Z -Message: fixes -URL: https://github.com/phryq/demo-repository/commit/6bfde238a2a34a93ce8ee02082eaf4ab3c189368 -Files changed: - - .gitignore (added) - Additions: 0, Deletions: 0, Changes: 0 - - README.md (removed) - Additions: 0, Deletions: 4, Changes: 4 - - README.org (added) - Additions: 7, Deletions: 0, Changes: 7 - -Commit SHA: be1ddf31e08fc790f54d68f8067b7b2f3805f999 -Author: Christian Cleberg <156287552+ccleberg@users.noreply.github.com> -Date: 2024-10-19T20:54:08Z -Message: Initial commit -URL: https://github.com/phryq/demo-repository/commit/be1ddf31e08fc790f54d68f8067b7b2f3805f999 -Files changed: - - .github/workflows/auto-assign.yml (added) - Additions: 19, Deletions: 0, Changes: 19 - - .github/workflows/proof-html.yml (added) - Additions: 11, Deletions: 0, Changes: 11 - - README.md (added) - Additions: 4, Deletions: 0, Changes: 4 - - index.html (added) - Additions: 1, Deletions: 0, Changes: 1 - - package.json (added) - Additions: 9, Deletions: 0, Changes: 9 -#+end_src \ No newline at end of file diff --git a/github/github_admins.py b/github/github_admins.py deleted file mode 100644 index d737887..0000000 --- a/github/github_admins.py +++ /dev/null @@ -1,76 +0,0 @@ -""" -Gather all members of a GitHub organization, all repos within that organization, -and list each user's permission per repo. -""" - -import requests - -GITHUB_TOKEN = 'your_personal_access_token' -ORGANIZATION = 'your_organization' -TIMEOUT = 30 - -# Headers for authentication -headers = { - 'Authorization': f'token {GITHUB_TOKEN}', - 'Accept': 'application/vnd.github.v3+json' -} - -def get_org_members(org): - """ - Get members of an organization - """ - url = f'https://api.github.com/orgs/{org}/members' - response = requests.get(url, headers=headers, timeout=TIMEOUT) - response.raise_for_status() - return response.json() - -def get_org_repos(org): - """ - Get repositories of an organization - """ - url = f'https://api.github.com/orgs/{org}/repos' - response = requests.get(url, headers=headers, timeout=TIMEOUT) - response.raise_for_status() - return response.json() - -def get_repo_collaborators(org, repo): - """ - Get collaborators of a repository with their permissions - """ - url = f'https://api.github.com/repos/{org}/{repo}/collaborators' - response = requests.get(url, headers=headers, timeout=TIMEOUT) - response.raise_for_status() - return response.json() - -def get_user_permissions(org, repo, user): - """ - Get a user's permissions for a repository - """ - url = f'https://api.github.com/repos/{org}/{repo}/collaborators/{user}/permission' - response = requests.get(url, headers=headers, timeout=TIMEOUT) - response.raise_for_status() - return response.json() - -# Main script -if __name__ == '__main__': - # Get organization members - members = get_org_members(ORGANIZATION) - print(f"Members of the organization '{ORGANIZATION}':") - for member in members: - print(f"- {member['login']}") - - # Get organization repositories - repositories = get_org_repos(ORGANIZATION) - print(f"\nRepositories in the organization '{ORGANIZATION}':") - for repository in repositories: - print(f"- {repository['name']}") - - # Get collaborators for each repository and their permissions - for repository in repositories: - repository_name = repository['name'] - collaborators = get_repo_collaborators(ORGANIZATION, repository_name) - print(f"\nCollaborators for the repository '{repository_name}':") - for collaborator in collaborators: - user_login = collaborator['login'] - permissions = get_user_permissions(ORGANIZATION, repository_name, user_login) - print(f"- {user_login}: {permissions['permission']}") diff --git a/github/github_audit_log.py b/github/github_audit_log.py deleted file mode 100644 index 0937764..0000000 --- a/github/github_audit_log.py +++ /dev/null @@ -1,59 +0,0 @@ -""" -Extract a specific list of events from the GitHub Audit Log API. - -NOTE: REQUIRES A GITHUB ENTERPRISE SUBSCRIPTION TO ACCESS THE API. -""" - -import requests - -GITHUB_TOKEN = 'your_personal_access_token' -ORGANIZATION = 'your_organization' -TIMEOUT = 30 - -# Headers for authentication -headers = { - 'Authorization': f'token {GITHUB_TOKEN}', - 'Accept': 'application/vnd.github.v3+json' -} - -def get_audit_log_events(org, actions): - """ - Get audit log events for specific actions - """ - events = [] - page = 1 - while True: - url = (f'https://api.github.com/orgs/{org}/audit-log?page={page}&per_page=100' - f'&action={",".join(actions)}') - response = requests.get(url, headers=headers, timeout=TIMEOUT) - response.raise_for_status() - page_events = response.json() - if not page_events: - break - events.extend(page_events) - page += 1 - return events - -if __name__ == '__main__': - try: - # Define the actions to filter - action_filters = ['protected_branch', - 'repository_branch_protection_evaluation', - 'repository_ruleset'] - - # Get audit log events for the specified actions - audit_log_events = get_audit_log_events(ORGANIZATION, action_filters) - print(f"Total audit log events for specified actions: {len(audit_log_events)}") - - # Print detailed information for each event - for event in audit_log_events: - print(f"\nEvent ID: {event['@id']}") - print(f"Action: {event['action']}") - print(f"Actor: {event['actor']}") - print(f"Repository: {event.get('repo', 'N/A')}") - print(f"Created At: {event['created_at']}") - print(f"Details: {event}") - except requests.exceptions.Timeout: - print("The request timed out") - except requests.exceptions.RequestException as e: - print(f"An error occurred: {e}") diff --git a/github/github_branch_protections.py b/github/github_branch_protections.py deleted file mode 100644 index 73c94b6..0000000 --- a/github/github_branch_protections.py +++ /dev/null @@ -1,78 +0,0 @@ -""" -Gathers branch protection rules for a repository. -""" - -import requests - -GITHUB_TOKEN = 'your_personal_access_token' -ORGANIZATION = 'your_organization' -REPOSITORY = 'your_repository' -TIMEOUT = 30 - -headers = { - 'Authorization': f'token {GITHUB_TOKEN}', - 'Accept': 'application/vnd.github.v3+json' -} - -def get_all_branches(org, repo): - """ - Get all branches in a repository - """ - all_branches = [] - page = 1 - while True: - url = f'https://api.github.com/repos/{org}/{repo}/branches?page={page}&per_page=100' - response = requests.get(url, headers=headers, timeout=TIMEOUT) - response.raise_for_status() - page_branches = response.json() - if not page_branches: - break - all_branches.extend(page_branches) - page += 1 - return all_branches - -def get_branch_protection(org, repo, repo_branch): - """ - Get branch protection settings - """ - url = f'https://api.github.com/repos/{org}/{repo}/branches/{repo_branch}/protection' - response = requests.get(url, headers=headers, timeout=TIMEOUT) - if response.status_code == 404: - return None # No protection settings for this branch - response.raise_for_status() - return response.json() - -def get_repository_rulesets(org, repo): - """ - Get repository rulesets - """ - url = f'https://api.github.com/repos/{org}/{repo}/rulesets' - response = requests.get(url, headers=headers, timeout=TIMEOUT) - response.raise_for_status() - return response.json() - -if __name__ == '__main__': - try: - # Get all branches in the repository - branches = get_all_branches(ORGANIZATION, REPOSITORY) - print(f"Total branches in the repository '{REPOSITORY}': {len(branches)}") - - # Get protection settings for each branch - for branch in branches: - branch_name = branch['name'] - protection_settings = get_branch_protection(ORGANIZATION, REPOSITORY, branch_name) - print(f"\nBranch: {branch_name}") - if protection_settings: - print(f"Protection settings: {protection_settings}") - else: - print("No protection settings") - - # Get repository rulesets - rulesets = get_repository_rulesets(ORGANIZATION, REPOSITORY) - print(f"\nRepository rulesets for '{REPOSITORY}':") - print(rulesets) - - except requests.exceptions.Timeout: - print("The request timed out") - except requests.exceptions.RequestException as e: - print(f"An error occurred: {e}") diff --git a/github/github_commits.py b/github/github_commits.py deleted file mode 100644 index f35d5d6..0000000 --- a/github/github_commits.py +++ /dev/null @@ -1,75 +0,0 @@ -""" -Gather all commits from a specific branch of a repository in a GitHub organization. -""" - -import requests - -GITHUB_TOKEN = 'your_personal_access_token' -ORGANIZATION = 'your_organization' -REPOSITORY = 'your_repository' -BRANCH = 'your_branch' - -# Headers for authentication -headers = { - 'Authorization': f'token {GITHUB_TOKEN}', - 'Accept': 'application/vnd.github.v3+json' -} - -# Define a timeout value (in seconds) -TIMEOUT = 10 - -def get_commit_log(org, repo, branch): - """ - Get the full commit log for a repository branch - """ - commits = [] - page = 1 - while True: - url = (f'https://api.github.com/repos/{org}/{repo}/commits?sha={branch}' - f'&page={page}&per_page=100') - response = requests.get(url, headers=headers, timeout=TIMEOUT) - response.raise_for_status() - page_commits = response.json() - if not page_commits: - break - commits.extend(page_commits) - page += 1 - return commits - -def get_commit_details(org, repo, sha): - """ - Get detailed information for a specific commit - """ - url = f'https://api.github.com/repos/{org}/{repo}/commits/{sha}' - response = requests.get(url, headers=headers, timeout=TIMEOUT) - response.raise_for_status() - return response.json() - -if __name__ == '__main__': - try: - # Get the full commit log for the specified branch - commit_log = get_commit_log(ORGANIZATION, REPOSITORY, BRANCH) - print(f"Total commits in the repository '{REPOSITORY}' on branch " - f"'{BRANCH}': {len(commit_log)}") - - # Get detailed information for each commit - for commit in commit_log: - sha_hash = commit['sha'] - commit_details = get_commit_details(ORGANIZATION, REPOSITORY, - sha_hash) - print(f"\nCommit SHA: {commit_details['sha']}") - print(f"Author: {commit_details['commit']['author']['name']} " - f"<{commit_details['commit']['author']['email']}>") - print(f"Date: {commit_details['commit']['author']['date']}") - print(f"Message: {commit_details['commit']['message']}") - print(f"URL: {commit_details['html_url']}") - print("Files changed:") - for file in commit_details['files']: - print(f" - {file['filename']} ({file['status']})") - print(f" Additions: {file['additions']}, " - f"Deletions: {file['deletions']}, " - f"Changes: {file['changes']}") - except requests.exceptions.Timeout: - print("The request timed out") - except requests.exceptions.RequestException as e: - print(f"An error occurred: {e}") -- cgit v1.2.3-70-g09d2