@overmap-ai/core 1.0.41 → 1.0.43-projects-licensing.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +4 -4
- package/dist/overmap-core.js +478 -185
- package/dist/overmap-core.js.map +1 -1
- package/dist/overmap-core.umd.cjs +478 -185
- package/dist/overmap-core.umd.cjs.map +1 -1
- package/dist/sdk/sdk.d.ts +2 -1
- package/dist/sdk/services/LicenseService.d.ts +12 -0
- package/dist/sdk/services/MainService.d.ts +2 -1
- package/dist/sdk/services/ProjectService.d.ts +2 -3
- package/dist/sdk/services/index.d.ts +1 -0
- package/dist/store/slices/categorySlice.d.ts +1 -0
- package/dist/store/slices/index.d.ts +1 -0
- package/dist/store/slices/issueSlice.d.ts +2 -4
- package/dist/store/slices/licenseSlice.d.ts +25 -0
- package/dist/store/slices/organizationSlice.d.ts +5 -1
- package/dist/store/slices/projectFileSlice.d.ts +1 -0
- package/dist/store/slices/projectSlice.d.ts +7 -1
- package/dist/store/slices/settingsSlice.d.ts +7 -1
- package/dist/store/slices/workspaceSlice.d.ts +1 -0
- package/dist/store/store.d.ts +4 -1
- package/dist/typings/models/base.d.ts +4 -0
- package/dist/typings/models/index.d.ts +1 -0
- package/dist/typings/models/license.d.ts +29 -0
- package/dist/typings/models/organizations.d.ts +2 -0
- package/dist/typings/models/projects.d.ts +2 -0
- package/package.json +151 -151
package/dist/overmap-core.js
CHANGED
|
@@ -632,15 +632,15 @@ const wrapMigration = (migrator) => (state) => {
|
|
|
632
632
|
};
|
|
633
633
|
const migrations = [initialVersioning, signOut, signOut, createOutboxState];
|
|
634
634
|
const manifest = Object.fromEntries(migrations.map((migration2, i) => [i, wrapMigration(migration2)]));
|
|
635
|
-
const initialState$
|
|
635
|
+
const initialState$m = {
|
|
636
636
|
accessToken: "",
|
|
637
637
|
refreshToken: "",
|
|
638
638
|
isLoggedIn: false
|
|
639
639
|
};
|
|
640
640
|
const authSlice = createSlice({
|
|
641
641
|
name: "auth",
|
|
642
|
-
initialState: initialState$
|
|
643
|
-
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$
|
|
642
|
+
initialState: initialState$m,
|
|
643
|
+
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$m)),
|
|
644
644
|
reducers: {
|
|
645
645
|
setTokens: (state, action) => {
|
|
646
646
|
state.accessToken = action.payload.accessToken;
|
|
@@ -1371,7 +1371,7 @@ const getLocalRelativeDateString = memoize((date, min, max) => {
|
|
|
1371
1371
|
return getLocalDateString(date);
|
|
1372
1372
|
return relative.format(days, "days");
|
|
1373
1373
|
});
|
|
1374
|
-
const initialState$
|
|
1374
|
+
const initialState$l = {
|
|
1375
1375
|
categories: {},
|
|
1376
1376
|
usedCategoryColors: [],
|
|
1377
1377
|
categoryVisibility: {
|
|
@@ -1381,8 +1381,8 @@ const initialState$k = {
|
|
|
1381
1381
|
};
|
|
1382
1382
|
const categorySlice = createSlice({
|
|
1383
1383
|
name: "categories",
|
|
1384
|
-
initialState: initialState$
|
|
1385
|
-
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$
|
|
1384
|
+
initialState: initialState$l,
|
|
1385
|
+
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$l)),
|
|
1386
1386
|
reducers: {
|
|
1387
1387
|
setCategories: (state, action) => {
|
|
1388
1388
|
if (!Array.isArray(action.payload))
|
|
@@ -1515,13 +1515,13 @@ const selectHiddenCategoryCount = (state) => {
|
|
|
1515
1515
|
return hiddenCategoryCount;
|
|
1516
1516
|
};
|
|
1517
1517
|
const categoryReducer = categorySlice.reducer;
|
|
1518
|
-
const initialState$
|
|
1518
|
+
const initialState$k = {
|
|
1519
1519
|
components: {}
|
|
1520
1520
|
};
|
|
1521
1521
|
const componentSlice = createSlice({
|
|
1522
1522
|
name: "components",
|
|
1523
|
-
initialState: initialState$
|
|
1524
|
-
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$
|
|
1523
|
+
initialState: initialState$k,
|
|
1524
|
+
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$k)),
|
|
1525
1525
|
reducers: {
|
|
1526
1526
|
addComponent: (state, action) => {
|
|
1527
1527
|
state.components[action.payload.offline_id] = action.payload;
|
|
@@ -1633,13 +1633,13 @@ const {
|
|
|
1633
1633
|
removeAllComponentsOfType
|
|
1634
1634
|
} = componentSlice.actions;
|
|
1635
1635
|
const componentReducer = componentSlice.reducer;
|
|
1636
|
-
const initialState$
|
|
1636
|
+
const initialState$j = {
|
|
1637
1637
|
completionsByComponentId: {}
|
|
1638
1638
|
};
|
|
1639
1639
|
const componentStageCompletionSlice = createSlice({
|
|
1640
1640
|
name: "componentStageCompletions",
|
|
1641
|
-
initialState: initialState$
|
|
1642
|
-
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$
|
|
1641
|
+
initialState: initialState$j,
|
|
1642
|
+
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$j)),
|
|
1643
1643
|
reducers: {
|
|
1644
1644
|
addStageCompletion: (state, action) => {
|
|
1645
1645
|
let stageToCompletionDateMapping = state.completionsByComponentId[action.payload.component];
|
|
@@ -1690,13 +1690,13 @@ const selectCompletedStageIdsForComponent = (component) => (state) => {
|
|
|
1690
1690
|
return Object.keys(state.componentStageCompletionReducer.completionsByComponentId[component.offline_id] ?? {});
|
|
1691
1691
|
};
|
|
1692
1692
|
const componentStageCompletionReducer = componentStageCompletionSlice.reducer;
|
|
1693
|
-
const initialState$
|
|
1693
|
+
const initialState$i = {
|
|
1694
1694
|
stages: {}
|
|
1695
1695
|
};
|
|
1696
1696
|
const componentStageSlice = createSlice({
|
|
1697
1697
|
name: "componentStages",
|
|
1698
|
-
initialState: initialState$
|
|
1699
|
-
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$
|
|
1698
|
+
initialState: initialState$i,
|
|
1699
|
+
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$i)),
|
|
1700
1700
|
reducers: {
|
|
1701
1701
|
addStages: (state, action) => {
|
|
1702
1702
|
Object.assign(state.stages, toOfflineIdRecord(action.payload));
|
|
@@ -1787,14 +1787,14 @@ const selectStageFormIdsFromStageIds = restructureCreateSelectorWithArgs(
|
|
|
1787
1787
|
);
|
|
1788
1788
|
const { addStages, updateStages, removeStages, linkStageToForm, unlinkStageToForm } = componentStageSlice.actions;
|
|
1789
1789
|
const componentStageReducer = componentStageSlice.reducer;
|
|
1790
|
-
const initialState$
|
|
1790
|
+
const initialState$h = {
|
|
1791
1791
|
componentTypes: {},
|
|
1792
1792
|
hiddenComponentTypeIds: {}
|
|
1793
1793
|
};
|
|
1794
1794
|
const componentTypeSlice = createSlice({
|
|
1795
1795
|
name: "componentTypes",
|
|
1796
|
-
initialState: initialState$
|
|
1797
|
-
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$
|
|
1796
|
+
initialState: initialState$h,
|
|
1797
|
+
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$h)),
|
|
1798
1798
|
reducers: {
|
|
1799
1799
|
addComponentType: (state, action) => {
|
|
1800
1800
|
state.componentTypes[action.payload.offline_id] = action.payload;
|
|
@@ -1853,13 +1853,13 @@ const selectComponentTypesByName = restructureCreateSelectorWithArgs(
|
|
|
1853
1853
|
const selectHiddenComponentTypeIds = (state) => state.componentTypeReducer.hiddenComponentTypeIds;
|
|
1854
1854
|
const { addComponentType, setComponentTypes, toggleComponentTypeVisibility, deleteComponentType } = componentTypeSlice.actions;
|
|
1855
1855
|
const componentTypeReducer = componentTypeSlice.reducer;
|
|
1856
|
-
const initialState$
|
|
1856
|
+
const initialState$g = {
|
|
1857
1857
|
workspaces: {},
|
|
1858
1858
|
activeWorkspaceId: null
|
|
1859
1859
|
};
|
|
1860
1860
|
const workspaceSlice = createSlice({
|
|
1861
1861
|
name: "workspace",
|
|
1862
|
-
initialState: initialState$
|
|
1862
|
+
initialState: initialState$g,
|
|
1863
1863
|
// The `reducers` field lets us define reducers and generate associated actions
|
|
1864
1864
|
reducers: {
|
|
1865
1865
|
setWorkspaces: (state, action) => {
|
|
@@ -1916,21 +1916,20 @@ const selectPermittedWorkspaceIds = createSelector(
|
|
|
1916
1916
|
);
|
|
1917
1917
|
const workspaceReducer = workspaceSlice.reducer;
|
|
1918
1918
|
const maxRecentIssues = 10;
|
|
1919
|
-
const initialState$
|
|
1919
|
+
const initialState$f = {
|
|
1920
1920
|
issues: {},
|
|
1921
1921
|
attachments: {},
|
|
1922
1922
|
comments: {},
|
|
1923
1923
|
visibleStatuses: [IssueStatus.BACKLOG, IssueStatus.SELECTED],
|
|
1924
|
-
isFetchingInitialData: false,
|
|
1925
1924
|
visibleUserIds: null,
|
|
1926
1925
|
recentIssueIds: [],
|
|
1927
1926
|
activeIssueId: null
|
|
1928
1927
|
};
|
|
1929
1928
|
const issueSlice = createSlice({
|
|
1930
1929
|
name: "issues",
|
|
1931
|
-
initialState: initialState$
|
|
1930
|
+
initialState: initialState$f,
|
|
1932
1931
|
extraReducers: (builder) => builder.addCase("RESET", (state) => {
|
|
1933
|
-
Object.assign(state, initialState$
|
|
1932
|
+
Object.assign(state, initialState$f);
|
|
1934
1933
|
}),
|
|
1935
1934
|
reducers: {
|
|
1936
1935
|
setIssues: (state, action) => {
|
|
@@ -2009,9 +2008,6 @@ const issueSlice = createSlice({
|
|
|
2009
2008
|
setVisibleStatuses: (state, action) => {
|
|
2010
2009
|
state.visibleStatuses = action.payload;
|
|
2011
2010
|
},
|
|
2012
|
-
setIsFetchingInitialData: (state, action) => {
|
|
2013
|
-
state.isFetchingInitialData = action.payload;
|
|
2014
|
-
},
|
|
2015
2011
|
setVisibleUserIds: (state, action) => {
|
|
2016
2012
|
state.visibleUserIds = [...new Set(action.payload)];
|
|
2017
2013
|
},
|
|
@@ -2070,7 +2066,6 @@ const {
|
|
|
2070
2066
|
resetRecentIssues,
|
|
2071
2067
|
setActiveIssueId,
|
|
2072
2068
|
setAttachments,
|
|
2073
|
-
setIsFetchingInitialData,
|
|
2074
2069
|
setIssueComments,
|
|
2075
2070
|
setIssues,
|
|
2076
2071
|
setVisibleStatuses,
|
|
@@ -2169,7 +2164,6 @@ const selectIssue = restructureCreateSelectorWithArgs(
|
|
|
2169
2164
|
return mapping[id];
|
|
2170
2165
|
})
|
|
2171
2166
|
);
|
|
2172
|
-
const selectIsFetchingInitialData = (state) => state.issueReducer.isFetchingInitialData;
|
|
2173
2167
|
const selectAllAttachments = createSelector([selectIssueAttachmentMapping], (mapping) => Object.values(mapping));
|
|
2174
2168
|
const searchIssues = restructureCreateSelectorWithArgs(
|
|
2175
2169
|
createSelector(
|
|
@@ -2261,15 +2255,15 @@ const selectRecentIssuesAsSearchResults = createSelector(
|
|
|
2261
2255
|
}
|
|
2262
2256
|
);
|
|
2263
2257
|
const issueReducer = issueSlice.reducer;
|
|
2264
|
-
const initialState$
|
|
2258
|
+
const initialState$e = {
|
|
2265
2259
|
s3Urls: {}
|
|
2266
2260
|
};
|
|
2267
2261
|
const msPerHour = 1e3 * 60 * 60;
|
|
2268
2262
|
const msPerWeek = msPerHour * 24 * 7;
|
|
2269
2263
|
const fileSlice = createSlice({
|
|
2270
2264
|
name: "file",
|
|
2271
|
-
initialState: initialState$
|
|
2272
|
-
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$
|
|
2265
|
+
initialState: initialState$e,
|
|
2266
|
+
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$e)),
|
|
2273
2267
|
reducers: {
|
|
2274
2268
|
setUploadUrl: (state, action) => {
|
|
2275
2269
|
const { url, fields, sha1 } = action.payload;
|
|
@@ -2296,7 +2290,7 @@ const selectUploadUrl = (sha1) => (state) => {
|
|
|
2296
2290
|
return url;
|
|
2297
2291
|
};
|
|
2298
2292
|
const fileReducer = fileSlice.reducer;
|
|
2299
|
-
const initialState$
|
|
2293
|
+
const initialState$d = {
|
|
2300
2294
|
// TODO: Change first MapStyle.SATELLITE to MaptStyle.None when project creation map is fixed
|
|
2301
2295
|
mapStyle: MapStyle.SATELLITE,
|
|
2302
2296
|
showTooltips: false,
|
|
@@ -2304,8 +2298,8 @@ const initialState$c = {
|
|
|
2304
2298
|
};
|
|
2305
2299
|
const mapSlice = createSlice({
|
|
2306
2300
|
name: "map",
|
|
2307
|
-
initialState: initialState$
|
|
2308
|
-
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$
|
|
2301
|
+
initialState: initialState$d,
|
|
2302
|
+
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$d)),
|
|
2309
2303
|
reducers: {
|
|
2310
2304
|
setMapStyle: (state, action) => {
|
|
2311
2305
|
state.mapStyle = action.payload;
|
|
@@ -2347,7 +2341,24 @@ var VerificationCodeType = /* @__PURE__ */ ((VerificationCodeType2) => {
|
|
|
2347
2341
|
VerificationCodeType2[VerificationCodeType2["RESET_PASSWORD"] = 10] = "RESET_PASSWORD";
|
|
2348
2342
|
return VerificationCodeType2;
|
|
2349
2343
|
})(VerificationCodeType || {});
|
|
2350
|
-
|
|
2344
|
+
var PaddleCheckoutEvent = /* @__PURE__ */ ((PaddleCheckoutEvent2) => {
|
|
2345
|
+
PaddleCheckoutEvent2["COMPLETED"] = "checkout.completed";
|
|
2346
|
+
PaddleCheckoutEvent2["CLOSED"] = "checkout.closed";
|
|
2347
|
+
return PaddleCheckoutEvent2;
|
|
2348
|
+
})(PaddleCheckoutEvent || {});
|
|
2349
|
+
var LicenseLevel = /* @__PURE__ */ ((LicenseLevel2) => {
|
|
2350
|
+
LicenseLevel2[LicenseLevel2["PRO"] = 0] = "PRO";
|
|
2351
|
+
return LicenseLevel2;
|
|
2352
|
+
})(LicenseLevel || {});
|
|
2353
|
+
var LicenseStatus = /* @__PURE__ */ ((LicenseStatus2) => {
|
|
2354
|
+
LicenseStatus2[LicenseStatus2["ACTIVE"] = 0] = "ACTIVE";
|
|
2355
|
+
LicenseStatus2[LicenseStatus2["PAUSED"] = 2] = "PAUSED";
|
|
2356
|
+
LicenseStatus2[LicenseStatus2["CANCELLED"] = 4] = "CANCELLED";
|
|
2357
|
+
LicenseStatus2[LicenseStatus2["INACTIVE"] = 6] = "INACTIVE";
|
|
2358
|
+
LicenseStatus2[LicenseStatus2["PAST_DUE"] = 8] = "PAST_DUE";
|
|
2359
|
+
return LicenseStatus2;
|
|
2360
|
+
})(LicenseStatus || {});
|
|
2361
|
+
const initialState$c = {
|
|
2351
2362
|
users: {},
|
|
2352
2363
|
currentUser: {
|
|
2353
2364
|
id: 0,
|
|
@@ -2358,8 +2369,8 @@ const initialState$b = {
|
|
|
2358
2369
|
};
|
|
2359
2370
|
const userSlice = createSlice({
|
|
2360
2371
|
name: "users",
|
|
2361
|
-
initialState: initialState$
|
|
2362
|
-
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$
|
|
2372
|
+
initialState: initialState$c,
|
|
2373
|
+
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$c)),
|
|
2363
2374
|
reducers: {
|
|
2364
2375
|
setUsers: (state, action) => {
|
|
2365
2376
|
const usersMapping = {};
|
|
@@ -2421,13 +2432,13 @@ const selectUser = (userId) => (state) => {
|
|
|
2421
2432
|
const selectUsersAsMapping = (state) => state.userReducer.users;
|
|
2422
2433
|
const selectFavouriteProjects = (state) => state.userReducer.currentUser.profile.favourite_project_ids;
|
|
2423
2434
|
const userReducer = userSlice.reducer;
|
|
2424
|
-
const initialState$
|
|
2435
|
+
const initialState$b = {
|
|
2425
2436
|
organizationAccesses: {}
|
|
2426
2437
|
};
|
|
2427
2438
|
const organizationAccessSlice = createSlice({
|
|
2428
2439
|
name: "organizationAccess",
|
|
2429
|
-
initialState: initialState$
|
|
2430
|
-
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$
|
|
2440
|
+
initialState: initialState$b,
|
|
2441
|
+
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$b)),
|
|
2431
2442
|
reducers: {
|
|
2432
2443
|
setOrganizationAccesses: (state, action) => {
|
|
2433
2444
|
if (!Array.isArray(action.payload))
|
|
@@ -2490,151 +2501,64 @@ const selectOrganizationAccessUserMapping = (state) => {
|
|
|
2490
2501
|
return organizationAccesses;
|
|
2491
2502
|
};
|
|
2492
2503
|
const organizationAccessReducer = organizationAccessSlice.reducer;
|
|
2493
|
-
const initialState$
|
|
2494
|
-
|
|
2495
|
-
activeOrganizationId: null
|
|
2504
|
+
const initialState$a = {
|
|
2505
|
+
licenses: {}
|
|
2496
2506
|
};
|
|
2497
|
-
const
|
|
2498
|
-
name: "
|
|
2499
|
-
initialState: initialState$
|
|
2500
|
-
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$
|
|
2507
|
+
const licenseSlice = createSlice({
|
|
2508
|
+
name: "license",
|
|
2509
|
+
initialState: initialState$a,
|
|
2510
|
+
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$a)),
|
|
2501
2511
|
reducers: {
|
|
2502
|
-
|
|
2503
|
-
|
|
2504
|
-
|
|
2512
|
+
setLicenses: (state, action) => {
|
|
2513
|
+
if (!Array.isArray(action.payload))
|
|
2514
|
+
throw new Error("Expected an array of Licenses");
|
|
2515
|
+
if (action.payload.filter(onlyUniqueOfflineIds).length !== action.payload.length) {
|
|
2516
|
+
throw new Error("Tried to use setLicenses reducer with duplicate ID's");
|
|
2505
2517
|
}
|
|
2506
|
-
|
|
2507
|
-
|
|
2508
|
-
|
|
2509
|
-
throw new Error("Cannot update name of active organization. Active organization ID does not exist");
|
|
2518
|
+
const licenses = {};
|
|
2519
|
+
for (const license of action.payload) {
|
|
2520
|
+
licenses[license.offline_id] = license;
|
|
2510
2521
|
}
|
|
2511
|
-
|
|
2512
|
-
|
|
2522
|
+
state.licenses = licenses;
|
|
2523
|
+
},
|
|
2524
|
+
addLicenses: (state, action) => {
|
|
2525
|
+
for (const license of action.payload) {
|
|
2526
|
+
state.licenses[license.offline_id] = license;
|
|
2513
2527
|
}
|
|
2514
|
-
state.organizations[state.activeOrganizationId] = action.payload;
|
|
2515
2528
|
},
|
|
2516
|
-
|
|
2517
|
-
|
|
2529
|
+
updateLicense: (state, action) => {
|
|
2530
|
+
if (!(action.payload.offline_id in state.licenses)) {
|
|
2531
|
+
throw new Error("Tried to update license that does not exist.");
|
|
2532
|
+
}
|
|
2533
|
+
state.licenses[action.payload.offline_id] = action.payload;
|
|
2518
2534
|
}
|
|
2519
2535
|
}
|
|
2520
2536
|
});
|
|
2521
|
-
const {
|
|
2522
|
-
const
|
|
2523
|
-
return state.
|
|
2537
|
+
const { setLicenses, addLicenses, updateLicense } = licenseSlice.actions;
|
|
2538
|
+
const selectLicenses = (state) => {
|
|
2539
|
+
return state.licenseReducer.licenses;
|
|
2524
2540
|
};
|
|
2525
|
-
const
|
|
2526
|
-
|
|
2527
|
-
|
|
2528
|
-
|
|
2529
|
-
|
|
2530
|
-
|
|
2541
|
+
const selectLicense = (licenseId) => (state) => state.licenseReducer.licenses[licenseId];
|
|
2542
|
+
const selectActiveLicense = (state) => Object.values(state.licenseReducer.licenses).find(
|
|
2543
|
+
(license) => license.project === state.projectReducer.activeProjectId
|
|
2544
|
+
) ?? null;
|
|
2545
|
+
const selectLicenseForProject = (projectId) => (state) => Object.values(state.licenseReducer.licenses).find((license) => license.project === projectId) ?? null;
|
|
2546
|
+
const selectActiveStatusLicenses = createSelector(
|
|
2547
|
+
[selectLicenses],
|
|
2548
|
+
(licenses) => Object.values(licenses).filter((license) => license.is_active)
|
|
2531
2549
|
);
|
|
2532
|
-
const
|
|
2533
|
-
|
|
2534
|
-
|
|
2535
|
-
return null;
|
|
2536
|
-
}
|
|
2537
|
-
const organization = state.organizationReducer.organizations[id];
|
|
2538
|
-
if (!organization) {
|
|
2539
|
-
return null;
|
|
2540
|
-
}
|
|
2541
|
-
return organization;
|
|
2542
|
-
};
|
|
2543
|
-
const selectOrganizationUsersIds = createSelector(
|
|
2544
|
-
[selectOrganizationAccesses],
|
|
2545
|
-
(organizationAccesses) => Object.values(organizationAccesses).map((organizationAccess) => organizationAccess.user)
|
|
2546
|
-
);
|
|
2547
|
-
const selectOrganizationUsersAsMapping = createSelector(
|
|
2548
|
-
[selectOrganizationUsersIds, selectUsersAsMapping],
|
|
2549
|
-
(organizationUserIds, users) => organizationUserIds.reduce((accum, userId) => ({ ...accum, [userId]: users[userId] }), {})
|
|
2550
|
+
const selectLicensesForProjectsMapping = createSelector(
|
|
2551
|
+
[selectLicenses],
|
|
2552
|
+
(licenses) => Object.values(licenses).filter((license) => license.project).reduce((accum, license) => ({ ...accum, [license.project]: license }), {})
|
|
2550
2553
|
);
|
|
2551
|
-
const
|
|
2552
|
-
|
|
2553
|
-
(currentUser, userMapping, organizationAccessMapping) => {
|
|
2554
|
-
return Object.values(userMapping).sort((userA, userB) => {
|
|
2555
|
-
if (userA.id === currentUser.id) {
|
|
2556
|
-
return -1;
|
|
2557
|
-
} else if (userB.id === currentUser.id) {
|
|
2558
|
-
return 1;
|
|
2559
|
-
}
|
|
2560
|
-
const organizationAccessesA = organizationAccessMapping[userA.id];
|
|
2561
|
-
const organizationAccessesB = organizationAccessMapping[userB.id];
|
|
2562
|
-
if ((organizationAccessesA == null ? void 0 : organizationAccessesA.access_level) === (organizationAccessesB == null ? void 0 : organizationAccessesB.access_level)) {
|
|
2563
|
-
return userA.username.localeCompare(userB.username);
|
|
2564
|
-
}
|
|
2565
|
-
if ((organizationAccessesA == null ? void 0 : organizationAccessesA.access_level) === OrganizationAccessLevel.ADMIN) {
|
|
2566
|
-
return -1;
|
|
2567
|
-
}
|
|
2568
|
-
return 1;
|
|
2569
|
-
});
|
|
2570
|
-
}
|
|
2571
|
-
);
|
|
2572
|
-
const selectOrganization = (id) => (state) => {
|
|
2573
|
-
return state.organizationReducer.organizations[id];
|
|
2574
|
-
};
|
|
2575
|
-
const organizationReducer = organizationSlice.reducer;
|
|
2576
|
-
const createOfflineAction = (request2, baseUrl) => {
|
|
2577
|
-
const requestWithUuid = request2.uuid ? request2 : { ...request2, uuid: v4() };
|
|
2578
|
-
return {
|
|
2579
|
-
payload: requestWithUuid,
|
|
2580
|
-
type: "",
|
|
2581
|
-
meta: {
|
|
2582
|
-
offline: {
|
|
2583
|
-
effect: {
|
|
2584
|
-
timestamp: (/* @__PURE__ */ new Date()).toISOString(),
|
|
2585
|
-
request: requestWithUuid,
|
|
2586
|
-
BASE_URL: baseUrl
|
|
2587
|
-
}
|
|
2588
|
-
}
|
|
2589
|
-
}
|
|
2590
|
-
};
|
|
2591
|
-
};
|
|
2592
|
-
const initialState$8 = {
|
|
2593
|
-
deletedRequests: [],
|
|
2594
|
-
latestRetryTime: 0
|
|
2595
|
-
};
|
|
2596
|
-
const outboxSlice = createSlice({
|
|
2597
|
-
name: "outbox",
|
|
2598
|
-
initialState: initialState$8,
|
|
2599
|
-
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$8)),
|
|
2600
|
-
reducers: {
|
|
2601
|
-
// enqueueActions is a reducer that does nothing but enqueue API request to the Redux Offline outbox
|
|
2602
|
-
// Whenever an issue is being created, a reducer addIssue() is responsible for adding it to the offline store
|
|
2603
|
-
// Then this reducer enqueueRequest() is responsible for adding the actual request data to the outbox
|
|
2604
|
-
enqueueRequest: {
|
|
2605
|
-
reducer: (state, _action) => {
|
|
2606
|
-
return state;
|
|
2607
|
-
},
|
|
2608
|
-
prepare: (payload) => {
|
|
2609
|
-
console.debug("Preparing to enqueue request", payload);
|
|
2610
|
-
const { BASE_URL, ...rest } = payload;
|
|
2611
|
-
return createOfflineAction(rest, BASE_URL);
|
|
2612
|
-
}
|
|
2613
|
-
},
|
|
2614
|
-
markForDeletion(state, action) {
|
|
2615
|
-
state.deletedRequests.push(action.payload);
|
|
2616
|
-
},
|
|
2617
|
-
markAsDeleted(state, action) {
|
|
2618
|
-
const index2 = state.deletedRequests.indexOf(action.payload);
|
|
2619
|
-
if (index2 !== -1)
|
|
2620
|
-
state.deletedRequests.splice(index2, 1);
|
|
2621
|
-
},
|
|
2622
|
-
_setLatestRetryTime: (state, action) => {
|
|
2623
|
-
state.latestRetryTime = action.payload;
|
|
2624
|
-
}
|
|
2625
|
-
}
|
|
2626
|
-
});
|
|
2627
|
-
const selectDeletedRequests = (state) => state.outboxReducer.deletedRequests;
|
|
2628
|
-
const selectLatestRetryTime = (state) => state.outboxReducer.latestRetryTime;
|
|
2629
|
-
const { enqueueRequest, markForDeletion, markAsDeleted, _setLatestRetryTime } = outboxSlice.actions;
|
|
2630
|
-
const outboxReducer = outboxSlice.reducer;
|
|
2631
|
-
const initialState$7 = {
|
|
2554
|
+
const licenseReducer = licenseSlice.reducer;
|
|
2555
|
+
const initialState$9 = {
|
|
2632
2556
|
projectAccesses: {}
|
|
2633
2557
|
};
|
|
2634
2558
|
const projectAccessSlice = createSlice({
|
|
2635
2559
|
name: "projectAccess",
|
|
2636
|
-
initialState: initialState$
|
|
2637
|
-
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$
|
|
2560
|
+
initialState: initialState$9,
|
|
2561
|
+
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$9)),
|
|
2638
2562
|
reducers: {
|
|
2639
2563
|
setProjectAccesses: (state, action) => {
|
|
2640
2564
|
if (!Array.isArray(action.payload))
|
|
@@ -2702,7 +2626,7 @@ const selectProjectAccessUserMapping = (state) => {
|
|
|
2702
2626
|
return projectAccesses;
|
|
2703
2627
|
};
|
|
2704
2628
|
const projectAccessReducer = projectAccessSlice.reducer;
|
|
2705
|
-
const initialState$
|
|
2629
|
+
const initialState$8 = {
|
|
2706
2630
|
projects: {},
|
|
2707
2631
|
activeProjectId: null,
|
|
2708
2632
|
recentProjectIds: [],
|
|
@@ -2711,7 +2635,7 @@ const initialState$6 = {
|
|
|
2711
2635
|
};
|
|
2712
2636
|
const projectSlice = createSlice({
|
|
2713
2637
|
name: "projects",
|
|
2714
|
-
initialState: initialState$
|
|
2638
|
+
initialState: initialState$8,
|
|
2715
2639
|
reducers: {
|
|
2716
2640
|
setProjects: (state, action) => {
|
|
2717
2641
|
const projectsMap = {};
|
|
@@ -2757,6 +2681,27 @@ const projectSlice = createSlice({
|
|
|
2757
2681
|
} else {
|
|
2758
2682
|
throw new Error("Accept project invite: user is not in this project");
|
|
2759
2683
|
}
|
|
2684
|
+
},
|
|
2685
|
+
addActiveProjectIssuesCount: (state, action) => {
|
|
2686
|
+
if (!state.activeProjectId || !(state.activeProjectId in state.projects)) {
|
|
2687
|
+
throw new Error("Update issues count: no active project");
|
|
2688
|
+
}
|
|
2689
|
+
if (!state.projects[state.activeProjectId].issues_count) {
|
|
2690
|
+
state.projects[state.activeProjectId].issues_count = action.payload;
|
|
2691
|
+
} else {
|
|
2692
|
+
state.projects[state.activeProjectId].issues_count += action.payload;
|
|
2693
|
+
}
|
|
2694
|
+
},
|
|
2695
|
+
addActiveProjectFormSubmissionsCount: (state, action) => {
|
|
2696
|
+
if (state.activeProjectId && state.activeProjectId in state.projects) {
|
|
2697
|
+
if (!state.projects[state.activeProjectId].form_submissions_count) {
|
|
2698
|
+
state.projects[state.activeProjectId].form_submissions_count = action.payload;
|
|
2699
|
+
} else {
|
|
2700
|
+
state.projects[state.activeProjectId].form_submissions_count += action.payload;
|
|
2701
|
+
}
|
|
2702
|
+
} else {
|
|
2703
|
+
throw new Error("Update form submissions count: no active project");
|
|
2704
|
+
}
|
|
2760
2705
|
}
|
|
2761
2706
|
}
|
|
2762
2707
|
});
|
|
@@ -2767,7 +2712,9 @@ const {
|
|
|
2767
2712
|
setActiveProjectId,
|
|
2768
2713
|
setCreateProjectType,
|
|
2769
2714
|
deleteProject,
|
|
2770
|
-
acceptProjectInvite
|
|
2715
|
+
acceptProjectInvite,
|
|
2716
|
+
addActiveProjectIssuesCount,
|
|
2717
|
+
addActiveProjectFormSubmissionsCount
|
|
2771
2718
|
} = projectSlice.actions;
|
|
2772
2719
|
const selectProjects = (state) => state.projectReducer.projects;
|
|
2773
2720
|
const selectActiveProjectId = (state) => state.projectReducer.activeProjectId;
|
|
@@ -2831,6 +2778,171 @@ const selectSortedProjectUsers = createSelector(
|
|
|
2831
2778
|
});
|
|
2832
2779
|
}
|
|
2833
2780
|
);
|
|
2781
|
+
const initialState$7 = {
|
|
2782
|
+
organizations: {},
|
|
2783
|
+
activeOrganizationId: null
|
|
2784
|
+
};
|
|
2785
|
+
const organizationSlice = createSlice({
|
|
2786
|
+
name: "organizations",
|
|
2787
|
+
initialState: initialState$7,
|
|
2788
|
+
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$7)),
|
|
2789
|
+
reducers: {
|
|
2790
|
+
setOrganizations: (state, action) => {
|
|
2791
|
+
for (const org of action.payload) {
|
|
2792
|
+
state.organizations[org.id] = org;
|
|
2793
|
+
}
|
|
2794
|
+
},
|
|
2795
|
+
updateActiveOrganization: (state, action) => {
|
|
2796
|
+
if (!state.activeOrganizationId) {
|
|
2797
|
+
throw new Error("Cannot update name of active organization. Active organization ID does not exist");
|
|
2798
|
+
}
|
|
2799
|
+
if (state.activeOrganizationId !== action.payload.id) {
|
|
2800
|
+
throw new Error("Tried updating active organization with different organization");
|
|
2801
|
+
}
|
|
2802
|
+
state.organizations[state.activeOrganizationId] = action.payload;
|
|
2803
|
+
},
|
|
2804
|
+
setActiveOrganizationId: (state, action) => {
|
|
2805
|
+
state.activeOrganizationId = action.payload;
|
|
2806
|
+
}
|
|
2807
|
+
}
|
|
2808
|
+
});
|
|
2809
|
+
const { setOrganizations, setActiveOrganizationId, updateActiveOrganization } = organizationSlice.actions;
|
|
2810
|
+
const selectActiveOrganizationId = (state) => {
|
|
2811
|
+
return state.organizationReducer.activeOrganizationId;
|
|
2812
|
+
};
|
|
2813
|
+
const selectOrganizations = (state) => {
|
|
2814
|
+
return Object.values(state.organizationReducer.organizations);
|
|
2815
|
+
};
|
|
2816
|
+
const selectOrganizationsMapping = (state) => {
|
|
2817
|
+
return state.organizationReducer.organizations;
|
|
2818
|
+
};
|
|
2819
|
+
const selectOrganizationsWithAccess = createSelector(
|
|
2820
|
+
[selectOrganizations],
|
|
2821
|
+
(organizations) => Object.values(organizations).filter((organization) => organization.has_access)
|
|
2822
|
+
);
|
|
2823
|
+
const selectActiveOrganization = (state) => {
|
|
2824
|
+
const id = selectActiveOrganizationId(state);
|
|
2825
|
+
if (!id) {
|
|
2826
|
+
return null;
|
|
2827
|
+
}
|
|
2828
|
+
const organization = state.organizationReducer.organizations[id];
|
|
2829
|
+
if (!organization) {
|
|
2830
|
+
return null;
|
|
2831
|
+
}
|
|
2832
|
+
return organization;
|
|
2833
|
+
};
|
|
2834
|
+
const selectOrganizationUsersIds = createSelector(
|
|
2835
|
+
[selectOrganizationAccesses],
|
|
2836
|
+
(organizationAccesses) => Object.values(organizationAccesses).map((organizationAccess) => organizationAccess.user)
|
|
2837
|
+
);
|
|
2838
|
+
const selectActiveOrganizationProjects = createSelector(
|
|
2839
|
+
[selectProjects, selectActiveOrganizationId],
|
|
2840
|
+
(projects, activeOrganizationId) => activeOrganizationId ? Object.values(projects).filter((project) => project.owner_organization === activeOrganizationId) : []
|
|
2841
|
+
);
|
|
2842
|
+
const selectActiveOrganizationLicenses = createSelector(
|
|
2843
|
+
[selectActiveOrganizationId, selectLicenses],
|
|
2844
|
+
(activeOrganizationId, licenses) => !activeOrganizationId ? [] : Object.values(licenses).filter((license) => license.organization_owner === activeOrganizationId)
|
|
2845
|
+
);
|
|
2846
|
+
const selectSortedOrganizationLicenses = createSelector(
|
|
2847
|
+
[selectActiveOrganizationLicenses, selectProjects],
|
|
2848
|
+
(licences, projects) => licences.sort((licenseA, licenseB) => {
|
|
2849
|
+
if (!licenseA.project) {
|
|
2850
|
+
return 1;
|
|
2851
|
+
}
|
|
2852
|
+
if (!licenseB.project) {
|
|
2853
|
+
return -1;
|
|
2854
|
+
}
|
|
2855
|
+
return projects[licenseA.project].name.toLowerCase().localeCompare(
|
|
2856
|
+
projects[licenseB.project].name.toLowerCase(),
|
|
2857
|
+
void 0,
|
|
2858
|
+
{ numeric: true }
|
|
2859
|
+
);
|
|
2860
|
+
})
|
|
2861
|
+
);
|
|
2862
|
+
const selectOrganizationUsersAsMapping = createSelector(
|
|
2863
|
+
[selectOrganizationUsersIds, selectUsersAsMapping],
|
|
2864
|
+
(organizationUserIds, users) => organizationUserIds.reduce((accum, userId) => ({ ...accum, [userId]: users[userId] }), {})
|
|
2865
|
+
);
|
|
2866
|
+
const selectSortedOrganizationUsers = createSelector(
|
|
2867
|
+
[selectCurrentUser, selectOrganizationUsersAsMapping, selectOrganizationAccessUserMapping],
|
|
2868
|
+
(currentUser, userMapping, organizationAccessMapping) => {
|
|
2869
|
+
return Object.values(userMapping).sort((userA, userB) => {
|
|
2870
|
+
if (userA.id === currentUser.id) {
|
|
2871
|
+
return -1;
|
|
2872
|
+
} else if (userB.id === currentUser.id) {
|
|
2873
|
+
return 1;
|
|
2874
|
+
}
|
|
2875
|
+
const organizationAccessesA = organizationAccessMapping[userA.id];
|
|
2876
|
+
const organizationAccessesB = organizationAccessMapping[userB.id];
|
|
2877
|
+
if ((organizationAccessesA == null ? void 0 : organizationAccessesA.access_level) === (organizationAccessesB == null ? void 0 : organizationAccessesB.access_level)) {
|
|
2878
|
+
return userA.username.localeCompare(userB.username);
|
|
2879
|
+
}
|
|
2880
|
+
if ((organizationAccessesA == null ? void 0 : organizationAccessesA.access_level) === OrganizationAccessLevel.ADMIN) {
|
|
2881
|
+
return -1;
|
|
2882
|
+
}
|
|
2883
|
+
return 1;
|
|
2884
|
+
});
|
|
2885
|
+
}
|
|
2886
|
+
);
|
|
2887
|
+
const selectOrganization = (id) => (state) => {
|
|
2888
|
+
return state.organizationReducer.organizations[id];
|
|
2889
|
+
};
|
|
2890
|
+
const organizationReducer = organizationSlice.reducer;
|
|
2891
|
+
const createOfflineAction = (request2, baseUrl) => {
|
|
2892
|
+
const requestWithUuid = request2.uuid ? request2 : { ...request2, uuid: v4() };
|
|
2893
|
+
return {
|
|
2894
|
+
payload: requestWithUuid,
|
|
2895
|
+
type: "",
|
|
2896
|
+
meta: {
|
|
2897
|
+
offline: {
|
|
2898
|
+
effect: {
|
|
2899
|
+
timestamp: (/* @__PURE__ */ new Date()).toISOString(),
|
|
2900
|
+
request: requestWithUuid,
|
|
2901
|
+
BASE_URL: baseUrl
|
|
2902
|
+
}
|
|
2903
|
+
}
|
|
2904
|
+
}
|
|
2905
|
+
};
|
|
2906
|
+
};
|
|
2907
|
+
const initialState$6 = {
|
|
2908
|
+
deletedRequests: [],
|
|
2909
|
+
latestRetryTime: 0
|
|
2910
|
+
};
|
|
2911
|
+
const outboxSlice = createSlice({
|
|
2912
|
+
name: "outbox",
|
|
2913
|
+
initialState: initialState$6,
|
|
2914
|
+
extraReducers: (builder) => builder.addCase("RESET", (state) => Object.assign(state, initialState$6)),
|
|
2915
|
+
reducers: {
|
|
2916
|
+
// enqueueActions is a reducer that does nothing but enqueue API request to the Redux Offline outbox
|
|
2917
|
+
// Whenever an issue is being created, a reducer addIssue() is responsible for adding it to the offline store
|
|
2918
|
+
// Then this reducer enqueueRequest() is responsible for adding the actual request data to the outbox
|
|
2919
|
+
enqueueRequest: {
|
|
2920
|
+
reducer: (state, _action) => {
|
|
2921
|
+
return state;
|
|
2922
|
+
},
|
|
2923
|
+
prepare: (payload) => {
|
|
2924
|
+
console.debug("Preparing to enqueue request", payload);
|
|
2925
|
+
const { BASE_URL, ...rest } = payload;
|
|
2926
|
+
return createOfflineAction(rest, BASE_URL);
|
|
2927
|
+
}
|
|
2928
|
+
},
|
|
2929
|
+
markForDeletion(state, action) {
|
|
2930
|
+
state.deletedRequests.push(action.payload);
|
|
2931
|
+
},
|
|
2932
|
+
markAsDeleted(state, action) {
|
|
2933
|
+
const index2 = state.deletedRequests.indexOf(action.payload);
|
|
2934
|
+
if (index2 !== -1)
|
|
2935
|
+
state.deletedRequests.splice(index2, 1);
|
|
2936
|
+
},
|
|
2937
|
+
_setLatestRetryTime: (state, action) => {
|
|
2938
|
+
state.latestRetryTime = action.payload;
|
|
2939
|
+
}
|
|
2940
|
+
}
|
|
2941
|
+
});
|
|
2942
|
+
const selectDeletedRequests = (state) => state.outboxReducer.deletedRequests;
|
|
2943
|
+
const selectLatestRetryTime = (state) => state.outboxReducer.latestRetryTime;
|
|
2944
|
+
const { enqueueRequest, markForDeletion, markAsDeleted, _setLatestRetryTime } = outboxSlice.actions;
|
|
2945
|
+
const outboxReducer = outboxSlice.reducer;
|
|
2834
2946
|
const initialState$5 = {
|
|
2835
2947
|
projectFiles: {},
|
|
2836
2948
|
activeProjectFileId: null,
|
|
@@ -2967,7 +3079,9 @@ const initialState$3 = {
|
|
|
2967
3079
|
Components: false,
|
|
2968
3080
|
Experimental: false
|
|
2969
3081
|
},
|
|
2970
|
-
appearance: "dark"
|
|
3082
|
+
appearance: "dark",
|
|
3083
|
+
isFetchingInitialData: false,
|
|
3084
|
+
isLoading: false
|
|
2971
3085
|
};
|
|
2972
3086
|
const settingSlice = createSlice({
|
|
2973
3087
|
name: "settings",
|
|
@@ -2991,6 +3105,12 @@ const settingSlice = createSlice({
|
|
|
2991
3105
|
},
|
|
2992
3106
|
setAppearance: (state, action) => {
|
|
2993
3107
|
state.appearance = action.payload;
|
|
3108
|
+
},
|
|
3109
|
+
setIsFetchingInitialData: (state, action) => {
|
|
3110
|
+
state.isFetchingInitialData = action.payload;
|
|
3111
|
+
},
|
|
3112
|
+
setIsLoading: (state, action) => {
|
|
3113
|
+
state.isLoading = action.payload;
|
|
2994
3114
|
}
|
|
2995
3115
|
}
|
|
2996
3116
|
});
|
|
@@ -2999,7 +3119,9 @@ const {
|
|
|
2999
3119
|
setEnablePlacementMode,
|
|
3000
3120
|
setSectionExpanded,
|
|
3001
3121
|
setEnableClustering,
|
|
3002
|
-
setAppearance
|
|
3122
|
+
setAppearance,
|
|
3123
|
+
setIsFetchingInitialData,
|
|
3124
|
+
setIsLoading
|
|
3003
3125
|
} = settingSlice.actions;
|
|
3004
3126
|
const selectEnablePlacementMode = (state) => state.settingReducer.placementMode;
|
|
3005
3127
|
const selectEnableDuplicateIssues = (state) => state.settingReducer.useIssueTemplate;
|
|
@@ -3008,6 +3130,8 @@ const selectExpandedSections = (state) => state.settingReducer.expandedSections;
|
|
|
3008
3130
|
const selectEnableClustering = (state) => state.settingReducer.enableClustering;
|
|
3009
3131
|
const selectAppearance = (state) => state.settingReducer.appearance;
|
|
3010
3132
|
const settingReducer = settingSlice.reducer;
|
|
3133
|
+
const selectIsFetchingInitialData = (state) => state.settingReducer.isFetchingInitialData;
|
|
3134
|
+
const selectIsLoading = (state) => state.settingReducer.isLoading;
|
|
3011
3135
|
const LATEST_REVISION_CACHE = {};
|
|
3012
3136
|
function considerCachingRevision(revision, formId2, preferPending = false) {
|
|
3013
3137
|
var _a2;
|
|
@@ -3426,7 +3550,8 @@ const overmapReducers = {
|
|
|
3426
3550
|
userFormReducer,
|
|
3427
3551
|
userReducer,
|
|
3428
3552
|
workspaceReducer,
|
|
3429
|
-
emailDomainsReducer
|
|
3553
|
+
emailDomainsReducer,
|
|
3554
|
+
licenseReducer
|
|
3430
3555
|
};
|
|
3431
3556
|
const overmapReducer = combineReducers(overmapReducers);
|
|
3432
3557
|
const resetStore = "RESET";
|
|
@@ -4913,6 +5038,7 @@ class IssueService extends BaseApiService {
|
|
|
4913
5038
|
});
|
|
4914
5039
|
store.dispatch(addIssue(issuePayload));
|
|
4915
5040
|
store.dispatch(addToRecentIssues(issuePayload.offline_id));
|
|
5041
|
+
store.dispatch(addActiveProjectIssuesCount(1));
|
|
4916
5042
|
const promise = this.enqueueRequest({
|
|
4917
5043
|
description: "Create issue",
|
|
4918
5044
|
method: HttpMethod.POST,
|
|
@@ -4922,6 +5048,7 @@ class IssueService extends BaseApiService {
|
|
|
4922
5048
|
},
|
|
4923
5049
|
payload: issuePayload,
|
|
4924
5050
|
blockers: [
|
|
5051
|
+
"add-issue",
|
|
4925
5052
|
...issuePayload.index_workspace ? [issuePayload.index_workspace] : [],
|
|
4926
5053
|
...issuePayload.visible_in_workspaces
|
|
4927
5054
|
],
|
|
@@ -4939,6 +5066,7 @@ class IssueService extends BaseApiService {
|
|
|
4939
5066
|
});
|
|
4940
5067
|
}
|
|
4941
5068
|
store.dispatch(removeIssue(issuePayload.offline_id));
|
|
5069
|
+
store.dispatch(addActiveProjectIssuesCount(-1));
|
|
4942
5070
|
throw error2;
|
|
4943
5071
|
});
|
|
4944
5072
|
return [issuePayload, promise];
|
|
@@ -4977,16 +5105,18 @@ class IssueService extends BaseApiService {
|
|
|
4977
5105
|
return [fullIssue, promise];
|
|
4978
5106
|
}
|
|
4979
5107
|
async remove(id) {
|
|
4980
|
-
const
|
|
5108
|
+
const { store } = this.client;
|
|
5109
|
+
const state = store.getState();
|
|
4981
5110
|
const backup = state.issueReducer.issues[id];
|
|
4982
5111
|
if (!backup) {
|
|
4983
5112
|
throw new Error(`No issue with id ${id} found in the store`);
|
|
4984
5113
|
}
|
|
4985
5114
|
const attachments = Object.values(state.issueReducer.attachments).filter((a) => a.issue_id === id);
|
|
4986
5115
|
const attachmentsOfIssue = selectPhotoAttachmentsOfIssue(id)(state);
|
|
4987
|
-
|
|
5116
|
+
store.dispatch(removeIssue(id));
|
|
5117
|
+
store.dispatch(addActiveProjectIssuesCount(-1));
|
|
4988
5118
|
if (attachmentsOfIssue) {
|
|
4989
|
-
|
|
5119
|
+
store.dispatch(removeAttachmentsOfIssue(id));
|
|
4990
5120
|
}
|
|
4991
5121
|
try {
|
|
4992
5122
|
return await this.enqueueRequest({
|
|
@@ -4997,8 +5127,9 @@ class IssueService extends BaseApiService {
|
|
|
4997
5127
|
blocks: []
|
|
4998
5128
|
});
|
|
4999
5129
|
} catch (e) {
|
|
5000
|
-
|
|
5001
|
-
|
|
5130
|
+
store.dispatch(addIssue(backup));
|
|
5131
|
+
store.dispatch(addAttachments(attachments));
|
|
5132
|
+
store.dispatch(addActiveProjectIssuesCount(1));
|
|
5002
5133
|
throw e;
|
|
5003
5134
|
}
|
|
5004
5135
|
}
|
|
@@ -5074,7 +5205,9 @@ class MainService extends BaseApiService {
|
|
|
5074
5205
|
owner_organization: projectData.organization_owner,
|
|
5075
5206
|
owner_user: projectData.user_owner,
|
|
5076
5207
|
bounds: projectData.bounds,
|
|
5077
|
-
invited: projectData.invited || false
|
|
5208
|
+
invited: projectData.invited || false,
|
|
5209
|
+
issues_count: projectData.issues_count,
|
|
5210
|
+
form_submissions_count: projectData.form_submissions_count
|
|
5078
5211
|
});
|
|
5079
5212
|
if (currentProjectId === projectData.id && !projectData.invited) {
|
|
5080
5213
|
isProjectIdValid = true;
|
|
@@ -5092,6 +5225,7 @@ class MainService extends BaseApiService {
|
|
|
5092
5225
|
}
|
|
5093
5226
|
store.dispatch(setCurrentUser(data.user));
|
|
5094
5227
|
store.dispatch(addUsers(data.project_owners));
|
|
5228
|
+
store.dispatch(setLicenses(data.licenses));
|
|
5095
5229
|
const organizationsData = data.organizations;
|
|
5096
5230
|
store.dispatch(setOrganizations(organizationsData));
|
|
5097
5231
|
const validProjects = projects.filter((project) => !project.invited);
|
|
@@ -5205,7 +5339,7 @@ class ProjectAccessService extends BaseApiService {
|
|
|
5205
5339
|
method: HttpMethod.PATCH,
|
|
5206
5340
|
url: `/access/${projectAccess.offline_id}/`,
|
|
5207
5341
|
payload: projectAccess,
|
|
5208
|
-
blockers: [projectAccess.offline_id],
|
|
5342
|
+
blockers: [projectAccess.offline_id, "change-access-level"],
|
|
5209
5343
|
blocks: [projectAccess.offline_id]
|
|
5210
5344
|
});
|
|
5211
5345
|
}
|
|
@@ -5404,6 +5538,7 @@ class ProjectService extends BaseApiService {
|
|
|
5404
5538
|
if (!project) {
|
|
5405
5539
|
throw new Error("Expected project to exist");
|
|
5406
5540
|
}
|
|
5541
|
+
const license = selectLicenseForProject(project.id);
|
|
5407
5542
|
const activeProjectId = state.projectReducer.activeProjectId;
|
|
5408
5543
|
if (activeProjectId === projectId) {
|
|
5409
5544
|
store.dispatch({ type: "project/setActiveProjectId", payload: null });
|
|
@@ -5414,6 +5549,9 @@ class ProjectService extends BaseApiService {
|
|
|
5414
5549
|
store.dispatch(removeProjectAccessesOfProject(project.id));
|
|
5415
5550
|
store.dispatch({ type: "rehydrated/setRehydrated", payload: false });
|
|
5416
5551
|
store.dispatch(deleteProject(project));
|
|
5552
|
+
if (license) {
|
|
5553
|
+
store.dispatch(updateLicense({ ...license, project: null }));
|
|
5554
|
+
}
|
|
5417
5555
|
try {
|
|
5418
5556
|
await this.enqueueRequest({
|
|
5419
5557
|
description: "Delete project",
|
|
@@ -5429,6 +5567,9 @@ class ProjectService extends BaseApiService {
|
|
|
5429
5567
|
store.dispatch(addOrReplaceProjectFiles(filesToDelete));
|
|
5430
5568
|
store.dispatch(setActiveProjectId(activeProjectId));
|
|
5431
5569
|
store.dispatch({ type: "rehydrated/setRehydrated", payload: true });
|
|
5570
|
+
if (license) {
|
|
5571
|
+
store.dispatch(updateLicense({ ...license, project: project.id }));
|
|
5572
|
+
}
|
|
5432
5573
|
throw e;
|
|
5433
5574
|
}
|
|
5434
5575
|
}
|
|
@@ -5803,7 +5944,7 @@ class UserFormSubmissionService extends BaseApiService {
|
|
|
5803
5944
|
method: HttpMethod.POST,
|
|
5804
5945
|
url: `/forms/revisions/${payload.form_revision}/respond/`,
|
|
5805
5946
|
payload: { ...payloadWithoutFiles, project: activeProjectId },
|
|
5806
|
-
blockers: [payload.issue, payload.component, payload.component_stage].filter(
|
|
5947
|
+
blockers: [payload.issue, payload.component, payload.component_stage, "add-form-entry"].filter(
|
|
5807
5948
|
(x) => x !== void 0
|
|
5808
5949
|
),
|
|
5809
5950
|
blocks: [payload.offline_id]
|
|
@@ -5822,10 +5963,12 @@ class UserFormSubmissionService extends BaseApiService {
|
|
|
5822
5963
|
};
|
|
5823
5964
|
store.dispatch(updateOrCreateUserFormSubmission(offlineResultWithoutFiles));
|
|
5824
5965
|
void promise.then((result) => {
|
|
5966
|
+
store.dispatch(addActiveProjectFormSubmissionsCount(1));
|
|
5825
5967
|
store.dispatch(updateOrCreateUserFormSubmission(result));
|
|
5826
5968
|
return result;
|
|
5827
5969
|
}).catch(() => {
|
|
5828
5970
|
store.dispatch(deleteUserFormSubmission(payload.offline_id));
|
|
5971
|
+
store.dispatch(addActiveProjectFormSubmissionsCount(-1));
|
|
5829
5972
|
});
|
|
5830
5973
|
const settledPromise = Promise.all([promise, ...attachFilesPromises]).then(() => promise);
|
|
5831
5974
|
return [fullOfflineResult, settledPromise];
|
|
@@ -5859,6 +6002,7 @@ class UserFormSubmissionService extends BaseApiService {
|
|
|
5859
6002
|
const state = store.getState();
|
|
5860
6003
|
const submission = state.userFormReducer.submissions[submissionId];
|
|
5861
6004
|
store.dispatch(deleteUserFormSubmission(submissionId));
|
|
6005
|
+
store.dispatch(addActiveProjectFormSubmissionsCount(-1));
|
|
5862
6006
|
try {
|
|
5863
6007
|
return await this.enqueueRequest({
|
|
5864
6008
|
description: "Delete user form submissions",
|
|
@@ -5869,6 +6013,7 @@ class UserFormSubmissionService extends BaseApiService {
|
|
|
5869
6013
|
});
|
|
5870
6014
|
} catch (e) {
|
|
5871
6015
|
if (submission) {
|
|
6016
|
+
store.dispatch(addActiveProjectFormSubmissionsCount(1));
|
|
5872
6017
|
store.dispatch(updateOrCreateUserFormSubmission(submission));
|
|
5873
6018
|
}
|
|
5874
6019
|
throw e;
|
|
@@ -5905,7 +6050,7 @@ class WorkspaceService extends BaseApiService {
|
|
|
5905
6050
|
method: HttpMethod.POST,
|
|
5906
6051
|
url: `/projects/${store.getState().projectReducer.activeProjectId}/workspaces/`,
|
|
5907
6052
|
payload: offlineWorkspace,
|
|
5908
|
-
blockers: [],
|
|
6053
|
+
blockers: ["add-workspace"],
|
|
5909
6054
|
blocks: [offlineWorkspace.offline_id]
|
|
5910
6055
|
});
|
|
5911
6056
|
void promise.then((result) => {
|
|
@@ -6282,10 +6427,12 @@ class OrganizationService extends BaseApiService {
|
|
|
6282
6427
|
const organizationAccesses = data.organization_accesses;
|
|
6283
6428
|
const emailDomains = data.email_domains;
|
|
6284
6429
|
const users = data.users;
|
|
6430
|
+
const licenses = data.licenses;
|
|
6285
6431
|
store.dispatch(addUsers(users));
|
|
6286
6432
|
store.dispatch(setActiveOrganizationId(activeOrganization.id));
|
|
6287
6433
|
store.dispatch(setOrganizationAccesses(organizationAccesses));
|
|
6288
6434
|
store.dispatch(setEmailDomains(emailDomains));
|
|
6435
|
+
store.dispatch(addLicenses(licenses));
|
|
6289
6436
|
if (showLoading) {
|
|
6290
6437
|
store.dispatch(setIsFetchingInitialData(false));
|
|
6291
6438
|
}
|
|
@@ -6326,6 +6473,128 @@ class OrganizationService extends BaseApiService {
|
|
|
6326
6473
|
});
|
|
6327
6474
|
}
|
|
6328
6475
|
}
|
|
6476
|
+
class LicenseService extends BaseApiService {
|
|
6477
|
+
async getLicensesForOrganization(organizationId, showLoading = false) {
|
|
6478
|
+
if (showLoading) {
|
|
6479
|
+
this.client.store.dispatch(setIsFetchingInitialData(true));
|
|
6480
|
+
}
|
|
6481
|
+
return this.enqueueRequest({
|
|
6482
|
+
description: "Get licenses",
|
|
6483
|
+
method: HttpMethod.GET,
|
|
6484
|
+
url: `/organizations/${organizationId}/licenses/`,
|
|
6485
|
+
isAuthNeeded: true,
|
|
6486
|
+
blockers: [organizationId.toString()],
|
|
6487
|
+
blocks: ["add-issue", "add-form-entry", "change-access-level", "add-workspace"]
|
|
6488
|
+
}).then((result) => {
|
|
6489
|
+
if (showLoading) {
|
|
6490
|
+
this.client.store.dispatch(setIsFetchingInitialData(false));
|
|
6491
|
+
}
|
|
6492
|
+
return result;
|
|
6493
|
+
});
|
|
6494
|
+
}
|
|
6495
|
+
async getLicense(license) {
|
|
6496
|
+
return this.enqueueRequest({
|
|
6497
|
+
description: "Get license",
|
|
6498
|
+
method: HttpMethod.GET,
|
|
6499
|
+
url: `/billing/${license.offline_id}/`,
|
|
6500
|
+
isAuthNeeded: true,
|
|
6501
|
+
blockers: [
|
|
6502
|
+
license.organization_owner ? license.organization_owner.toString() : license.user_owner ? license.user_owner.toString() : ""
|
|
6503
|
+
],
|
|
6504
|
+
blocks: []
|
|
6505
|
+
}).then((result) => {
|
|
6506
|
+
this.client.store.dispatch(updateLicense(result));
|
|
6507
|
+
return result;
|
|
6508
|
+
});
|
|
6509
|
+
}
|
|
6510
|
+
async pauseLicense(license) {
|
|
6511
|
+
return this.enqueueRequest({
|
|
6512
|
+
description: "Pause license",
|
|
6513
|
+
method: HttpMethod.DELETE,
|
|
6514
|
+
url: `/billing/${license.offline_id}/suspend/`,
|
|
6515
|
+
isAuthNeeded: true,
|
|
6516
|
+
blockers: [
|
|
6517
|
+
license.organization_owner ? license.organization_owner.toString() : license.user_owner ? license.user_owner.toString() : ""
|
|
6518
|
+
],
|
|
6519
|
+
blocks: []
|
|
6520
|
+
}).then((result) => {
|
|
6521
|
+
this.client.store.dispatch(updateLicense(result));
|
|
6522
|
+
return result;
|
|
6523
|
+
});
|
|
6524
|
+
}
|
|
6525
|
+
async resumeLicense(license) {
|
|
6526
|
+
return this.enqueueRequest({
|
|
6527
|
+
description: "Resume license",
|
|
6528
|
+
method: HttpMethod.PATCH,
|
|
6529
|
+
url: `/billing/${license.offline_id}/suspend/`,
|
|
6530
|
+
isAuthNeeded: true,
|
|
6531
|
+
blockers: [
|
|
6532
|
+
license.organization_owner ? license.organization_owner.toString() : license.user_owner ? license.user_owner.toString() : ""
|
|
6533
|
+
],
|
|
6534
|
+
blocks: []
|
|
6535
|
+
}).then((result) => {
|
|
6536
|
+
this.client.store.dispatch(updateLicense(result));
|
|
6537
|
+
return result;
|
|
6538
|
+
});
|
|
6539
|
+
}
|
|
6540
|
+
async cancelLicense(license) {
|
|
6541
|
+
return this.enqueueRequest({
|
|
6542
|
+
description: "Cancel license",
|
|
6543
|
+
method: HttpMethod.DELETE,
|
|
6544
|
+
url: `/billing/${license.offline_id}/`,
|
|
6545
|
+
isAuthNeeded: true,
|
|
6546
|
+
blockers: [
|
|
6547
|
+
license.organization_owner ? license.organization_owner.toString() : license.user_owner ? license.user_owner.toString() : ""
|
|
6548
|
+
],
|
|
6549
|
+
blocks: []
|
|
6550
|
+
}).then((result) => {
|
|
6551
|
+
this.client.store.dispatch(updateLicense(result));
|
|
6552
|
+
return result;
|
|
6553
|
+
});
|
|
6554
|
+
}
|
|
6555
|
+
async attachLicenseToProject(license, project) {
|
|
6556
|
+
return this.enqueueRequest({
|
|
6557
|
+
description: "Attach license",
|
|
6558
|
+
method: HttpMethod.PATCH,
|
|
6559
|
+
url: `/billing/${license.offline_id}/project/`,
|
|
6560
|
+
isAuthNeeded: true,
|
|
6561
|
+
payload: { project: project.id },
|
|
6562
|
+
blockers: [
|
|
6563
|
+
license.organization_owner ? license.organization_owner.toString() : license.user_owner ? license.user_owner.toString() : "",
|
|
6564
|
+
project.id ? project.id.toString() : ""
|
|
6565
|
+
],
|
|
6566
|
+
blocks: ["add-issue", "add-form-entry", "change-access-level", "add-workspace"]
|
|
6567
|
+
}).then((result) => {
|
|
6568
|
+
this.client.store.dispatch(updateLicense(result));
|
|
6569
|
+
return result;
|
|
6570
|
+
});
|
|
6571
|
+
}
|
|
6572
|
+
async detachLicenseFromProject(license) {
|
|
6573
|
+
return this.enqueueRequest({
|
|
6574
|
+
description: "Detach license",
|
|
6575
|
+
method: HttpMethod.DELETE,
|
|
6576
|
+
url: `/billing/${license.offline_id}/project/`,
|
|
6577
|
+
isAuthNeeded: true,
|
|
6578
|
+
blockers: [
|
|
6579
|
+
license.organization_owner ? license.organization_owner.toString() : license.user_owner ? license.user_owner.toString() : ""
|
|
6580
|
+
],
|
|
6581
|
+
blocks: ["add-issue", "add-form-entry", "change-access-level", "add-workspace"]
|
|
6582
|
+
}).then((result) => {
|
|
6583
|
+
this.client.store.dispatch(updateLicense(result));
|
|
6584
|
+
return result;
|
|
6585
|
+
});
|
|
6586
|
+
}
|
|
6587
|
+
async getLatestTransaction(license) {
|
|
6588
|
+
return this.enqueueRequest({
|
|
6589
|
+
description: "Get latest transaction",
|
|
6590
|
+
method: HttpMethod.GET,
|
|
6591
|
+
url: `/billing/${license.offline_id}/transaction/`,
|
|
6592
|
+
isAuthNeeded: true,
|
|
6593
|
+
blockers: [license.offline_id],
|
|
6594
|
+
blocks: [license.offline_id]
|
|
6595
|
+
});
|
|
6596
|
+
}
|
|
6597
|
+
}
|
|
6329
6598
|
class OvermapSDK {
|
|
6330
6599
|
constructor(apiUrl, store) {
|
|
6331
6600
|
__publicField(this, "API_URL");
|
|
@@ -6351,6 +6620,7 @@ class OvermapSDK {
|
|
|
6351
6620
|
__publicField(this, "projectFiles", new ProjectFileService(this));
|
|
6352
6621
|
__publicField(this, "emailVerification", new EmailVerificationService(this));
|
|
6353
6622
|
__publicField(this, "emailDomains", new EmailDomainsService(this));
|
|
6623
|
+
__publicField(this, "licenses", new LicenseService(this));
|
|
6354
6624
|
this.API_URL = apiUrl;
|
|
6355
6625
|
this.store = store;
|
|
6356
6626
|
}
|
|
@@ -14364,6 +14634,9 @@ export {
|
|
|
14364
14634
|
IssuePriority,
|
|
14365
14635
|
IssueService,
|
|
14366
14636
|
IssueStatus,
|
|
14637
|
+
LicenseLevel,
|
|
14638
|
+
LicenseService,
|
|
14639
|
+
LicenseStatus,
|
|
14367
14640
|
MainService,
|
|
14368
14641
|
MapStyle,
|
|
14369
14642
|
MultiSelectField,
|
|
@@ -14381,6 +14654,7 @@ export {
|
|
|
14381
14654
|
OvermapProvider,
|
|
14382
14655
|
OvermapSDK,
|
|
14383
14656
|
PDFViewer,
|
|
14657
|
+
PaddleCheckoutEvent,
|
|
14384
14658
|
PatchField,
|
|
14385
14659
|
PatchFormProvider,
|
|
14386
14660
|
ProjectAccessLevel,
|
|
@@ -14407,6 +14681,8 @@ export {
|
|
|
14407
14681
|
YELLOW,
|
|
14408
14682
|
_setLatestRetryTime,
|
|
14409
14683
|
acceptProjectInvite,
|
|
14684
|
+
addActiveProjectFormSubmissionsCount,
|
|
14685
|
+
addActiveProjectIssuesCount,
|
|
14410
14686
|
addAttachment,
|
|
14411
14687
|
addAttachments,
|
|
14412
14688
|
addCategory,
|
|
@@ -14416,6 +14692,7 @@ export {
|
|
|
14416
14692
|
addEmailDomain,
|
|
14417
14693
|
addFavouriteProjectId,
|
|
14418
14694
|
addIssue,
|
|
14695
|
+
addLicenses,
|
|
14419
14696
|
addOrReplaceCategories,
|
|
14420
14697
|
addOrReplaceIssueComment,
|
|
14421
14698
|
addOrReplaceProjectFile,
|
|
@@ -14515,6 +14792,8 @@ export {
|
|
|
14515
14792
|
issueReducer,
|
|
14516
14793
|
issueSlice,
|
|
14517
14794
|
issueToSearchResult,
|
|
14795
|
+
licenseReducer,
|
|
14796
|
+
licenseSlice,
|
|
14518
14797
|
linkStageToForm,
|
|
14519
14798
|
literalToCoordinates,
|
|
14520
14799
|
logOnlyOnce,
|
|
@@ -14582,13 +14861,17 @@ export {
|
|
|
14582
14861
|
searchIssues,
|
|
14583
14862
|
selectAccessToken,
|
|
14584
14863
|
selectActiveIssueId,
|
|
14864
|
+
selectActiveLicense,
|
|
14585
14865
|
selectActiveOrganization,
|
|
14586
14866
|
selectActiveOrganizationAccess,
|
|
14587
14867
|
selectActiveOrganizationId,
|
|
14868
|
+
selectActiveOrganizationLicenses,
|
|
14869
|
+
selectActiveOrganizationProjects,
|
|
14588
14870
|
selectActiveProject,
|
|
14589
14871
|
selectActiveProjectAccess,
|
|
14590
14872
|
selectActiveProjectFileId,
|
|
14591
14873
|
selectActiveProjectId,
|
|
14874
|
+
selectActiveStatusLicenses,
|
|
14592
14875
|
selectActiveWorkspace,
|
|
14593
14876
|
selectActiveWorkspaceId,
|
|
14594
14877
|
selectAllAttachments,
|
|
@@ -14634,6 +14917,7 @@ export {
|
|
|
14634
14917
|
selectHiddenComponentTypeIds,
|
|
14635
14918
|
selectIsFetchingInitialData,
|
|
14636
14919
|
selectIsImportingProjectFile,
|
|
14920
|
+
selectIsLoading,
|
|
14637
14921
|
selectIsLoggedIn,
|
|
14638
14922
|
selectIssue,
|
|
14639
14923
|
selectIssueAttachmentMapping,
|
|
@@ -14644,6 +14928,10 @@ export {
|
|
|
14644
14928
|
selectLatestRetryTime,
|
|
14645
14929
|
selectLatestRevisionByFormId,
|
|
14646
14930
|
selectLatestRevisionsFromComponentTypeIds,
|
|
14931
|
+
selectLicense,
|
|
14932
|
+
selectLicenseForProject,
|
|
14933
|
+
selectLicenses,
|
|
14934
|
+
selectLicensesForProjectsMapping,
|
|
14647
14935
|
selectMainWorkspace,
|
|
14648
14936
|
selectMapStyle,
|
|
14649
14937
|
selectNumberOfComponentTypesMatchingCaseInsensitiveName,
|
|
@@ -14658,6 +14946,7 @@ export {
|
|
|
14658
14946
|
selectOrganizationUsersAsMapping,
|
|
14659
14947
|
selectOrganizationUsersIds,
|
|
14660
14948
|
selectOrganizations,
|
|
14949
|
+
selectOrganizationsMapping,
|
|
14661
14950
|
selectOrganizationsWithAccess,
|
|
14662
14951
|
selectPermittedWorkspaceIds,
|
|
14663
14952
|
selectPhotoAttachmentsOfIssue,
|
|
@@ -14679,6 +14968,7 @@ export {
|
|
|
14679
14968
|
selectRevisionsForForm,
|
|
14680
14969
|
selectShowTooltips,
|
|
14681
14970
|
selectSortedEmailDomains,
|
|
14971
|
+
selectSortedOrganizationLicenses,
|
|
14682
14972
|
selectSortedOrganizationUsers,
|
|
14683
14973
|
selectSortedProjectUsers,
|
|
14684
14974
|
selectSortedProjects,
|
|
@@ -14722,8 +15012,10 @@ export {
|
|
|
14722
15012
|
setEnablePlacementMode,
|
|
14723
15013
|
setIsFetchingInitialData,
|
|
14724
15014
|
setIsImportingProjectFile,
|
|
15015
|
+
setIsLoading,
|
|
14725
15016
|
setIssueComments,
|
|
14726
15017
|
setIssues,
|
|
15018
|
+
setLicenses,
|
|
14727
15019
|
setLoggedIn,
|
|
14728
15020
|
setMapStyle,
|
|
14729
15021
|
setOrganizationAccesses,
|
|
@@ -14763,6 +15055,7 @@ export {
|
|
|
14763
15055
|
updateAttachment,
|
|
14764
15056
|
updateComponent,
|
|
14765
15057
|
updateIssue,
|
|
15058
|
+
updateLicense,
|
|
14766
15059
|
updateOrCreateProject,
|
|
14767
15060
|
updateOrCreateUserFormSubmission,
|
|
14768
15061
|
updateOrganizationAccess,
|