cli icon indicating copy to clipboard operation
cli copied to clipboard

Unable to include the same component file in preDestructiveChanges.xml and package.xml

Open filiprafalowicz opened this issue 11 months ago • 4 comments

Summary

When attempting to delete and re-deploy the same component as part of a single deployment, component is included only in the preDestructiveChanges.xml file.

This scenario should be valid and is useful, when we want to change what value set picklist field uses when we accidentally deployed the field with wrong value set. If we try to deploy field with changed value set we get following error: Cannot change which global value set this picklist uses.. However if we delete the field first and then deploy it again, we will not get any errors.

Steps To Reproduce

  1. Create following files: force-app/main/default/globalValueSets/Value_Set_1.globalValueSet-meta.xml
<?xml version="1.0" encoding="UTF-8"?>
<GlobalValueSet xmlns="http://soap.sforce.com/2006/04/metadata">
    <customValue>
        <fullName>Value 1</fullName>
        <default>false</default>
        <label>Value 1</label>
    </customValue>
    <customValue>
        <fullName>Value 2</fullName>
        <default>false</default>
        <label>Value 2</label>
    </customValue>
    <customValue>
        <fullName>Value 3</fullName>
        <default>false</default>
        <label>Value 3</label>
    </customValue>
    <masterLabel>Value Set 1</masterLabel>
    <sorted>false</sorted>
</GlobalValueSet>

force-app/main/default/globalValueSets/Value_Set_2.globalValueSet-meta.xml

<?xml version="1.0" encoding="UTF-8"?>
<GlobalValueSet xmlns="http://soap.sforce.com/2006/04/metadata">
    <customValue>
        <fullName>Value 4</fullName>
        <default>false</default>
        <label>Value 4</label>
    </customValue>
    <customValue>
        <fullName>Value 5</fullName>
        <default>false</default>
        <label>Value 5</label>
    </customValue>
    <customValue>
        <fullName>Value 6</fullName>
        <default>false</default>
        <label>Value 6</label>
    </customValue>
    <masterLabel>Value Set 2</masterLabel>
    <sorted>false</sorted>
</GlobalValueSet>

force-app/main/default/objects/Account/fields/My_Picklist__c.field-meta.xml

<?xml version="1.0" encoding="UTF-8" ?>
<CustomField xmlns="http://soap.sforce.com/2006/04/metadata">
    <fullName>My_Picklist__c</fullName>
    <externalId>false</externalId>
    <label>My Picklist</label>
    <required>false</required>
    <trackFeedHistory>false</trackFeedHistory>
    <trackHistory>false</trackHistory>
    <type>Picklist</type>
    <valueSet>
        <restricted>true</restricted>
        <valueSetName>Value_Set_1</valueSetName>
    </valueSet>
</CustomField>
  1. Deploy provided files to the org.
  2. Update force-app/main/default/objects/Account/fields/My_Picklist__c.field-meta.xml to use Value_Set_2.
  3. Try to deploy the field and see Cannot change which global value set this picklist uses. error.
  4. Create following manifest files: preDestructiveChanges.xml
<?xml version="1.0" encoding="UTF-8" ?>
<Package xmlns="http://soap.sforce.com/2006/04/metadata">
    <types>
        <members>Account.My_Picklist__c</members>
        <name>CustomField</name>
    </types>
    <version>60.0</version>
</Package>

package.xml

<?xml version="1.0" encoding="UTF-8" ?>
<Package xmlns="http://soap.sforce.com/2006/04/metadata">
    <types>
        <members>Account.My_Picklist__c</members>
        <name>CustomField</name>
    </types>
    <version>60.0</version>
</Package>
  1. Run following CLI command: SF_MDAPI_TEMP_DIR=mdapiout sf project deploy start --dry-run --pre-destructive-changes preDestructiveChanges.xml --manifest package.xml

Expected result

  1. Package generated in mdapiout should have Account.My_Picklist__c field included in the objects/Account.object file.
  2. Package generated in mdapiout should have Account.My_Picklist__c field included in the package.xml file.

