Skip to content
Merged
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
2 changes: 1 addition & 1 deletion VERSION
Original file line number Diff line number Diff line change
@@ -1 +1 @@
0.18.2
0.19.0
6 changes: 6 additions & 0 deletions entries.go
Original file line number Diff line number Diff line change
Expand Up @@ -172,6 +172,12 @@ type entryListRawResponse struct {
TotalPage int `json:"totalPage"`
}

// GetByNameOptions contains optional filters for GetByName.
// A nil field means the filter is not applied.
type GetByNameOptions struct {
Path *string
}

// getEntriesOptions contains optional filters for listing entries.
// A nil value means the filter is not applied.
type GetEntriesOptions struct {
Expand Down
6 changes: 0 additions & 6 deletions entry_credential.go
Original file line number Diff line number Diff line change
Expand Up @@ -481,12 +481,6 @@ func (c *EntryCredentialService) GetEntriesWithContext(ctx context.Context, vaul
return credentials, nil
}

// GetByNameOptions contains optional filters for GetByName.
// A nil field means the filter is not applied.
type GetByNameOptions struct {
Path *string
}

// GetByName retrieves a single credential entry by name, subType, and optional filters.
// Returns ErrEntryNotFound if no match exists.
// Returns ErrMultipleEntriesFound if more than one match exists.
Expand Down
22 changes: 22 additions & 0 deletions entry_folder.go
Original file line number Diff line number Diff line change
Expand Up @@ -266,6 +266,28 @@ func (c *EntryFolderService) DeleteByIdWithContext(ctx context.Context, vaultId
return nil
}

// GetByName retrieves a single folder entry by name and optional filters.
// Returns ErrEntryNotFound if no match exists.
func (c *EntryFolderService) GetByName(vaultId, name string, opts GetByNameOptions) (Entry, error) {
return c.GetByNameWithContext(context.Background(), vaultId, name, opts)
}

// GetByNameWithContext retrieves a single folder entry by name and optional filters.
// Returns ErrEntryNotFound if no match exists.
// The provided context can be used to cancel the request.
func (c *EntryFolderService) GetByNameWithContext(ctx context.Context, vaultId, name string, opts GetByNameOptions) (Entry, error) {
entries, err := c.GetEntriesWithContext(ctx, vaultId, GetEntriesOptions{Name: &name, Path: opts.Path})
if err != nil {
return Entry{}, err
}

if len(entries) == 0 {
return Entry{}, ErrEntryNotFound
}

return c.GetByIdWithContext(ctx, vaultId, entries[0].Id)
}

// GetEntries returns a list of folder entries from a vault with optional filters.
// Note: The API does not support filtering by entry type, so all entries are fetched and filtered client-side.
func (c *EntryFolderService) GetEntries(vaultId string, opts GetEntriesOptions) ([]Entry, error) {
Expand Down
56 changes: 56 additions & 0 deletions entry_folder_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -196,6 +196,62 @@ func Test_NestedFolders(t *testing.T) {
require.NoError(t, err, "Failed to delete parent folder")
}

func Test_GetFolderByName(t *testing.T) {
vault := createTestVault(t, "folder-getbyname")
testPath := "go-dvls\\folder-getbyname"

entry := Entry{
VaultId: vault.Id,
Name: "MyFolder",
Path: testPath,
Type: EntryFolderType,
SubType: EntryFolderSubTypeFolder,
Data: &EntryFolderData{Domain: "test.local", Username: "testuser"},
}

id, err := testClient.Entries.Folder.New(entry)
require.NoError(t, err, "Failed to create folder entry")
t.Cleanup(func() {
_ = testClient.Entries.Folder.DeleteById(vault.Id, id)
})

// GetByName with name only
got, err := testClient.Entries.Folder.GetByName(vault.Id, "MyFolder", GetByNameOptions{Path: &testPath})
require.NoError(t, err)
assert.Equal(t, id, got.Id)
assert.Equal(t, "MyFolder", got.Name)
assert.Equal(t, testPath+`\MyFolder`, got.Path)

// GetByName with non-existent name returns ErrEntryNotFound
_, err = testClient.Entries.Folder.GetByName(vault.Id, "NonExistentFolder", GetByNameOptions{Path: &testPath})
assert.ErrorIs(t, err, ErrEntryNotFound)

// GetByName without path filter also finds the entry
got, err = testClient.Entries.Folder.GetByName(vault.Id, "MyFolder", GetByNameOptions{})
require.NoError(t, err)
assert.Equal(t, id, got.Id)

// Root-level folder: path returned by API is the folder name itself
rootEntry := Entry{
VaultId: vault.Id,
Name: "MyRootFolder",
Path: "",
Type: EntryFolderType,
SubType: EntryFolderSubTypeFolder,
Data: &EntryFolderData{},
}
rootId, err := testClient.Entries.Folder.New(rootEntry)
require.NoError(t, err)
t.Cleanup(func() {
_ = testClient.Entries.Folder.DeleteById(vault.Id, rootId)
})

root, err := testClient.Entries.Folder.GetByName(vault.Id, "MyRootFolder", GetByNameOptions{})
require.NoError(t, err)
assert.Equal(t, rootId, root.Id)
assert.Equal(t, "MyRootFolder", root.Path)
}

func Test_GetFolderEntries_Filters(t *testing.T) {
vault := createTestVault(t, "folder-getentries")
testPath := "go-dvls\\folder-getentries"
Expand Down