Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

W-16273581 fix: manifests for custom object can omit parent #1375

Merged
merged 9 commits into from
Aug 1, 2024

Conversation

mshanemc
Copy link
Contributor

@mshanemc mshanemc commented Jul 25, 2024

What does this PR do?

deploy -d of an entire folder including a blank CustomObject file causes the Object to be in the manifest.

Case 1: If the Object is in the manifest, the mdapi will validate that the Object metadata contains all the required fields.

Case 2: If the Object is not in the manifest (only one or more of its child types are) then the validation doesn't happen (only the child types are validated)

SDR, when generating the manifest, needs to ask if the top-level (ex: object.meta.xml) is effectively empty. If so, that type should be omitted from the manifest (to get Case 2 behavior from the API)

other changes

update some tests that were based on an invalid mock
update the workflow preset to make all children of workflow unaddressable

What issues does this PR fix or reference?

@W-16273581@ (see inv)

@mshanemc mshanemc requested a review from a team as a code owner July 25, 2024 15:32
@mshanemc mshanemc changed the title Sm/manifests-for-custom-object-no-parent fix: manifests for custom object can omit parent Jul 25, 2024
? fullName.split('.')[1]
: fullName
);
const type = this.registry.getTypeByName(typeId);

// Add children
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

the children are always added. the parent might or might not be depending on if it has content.

doing the children first lets the parent conditionally return early

@@ -750,3 +737,28 @@ const splitOnFirstDelimiter = (input: string): [string, string] => {
const indexOfSplitChar = input.indexOf(KEY_DELIMITER);
return [input.substring(0, indexOfSplitChar), input.substring(indexOfSplitChar + 1)];
};

/** side effect: mutates the typeMap property */
const addToTypeMap = ({
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this code is simplified and now uses a set instead of an array

@@ -199,19 +199,3 @@ const getXmlFromCache =
}
return xmlCache.get(key) ?? {};
};

/** composed function, exported from module for test */
export const unwrapAndOmitNS =
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

moved for easier sharing

@@ -34,11 +40,9 @@ export const DECOMPOSED_VIRTUAL_FS: VirtualDirectory[] = [
name: DECOMPOSED_XML_NAME,
data: Buffer.from(`<CustomObject xmlns="${XML_NS_URL}"><fullName>customObject__c</fullName></CustomObject>`),
},
{
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think it should be
objects/CustomObject__c/Fields__c.field-meta.xml

@@ -51,11 +55,11 @@ export const DECOMPOSED_VIRTUAL_FS: VirtualDirectory[] = [
],
},
{
dirPath: 'fields',
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this didn't have the relative path, just the last segment

@@ -0,0 +1,91 @@
/*
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

copy of the existing one, but has no "real" content in the CustomObject

@@ -370,7 +370,9 @@ describe('SourceComponent', () => {
);

it('should return child components for a component', () => {
expect(decomposed.DECOMPOSED_COMPONENT.getChildren()).to.deep.equal([expectedChild, expectedChild2]);
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

order changed

@iowillhoit
Copy link
Contributor

iowillhoit commented Jul 31, 2024

QA NOTES

Steps to repro

  • Create an empty project
  • Create a scratch org
  • Open the org
  • Create a Custom Object
  • Create a custom field for that object
  • Retrieve with manifest
<?xml version="1.0" encoding="UTF-8"?>
<Package xmlns="http://soap.sforce.com/2006/04/metadata">
    <types>
        <members>Cat__c.Legs__c</members>
        <name>CustomField</name>
    </types>
    <version>61.0</version>
</Package>
  • Deploy with --source-dir force-app

  • See error Error Cat__c Must specify a non-empty label for the CustomObject

  • 🟢 As described, seeing error before changes

  • 🟢 After changes, able to deploy with an empty parent (Cat__c)

  • 🟢 Works with multiple different children specified (CustomField and Layout)

<types>
    <members>Cat__c-Cat Layout</members>
     <name>Layout</name>
</types>
  • 🟡 NIT: The number of components in the status is briefly incorrect (2/2)
    • During: Status: In Progress | ████████████████████████████████████████ | 2/2 Components
    • After: Status: Succeeded | ████████████████████████████████████████ | 1/1 Components

@iowillhoit
Copy link
Contributor

QA UPDATE

  • 🟢 JSON output looks good
  • 🟢 Played around with this with custom source behavior and did not see any issues.
  • 🟡 I am not sure if this is something we want to address, might be best to just say "Don't do this".
    • When I retrieve a CustomField via a manifest, it gets the CustomField and the empty CustomObject.
    • If I delete the empty CustomObject, it shows up as a deleted in source tracking
    • Deploying that delete does nothing in the org
    • If I delete the empty CustomObject and then reset tracking, I can still deploy changes to the CustomField (without its empty parent metadata file).
    • Do we want to ignore (commit) an "empty parent" deletion in STL so that it could be removed without being tracked as a delete?

@iowillhoit iowillhoit merged commit 8fd9c9e into main Aug 1, 2024
74 checks passed
@iowillhoit iowillhoit deleted the sm/manifests-for-custom-object-no-parent branch August 1, 2024 18:11
@iowillhoit iowillhoit changed the title fix: manifests for custom object can omit parent W-16273581 fix: manifests for custom object can omit parent Jan 27, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants