|
6 | 6 | package repo
|
7 | 7 |
|
8 | 8 | import (
|
| 9 | + "path" |
| 10 | + |
9 | 11 | "code.gitea.io/gitea/models"
|
| 12 | + "code.gitea.io/gitea/modules/cache" |
10 | 13 | "code.gitea.io/gitea/modules/context"
|
11 | 14 | "code.gitea.io/gitea/modules/git"
|
12 | 15 | "code.gitea.io/gitea/modules/httpcache"
|
@@ -79,34 +82,57 @@ func ServeBlobOrLFS(ctx *context.Context, blob *git.Blob) error {
|
79 | 82 | return common.ServeBlob(ctx, blob)
|
80 | 83 | }
|
81 | 84 |
|
| 85 | +func getBlobForEntry(ctx *context.Context) *git.Blob { |
| 86 | + entry, err := ctx.Repo.Commit.GetTreeEntryByPath(ctx.Repo.TreePath) |
| 87 | + if err != nil { |
| 88 | + ctx.ServerError("GetBlobByPath", err) |
| 89 | + return nil |
| 90 | + } |
| 91 | + |
| 92 | + if entry.IsDir() || entry.IsSubModule() { |
| 93 | + ctx.NotFound("GetBlobByPath", nil) |
| 94 | + return nil |
| 95 | + } |
| 96 | + |
| 97 | + var c *git.LastCommitCache |
| 98 | + if setting.CacheService.LastCommit.Enabled && ctx.Repo.CommitsCount >= setting.CacheService.LastCommit.CommitsCount { |
| 99 | + c = git.NewLastCommitCache(ctx.Repo.Repository.FullName(), ctx.Repo.GitRepo, setting.LastCommitCacheTTLSeconds, cache.GetCache()) |
| 100 | + } |
| 101 | + |
| 102 | + info, _, err := git.Entries([]*git.TreeEntry{entry}).GetCommitsInfo(ctx, ctx.Repo.Commit, path.Dir("/" + ctx.Repo.TreePath)[1:], c) |
| 103 | + if err != nil { |
| 104 | + ctx.ServerError("GetCommitsInfo", err) |
| 105 | + return nil |
| 106 | + } |
| 107 | + |
| 108 | + if len(info) == 1 && httpcache.HandleGenericTimeCache(ctx.Req, ctx.Resp, info[0].Commit.Committer.When) { |
| 109 | + // Not Modified |
| 110 | + return nil |
| 111 | + } |
| 112 | + |
| 113 | + return entry.Blob() |
| 114 | +} |
| 115 | + |
82 | 116 | // SingleDownload download a file by repos path
|
83 | 117 | func SingleDownload(ctx *context.Context) {
|
84 |
| - blob, err := ctx.Repo.Commit.GetBlobByPath(ctx.Repo.TreePath) |
85 |
| - if err != nil { |
86 |
| - if git.IsErrNotExist(err) { |
87 |
| - ctx.NotFound("GetBlobByPath", nil) |
88 |
| - } else { |
89 |
| - ctx.ServerError("GetBlobByPath", err) |
90 |
| - } |
| 118 | + blob := getBlobForEntry(ctx) |
| 119 | + if blob == nil { |
91 | 120 | return
|
92 | 121 | }
|
93 |
| - if err = common.ServeBlob(ctx, blob); err != nil { |
| 122 | + |
| 123 | + if err := common.ServeBlob(ctx, blob); err != nil { |
94 | 124 | ctx.ServerError("ServeBlob", err)
|
95 | 125 | }
|
96 | 126 | }
|
97 | 127 |
|
98 | 128 | // SingleDownloadOrLFS download a file by repos path redirecting to LFS if necessary
|
99 | 129 | func SingleDownloadOrLFS(ctx *context.Context) {
|
100 |
| - blob, err := ctx.Repo.Commit.GetBlobByPath(ctx.Repo.TreePath) |
101 |
| - if err != nil { |
102 |
| - if git.IsErrNotExist(err) { |
103 |
| - ctx.NotFound("GetBlobByPath", nil) |
104 |
| - } else { |
105 |
| - ctx.ServerError("GetBlobByPath", err) |
106 |
| - } |
| 130 | + blob := getBlobForEntry(ctx) |
| 131 | + if blob == nil { |
107 | 132 | return
|
108 | 133 | }
|
109 |
| - if err = ServeBlobOrLFS(ctx, blob); err != nil { |
| 134 | + |
| 135 | + if err := ServeBlobOrLFS(ctx, blob); err != nil { |
110 | 136 | ctx.ServerError("ServeBlobOrLFS", err)
|
111 | 137 | }
|
112 | 138 | }
|
|
0 commit comments