Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
24 commits
Select commit Hold shift + click to select a range
d7c7044
fix: use UTC dates consistently when displaying the usage data, switc…
netomi Mar 19, 2026
6ebea74
feat(UI): adding option to add members to customers (#1700)
gnugomez Mar 19, 2026
c2ee1b3
fix navigation in sidepanel
netomi Mar 19, 2026
e2a496a
overhaul admin dashboard: make sidepanel collabsible, add breadcrumbs
netomi Mar 19, 2026
e902a0e
fix: app bar not showing proper bg color on dark mode (#1704)
gnugomez Mar 20, 2026
83fa412
make sidebar open by default
netomi Mar 20, 2026
4c846e4
feat: adding sidebar groups (#1705)
gnugomez Mar 20, 2026
7b1db50
add eslint plugin for react refresh, fix and update target
netomi Mar 20, 2026
c098622
suppress remaining eslint errors
netomi Mar 20, 2026
cbdf9c3
feat: adding rate limiting tab to user settings (#1707)
gnugomez Mar 20, 2026
c2cd2ce
add CustomerMembership entity
netomi Mar 23, 2026
1480585
add customer membership repository
netomi Mar 23, 2026
bbb6e84
support editing customer membership
netomi Mar 24, 2026
c226338
update openapi documentation wrt rate limit headers
netomi Apr 1, 2026
6938258
add default rate limit headers to all responses
netomi Apr 3, 2026
492291d
support getting usage stats for a user assigned to a customer
netomi Apr 3, 2026
5c6d7cc
fix unit test
netomi Apr 3, 2026
23b17a6
feat(UI): adding rate limiting tokens UI (#1731)
gnugomez Apr 7, 2026
8787ab2
improve token dialog
netomi Apr 7, 2026
19ae806
update admin calls to get / create rate limit tokens
netomi Apr 7, 2026
2db0b3a
fix: stop uding variants for runtime style updates (#1746)
gnugomez Apr 7, 2026
0ef907e
add support for rate limit tokens
netomi Apr 7, 2026
d0616ba
add rate limit token handling
netomi Apr 7, 2026
cd8dc23
add on delete cascase to usage_stats table
netomi Apr 7, 2026
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
54 changes: 46 additions & 8 deletions server/src/main/java/org/eclipse/openvsx/UserAPI.java
Original file line number Diff line number Diff line change
Expand Up @@ -12,19 +12,13 @@
import jakarta.servlet.http.HttpServletRequest;
import org.eclipse.openvsx.accesstoken.AccessTokenService;
import org.eclipse.openvsx.eclipse.EclipseService;
import org.eclipse.openvsx.entities.ExtensionVersion;
import org.eclipse.openvsx.entities.NamespaceMembership;
import org.eclipse.openvsx.entities.ScanStatus;
import org.eclipse.openvsx.entities.UserData;
import org.eclipse.openvsx.entities.*;
import org.eclipse.openvsx.json.*;
import org.eclipse.openvsx.repositories.ExtensionScanRepository;
import org.eclipse.openvsx.repositories.RepositoryService;
import org.eclipse.openvsx.security.CodedAuthException;
import org.eclipse.openvsx.storage.StorageUtilService;
import org.eclipse.openvsx.util.ErrorResultException;
import org.eclipse.openvsx.util.NamingUtil;
import org.eclipse.openvsx.util.NotFoundException;
import org.eclipse.openvsx.util.UrlUtil;
import org.eclipse.openvsx.util.*;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.http.CacheControl;
Expand Down Expand Up @@ -484,6 +478,50 @@ public ResponseEntity<ResultJson> setNamespaceMember(@PathVariable String namesp
}
}

@GetMapping(
path = "/user/customers",
produces = MediaType.APPLICATION_JSON_VALUE
)
public List<CustomerJson> getOwnCustomers() {
var user = users.findLoggedInUser();
if (user == null) {
throw new ResponseStatusException(HttpStatus.FORBIDDEN);
}

return repositories.findCustomerMemberships(user).map(membership -> membership.getCustomer().toUserJson() ).toList();
}

@GetMapping(
path = "/user/customers/{name}/usage",
produces = MediaType.APPLICATION_JSON_VALUE
)
public ResponseEntity<UsageStatsListJson> getOwnUsageStats(@PathVariable String name, @RequestParam(required = false) String date) {
try {
var user = users.findLoggedInUser();
if (user == null) {
throw new ResponseStatusException(HttpStatus.FORBIDDEN);
}

var customer = repositories.findCustomer(name);
if (customer == null) {
return ResponseEntity.notFound().build();
}

var membership = repositories.findCustomerMembership(user, customer);
if (membership == null) {
throw new ResponseStatusException(HttpStatus.FORBIDDEN);
}

var localDateTime = date != null ? TimeUtil.fromUTCString(date) : TimeUtil.getCurrentUTC();
var stats = repositories.findUsageStatsByCustomerAndDate(customer, localDateTime);
var result = new UsageStatsListJson(stats.stream().map(UsageStats::toJson).toList());
return ResponseEntity.ok(result);
} catch (Exception exc) {
logger.error("failed retrieving usage stats", exc);
return ResponseEntity.internalServerError().build();
}
}

@GetMapping(
path = "/user/search/{name}",
produces = MediaType.APPLICATION_JSON_VALUE
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,6 @@
import org.springframework.stereotype.Service;

import java.time.LocalDateTime;
import java.util.List;
import java.util.UUID;

import static org.eclipse.openvsx.util.UrlUtil.createApiUrl;
Expand Down
Loading
Loading