From efa6f33b4c67f64a4a8d8cd723b9bbc9494fc735 Mon Sep 17 00:00:00 2001 From: Runxi Yu Date: Sat, 05 Apr 2025 21:47:44 +0800 Subject: [PATCH] Unexport fields in Server --- acl.go | 2 +- config.go | 8 ++++---- database.go | 2 +- fedauth.go | 2 +- git2d_deploy.go | 2 +- git_hooks_deploy.go | 6 +++--- git_hooks_handle_linux.go | 10 +++++----- git_init.go | 2 +- git_misc.go | 2 +- http_auth.go | 2 +- http_handle_group_index.go | 14 +++++++------- http_handle_login.go | 6 +++--- http_handle_repo_contrib_index.go | 2 +- http_handle_repo_contrib_one.go | 2 +- http_handle_repo_index.go | 2 +- http_handle_repo_info.go | 2 +- http_handle_repo_raw.go | 2 +- http_handle_repo_tree.go | 2 +- http_handle_repo_upload_pack.go | 4 ++-- http_server.go | 10 +++++----- irc.go | 24 ++++++++++++------------ lmtp_server.go | 16 ++++++++-------- remote_url.go | 4 ++-- server.go | 98 +++++++++++++++++++++++++++--------------------------- ssh_handle_receive_pack.go | 8 ++++---- ssh_handle_upload_pack.go | 2 +- ssh_server.go | 10 +++++----- users.go | 2 +- diff --git a/acl.go b/acl.go index c4bf29fe4f992004c6b15669619f93eed883b410..aaf190ba79f2a74c6fea09f58154b39eb3ac0865 100644 --- a/acl.go +++ b/acl.go @@ -14,7 +14,7 @@ // given repo and a provided ssh public key. // // TODO: Revamp. func (s *Server) getRepoInfo(ctx context.Context, groupPath []string, repoName, sshPubkey string) (repoID int, fsPath string, access bool, contribReq, userType string, userID int, err error) { - err = s.Database.QueryRow(ctx, ` + err = s.database.QueryRow(ctx, ` WITH RECURSIVE group_path_cte AS ( -- Start: match the first name in the path where parent_group IS NULL SELECT diff --git a/config.go b/config.go index 84633eafa22b66ad06bb46b6e02ae95c5949d4c3..35484783b76fa65703b22da42faa042210df90c4 100644 --- a/config.go +++ b/config.go @@ -84,19 +84,19 @@ } defer configFile.Close() decoder := scfg.NewDecoder(bufio.NewReader(configFile)) - if err = decoder.Decode(&s.Config); err != nil { + if err = decoder.Decode(&s.config); err != nil { return err } - if s.Config.DB.Type != "postgres" { + if s.config.DB.Type != "postgres" { return errors.New("unsupported database type") } - if s.Database, err = pgxpool.New(context.Background(), s.Config.DB.Conn); err != nil { + if s.database, err = pgxpool.New(context.Background(), s.config.DB.Conn); err != nil { return err } - s.GlobalData["forge_title"] = s.Config.General.Title + s.globalData["forge_title"] = s.config.General.Title return nil } diff --git a/database.go b/database.go index a627f2d9a07a1042cbba9fdbcf4250a025ba3335..edfadbf28f7972c6bd77db31ad77488d42463d9f 100644 --- a/database.go +++ b/database.go @@ -21,7 +21,7 @@ // name and a description. func (s *Server) QueryNameDesc(ctx context.Context, query string, args ...any) (result []NameDesc, err error) { var rows pgx.Rows - if rows, err = s.Database.Query(ctx, query, args...); err != nil { + if rows, err = s.database.Query(ctx, query, args...); err != nil { return nil, err } defer rows.Close() diff --git a/fedauth.go b/fedauth.go index fd84047004b755bf7ade0e78ccd152a13e340286..7866e581416f7b73d6d0e28125f82a730abaea92 100644 --- a/fedauth.go +++ b/fedauth.go @@ -77,7 +77,7 @@ return false, nil } var txn pgx.Tx - if txn, err = s.Database.Begin(ctx); err != nil { + if txn, err = s.database.Begin(ctx); err != nil { return false, err } defer func() { diff --git a/git2d_deploy.go b/git2d_deploy.go index 5a5f336b44411ebd5e36443d2ddbd077d8588088..b75b63abf1974962417cdc54f3f133938c5447f0 100644 --- a/git2d_deploy.go +++ b/git2d_deploy.go @@ -18,7 +18,7 @@ return err } defer srcFD.Close() - if dstFD, err = os.OpenFile(s.Config.Git.DaemonPath, os.O_WRONLY|os.O_CREATE|os.O_TRUNC, 0o755); err != nil { + if dstFD, err = os.OpenFile(s.config.Git.DaemonPath, os.O_WRONLY|os.O_CREATE|os.O_TRUNC, 0o755); err != nil { return err } defer dstFD.Close() diff --git a/git_hooks_deploy.go b/git_hooks_deploy.go index eeda995637ae65b045a982c863379e45115df30d..afab7f036af14bb189ee84ee7fc45b1beeb145eb 100644 --- a/git_hooks_deploy.go +++ b/git_hooks_deploy.go @@ -24,7 +24,7 @@ return err } defer srcFD.Close() - if dstFD, err = os.OpenFile(filepath.Join(s.Config.Hooks.Execs, "hookc"), os.O_WRONLY|os.O_CREATE|os.O_TRUNC, 0o755); err != nil { + if dstFD, err = os.OpenFile(filepath.Join(s.config.Hooks.Execs, "hookc"), os.O_WRONLY|os.O_CREATE|os.O_TRUNC, 0o755); err != nil { return err } defer dstFD.Close() @@ -41,14 +41,14 @@ } // Go's embed filesystems do not store permissions; but in any case, // they would need to be 0o755: - if err = os.Chmod(filepath.Join(s.Config.Hooks.Execs, "hookc"), 0o755); err != nil { + if err = os.Chmod(filepath.Join(s.config.Hooks.Execs, "hookc"), 0o755); err != nil { return err } for _, hookName := range []string{ "pre-receive", } { - if err = os.Symlink(filepath.Join(s.Config.Hooks.Execs, "hookc"), filepath.Join(s.Config.Hooks.Execs, hookName)); err != nil { + if err = os.Symlink(filepath.Join(s.config.Hooks.Execs, "hookc"), filepath.Join(s.config.Hooks.Execs, hookName)); err != nil { if !errors.Is(err, fs.ErrExist) { return err } diff --git a/git_hooks_handle_linux.go b/git_hooks_handle_linux.go index 3d8c0110443d1877dbea2794f1305c34ad3fae8e..aba47d3e10088417150458561dd4131dbb916602 100644 --- a/git_hooks_handle_linux.go +++ b/git_hooks_handle_linux.go @@ -77,7 +77,7 @@ } { var ok bool - packPass, ok = s.PackPasses.Load(misc.BytesToString(cookie)) + packPass, ok = s.packPasses.Load(misc.BytesToString(cookie)) if !ok { if _, err = conn.Write([]byte{1}); err != nil { return @@ -233,12 +233,12 @@ fmt.Fprintln(sshStderr, ansiec.Blue+"POK"+ansiec.Reset, refName) var newMRLocalID int if packPass.userID != 0 { - err = s.Database.QueryRow(ctx, + err = s.database.QueryRow(ctx, "INSERT INTO merge_requests (repo_id, creator, source_ref, status) VALUES ($1, $2, $3, 'open') RETURNING repo_local_id", packPass.repoID, packPass.userID, strings.TrimPrefix(refName, "refs/heads/"), ).Scan(&newMRLocalID) } else { - err = s.Database.QueryRow(ctx, + err = s.database.QueryRow(ctx, "INSERT INTO merge_requests (repo_id, source_ref, status) VALUES ($1, $2, 'open') RETURNING repo_local_id", packPass.repoID, strings.TrimPrefix(refName, "refs/heads/"), ).Scan(&newMRLocalID) @@ -251,7 +251,7 @@ mergeRequestWebURL := fmt.Sprintf("%s/contrib/%d/", s.genHTTPRemoteURL(packPass.groupPath, packPass.repoName), newMRLocalID) fmt.Fprintln(sshStderr, ansiec.Blue+"Created merge request at", mergeRequestWebURL+ansiec.Reset) select { - case s.IrcSendBuffered <- "PRIVMSG #chat :New merge request at " + mergeRequestWebURL: + case s.ircSendBuffered <- "PRIVMSG #chat :New merge request at " + mergeRequestWebURL: default: slog.Error("IRC SendQ exceeded") } @@ -259,7 +259,7 @@ } else { // Existing contrib branch var existingMRUser int var isAncestor bool - err = s.Database.QueryRow(ctx, + err = s.database.QueryRow(ctx, "SELECT COALESCE(creator, 0) FROM merge_requests WHERE source_ref = $1 AND repo_id = $2", strings.TrimPrefix(refName, "refs/heads/"), packPass.repoID, ).Scan(&existingMRUser) diff --git a/git_init.go b/git_init.go index b448451ad5051513d7e6daf92a9949baa8e61c6b..d1922eed2757251cbd81c60efebd7e595d6f2c0a 100644 --- a/git_init.go +++ b/git_init.go @@ -23,7 +23,7 @@ if gitConf, err = repo.Config(); err != nil { return err } - gitConf.Raw.SetOption("core", gitFmtConfig.NoSubsection, "hooksPath", s.Config.Hooks.Execs) + gitConf.Raw.SetOption("core", gitFmtConfig.NoSubsection, "hooksPath", s.config.Hooks.Execs) gitConf.Raw.SetOption("receive", gitFmtConfig.NoSubsection, "advertisePushOptions", "true") if err = repo.SetConfig(gitConf); err != nil { diff --git a/git_misc.go b/git_misc.go index 8ba10e1343841a9f17acc51a6c73dc4ca93ba77b..37f427b373e51e3a0a2ada673388c0a16f8a15cb 100644 --- a/git_misc.go +++ b/git_misc.go @@ -23,7 +23,7 @@ // TODO: This should be deprecated in favor of doing it in the relevant // request/router context in the future, as it cannot cover the nuance of // fields needed. func (s *Server) openRepo(ctx context.Context, groupPath []string, repoName string) (repo *git.Repository, description string, repoID int, fsPath string, err error) { - err = s.Database.QueryRow(ctx, ` + err = s.database.QueryRow(ctx, ` WITH RECURSIVE group_path_cte AS ( -- Start: match the first name in the path where parent_group IS NULL SELECT diff --git a/http_auth.go b/http_auth.go index 5ba278bb69141993ead568d6d23bf9362439912d..44e087dc79fa4b13e44b214c731e4009744cd7a1 100644 --- a/http_auth.go +++ b/http_auth.go @@ -16,7 +16,7 @@ if sessionCookie, err = request.Cookie("session"); err != nil { return } - err = s.Database.QueryRow( + err = s.database.QueryRow( request.Context(), "SELECT user_id, COALESCE(username, '') FROM users u JOIN sessions s ON u.id = s.user_id WHERE s.session_id = $1;", sessionCookie.Value, diff --git a/http_handle_group_index.go b/http_handle_group_index.go index 3f6ed68165ed483f15e493a7a61782be13f6d747..bb9c94f0fe67c8318da88427957ef21934a06e3e 100644 --- a/http_handle_group_index.go +++ b/http_handle_group_index.go @@ -28,7 +28,7 @@ groupPath = params["group_path"].([]string) // The group itself - err = s.Database.QueryRow(request.Context(), ` + err = s.database.QueryRow(request.Context(), ` WITH RECURSIVE group_path_cte AS ( SELECT id, @@ -69,7 +69,7 @@ } // ACL var count int - err = s.Database.QueryRow(request.Context(), ` + err = s.database.QueryRow(request.Context(), ` SELECT COUNT(*) FROM user_group_roles WHERE user_id = $1 @@ -96,7 +96,7 @@ return } var newRepoID int - err := s.Database.QueryRow( + err := s.database.QueryRow( request.Context(), `INSERT INTO repos (name, description, group_id, contrib_requirements) VALUES ($1, $2, $3, $4) @@ -111,9 +111,9 @@ errorPage500(writer, params, "Error creating repo: "+err.Error()) return } - filePath := filepath.Join(s.Config.Git.RepoDir, strconv.Itoa(newRepoID)+".git") + filePath := filepath.Join(s.config.Git.RepoDir, strconv.Itoa(newRepoID)+".git") - _, err = s.Database.Exec( + _, err = s.database.Exec( request.Context(), `UPDATE repos SET filesystem_path = $1 @@ -137,7 +137,7 @@ } // Repos var rows pgx.Rows - rows, err = s.Database.Query(request.Context(), ` + rows, err = s.database.Query(request.Context(), ` SELECT name, COALESCE(description, '') FROM repos WHERE group_id = $1 @@ -162,7 +162,7 @@ return } // Subgroups - rows, err = s.Database.Query(request.Context(), ` + rows, err = s.database.Query(request.Context(), ` SELECT name, COALESCE(description, '') FROM groups WHERE parent_group = $1 diff --git a/http_handle_login.go b/http_handle_login.go index e02ba10861658678c82e9b8d04122974d5b989c3..e6267190e65f0aece20b5d9c9cd53cc620b4501c 100644 --- a/http_handle_login.go +++ b/http_handle_login.go @@ -35,7 +35,7 @@ username = request.PostFormValue("username") password = request.PostFormValue("password") - err = s.Database.QueryRow(request.Context(), + err = s.database.QueryRow(request.Context(), "SELECT id, COALESCE(password, '') FROM users WHERE username = $1", username, ).Scan(&userID, &passwordHash) @@ -71,7 +71,7 @@ return } now = time.Now() - expiry = now.Add(time.Duration(s.Config.HTTP.CookieExpiry) * time.Second) + expiry = now.Add(time.Duration(s.config.HTTP.CookieExpiry) * time.Second) cookie = http.Cookie{ Name: "session", @@ -85,7 +85,7 @@ } //exhaustruct:ignore http.SetCookie(writer, &cookie) - _, err = s.Database.Exec(request.Context(), "INSERT INTO sessions (user_id, session_id) VALUES ($1, $2)", userID, cookieValue) + _, err = s.database.Exec(request.Context(), "INSERT INTO sessions (user_id, session_id) VALUES ($1, $2)", userID, cookieValue) if err != nil { errorPage500(writer, params, "Error inserting session: "+err.Error()) return diff --git a/http_handle_repo_contrib_index.go b/http_handle_repo_contrib_index.go index f729cbe82ba7478c180a20f4274e6f6228a21f3e..a4b1eacabcf00b7ddbd4013f381dc81cad5bd184 100644 --- a/http_handle_repo_contrib_index.go +++ b/http_handle_repo_contrib_index.go @@ -23,7 +23,7 @@ var rows pgx.Rows var result []idTitleStatus var err error - if rows, err = s.Database.Query(request.Context(), + if rows, err = s.database.Query(request.Context(), "SELECT repo_local_id, COALESCE(title, 'Untitled'), status FROM merge_requests WHERE repo_id = $1", params["repo_id"], ); err != nil { diff --git a/http_handle_repo_contrib_one.go b/http_handle_repo_contrib_one.go index 9a261a45ea57c1d22c9f21a41d49aee17a860736..55af74c759bbe9355637bcf4e4c1eef0e6e99f25 100644 --- a/http_handle_repo_contrib_one.go +++ b/http_handle_repo_contrib_one.go @@ -33,7 +33,7 @@ return } mrIDInt = int(mrIDInt64) - if err = s.Database.QueryRow(request.Context(), + if err = s.database.QueryRow(request.Context(), "SELECT COALESCE(title, ''), status, source_ref, COALESCE(destination_branch, '') FROM merge_requests WHERE repo_id = $1 AND repo_local_id = $2", params["repo_id"], mrIDInt, ).Scan(&title, &status, &srcRefStr, &dstBranchStr); err != nil { diff --git a/http_handle_repo_index.go b/http_handle_repo_index.go index 40fd9b0ca4a87143a254058d31202adedcc1f139..d28311b8e3a4e544703b209e97f6bf9178422afb 100644 --- a/http_handle_repo_index.go +++ b/http_handle_repo_index.go @@ -25,7 +25,7 @@ groupPath := params["group_path"].([]string) _, repoPath, _, _, _, _, _ := s.getRepoInfo(req.Context(), groupPath, repoName, "") // TODO: Don't use getRepoInfo - client, err := git2c.NewClient(s.Config.Git.Socket) + client, err := git2c.NewClient(s.config.Git.Socket) if err != nil { errorPage500(w, params, err.Error()) return diff --git a/http_handle_repo_info.go b/http_handle_repo_info.go index e2080acf4216cd6d41740ae8cf24b11c16fe281e..303fad7e6e2028acb0258e08d95cf3cc44e75290 100644 --- a/http_handle_repo_info.go +++ b/http_handle_repo_info.go @@ -21,7 +21,7 @@ groupPath := params["group_path"].([]string) repoName := params["repo_name"].(string) var repoPath string - if err := s.Database.QueryRow(request.Context(), ` + if err := s.database.QueryRow(request.Context(), ` WITH RECURSIVE group_path_cte AS ( -- Start: match the first name in the path where parent_group IS NULL SELECT diff --git a/http_handle_repo_raw.go b/http_handle_repo_raw.go index b714397e5200867003dea84c6f8f60cf1ed0716b..0407574e5e4d7dad8e6c81725e5e8697c3fe9cb4 100644 --- a/http_handle_repo_raw.go +++ b/http_handle_repo_raw.go @@ -24,7 +24,7 @@ params["path_spec"] = pathSpec _, repoPath, _, _, _, _, _ := s.getRepoInfo(request.Context(), groupPath, repoName, "") - client, err := git2c.NewClient(s.Config.Git.Socket) + client, err := git2c.NewClient(s.config.Git.Socket) if err != nil { errorPage500(writer, params, err.Error()) return diff --git a/http_handle_repo_tree.go b/http_handle_repo_tree.go index 00c682148932a6138817077334e597b36305ed1a..7667435ce5ffdd0abe94eb3f67257e0e864cbbfa 100644 --- a/http_handle_repo_tree.go +++ b/http_handle_repo_tree.go @@ -25,7 +25,7 @@ params["path_spec"] = pathSpec _, repoPath, _, _, _, _, _ := s.getRepoInfo(request.Context(), groupPath, repoName, "") - client, err := git2c.NewClient(s.Config.Git.Socket) + client, err := git2c.NewClient(s.config.Git.Socket) if err != nil { errorPage500(writer, params, err.Error()) return diff --git a/http_handle_repo_upload_pack.go b/http_handle_repo_upload_pack.go index 4c7291b28cd23868696aa54f72134b4639adc988..475c0a2d37800149a4ace0bec3471a30387ae5ac 100644 --- a/http_handle_repo_upload_pack.go +++ b/http_handle_repo_upload_pack.go @@ -24,7 +24,7 @@ var cmd *exec.Cmd groupPath, repoName = params["group_path"].([]string), params["repo_name"].(string) - if err := s.Database.QueryRow(request.Context(), ` + if err := s.database.QueryRow(request.Context(), ` WITH RECURSIVE group_path_cte AS ( -- Start: match the first name in the path where parent_group IS NULL SELECT @@ -67,7 +67,7 @@ writer.Header().Set("Transfer-Encoding", "chunked") writer.WriteHeader(http.StatusOK) cmd = exec.Command("git", "upload-pack", "--stateless-rpc", repoPath) - cmd.Env = append(os.Environ(), "LINDENII_FORGE_HOOKS_SOCKET_PATH="+s.Config.Hooks.Socket) + cmd.Env = append(os.Environ(), "LINDENII_FORGE_HOOKS_SOCKET_PATH="+s.config.Hooks.Socket) if stdout, err = cmd.StdoutPipe(); err != nil { return err } diff --git a/http_server.go b/http_server.go index cad3a3d6d3b1d8101054963a67c6a0d70cf192ff..f5f63283ff74fee938a604ee263ca84b273ac5b2 100644 --- a/http_server.go +++ b/http_server.go @@ -21,7 +21,7 @@ // // TODO: This function is way too large. func (s *Server) ServeHTTP(writer http.ResponseWriter, request *http.Request) { var remoteAddr string - if s.Config.HTTP.ReverseProxy { + if s.config.HTTP.ReverseProxy { remoteAddrs, ok := request.Header["X-Forwarded-For"] if ok && len(remoteAddrs) == 1 { remoteAddr = remoteAddrs[0] @@ -50,7 +50,7 @@ } params["url_segments"] = segments params["dir_mode"] = dirMode - params["global"] = s.GlobalData + params["global"] = s.globalData var userID int // 0 for none userID, params["username"], err = s.getUserFromRequest(request) params["user_id"] = userID @@ -87,10 +87,10 @@ } switch segments[1] { case "static": - s.StaticHandler.ServeHTTP(writer, request) + s.staticHandler.ServeHTTP(writer, request) return case "source": - s.SourceHandler.ServeHTTP(writer, request) + s.sourceHandler.ServeHTTP(writer, request) return } } @@ -183,7 +183,7 @@ for _, part := range segments[:sepIndex+3] { repoURLRoot = repoURLRoot + url.PathEscape(part) + "/" } params["repo_url_root"] = repoURLRoot - params["repo_patch_mailing_list"] = repoURLRoot[1:len(repoURLRoot)-1] + "@" + s.Config.LMTP.Domain + params["repo_patch_mailing_list"] = repoURLRoot[1:len(repoURLRoot)-1] + "@" + s.config.LMTP.Domain params["http_clone_url"] = s.genHTTPRemoteURL(groupPath, moduleName) params["ssh_clone_url"] = s.genSSHRemoteURL(groupPath, moduleName) diff --git a/irc.go b/irc.go index 298930f19cc6a22129fde1a06c722e9d8696cddb..4f4c5c990ae06445d3b7054d97fc3955133da2e8 100644 --- a/irc.go +++ b/irc.go @@ -19,10 +19,10 @@ func (s *Server) ircBotSession() error { var err error var underlyingConn net.Conn - if s.Config.IRC.TLS { - underlyingConn, err = tls.Dial(s.Config.IRC.Net, s.Config.IRC.Addr, nil) + if s.config.IRC.TLS { + underlyingConn, err = tls.Dial(s.config.IRC.Net, s.config.IRC.Addr, nil) } else { - underlyingConn, err = net.Dial(s.Config.IRC.Net, s.Config.IRC.Addr) + underlyingConn, err = net.Dial(s.config.IRC.Net, s.config.IRC.Addr) } if err != nil { return err @@ -36,11 +36,11 @@ slog.Debug("irc tx", "line", s) return conn.WriteString(s + "\r\n") } - _, err = logAndWriteLn("NICK " + s.Config.IRC.Nick) + _, err = logAndWriteLn("NICK " + s.config.IRC.Nick) if err != nil { return err } - _, err = logAndWriteLn("USER " + s.Config.IRC.User + " 0 * :" + s.Config.IRC.Gecos) + _, err = logAndWriteLn("USER " + s.config.IRC.User + " 0 * :" + s.config.IRC.Gecos) if err != nil { return err } @@ -81,7 +81,7 @@ c, ok := msg.Source.(irc.Client) if !ok { slog.Error("unable to convert source of JOIN to client") } - if c.Nick != s.Config.IRC.Nick { + if c.Nick != s.config.IRC.Nick { continue } default: @@ -93,18 +93,18 @@ for { select { case err = <-readLoopError: return err - case line := <-s.IrcSendBuffered: + case line := <-s.ircSendBuffered: _, err = logAndWriteLn(line) if err != nil { select { - case s.IrcSendBuffered <- line: + case s.ircSendBuffered <- line: default: slog.Error("unable to requeue message", "line", line) } writeLoopAbort <- struct{}{} return err } - case lineErrorBack := <-s.IrcSendDirectChan: + case lineErrorBack := <-s.ircSendDirectChan: _, err = logAndWriteLn(lineErrorBack.content) lineErrorBack.errorBack <- err if err != nil { @@ -120,7 +120,7 @@ // the buffering system. func (s *Server) ircSendDirect(line string) error { ech := make(chan error, 1) - s.IrcSendDirectChan <- errorBack[string]{ + s.ircSendDirectChan <- errorBack[string]{ content: line, errorBack: ech, } @@ -130,8 +130,8 @@ } // TODO: Delay and warnings? func (s *Server) ircBotLoop() { - s.IrcSendBuffered = make(chan string, s.Config.IRC.SendQ) - s.IrcSendDirectChan = make(chan errorBack[string]) + s.ircSendBuffered = make(chan string, s.config.IRC.SendQ) + s.ircSendDirectChan = make(chan errorBack[string]) for { err := s.ircBotSession() diff --git a/lmtp_server.go b/lmtp_server.go index ae912c5e91b6acfbc25f79743c4867be379e6a07..3abfdb6aca095653380bfa8010576336b6c63d9e 100644 --- a/lmtp_server.go +++ b/lmtp_server.go @@ -66,10 +66,10 @@ func (s *Server) serveLMTP(listener net.Listener) error { smtpServer := smtp.NewServer(&lmtpHandler{}) smtpServer.LMTP = true - smtpServer.Domain = s.Config.LMTP.Domain - smtpServer.Addr = s.Config.LMTP.Socket - smtpServer.WriteTimeout = time.Duration(s.Config.LMTP.WriteTimeout) * time.Second - smtpServer.ReadTimeout = time.Duration(s.Config.LMTP.ReadTimeout) * time.Second + smtpServer.Domain = s.config.LMTP.Domain + smtpServer.Addr = s.config.LMTP.Socket + smtpServer.WriteTimeout = time.Duration(s.config.LMTP.WriteTimeout) * time.Second + smtpServer.ReadTimeout = time.Duration(s.config.LMTP.ReadTimeout) * time.Second smtpServer.EnableSMTPUTF8 = true return smtpServer.Serve(listener) } @@ -85,9 +85,9 @@ data []byte n int64 ) - n, err = io.CopyN(&buf, r, session.s.Config.LMTP.MaxSize) + n, err = io.CopyN(&buf, r, session.s.config.LMTP.MaxSize) switch { - case n == session.s.Config.LMTP.MaxSize: + case n == session.s.config.LMTP.MaxSize: err = errors.New("Message too big.") // drain whatever is left in the pipe _, _ = io.Copy(io.Discard, r) @@ -133,10 +133,10 @@ _ = from for _, to := range to { - if !strings.HasSuffix(to, "@"+session.s.Config.LMTP.Domain) { + if !strings.HasSuffix(to, "@"+session.s.config.LMTP.Domain) { continue } - localPart := to[:len(to)-len("@"+session.s.Config.LMTP.Domain)] + localPart := to[:len(to)-len("@"+session.s.config.LMTP.Domain)] var segments []string segments, err = misc.PathToSegments(localPart) if err != nil { diff --git a/remote_url.go b/remote_url.go index 8fc5528be9b0661c2d87a56b51d8ac4959ac47dd..a9d8bf286f7fe3ba1a44a30d7ae852c372a75e0d 100644 --- a/remote_url.go +++ b/remote_url.go @@ -15,11 +15,11 @@ // genSSHRemoteURL generates SSH remote URLs from a given group path and repo // name. func (s *Server) genSSHRemoteURL(groupPath []string, repoName string) string { - return strings.TrimSuffix(s.Config.SSH.Root, "/") + "/" + misc.SegmentsToURL(groupPath) + "/-/repos/" + url.PathEscape(repoName) + return strings.TrimSuffix(s.config.SSH.Root, "/") + "/" + misc.SegmentsToURL(groupPath) + "/-/repos/" + url.PathEscape(repoName) } // genHTTPRemoteURL generates HTTP remote URLs from a given group path and repo // name. func (s *Server) genHTTPRemoteURL(groupPath []string, repoName string) string { - return strings.TrimSuffix(s.Config.HTTP.Root, "/") + "/" + misc.SegmentsToURL(groupPath) + "/-/repos/" + url.PathEscape(repoName) + return strings.TrimSuffix(s.config.HTTP.Root, "/") + "/" + misc.SegmentsToURL(groupPath) + "/-/repos/" + url.PathEscape(repoName) } diff --git a/server.go b/server.go index c025f4587ba4e1c235acfb2194c6dc1fb04ce3eb..75226d4a11c75898136431b0b27b21d1ad46e082 100644 --- a/server.go +++ b/server.go @@ -21,32 +21,32 @@ goSSH "golang.org/x/crypto/ssh" ) type Server struct { - Config Config + config Config - // Database serves as the primary Database handle for this entire application. + // database serves as the primary database handle for this entire application. // Transactions or single reads may be used from it. A [pgxpool.Pool] is // necessary to safely use pgx concurrently; pgx.Conn, etc. are insufficient. - Database *pgxpool.Pool + database *pgxpool.Pool - SourceHandler http.Handler - StaticHandler http.Handler + sourceHandler http.Handler + staticHandler http.Handler - IrcSendBuffered chan string - IrcSendDirectChan chan errorBack[string] + ircSendBuffered chan string + ircSendDirectChan chan errorBack[string] - // GlobalData is passed as "global" when rendering HTML templates. - GlobalData map[string]any + // globalData is passed as "global" when rendering HTML templates. + globalData map[string]any - ServerPubkeyString string - ServerPubkeyFP string - ServerPubkey goSSH.PublicKey + serverPubkeyString string + serverPubkeyFP string + serverPubkey goSSH.PublicKey - // PackPasses contains hook cookies mapped to their packPass. - PackPasses cmap.Map[string, packPass] + // packPasses contains hook cookies mapped to their packPass. + packPasses cmap.Map[string, packPass] } func (s *Server) Setup() { - s.SourceHandler = http.StripPrefix( + s.sourceHandler = http.StripPrefix( "/-/source/", http.FileServer(http.FS(embeddedSourceFS)), ) @@ -54,10 +54,10 @@ staticFS, err := fs.Sub(embeddedResourcesFS, "static") if err != nil { panic(err) } - s.StaticHandler = http.StripPrefix("/-/static/", http.FileServer(http.FS(staticFS))) - s.GlobalData = map[string]any{ - "server_public_key_string": &s.ServerPubkeyString, - "server_public_key_fingerprint": &s.ServerPubkeyFP, + s.staticHandler = http.StripPrefix("/-/static/", http.FileServer(http.FS(staticFS))) + s.globalData = map[string]any{ + "server_public_key_string": &s.serverPubkeyString, + "server_public_key_fingerprint": &s.serverPubkeyFP, "forge_version": VERSION, // Some other ones are populated after config parsing } @@ -79,7 +79,7 @@ } // Launch Git2D go func() { - cmd := exec.Command(s.Config.Git.DaemonPath, s.Config.Git.Socket) //#nosec G204 + cmd := exec.Command(s.config.Git.DaemonPath, s.config.Git.Socket) //#nosec G204 cmd.Stderr = log.Writer() cmd.Stdout = log.Writer() if err := cmd.Run(); err != nil { @@ -89,14 +89,14 @@ }() // UNIX socket listener for hooks { - hooksListener, err := net.Listen("unix", s.Config.Hooks.Socket) + hooksListener, err := net.Listen("unix", s.config.Hooks.Socket) if errors.Is(err, syscall.EADDRINUSE) { - slog.Warn("removing existing socket", "path", s.Config.Hooks.Socket) - if err = syscall.Unlink(s.Config.Hooks.Socket); err != nil { - slog.Error("removing existing socket", "path", s.Config.Hooks.Socket, "error", err) + slog.Warn("removing existing socket", "path", s.config.Hooks.Socket) + if err = syscall.Unlink(s.config.Hooks.Socket); err != nil { + slog.Error("removing existing socket", "path", s.config.Hooks.Socket, "error", err) os.Exit(1) } - if hooksListener, err = net.Listen("unix", s.Config.Hooks.Socket); err != nil { + if hooksListener, err = net.Listen("unix", s.config.Hooks.Socket); err != nil { slog.Error("listening hooks", "error", err) os.Exit(1) } @@ -104,7 +104,7 @@ } else if err != nil { slog.Error("listening hooks", "error", err) os.Exit(1) } - slog.Info("listening hooks on unix", "path", s.Config.Hooks.Socket) + slog.Info("listening hooks on unix", "path", s.config.Hooks.Socket) go func() { if err = s.serveGitHooks(hooksListener); err != nil { slog.Error("serving hooks", "error", err) @@ -115,14 +115,14 @@ } // UNIX socket listener for LMTP { - lmtpListener, err := net.Listen("unix", s.Config.LMTP.Socket) + lmtpListener, err := net.Listen("unix", s.config.LMTP.Socket) if errors.Is(err, syscall.EADDRINUSE) { - slog.Warn("removing existing socket", "path", s.Config.LMTP.Socket) - if err = syscall.Unlink(s.Config.LMTP.Socket); err != nil { - slog.Error("removing existing socket", "path", s.Config.LMTP.Socket, "error", err) + slog.Warn("removing existing socket", "path", s.config.LMTP.Socket) + if err = syscall.Unlink(s.config.LMTP.Socket); err != nil { + slog.Error("removing existing socket", "path", s.config.LMTP.Socket, "error", err) os.Exit(1) } - if lmtpListener, err = net.Listen("unix", s.Config.LMTP.Socket); err != nil { + if lmtpListener, err = net.Listen("unix", s.config.LMTP.Socket); err != nil { slog.Error("listening LMTP", "error", err) os.Exit(1) } @@ -130,7 +130,7 @@ } else if err != nil { slog.Error("listening LMTP", "error", err) os.Exit(1) } - slog.Info("listening LMTP on unix", "path", s.Config.LMTP.Socket) + slog.Info("listening LMTP on unix", "path", s.config.LMTP.Socket) go func() { if err = s.serveLMTP(lmtpListener); err != nil { slog.Error("serving LMTP", "error", err) @@ -141,14 +141,14 @@ } // SSH listener { - sshListener, err := net.Listen(s.Config.SSH.Net, s.Config.SSH.Addr) - if errors.Is(err, syscall.EADDRINUSE) && s.Config.SSH.Net == "unix" { - slog.Warn("removing existing socket", "path", s.Config.SSH.Addr) - if err = syscall.Unlink(s.Config.SSH.Addr); err != nil { - slog.Error("removing existing socket", "path", s.Config.SSH.Addr, "error", err) + sshListener, err := net.Listen(s.config.SSH.Net, s.config.SSH.Addr) + if errors.Is(err, syscall.EADDRINUSE) && s.config.SSH.Net == "unix" { + slog.Warn("removing existing socket", "path", s.config.SSH.Addr) + if err = syscall.Unlink(s.config.SSH.Addr); err != nil { + slog.Error("removing existing socket", "path", s.config.SSH.Addr, "error", err) os.Exit(1) } - if sshListener, err = net.Listen(s.Config.SSH.Net, s.Config.SSH.Addr); err != nil { + if sshListener, err = net.Listen(s.config.SSH.Net, s.config.SSH.Addr); err != nil { slog.Error("listening SSH", "error", err) os.Exit(1) } @@ -156,7 +156,7 @@ } else if err != nil { slog.Error("listening SSH", "error", err) os.Exit(1) } - slog.Info("listening SSH on", "net", s.Config.SSH.Net, "addr", s.Config.SSH.Addr) + slog.Info("listening SSH on", "net", s.config.SSH.Net, "addr", s.config.SSH.Addr) go func() { if err = s.serveSSH(sshListener); err != nil { slog.Error("serving SSH", "error", err) @@ -167,14 +167,14 @@ } // HTTP listener { - httpListener, err := net.Listen(s.Config.HTTP.Net, s.Config.HTTP.Addr) - if errors.Is(err, syscall.EADDRINUSE) && s.Config.HTTP.Net == "unix" { - slog.Warn("removing existing socket", "path", s.Config.HTTP.Addr) - if err = syscall.Unlink(s.Config.HTTP.Addr); err != nil { - slog.Error("removing existing socket", "path", s.Config.HTTP.Addr, "error", err) + httpListener, err := net.Listen(s.config.HTTP.Net, s.config.HTTP.Addr) + if errors.Is(err, syscall.EADDRINUSE) && s.config.HTTP.Net == "unix" { + slog.Warn("removing existing socket", "path", s.config.HTTP.Addr) + if err = syscall.Unlink(s.config.HTTP.Addr); err != nil { + slog.Error("removing existing socket", "path", s.config.HTTP.Addr, "error", err) os.Exit(1) } - if httpListener, err = net.Listen(s.Config.HTTP.Net, s.Config.HTTP.Addr); err != nil { + if httpListener, err = net.Listen(s.config.HTTP.Net, s.config.HTTP.Addr); err != nil { slog.Error("listening HTTP", "error", err) os.Exit(1) } @@ -184,11 +184,11 @@ os.Exit(1) } server := http.Server{ Handler: s, - ReadTimeout: time.Duration(s.Config.HTTP.ReadTimeout) * time.Second, - WriteTimeout: time.Duration(s.Config.HTTP.ReadTimeout) * time.Second, - IdleTimeout: time.Duration(s.Config.HTTP.ReadTimeout) * time.Second, + ReadTimeout: time.Duration(s.config.HTTP.ReadTimeout) * time.Second, + WriteTimeout: time.Duration(s.config.HTTP.ReadTimeout) * time.Second, + IdleTimeout: time.Duration(s.config.HTTP.ReadTimeout) * time.Second, } //exhaustruct:ignore - slog.Info("listening HTTP on", "net", s.Config.HTTP.Net, "addr", s.Config.HTTP.Addr) + slog.Info("listening HTTP on", "net", s.config.HTTP.Net, "addr", s.config.HTTP.Addr) go func() { if err = server.Serve(httpListener); err != nil && !errors.Is(err, http.ErrServerClosed) { slog.Error("serving HTTP", "error", err) diff --git a/ssh_handle_receive_pack.go b/ssh_handle_receive_pack.go index 724c3fdf8399e5e142414f5264809ace586b0369..de6843a6ff121f5bb4fb0b6d1a33bf7a2e17cd9d 100644 --- a/ssh_handle_receive_pack.go +++ b/ssh_handle_receive_pack.go @@ -51,7 +51,7 @@ return errors.New("repository has no core section in config") } hooksPath := repoConfCore.OptionAll("hooksPath") - if len(hooksPath) != 1 || hooksPath[0] != s.Config.Hooks.Execs { + if len(hooksPath) != 1 || hooksPath[0] != s.config.Hooks.Execs { return errors.New("repository has hooksPath set to an unexpected value") } @@ -91,7 +91,7 @@ if err != nil { fmt.Fprintln(session.Stderr(), "Error while generating cookie:", err) } - s.PackPasses.Store(cookie, packPass{ + s.packPasses.Store(cookie, packPass{ session: session, pubkey: pubkey, directAccess: directAccess, @@ -104,13 +104,13 @@ repo: repo, contribReq: contribReq, userType: userType, }) - defer s.PackPasses.Delete(cookie) + defer s.packPasses.Delete(cookie) // The Delete won't execute until proc.Wait returns unless something // horribly wrong such as a panic occurs. proc := exec.CommandContext(session.Context(), "git-receive-pack", repoPath) proc.Env = append(os.Environ(), - "LINDENII_FORGE_HOOKS_SOCKET_PATH="+s.Config.Hooks.Socket, + "LINDENII_FORGE_HOOKS_SOCKET_PATH="+s.config.Hooks.Socket, "LINDENII_FORGE_HOOKS_COOKIE="+cookie, ) proc.Stdin = session diff --git a/ssh_handle_upload_pack.go b/ssh_handle_upload_pack.go index 45ecfd84b7c9c03998fb0cc3c12540e4c94cba50..34a1d9e651da875cbf86b7676fd2d26e6860eef0 100644 --- a/ssh_handle_upload_pack.go +++ b/ssh_handle_upload_pack.go @@ -20,7 +20,7 @@ return err } proc := exec.CommandContext(session.Context(), "git-upload-pack", repoPath) - proc.Env = append(os.Environ(), "LINDENII_FORGE_HOOKS_SOCKET_PATH="+s.Config.Hooks.Socket) + proc.Env = append(os.Environ(), "LINDENII_FORGE_HOOKS_SOCKET_PATH="+s.config.Hooks.Socket) proc.Stdin = session proc.Stdout = session proc.Stderr = session.Stderr() diff --git a/ssh_server.go b/ssh_server.go index 07a1f34810799b464746a4d8d867b320c2025708..bac7d53ecaf62ddc4c0334aad8dd21c14cb0d52c 100644 --- a/ssh_server.go +++ b/ssh_server.go @@ -25,7 +25,7 @@ var hostKey goSSH.Signer var err error var server *gliderSSH.Server - if hostKeyBytes, err = os.ReadFile(s.Config.SSH.Key); err != nil { + if hostKeyBytes, err = os.ReadFile(s.config.SSH.Key); err != nil { return err } @@ -33,9 +33,9 @@ if hostKey, err = goSSH.ParsePrivateKey(hostKeyBytes); err != nil { return err } - s.ServerPubkey = hostKey.PublicKey() - s.ServerPubkeyString = misc.BytesToString(goSSH.MarshalAuthorizedKey(s.ServerPubkey)) - s.ServerPubkeyFP = goSSH.FingerprintSHA256(s.ServerPubkey) + s.serverPubkey = hostKey.PublicKey() + s.serverPubkeyString = misc.BytesToString(goSSH.MarshalAuthorizedKey(s.serverPubkey)) + s.serverPubkeyFP = goSSH.FingerprintSHA256(s.serverPubkey) server = &gliderSSH.Server{ Handler: func(session gliderSSH.Session) { @@ -46,7 +46,7 @@ clientPubkeyStr = strings.TrimSuffix(misc.BytesToString(goSSH.MarshalAuthorizedKey(clientPubkey)), "\n") } slog.Info("incoming ssh", "addr", session.RemoteAddr().String(), "key", clientPubkeyStr, "command", session.RawCommand()) - fmt.Fprintln(session.Stderr(), ansiec.Blue+"Lindenii Forge "+VERSION+", source at "+strings.TrimSuffix(s.Config.HTTP.Root, "/")+"/-/source/"+ansiec.Reset+"\r") + fmt.Fprintln(session.Stderr(), ansiec.Blue+"Lindenii Forge "+VERSION+", source at "+strings.TrimSuffix(s.config.HTTP.Root, "/")+"/-/source/"+ansiec.Reset+"\r") cmd := session.Command() diff --git a/users.go b/users.go index 3f57a35e321fc0bd42cb4570b2da5093b8fe5e3d..2b529f39ab1bdfaa3f1f57589b32550848c86850 100644 --- a/users.go +++ b/users.go @@ -15,7 +15,7 @@ // TODO: Audit all users of this function. func (s *Server) addUserSSH(ctx context.Context, pubkey string) (userID int, err error) { var txn pgx.Tx - if txn, err = s.Database.Begin(ctx); err != nil { + if txn, err = s.database.Begin(ctx); err != nil { return } defer func() { -- 2.48.1