Owners and Pagination
Philter scopes its data to the user whose API key made the request. Every call in this client therefore acts on your own policies, contexts, documents, holds, ledger entries, and lists by default.
Acting on another user's data
Endpoints that accept an owner have an overload taking that owner's username. It is the last argument everywhere except the listings that take ListOptions, where it comes just before the options, and reidentifyValues(owner, request) and reidentifyText(owner, request), where it comes first.
// Your own policies.
Page<PolicySummary> mine = client.listPolicies(null, null);
// Another user's policies, as an administrator.
Page<PolicySummary> theirs = client.listPolicies("someone@example.com", null);
String policy = client.getPolicy("default", "someone@example.com");
Naming your own username always works. Reaching another user's data requires both an administrator API key and ADMIN_CROSS_USER_ACCESS_ENABLED=true on the deployment; without them Philter answers 404, which the client raises as a ClientException. The 404 is deliberate, so an owner name cannot be used to discover which users exist.
Passing null for an owner is the same as omitting it: the call acts on your own data.
getApiKeys is the exception: listing another user's API keys requires an administrator key, but not ADMIN_CROSS_USER_ACCESS_ENABLED. Changing and revoking keys take a key ID rather than an owner. See Users and API Keys.
Listings: paging, sorting, search, and filters
Every listing returns a page of items and getTotal(), how many items it has across every page, counting only those that match the search and filters. Pass a ListOptions to choose the page, the order, a search, and the listing's filters; every setting is optional, and null options use Philter's defaults: the first 25 items in the listing's default order.
import ai.philterd.philter.model.ListOptions;
import ai.philterd.philter.model.Page;
// The third page of 50 policies whose name contains "claims", newest first.
Page<PolicySummary> page = client.listPolicies(null,
new ListOptions().offset(100).limit(50).sort("created").descending().search("claims"));
long total = page.getTotal();
for (PolicySummary policy : page.getItems()) {
System.out.println(policy.getName());
}
offset(n)andlimit(n)choose the page: the limit defaults to 25 and is at most 100.sort(field)orders by one of the listing's fields, below. An unknown field is an HTTP 400 naming the fields it accepts, raised as aClientExceptionwhosegetField()issort.ascending()anddescending()set the order. Left out, the default sort keeps its default direction, and any other sort is ascending.search(text)keeps items whose searched field contains the text, ignoring case, matched as plain text. It is sent asq.- The filters apply to one listing each:
role(...)andactive(...)to users,status(...)to documents, andsession(...)to API keys.
| Method | Returns | sort (default first) |
search matches |
Filters |
|---|---|---|---|---|
listPolicies(owner, options) |
Page<PolicySummary> |
name, created, updated |
name | |
listPoliciesAcrossUsers(options) |
Page<PolicySummary> |
name, created, updated |
name | |
listManagedPolicies(options) |
Page<PolicySummary> |
name |
name | |
getDeletedPolicies(owner, options) |
GetDeletedPoliciesResponse |
name |
name | |
listPolicyVersions(name, owner, options) |
Page<PolicyVersionSummary> |
revision (newest first) |
||
listContexts(owner, options) |
GetContextsResponse |
name, created |
name | |
listContextsAcrossUsers(options) |
GetContextsAcrossUsersResponse |
name, created |
name | |
listContextEntries(name, owner, options) |
GetContextEntriesResponse |
created (newest first), reads |
||
listCustomLists(owner, options) |
Page<CustomListSummary> |
name |
name | |
listCustomListsAcrossUsers(options) |
Page<CustomListSummary> |
name |
name | |
listHolds(owner, options) |
Page<LegalHoldResponse> |
set (newest first), reference |
reference | |
listHoldsAcrossUsers(options) |
Page<OwnedLegalHoldResponse> |
set (newest first), reference |
reference | |
listDocuments(owner, options) |
GetDocumentsResponse |
submitted (newest first), fileName |
status |
|
listLedgerChains(owner, options) |
GetLedgerResponse |
created (newest first), filename |
document ID or file name | |
listLedgerChainsAcrossUsers(options) |
GetLedgerResponse |
created (newest first), filename |
document ID or file name | |
getUsers(options) |
GetUsersResponse |
username, created |
username | role, active |
getApiKeys(owner, options) |
GetApiKeysResponse |
created (oldest first) |
session |
|
getAuditLog(event, from, to, owner, options) |
GetAuditLogResponse |
timestamp (newest first), order only |
||
getWebhookDeliveries(owner, options) |
GetWebhookDeliveriesResponse |
created (newest first), order only |
Items with the same sort value keep a stable order, so paging does not skip or repeat them.
Listing across all users
An administrator can list every user's policies, contexts, custom lists, ledger chains, and legal holds in one call, with the ...AcrossUsers(options) methods above. Each item names its owner. The same two conditions apply as for owner: an administrator key and ADMIN_CROSS_USER_ACCESS_ENABLED=true, otherwise a 404 raised as a ClientException. Managed policies are not included in listPoliciesAcrossUsers.
Page<PolicySummary> policies = client.listPoliciesAcrossUsers(new ListOptions().search("claims"));
Page<OwnedLegalHoldResponse> holds = client.listHoldsAcrossUsers(new ListOptions().limit(100));
Offset and limit overloads
Some listings, such as listContexts(owner, offset, limit) and getUsers(offset, limit), also have an overload that takes offset and limit directly. It returns the same page and total, without sorting or search.
exportAuditLog is paged with offset and limit too, but with its own defaults and a truncation flag; see Audit Log. listRedactLists is not a listing: it returns the two redact lists.