Skip to content

Commit

Permalink
fix: quick-action-definition (#590)
Browse files Browse the repository at this point in the history
* refactor: simplify logger and maxRevision

* fix: quickActionDefinition isn't a real mdtype

* refactor: use newer error

* test: update for logger refactor

* chore: bump deps for xnuts

* Update remoteSourceTrackingService.ts

link to WI assigned to Platform Actions

* chore: bump deps

---------

Co-authored-by: Cristian Dominguez <[email protected]>
  • Loading branch information
mshanemc and cristiand391 authored May 23, 2024
1 parent bde6cfc commit 73228f3
Show file tree
Hide file tree
Showing 4 changed files with 65 additions and 93 deletions.
6 changes: 3 additions & 3 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -50,9 +50,9 @@
},
"dependencies": {
"@oclif/core": "^3.26.6",
"@salesforce/core": "^7.3.8",
"@salesforce/core": "^7.3.9",
"@salesforce/kit": "^3.1.1",
"@salesforce/source-deploy-retrieve": "^11.4.4",
"@salesforce/source-deploy-retrieve": "^11.6.1",
"@salesforce/ts-types": "^2.0.9",
"fast-xml-parser": "^4.3.6",
"graceful-fs": "^4.2.11",
Expand All @@ -63,7 +63,7 @@
"@salesforce/cli-plugins-testkit": "^5.3.4",
"@salesforce/dev-scripts": "^9.1.2",
"@types/graceful-fs": "^4.1.9",
"eslint-plugin-sf-plugin": "^1.18.3",
"eslint-plugin-sf-plugin": "^1.18.4",
"ts-node": "^10.9.2",
"ts-patch": "^3.1.2",
"typescript": "^5.4.5"
Expand Down
83 changes: 40 additions & 43 deletions src/shared/remoteSourceTrackingService.ts
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ export type Contents = {
sourceMembers: Record<string, MemberRevision>;
};
type MemberRevisionMapEntry = [string, MemberRevision];
type PinoLogger = ReturnType<(typeof Logger)['getRawRootLogger']>;

const FILENAME = 'maxRevision.json';

Expand Down Expand Up @@ -88,7 +89,7 @@ export class RemoteSourceTrackingService {
private static instanceMap = new Map<string, RemoteSourceTrackingService>();
public readonly filePath: string;

private logger!: Logger;
private logger!: PinoLogger;
private serverMaxRevisionCounter = 0;
private sourceMembers = new Map<string, MemberRevision>();

Expand Down Expand Up @@ -146,10 +147,8 @@ export class RemoteSourceTrackingService {
if (elements.length === 0) {
return;
}
const quiet = elements.length > 100;
if (quiet) {
this.logger.debug(`Syncing ${elements.length} Revisions by key`);
}
const quietLogger = elements.length > 100 ? this.logger.silent : this.logger.debug;
quietLogger(`Syncing ${elements.length} Revisions by key`);

// this can be super-repetitive on a large ExperienceBundle where there is an element for each file but only one Revision for the entire bundle
// any item in an aura/LWC bundle needs to represent the top (bundle) level and the file itself
Expand All @@ -159,11 +158,9 @@ export class RemoteSourceTrackingService {
if (!revision) {
this.logger.warn(`found no matching revision for ${metadataKey}`);
} else if (doesNotMatchServer(revision)) {
if (!quiet) {
this.logger.debug(
`Syncing ${metadataKey} revision from ${revision.lastRetrievedFromServer} to ${revision.serverRevisionCounter}`
);
}
quietLogger(
`Syncing ${metadataKey} revision from ${revision.lastRetrievedFromServer} to ${revision.serverRevisionCounter}`
);
this.setMemberRevision(metadataKey, { ...revision, lastRetrievedFromServer: revision.serverRevisionCounter });
}
});
Expand Down Expand Up @@ -377,13 +374,17 @@ ${formatSourceMemberWarnings(outstandingSourceMembers)}`
if (sourceMembers.length === 0) {
return;
}
const quiet = sourceMembers.length > 100;
if (quiet) {
this.logger.debug(`Upserting ${sourceMembers.length} SourceMembers to maxRevision.json`);
}
const quietLogger = sourceMembers.length > 100 ? this.logger.silent : this.logger.debug;
quietLogger(`Upserting ${sourceMembers.length} SourceMembers to maxRevision.json`);

let serverMaxRevisionCounter = this.serverMaxRevisionCounter;
sourceMembers.forEach((change) => {
// Update the serverMaxRevisionCounter to the highest RevisionCounter
this.serverMaxRevisionCounter = Math.max(
this.serverMaxRevisionCounter,
...sourceMembers.map((m) => m.RevisionCounter)
);
this.logger.debug(`Updating serverMaxRevisionCounter to ${this.serverMaxRevisionCounter}`);

sourceMembers.map((change) => {
// try accessing the sourceMembers object at the index of the change's name
// if it exists, we'll update the fields - if it doesn't, we'll create and insert it
const key = getMetadataKey(change.MemberType, change.MemberName);
Expand All @@ -395,35 +396,23 @@ ${formatSourceMemberWarnings(outstandingSourceMembers)}`
};
if (sourceMember.lastRetrievedFromServer) {
// We are already tracking this element so we'll update it
if (!quiet) {
this.logger.debug(
`Updating ${key} to RevisionCounter: ${change.RevisionCounter}${sync ? ' and syncing' : ''}`
);
}
quietLogger(`Updating ${key} to RevisionCounter: ${change.RevisionCounter}${sync ? ' and syncing' : ''}`);
sourceMember.serverRevisionCounter = change.RevisionCounter;
sourceMember.isNameObsolete = change.IsNameObsolete;
} else if (!quiet) {
} else {
// We are not yet tracking it so we'll insert a new record
this.logger.debug(
`Inserting ${key} with RevisionCounter: ${change.RevisionCounter}${sync ? ' and syncing' : ''}`
);
quietLogger(`Inserting ${key} with RevisionCounter: ${change.RevisionCounter}${sync ? ' and syncing' : ''}`);
}

// If we are syncing changes then we need to update the lastRetrievedFromServer field to
// match the RevisionCounter from the SourceMember.
if (sync) {
sourceMember.lastRetrievedFromServer = change.RevisionCounter;
}
// Keep track of the highest RevisionCounter for setting the serverMaxRevisionCounter
if (change.RevisionCounter > serverMaxRevisionCounter) {
serverMaxRevisionCounter = change.RevisionCounter;
}

// Update the state with the latest SourceMember data
this.setMemberRevision(key, sourceMember);
});
// Update the serverMaxRevisionCounter to the highest RevisionCounter
this.serverMaxRevisionCounter = serverMaxRevisionCounter;
this.logger.debug(`Updating serverMaxRevisionCounter to ${serverMaxRevisionCounter}`);

