Page Menu
Home
Phabricator
Search
Configure Global Search
Log In
Files
F3332852
No One
Temporary
Actions
View File
Edit File
Delete File
View Transforms
Subscribe
Mute Notifications
Award Token
Flag For Later
Size
7 KB
Referenced Files
None
Subscribers
None
View Options
diff --git a/keyserver/src/deleters/account-deleters.js b/keyserver/src/deleters/account-deleters.js
index d6c8a8c72..6a869dd3f 100644
--- a/keyserver/src/deleters/account-deleters.js
+++ b/keyserver/src/deleters/account-deleters.js
@@ -1,152 +1,152 @@
// @flow
import { getRustAPI } from 'rust-node-addon';
import type { LogOutResponse } from 'lib/types/account-types.js';
import type { ReservedUsernameMessage } from 'lib/types/crypto-types.js';
import { updateTypes } from 'lib/types/update-types-enum.js';
import type { UserInfo } from 'lib/types/user-types.js';
import { ServerError } from 'lib/utils/errors.js';
import { values } from 'lib/utils/objects.js';
import { promiseAll, ignorePromiseRejections } from 'lib/utils/promises.js';
import { createUpdates } from '../creators/update-creator.js';
import { dbQuery, SQL } from '../database/database.js';
import {
fetchKnownUserInfos,
fetchUsername,
} from '../fetchers/user-fetchers.js';
import { rescindPushNotifs } from '../push/rescind.js';
import { createNewAnonymousCookie } from '../session/cookies.js';
import type { Viewer, AnonymousViewerData } from '../session/viewer.js';
import { fetchOlmAccount } from '../updaters/olm-account-updater.js';
async function deleteAccount(viewer: Viewer): Promise<?LogOutResponse> {
if (!viewer.loggedIn) {
throw new ServerError('not_logged_in');
}
const deletedUserID = viewer.userID;
await rescindPushNotifs(SQL`n.user = ${deletedUserID}`, SQL`NULL`);
const knownUserInfos = await fetchKnownUserInfos(viewer);
const usersToUpdate: $ReadOnlyArray<UserInfo> = values(knownUserInfos).filter(
(user: UserInfo): boolean => user.id !== deletedUserID,
);
// TODO: if this results in any orphaned orgs, convert them to chats
const deletionQuery = SQL`
START TRANSACTION;
DELETE FROM users WHERE id = ${deletedUserID};
DELETE FROM ids WHERE id = ${deletedUserID};
DELETE c, i
FROM cookies c
LEFT JOIN ids i ON i.id = c.id
WHERE c.user = ${deletedUserID};
DELETE FROM memberships WHERE user = ${deletedUserID};
DELETE FROM focused WHERE user = ${deletedUserID};
DELETE n, i
FROM notifications n
LEFT JOIN ids i ON i.id = n.id
WHERE n.user = ${deletedUserID};
DELETE u, i
FROM updates u
LEFT JOIN ids i ON i.id = u.id
WHERE u.user = ${deletedUserID};
DELETE s, i
FROM sessions s
LEFT JOIN ids i ON i.id = s.id
WHERE s.user = ${deletedUserID};
DELETE r, i
FROM reports r
LEFT JOIN ids i ON i.id = r.id
WHERE r.user = ${deletedUserID};
DELETE u, i
FROM uploads u
LEFT JOIN ids i on i.id = u.id
- WHERE u.container = ${deletedUserID};
+ WHERE u.user_container = ${deletedUserID};
DELETE FROM relationships_undirected WHERE user1 = ${deletedUserID};
DELETE FROM relationships_undirected WHERE user2 = ${deletedUserID};
DELETE FROM relationships_directed WHERE user1 = ${deletedUserID};
DELETE FROM relationships_directed WHERE user2 = ${deletedUserID};
COMMIT;
`;
const deletionPromise = dbQuery(deletionQuery, { multipleStatements: true });
const anonymousViewerDataPromise: Promise<?AnonymousViewerData> =
(async () => {
if (viewer.isScriptViewer) {
return undefined;
}
return await createNewAnonymousCookie({
platformDetails: viewer.platformDetails,
deviceToken: viewer.deviceToken,
});
})();
const usernamePromise = fetchUsername(deletedUserID);
const { anonymousViewerData, username } = await promiseAll({
anonymousViewerData: anonymousViewerDataPromise,
username: usernamePromise,
deletion: deletionPromise,
});
if (username) {
const issuedAt = new Date().toISOString();
const reservedUsernameMessage: ReservedUsernameMessage = {
statement: 'Remove the following username from reserved list',
payload: username,
issuedAt,
};
const message = JSON.stringify(reservedUsernameMessage);
ignorePromiseRejections(
(async () => {
const rustAPI = await getRustAPI();
const accountInfo = await fetchOlmAccount('content');
const signature = accountInfo.account.sign(message);
await rustAPI.removeReservedUsername(message, signature);
})(),
);
}
if (anonymousViewerData) {
viewer.setNewCookie(anonymousViewerData);
}
const deletionUpdatesPromise = createAccountDeletionUpdates(
usersToUpdate,
deletedUserID,
);
if (viewer.isScriptViewer) {
await deletionUpdatesPromise;
} else {
ignorePromiseRejections(deletionUpdatesPromise);
}
if (viewer.isScriptViewer) {
return null;
}
return {
currentUserInfo: {
anonymous: true,
},
};
}
async function createAccountDeletionUpdates(
knownUserInfos: $ReadOnlyArray<UserInfo>,
deletedUserID: string,
): Promise<void> {
const time = Date.now();
const updateDatas = [];
for (const userInfo of knownUserInfos) {
const { id: userID } = userInfo;
updateDatas.push({
type: updateTypes.DELETE_ACCOUNT,
userID,
time,
deletedUserID,
});
}
await createUpdates(updateDatas);
}
export { deleteAccount };
diff --git a/keyserver/src/deleters/upload-deleters.js b/keyserver/src/deleters/upload-deleters.js
index 0625cb1a4..4f44ed1d2 100644
--- a/keyserver/src/deleters/upload-deleters.js
+++ b/keyserver/src/deleters/upload-deleters.js
@@ -1,51 +1,56 @@
// @flow
import { ServerError } from 'lib/utils/errors.js';
import { dbQuery, SQL } from '../database/database.js';
import type { Viewer } from '../session/viewer.js';
async function deleteUpload(viewer: Viewer, id: string): Promise<void> {
if (!viewer.loggedIn) {
throw new ServerError('not_logged_in');
}
const fetchQuery = SQL`
- SELECT uploader, container
+ SELECT uploader, container, user_container AS userContainer
FROM uploads
WHERE id = ${id}
`;
const [result] = await dbQuery(fetchQuery);
if (result.length === 0) {
throw new ServerError('invalid_parameters');
}
const [row] = result;
- const { uploader, container } = row;
+ const { uploader, container, userContainer } = row;
- if (uploader.toString() !== viewer.userID || container !== null) {
+ if (
+ uploader.toString() !== viewer.userID ||
+ container !== null ||
+ userContainer !== null
+ ) {
throw new ServerError('invalid_parameters');
}
const deleteQuery = SQL`
DELETE u, i
FROM uploads u
LEFT JOIN ids i ON i.id = u.id
WHERE u.id = ${id}
`;
await dbQuery(deleteQuery);
}
const maxUnassignedUploadAge = 24 * 60 * 60 * 1000;
async function deleteUnassignedUploads(): Promise<void> {
const oldestUnassignedUploadToKeep = Date.now() - maxUnassignedUploadAge;
await dbQuery(SQL`
DELETE u, i
FROM uploads u
LEFT JOIN ids i ON i.id = u.id
WHERE u.container IS NULL
+ AND u.user_container IS NULL
AND creation_time < ${oldestUnassignedUploadToKeep}
`);
}
export { deleteUpload, deleteUnassignedUploads };
File Metadata
Details
Attached
Mime Type
text/x-diff
Expires
Sat, Nov 23, 2:20 AM (1 d, 4 h)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
2559373
Default Alt Text
(7 KB)
Attached To
Mode
rCOMM Comm
Attached
Detach File
Event Timeline
Log In to Comment