Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
86 changes: 86 additions & 0 deletions admin/server/virtual_file.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,86 @@
package server

import (
"context"
"fmt"
"path"

"github.com/rilldata/rill/admin/database"
"github.com/rilldata/rill/admin/server/auth"
adminv1 "github.com/rilldata/rill/proto/gen/rill/admin/v1"
"github.com/rilldata/rill/runtime/pkg/observability"
"go.opentelemetry.io/otel/attribute"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)

func (s *Server) GetPersonalFile(ctx context.Context, req *adminv1.GetPersonalFileRequest) (*adminv1.GetPersonalFileResponse, error) {
observability.AddRequestAttributes(ctx,
attribute.String("args.organization", req.Org),
attribute.String("args.project", req.Project),
attribute.String("args.name", req.Name),
)

proj, err := s.admin.DB.FindProjectByName(ctx, req.Org, req.Project)
if err != nil {
return nil, err
}

permissions := auth.GetClaims(ctx).ProjectPermissions(ctx, proj.OrganizationID, proj.ID)
if !permissions.ReadProject {
return nil, status.Error(codes.PermissionDenied, "does not have permission to read project")
}

vf, err := s.admin.DB.FindVirtualFile(ctx, proj.ID, "prod", virtualFilePathForPersonalFile(req.Name, auth.GetClaims(ctx).OwnerID()))
if err != nil {
return nil, fmt.Errorf("failed to get personal file: %w", err)
}

return &adminv1.GetPersonalFileResponse{
Yaml: string(vf.Data),
}, nil
}

func (s *Server) PutPersonalFile(ctx context.Context, req *adminv1.PutPersonalFileRequest) (*adminv1.PutPersonalFileResponse, error) {
observability.AddRequestAttributes(ctx,
attribute.String("args.organization", req.Org),
attribute.String("args.project", req.Project),
attribute.String("args.name", req.Name),
)

proj, err := s.admin.DB.FindProjectByName(ctx, req.Org, req.Project)
if err != nil {
return nil, err
}

permissions := auth.GetClaims(ctx).ProjectPermissions(ctx, proj.OrganizationID, proj.ID)
if !permissions.ReadProject {
return nil, status.Error(codes.PermissionDenied, "does not have permission to read project")
}

err = s.admin.DB.UpsertVirtualFile(ctx, &database.InsertVirtualFileOptions{
ProjectID: proj.ID,
Environment: "prod",
Path: virtualFilePathForPersonalFile(req.Name, auth.GetClaims(ctx).OwnerID()),
Data: []byte(req.Yaml),
})
if err != nil {
return nil, fmt.Errorf("failed to create personal file: %w", err)
}

depl, err := s.admin.DB.FindDeployment(ctx, *proj.PrimaryDeploymentID)
if err != nil {
return nil, err
}

err = s.admin.TriggerParser(ctx, depl)
if err != nil {
return nil, fmt.Errorf("failed to trigger parser: %w", err)
}

return nil, nil
}

func virtualFilePathForPersonalFile(name, userID string) string {
return path.Join("personal", fmt.Sprintf("%s_%s.yaml", name, userID))
}
64 changes: 64 additions & 0 deletions proto/gen/rill/admin/v1/admin.swagger.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -2004,6 +2004,63 @@ paths:
in: path
required: true
type: string
/v1/orgs/{org}/projects/{project}/personal-file/{name}:
get:
operationId: AdminService_GetPersonalFile
responses:
"200":
description: A successful response.
schema:
$ref: '#/definitions/v1GetPersonalFileResponse'
default:
description: An unexpected error response.
schema:
$ref: '#/definitions/rpcStatus'
parameters:
- name: org
in: path
required: true
type: string
- name: project
in: path
required: true
type: string
- name: name
in: path
required: true
type: string
post:
operationId: AdminService_PutPersonalFile
responses:
"200":
description: A successful response.
schema:
$ref: '#/definitions/v1PutPersonalFileResponse'
default:
description: An unexpected error response.
schema:
$ref: '#/definitions/rpcStatus'
parameters:
- name: org
in: path
required: true
type: string
- name: project
in: path
required: true
type: string
- name: name
in: path
required: true
type: string
- name: body
in: body
required: true
schema:
type: object
properties:
yaml:
type: string
/v1/orgs/{org}/projects/{project}/redeploy:
post:
summary: |-
Expand Down Expand Up @@ -5434,6 +5491,11 @@ definitions:
properties:
url:
type: string
v1GetPersonalFileResponse:
type: object
properties:
yaml:
type: string
v1GetProjectAccessRequestResponse:
type: object
properties:
Expand Down Expand Up @@ -6358,6 +6420,8 @@ definitions:
nextPageToken:
type: string
description: Next page token for pagination.
v1PutPersonalFileResponse:
type: object
v1Quotas:
type: object
properties:
Expand Down
Loading
Loading