await this.write();
}
Expand All @@ -435,7 +424,7 @@ ${formatSourceMemberWarnings(outstandingSourceMembers)}`
const messages = Messages.loadMessages('@salesforce/source-tracking', 'source');
throw new SfError(messages.getMessage('NonSourceTrackedOrgError'), 'NonSourceTrackedOrgError');
}
this.logger = await Logger.child(this.constructor.name);
this.logger = Logger.getRawRootLogger().child({ name: this.constructor.name });
if (fs.existsSync(this.filePath)) {
// read the file contents and turn it into the map
const rawContents = await readFileContents(this.filePath);
Expand Down Expand Up @@ -486,9 +475,7 @@ ${formatSourceMemberWarnings(outstandingSourceMembers)}`

// because `serverMaxRevisionCounter` is always updated, we need to select > to catch the most recent change
const query = `SELECT MemberType, MemberName, IsNameObsolete, RevisionCounter FROM SourceMember WHERE RevisionCounter > ${rev}`;
if (!quiet) {
this.logger.debug(`Query: ${query}`);
}
this.logger[quiet ? 'silent' : 'debug'](`Query: ${query}`);
const queryResult = await queryFn(this.org.getConnection(), query);
this.queryCache.set(rev, queryResult);

Expand Down Expand Up @@ -536,15 +523,15 @@ const revisionToRemoteChangeElement = ([memberKey, memberRevision]: MemberRevisi
* iterate SourceMember keys and compare their decoded value with the decoded key.
* if there's a match, return the matching decoded key, otherwise, return the original key
*/
function getDecodedKeyIfSourceMembersHas({
const getDecodedKeyIfSourceMembersHas = ({
key,
sourceMembers,
logger,
}: {
sourceMembers: Map<string, MemberRevision>;
key: string;
logger: Logger;
}): string {
logger: PinoLogger;
}): string => {
try {
const originalKeyDecoded = decodeURIComponent(key);
const match = Array.from(sourceMembers.keys()).find(
Expand All @@ -560,7 +547,7 @@ function getDecodedKeyIfSourceMembersHas({
logger.debug(`Could not decode metadata key: ${key} due to: ${errMsg}`);
}
return key;
}
};

const getFilePath = (orgId: string): string => path.join('.sf', 'orgs', orgId, FILENAME);

Expand All @@ -579,7 +566,7 @@ const readFileContents = async (filePath: string): Promise<Contents | Record<str
};

export const calculateTimeout =
(logger: Logger) =>
(logger: PinoLogger) =>
(memberCount: number): Duration => {
const overriddenTimeout = env.getNumber('SFDX_SOURCE_MEMBER_POLLING_TIMEOUT', 0);
if (overriddenTimeout > 0) {
Expand All @@ -603,9 +590,11 @@ export const querySourceMembersTo = async (conn: Connection, toRevision: number)

const queryFn = async (conn: Connection, query: string): Promise<SourceMember[]> => {
try {
return (await conn.tooling.query<SourceMember>(query, { autoFetch: true, maxFetch: 50_000 })).records;
return (await conn.tooling.query<SourceMember>(query, { autoFetch: true, maxFetch: 50_000 })).records.map(
sourceMemberCorrections
);
} catch (error) {
throw error instanceof Error ? SfError.wrap(error) : error;
throw SfError.wrap(error);
}
};

Expand All @@ -625,3 +614,11 @@ const revisionDoesNotMatch = ([, member]: MemberRevisionMapEntry): boolean => do

const doesNotMatchServer = (member: MemberRevision): boolean =>
member.serverRevisionCounter !== member.lastRetrievedFromServer;

/** A series of workarounds for server-side bugs. Each bug should be filed against a team, with a WI, so we know when these are fixed and can be removed */
const sourceMemberCorrections = (sourceMember: SourceMember): SourceMember => {
if (sourceMember.MemberType === 'QuickActionDefinition') {
return { ...sourceMember, MemberType: 'QuickAction' }; // W-15837125
}
return sourceMember;
};
2 changes: 1 addition & 1 deletion test/unit/remoteSourceTracking.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -584,7 +584,7 @@ describe('remoteSourceTrackingService', () => {
});

describe('calculateTimeout', () => {
const logger = new Logger({ useMemoryLogger: true, name: 'test' });
const logger = new Logger({ useMemoryLogger: true, name: 'test' }).getRawLogger();
const functionUnderTest = calculateTimeout(logger);
afterEach(() => {
delete process.env.SFDX_SOURCE_MEMBER_POLLING_TIMEOUT;
Expand Down
67 changes: 21 additions & 46 deletions yarn.lock
Original file line number Diff line number Diff line change
Expand Up @@ -598,14 +598,14 @@
strip-ansi "6.0.1"
ts-retry-promise "^0.8.0"

"@salesforce/core@^7.3.1", "@salesforce/core@^7.3.5", "@salesforce/core@^7.3.8":
version "7.3.8"
resolved "https://registry.yarnpkg.com/@salesforce/core/-/core-7.3.8.tgz#8a646b5321f08c0fb4d22e2fa8b1d60b3a20df9b"
integrity sha512-VWhXHfjwjtC3pJWYp8wt5/fnNQ5tK61ovMG5eteXzVD2oFd7og1f6YjwuAzoYIZK7kYWWv7KJfGtCsPs7Zw+Ww==
"@salesforce/core@^7.3.5", "@salesforce/core@^7.3.8", "@salesforce/core@^7.3.9":
version "7.3.9"
resolved "https://registry.yarnpkg.com/@salesforce/core/-/core-7.3.9.tgz#8abe2b3e2393989d11e92b7a6b96043fc9d5b9c8"
integrity sha512-eJqDiA5b7wU50Ee/xjmGzSnHrNVJ8S77B7enfX30gm7gxU3i3M3QeBdiV6XAOPLSIL96DseofP6Tv6c+rljlKA==
dependencies:
"@jsforce/jsforce-node" "^3.2.0"
"@salesforce/kit" "^3.1.1"
"@salesforce/schemas" "^1.7.0"
"@salesforce/schemas" "^1.9.0"
"@salesforce/ts-types" "^2.0.9"
ajv "^8.13.0"
change-case "^4.1.2"
Expand Down Expand Up @@ -671,15 +671,15 @@
resolved "https://registry.yarnpkg.com/@salesforce/prettier-config/-/prettier-config-0.0.3.tgz#ba648d4886bb38adabe073dbea0b3a91b3753bb0"
integrity sha512-hYOhoPTCSYMDYn+U1rlEk16PoBeAJPkrdg4/UtAzupM1mRRJOwEPMG1d7U8DxJFKuXW3DMEYWr2MwAIBDaHmFg==

"@salesforce/schemas@^1.7.0":
version "1.7.0"
resolved "https://registry.yarnpkg.com/@salesforce/schemas/-/schemas-1.7.0.tgz#b7e0af3ee414ae7160bce351c0184d77ccb98fe3"
integrity sha512-Z0PiCEV55khm0PG+DsnRYCjaDmacNe3HDmsoSm/CSyYvJJm+D5vvkHKN9/PKD/gaRe8XAU836yfamIYFblLINw==
"@salesforce/schemas@^1.9.0":
version "1.9.0"
resolved "https://registry.yarnpkg.com/@salesforce/schemas/-/schemas-1.9.0.tgz#ba477a112653a20b4edcf989c61c57bdff9aa3ca"
integrity sha512-LiN37zG5ODT6z70sL1fxF7BQwtCX9JOWofSU8iliSNIM+WDEeinnoFtVqPInRSNt8I0RiJxIKCrqstsmQRBNvA==

"@salesforce/source-deploy-retrieve@^11.4.4":
version "11.4.4"
resolved "https://registry.yarnpkg.com/@salesforce/source-deploy-retrieve/-/source-deploy-retrieve-11.4.4.tgz#c853e0888c6a5b64c4af3e705010ef1a6dac4c13"
integrity sha512-6dohRR9t6Aj2mbHzfYtbphxqxF83AwmAjkFFQPB6+Yn1ceVKmJjd0WY23fgWTTaTum+2pnw9XA35qwu4naBCVw==
"@salesforce/source-deploy-retrieve@^11.6.1":
version "11.6.1"
resolved "https://registry.yarnpkg.com/@salesforce/source-deploy-retrieve/-/source-deploy-retrieve-11.6.1.tgz#381d7ecb41025fee71db32e765b8fbf434255a4d"
integrity sha512-7v52S871V0fzIABxWmcvbI4iELTAyniiBM0+HHAvwO2rGclULKIf4IgkomL4l4Hz4BPd2v0fRlLJ4INkG/3+sA==
dependencies:
"@salesforce/core" "^7.3.5"
"@salesforce/kit" "^3.1.1"
Expand Down Expand Up @@ -2238,12 +2238,12 @@ eslint-plugin-jsdoc@^46.10.1:
semver "^7.5.4"
spdx-expression-parse "^4.0.0"

eslint-plugin-sf-plugin@^1.18.3:
version "1.18.3"
resolved "https://registry.yarnpkg.com/eslint-plugin-sf-plugin/-/eslint-plugin-sf-plugin-1.18.3.tgz#8711ba1544e86fb8227375415865fca2c3566348"
integrity sha512-Cl2ZpraMOwOm/kDn2hlud7mkDH3OrImueAyX8nkX1LA0kFma9/yokdxabWE/uaPpWPUlADeqgKWwgTjgf75SYQ==
eslint-plugin-sf-plugin@^1.18.4:
version "1.18.4"
resolved "https://registry.yarnpkg.com/eslint-plugin-sf-plugin/-/eslint-plugin-sf-plugin-1.18.4.tgz#59a41e224d620e20d0fe0e3902c43208c2629037"
integrity sha512-bPYmEh+5ARunhIfBoHc9UqrvPslRcYcloXJRKWqVkvU8tIBAiq2lqp6GWjVuUMPGjhvtUgICMolp6ozjO9wvmA==
dependencies:
"@salesforce/core" "^7.3.1"
"@salesforce/core" "^7.3.8"
"@typescript-eslint/utils" "^6.17.0"

eslint-plugin-unicorn@^50.0.1:
Expand Down Expand Up @@ -5178,16 +5178,7 @@ srcset@^5.0.0:
resolved "https://registry.yarnpkg.com/srcset/-/srcset-5.0.0.tgz#9df6c3961b5b44a02532ce6ae4544832609e2e3f"
integrity sha512-SqEZaAEhe0A6ETEa9O1IhSPC7MdvehZtCnTR0AftXk3QhY2UNgb+NApFOUPZILXk/YTDfFxMTNJOBpzrJsEdIA==

"string-width-cjs@npm:string-width@^4.2.0":
version "4.2.3"
resolved "https://registry.yarnpkg.com/string-width/-/string-width-4.2.3.tgz#269c7117d27b05ad2e536830a8ec895ef9c6d010"
integrity sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==
dependencies:
emoji-regex "^8.0.0"
is-fullwidth-code-point "^3.0.0"
strip-ansi "^6.0.1"

string-width@^4.0.0, string-width@^4.1.0, string-width@^4.2.0, string-width@^4.2.3:
"string-width-cjs@npm:string-width@^4.2.0", string-width@^4.0.0, string-width@^4.1.0, string-width@^4.2.0, string-width@^4.2.3:
version "4.2.3"
resolved "https://registry.yarnpkg.com/string-width/-/string-width-4.2.3.tgz#269c7117d27b05ad2e536830a8ec895ef9c6d010"
integrity sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==
Expand Down Expand Up @@ -5246,14 +5237,7 @@ string_decoder@~1.1.1:
dependencies:
safe-buffer "~5.1.0"

"strip-ansi-cjs@npm:strip-ansi@^6.0.1":
version "6.0.1"
resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-6.0.1.tgz#9e26c63d30f53443e9489495b2105d37b67a85d9"
integrity sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==
dependencies:
ansi-regex "^5.0.1"

[email protected], strip-ansi@^6.0.0, strip-ansi@^6.0.1:
"strip-ansi-cjs@npm:strip-ansi@^6.0.1", [email protected], strip-ansi@^6.0.0, strip-ansi@^6.0.1:
version "6.0.1"
resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-6.0.1.tgz#9e26c63d30f53443e9489495b2105d37b67a85d9"
integrity sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==
Expand Down Expand Up @@ -5770,7 +5754,7 @@ [email protected]:
resolved "https://registry.yarnpkg.com/workerpool/-/workerpool-6.2.1.tgz#46fc150c17d826b86a008e5a4508656777e9c343"
integrity sha512-ILEIE97kDZvF9Wb9f6h5aXK4swSlKGUcOEGiIYb2OOu/IrDU9iwj0fD//SsA6E5ibwJxpEvhullJY4Sl4GcpAw==

"wrap-ansi-cjs@npm:wrap-ansi@^7.0.0":
"wrap-ansi-cjs@npm:wrap-ansi@^7.0.0", wrap-ansi@^7.0.0:
version "7.0.0"
resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-7.0.0.tgz#67e145cff510a6a6984bdf1152911d69d2eb9e43"
integrity sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==
Expand All @@ -5788,15 +5772,6 @@ wrap-ansi@^6.2.0:
string-width "^4.1.0"
strip-ansi "^6.0.0"

wrap-ansi@^7.0.0:
version "7.0.0"
resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-7.0.0.tgz#67e145cff510a6a6984bdf1152911d69d2eb9e43"
integrity sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==
dependencies:
ansi-styles "^4.0.0"
string-width "^4.1.0"
strip-ansi "^6.0.0"

wrap-ansi@^8.1.0:
version "8.1.0"
resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-8.1.0.tgz#56dc22368ee570face1b49819975d9b9a5ead214"
Expand Down

0 comments on commit 73228f3

Please sign in to comment.