Actual result

  1. Package generated in mdapiout does has only destructiveChangesPre.xml and package.xml files without any metadata components.
  2. Package generated in mdapiout has empty package.xml file.

System Information

{
  "architecture": "darwin-x64",
  "cliVersion": "@salesforce/cli/2.30.8",
  "nodeVersion": "node-v18.16.1",
  "osVersion": "Darwin 22.6.0",
  "rootPath": "/Users/filiprafalowicz/.nvm/versions/node/v18.16.1/lib/node_modules/@salesforce/cli",
  "shell": "bash",
  "pluginVersions": [
    "@oclif/plugin-autocomplete 3.0.9 (core)",
    "@oclif/plugin-commands 3.1.4 (core)",
    "@oclif/plugin-help 6.0.13 (core)",
    "@oclif/plugin-not-found 3.0.11 (core)",
    "@oclif/plugin-plugins 4.2.5 (core)",
    "@oclif/plugin-search 1.0.16 (core)",
    "@oclif/plugin-update 4.1.13 (core)",
    "@oclif/plugin-version 2.0.12 (core)",
    "@oclif/plugin-warn-if-update-available 3.0.12 (core)",
    "@oclif/plugin-which 3.1.0 (core)",
    "@salesforce/cli 2.30.8 (core)",
    "apex 3.0.25 (core)",
    "auth 3.3.13 (core)",
    "data 3.1.1 (core)",
    "deploy-retrieve 3.2.16 (core)",
    "dev 1.1.8 (user)",
    "info 3.0.27 (core)",
    "limits 3.1.10 (core)",
    "marketplace 1.0.25 (core)",
    "org 3.3.14 (core)",
    "packaging 2.1.10 (core)",
    "schema 3.1.3 (core)",
    "settings 2.0.27 (core)",
    "signups 1.4.31 (user)",
    "sobject 1.1.13 (core)",
    "source 3.1.15 (core)",
    "telemetry 3.1.13 (core)",
    "templates 56.0.16 (core)",
    "trust 3.3.10 (core)",
    "user 3.2.11 (core)",
    "@salesforce/sfdx-scanner 3.18.0 (user)",
    "lightning-flow-scanner 2.17.0 (user)",
    "sfdmu 4.30.0 (user)",
    "sfdx-git-delta 5.27.0 (user)"
  ]
}

filiprafalowicz avatar Mar 09 '24 17:03 filiprafalowicz

Thank you for filing this issue. We appreciate your feedback and will review the issue as soon as possible. Remember, however, that GitHub isn't a mechanism for receiving support under any agreement or SLA. If you require immediate assistance, contact Salesforce Customer Support.

github-actions[bot] avatar Mar 09 '24 17:03 github-actions[bot]

Thanks for the detailed report! This behavior was done intentionally because we couldn't think of a case where this would be desired, and if you really wanted to do it you could just run 2 commands; first to delete it, followed by the deploy. However, it's a valid action and it should be possible to support it.

shetzel avatar Mar 12 '24 04:03 shetzel

This issue has been linked to a new work item: W-15231435

git2gus[bot] avatar Mar 12 '24 04:03 git2gus[bot]

Thanks for the detailed report! This behavior was done intentionally because we couldn't think of a case where this would be desired, and if you really wanted to do it you could just run 2 commands; first to delete it, followed by the deploy. However, it's a valid action and it should be possible to support it.

Glad to hear this is going to be supported.

In the past we've had to use this trick to deploy something. I don't recall the exact details now but it had something to do with a Visualforce component, an Apex controller for that component and an email template referencing that Visualforce component. We were trying to change some property on the controller but the dependency on the VF component and/or email template was resulting in some kind of deployment error, even when we included all the components in the package.xml manifest for deployment.

The workaround was the use destructiveChangesPre.xml to remove those components, in that pre deployment phase and then have the package.xml redeploy the newer version of the components and this resulted in a single atomic deployment, rather than having to split it into 2 deployment operations (delete and deploy).

alan-morey avatar Mar 12 '24 18:03 alan-morey

Fixed in version 2.35.6.

jshackell-sfdc avatar Apr 03 '24 18:04 jshackell-sfdc