Skip to content

Commit f09e983

Browse files
committed
IOT-1157: Fetch all gateways at once instead of pagination
1 parent 99353c6 commit f09e983

File tree

6 files changed

+82
-35
lines changed

6 files changed

+82
-35
lines changed

src/controllers/admin-controller/chirpstack/chirpstack-gateway.controller.ts

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,7 @@ import { checkIfUserHasWriteAccessToOrganization } from "@helpers/security-helpe
3535
import { AuthenticatedRequest } from "@dto/internal/authenticated-request";
3636
import { AuditLog } from "@services/audit-log.service";
3737
import { ActionType } from "@entities/audit-log-entry";
38+
import { ChirpstackGetAll } from "@dto/chirpstack/chirpstack-get-all.dto";
3839

3940
@ApiTags("Chirpstack")
4041
@Controller("chirpstack/gateway")
@@ -87,11 +88,9 @@ export class ChirpstackGatewayController {
8788
@ApiOperation({ summary: "List all Chirpstack gateways" })
8889
@Read()
8990
async getAll(
90-
@Query() query?: ChirpstackPaginatedListDto
91+
@Query() query?: ChirpstackGetAll
9192
): Promise<ListAllGatewaysResponseDto> {
92-
return await this.chirpstackGatewayService.listAllPaginated(
93-
query.limit,
94-
query.offset,
93+
return await this.chirpstackGatewayService.getAll(
9594
query.organizationId
9695
);
9796
}
Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
import { PickType } from "@nestjs/swagger";
2+
import { ChirpstackPaginatedListDto } from "./chirpstack-paginated-list.dto";
3+
4+
export class ChirpstackGetAll extends PickType(ChirpstackPaginatedListDto, [
5+
"organizationId",
6+
]) {}

src/services/chirpstack/chirpstack-gateway.service.ts

Lines changed: 35 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@ import { GatewayContentsDto } from "@dto/chirpstack/gateway-contents.dto";
2525
import * as _ from "lodash";
2626
import { AuthenticatedRequest } from "@dto/internal/authenticated-request";
2727
import { checkIfUserHasWriteAccessToOrganization } from "@helpers/security-helper";
28+
import { GatewayResponseDto } from "@dto/chirpstack/gateway-response.dto";
2829

2930
@Injectable()
3031
export class ChirpstackGatewayService extends GenericChirpstackConfigurationService {
@@ -78,25 +79,42 @@ export class ChirpstackGatewayService extends GenericChirpstackConfigurationServ
7879
return tags;
7980
}
8081

81-
async listAllPaginated(
82-
limit?: number,
83-
offset?: number,
84-
organizationId?: number
85-
): Promise<ListAllGatewaysResponseDto> {
86-
// Default parameters if not set
87-
if (!offset) {
88-
offset = 0;
89-
}
90-
if (!limit) {
91-
limit = 100;
82+
async getAll(organizationId?: number): Promise<ListAllGatewaysResponseDto> {
83+
const limit = 1000;
84+
let allResults: GatewayResponseDto[] = [];
85+
let totalCount = 0;
86+
let lastResults;
87+
do {
88+
// Default parameters if not set
89+
lastResults = await this.getAllWithPagination<ListAllGatewaysResponseDto>(
90+
"gateways",
91+
limit,
92+
allResults.length
93+
);
94+
allResults = _.union(allResults, lastResults.result);
95+
totalCount = lastResults.totalCount;
96+
} while (totalCount > allResults.length && lastResults.result.length > 0);
97+
98+
await this.enrichWithOrganizationId(allResults);
99+
if (organizationId !== undefined) {
100+
const filteredResults = _.filter(allResults, x => {
101+
return x.internalOrganizationId === +organizationId;
102+
});
103+
return {
104+
result: filteredResults,
105+
totalCount: filteredResults.length,
106+
};
92107
}
93-
const results = await this.getAllWithPagination<ListAllGatewaysResponseDto>(
94-
"gateways",
95-
limit,
96-
offset
97-
);
108+
109+
return {
110+
result: allResults,
111+
totalCount: totalCount,
112+
};
113+
}
114+
115+
private async enrichWithOrganizationId(results: GatewayResponseDto[]) {
98116
await Promise.all(
99-
results.result.map(async x => {
117+
results.map(async x => {
100118
try {
101119
const gw = await this.getOne(x.id);
102120
x.internalOrganizationId = gw.gateway.internalOrganizationId;
@@ -109,17 +127,6 @@ export class ChirpstackGatewayService extends GenericChirpstackConfigurationServ
109127
}
110128
})
111129
);
112-
if (organizationId !== undefined) {
113-
const filteredResults = _.filter(results.result, x => {
114-
return x.internalOrganizationId === +organizationId;
115-
});
116-
return {
117-
result: filteredResults,
118-
totalCount: filteredResults.length,
119-
};
120-
}
121-
122-
return results;
123130
}
124131

125132
async getOne(gatewayId: string): Promise<SingleGatewayResponseDto> {

test/e2e/chirpstack/chirpstack-gateway-configuration.e2e-spec.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -81,7 +81,7 @@ describe("ChirpstackGatewayController (e2e)", () => {
8181
beforeEach(async () => {
8282
await clearDatabase();
8383
// Delete all gateways created in E2E tests:
84-
const existing = await service.listAllPaginated(1000, 0);
84+
const existing = await service.getAll(1000, 0);
8585
existing.result.forEach(async element => {
8686
if (element.name.startsWith(gatewayNamePrefix)) {
8787
// Logger.debug(`Found ${element.name}, deleting.`);

test/e2e/crud/search.e2e-spec.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -93,7 +93,7 @@ describe("SearchController (e2e)", () => {
9393
await clearDatabase();
9494

9595
// Delete all gateways created in E2E tests:
96-
const existing = await chirpstackGatewayService.listAllPaginated(1000, 0);
96+
const existing = await chirpstackGatewayService.getAll(1000, 0);
9797
existing.result.forEach(async element => {
9898
if (element.name.startsWith(gatewayNamePrefix)) {
9999
// Logger.debug(`Found ${element.name}, deleting.`);

test/e2e/generate_data_for_loadtest.py

Lines changed: 36 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,8 +9,14 @@
99
"Authorization": f"Bearer {JWT}"
1010
}
1111

12+
1213
def random_mac():
13-
return "02:00:00:%02x:%02x:%02x" % (random.randint(0, 255), random.randint(0, 255), random.randint(0, 255))
14+
return "02:00:00:%02x:%02x:%02x" % (random.randint(0, 255), random.randint(0, 255), random.randint(0, 255)
15+
)
16+
17+
18+
def random_mac_16_no_seperator():
19+
return "0201020100%02x%02x%02x" % (random.randint(0, 255), random.randint(0, 255), random.randint(0, 255))
1420

1521

1622
def generate_application():
@@ -41,8 +47,37 @@ def generate_iot_device():
4147
return id
4248

4349

50+
def generate_gateway():
51+
id = random_mac_16_no_seperator()
52+
dto = {
53+
"gateway": {
54+
"boards": [],
55+
"description": PREFIX,
56+
"discoveryEnabled": False,
57+
"id": id,
58+
"location": {
59+
"longitude": random.uniform(10, 12),
60+
"latitude": random.uniform(55, 57),
61+
"altitude": random.uniform(10, 100),
62+
},
63+
"metadata": {},
64+
"name": f"{PREFIX}-gw-{id}",
65+
"tagsString": "{}"
66+
},
67+
"organizationId": 1
68+
}
69+
res = requests.post(
70+
'http://[::1]:3000/api/v1/chirpstack/gateway', json=dto, headers=headers)
71+
id = res.json()
72+
print(f"made gateway: {id}")
73+
return id
74+
75+
4476
for i in range(100):
4577
applications_made.append(generate_application())
4678

4779
for i in range(10000):
4880
generate_iot_device()
81+
82+
for i in range(100):
83+
generate_gateway()

0 commit comments

Comments
 (0)