You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

repo_commit_nogogit.go 4.0KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163
  1. // Copyright 2020 The Gitea Authors. All rights reserved.
  2. // Use of this source code is governed by a MIT-style
  3. // license that can be found in the LICENSE file.
  4. //go:build !gogit
  5. package git
  6. import (
  7. "bufio"
  8. "errors"
  9. "io"
  10. "strings"
  11. "code.gitea.io/gitea/modules/log"
  12. )
  13. // ResolveReference resolves a name to a reference
  14. func (repo *Repository) ResolveReference(name string) (string, error) {
  15. stdout, _, err := NewCommand(repo.Ctx, "show-ref", "--hash", name).RunStdString(&RunOpts{Dir: repo.Path})
  16. if err != nil {
  17. if strings.Contains(err.Error(), "not a valid ref") {
  18. return "", ErrNotExist{name, ""}
  19. }
  20. return "", err
  21. }
  22. stdout = strings.TrimSpace(stdout)
  23. if stdout == "" {
  24. return "", ErrNotExist{name, ""}
  25. }
  26. return stdout, nil
  27. }
  28. // GetRefCommitID returns the last commit ID string of given reference (branch or tag).
  29. func (repo *Repository) GetRefCommitID(name string) (string, error) {
  30. wr, rd, cancel := repo.CatFileBatchCheck(repo.Ctx)
  31. defer cancel()
  32. _, err := wr.Write([]byte(name + "\n"))
  33. if err != nil {
  34. return "", err
  35. }
  36. shaBs, _, _, err := ReadBatchLine(rd)
  37. if IsErrNotExist(err) {
  38. return "", ErrNotExist{name, ""}
  39. }
  40. return string(shaBs), nil
  41. }
  42. // SetReference sets the commit ID string of given reference (e.g. branch or tag).
  43. func (repo *Repository) SetReference(name, commitID string) error {
  44. _, _, err := NewCommand(repo.Ctx, "update-ref", name, commitID).RunStdString(&RunOpts{Dir: repo.Path})
  45. return err
  46. }
  47. // RemoveReference removes the given reference (e.g. branch or tag).
  48. func (repo *Repository) RemoveReference(name string) error {
  49. _, _, err := NewCommand(repo.Ctx, "update-ref", "--no-deref", "-d", name).RunStdString(&RunOpts{Dir: repo.Path})
  50. return err
  51. }
  52. // IsCommitExist returns true if given commit exists in current repository.
  53. func (repo *Repository) IsCommitExist(name string) bool {
  54. _, _, err := NewCommand(repo.Ctx, "cat-file", "-e", name).RunStdString(&RunOpts{Dir: repo.Path})
  55. return err == nil
  56. }
  57. func (repo *Repository) getCommit(id SHA1) (*Commit, error) {
  58. wr, rd, cancel := repo.CatFileBatch(repo.Ctx)
  59. defer cancel()
  60. _, _ = wr.Write([]byte(id.String() + "\n"))
  61. return repo.getCommitFromBatchReader(rd, id)
  62. }
  63. func (repo *Repository) getCommitFromBatchReader(rd *bufio.Reader, id SHA1) (*Commit, error) {
  64. _, typ, size, err := ReadBatchLine(rd)
  65. if err != nil {
  66. if errors.Is(err, io.EOF) || IsErrNotExist(err) {
  67. return nil, ErrNotExist{ID: id.String()}
  68. }
  69. return nil, err
  70. }
  71. switch typ {
  72. case "missing":
  73. return nil, ErrNotExist{ID: id.String()}
  74. case "tag":
  75. // then we need to parse the tag
  76. // and load the commit
  77. data, err := io.ReadAll(io.LimitReader(rd, size))
  78. if err != nil {
  79. return nil, err
  80. }
  81. _, err = rd.Discard(1)
  82. if err != nil {
  83. return nil, err
  84. }
  85. tag, err := parseTagData(data)
  86. if err != nil {
  87. return nil, err
  88. }
  89. commit, err := tag.Commit(repo)
  90. if err != nil {
  91. return nil, err
  92. }
  93. commit.CommitMessage = strings.TrimSpace(tag.Message)
  94. commit.Author = tag.Tagger
  95. commit.Signature = tag.Signature
  96. return commit, nil
  97. case "commit":
  98. commit, err := CommitFromReader(repo, id, io.LimitReader(rd, size))
  99. if err != nil {
  100. return nil, err
  101. }
  102. _, err = rd.Discard(1)
  103. if err != nil {
  104. return nil, err
  105. }
  106. return commit, nil
  107. default:
  108. log.Debug("Unknown typ: %s", typ)
  109. _, err = rd.Discard(int(size) + 1)
  110. if err != nil {
  111. return nil, err
  112. }
  113. return nil, ErrNotExist{
  114. ID: id.String(),
  115. }
  116. }
  117. }
  118. // ConvertToSHA1 returns a Hash object from a potential ID string
  119. func (repo *Repository) ConvertToSHA1(commitID string) (SHA1, error) {
  120. if len(commitID) == 40 && SHAPattern.MatchString(commitID) {
  121. sha1, err := NewIDFromString(commitID)
  122. if err == nil {
  123. return sha1, nil
  124. }
  125. }
  126. wr, rd, cancel := repo.CatFileBatchCheck(repo.Ctx)
  127. defer cancel()
  128. _, err := wr.Write([]byte(commitID + "\n"))
  129. if err != nil {
  130. return SHA1{}, err
  131. }
  132. sha, _, _, err := ReadBatchLine(rd)
  133. if err != nil {
  134. if IsErrNotExist(err) {
  135. return SHA1{}, ErrNotExist{commitID, ""}
  136. }
  137. return SHA1{}, err
  138. }
  139. return MustIDFromString(string(sha)), nil
  140. }