Compare commits
2 Commits
main
...
feat/drive
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
ced43a5a70 | ||
|
|
515bf1ad69 |
@ -6,6 +6,7 @@
|
||||
- Sheets: add `sheets insert` to insert rows/columns into a sheet. (#203) — thanks @andybergon.
|
||||
- Gmail: add `watch serve --history-types` filtering (`messageAdded|messageDeleted|labelAdded|labelRemoved`) and include `deletedMessageIds` in webhook payloads. (#168) — thanks @salmonumbrella.
|
||||
- Contacts: support `--org`, `--title`, `--url`, `--note`, and `--custom` on create/update; include custom fields in get output with deterministic ordering. (#199) — thanks @phuctm97.
|
||||
- Drive: add `drive ls --all` (alias `--global`) to list across all accessible files; make `--all` and `--parent` mutually exclusive. (#107) — thanks @struong.
|
||||
|
||||
### Fixed
|
||||
- Calendar: respond patches only attendees to avoid custom reminders validation errors. (#265) — thanks @sebasrodriguez.
|
||||
|
||||
@ -833,6 +833,7 @@ gog time now --timezone UTC
|
||||
# List and search
|
||||
gog drive ls --max 20
|
||||
gog drive ls --parent <folderId> --max 20
|
||||
gog drive ls --all --max 20 # List across all accessible files (cannot combine with --parent)
|
||||
gog drive ls --no-all-drives # Only list from "My Drive"
|
||||
gog drive search "invoice" --max 20
|
||||
gog drive search "invoice" --no-all-drives
|
||||
|
||||
@ -178,7 +178,7 @@ Flag aliases:
|
||||
- `gog config set <key> <value>`
|
||||
- `gog config unset <key>`
|
||||
- `gog version`
|
||||
- `gog drive ls [--parent ID] [--max N] [--page TOKEN] [--query Q] [--[no-]all-drives]`
|
||||
- `gog drive ls [--all] [--parent ID] [--max N] [--page TOKEN] [--query Q] [--[no-]all-drives]` (`--all` and `--parent` are mutually exclusive)
|
||||
- `gog drive search <text> [--raw-query] [--max N] [--page TOKEN] [--[no-]all-drives]`
|
||||
- `gog drive get <fileId>`
|
||||
- `gog drive download <fileId> [--out PATH] [--format F]` (`--format` only applies to Google Workspace files)
|
||||
|
||||
@ -84,10 +84,15 @@ type DriveLsCmd struct {
|
||||
Page string `name:"page" aliases:"cursor" help:"Page token"`
|
||||
Query string `name:"query" help:"Drive query filter"`
|
||||
Parent string `name:"parent" help:"Folder ID to list (default: root)"`
|
||||
All bool `name:"all" aliases:"global" help:"List all accessible files (mutually exclusive with --parent)"`
|
||||
AllDrives bool `name:"all-drives" help:"Include shared drives (default: true; use --no-all-drives for My Drive only)" default:"true" negatable:"_"`
|
||||
}
|
||||
|
||||
func (c *DriveLsCmd) Run(ctx context.Context, flags *RootFlags) error {
|
||||
if c.All && strings.TrimSpace(c.Parent) != "" {
|
||||
return usage("--all cannot be combined with --parent")
|
||||
}
|
||||
|
||||
u := ui.FromContext(ctx)
|
||||
account, err := requireAccount(flags)
|
||||
if err != nil {
|
||||
@ -104,7 +109,12 @@ func (c *DriveLsCmd) Run(ctx context.Context, flags *RootFlags) error {
|
||||
return err
|
||||
}
|
||||
|
||||
q := buildDriveListQuery(folderID, c.Query)
|
||||
var q string
|
||||
if c.All {
|
||||
q = buildDriveAllListQuery(c.Query)
|
||||
} else {
|
||||
q = buildDriveListQuery(folderID, c.Query)
|
||||
}
|
||||
|
||||
// Include files from shared drives, not just personal "My Drive"
|
||||
call := svc.Files.List().
|
||||
@ -988,6 +998,17 @@ func buildDriveListQuery(folderID string, userQuery string) string {
|
||||
return q
|
||||
}
|
||||
|
||||
func buildDriveAllListQuery(userQuery string) string {
|
||||
q := strings.TrimSpace(userQuery)
|
||||
if q == "" {
|
||||
return "trashed = false"
|
||||
}
|
||||
if !hasDriveTrashedPredicate(q) {
|
||||
q += " and trashed = false"
|
||||
}
|
||||
return q
|
||||
}
|
||||
|
||||
func buildDriveSearchQuery(text string, rawQuery bool) string {
|
||||
q := strings.TrimSpace(text)
|
||||
if q == "" {
|
||||
|
||||
@ -14,6 +14,11 @@ func TestDriveCommand_ValidationErrors(t *testing.T) {
|
||||
t.Fatalf("expected parent error, got %v", err)
|
||||
}
|
||||
|
||||
lsCmd := &DriveLsCmd{}
|
||||
if err := runKong(t, lsCmd, []string{"--all", "--parent", "p1"}, context.Background(), flags); err == nil || !strings.Contains(err.Error(), "--all cannot be combined with --parent") {
|
||||
t.Fatalf("expected mutually exclusive error, got %v", err)
|
||||
}
|
||||
|
||||
shareCmd := &DriveShareCmd{}
|
||||
if err := runKong(t, shareCmd, []string{"file1"}, context.Background(), flags); err == nil || !strings.Contains(err.Error(), "must specify --to") {
|
||||
t.Fatalf("expected share target error, got %v", err)
|
||||
|
||||
@ -32,6 +32,27 @@ func TestBuildDriveListQuery(t *testing.T) {
|
||||
})
|
||||
}
|
||||
|
||||
func TestBuildDriveAllListQuery(t *testing.T) {
|
||||
tests := []struct {
|
||||
name string
|
||||
query string
|
||||
expected string
|
||||
}{
|
||||
{"empty query", "", "trashed = false"},
|
||||
{"with query", "mimeType='image/png'", "mimeType='image/png' and trashed = false"},
|
||||
{"query mentions trashed", "trashed = true", "trashed = true"},
|
||||
{"quoted trashed string", "name contains 'trashed'", "name contains 'trashed' and trashed = false"},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
got := buildDriveAllListQuery(tt.query)
|
||||
if got != tt.expected {
|
||||
t.Errorf("buildDriveAllListQuery(%q) = %q, want %q", tt.query, got, tt.expected)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestBuildDriveSearchQuery(t *testing.T) {
|
||||
got := buildDriveSearchQuery("hello world", false)
|
||||
if got != "fullText contains 'hello world' and trashed = false" {
|
||||
|
||||
Loading…
Reference in New Issue
Block a user