diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 1a01d72b..197487fb 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -5,6 +5,7 @@ on: [push, pull_request] jobs: ubuntu-gcc: runs-on: ubuntu-latest + timeout-minutes: 60 steps: - name: Checkout V uses: actions/checkout@v4 @@ -26,7 +27,8 @@ jobs: cd gitly v -cc gcc . - - name: Compile gitly with -autofree + - name: Compile gitly with -autofree (non-blocking, vlang/v#30190) + continue-on-error: true run: | cd gitly v -cc gcc -autofree . @@ -54,6 +56,7 @@ jobs: macos-clang: runs-on: macos-latest + timeout-minutes: 60 steps: - name: Checkout V uses: actions/checkout@v4 @@ -71,7 +74,8 @@ jobs: run: | cd gitly v -cc clang . - - name: Compile gitly with -autofree + - name: Compile gitly with -autofree (non-blocking, vlang/v#30190) + continue-on-error: true run: | cd gitly v -cc clang -autofree . @@ -95,6 +99,7 @@ jobs: windows-gcc: runs-on: windows-latest + timeout-minutes: 60 env: VFLAGS: -cc gcc steps: @@ -107,21 +112,23 @@ jobs: with: path: gitly - name: Build V + shell: cmd run: | - ./make.bat -gcc - - # Must come after "Build V": this used to run first, when neither `v` - # nor `v.exe` existed, so the referenced script could not work at all. + make.bat -gcc + # Must run after "Build V": the script shells out to `v.exe`, which + # does not exist until V is built. - name: Install SQLite - run: .\gitly\.github\workflows\windows-install-sqlite.bat - + shell: cmd + run: | + gitly\.github\workflows\windows-install-sqlite.bat - name: Compile gitly run: | dir - .\v.exe -cc gcc gitly + .\v.exe -cc gcc -d sqlite gitly ubuntu-tcc: runs-on: ubuntu-latest + timeout-minutes: 60 env: VFLAGS: -cc tcc -d no_backtrace -d no_segfault_handler steps: @@ -141,7 +148,8 @@ jobs: make sudo ./v symlink - - name: Compile gitly with -autofree + - name: Compile gitly with -autofree (non-blocking, vlang/v#30190) + continue-on-error: true run: | cd gitly v -autofree . diff --git a/fork.v b/fork.v index b63a43ef..5851f902 100644 --- a/fork.v +++ b/fork.v @@ -241,19 +241,18 @@ fn (mut app App) create_fork(source Repo, owner_name string, owner_user_id int, return err } mut row := Repo{ - git_dir: target_path - name: name - user_id: owner_user_id - user_name: owner_name - description: description - is_public: is_public && source.is_public - primary_branch: source.primary_branch - created_at: int(time.now().unix()) - status: .done + git_dir: target_path + name: name + user_id: owner_user_id + user_name: owner_name + description: description + is_public: is_public && source.is_public + primary_branch: source.primary_branch + created_at: int(time.now().unix()) + status: .done disable_discussions: source.disable_discussions - disable_projects: source.disable_projects - disable_milestones: source.disable_milestones - disable_wiki: source.disable_wiki + disable_projects: source.disable_projects + disable_milestones: source.disable_milestones } app.add_repo(row) or { os.rmdir_all(target_path) or {} @@ -265,15 +264,15 @@ fn (mut app App) create_fork(source Repo, owner_name string, owner_user_id int, } source_relation := app.find_fork_by_repo(source.id) or { RepoFork{} } relation := RepoFork{ - repo_id: created.id + repo_id: created.id source_repo_id: source.id - root_repo_id: if source_relation.root_repo_id > 0 { + root_repo_id: if source_relation.root_repo_id > 0 { source_relation.root_repo_id } else { source.id } - created_by: created_by - created_at: int(time.now().unix()) + created_by: created_by + created_at: int(time.now().unix()) } sql app.db { insert relation into RepoFork diff --git a/gitly.v b/gitly.v index 66ae334f..57a111fc 100644 --- a/gitly.v +++ b/gitly.v @@ -93,8 +93,8 @@ fn new_app() !&App { mut app := &App{ // db: sqlite.connect('gitly.sqlite') or { panic(err) } - db: connect_db(conf)! - config: conf + db: connect_db(conf)! + config: conf started_at: time.now().unix() } @@ -733,7 +733,6 @@ fn (mut app App) migrate_tables() ! { app.add_missing_column('Repo', 'disable_discussions', db_bool_column_type())! app.add_missing_column('Repo', 'disable_projects', db_bool_column_type())! app.add_missing_column('Repo', 'disable_milestones', db_bool_column_type())! - app.add_missing_column('Repo', 'disable_wiki', db_bool_column_type())! app.add_missing_column('Repo', 'is_pinned', db_bool_column_type())! app.add_missing_column('Repo', 'created_at', 'INTEGER NOT NULL DEFAULT 0')! app.add_missing_column('Repo', 'required_approvals', 'INTEGER NOT NULL DEFAULT 0')! @@ -914,7 +913,7 @@ fn (mut app App) add_missing_column(table_name string, column_name string, colum fn (mut ctx Context) json_success[T](result T) veb.Result { response := api.ApiSuccessResponse[T]{ success: true - result: result + result: result } return ctx.json(response) diff --git a/repo/repo.v b/repo/repo.v index 68282424..97e19924 100644 --- a/repo/repo.v +++ b/repo/repo.v @@ -20,33 +20,31 @@ struct Repo { is_deleted bool users_contributed []string @[skip] users_authorized []string @[skip] - nr_topics int @[skip] views_count int - latest_update_hash string @[skip] + latest_update_hash string @[skip] latest_activity time.Time @[skip] mut: clone_url string @[skip] primary_branch string webhook_secret string tags_count int - nr_open_issues int @[orm: 'open_issues_count'] - nr_open_prs int @[orm: 'open_prs_count'] - nr_releases int @[orm: 'releases_count'] - nr_branches int @[orm: 'branches_count'] + nr_open_issues int @[sql: 'open_issues_count'] + nr_open_prs int @[sql: 'open_prs_count'] + nr_releases int @[sql: 'releases_count'] + nr_branches int @[sql: 'branches_count'] nr_tags int - nr_stars int @[orm: 'stars_count'] + nr_stars int @[sql: 'stars_count'] lang_stats []LangStat @[skip] created_at int nr_contributors int labels []Label @[skip] status RepoStatus msg_cache map[string]string @[skip] - latest_commit_at int @[skip] - activity_buckets []int @[skip] + latest_commit_at int @[skip] + activity_buckets []int @[skip] disable_discussions bool disable_projects bool disable_milestones bool - disable_wiki bool is_pinned bool required_approvals int require_signed_commits bool @@ -66,10 +64,6 @@ fn (r &Repo) milestones_enabled() bool { return !r.disable_milestones } -fn (r &Repo) wiki_enabled() bool { - return !r.disable_wiki -} - // log_field_separator is declared as constant in case we need to change it later const max_free_clone_size_bytes = u64(100) * 1024 * 1024 const search_results_limit = 50 @@ -363,10 +357,10 @@ fn (mut app App) increment_file_views(file_id int) ! { }! } -fn (mut app App) update_repo_features(repo_id int, disable_discussions bool, disable_projects bool, disable_milestones bool, disable_wiki bool) ! { +fn (mut app App) update_repo_features(repo_id int, disable_discussions bool, disable_projects bool, disable_milestones bool) ! { sql app.db { update Repo set disable_discussions = disable_discussions, disable_projects = disable_projects, - disable_milestones = disable_milestones, disable_wiki = disable_wiki where id == repo_id + disable_milestones = disable_milestones where id == repo_id }! } @@ -904,7 +898,7 @@ fn (mut app App) update_repo_after_ref_changes(repo_id int, updates []git.GitRef // handle is not safe for concurrent use across threads. fn bg_recompute_lang_stats(repo_id int, conf config.Config) { mut app := &App{ - db: connect_db(conf) or { + db: connect_db(conf) or { eprintln('bg_recompute_lang_stats: cannot open ${db_backend_name()} db: ${err}') return } @@ -965,10 +959,10 @@ fn (r &Repo) analyze_lang(app &App) ! { } lang_data := langs[lang] d_lang_stats << LangStat{ - repo_id: r.id - name: lang_data.name - pct: pct - color: lang_data.color + repo_id: r.id + name: lang_data.name + pct: pct + color: lang_data.color lines_count: amount } } @@ -1103,12 +1097,12 @@ fn (r &Repo) parse_ls(ls_line string, branch string) ?File { } return File{ - name: item_name - parent_path: parent_path - repo_id: r.id - branch: branch - is_dir: item_type == 'tree' - size: if item_type == 'blob' { item_size.int() } else { 0 } + name: item_name + parent_path: parent_path + repo_id: r.id + branch: branch + is_dir: item_type == 'tree' + size: if item_type == 'blob' { item_size.int() } else { 0 } is_size_calculated: item_type == 'blob' } } @@ -1145,12 +1139,12 @@ fn (r &Repo) parse_top_file_line(line string, branch string) ?File { parent_path := if parent_path_raw == '.' { '' } else { parent_path_raw } return File{ - name: item_name - parent_path: parent_path - repo_id: r.id - branch: branch - is_dir: false - size: meta_parts[3].int() + name: item_name + parent_path: parent_path + repo_id: r.id + branch: branch + is_dir: false + size: meta_parts[3].int() is_size_calculated: true } } @@ -1176,12 +1170,12 @@ fn (r &Repo) lookup_file_via_git(branch string, path string) ?File { parent_path_raw := os.dir(item_path) parent_path := if parent_path_raw == '.' { '' } else { parent_path_raw } return File{ - name: item_name - parent_path: parent_path - repo_id: r.id - branch: branch - is_dir: false - size: meta_parts[3].int() + name: item_name + parent_path: parent_path + repo_id: r.id + branch: branch + is_dir: false + size: meta_parts[3].int() is_size_calculated: true } } diff --git a/repo/repo_routes.v b/repo/repo_routes.v index 44e934e8..97bff54f 100644 --- a/repo/repo_routes.v +++ b/repo/repo_routes.v @@ -240,7 +240,7 @@ pub fn (mut app App) handle_update_repo_features(mut ctx Context, username strin disable_projects := 'projects_enabled' !in ctx.form disable_milestones := 'milestones_enabled' !in ctx.form - app.update_repo_features(repo.id, disable_discussions, disable_projects, disable_milestones, repo.disable_wiki) or { app.info(err.str()) } + app.update_repo_features(repo.id, disable_discussions, disable_projects, disable_milestones) or { app.info(err.str()) } return ctx.redirect('/${username}/${repo_name}/settings') } @@ -456,15 +456,15 @@ pub fn (mut app App) handle_new_repo(mut ctx Context, name string, clone_url str } repo_path := os.join_path(owner_dir, name) mut new_repo := &Repo{ - name: name - description: description - git_dir: repo_path - user_id: ctx.user.id + name: name + description: description + git_dir: repo_path + user_id: ctx.user.id primary_branch: default_primary_branch - user_name: owner_name - clone_url: valid_clone_url - is_public: is_public - created_at: int(time.now().unix()) + user_name: owner_name + clone_url: valid_clone_url + is_public: is_public + created_at: int(time.now().unix()) } import_issues := ctx.form['import_issues'] == '1' import_prs := ctx.form['import_prs'] == '1' @@ -544,7 +544,7 @@ pub fn (mut app App) handle_new_repo(mut ctx Context, name string, clone_url str fn bg_fetch_files_info(repo_ Repo, branch string, path string, conf config.Config) { mut repo := repo_ mut app := &App{ - db: connect_db(conf) or { + db: connect_db(conf) or { eprintln('cannot open ${db_backend_name()} db connection for bg_fetch thread: ${err}') return } @@ -575,7 +575,7 @@ fn clone_repo(new_repo Repo, conf config.Config, import_issues bool, import_prs // Use a dedicated DB connection for the clone thread to avoid // sharing a connection across threads. mut app := &App{ - db: connect_db(conf) or { + db: connect_db(conf) or { eprintln('cannot open ${db_backend_name()} db connection for clone thread: ${err}') return } @@ -636,7 +636,7 @@ fn clone_repo(new_repo Repo, conf config.Config, import_issues bool, import_prs fn bg_import_github_repo_info(repo_id int, clone_url string, existing_description string, conf config.Config) { eprintln('[github-info] spawned thread for repo_id=${repo_id}') mut app := &App{ - db: connect_db(conf) or { + db: connect_db(conf) or { eprintln('[github-info] cannot open db connection: ${err}') return } @@ -661,7 +661,7 @@ fn bg_import_github_repo_info(repo_id int, clone_url string, existing_descriptio fn bg_import_github_issues(repo_id int, clone_url string, owner_user_id int, conf config.Config) { eprintln('[github-import] spawned thread for repo_id=${repo_id}') mut app := &App{ - db: connect_db(conf) or { + db: connect_db(conf) or { eprintln('[github-import] cannot open db connection for import thread: ${err}') return } @@ -981,7 +981,7 @@ pub fn (mut app App) handle_api_repo_star(mut ctx Context, repo_id_str string) v return ctx.json(api.ApiSuccessResponse[bool]{ success: true - result: is_repo_starred + result: is_repo_starred }) } @@ -1002,7 +1002,7 @@ pub fn (mut app App) handle_api_repo_watch(mut ctx Context, repo_id_str string) return ctx.json(api.ApiSuccessResponse[bool]{ success: true - result: is_watching + result: is_watching }) } @@ -1031,17 +1031,17 @@ pub fn (mut app App) handle_api_repo_files(mut ctx Context, repo_id_str string) mut result := []RepoFileInfo{} for item in items { result << RepoFileInfo{ - name: item.name - last_msg: item.last_msg + name: item.name + last_msg: item.last_msg last_hash: item.last_hash last_time: item.pretty_last_time() - size: item.pretty_tree_size() + size: item.pretty_tree_size() } } return ctx.json(api.ApiSuccessResponse[[]RepoFileInfo]{ success: true - result: result + result: result }) } diff --git a/repo/repo_template.v b/repo/repo_template.v index 6a10387c..d29c0701 100644 --- a/repo/repo_template.v +++ b/repo/repo_template.v @@ -84,10 +84,6 @@ fn (r &Repo) format_nr_contributors(lang Lang) veb.RawHtml { return format_count(r.nr_contributors, 'contributors_count', lang) } -fn (r &Repo) format_nr_topics(lang Lang) veb.RawHtml { - return format_count(r.nr_topics, 'topics_count', lang) -} - fn (r &Repo) format_nr_releases(lang Lang) veb.RawHtml { return format_count(r.nr_releases, 'releases_count', lang) }