mirror of
https://github.com/go-gitea/gitea.git
synced 2026-08-11 21:48:41 +00:00
2087d4a1a5
Pairs with https://gitea.com/gitea/runner/pulls/1143. Gitea depends on `gitea.com/gitea/runner` for exactly two packages: `act/model` and `act/exprparser`, the workflow model and the expression evaluator it needs to parse workflows and to build the task payload the runner consumes. Pulling the whole runner module in for that is heavy and puts shared code in the repository of one of the two consumers. Both packages now live in `gitea.dev/actionslib` (`pkg/model`, `pkg/exprparser`), the module Gitea and the runner already share for the runner API, so the dependency on the runner repository is dropped here. ### Changes - `gitea.com/gitea/runner/act/model` -> `gitea.dev/actionslib/pkg/model`, `.../act/exprparser` -> `gitea.dev/actionslib/pkg/exprparser` (22 files, import paths only). - `routers/api/actions/runner/interceptor.go` takes the `x-runner-uuid` / `x-runner-token` names from `gitea.dev/actionslib/pkg/protocol` instead of repeating the literals the runner also has. - `go.mod`: `gitea.com/gitea/runner` removed. --------- Signed-off-by: Lunny Xiao <xiaolunwen@gmail.com> Co-authored-by: silverwind <me@silverwind.io> Co-authored-by: Zettat123 <zettat123@gmail.com>
92 lines
3.4 KiB
Go
92 lines
3.4 KiB
Go
// Copyright 2026 The Gitea Authors. All rights reserved.
|
|
// SPDX-License-Identifier: MIT
|
|
|
|
package integration
|
|
|
|
import (
|
|
"fmt"
|
|
"net/url"
|
|
"os"
|
|
"testing"
|
|
|
|
runnerv1 "gitea.dev/actionslib/runner/v1"
|
|
actions_model "gitea.dev/models/actions"
|
|
auth_model "gitea.dev/models/auth"
|
|
"gitea.dev/models/dbfs"
|
|
repo_model "gitea.dev/models/repo"
|
|
"gitea.dev/models/unittest"
|
|
user_model "gitea.dev/models/user"
|
|
actions_module "gitea.dev/modules/actions"
|
|
"gitea.dev/modules/storage"
|
|
|
|
"connectrpc.com/connect"
|
|
"github.com/stretchr/testify/assert"
|
|
"github.com/stretchr/testify/require"
|
|
)
|
|
|
|
// Regression for https://gitea.com/gitea/runner/issues/950: a runner that
|
|
// finalizes a task with no log output sends UpdateLog{Rows:[], NoMore:true}.
|
|
// The previous short-circuit on len(Rows)==0 skipped TransferLogs, leaving
|
|
// an orphan dbfs_data row. Verify the row is now archived and removed.
|
|
func TestActionsLogFinalizeWithoutRows(t *testing.T) {
|
|
onGiteaRun(t, func(t *testing.T, _ *url.URL) {
|
|
user2 := unittest.AssertExistsAndLoadBean(t, &user_model.User{ID: 2})
|
|
session := loginUser(t, user2.Name)
|
|
token := getTokenForLoggedInUser(t, session, auth_model.AccessTokenScopeWriteRepository, auth_model.AccessTokenScopeWriteUser)
|
|
|
|
apiRepo := createActionsTestRepo(t, token, "actions-finalize-no-rows", false)
|
|
repo := unittest.AssertExistsAndLoadBean(t, &repo_model.Repository{ID: apiRepo.ID})
|
|
|
|
runner := newMockRunner()
|
|
runner.registerAsRepoRunner(t, user2.Name, repo.Name, "mock-runner", []string{"ubuntu-latest"}, false)
|
|
|
|
const wfTreePath = ".gitea/workflows/finalize-no-rows.yml"
|
|
wfFileContent := fmt.Sprintf(`name: finalize-no-rows
|
|
on:
|
|
push:
|
|
paths:
|
|
- '%s'
|
|
jobs:
|
|
job1:
|
|
runs-on: ubuntu-latest
|
|
steps:
|
|
- run: noop
|
|
`, wfTreePath)
|
|
createWorkflowFile(t, token, user2.Name, repo.Name, wfTreePath, getWorkflowCreateFileOptions(user2, repo.DefaultBranch, "trigger", wfFileContent))
|
|
|
|
task := runner.fetchTask(t)
|
|
|
|
resp, err := runner.client.runnerServiceClient.UpdateLog(t.Context(), connect.NewRequest(&runnerv1.UpdateLogRequest{
|
|
TaskId: task.Id,
|
|
Index: 0,
|
|
Rows: nil,
|
|
NoMore: true,
|
|
}))
|
|
require.NoError(t, err)
|
|
assert.EqualValues(t, 0, resp.Msg.AckIndex)
|
|
|
|
freshTask := unittest.AssertExistsAndLoadBean(t, &actions_model.ActionTask{ID: task.Id})
|
|
require.True(t, freshTask.LogInStorage, "log_in_storage must flip after empty NoMore=true")
|
|
|
|
_, err = storage.Actions.Stat(freshTask.LogFilename)
|
|
assert.NoError(t, err, "archived log must exist in storage")
|
|
|
|
_, err = dbfs.Open(t.Context(), actions_module.DBFSPrefix+freshTask.LogFilename)
|
|
assert.ErrorIs(t, err, os.ErrNotExist, "DBFS row must be cleaned up after TransferLogs")
|
|
|
|
// The runner re-sends its final UpdateLog when the response was lost.
|
|
// A sealed log must ack the re-send and still reject new appended rows.
|
|
t.Run("re-sent finalize is idempotent", func(t *testing.T) {
|
|
finalize := &runnerv1.UpdateLogRequest{TaskId: task.Id, Index: 0, Rows: nil, NoMore: true}
|
|
resp, err := runner.client.runnerServiceClient.UpdateLog(t.Context(), connect.NewRequest(finalize))
|
|
require.NoError(t, err)
|
|
assert.EqualValues(t, 0, resp.Msg.AckIndex)
|
|
|
|
_, err = runner.client.runnerServiceClient.UpdateLog(t.Context(), connect.NewRequest(&runnerv1.UpdateLogRequest{
|
|
TaskId: task.Id, Index: 0, Rows: []*runnerv1.LogRow{{Content: "late"}}, NoMore: true,
|
|
}))
|
|
require.Error(t, err, "appending rows past the seal must be rejected")
|
|
})
|
|
})
|
|
}
|